Как определить два отношения к одной таблице в SQLAlchemy

Ive просмотрел учебник по SQLAlchemy и другие подобные вопросы, но я, похоже, изо всех сил пытаюсь заставить это соединение работать:

Сценарий. У меня есть таблица pages, представленная моделью Page. Страницы могут быть созданы пользователем и отредактированы пользователем, но не обязательно одним и тем же. Моя модель Page выглядит так (сокращенная):

class Page(Base):
    __tablename__ = 'pages'

    id = Column(Integer, primary_key = True)
    slug = Column(Text)
    title = Column(Text)
    direct_link = Column(Text)
    body = Column(Text)
    category_id = Column(Integer, ForeignKey('categories.id'))
    published_on = Column(DateTime)
    publishing_user_id = Column(Integer, ForeignKey('users.id'))
    last_edit_on = Column(DateTime)
    last_edit_user_id = Column(Integer, ForeignKey('users.id'))

    # Define relationships
    publish_user = relationship('User', backref = backref('pages', order_by = id), primaryjoin = "Page.publishing_user_id == User.id")
    edit_user = relationship('User', primaryjoin = "Page.last_edit_user_id == User.id")
    category = relationship('Category', backref = backref('pages', order_by = id))

Мои пользователи хранятся в таблице пользователей, представленной моделью User. Поскольку я сказал, что я был во всех документах SQLAlchemy, которые искали это, я попытался сделать его похожим на их пример, насколько это возможно, но безрезультатно. Любая помощь будет принята с благодарностью.

Ответы

Ответ 1

Начиная с версии 0.8, SQLAlchemy может разрешить неоднозначное соединение, используя только параметр ключевого слова foreign_keys до relationship.

publish_user = relationship(User, foreign_keys=[publishing_user_id],
                                  backref=backref('pages', order_by=id))
edit_user = relationship(User, foreign_keys=[last_edit_user_id])

Документация на http://docs.sqlalchemy.org/en/rel_0_9/orm/join_conditions.html#handling-multiple-join-paths

Ответ 2

Я думаю, вы почти все поняли; только вместо имен Model вы должны использовать имена Table при определении primaryjoin. Поэтому вместо

# Define relationships
publish_user = relationship('User', backref = backref('pages', order_by = id), 
    primaryjoin = "Page.publishing_user_id == User.id")
edit_user = relationship('User', 
    primaryjoin = "Page.last_edit_user_id == User.id")

использование:

# Define relationships
publish_user = relationship('User', backref = backref('pages', order_by = id), 
    primaryjoin = "pages.publishing_user_id == users.id")
edit_user = relationship('User', 
    primaryjoin = "pages.last_edit_user_id == users.id")

Ответ 3

Попробуйте параметр foreign_keys:

publish_user = relationship(User, foreign_keys=publishing_user_id,
                                  primaryjoin=publishing_user_id == User.id,
                                  backref=backref('pages', order_by=id))
edit_user = relationship(User, foreign_keys=last_edit_user_id,
                               primaryjoin=last_edit_user_id == User.id)