diff --git a/coolamqp/__init__.py b/coolamqp/__init__.py
index 955cb63b74128c1201b505e06bf6372b4f688040..09e082214690cacdfe7243b72f6bb09bce711a7a 100644
--- a/coolamqp/__init__.py
+++ b/coolamqp/__init__.py
@@ -1 +1 @@
-__version__ = '1.4.4a1'
+__version__ = '1.5.0a1'
diff --git a/coolamqp/clustering/cluster.py b/coolamqp/clustering/cluster.py
index 80e5864427bd68f5c2b5988631489b7cc8e639ea..a3ec6e8582d405a74b7e9ee11a4e76431ed1b76b 100644
--- a/coolamqp/clustering/cluster.py
+++ b/coolamqp/clustering/cluster.py
@@ -348,6 +348,13 @@ class Cluster(object):
                     raise ConnectionDead(
                         '[%s] Could not connect within %s seconds' % (self.name, timeout,))
 
+    @property
+    def properties(self):
+        """
+        Return a :class:`coolamqp.object.ServerProperties` if a connection was established
+        """
+        return self.snr.properties
+
     def shutdown(self, wait=True):  # type: (bool) -> None
         """
         Terminate all connections, release resources - finish the job.
diff --git a/coolamqp/clustering/single.py b/coolamqp/clustering/single.py
index cc86b45a28e7c7c924b162b084484d4f9879aaa7..1c856da672982b3ddd0f2604da30caa6ea5a7e32 100644
--- a/coolamqp/clustering/single.py
+++ b/coolamqp/clustering/single.py
@@ -18,6 +18,10 @@ class SingleNodeReconnector(object):
     Connection to one node. It will do it's best to remain alive.
     """
 
