Relationships#
Module: restalchemy.dm.relationships
Relationships connect DM models to each other.
Relationship factories#
relationship(property_type, *args, **kwargs)#
Main factory for defining relationships inside DM models.
Arguments:
property_type: the related model class (subclass ofmodels.Model).- Positional
*args: typically model classes used for validation. - Keyword arguments:
prefetch: ifTrue, usesPrefetchRelationshipas property class.required,read_only,default, etc.
Under the hood this function:
- Verifies that all positional arguments are DM model classes.
- Chooses the property class:
PrefetchRelationshipwhenprefetch=True.Relationshipotherwise.- Delegates to
properties.property()with appropriateproperty_class.
required_relationship(property_type, *args, **kwargs)#
Same as relationship(), but sets required=True.
readonly_relationship(property_type, *args, **kwargs)#
Same as required_relationship(), but also sets read_only=True.
Relationship classes#
Relationship#
A property representing a single related model instance.
Constructor parameters mirror scalar Property, but property_type is a model class:
property_type: DM model class.default,required,read_only,value.
Behavior:
- Accepts
Noneor an instance ofproperty_type. - Enforces
requiredandread_onlyflags. - Tracks
is_dirty()by comparing current value with the initial value. - Exposes
property_type(get_property_type()returns the model class).
If you pass a value of the wrong type, a TypeError is raised.
PrefetchRelationship#
Subclass of Relationship used when prefetch=True:
- Overrides
is_prefetch()class method to returnTrue. - Otherwise behaves like
Relationship.
Prefetch flags are typically used by storage or API layers to optimize data loading.
Example: one-to-many via DM + API#
Below is a simplified version of the Foo/Bar relationship used in examples.
from restalchemy.dm import models, properties, relationships, types
class FooModel(models.ModelWithUUID):
value = properties.property(types.Integer(), required=True)
class BarModel(models.ModelWithUUID):
# Simple string field
name = properties.property(types.String(max_length=10), required=True)
# Link to a FooModel instance
foo = relationships.relationship(FooModel)
Now you can work with relationships as normal attributes:
Combined with storage (see DM + SQL examples), relationships can be used to express foreign keys and joins.
Example: required and read-only relationships#
- The
foorelationship must always be set (required). - It cannot be changed after initialization (read-only), unless you use
set_value_force()at a lower level.
Best practices#
- Use relationships for DM-level modeling of links between entities; actual foreign keys and joins are handled by the storage layer.
- Keep relationships simple: one model field usually represents one logical relation.
- Use
prefetch=Trueonly when you need to hint storage/API layers about preloading behavior.