我有一张Track
桌子和一张Artist
桌子。该Artist
表有一个id
,Track
表有一个外键,artist_id
。我想删除所有没有关联曲目的艺术家。
在 SQL 中:
delete from artists
where id in (select artists.id
from artists left outer join tracks
on tracks.artist_id = artists.id
where tracks.id is null);
效果很好。但是当我尝试在 SQLAlchemy 中复制它时:
artists = session.query(Artist.id).outerjoin((Track, Artist.id == Track.artist_id)).filter(Track.id == None)
print('deleting %d unused artists' % artists.count())
session.query(Artist).filter(Artist.id.in_(artists.all())).delete()
工作print()
正常(并显示正确的行数)但删除给出了错误:
...
sqlalchemy.orm.evaluator.UnevaluatableError: Cannot evaluate clauselist with operator <function comma_op at 0x2d3e0d8>
During handling of the above exception, another exception occurred:
...
"Could not evaluate current criteria in Python. "
sqlalchemy.exc.InvalidRequestError: Could not evaluate current criteria in Python. Specify 'fetch' or False for the synchronize_session parameter.
那么我如何在 SQLAlchemy 中做到这一点?我不介意方法是否不同,只要我可以删除所有不属于任何轨道的艺术家。
PS我也尝试过artists.delete()
(在选择Artist实例时,而不是上面的ID),这也给出了一个错误——在这种情况下,外连接“丢失”并且SQL不一致。
更新
万一这对任何人都有用,如果您artists
的模型中有一个反向引用(,下面),则有一种比外连接更简单的方法:
session.query(Artist).filter(Artist.tracks == None).delete(synchronize_session=False)