10、监控与告警系统:Prometheus + Grafana 指标采集,日志聚合(ELK Stack),业务告警规则设计

做量化交易系统,最怕什么?

怕半夜三点系统崩了,你还在睡觉。怕策略跑偏了,亏了一晚上你才发现。怕日志堆成山,出了事根本不知道从哪查起。

我做了这么多年做市商系统,可以负责任地告诉你:监控和告警,比策略本身还重要。策略亏钱可以改,系统崩了没发现,那才是真灾难。

这一章,我们就来聊聊怎么把监控体系搭起来。说白了,就是三件事:指标采集、日志聚合、告警规则

核心思路:用 Prometheus 抓业务指标,用 Grafana 展示大盘,用 ELK 管日志,最后用 Alertmanager 把告警推到你手机上。

10.1 为什么需要三层监控?

我个人习惯把监控分成三层:

  • 基础设施层:CPU、内存、磁盘、网络。这些挂了,啥都别谈。
  • 应用层:订单处理延迟、撮合成功率、WebSocket 连接数。这些是系统的「心跳」。
  • 业务层:持仓盈亏、资金费率、敞口风险。这些直接关系到赚不赚钱。

你想想看,如果只盯着业务层,服务器磁盘满了你都不知道。反过来,只看基础设施,策略跑偏了你也发现不了。三层都得看。

我在项目中遇到过最坑的一次:服务器 CPU 负载正常,内存也够,但订单处理延迟从 2ms 飙到了 500ms。为什么?因为网卡队列被某个日志进程占满了。如果只看 CPU 和内存,你永远找不到原因。

10.2 Prometheus + Grafana:指标采集与可视化

Prometheus 这东西,说白了就是一个时序数据库。它每隔几秒去拉一次数据,存下来,然后 Grafana 负责画图。

10.2.1 暴露指标端点

你的交易系统需要暴露一个 /metrics 接口,Prometheus 会来抓。我一般用 Python 的 prometheus_client 库,几行代码搞定:

from prometheus_client import start_http_server, Gauge, Counter, Histogram
import random
import time

# 定义指标
order_latency = Histogram('order_latency_seconds', '订单处理延迟', buckets=[0.001, 0.005, 0.01, 0.05, 0.1])
open_orders = Gauge('open_orders_total', '当前挂单数量')
trade_volume = Counter('trade_volume_usdt_total', '累计交易量', ['symbol'])

# 模拟业务逻辑
def process_order():
    with order_latency.time():
        time.sleep(random.uniform(0.001, 0.05))
        open_orders.set(random.randint(0, 100))
        trade_volume.labels(symbol='BTCUSDT').inc(random.uniform(100, 1000))

if __name__ == '__main__':
    start_http_server(8000)  # 暴露 /metrics 端口
    while True:
        process_order()
        time.sleep(1)
避坑指南:我曾经把 Histogram 的 buckets 设得太宽,导致延迟分布看不清楚。建议根据业务实际范围来设,比如做市商系统延迟通常在 1ms-50ms 之间,buckets 就设在这个区间。

10.2.2 Prometheus 配置

配置文件 prometheus.yml 里,告诉它去哪抓数据:

scrape_configs:
  - job_name: 'market_maker'
    scrape_interval: 5s
    static_configs:
      - targets: ['localhost:8000']

嗯,这里要注意:scrape_interval 别设太短,5秒足够了。太频繁反而增加系统开销。

10.2.3 Grafana 仪表盘

Grafana 这边,我习惯建三个 Dashboard:

  • 系统概览:CPU、内存、网络、磁盘 IO
  • 交易监控:订单延迟分布、挂单数量、成交笔数
  • 风控看板:敞口、盈亏、资金费率

每个 Dashboard 配上告警阈值,比如「订单延迟 P99 超过 100ms」就标红。

10.3 ELK Stack:日志聚合与分析

指标是数字,日志是文字。两者缺一不可。

ELK 就是 Elasticsearch + Logstash + Kibana。流程很简单:

  • Logstash 收集日志,解析成结构化数据
  • Elasticsearch 存起来,支持全文搜索
  • Kibana 负责展示和查询

10.3.1 日志格式规范

