We are currently solving the following issue within our repository. Here is the issue text:
--- BEGIN ISSUE ---
no type checking with __eq__ in all the graph classes
**Version**: redis-py version 4.4.0 (redis version shouldnt matter but i'm using redis-stack 6.2.4-v3)

**Platform**: python version 3.10.9 (but should effect all versions) on wsl Ubuntu 20.04.5 LTS

**Description**: none of the redis graph classes check the types when checking equality 
```python
import redis.commands.graph as redisGraph
foo = redisGraph.Node()

foo == None # this line causes the error
```
```python 
AttributeError: 'NoneType' object has no attribute 'label'
```
you get the same error when checking against any type that is not a `Node`

it also happens with the `Edge` class
```python
bar = redisGraph.Edge(foo,"",foo)
bar == ""
```
```python
AttributeError: 'str' object has no attribute 'src_node'
```
and also the `Path` class
```python
baz = redisGraph.Path([],[])
baz == 4
```
```python
AttributeError: 'int' object has no attribute 'nodes'
```
i suspect adding this sort of code in would fix it
```python
# Check that the rhs the correct type
if not isinstance(rhs, type(self)):
    return False
```

--- END ISSUE ---

Below are some code segments, each from a relevant file. One or more of these files may contain bugs.
--- BEGIN FILES ---
Path: `redis/commands/graph/edge.py`
Content:
```
1 from ..helpers import quote_string
2 from .node import Node
3 
4 
5 class Edge:
6     """
7     An edge connecting two nodes.
8     """
9 
10     def __init__(self, src_node, relation, dest_node, edge_id=None, properties=None):
11         """
12         Create a new edge.
13         """
14         if src_node is None or dest_node is None:
15             # NOTE(bors-42): It makes sense to change AssertionError to
16             #                ValueError here
17             raise AssertionError("Both src_node & dest_node must be provided")
18 
19         self.id = edge_id
20         self.relation = relation or ""
21         self.properties = properties or {}
22         self.src_node = src_node
23         self.dest_node = dest_node
24 
25     def to_string(self):
26         res = ""
27         if self.properties:
28             props = ",".join(
29                 key + ":" + str(quote_string(val))
30                 for key, val in sorted(self.properties.items())
31             )
32             res += "{" + props + "}"
33 
34         return res
35 
36     def __str__(self):
37         # Source node.
38         if isinstance(self.src_node, Node):
39             res = str(self.src_node)
40         else:
41             res = "()"
42 
43         # Edge
44         res += "-["
45         if self.relation:
46             res += ":" + self.relation
47         if self.properties:
48             props = ",".join(
49                 key + ":" + str(quote_string(val))
50                 for key, val in sorted(self.properties.items())
51             )
52             res += "{" + props + "}"
53         res += "]->"
54 
55         # Dest node.
56         if isinstance(self.dest_node, Node):
57             res += str(self.dest_node)
58         else:
59             res += "()"
60 
61         return res
62 
63     def __eq__(self, rhs):
64         # Quick positive check, if both IDs are set.
65         if self.id is not None and rhs.id is not None and self.id == rhs.id:
66             return True
67 
68         # Source and destination nodes should match.
69         if self.src_node != rhs.src_node:
70             return False
71 
72         if self.dest_node != rhs.dest_node:
73             return False
74 
75         # Relation should match.
76         if self.relation != rhs.relation:
77             return False
78 
79         # Quick check for number of properties.
80         if len(self.properties) != len(rhs.properties):
81             return False
82 
83         # Compare properties.
84         if self.properties != rhs.properties:
85             return False
86 
87         return True
88
```

Path: `redis/commands/graph/path.py`
Content:
```
1 from .edge import Edge
2 from .node import Node
3 
4 
5 class Path:
6     def __init__(self, nodes, edges):
7         if not (isinstance(nodes, list) and isinstance(edges, list)):
8             raise TypeError("nodes and edges must be list")
9 
10         self._nodes = nodes
11         self._edges = edges
12         self.append_type = Node
13 
14     @classmethod
15     def new_empty_path(cls):
16         return cls([], [])
17 
18     def nodes(self):
19         return self._nodes
20 
21     def edges(self):
22         return self._edges
23 
24     def get_node(self, index):
25         return self._nodes[index]
26 
27     def get_relationship(self, index):
28         return self._edges[index]
29 
30     def first_node(self):
31         return self._nodes[0]
32 
33     def last_node(self):
34         return self._nodes[-1]
35 
36     def edge_count(self):
37         return len(self._edges)
38 
39     def nodes_count(self):
40         return len(self._nodes)
41 
42     def add_node(self, node):
43         if not isinstance(node, self.append_type):
44             raise AssertionError("Add Edge before adding Node")
45         self._nodes.append(node)
46         self.append_type = Edge
47         return self
48 
49     def add_edge(self, edge):
50         if not isinstance(edge, self.append_type):
51             raise AssertionError("Add Node before adding Edge")
52         self._edges.append(edge)
53         self.append_type = Node
54         return self
55 
56     def __eq__(self, other):
57         return self.nodes() == other.nodes() and self.edges() == other.edges()
58 
59     def __str__(self):
60         res = "<"
61         edge_count = self.edge_count()
62         for i in range(0, edge_count):
63             node_id = self.get_node(i).id
64             res += "(" + str(node_id) + ")"
65             edge = self.get_relationship(i)
66             res += (
67                 "-[" + str(int(edge.id)) + "]->"
68                 if edge.src_node == node_id
69                 else "<-[" + str(int(edge.id)) + "]-"
70             )
71         node_id = self.get_node(edge_count).id
72         res += "(" + str(node_id) + ")"
73         res += ">"
74         return res
75
```

Path: `redis/commands/graph/node.py`
Content:
```
1 from ..helpers import quote_string
2 
3 
4 class Node:
5     """
6     A node within the graph.
7     """
8 
9     def __init__(self, node_id=None, alias=None, label=None, properties=None):
10         """
11         Create a new node.
12         """
13         self.id = node_id
14         self.alias = alias
15         if isinstance(label, list):
16             label = [inner_label for inner_label in label if inner_label != ""]
17 
18         if (
19             label is None
20             or label == ""
21             or (isinstance(label, list) and len(label) == 0)
22         ):
23             self.label = None
24             self.labels = None
25         elif isinstance(label, str):
26             self.label = label
27             self.labels = [label]
28         elif isinstance(label, list) and all(
29             [isinstance(inner_label, str) for inner_label in label]
30         ):
31             self.label = label[0]
32             self.labels = label
33         else:
34             raise AssertionError(
35                 "label should be either None, string or a list of strings"
36             )
37 
38         self.properties = properties or {}
39 
40     def to_string(self):
41         res = ""
42         if self.properties:
43             props = ",".join(
44                 key + ":" + str(quote_string(val))
45                 for key, val in sorted(self.properties.items())
46             )
47             res += "{" + props + "}"
48 
49         return res
50 
51     def __str__(self):
52         res = "("
53         if self.alias:
54             res += self.alias
55         if self.labels:
56             res += ":" + ":".join(self.labels)
57         if self.properties:
58             props = ",".join(
59                 key + ":" + str(quote_string(val))
60                 for key, val in sorted(self.properties.items())
61             )
62             res += "{" + props + "}"
63         res += ")"
64 
65         return res
66 
67     def __eq__(self, rhs):
68         # Quick positive check, if both IDs are set.
69         if self.id is not None and rhs.id is not None and self.id != rhs.id:
70             return False
71 
72         # Label should match.
73         if self.label != rhs.label:
74             return False
75 
76         # Quick check for number of properties.
77         if len(self.properties) != len(rhs.properties):
78             return False
79 
80         # Compare properties.
81         if self.properties != rhs.properties:
82             return False
83 
84         return True
85
```
--- END FILES ---

Please first localize the bug based on the issue statement, and then generate a patch according to the `git diff` format fenced by three backticks.

Here is an example:

```diff
diff --git a/examples/server_async.py b/examples/server_async.py
--- a/examples/server_async.py
+++ b/examples/server_async.py
@@ -313,4 +313,4 @@
 
 
 if __name__ == "__main__":
-    asyncio.run(run_async_server("."), debug=True)
+    asyncio.run(run_async_server(), debug=True)
diff --git a/examples/server_sync.py b/examples/server_sync.py
--- a/examples/server_sync.py
+++ b/examples/server_sync.py
@@ -313,5 +313,5 @@
 
 
 if __name__ == "__main__":
-    server = run_sync_server(".")
+    server = run_sync_server()
     server.shutdown()

```

diff --git a/redis/commands/graph/edge.py b/redis/commands/graph/edge.py
--- a/redis/commands/graph/edge.py
+++ b/redis/commands/graph/edge.py
@@ -61,6 +61,10 @@
         return res
 
     def __eq__(self, rhs):
+        # Type checking
+        if not isinstance(rhs, Edge):
+            return False
+
         # Quick positive check, if both IDs are set.
         if self.id is not None and rhs.id is not None and self.id == rhs.id:
             return True
diff --git a/redis/commands/graph/node.py b/redis/commands/graph/node.py
--- a/redis/commands/graph/node.py
+++ b/redis/commands/graph/node.py
@@ -65,6 +65,10 @@
         return res
 
     def __eq__(self, rhs):
+        # Type checking
+        if not isinstance(rhs, Node):
+            return False
+
         # Quick positive check, if both IDs are set.
         if self.id is not None and rhs.id is not None and self.id != rhs.id:
             return False
diff --git a/redis/commands/graph/path.py b/redis/commands/graph/path.py
--- a/redis/commands/graph/path.py
+++ b/redis/commands/graph/path.py
@@ -54,6 +54,10 @@
         return self
 
     def __eq__(self, other):
+        # Type checking
+        if not isinstance(other, Path):
+            return False
+
         return self.nodes() == other.nodes() and self.edges() == other.edges()
 
     def __str__(self):

{"golden_diff": "diff --git a/redis/commands/graph/edge.py b/redis/commands/graph/edge.py\n--- a/redis/commands/graph/edge.py\n+++ b/redis/commands/graph/edge.py\n@@ -61,6 +61,10 @@\n         return res\n \n     def __eq__(self, rhs):\n+        # Type checking\n+        if not isinstance(rhs, Edge):\n+            return False\n+\n         # Quick positive check, if both IDs are set.\n         if self.id is not None and rhs.id is not None and self.id == rhs.id:\n             return True\ndiff --git a/redis/commands/graph/node.py b/redis/commands/graph/node.py\n--- a/redis/commands/graph/node.py\n+++ b/redis/commands/graph/node.py\n@@ -65,6 +65,10 @@\n         return res\n \n     def __eq__(self, rhs):\n+        # Type checking\n+        if not isinstance(rhs, Node):\n+            return False\n+\n         # Quick positive check, if both IDs are set.\n         if self.id is not None and rhs.id is not None and self.id != rhs.id:\n             return False\ndiff --git a/redis/commands/graph/path.py b/redis/commands/graph/path.py\n--- a/redis/commands/graph/path.py\n+++ b/redis/commands/graph/path.py\n@@ -54,6 +54,10 @@\n         return self\n \n     def __eq__(self, other):\n+        # Type checking\n+        if not isinstance(other, Path):\n+            return False\n+\n         return self.nodes() == other.nodes() and self.edges() == other.edges()\n \n     def __str__(self):\n", "issue": "no type checking with __eq__ in all the graph classes\n**Version**: redis-py version 4.4.0 (redis version shouldnt matter but i'm using redis-stack 6.2.4-v3)\r\n\r\n**Platform**: python version 3.10.9 (but should effect all versions) on wsl Ubuntu 20.04.5 LTS\r\n\r\n**Description**: none of the redis graph classes check the types when checking equality \r\n```python\r\nimport redis.commands.graph as redisGraph\r\nfoo = redisGraph.Node()\r\n\r\nfoo == None # this line causes the error\r\n```\r\n```python \r\nAttributeError: 'NoneType' object has no attribute 'label'\r\n```\r\nyou get the same error when checking against any type that is not a `Node`\r\n\r\nit also happens with the `Edge` class\r\n```python\r\nbar = redisGraph.Edge(foo,\"\",foo)\r\nbar == \"\"\r\n```\r\n```python\r\nAttributeError: 'str' object has no attribute 'src_node'\r\n```\r\nand also the `Path` class\r\n```python\r\nbaz = redisGraph.Path([],[])\r\nbaz == 4\r\n```\r\n```python\r\nAttributeError: 'int' object has no attribute 'nodes'\r\n```\r\ni suspect adding this sort of code in would fix it\r\n```python\r\n# Check that the rhs the correct type\r\nif not isinstance(rhs, type(self)):\r\n    return False\r\n```\n", "before_files": [{"content": "from ..helpers import quote_string\nfrom .node import Node\n\n\nclass Edge:\n    \"\"\"\n    An edge connecting two nodes.\n    \"\"\"\n\n    def __init__(self, src_node, relation, dest_node, edge_id=None, properties=None):\n        \"\"\"\n        Create a new edge.\n        \"\"\"\n        if src_node is None or dest_node is None:\n            # NOTE(bors-42): It makes sense to change AssertionError to\n            #                ValueError here\n            raise AssertionError(\"Both src_node & dest_node must be provided\")\n\n        self.id = edge_id\n        self.relation = relation or \"\"\n        self.properties = properties or {}\n        self.src_node = src_node\n        self.dest_node = dest_node\n\n    def to_string(self):\n        res = \"\"\n        if self.properties:\n            props = \",\".join(\n                key + \":\" + str(quote_string(val))\n                for key, val in sorted(self.properties.items())\n            )\n            res += \"{\" + props + \"}\"\n\n        return res\n\n    def __str__(self):\n        # Source node.\n        if isinstance(self.src_node, Node):\n            res = str(self.src_node)\n        else:\n            res = \"()\"\n\n        # Edge\n        res += \"-[\"\n        if self.relation:\n            res += \":\" + self.relation\n        if self.properties:\n            props = \",\".join(\n                key + \":\" + str(quote_string(val))\n                for key, val in sorted(self.properties.items())\n            )\n            res += \"{\" + props + \"}\"\n        res += \"]->\"\n\n        # Dest node.\n        if isinstance(self.dest_node, Node):\n            res += str(self.dest_node)\n        else:\n            res += \"()\"\n\n        return res\n\n    def __eq__(self, rhs):\n        # Quick positive check, if both IDs are set.\n        if self.id is not None and rhs.id is not None and self.id == rhs.id:\n            return True\n\n        # Source and destination nodes should match.\n        if self.src_node != rhs.src_node:\n            return False\n\n        if self.dest_node != rhs.dest_node:\n            return False\n\n        # Relation should match.\n        if self.relation != rhs.relation:\n            return False\n\n        # Quick check for number of properties.\n        if len(self.properties) != len(rhs.properties):\n            return False\n\n        # Compare properties.\n        if self.properties != rhs.properties:\n            return False\n\n        return True\n", "path": "redis/commands/graph/edge.py"}, {"content": "from .edge import Edge\nfrom .node import Node\n\n\nclass Path:\n    def __init__(self, nodes, edges):\n        if not (isinstance(nodes, list) and isinstance(edges, list)):\n            raise TypeError(\"nodes and edges must be list\")\n\n        self._nodes = nodes\n        self._edges = edges\n        self.append_type = Node\n\n    @classmethod\n    def new_empty_path(cls):\n        return cls([], [])\n\n    def nodes(self):\n        return self._nodes\n\n    def edges(self):\n        return self._edges\n\n    def get_node(self, index):\n        return self._nodes[index]\n\n    def get_relationship(self, index):\n        return self._edges[index]\n\n    def first_node(self):\n        return self._nodes[0]\n\n    def last_node(self):\n        return self._nodes[-1]\n\n    def edge_count(self):\n        return len(self._edges)\n\n    def nodes_count(self):\n        return len(self._nodes)\n\n    def add_node(self, node):\n        if not isinstance(node, self.append_type):\n            raise AssertionError(\"Add Edge before adding Node\")\n        self._nodes.append(node)\n        self.append_type = Edge\n        return self\n\n    def add_edge(self, edge):\n        if not isinstance(edge, self.append_type):\n            raise AssertionError(\"Add Node before adding Edge\")\n        self._edges.append(edge)\n        self.append_type = Node\n        return self\n\n    def __eq__(self, other):\n        return self.nodes() == other.nodes() and self.edges() == other.edges()\n\n    def __str__(self):\n        res = \"<\"\n        edge_count = self.edge_count()\n        for i in range(0, edge_count):\n            node_id = self.get_node(i).id\n            res += \"(\" + str(node_id) + \")\"\n            edge = self.get_relationship(i)\n            res += (\n                \"-[\" + str(int(edge.id)) + \"]->\"\n                if edge.src_node == node_id\n                else \"<-[\" + str(int(edge.id)) + \"]-\"\n            )\n        node_id = self.get_node(edge_count).id\n        res += \"(\" + str(node_id) + \")\"\n        res += \">\"\n        return res\n", "path": "redis/commands/graph/path.py"}, {"content": "from ..helpers import quote_string\n\n\nclass Node:\n    \"\"\"\n    A node within the graph.\n    \"\"\"\n\n    def __init__(self, node_id=None, alias=None, label=None, properties=None):\n        \"\"\"\n        Create a new node.\n        \"\"\"\n        self.id = node_id\n        self.alias = alias\n        if isinstance(label, list):\n            label = [inner_label for inner_label in label if inner_label != \"\"]\n\n        if (\n            label is None\n            or label == \"\"\n            or (isinstance(label, list) and len(label) == 0)\n        ):\n            self.label = None\n            self.labels = None\n        elif isinstance(label, str):\n            self.label = label\n            self.labels = [label]\n        elif isinstance(label, list) and all(\n            [isinstance(inner_label, str) for inner_label in label]\n        ):\n            self.label = label[0]\n            self.labels = label\n        else:\n            raise AssertionError(\n                \"label should be either None, string or a list of strings\"\n            )\n\n        self.properties = properties or {}\n\n    def to_string(self):\n        res = \"\"\n        if self.properties:\n            props = \",\".join(\n                key + \":\" + str(quote_string(val))\n                for key, val in sorted(self.properties.items())\n            )\n            res += \"{\" + props + \"}\"\n\n        return res\n\n    def __str__(self):\n        res = \"(\"\n        if self.alias:\n            res += self.alias\n        if self.labels:\n            res += \":\" + \":\".join(self.labels)\n        if self.properties:\n            props = \",\".join(\n                key + \":\" + str(quote_string(val))\n                for key, val in sorted(self.properties.items())\n            )\n            res += \"{\" + props + \"}\"\n        res += \")\"\n\n        return res\n\n    def __eq__(self, rhs):\n        # Quick positive check, if both IDs are set.\n        if self.id is not None and rhs.id is not None and self.id != rhs.id:\n            return False\n\n        # Label should match.\n        if self.label != rhs.label:\n            return False\n\n        # Quick check for number of properties.\n        if len(self.properties) != len(rhs.properties):\n            return False\n\n        # Compare properties.\n        if self.properties != rhs.properties:\n            return False\n\n        return True\n", "path": "redis/commands/graph/node.py"}], "after_files": [{"content": "from ..helpers import quote_string\nfrom .node import Node\n\n\nclass Edge:\n    \"\"\"\n    An edge connecting two nodes.\n    \"\"\"\n\n    def __init__(self, src_node, relation, dest_node, edge_id=None, properties=None):\n        \"\"\"\n        Create a new edge.\n        \"\"\"\n        if src_node is None or dest_node is None:\n            # NOTE(bors-42): It makes sense to change AssertionError to\n            #                ValueError here\n            raise AssertionError(\"Both src_node & dest_node must be provided\")\n\n        self.id = edge_id\n        self.relation = relation or \"\"\n        self.properties = properties or {}\n        self.src_node = src_node\n        self.dest_node = dest_node\n\n    def to_string(self):\n        res = \"\"\n        if self.properties:\n            props = \",\".join(\n                key + \":\" + str(quote_string(val))\n                for key, val in sorted(self.properties.items())\n            )\n            res += \"{\" + props + \"}\"\n\n        return res\n\n    def __str__(self):\n        # Source node.\n        if isinstance(self.src_node, Node):\n            res = str(self.src_node)\n        else:\n            res = \"()\"\n\n        # Edge\n        res += \"-[\"\n        if self.relation:\n            res += \":\" + self.relation\n        if self.properties:\n            props = \",\".join(\n                key + \":\" + str(quote_string(val))\n                for key, val in sorted(self.properties.items())\n            )\n            res += \"{\" + props + \"}\"\n        res += \"]->\"\n\n        # Dest node.\n        if isinstance(self.dest_node, Node):\n            res += str(self.dest_node)\n        else:\n            res += \"()\"\n\n        return res\n\n    def __eq__(self, rhs):\n        # Type checking\n        if not isinstance(rhs, Edge):\n            return False\n\n        # Quick positive check, if both IDs are set.\n        if self.id is not None and rhs.id is not None and self.id == rhs.id:\n            return True\n\n        # Source and destination nodes should match.\n        if self.src_node != rhs.src_node:\n            return False\n\n        if self.dest_node != rhs.dest_node:\n            return False\n\n        # Relation should match.\n        if self.relation != rhs.relation:\n            return False\n\n        # Quick check for number of properties.\n        if len(self.properties) != len(rhs.properties):\n            return False\n\n        # Compare properties.\n        if self.properties != rhs.properties:\n            return False\n\n        return True\n", "path": "redis/commands/graph/edge.py"}, {"content": "from .edge import Edge\nfrom .node import Node\n\n\nclass Path:\n    def __init__(self, nodes, edges):\n        if not (isinstance(nodes, list) and isinstance(edges, list)):\n            raise TypeError(\"nodes and edges must be list\")\n\n        self._nodes = nodes\n        self._edges = edges\n        self.append_type = Node\n\n    @classmethod\n    def new_empty_path(cls):\n        return cls([], [])\n\n    def nodes(self):\n        return self._nodes\n\n    def edges(self):\n        return self._edges\n\n    def get_node(self, index):\n        return self._nodes[index]\n\n    def get_relationship(self, index):\n        return self._edges[index]\n\n    def first_node(self):\n        return self._nodes[0]\n\n    def last_node(self):\n        return self._nodes[-1]\n\n    def edge_count(self):\n        return len(self._edges)\n\n    def nodes_count(self):\n        return len(self._nodes)\n\n    def add_node(self, node):\n        if not isinstance(node, self.append_type):\n            raise AssertionError(\"Add Edge before adding Node\")\n        self._nodes.append(node)\n        self.append_type = Edge\n        return self\n\n    def add_edge(self, edge):\n        if not isinstance(edge, self.append_type):\n            raise AssertionError(\"Add Node before adding Edge\")\n        self._edges.append(edge)\n        self.append_type = Node\n        return self\n\n    def __eq__(self, other):\n        # Type checking\n        if not isinstance(other, Path):\n            return False\n\n        return self.nodes() == other.nodes() and self.edges() == other.edges()\n\n    def __str__(self):\n        res = \"<\"\n        edge_count = self.edge_count()\n        for i in range(0, edge_count):\n            node_id = self.get_node(i).id\n            res += \"(\" + str(node_id) + \")\"\n            edge = self.get_relationship(i)\n            res += (\n                \"-[\" + str(int(edge.id)) + \"]->\"\n                if edge.src_node == node_id\n                else \"<-[\" + str(int(edge.id)) + \"]-\"\n            )\n        node_id = self.get_node(edge_count).id\n        res += \"(\" + str(node_id) + \")\"\n        res += \">\"\n        return res\n", "path": "redis/commands/graph/path.py"}, {"content": "from ..helpers import quote_string\n\n\nclass Node:\n    \"\"\"\n    A node within the graph.\n    \"\"\"\n\n    def __init__(self, node_id=None, alias=None, label=None, properties=None):\n        \"\"\"\n        Create a new node.\n        \"\"\"\n        self.id = node_id\n        self.alias = alias\n        if isinstance(label, list):\n            label = [inner_label for inner_label in label if inner_label != \"\"]\n\n        if (\n            label is None\n            or label == \"\"\n            or (isinstance(label, list) and len(label) == 0)\n        ):\n            self.label = None\n            self.labels = None\n        elif isinstance(label, str):\n            self.label = label\n            self.labels = [label]\n        elif isinstance(label, list) and all(\n            [isinstance(inner_label, str) for inner_label in label]\n        ):\n            self.label = label[0]\n            self.labels = label\n        else:\n            raise AssertionError(\n                \"label should be either None, string or a list of strings\"\n            )\n\n        self.properties = properties or {}\n\n    def to_string(self):\n        res = \"\"\n        if self.properties:\n            props = \",\".join(\n                key + \":\" + str(quote_string(val))\n                for key, val in sorted(self.properties.items())\n            )\n            res += \"{\" + props + \"}\"\n\n        return res\n\n    def __str__(self):\n        res = \"(\"\n        if self.alias:\n            res += self.alias\n        if self.labels:\n            res += \":\" + \":\".join(self.labels)\n        if self.properties:\n            props = \",\".join(\n                key + \":\" + str(quote_string(val))\n                for key, val in sorted(self.properties.items())\n            )\n            res += \"{\" + props + \"}\"\n        res += \")\"\n\n        return res\n\n    def __eq__(self, rhs):\n        # Type checking\n        if not isinstance(rhs, Node):\n            return False\n\n        # Quick positive check, if both IDs are set.\n        if self.id is not None and rhs.id is not None and self.id != rhs.id:\n            return False\n\n        # Label should match.\n        if self.label != rhs.label:\n            return False\n\n        # Quick check for number of properties.\n        if len(self.properties) != len(rhs.properties):\n            return False\n\n        # Compare properties.\n        if self.properties != rhs.properties:\n            return False\n\n        return True\n", "path": "redis/commands/graph/node.py"}]}