Mysql
 sql >> Datenbank >  >> RDS >> Mysql

So konvertieren Sie eine skalare SQL-Unterabfrage in einen SQLAlchemy-Ausdruck

Verwenden Sie as_scalar() , oder label() :

subquery = (
    session.query(PropertyValuation.valuation)
    .filter(PropertyValuation.zip_code == Property.address_zip)
    .order_by(func.abs(func.datediff(PropertyValuation.as_of, Sale.date_sold)))
    .limit(1)
)

query = session.query(Sale.agent_id,
                      Sale.property_id,
                      Property.address_zip,
                      # `subquery.as_scalar()` or
                      subquery.label('back_valuation'))\
        .join(Property)

Verwendung von as_scalar() Begrenzt zurückgegebene Spalten und Zeilen auf 1, sodass Sie nicht das gesamte Modellobjekt abrufen können, indem Sie es verwenden (als query(PropertyValuation)). ist eine Auswahl aller Attribute von PropertyValuation ), aber nur die Bewertung erhalten Attribut funktioniert.

Es besteht keine Notwendigkeit, es später zu bestehen. Ihre aktuelle Art, die Unterabfrage zu deklarieren, ist in Ordnung, da SQLAlchemy korrelieren automatisch FROM-Objekte mit denen einer einschließenden Abfrage . Ich habe versucht, Modelle zu erstellen, die das darstellen, was Sie haben, und so funktioniert die obige Abfrage (mit zusätzlichen Zeilenumbrüchen und Einrückungen zur besseren Lesbarkeit):

In [10]: print(query)
SELECT sale.agent_id AS sale_agent_id,
       sale.property_id AS sale_property_id,
       property.address_zip AS property_address_zip,
       (SELECT property_valuations.valuation
        FROM property_valuations 
        WHERE property_valuations.zip_code = property.address_zip
        ORDER BY abs(datediff(property_valuations.as_of, sale.date_sold))
        LIMIT ? OFFSET ?) AS back_valuation 
FROM sale
JOIN property ON property.id = sale.property_id