我要求团队所有日志必须用 JSON 格式。为什么?因为 Logstash 解析 JSON 最方便,而且字段清晰。

{
  "timestamp": "2025-01-15T10:30:00.123Z",
  "level": "ERROR",
  "module": "order_executor",
  "message": "订单提交失败",
  "order_id": "ORD123456",
  "error_code": "INSUFFICIENT_BALANCE",
  "latency_ms": 45
}
注意:千万不要把敏感信息写进日志,比如 API Key、私钥。我曾经见过有人把私钥打到了日志里,还好发现得早,不然就出大事了。

10.3.2 Logstash 配置示例

input {
  beats {
    port => 5044
  }
}

filter {
  json {
    source => "message"
  }
  date {
    match => ["timestamp", "ISO8601"]
  }
}

output {
  elasticsearch {
    hosts => ["localhost:9200"]
    index => "market-maker-%{+YYYY.MM.dd}"
  }
}

Logstash 的 filter 很强大。你可以用它做字段提取、类型转换、甚至数据脱敏。我个人习惯把 latency_ms 这种数值字段单独提取出来,方便在 Kibana 里做聚合分析。

10.4 业务告警规则设计

告警不是越多越好。告警太多,人会麻木,最后变成「狼来了」。

我总结了一套规则:只告警那些需要人干预的事情。系统自己能恢复的,别吵我。

10.4.1 告警分级

级别 响应时间 示例
P0(致命) 立即处理 系统宕机、数据库连接失败、持仓敞口超限
P1(严重) 15分钟内 订单延迟 > 500ms、WebSocket 断连
P2(警告) 1小时内 磁盘使用率 > 80%、内存使用率 > 90%
P3(通知) 次日处理 日志中出现异常模式、交易量异常波动

10.4.2 Prometheus 告警规则

alert.rules.yml 里定义:

groups:
  - name: market_maker_alerts
    rules:
      - alert: HighOrderLatency
        expr: histogram_quantile(0.99, rate(order_latency_seconds_bucket[5m])) > 0.1
        for: 2m
        labels:
          severity: P1
        annotations:
          summary: "订单延迟 P99 超过 100ms"
          description: "当前延迟 {{ $value }}s"

      - alert: OpenOrdersTooHigh
        expr: open_orders_total > 500
        for: 1m
        labels:
          severity: P2
        annotations:
          summary: "挂单数量超过 500"

这里有个细节:for: 2m 表示持续 2 分钟才触发告警。为什么要加这个?因为瞬时抖动很正常,持续异常才需要处理。我刚开始做的时候没加这个,结果半夜被瞬时的网络抖动吵醒了好几次。

10.4.3 告警通知渠道

Alertmanager 支持多种通知方式。我个人推荐:

  • P0/P1:电话 + 短信 + 企业微信/钉钉
  • P2:企业微信/钉钉
  • P3:邮件,第二天看就行
避坑指南:我曾经把所有告警都发到同一个群里,结果 P3 的邮件通知把 P0 的电话告警淹没了。后来我分了三个群,每个群只接收对应级别的告警,效果好了很多。

10.5 整体架构图

下面这张图,是我做监控系统时的标准架构。你可以照着搭:

交易系统 /metrics 端点 Prometheus 指标采集 & 告警规则 Grafana 可视化仪表盘 拉取指标 数据源 Alertmanager 告警路由 & 通知 电话 / 短信 / 微信 通知渠道 Logstash Elasticsearch Kibana 日志推送 业务系统 指标采集 告警管理 日志系统

10.6 实战建议

最后,给你几个我踩过坑之后总结的建议:

  • 先搭监控,再写策略。没有监控的策略,就像闭着眼睛开车。
  • 告警规则要迭代。刚开始可以松一点,慢慢收紧。别一上来就设一堆规则,你会被烦死的。
  • 日志要保留至少 30 天。很多问题不是当天能发现的,需要回溯历史数据。
  • 定期演练告警。我每季度会做一次「断网演练」,看看告警能不能正常触发,通知能不能正常收到。
一句话总结:监控系统不是摆设,它是你的「夜间值班员」。搭好了,你可以安心睡觉;搭不好,你就等着半夜被电话吵醒吧。

无相订单流研究社 微信Lucian808555