3. 数据源配置:Prometheus、Loki、Elasticsearch 数据源接入与查询语言基础
在构建可观测性体系时,数据源是告警与面板的根基。本章聚焦三大核心数据源——Prometheus(指标)、Loki(日志)、Elasticsearch(搜索与分析)的接入配置,并深入对应的查询语言 PromQL 与 LogQL,为后续质量门禁与阈值优化打下数据基础。
3.1 数据源接入对比与配置要点
三种数据源在 Grafana 中的接入方式、数据模型与适用场景存在显著差异。下表梳理了核心配置参数与最佳实践:
| 数据源 | 默认端口 | 认证方式 | 核心配置项 | 数据模型 | 典型场景 |
|---|---|---|---|---|---|
| Prometheus | 9090 | Basic Auth / Bearer | URL、Scrape Interval、Timeout | 时间序列(Metric + Label) | CPU、内存、请求速率、错误率 |
| Loki | 3100 | Basic Auth / Multi-tenant | URL、Max Lines、Derived Fields | 日志流(Stream + Label) | 应用错误日志、审计日志、事件追踪 |
| Elasticsearch | 9200 | Basic Auth / | URL、Index、Time Field、Version | 文档(JSON 结构化数据) | 业务指标、全文搜索、聚合分析 |
配置建议:生产环境中,建议为每个数据源单独配置 Datasource UID,并在面板变量中引用 UID 而非名称,避免数据源重命名导致面板失效。同时,为 Prometheus 和 Loki 开启 HTTP Keep-Alive,减少连接建立开销。
3.2 Prometheus 数据源与 PromQL 基础
Prometheus 是时序指标的事实标准。接入时需确保 Grafana 与 Prometheus 网络可达,并正确配置 Scrape Interval(通常 15s-30s)与 Timeout(通常 10s)。
3.2.1 PromQL 核心概念
- Instant Vector:某一时刻的时序数据集合,如
http_requests_total{job="api"} - Range Vector:一段时间窗口内的时序数据,如
http_requests_total[5m] - Scalar:纯数值,如
1、100 - String:字符串,用于标签匹配
3.2.2 常用 PromQL 查询模式
# 瞬时向量查询:获取当前所有 API 服务的请求总数
http_requests_total{job="api"}
# 速率计算:过去 5 分钟每秒请求数
rate(http_requests_total[5m])
# 聚合查询:按状态码分组统计错误率
sum(rate(http_requests_total{status=~"5.."}[5m])) / sum(rate(http_requests_total[5m]))
# 阈值判断:返回超过 0.05 错误率的服务
(sum(rate(http_requests_total{status=~"5.."}[5m])) by (service)
/
sum(rate(http_requests_total[5m])) by (service)) > 0.05
常见陷阱:使用
rate() 时,必须确保时间窗口至少为 Scrape Interval 的 4 倍,否则结果可能不准确。例如 Scrape Interval 为 15s,则 [1m] 是安全下限。
3.3 Loki 数据源与 LogQL 基础
Loki 专为日志设计,与 Prometheus 共享标签体系。接入时需配置 Derived Fields,将日志中的 trace ID 或 request ID 提取为可点击链接,实现日志与链路追踪的联动。
3.3.1 LogQL 核心概念
- Log Stream Selector:通过标签过滤日志流,如
{app="nginx", env="prod"} - Line Filter:对日志行内容进行过滤,如
|= "ERROR"、!= "DEBUG" - Parser:解析日志内容为结构化字段,如
| json、| logfmt、| regexp - Metric Query:将日志转换为指标,如
rate({app="nginx"} |= "5xx" [5m])
3.3.2 常用 LogQL 查询模式
# 基础日志流查询:获取生产环境 Nginx 的错误日志
{app="nginx", env="prod"} |= "ERROR"
# 解析 JSON 日志并过滤特定字段
{app="api"} | json | status >= 500
# 日志速率指标:过去 5 分钟 5xx 错误日志的速率
rate({app="api"} |= "5xx" [5m])
# 聚合统计:按 service 分组统计错误日志数量
sum by (service) (count_over_time({app="api"} |= "ERROR" [5m]))
质量门禁应用:在告警规则中,使用
rate({app="api"} |= "5xx" [5m]) > 0.1 作为阈值,表示过去 5 分钟内每秒超过 0.1 条 5xx 日志时触发告警。相比固定数量阈值,速率阈值更能反映异常趋势。
3.4 Elasticsearch 数据源接入
Elasticsearch 适合存储结构化业务数据与全文搜索。接入时需指定 Index 名称(支持通配符如 nginx-*)和 Time Field(如 @timestamp)。
3.4.1 查询语言基础
Grafana 中的 Elasticsearch 数据源支持两种查询模式:
- Lucene Query:简单文本搜索,如
status:500 AND method:POST - Elasticsearch Query DSL:JSON 格式的复杂查询,支持聚合、过滤、排序
# Lucene 查询示例:查找状态码为 500 且请求方法为 POST 的日志
status:500 AND method:POST
# Query DSL 示例:按 service 分组统计错误数
{
"query": {
"bool": {
"filter": [
{"range": {"@timestamp": {"gte": "now-5m"}}},
{"term": {"status": 500}}
]
}
},
"aggs": {
"by_service": {
"terms": {"field": "service.keyword", "size": 10}
}
}
}
性能优化:在 Elasticsearch 面板中,尽量使用 Terms Aggregation 而非 Filters Aggregation,前者在大量分桶时性能更优。同时,为常用字段设置 keyword 类型,避免 text 类型导致的聚合性能问题。
3.5 数据源查询语言对比与选择
| 维度 | PromQL | LogQL | Elasticsearch Query |
|---|---|---|---|
| 数据对象 | 时序指标 | 日志流 | 文档 |
| 过滤方式 | 标签匹配 | 标签 + 行内容 | 全文搜索 + 结构化字段 |
| 聚合能力 | 强(rate、avg、quantile) | 中(rate、count_over_time) | 强(Terms、Date Histogram) |
| 告警适用性 | 最佳(趋势、速率、分位数) | 良好(异常日志速率) | 一般(适合静态阈值) |
| 学习曲线 | 中等 | 低(与 PromQL 相似) | 高(DSL 复杂) |
3.6 数据源与查询语言在质量门禁中的角色
下图展示了三种数据源如何协同支撑质量门禁的阈值优化流程:
关键洞察:在质量门禁中,PromQL 的
rate() 和 histogram_quantile() 用于动态阈值计算;LogQL 的 rate() 用于异常日志速率告警;Elasticsearch 的聚合查询用于业务指标基线分析。三者结合,可实现从指标到日志的全链路阈值优化。
3.7 数据源配置最佳实践清单
- 统一标签命名规范:Prometheus 与 Loki 共享标签体系,建议使用
service、env、region等通用标签,便于跨数据源关联。 - 配置 Derived Fields:在 Loki 数据源中,将 trace ID 提取为派生字段,实现日志与 Tempo 或 Jaeger 的链路跳转。
- 启用缓存:为 Elasticsearch 数据源开启查询缓存,减少重复查询对 ES 集群的压力。
- 设置最大行数:Loki 数据源中设置
Max Lines为 1000-5000,避免返回过多日志导致面板渲染缓慢。 - 使用变量:在面板中使用
$datasource变量引用数据源 UID,便于在不同环境间迁移。
安全提醒:避免在 Grafana 数据源配置中直接使用明文密码。建议使用 Grafana 加密 API 或 环境变量 注入敏感信息,如
${PROM_PASSWORD}。