1+ import datetime
12from typing import Optional
23
4+ from sqlalchemy import DateTime , func
35from sqlalchemy .orm import declared_attr , relationship
46from sqlmodel import Field , Relationship , Session , SQLModel , create_engine , select
57
68
79def test_relationship_inheritance () -> None :
10+ def now ():
11+ return datetime .datetime .now (tz = datetime .timezone .utc )
12+
813 class User (SQLModel , table = True ):
914 id : Optional [int ] = Field (default = None , primary_key = True )
1015 name : str
1116
1217 class CreatedUpdatedMixin (SQLModel ):
18+ # Fields in reusable base models must be defined using `sa_type` and `sa_column_kwargs` instead of `sa_column`
19+ # https://github.com/tiangolo/sqlmodel/discussions/743
20+ #
21+ # created_at: datetime.datetime = Field(default_factory=now, sa_column=DateTime(default=now))
22+ created_at : datetime .datetime = Field (
23+ default_factory = now , sa_type = DateTime , sa_column_kwargs = {"default" : now }
24+ )
25+
1326 # With Pydantic V2, it is also possible to define `created_by` like this:
1427 #
1528 # ```python
@@ -34,6 +47,9 @@ class CreatedUpdatedMixin(SQLModel):
3447 )
3548 )
3649
50+ updated_at : datetime .datetime = Field (
51+ default_factory = now , sa_type = DateTime , sa_column_kwargs = {"default" : now }
52+ )
3753 updated_by_id : Optional [int ] = Field (default = None , foreign_key = "user.id" )
3854 updated_by : Optional [User ] = Relationship (
3955 sa_relationship = declared_attr (
@@ -43,20 +59,34 @@ class CreatedUpdatedMixin(SQLModel):
4359
4460 class Asset (CreatedUpdatedMixin , table = True ):
4561 id : Optional [int ] = Field (default = None , primary_key = True )
62+ name : str
63+
64+ # Demonstrate that the mixin can be applied to more than 1 model
65+ class Document (CreatedUpdatedMixin , table = True ):
66+ id : Optional [int ] = Field (default = None , primary_key = True )
67+ name : str
4668
4769 engine = create_engine ("sqlite://" )
4870
4971 SQLModel .metadata .create_all (engine )
5072
5173 john = User (name = "John" )
5274 jane = User (name = "Jane" )
53- asset = Asset (created_by = john , updated_by = jane )
75+ asset = Asset (name = "Test" , created_by = john , updated_by = jane )
76+ doc = Document (name = "Resume" , created_by = jane , updated_by = john )
5477
5578 with Session (engine ) as session :
5679 session .add (asset )
80+ session .add (doc )
5781 session .commit ()
5882
5983 with Session (engine ) as session :
84+ assert session .scalar (select (func .count ()).select_from (User )) == 2
85+
6086 asset = session .exec (select (Asset )).one ()
6187 assert asset .created_by .name == "John"
6288 assert asset .updated_by .name == "Jane"
89+
90+ doc = session .exec (select (Document )).one ()
91+ assert doc .created_by .name == "Jane"
92+ assert doc .updated_by .name == "John"
0 commit comments