简体   繁体   English

SQLAlchemy - 关系不仅限于外键

[英]SQLAlchemy - relationship limited on more than just the foreign key

I have a wiki db layout with Page and Revisions . 我有一个带有PageRevisions的wiki db布局。 Each Revision has a page_id referencing the Page, a page relationship to the referenced page; 每个版本都有一个引用页面的page_id ,一个与引用页面的page关系; each Page has a all_revisions relationship to all its revisions. 每个页面都与其所有修订版具有all_revisions关系。 So far so common. 到目前为止很常见。

But I want to implement different epochs for the pages: If a page was deleted and is recreated, the new revisions have a new epoch . 但是我想为页面实现不同的时期:如果页面被删除并重新创建,则新的修订版本将有一个epoch To help find the correct revisions, each page has a current_epoch field. 为帮助找到正确的修订版,每个页面都有一个current_epoch字段。 Now I want to provide a revisions relation on the page that only contains its revisions, but only those where the epochs match. 现在,我想在页面上提供仅包含其修订版本的revisions关系,但仅包含与历元记录匹配的revisions关系。

This is what I've tried: 这就是我尝试过的:

revisions = relationship('Revision',
    primaryjoin = and_(
        'Page.id == Revision.page_id',
        'Page.current_epoch == Revision.epoch',
    ),
    foreign_keys=['Page.id', 'Page.current_epoch']
)

Full code (you may run that as it is) 完整代码 (您可以按原样运行)

However this always raises ArgumentError: Could not determine relationship direction for primaryjoin condition ...` , I've tried all I had come to mind, it didn't work. 然而,这总是引发ArgumentError:无法确定主连接条件的关系方向......` ,我已经尝试了所有我想到的,它没有用。

What am I doing wrong? 我究竟做错了什么? Is this a bad approach for doing this, how could it be done other than with a relationship? 这样做是不是一个糟糕的方法,除了关系之外怎么办呢?

Try installing relationship after both classes are created: 创建两个类后尝试安装关系:

Page.revisions = relationship(
    'Revision',
    primaryjoin = (Page.id==Revision.page_id) & \
                    (Page.current_epoch==Revision.epoch),
    foreign_keys=[Page.id, Page.current_epoch],
    uselist=True,
)

BTW, your test is not correct: revisions property loads data from database while you haven't added them to session. 顺便说一句,您的测试不正确: revisions属性在您尚未将数据添加到会话时从数据库加载数据。

Update : The problem in your code is that primaryjoin parameter is not string, so it's not evaluated . 更新 :代码中的问题是primaryjoin参数不是字符串,因此不进行评估 Using string in primaryjoin works fine: primaryjoin使用string工作正常:

class Page(Base):
    # [skipped]
    revisions = relationship(
        'Revision',
        primaryjoin = '(Page.id==Revision.page_id) & '\
                        '(Page.current_epoch==Revision.epoch)',
        foreign_keys=[id, current_epoch],
        uselist=True,
    )

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM