SQL(Alchemy)查询,获取具有相同外键的所有条目的最新条目

时间:2015-03-02 11:15:34

标签: python sql sqlalchemy

我在项目中使用SQLAlchemy,遇到了需要复杂查询的问题。我不得不承认SQL不是我最强的套装。我的问题是这样的。

有两个表问题(父)和一对多关系的更改。更改有一个条目“changed_on”和一个外键“issue_id”,以及一个用“new”值更改的“字段”。

(例如 变更可以有issue_id = 1, field='status', new='closed' changed_on='25/01/2012'issue_id = 1, field='status', new='resolved', changed_on='24/01/2012'

我想计算我们在X日期之前有多少这些更改,只获取具有最新日期的更改(最新与查找日期相关)。

我的代码到目前为止在某天X之前得到了计数

for day in dates:
      q2 = Change.session.query(func.count(Change.id)).\
           filter(Change.changed_on <= day, Change.field == attr, Change.new == value).all()

这会在“日期”之前获得特定字段和值的正确计数,但不会考虑最新更新的值。

我意识到在过滤中我必须删除Change.new == value但之后如何过滤它以仅获得带有Y issue_id的X变更的最新更新

编辑:

更好的方法是每天都能获得像这样的词典

{
'01/04/2015': { 
           'open' :10, 
           'closed' : 15....}
    }

但有些日子问题可以从new-&gt;关闭,所以我们只需要计算已关闭的(最新更新)

1 个答案:

答案 0 :(得分:1)

您需要将group_by添加到查询中,以便按日期和状态进行分组。 在SQL中,您需要使用GROUP BY语句按字段计数。

    query(
        IssueChange.changed_on,
        Change.new,
        func.count(Change.id),
    ).filter(
        IssueChange.changed_on <= day,
        Change.field == attr,
        Change.new == value
    ).group_by(
        IssueChange.changed_on,
        Change.new 
    ).all()

您将收到如下输出:

[
 ('24/01/2012', 'resolved', 3),
 ('24/01/2012', 'closed', 2),
 ('25/01/2012', 'resolved', 5),
 ('25/01/2012', 'closed', 5)
]

<强>加入:

如果每个日期需要一行,则可以使用SQL子查询,如:

SELECT parent.changed_on, 
    (SELECT COUNT(child.id) FROM change AS child WHERE child.changed_on = parent.changed_on AND child.new == 'resolved') AS Resolved,
    (SELECT COUNT(child.id) FROM change AS child WHERE child.changed_on = parent.changed_on AND child.new == 'closed') AS Closed
FROM change AS parent

但是在SQLAlchemy中它非常棘手......(