1. 一对多关系

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
class Team(SQLModel, table=True):
id: int | None = Field(default=None, primary_key=True)
name: str = Field(index=True)
headquarters: str

heroes: list["Hero"] = Relationship(back_populates="team")


class Hero(SQLModel, table=True):
id: int | None = Field(default=None, primary_key=True)
name: str = Field(index=True)
secret_name: str
age: int | None = Field(default=None, index=True)

team_id: int | None = Field(default=None, foreign_key="team.id")
team: Team | None = Relationship(back_populates="heroes")

在一对多的数据模型定义中,除了常规字段外,还需要额外定义两个关系字段,以建立双方的关系链。

首先在父表中,需要定义一个指向子表的Relationship

1
heroes: list["Hero"] = Relationship(back_populates="team")

在这里,需要注意:

  • heroes是一个list,表示一对多中的多,所以这里用了list数据结构。
  • “Hero”这里需要用引号括起来,因为这个类至此还未定义,无法直接引用类名。这里传入字符串,底层系统会自动将此转化成类。
  • back_populates提供反向引用的声明,表示在一方模型中定义属性,并在另一方模型中反向引用该属性。也就是说在Hero模型中可以用team来引用其对应的Team对象。

其次,需要在子表中定义一个指向父表的 Relationship

1
team: Team | None = Relationship(back_populates="heroes")

在这里,需要注意:

  • team是可选字段,即team可空。
  • 这里的Team是类名,因为上面已经定义好了。
  • back_populates提供反向引用的声明,内容为Team类中的heroes属性。

通过两个Relationship,即可建立一个一对多的双向关系,两者缺一不可。