2012-02-28 27 views
8
class Employee 
    id 
    name 

class Location 
    id 
    city 

class Work 
    id 
    employee_id 
    location_id 

Todo: Trái tham gia với số lượng (bao gồm zero)SQLAlchemy Left Tham gia với số lượng

kết quả mong muốn

location.city count 
    NYC 10 
    SFO 5 
    CHI 0 

liệu Query:

select location.id, count(work.id) as count 
    from location 
    left join work 
    on location.id = work.location_id 
    group by location.id 

SQLAlchemy:

db_session.query(Location, func.count.work_id).label('count')). \ 
       filter(location.id == work.location_id). \ 
       group_by(location._id). \ 

Cách đúng để chỉ định các cột được chọn trong khi thực hiện một phép nối trái là gì?

Trả lời

7

Xác định mối quan hệ giữa các bảng khi bạn xác định mô hình orm. Xem this tutorial. Trong ví dụ của bạn, Work là một bảng hiệp hội, vì vậy nếu bạn không có bất kỳ dữ liệu khác trong Work, bạn có thể sử dụng một many to many relationship ví dụ:

from sqlalchemy.orm import relationship 

class Work 
    id 
    employee_id 
    location_id 

class Employee 
    id 
    name 

class Location 
    id 
    city 
    employees = relationship(Employee, secondary=Work, backref='locations') 

Sau đó truy vấn:

session.query(Location, func.count(Work.id)).outerjoin(Work).group_by(Location) 

Như bạn có xác định mối quan hệ, sqlalchemy sẽ biết hướng và các cột cho outerjoin.

Khi bạn làm group_by, điều quan trọng là phải vượt qua Location và không chỉ Location.id, bởi vì bằng cách làm select(Location), SQLAlchemy sẽ chọn tất cả các cột trong Vị trí, và do đó bạn cũng phải vượt qua tất cả các cột trong Location.