解决Grafana Loki LogQL查询24小时未发日志服务的问题
解决方案
问题出在absent_over_time的工作机制上:它会对整个查询匹配到的所有日志流做判断,只要其中任意一个流在24小时内有日志,函数就会返回空结果,无法单独识别每个customer_id+service_name组合的状态。
要实现逐个检查每个服务组合的日志缺失情况,可采用以下两种方法:
方法一:模板变量循环生成独立查询
假设$customer_id和$service_name是多值变量(已配置为包含所有可能取值),使用Grafana的模板语法遍历所有组合,对每个组合单独执行absent_over_time:
{{ range $c := split $customer_id "," }} {{ range $s := split $service_name "," }} absent_over_time({customer_id="{{$c}}", service_name="{{$s}}"}[24h]) {{ if not (and (eq $c (last (split $customer_id ","))) (eq $s (last (split $service_name ",")))) }} or {{ end }} {{ end }} {{ end }}
- 原理:每个组合的查询独立执行,缺失日志的组合会返回值为
1的时间序列,有日志的组合返回空。 - 面板配置:在Grafana表格面板中,只需展示有数据的行,即可得到24小时内未发日志的服务列表。
方法二:组合对比筛选缺失项
通过生成所有可能的服务组合,再与有日志的组合做差集,直接定位缺失项:
sum by (customer_id, service_name) ( (vector(1) | label_replace("", "customer_id", "$customer_id", "", ".*") | label_replace("", "service_name", "$service_name", "", ".*")) - (sum by (customer_id, service_name) ( count_over_time({customer_id=~"$customer_id", service_name=~"$service_name"}[24h]) ) or vector(0)) )
- 原理:
- 第一部分生成所有
customer_id+service_name组合的向量,每个组合值为1; - 第二部分统计过去24小时内有日志的组合,值为日志条数(无日志则返回
0); - 两者相减后,值为
1的组合即为未发送日志的服务。
- 第一部分生成所有
- 面板配置:添加筛选条件,只显示值为
1的行。
注意事项
- 确保
$customer_id和$service_name变量开启多值模式,且包含所有需要检查的取值; - 若服务组合数量极大,方法二的性能更优,方法一的查询语句会更冗长但逻辑更直观。
内容的提问来源于stack exchange,提问作者Fabian Reifer
相关产品推荐
相关产品推荐

