如何使用多表相关的sqlalchemy进行查询

时间:2016-07-25 14:36:05

标签: python flask sqlalchemy

我有下一个型号。

class Provider(Base):
    __tablename__ = "providers"

    providerId = Column(Integer, primary_key=True)
    thirdPartyId = Column(Integer, ForeignKey("thirdparties.thirdPartyId"))
    thirdParty = relationship("ThirdParty")


class ThirdParty(Base):
    __tablename__ = 'thirdparties'

    thirdPartyId = Column(Integer, primary_key=True, nullable=False)
    economicActivityId = Column(Integer, ForeignKey('economicactivities.economicActivityId'))

class EconomicActivity(Base):
    __tablename__ = 'economicactivities'

    economicActivityId = Column(Integer, primary_key=True, nullable=False)
    puc = relationship(u'PUC',
                       secondary=economicactivitypuc,
                       primaryjoin=economicActivityId == economicactivitypuc.c.economicActivityId,
                       secondaryjoin=PUC.pucId == economicactivitypuc.c.pucId,
                       lazy="dynamic")

    economicactivitypuc = Table(
        'economicactivitypuc', Base.metadata,

        Column('economicActivityId', ForeignKey(u'economicactivities.economicActivityId'), primary_key=True, nullable=False),
        Column('pucId', ForeignKey(u'puc.pucId'), primary_key=True, nullable=False, index=True))

class PUC(Base):
    __tablename__ = "puc"

    pucId = Column(Integer, primary_key=True, nullable=False)

这是我的疑问:

list_provider = [Provider.export_data_simple_search(provider)
                         for provider
                         in session.query(Provider.providerId, Provider.branch, Provider.name, Provider.isMain,
                                          Provider.companyId, ThirdParty.isWithholdingCREE, ThirdParty.thirdPartyId,
                                          ThirdParty.tradeName, ThirdParty.lastName,
                                          ThirdParty.maidenName, ThirdParty.firstName,
                                          ThirdParty.identificationNumber, EconomicActivity,)
                                   # .options(defer(Provider.cityId))
                                   .join(ThirdParty, ThirdParty.thirdPartyId == Provider.thirdPartyId)
                                   .join(EconomicActivity, ThirdParty.economicActivityId == EconomicActivity.economicActivityId)
                                   .filter(and_(
                                        Provider.companyId == company_id,
                                        or_(
                                            True if search == "" else None,
                                            # or_(*[Provider.name.like('%{0}%'.format(s)) for s in words])
                                            or_(*[func.concat(ThirdParty.tradeName +
                                                   ThirdParty.lastName +
                                                   ThirdParty.maidenName +
                                                   ThirdParty.firstName +
                                                   ThirdParty.identificationNumber +
                                                   Provider.name).like('%{0}%'.format(s)) for s in words]
                                        ))))
                                   .limit(page_size)
                                   .offset((int(page_number) - 1) * int(page_size))]

        total_count = session.query(Provider).filter(and_(
                                        Provider.companyId == company_id,
                                        or_(
                                            True if search == "" else None,
                                            # or_(*[Provider.name.like('%{0}%'.format(s)) for s in words])
                                            or_(*[func.concat(ThirdParty.tradeName +
                                                   ThirdParty.lastName +
                                                   ThirdParty.maidenName +
                                                   ThirdParty.firstName +
                                                   ThirdParty.identificationNumber +
                                                   Provider.name).like('%{0}%'.format(s)) for s in words]
                                        )))).count()
        total_pages = int(ceil(total_count / float(page_size)))
        response = jsonify({
            'listThirdParty': list_provider,
            'totalCount': total_count,
            'totalPages': total_pages
        })
        return response

并且export_data方法是下一个:

class Provider(Base):
    ##### models, anothers methods, etc 
    @staticmethod
    def export_data_simple_search(data):
        pucs = None if data.EconomicActivity is None \
            else data.EconomicActivity.puc.filter(PUC.companyId == data.companyId).first()
        return {
            "providerId": data.providerId,
            "branch": data.branch,
            "puc": None if pucs is None
            else {
                "pucId": pucs.pucId,
                "companyId": pucs.companyId,
                "account": '{0}{1}{2}{3}{4} {5}'.format(pucs.pucClass,
                                                        pucs.pucSubClass,
                                                        pucs.account,
                                                        pucs.subAccount,
                                                        pucs.auxiliary1,
                                                        pucs.name),
                "percentage": pucs.percentage,
                "name": pucs.name,
                  },
            "thirdPartyId": data.thirdPartyId
        }

我需要的信息来自我的查询:提供商> ThirdParty> EconomicActivity> m2m(由companyId过滤)> PUC

此实现有效,但每页大约需要25秒,我需要跳过此步骤:

data.EconomicActivity.puc.filter(PUC.companyId == data.companyId).first()

因为它做了15(页面大小)新选择。

0 个答案:

没有答案