用一个 OpenTelemetry Collector 同时接收日志、指标和链路数据,统一清洗、脱敏后上报炬鲸 OBSERVE,避免每类信号各配一套采集器,附完整配置与排错清单。
接入可观测平台时,最常见的坑是“三套采集器”:日志用 Filebeat,指标用 node_exporter,链路用 Jaeger Agent。三套配置、三套升级、三套故障排查,运维成本随服务数量线性增长。更糟的是,三套采集器的数据格式、时间戳、标签命名各不相同,到了后端还得再对齐一遍。
OpenTelemetry Collector 把日志、指标、链路三类信号统一到一个组件里:receiver 负责收,processor 负责清洗、脱敏、采样,exporter 负责发。改一个 YAML 就能调整整条采集链路,而且完全开源、厂商中立,不绑定任何后端。即便将来换后端,也只需换 exporter,采集侧零改动。
顺带一提,OpenTelemetry 是 CNCF 旗下的开放标准,近年已成为可观测数据采集的事实标准,主流语言 SDK 和云厂商都已支持。选它做接入层,等于把“采集”和“后端”解耦:团队只需要维护这一套采集配置,后端选型可以独立演进。
先装 Collector。以 Linux 二进制为例:
wget https://github.com/open-telemetry/opentelemetry-collector-releases/releases/latest/download/otelcol_linux_amd64.tar.gz
tar -xzf otelcol_linux_amd64.tar.gz
sudo mv otelcol /usr/local/bin/
然后写 config.yaml。下面这份配置同时收三类信号,统一上报到炬鲸 OBSERVE:
receivers:
otlp:
protocols: { grpc: { endpoint: "0.0.0.0:4317" }, http: { endpoint: "0.0.0.0:4318" } }
filelog:
include: ["/var/log/app/*.log"]
start_at: end
prometheus:
config:
scrape_configs:
- job_name: "node"
static_configs: [{ targets: ["localhost:9100"] }]
processors:
batch:
timeout: 5s
send_batch_size: 1024
attributes:
actions:
- key: "card_number"
action: "delete" # 脱敏:删除敏感字段
- key: "env"
action: "upsert"
value: "prod"
exporters:
otlphttp:
endpoint: "https://ob.example.com/otel"
headers: { "Authorization": "Bearer <你的接入Token>" }
service:
pipelines:
traces: { receivers: [otlp], processors: [batch, attributes], exporters: [otlphttp] }
metrics: { receivers: [otlp, prometheus], processors: [batch, attributes], exporters: [otlphttp] }
logs: { receivers: [otlp, filelog], processors: [batch, attributes], exporters: [otlphttp] }
要点逐条说:
start_at: end 表示只收新日志,避免首次启动把历史文件全量重放card_number 这类字段直接删除,env: prod 这类标签统一补上,避免各服务命名不一致应用不需要关心 Collector 的细节,只要把数据发到本机 4317/4318 端口即可。以 Spring Boot 为例,引入 OpenTelemetry Java Agent:
java -javaagent:opentelemetry-javaagent.jar \
-Dotel.traces.exporter=otlp \
-Dotel.metrics.exporter=otlp \
-Dotel.logs.exporter=otlp \
-Dotel.exporter.otlp.endpoint=http://localhost:4317 \
-jar app.jar
其他语言同理:Python 用 opentelemetry-distro,Go 用 otel SDK,Node.js 用 @opentelemetry/sdk-node——都是“数据发到本机 OTLP 端口”这一个约定,后端细节全部由 Collector 处理。
日志走 OTLP 需要 Logback 配合 otel appender,但更省事的做法是让应用继续写本地文件,由 Collector 的 filelog 统一采集——应用零改动,采集逻辑全部收口到 Collector。我们更推荐后者起步,改动最小、回退最方便。
生产、预发、测试环境最好用不同的 namespace 或 env 标签区分,而不是各起一套 Collector。Collector 本身可以按环境分开部署(生产一台、预发一台),但上报时统一带上 env 标签,后端就能按环境过滤。服务命名也建议统一:service.name 用稳定的服务标识,不要带版本号或机器名,否则链路追踪里同一个服务会被拆成十几个节点。
Kubernetes 场景下,推荐用 DaemonSet 把 Collector 部署到每个节点:filelog receiver 采集 Pod 落盘的日志,otlp receiver 接收应用侧上报,应用通过本节点地址发现 Collector。这样既省跨节点网络开销,采集压力也均匀分摊。
默认配置能跑,但生产环境建议先调两个点:batch processor 的 send_batch_size 和 exporter 的队列长度。日志量大时,批处理能显著降低上报次数和 CPU 占用。
endpoint 和 Authorization 头是否写对,再看 Collector 日志里有没有 4xx/5xxstart_at 和 batch 参数接入完成后,回到炬鲸 OBSERVE 控制台,日志、指标、链路应该能在同一个服务视图里看到,并且能用类 SQL 统一检索。