sqlalchemy从SQL查询多个where条件

时间:2012-04-05 00:06:45

标签: sql sqlalchemy

我有三个表定义为:

class User(Base):
    __tablename__ = 'users'

    id = Column(Integer(10), primary_key=True)
    firstname = Column(String(64))
    surname = Column(String(64))

class SWMS(Base):
    __tablename__ = 'swms'
    id = Column(Integer(10), primary_key=True)
    owner_id = Column(Integer(10), ForeignKey('users.id', ondelete='CASCADE'))
    filename = Column(String(255))

    swmowner = relationship('User', backref=backref('users'))

class SWM_perms(Base):
    __tablename__ = 'swm_perms'
    id = Column(Integer(10), primary_key=True)
    swm_id = Column(Integer(10), ForeignKey('swms.id', ondelete='CASCADE'))
    user_id = Column(Integer(10), ForeignKey('users.id', ondelete='CASCADE'))

    swm = relationship('SWMS', backref=backref('swms'))
    swmuser = relationship('User', backref=backref('swmusers'))

基本上,SWMS表是文档信息表,其中owner_id定义了创建文档的用户。 SWM_perms是一个表,其中包含文档ID到用户ID的映射 - 用于定义允许哪些用户查看文档。

要生成一个表,其中包含1)用户拥有的所有文档,或者2)用户可以查看,我会这样做:

select owner_id, users.firstname, users.surname, filename
from swms, swm_perms, users
where users.id=swms.owner_id and 
  ((swms.id=swm_perms.swm_id and swm_perms.user_id = 27) or (owner_id = 27));

您如何在sqlalchemy中定义此查询?我熟悉or_()函数,但我尝试的变体不会生成正确的对象。

2 个答案:

答案 0 :(得分:6)

cond1 = and_(SWMS.id==SWM_perms.swm_id,SWM_perms.user_id==27)
swms = DBSession.query(User,SWMS).filter(or_(cond1,SWMS.owner_id==27)).\
                                  filter(User.id==SWMS.owner_id).all()

然后你可以做一个列表理解来拉出你想要的字段:

details = [(u.firstname, s.filename, s.blob_key, s.last_modified) for u,s in swms]

答案 1 :(得分:1)

另外值得注意的是,您可以使用'&'运算符,代替查询正文中的'和_'。请参阅这里给出的示例(第二个代码块):

http://docs.sqlalchemy.org/en/rel_1_0/core/sqlelement.html#sqlalchemy.sql.expression.and_