Multiple foreign-keys to the same Model

When there are multiple foreign keys to the same model, it is good practice to explicitly specify which field you are joining on.

Referring back to the example app’s models, consider the Relationship model, which is used to denote when one user follows another. Here is the model definition:

  1. class Relationship(BaseModel):
  2. from_user = ForeignKeyField(User, backref='relationships')
  3. to_user = ForeignKeyField(User, backref='related_to')
  4. class Meta:
  5. indexes = (
  6. # Specify a unique multi-column index on from/to-user.
  7. (('from_user', 'to_user'), True),
  8. )

Since there are two foreign keys to User, we should always specify which field we are using in a join.

For example, to determine which users I am following, I would write:

  1. (User
  2. .select()
  3. .join(Relationship, on=Relationship.to_user)
  4. .where(Relationship.from_user == charlie))

On the other hand, if I wanted to determine which users are following me, I would instead join on the from_user column and filter on the relationship’s to_user:

  1. (User
  2. .select()
  3. .join(Relationship, on=Relationship.from_user)
  4. .where(Relationship.to_user == charlie))