使用OpenTelemetry来监控GoLang应用

1. 前言

我曾经写过一篇关于OpenTelemetry的文章,介绍如何使用基于eBPF的绝对无侵入方式来监控各种语言的应用。这种方式仍然是OpenTelemetry非侵入式监控GoLang应用的主要方式之一,但还有一种不修改应用代码来监控GoLang应用的方法,也比较成熟并被广泛使用,这里一并介绍一下。

2. 使用基于eBPF的绝对无侵入方式(OBI)

这是对我原来的文章《OpenTelemetry OBI - 非侵入式监控各种语言应用的神器的简单回顾,详细信息请参照原文。

首先要下载OBI工具,到 OBI 的发行网页(Releases · open-telemetry/opentelemetry-ebpf-instrumentation · GitHub),根据您的平台选择最新的发行版来下载。比如对于最常见的平台(amd64) 和当前最新的版本好v0.10.0, 下载:obi-v0.10.0-linux-amd64.tar.gz

配饰OBI的方式非常多。可以采用环境变量,也可以用配置文件。对于这个简单的测试,我使用了以下的配置文件:obi.yaml

XML 复制代码
discovery:
  instrument:
    - open_ports: 8080,9090,28080
log_level: DEBUG

ebpf:
  context_propagation: all

otel_traces_export:
  endpoint: http://localhost:4318

otel_metrics_export:
  endpoint: http://loalhost:4318

注意:

  • 这个配置文件说明我要监控8080、9090和28080三个端口的应用。
  • 通过OTLP协议发送信息到OpenTelemetry Collector或者OpenTelemetry后端,这个例子里是http://localhost:4318

以下是运行OBI的命令(在应用所在的Linux主机上运行,注意应用的端口必须在 obi.yaml 设置的范围之内):

bash 复制代码
sudo ./obi --config=./obi.yaml

至于配置OBI的详细说明,请参照官方文档:Configure OBI | OpenTelemetry

为了让OpenTelemetry很好的区分不同的应用,请在启动应用之前,设置OTEL_SERVICE_NAME环境变量。例如:

复制代码
export OTEL_SERVICE_NAME=my-godemo
./app

这样,如果访问您的程序,在OpenTelemetry Collector或者OpenTelemetry后端,就可以发现大量的metrics和traces。

3. 使用编译时无侵入插桩(Compile-Time Instrumentation)

3.1 概述

这种方式也不需要修改应用代码,只是需要稍微调整一下编译的命令。

没有额外配置的情况下,编译时无侵入插桩 otelc 会自动扫描并识别项目中引入的以下依赖,并自动为你应用内置的 Hook 规则:

  1. HTTP 框架
  • net/http(标准库)、github.com/gin-gonic/gin

  • 自动拦截 HTTP Request/Response,自动从 Header 提取/注入 TraceContext

  1. RPC 框架
  1. 数据库/SQL
  1. 缓存/MQ
  1. 日志与指标

3.2 下载 otelc 工具

到"Releases · open-telemetry/opentelemetry-go-compile-instrumentation · GitHub"选择和您的平台匹配的otelc的最高版本下载即可。对于我使用的Linux平台,大致的命令如下:

复制代码
wget https://github.com/open-telemetry/opentelemetry-go-compile-instrumentation/releases/download/v1.0.1/otelc-linux-amd64
mv otelc-linux-amd64 otelc
chmod +x otelc

如果为了方便调用,可以把 otelc 放到 /usr/bin 下。

3.3 使用 otelc 编译GoLang代码

如果您原来的编译命令是:

复制代码
go build -o httpsvr 

那就改成:

复制代码
otelc go build -o httpsvr 

自动插桩在编译时完成!

3.4 运行被编译时插桩的程序

如果您原来只是简单地执行:

复制代码
./httpsvr

现在还需要指定您的应用的OpenTelemetry服务名(这里假设是my-service),还有如何发送数据到OpenTelemetry Collector或者OpenTelemetry后端(这里假设是http://localhost:4318)。那么需要的命令是:

复制代码
export OTEL_SERVICE_NAME=my-service
export OTEL_TRACES_EXPORTER=otlp
export OTEL_METRICS_EXPORTER=otlp
export OTEL_LOGS_EXPORTER=otlp
export OTEL_EXPORTER_OTLP_ENDPOINT="http://localhost:4318"
export OTEL_EXPORTER_OTLP_PROTOCOL=http/protobuf

./httpsvr

好了,这时候如果访问您的程序,您就可以在OpenTelemetry Collector或者OpenTelemetry后端看到大量metrics和traces了。

3.5 编译时插装还可以使用配置文件进行增强

通过使用编译时插装的配置文件,可以给指定的任意函数加trace。但是目前没有官方提供的通用包,不但要有配置, 还需要自己编写一些代码。 虽然加trace不难, 但是拼接trace和span有难度。我这里就先不写了,详情请参考:Go compile-time instrumentation | OpenTelemetry

4. 比较"编译时无侵入插桩 (otelc)"和"基于 eBPF 的无侵入插桩 (OBI)"

  1. "编译时无侵入插桩 (otelc)"的强项
  • Go 框架的理解
  • 自定义函数插桩(目前还没有通用的代码)
  1. "基于 eBPF 的无侵入插桩 (OBI)"的强项
  • 真正零侵入,简单易行
  • 跨语言
  • 操作系统底层网络连接的感知能力

您可以配合两种插桩方式,为了避免一个调用多个trace,可以禁止一部分"编译时无侵入插桩 (otelc)",在启动引用前可以增加如下的环境变量:

复制代码
export OTEL_GO_DISABLED_INSTRUMENTATIONS=nethttp,grpc

5. 总结

本文介绍了两种非侵入式监控GoLang应用的方法:基于eBPF的绝对无侵入方式(OBI)和编译时无侵入插桩(otelc)。OBI通过下载工具并配置监控端口,无需修改代码即可收集应用指标和追踪数据。编译时插桩则需在构建阶段使用otelc工具,自动为常见框架添加监控功能,运行时通过环境变量配置数据导出。两种方式各有优势:OBI简单跨语言,otelc对Go框架支持更深入且支持自定义函数插桩。文章详细说明了两种方法的配置步骤,并建议可根据需求配合使用,同时提供了相关官方文档链接供进一步参考。

相关推荐
羑悻的小杀马特2 小时前
把随身WiFi改成网盘聚合器:中兴F50挂载本地存储+夸克网盘实战
运维·服务器·人工智能·网盘·openlist
Yana.nice10 小时前
Linux 只保留 30 天内日志(find命令删除日志文件)
linux·运维·chrome
2601_9605679613 小时前
电商套图自动化效率的工程量化分析——从逐张生成到批量套图的架构演进
运维·架构·自动化
吳所畏惧14 小时前
宝塔面板Redis密码修改指南:SSH命令修改 vs 面板UI界面修改,哪个更靠谱?
运维·服务器·数据库·redis·缓存·ssh
HiDev_14 小时前
【非标自动化】2、认识元器件(确定目标)
运维·自动化
ttwuai14 小时前
Cursor 生成 CRUD 后,Go 后台接口别只测 200:JWT、RBAC 和 tenant_id 怎么验
开发语言·后端·golang
Zhang~Ling15 小时前
从 fopen 到 struct file:从零开始拆解 Linux 文件 I/O
linux·运维·服务器
爱写代码的森15 小时前
蒙三方库 | harmony-utils之FileUtil文件重命名与属性查询详解
linux·运维·服务器·华为·harmonyos·鸿蒙·huawei
中微极客15 小时前
2026主流AI Agent框架技术选型与性能对比
运维·网络·人工智能