+    @property
+    def properties(self):
+        return self.connection.properties
+
     def __init__(self, node_def,  # type: coolamqp.objects.NodeDefinition
                  attache_group,  # type: coolamqp.attaches.AttacheGroup
                  listener_thread,  # type: coolamqp.uplink.ListenerThread
diff --git a/coolamqp/objects.py b/coolamqp/objects.py
index 675f7416778545fa91a7f9a2900ca4e56b3c39cd..eb6731d1bc2d4658705a259d1299f58eef042c1c 100644
--- a/coolamqp/objects.py
+++ b/coolamqp/objects.py
@@ -10,7 +10,6 @@ import warnings
 
 import six
 
-from coolamqp.framing.base import AMQPFrame
 from coolamqp.framing.definitions import \
     BasicContentPropertyList as MessageProperties
 from coolamqp.framing.field_table import get_type_for
@@ -232,6 +231,37 @@ class Exchange(object):
 Exchange.direct = Exchange()
 
 
+
+class ServerProperties(object):
+    """
+    An object describing properties of the target server.
+
+    :ivar version: tuple of (major version, minor version)
+    :ivar properties: dictionary of properties (key str, value any)
+    :ivar mechanisms: a list of strings, supported auth mechanisms
+    :ivar locales: locale in use
+    """
+
+    __slots__ = ('version', 'properties', 'mechanisms', 'locales')
+
+    def __init__(self, data):
+        self.version = data.version_major, data.version_minor
+        self.properties = {}
+        for prop_name, prop_value in data.server_properties:
+            prop_name = toutf8(prop_name)
+            prop_value = prop_value[0]
+            if isinstance(prop_value, memoryview):
+                prop_value = prop_value.tobytes().decode('utf-8')
+            elif isinstance(prop_value, list):
+                prop_value = [toutf8(prop[0]) for prop in prop_value]
+            self.properties[prop_name] = prop_value
+        self.mechanisms = data.mechanisms.tobytes().decode('utf-8').split(' ')
+        self.locales = data.locales.tobytes().decode('utf-8')
+
+    def __str__(self):
+        return '%s %s %s %s' % (self.version, repr(self.properties), self.mechanisms, self.locales)
+
+
 class Queue(object):
     """
     This object represents a Queue that applications consume from or publish to.
diff --git a/coolamqp/uplink/connection/connection.py b/coolamqp/uplink/connection/connection.py
index bc157f117b765db7ad14049ca1d0ac9fadf9e225..0974f5cf876993f70ea46bdd7f81961ed42c5043 100644
--- a/coolamqp/uplink/connection/connection.py
+++ b/coolamqp/uplink/connection/connection.py
@@ -119,6 +119,7 @@ class Connection(object):
         self.frame_max = None
         self.heartbeat = None
         self.extensions = []
+        self.properties = None
 
         # To be filled in later
         self.listener_socket = None
diff --git a/coolamqp/uplink/handshake.py b/coolamqp/uplink/handshake.py
index acfb3b7c230f690c43b6481c73ee9712dbdf9acb..99d99bbfc7e2bfc67fcadd5c15b38b4dd59b858d 100644
--- a/coolamqp/uplink/handshake.py
+++ b/coolamqp/uplink/handshake.py
@@ -13,6 +13,8 @@ from coolamqp.framing.definitions import ConnectionStart, ConnectionStartOk, \
 from coolamqp.framing.frames import AMQPMethodFrame
 from coolamqp.uplink.connection.states import ST_ONLINE
 from coolamqp.uplink.heartbeat import Heartbeater
+from coolamqp.objects import ServerProperties
+
 from coolamqp import __version__
 
 PUBLISHER_CONFIRMS = b'publisher_confirms'
@@ -100,7 +102,7 @@ class Handshaker(object):
                 if label in SUPPORTED_EXTENSIONS:
                     if fv[0]:
                         self.connection.extensions.append(label)
-
+        self.connection.properties = ServerProperties(payload)
         self.connection.watchdog(WATCHDOG_TIMEOUT, self.on_watchdog)
         self.connection.watch_for_method(0, ConnectionTune,
                                          self.on_connection_tune)
diff --git a/docs/basics.rst b/docs/basics.rst
index 81c42ac2d899677835244a326d4c51088565b44a..1531b9beda10a3a89a4b7a9b36089d217a0843fb 100644
--- a/docs/basics.rst
+++ b/docs/basics.rst
@@ -34,3 +34,11 @@ Take care, as :class:`~coolamqp.objects.MessageProperties` will hash the
 keys found and store it within non-GCable memory. So each "variant" of message
 properties encountered will be compiled as a separate class.
 
+Who am I talking to?
+--------------------
+
+:class:`coolamqp.clustering.Cluster` has a nice property, that will return None until the connection is established.
+If it is, it will return something like this:
+
+.. autoclass:: coolamqp.objects.ServerProperties
+    :members:
diff --git a/docs/conf.py b/docs/conf.py
index 3c2a143d22cd9bbe5dcc63441041541f2a4e1ee2..29896f768b9948b827dc234c7c95576286d2306a 100644
--- a/docs/conf.py
+++ b/docs/conf.py
@@ -48,7 +48,7 @@ master_doc = 'index'
 
 # General information about the project.
 project = u'CoolAMQP'
-copyright = u'2016-2020, SMOK sp. z o. o.'
+copyright = u'2016-2024, SMOK sp. z o. o.'
 author = u'SMOK sp. z o. o.'
 
 # The version info for the project you're documenting, acts as replacement for
diff --git a/tests/test_clustering/test_a.py b/tests/test_clustering/test_a.py
index 8383c0548cc42a4dce52247fb0a226b30aa9f20c..27f5d69e58d3fe620b7cc85764546fac9d67caf6 100644
--- a/tests/test_clustering/test_a.py
+++ b/tests/test_clustering/test_a.py
@@ -23,11 +23,14 @@ logging.basicConfig(level=logging.DEBUG)
 class TestA(unittest.TestCase):
     def setUp(self):
         self.c = Cluster([NODE])
-        self.c.start()
+        self.c.start(timeout=20)
 
     def tearDown(self):
         self.c.shutdown()
 
+    def test_properties(self):
+        self.assertEqual(self.c.properties.properties['product'], 'RabbitMQ')
+
     def test_queue_bind(self):
         queue = Queue('my-queue')
         exchange = Exchange('my-exchange', type='topic')
diff --git a/tests/test_clustering/test_things.py b/tests/test_clustering/test_things.py
index 98ee35938b1ea30c4a8c490586c97fbe94e362b4..e49fa12b7ddad7d9b0e3bcd81409dc58a1e47636 100644
--- a/tests/test_clustering/test_things.py
+++ b/tests/test_clustering/test_things.py
@@ -77,7 +77,7 @@ class TestConnecting(unittest.TestCase):
 
     def test_start_called_multiple_times(self):
         c = Cluster([NODE])
-        c.start(wait=True)
+        c.start(wait=True, timeout=20)
         self.assertRaises(RuntimeError, lambda: c.start())
         c.shutdown(wait=True)