1
0
Эх сурвалжийг харах

Prevent Substate class shadowing (#1827)

Elijah Ahianyo 1 жил өмнө
parent
commit
2750228dbb

+ 10 - 1
reflex/state.py

@@ -93,6 +93,9 @@ class State(Base, ABC, extra=pydantic.Extra.allow):
             *args: The args to pass to the Pydantic init method.
             parent_state: The parent state.
             **kwargs: The kwargs to pass to the Pydantic init method.
+
+        Raises:
+            ValueError: If a substate class shadows another.
         """
         kwargs["parent_state"] = parent_state
         super().__init__(*args, **kwargs)
@@ -103,7 +106,13 @@ class State(Base, ABC, extra=pydantic.Extra.allow):
 
         # Setup the substates.
         for substate in self.get_substates():
-            self.substates[substate.get_name()] = substate(parent_state=self)
+            substate_name = substate.get_name()
+            if substate_name in self.substates:
+                raise ValueError(
+                    f"The substate class '{substate_name}' has been defined multiple times. Shadowing "
+                    f"substate classes is not allowed."
+                )
+            self.substates[substate_name] = substate(parent_state=self)
         # Convert the event handlers to functions.
         self._init_event_handlers()
 

+ 20 - 0
tests/conftest.py

@@ -584,3 +584,23 @@ def mutable_state():
             self.test_set = {1, 2, 3, 4, "five"}
 
     return MutableTestState()
+
+
+@pytest.fixture
+def duplicate_substate():
+    """Create a Test state that has duplicate child substates.
+
+    Returns:
+        The test state.
+    """
+
+    class TestState(rx.State):
+        pass
+
+    class ChildTestState(TestState):  # type: ignore # noqa
+        pass
+
+    class ChildTestState(TestState):  # type: ignore # noqa
+        pass
+
+    return TestState

+ 5 - 0
tests/test_state.py

@@ -1583,3 +1583,8 @@ def test_mutable_backend(mutable_state):
     assert_custom_dirty()
     mutable_state._be_custom.custom.bar = "baz"
     assert_custom_dirty()
+
+
+def test_duplicate_substate_class(duplicate_substate):
+    with pytest.raises(ValueError):
+        duplicate_substate()