core.orm.mixins.content
Attributes
Classes
Base class for protocol classes. |
|
Mixin providing a meta/content JSON pair. Meta is a JSON column loaded |
|
Enables access of dictionaries through properties. |
|
Enables access of dictionaries through properties. |
Functions
|
|
|
Module Contents
- class core.orm.mixins.content._dict_property_factory[source]
Bases:
Protocol
Base class for protocol classes.
Protocol classes are defined as:
class Proto(Protocol): def meth(self) -> int: ...
Such classes are primarily used with static type checkers that recognize structural subtyping (static duck-typing).
For example:
class C: def meth(self) -> int: return 0 def func(x: Proto) -> int: return x.meth() func(C()) # Passes static type check
See PEP 544 for details. Protocol classes decorated with @typing.runtime_checkable act as simple-minded runtime protocols that check only the presence of given attributes, ignoring their type signatures. Protocol classes can be generic, they are defined as:
class GenProto(Protocol[T]): def meth(self) -> T: ...
- __call__(key: str | None = None, default: None = None, value_type: None = None) dict_property[Any | None] [source]
- __call__(key: str | None, default: _T | Callable[[], _T], value_type: None = None) dict_property[_T]
- __call__(key: str | None = None, *, default: _T | Callable[[], _T], value_type: None = None) dict_property[_T]
- __call__(key: str | None, default: None, *, value_type: type[_T]) dict_property[_T]
- __call__(key: str | None = None, default: None = None, *, value_type: type[_T]) dict_property[_T]
- __call__(key: str | None, default: _T | Callable[[], _T], value_type: type[_T]) dict_property[_T]
- __call__(key: str | None = None, *, default: _T | Callable[[], _T], value_type: type[_T]) dict_property[_T]
- class core.orm.mixins.content.ContentMixin[source]
Mixin providing a meta/content JSON pair. Meta is a JSON column loaded with each request, content is a JSON column loaded deferred (to be shown only in the detail view).
- class core.orm.mixins.content.dict_property(attribute: str, key: str | None = None, default: None = None, value_type: None = None)[source]
- class core.orm.mixins.content.dict_property(attribute: str, key: str | None, default: _T | Callable[[], _T], value_type: None = None)
- class core.orm.mixins.content.dict_property(attribute: str, key: str | None = None, *, default: _T | Callable[[], _T], value_type: None = None)
- class core.orm.mixins.content.dict_property(attribute: str, key: str | None, default: None, *, value_type: type[_T])
- class core.orm.mixins.content.dict_property(attribute: str, key: str | None = None, default: None = None, *, value_type: type[_T])
- class core.orm.mixins.content.dict_property(attribute: str, key: str | None, default: _T | Callable[[], _T], value_type: type[_T])
- class core.orm.mixins.content.dict_property(attribute: str, key: str | None = None, *, default: _T | Callable[[], _T], value_type: type[_T])
Bases:
sqlalchemy.orm.interfaces.InspectionAttrInfo
,Generic
[_T
]Enables access of dictionaries through properties.
Usage:
class Model(ContentMixin): access_times = dict_property('meta')
This creates a property that accesses the meta directory with the key ‘access_times’. The key is implicitly copied from the definition.
Another way of writing this out would be:
class Model(ContentMixin): access_times = dict_property('meta', 'access_times')
As is apparent, the ‘access_times’ key is duplicated in this case. Usually you do not need to provide the name. The exception being if you want the property name and the dictionary key to differ:
class Model(ContentMixin): access_times = dict_property('meta', 'access')
Here, the key in the dictionary is ‘access’, while the property is ‘access_times’.
Since we often use the same kind of dictionaries we can use the builtin properties that are scoped to a specific dictionary:
class Model(ContentMixin): access_times = meta_property()
This is equivalent to the initial example.
We can also create our own scoped properties as follows:
foo_property = dict_property_factory(‘foo’)
class Model:
foo = {}
bar = foo_property()
Here, model.bar would read model.foo[‘bar’].
Dict properties are compatible with typical python properties, so the usual getter/setter/deleter methods are also available:
class Model(ContentMixin): content = meta_property() @content.setter def set_content(self, value): self.meta['content'] = value self.meta['content_html'] = to_html_ul(value) @content.deleter def del_content(self): del self.meta['content'] del self.meta['content_html']
This also behaves like a hybrid_property in that you can use these properties inside select and filter statements, if you provider a custom getter you will also need to provide a custom expression, otherwise we will return an expression which retrieves the value from the JSON column:
class Model(ContentMixin): names = meta_property(default=list) session.query(Model).filter(Model.names.contains('foo'))
By default that will mean that the RHS of a comparison will also expect a JSONB object, but if you explicitly pass in a value_type or a default that is not None, then we will try to first convert to that type, so type coercion is a bit more flexible:
class Model(ContentMixin): name = meta_property(value_type=str) session.query(Model.name)
- is_attribute = True[source]
True if this object is a Python descriptor.
This can refer to one of many types. Usually a
QueryableAttribute
which handles attributes events on behalf of aMapperProperty
. But can also be an extension type such asAssociationProxy
orhybrid_property
. TheInspectionAttr.extension_type
will refer to a constant identifying the specific subtype.See also
_orm.Mapper.all_orm_descriptors
- __set_name__(owner: type[object], name: str) None [source]
Sets the dictionary key, if none is provided.
- class core.orm.mixins.content.dict_markup_property(attribute: str, key: str | None = None, default: None = None)[source]
- class core.orm.mixins.content.dict_markup_property(attribute: str, key: str | None, default: markupsafe.Markup)
- class core.orm.mixins.content.dict_markup_property(attribute: str, key: str | None = None, *, default: markupsafe.Markup)
Bases:
dict_property
[_MarkupT
]Enables access of dictionaries through properties.
Usage:
class Model(ContentMixin): access_times = dict_property('meta')
This creates a property that accesses the meta directory with the key ‘access_times’. The key is implicitly copied from the definition.
Another way of writing this out would be:
class Model(ContentMixin): access_times = dict_property('meta', 'access_times')
As is apparent, the ‘access_times’ key is duplicated in this case. Usually you do not need to provide the name. The exception being if you want the property name and the dictionary key to differ:
class Model(ContentMixin): access_times = dict_property('meta', 'access')
Here, the key in the dictionary is ‘access’, while the property is ‘access_times’.
Since we often use the same kind of dictionaries we can use the builtin properties that are scoped to a specific dictionary:
class Model(ContentMixin): access_times = meta_property()
This is equivalent to the initial example.
We can also create our own scoped properties as follows:
foo_property = dict_property_factory(‘foo’)
class Model:
foo = {}
bar = foo_property()
Here, model.bar would read model.foo[‘bar’].
Dict properties are compatible with typical python properties, so the usual getter/setter/deleter methods are also available:
class Model(ContentMixin): content = meta_property() @content.setter def set_content(self, value): self.meta['content'] = value self.meta['content_html'] = to_html_ul(value) @content.deleter def del_content(self): del self.meta['content'] del self.meta['content_html']
This also behaves like a hybrid_property in that you can use these properties inside select and filter statements, if you provider a custom getter you will also need to provide a custom expression, otherwise we will return an expression which retrieves the value from the JSON column:
class Model(ContentMixin): names = meta_property(default=list) session.query(Model).filter(Model.names.contains('foo'))
By default that will mean that the RHS of a comparison will also expect a JSONB object, but if you explicitly pass in a value_type or a default that is not None, then we will try to first convert to that type, so type coercion is a bit more flexible:
class Model(ContentMixin): name = meta_property(value_type=str) session.query(Model.name)
- core.orm.mixins.content.dict_property_factory(attribute: str) _dict_property_factory [source]