操作场景
CLS 已兼容 OpenTelemetry OTLP/HTTP 协议,开发者只需使用标准 OTLP Exporter,配置对应的 Endpoint、Authorization 和 topic_id 即可完成上报,无需引入 CLS 专属 SDK。本文介绍如何在 Go 项目中,使用 OpenTelemetry(OTLP)SDK 将 Trace(链路追踪)、Metric(指标)、Log(日志)三类可观测数据上报至腾讯云日志服务(Cloud Log Service,CLS)。三类数据上报统一规范如下:
数据类型 | SDK 模块 | Exporter |
Log | go.opentelemetry.io/otel/sdk/log | otlploghttp |
Trace | go.opentelemetry.io/otel/sdk/trace | otlptracehttp |
Metric | go.opentelemetry.io/otel/sdk/metric | otlpmetrichttp |
前提条件
已注册腾讯云账号并开通日志服务(CLS)。
已在目标地域创建日志集和日志主题,并记录每个主题的
topic_id。具体操作请参见 创建日志主题。已获取子账号的 SecretId(AK)和 SecretKey(SK)。具体操作请参见 访问密钥。
注意:
不建议把 AK/SK 硬编码在代码中或提交到代码仓库,建议通过环境变量或密钥管理服务注入。
本地已安装 Go 1.21及以上版本。
操作步骤
步骤1:确定上报 Endpoint
CLS 提供公网和内网两类接入点,根据网络环境选择其中一种。
网络类型 | 域名格式 | 适用场景 |
公网 | <region>.cls.tencentcs.com | 本地调试、非腾讯云环境、跨云上报 |
内网 | <region>.cls.tencentyun.com | 部署在同地域腾讯云 VPC/CVM 中,免公网流量费用、低延迟 |
常见地域 Endpoint 对照表如下。
地域 | 公网 Endpoint | 内网 Endpoint |
广州 | ap-guangzhou.cls.tencentcs.com | ap-guangzhou.cls.tencentyun.com |
上海 | ap-shanghai.cls.tencentcs.com | ap-shanghai.cls.tencentyun.com |
北京 | ap-beijing.cls.tencentcs.com | ap-beijing.cls.tencentyun.com |
新加坡 | ap-singapore.cls.tencentcs.com | ap-singapore.cls.tencentyun.com |
注意:
内网接入点仅在同地域的腾讯云内网中可访问,跨地域或公网环境请使用公网接入点。
步骤2:安装依赖
在项目目录下执行以下命令安装 OpenTelemetry 相关依赖(版本以最新稳定版为准)。
# OpenTelemetry 核心go get go.opentelemetry.io/otelgo get go.opentelemetry.io/otel/sdk# Loggo get go.opentelemetry.io/otel/loggo get go.opentelemetry.io/otel/sdk/loggo get go.opentelemetry.io/otel/exporters/otlp/otlplog/otlploghttp# Tracego get go.opentelemetry.io/otel/sdk/tracego get go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracehttp# Metricgo get go.opentelemetry.io/otel/sdk/metricgo get go.opentelemetry.io/otel/exporters/otlp/otlpmetric/otlpmetrichttp# 语义约定go get go.opentelemetry.io/otel/semconv/v1.37.0
步骤3:实现鉴权函数
CLS OTLP 接入点使用 HTTP Basic 鉴权,请求头格式如下。
Authorization: Basic base64(SecretId:SecretKey)topic_id: <您的 topic_id>
在 Go 项目中实现鉴权函数。
import "encoding/base64"func basicAuth(username, password string) string {auth := username + ":" + passwordreturn base64.StdEncoding.EncodeToString([]byte(auth))}
步骤4:接入 Log(日志)
创建 OTLP/HTTP Log Exporter 并挂载到 LoggerProvider。
package mainimport ("context""go.opentelemetry.io/otel/exporters/otlp/otlplog/otlploghttp")func otlplog() {ctx := context.Background()// 创建 OTLP/HTTP Log Exporterexporter, err := otlploghttp.New(ctx,otlploghttp.WithEndpoint("ap-guangzhou.cls.tencentcs.com"),otlploghttp.WithHeaders(map[string]string{"Authorization": "Basic " + basicAuth("<SecretId>", "<SecretKey>"),"topic_id": "<log topic_id>",}),)if err != nil {panic(err)}_ = exporter// 后续使用 sdklog.NewLoggerProvider(...) 将 exporter 挂载到 LoggerProvider 即可上报}
关键参数说明:
参数 | 说明 |
Endpoint | CLS OTLP 接入点域名,不需要携带 http:// 前缀 |
Authorization | Basic base64(AK:SK) 格式的鉴权头 |
topic_id | 日志数据对应的 CLS 日志主题 ID |
Processor 选择:
SimpleProcessor: 同步导出,写一条上报一条,适合调试环境。
BatchProcessor(推荐): 批量异步导出,降低上报频次,适合生产环境。
sdklog.WithProcessor(sdklog.NewBatchProcessor(exporter,sdklog.WithExportInterval(5*time.Second),sdklog.WithExportMaxBatchSize(512),))
步骤5:接入 Trace(链路追踪)
创建 OTLP/HTTP Trace Exporter 并挂载到 TracerProvider。
package mainimport ("context""log""go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracehttp")func otlptrace() {ctx := context.Background()// 创建 OTLP/HTTP Trace ExportertraceExporter, err := otlptracehttp.New(ctx,otlptracehttp.WithEndpoint("ap-guangzhou.cls.tencentcs.com"),otlptracehttp.WithHeaders(map[string]string{"Authorization": "Basic " + basicAuth("<SecretId>", "<SecretKey>"),"topic_id": "<trace topic_id>",}),)if err != nil {log.Printf("create trace exporter failed: %v", err)return}_ = traceExporter// 后续通过 sdktrace.NewTracerProvider(...) 挂载 exporter 即可上报}
采样器(Sampler)选择:
采样器 | 说明 |
AlwaysSample() | 全量采样,适合测试或低流量服务 |
NeverSample() | 全部不采样 |
TraceIDRatioBased(0.1) | 按比例采样(10%),生产推荐 |
ParentBased(...) | 根据父 Span 决定,适合分布式链路场景 |
SpanProcessor 配置(生产推荐 BatchSpanProcessor):
sdktrace.WithSpanProcessor(sdktrace.NewBatchSpanProcessor(traceExporter,sdktrace.WithMaxExportBatchSize(512),sdktrace.WithBatchTimeout(5*time.Second),))
步骤6:接入 Metric(指标)
创建 OTLP/HTTP Metric Exporter 并挂载到 MeterProvider。
package mainimport ("context""go.opentelemetry.io/otel/exporters/otlp/otlpmetric/otlpmetrichttp")func otlpMetric() {ctx := context.Background()// 创建 OTLP/HTTP Metric Exporterexporter, err := otlpmetrichttp.New(ctx,otlpmetrichttp.WithEndpoint("ap-guangzhou.cls.tencentcs.com"),otlpmetrichttp.WithHeaders(map[string]string{"Authorization": "Basic " + basicAuth("<SecretId>", "<SecretKey>"),"topic_id": "<metric topic_id>",}),)if err != nil {panic(err)}_ = exporter// 后续通过 metric.NewMeterProvider(metric.WithReader(metric.NewPeriodicReader(exporter, ...))) 挂载 exporter 即可周期性上报}
常用指标类型:
类型 | API | 适用场景 |
Counter | Int64Counter / Float64Counter | 单调递增,如请求总数 |
UpDownCounter | Int64UpDownCounter | 可增可减,如连接数 |
Histogram | Float64Histogram | 分布统计,如耗时 |
Gauge(观察器) | Float64ObservableGauge | 瞬时值,如 CPU 使用率 |
PeriodicReader 配置建议:
metric.NewPeriodicReader(exporter,metric.WithInterval(15*time.Second), // 生产建议 15~30smetric.WithTimeout(5*time.Second),)
步骤7:配置 Resource 公共属性
建议三类数据使用统一的 Resource,便于在 CLS 侧关联分析。
res, _ := resource.New(ctx,resource.WithFromEnv(),resource.WithProcess(),resource.WithTelemetrySDK(),resource.WithHost(),resource.WithAttributes(semconv.ServiceNameKey.String("my-service"),semconv.ServiceNamespaceKey.String("Production"),semconv.ServiceVersionKey.String("v1.0.0"),semconv.DeploymentEnvironmentKey.String("prod"),),)
Resource 关键字段说明:
字段 | 说明 |
service.name | 服务名,必填 |
service.namespace | 服务命名空间(如环境名) |
service.version | 服务版本 |
常见问题
上报401 / 403鉴权失败
检查 AK/SK 是否正确。
确认该子账号已授权 CLS 写入权限(
cls:PushLog 等)。Authorization 头格式必须为
Basic <base64(AK:SK)>。上报404或 topic not found
topic_id 与 Endpoint 的地域不一致。需保证 topic 所属地域与 Endpoint 地域相同。无数据或数据延迟
SimpleProcessor 下若进程退出过快,可能导致最后一批数据未发送,请确保调用
Shutdown。BatchProcessor 有批处理间隔,出现短暂延迟属于正常现象。
Endpoint 是否需要带协议前缀
OTLP/HTTP Exporter 的
WithEndpoint 只传域名,不要带 http:// 或 https://。默认使用 HTTPS 上报,无需显式添加协议选项。
如果确实需要明文(HTTP)上报(例如测试环境),可添加
WithInsecure() 选项。公网和内网接入点如何选择
内网(
<region>.cls.tencentyun.com):部署在同地域腾讯云 VPC/CVM 内推荐使用,免公网流量费用、延迟更低。公网(
<region>.cls.tencentcs.com):本地调试、非腾讯云环境或跨云厂商环境使用。Endpoint 的地域必须与
topic_id 所属地域保持一致,否则会报 topic not found。跨地域上报
如需使用跨地域加速接入点,可在请求 Header 中添加源地域标识:
"x-cross-region": "ap-guangzhou"