django 中的聚合、分组查询 - annotate

SQL查询执行顺序

三、select ...聚合函数 from 表名
一、where ...
二、group by ...
四、having ...
五、order by ...
六、limit ...

order by(给查询结果进行排序)

1. order by 字段名 排序方式
2. 排序方式
	一、 ASC(默认) :升序
	二、 DESC :降序

django 中的聚合、分组查询 - annotates

1. 假设有一个日志以下定义:python

1.定义:
	levelname:
		DEBUG
		INFO	
		WARNING
		CRITICAL
	status:
		newTask - 新任务
		executeTask - 执行中
		finishTask - 已完成
		failTask - 执行失败
		backTask - 从新执行	
2.日志格式: %(asctime)s --- %(levelname)s ---%(message)s
日志时间     级别     状态    任务名称   定时时间     任务发起人  任务惟一编码
createTime---levelName---status---appName---arrangeTime---userName---serialNumber
例:
2019-01-25 17:00:00,619---INFO---newTask---外部用户一体化平台---00:02:00---jack---10000
2019-01-25 17:02:00,619---INFO---executeTask---发票小助手---null---tom---10001
2019-01-25 17:03:00,619---INFO---backTask---凭证小助手---null---tom---10002
2019-01-25 17:04:00,619---WARNING---failTask---智能发票处理功具箱---null---jack---10003
2019-01-25 17:05:00,619---INFO---finishTask---智能内部数据容器---00:03:00---tom---10004

2. 构建django数据模型web

from django.db import models

# Create your models here.
class info(models.Model):
    # 从createTime 中提取年-月-日方便查找
    time = models.CharField(max_length=15)
    createTime = models.DateTimeField()
    createSeconds = models.FloatField(default=0)
    levelName =  models.CharField(max_length=30)
    status = models.CharField(max_length=30)
    appName = models.CharField(max_length=50)
    arrangeTime = models.CharField(max_length=30)
    userName = models.CharField(max_length=30)
    serialNumber = models.CharField(max_length=30)
    # 保存上次log文件读写位置
    seek = models.IntegerField(default=0)

    def __str__(self):
        return self.appName

3. 聚合、分组查询 - annotate
info.objects.filter(status=“finishTask”).values(“appName”,“status”).annotate(Count(“serialNumber”))  等价于sql

SELECT `index_info`.`appName`, `index_info`.`status`, COUNT(`index_info`.`serialNumber`) AS `serialNumber__count` FROM `index_info` WHERE `index_info`.`status` = finishTask GROUP BY `index_info`.`appName`, `index_info`.`status` ORDER BY NULL
  • filter(条件) = where 条件
  • values(字段1,字段2) = select 字段1,字段2
  • values(字段1,字段2) .annotate(聚合函数(字段3)):
    先执行 group by 字段1,字段2 而后执行 聚合函数(字段3)

info.objects.filter(status=“finishTask”).values(“appName”,“status”).annotate(Count(“serialNumber”)).order_by("-appName")[:2] 等价于django

SELECT `index_info`.`appName`, `index_info`.`status`, COUNT(`index_info`.`serialNumber`) AS `serialNumber__count` FROM `index_info` WHERE `index_info`.`status` = finishTask GROUP BY `index_info`.`appName`, `index_info`.`status` ORDER BY `index_info`.`appName` DESC  LIMIT 2
  • order_by("-appName")[:2] = order by 字段 DESC limit 数值