diff options
author | Mike Bayer <mike_mp@zzzcomputing.com> | 2022-11-25 14:29:30 -0500 |
---|---|---|
committer | Mike Bayer <mike_mp@zzzcomputing.com> | 2022-11-29 19:25:59 -0500 |
commit | 3e3e3ab0d46b8912649afc7c3eb63b76c19d93fe (patch) | |
tree | f2c5b6fde3c6679138b255056d1b38db2ac67fc6 /lib/sqlalchemy/ext/mutable.py | |
parent | 78833af4e650d37e6257cfbb541e4db56e2a285f (diff) | |
download | sqlalchemy-3e3e3ab0d46b8912649afc7c3eb63b76c19d93fe.tar.gz |
annotated / DC forms for association proxy
Added support for the :func:`.association_proxy` extension function to
take part within Python ``dataclasses`` configuration, when using
the native dataclasses feature described at
:ref:`orm_declarative_native_dataclasses`. Included are attribute-level
arguments including :paramref:`.association_proxy.init` and
:paramref:`.association_proxy.default_factory`.
Documentation for association proxy has also been updated to use
"Annotated Declarative Table" forms within examples, including type
annotations used for :class:`.AssocationProxy` itself.
Also modernized documentation examples in sqlalchemy.ext.mutable,
which was not up to date even for 1.4 style code.
Corrected typing for relationship(secondary) where "secondary"
accepts a callable (i.e. lambda) as well
Fixes: #8878
Fixes: #8876
Fixes: #8880
Change-Id: Ibd4f3591155a89f915713393e103e61cc072ed57
Diffstat (limited to 'lib/sqlalchemy/ext/mutable.py')
-rw-r--r-- | lib/sqlalchemy/ext/mutable.py | 47 |
1 files changed, 25 insertions, 22 deletions
diff --git a/lib/sqlalchemy/ext/mutable.py b/lib/sqlalchemy/ext/mutable.py index f9ed17efc..242f5ee8f 100644 --- a/lib/sqlalchemy/ext/mutable.py +++ b/lib/sqlalchemy/ext/mutable.py @@ -111,34 +111,27 @@ Above, :meth:`~.Mutable.as_mutable` returns an instance of ``JSONEncodedDict`` attributes which are mapped against this type. Below we establish a simple mapping against the ``my_data`` table:: - from sqlalchemy import mapper + from sqlalchemy.orm import DeclarativeBase + from sqlalchemy.orm import Mapped + from sqlalchemy.orm import mapped_column - class MyDataClass: + class Base(DeclarativeBase): pass - # associates mutation listeners with MyDataClass.data - mapper(MyDataClass, my_data) + class MyDataClass(Base): + __tablename__ = 'my_data' + id: Mapped[int] = mapped_column(primary_key=True) + data: Mapped[dict[str, str]] = mapped_column(MutableDict.as_mutable(JSONEncodedDict)) The ``MyDataClass.data`` member will now be notified of in place changes to its value. -There's no difference in usage when using declarative:: - - from sqlalchemy.ext.declarative import declarative_base - - Base = declarative_base() - - class MyDataClass(Base): - __tablename__ = 'my_data' - id = Column(Integer, primary_key=True) - data = Column(MutableDict.as_mutable(JSONEncodedDict)) - Any in-place changes to the ``MyDataClass.data`` member will flag the attribute as "dirty" on the parent object:: >>> from sqlalchemy.orm import Session - >>> sess = Session() + >>> sess = Session(some_engine) >>> m1 = MyDataClass(data={'value1':'foo'}) >>> sess.add(m1) >>> sess.commit() @@ -154,12 +147,19 @@ of ``JSONEncodedDict`` in one step, using of ``MutableDict`` in all mappings unconditionally, without the need to declare it individually:: + from sqlalchemy.orm import DeclarativeBase + from sqlalchemy.orm import Mapped + from sqlalchemy.orm import mapped_column + MutableDict.associate_with(JSONEncodedDict) + class Base(DeclarativeBase): + pass + class MyDataClass(Base): __tablename__ = 'my_data' - id = Column(Integer, primary_key=True) - data = Column(JSONEncodedDict) + id: Mapped[int] = mapped_column(primary_key=True) + data: Mapped[dict[str, str]] = mapped_column(JSONEncodedDict) Supporting Pickling @@ -208,15 +208,18 @@ an event when a mutable scalar emits a change event. This event handler is called when the :func:`.attributes.flag_modified` function is called from within the mutable extension:: - from sqlalchemy.ext.declarative import declarative_base + from sqlalchemy.orm import DeclarativeBase + from sqlalchemy.orm import Mapped + from sqlalchemy.orm import mapped_column from sqlalchemy import event - Base = declarative_base() + class Base(DeclarativeBase): + pass class MyDataClass(Base): __tablename__ = 'my_data' - id = Column(Integer, primary_key=True) - data = Column(MutableDict.as_mutable(JSONEncodedDict)) + id: Mapped[int] = mapped_column(primary_key=True) + data: Mapped[dict[str, str]] = mapped_column(MutableDict.as_mutable(JSONEncodedDict)) @event.listens_for(MyDataClass.data, "modified") def modified_json(instance, initiator): |