6

私の Pyramid+SQLAlchemy Web サイトで、顧客が行ったすべての購入を表示したいと考えています。Purchase には多くの PurchaseOrder があり、 PurchaseOrder には多くの PurchaseOrderDetail があります。

最適化された方法ですべての購入コンテキスト (注文と詳細を含む) を取得したいので、SQLAlchemy の読み込み戦略を検討しています。

私のモデル宣言は次のようになります。

class Purchase(Base):
    __tablename__ = 'purchase'
    __table_args__ = {'schema':'db','autoload':True}

    customer = relationship(Customer)
    billing_address = relationship(Address,primaryjoin="Address.AddressId==Purchase.BillingAddressId")
    shipping_address = relationship(Address,primaryjoin="Address.AddressId==Purchase.ShippingAddressId")
    orders = relationship(PurchaseOrder)

class PurchaseOrder(Base):
    __tablename__ = 'purchase_order'
    __table_args__ = {'schema':'db','autoload':True}

    company = relationship(Company)
    delivery_service = relationship(DeliveryService)
    details = relationship(PurchaseOrderDetail)

class PurchaseOrderDetail(Base):
    __tablename__ = 'purchase_order_detail'
    __table_args__ = {'schema':'db','autoload':True}

    product_variant = relationship(ProductVariant)

そして、私が欲しいのは、この形式の何かです:

    db_session = DBSession()
    p = db_session.query(Purchase).\
        options(joinedload_all(Purchase.customer,
                                Purchase.billing_address,
                                Purchase.shipping_address)
                ,subqueryload_all(Purchase.orders,
                                Purchase.orders.details)).all()

ただし、このPurchase.orders.details部分は許可されておらず、次の例外が発生します。

Traceback (most recent call last):
  File "<input>", line 1, in <module>
  File "C:\apps\pyramid\lib\site-packages\sqlalchemy\orm\attributes.py", line 139, in __getattr__
    key)
AttributeError: Neither 'InstrumentedAttribute' object nor 'Comparator' object has an attribute 'details'

だから、私の質問は次のとおりです。

  1. Purchase モデルを照会するときに PurchaseOrderDetails をロードするにはどうすればよいですか?
  2. これは、すべての購入コンテキストを取得するための最良の方法ですか?

前もって感謝します

4

2 に答える 2

13

このsubqueryload_all関数はバージョン 0.9 以降非推奨です。

subqueryload代わりにメソッド チェーンを使用します。

from sqlalchemy.orm import subqueryload

session.query(MyClass).options(
    subqueryload("someattribute").subqueryload("anotherattribute")
)
于 2015-09-25T00:39:22.597 に答える
6

クエリの一部を次の 2 つのオプションのいずれかに変更するsubqueryload_all(...)と、うまくいきます。

# option-1:
subqueryload_all(
    'orders.details', # @note: this will load both *orders* and their *details*
    )

# option-2:
subqueryload_all(
    Purchase.orders,       # @note: this will load orders
    PurchaseOrder.details, # @note: this will load orders' details
    )

上のドキュメントsqlalchemy.orm.subqueryload_allは、リストされている例でこれについて非常に明確です。

于 2012-10-03T19:04:19.473 に答える