SqlAlchemy - 按字段过滤定义为ForeignKey

Bor*_*jaX 9 python sqlalchemy foreign-key-relationship relational-database

我试图通过作为外键的字段来过滤类的实例,但是当我尝试这样做时,我总是得到数据库中的所有条目,而不是符合条件的条目.

假设我在一个简单的N:1关系中使用了声明式基类.我的建模如下:

#!/usr/bin/python2.6
class ContainerClass(declarativeBase):
     __tablename__ = "container_classes"
     _id = Column("id", Integer, primary_key=True)
     id = sqlalchemy.orm.synonym('_id', descriptor=property(getId, setId))


class WhateverClass(declarativeBase):
     __tablename__ = "whatever_classes"

     _id = Column("id", Integer, primary_key=True)
     _total = Column("total", Integer)
     _containerClassId = Column("container_class_id", Integer, ForeignKey("other_classes.id"))

     _containerClass = relationship("ContainerClass", uselist=False)

     id = sqlalchemy.orm.synonym('_id', descriptor=property(getId, setId))
     total = sqlalchemy.orm.synonym('_total', descriptor=property(getTotal, setTotal))
     containerClassId = sqlalchemy.orm.synonym('_containerClassId', decriptor=property(getContainerClassId, setContainerClassId))
     containerClass = sqlalchemy.orm.synonym('_containerClass', descriptor=property(getContainerClass setContainerClass))
Run Code Online (Sandbox Code Playgroud)

"WhateverClass"的实例可以属于"ContainerClass"的一个实例(并且每个ContainerClass可以具有WhateverClass的多个实例).这种关系似乎运作良好.如果我向"ContainerClass"添加一个新的"WhateverClass",那么whateverClass.containerClassId将正确获取它所属的ContainerClass的值.

但是,假设我需要获取一个属于"ContainerClass"的"WhateverClass"实例列表,其中id == 5.

如果我尝试做:

from myClasses import WhateverClass
session.query(WhateverClass.WhateverClass).filter(WhateverClass.WhateverClass.containerClass.id == 5).all()
Run Code Online (Sandbox Code Playgroud)

我得到了存储在数据库中的所有WhateverClass实例,而不仅仅是那些链接到具有id == 5的ContainerClass的实例

但是,如果我执行session.query(WhateverClass.WhateverClass).filter(total <= 100).all()我正确获取其"total"字段<= 100的WhateverClass的实例.

我对sqlalchemy很新手......我是否必须使用加入的查询或类似的东西?我知道它不复杂,但我找不到任何合适的解决方案.我试过加入,工会......但(显然)我做错了什么.

我正在使用SqlAlchemy 0.6.6和Python 2.6(以防它是相关的)

先感谢您!

car*_*arl 15

对于简单查询,您可以直接查询:

session.query(WhateverClass).filter(WhateverClass._containerClassId == 5).all()
Run Code Online (Sandbox Code Playgroud)

对于更复杂的关系,您需要一个联接:

session.query(WhateverClass).join(ContainerClass).filter(ContainerClass.id == 5).all()
Run Code Online (Sandbox Code Playgroud)

  • 更新:我很笨……笨蛋,笨蛋,笨蛋……我查看了数据库中的所有记录,结果发现我在 id == 5 的 ContainerClass 中拥有比我想象的更多的 WhatClass !!!它是从壁虎工作的!再次感谢你... (2认同)