--- /dev/null
+.. change::
+ :tags: bug, orm
+ :tickets: 9211
+
+ An explicit error is raised if a mapping attempts to mix the use of
+ :class:`_orm.MappedAsDataclass` with
+ :meth:`_orm.registry.mapped_as_dataclass` within the same class hierarchy,
+ as this produces issues with the dataclass function being applied at the
+ wrong time to the mapped class, leading to errors during the mapping
+ process.
if not dataclass_setup_arguments:
return
+ # can't use is_dataclass since it uses hasattr
+ if "__dataclass_fields__" in self.cls.__dict__:
+ raise exc.InvalidRequestError(
+ f"Class {self.cls} is already a dataclass; ensure that "
+ "base classes / decorator styles of establishing dataclasses "
+ "are not being mixed. "
+ "This can happen if a class that inherits from "
+ "'MappedAsDataclass', even indirectly, is been mapped with "
+ "'@registry.mapped_as_dataclass'"
+ )
+
manager = instrumentation.manager_of_class(self.cls)
assert manager is not None
b1 = Bar(mixin_value=5)
eq_(b1.bar_value, 78)
+ def test_mixing_MappedAsDataclass_with_decorator_raises(self, registry):
+ """test #9211"""
+
+ class Mixin(MappedAsDataclass):
+ id: Mapped[int] = mapped_column(primary_key=True, init=False)
+
+ with expect_raises_message(
+ exc.InvalidRequestError,
+ "Class .*Foo.* is already a dataclass; ensure that "
+ "base classes / decorator styles of establishing dataclasses "
+ "are not being mixed. ",
+ ):
+
+ @registry.mapped_as_dataclass
+ class Foo(Mixin):
+ bar_value: Mapped[float] = mapped_column(default=78)
+
class RelationshipDefaultFactoryTest(fixtures.TestBase):
def test_list(self, dc_decl_base: Type[MappedAsDataclass]):