下载安卓APP箭头
箭头给我发消息

客服QQ:3315713922

在 Kubernetes 中无侵入安装 OpenTelemetry 探针,你学会了吗?

作者:匿名     来源: 云计算点击数:306发布时间: 2023-12-11 15:28:21

标签: APIsSDKs

  OpenTelemetry Operator 通过 CRD(OpenTelemetryCollector[3]、Instrumentation[4]、OpAMPBridge[5]) 实现在 Kubernetes 集群中自动部署和管理 OpenTelemetry Collector;在工作负载中自动安装 OpenTelemetry 探针。

  背景

  OpenTelemetry 探针

  OpenTelemetry(简称 Otel,最新的版本是 1.27) 是一个用于观察性的开源项目,提供了一套工具、APIs 和 SDKs,用于收集、处理和导出遥测数据(如指标、日志和追踪信息)。应用程序遥测数据(如追踪、指标和日志)的收集是通过探针来完成的,探针通常以库的形式集成到应用程序中,自动捕获重要信息协助监控和调试。OpenTelemetry 探针支持市面上大多数的编程语言,探针的安装(通常被称为插桩,Instrumentation)分为手动和自动两种方式。

  手动插桩:指开发者直接在其应用程序代码中显式地添加遥测数据收集的代码,需要手动完成 SDK 初始化、插入追踪点、添加上下文信息等一系列操作。

  自动插桩:利用 OpenTelemetry 提供的库自动捕获应用程序的遥测数据,无需或只需很少的代码更改。比如,Java 通过 `javaagent` 实现探针的自动安装[1]。

  二者各有优劣:手动插桩适用于需要高度定制和精确控制遥测数据收集的场景;自动插桩适合快速启动和简化集成,特别是在使用标准框架和库的应用程序中。

  OpenTelemetry Operator 介绍

  OpenTelemetry Operator[2] 是一个为了简化 OpenTelemetry 组件在 Kubernetes 环境中的部署和管理而设计的 Kubernetes Operator。

  OpenTelemetry Operator 通过 CRD(OpenTelemetryCollector[3]、Instrumentation[4]、OpAMPBridge[5]) 实现在 Kubernetes 集群中自动部署和管理 OpenTelemetry Collector;在工作负载中自动安装 OpenTelemetry 探针。

  今天我们就将体验如何使用 OpenTelemetry Operator 自动安装探针,实现链路跟踪。

  演示

  架构

  这是演示的架构,Otel 提供了 多种语言的 instrumentation SDK[6],这篇文章中我们将使用 Java 和 Go 两种语言的应用。这两种语言会使用全自动和半自动的注入安装:

  Java 全自动注入安装,Otel Operator 通过使用 init container 引入 sdk ,并通过 JAVA_TOOL_OPTIONS 来指定 javaagent 来插桩。这里将使用 pinakispecial/spring-boot-rest 镜像来运行一个简单的 Spring Boot REST 服务。

  Go 半自动注入安装,为什么是半自动?Go 的全自动是通过 eBPF 的方式实现的:在 Pod 注入独立的容器,加载 BPF 程序。但是 eBPF 的实现对内核要求十分苛刻 5.4 - 5.14。这里演示半自动的方式:手动引入 Go instrumentation SDK[7],自动注入配置[8]。

  

图片

  Jaeger

  为了便于演示这里使用 jaegertracing/all-in-one 镜像来部署 Jaeger,这个镜像包含了 Jaeger 收集器、内存存储、查询服务和 UI 等组件,非常适合开发和测试使用。

  通过环境变量 COLLECTOR_OTLP_ENABLED 启动对 OTLP(OpenTelemetry Protocol)[9] 的支持,OTEL 在 8。

  复制

  1.  kubectl apply -f - <

  2.  apiVersion: apps/v1

  3.  kind: Deployment

  4.  metadata:

  5.  name: jaeger

  6.  spec:

  7.  replicas: 1

  8.  selector:

  9.  matchLabels:

  10.  app: jaeger

  11.  template:

  12.  metadata:

  13.  labels:

  14.  app: jaeger

  15.  spec:

  16.  containers:

  17.  - name: jaeger

  18.  image: jaegertracing/all-in-one:latest

  19.  env:

  20.  - name: COLLECTOR_OTLP_ENABLED

  21.  value: "true"

  22.  ports:

  23.  - containerPort: 16686

  24.  - containerPort: 14268

  25.  ---

  26.  apiVersion: v1

  27.  kind: Service

  28.  metadata:

  29.  name: jaeger

  30.  spec:

  31.  selector:

  32.  app: jaeger

  33.  type: ClusterIP

  34.  ports:

  35.  - name: ui

  36.  port: 16686

  37.  targetPort: 16686

  38.  - name: collector

  39.  port: 14268

  40.  targetPort: 14268

  41.  - name: http

  42.  protocol: TCP

  43.  port: 4318

  44.  targetPort: 4318

  45.  - name: grpc

  46.  protocol: TCP

  47.  port: 4317

  48.  targetPort: 4317

  49.  EOF

  安装 cert-manager

  Otel Operator 依赖 cert-manager 进行证书的管理,安装 operator 之前需要安装 cert-manager。

  复制

  1.  kubectl apply -f https://github.com/cert-manager/cert-manager/releases/download/v1.13.2/cert-manager.yaml

  安装 OpenTelemetry Operator

  执行下面命令安装 Otel Operator

  复制

  1.  kubectl apply -f https://github.com/open-telemetry/opentelemetry-operator/releases/latest/download/opentelemetry-operator.yaml

  配置 OpenTelemetry Collector

  通过创建 CR OpenTelemetryCollector 来配置 Otel 的采集器,这里我们配置了:

  otel 接收器:支持 grpc(端口 4317)和 http(端口 4318)

  memory_limiter 和 batch 处理器,但是为了方便快速查看数据,这两个并没有启用,仅作展示用。

  debug 和 otlp/jaeger 的输出器,分别用于在标准输出中打印信息和使用 otlp 协议输出到 Jaeger。

  pipeline 服务,用于配置跟踪数据的处理流程:接收、处理和输出。

  复制

  1.  kubectl apply -f - <

  2.  apiVersion: opentelemetry.io/v1alpha1

  3.  kind: OpenTelemetryCollector

  4.  metadata:

  5.  name: otel

  6.  spec:

  7.  config: |

  8.  receivers:

  9.  otlp:

  10.  protocols:

  11.  grpc:

  12.  http:

  13.  processors:

  14.  memory_limiter:

  15.  check_interval: 1s

  16.  limit_percentage: 75

  17.  spike_limit_percentage: 15

  18.  batch:

  19.  send_batch_size: 10000

  20.  timeout: 10s

      21.

  22.  exporters:

  23.  debug:

  24.  otlp/jaeger:

  25.  endpoint: "jaeger.default:4317"

  26.  tls:

  27.  insecure: true

      28.

  29.  service:

  30.  pipelines:

  31.  traces:

  32.  receivers: [otlp]

  33.  processors: []

  34.  exporters: [debug,otlp/jaeger]

  35.  EOF

  创建 CR OpenTelemetryCollector 后,Otel Operator 会创建一个 deployment 和 多个 service。

  复制

  1.  kubectl get deployment,service -l app.kubernetes.io/compnotallow=opentelemetry-collector

  2.  NAME READY UP-TO-DATE AVAILABLE AGE

  3.  deployment.apps/otel-collector 1/1 1 1 12h

      4.

  5.  NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE

  6.  service/otel-collector ClusterIP 10.43.152.81 4317/TCP,4318/TCP,8889/TCP,9411/TCP 12h

  7.  service/otel-collector-headless ClusterIP None 4317/TCP,4318/TCP,8889/TCP,9411/TCP 12h

  8.  service/otel-collector-monitoring ClusterIP 10.43.115.103 8888/TCP 12h

  Collector 部署的四种部署模型[10] Deployment、DaemonSet、StatefulSet、Sidecar,默认为 Deployment。

  配置 Instrumentation

  Instrumentation 是 Otel Operator 的另一个 CRD,用于自动安装 Otel 探针和配置:

  propagators 用于配置跟踪信息在上下文的传递方式。

  sampler 采样器

  env 和 [language].env 添加到容器的环境变量

  更多配置说明,请参考 Instrumentation API 文档[11]。

  复制

  1.  kubectl apply -f - <

  2.  apiVersion: opentelemetry.io/v1alpha1

  3.  kind: Instrumentation

  4.  metadata:

  5.  name: instrumentation-sample

  6.  spec:

  7.  propagators:

  8.  - tracecontext

  9.  - baggage

  10.  - b3

  11.  sampler:

  12.  type: parentbased_traceidratio

  13.  argument: "1"

  14.  env:

  15.  - name: OTEL_EXPORTER_OTLP_ENDPOINT

  16.  value: otel-collector.default:4318

  17.  java:

  18.  env:

  19.  - name: OTEL_EXPORTER_OTLP_ENDPOINT

  20.  value: http://otel-collector.default:4317

  21.  EOF

  Java 示例应用

  为 Pod 添加注解 instrumentation.opentelemetry.io/inject-java: "true" 通知 Otel Operator 该应用的类型以便注入正确的探针。

  复制

  1.  kubectl apply -f - <

  2.  apiVersion: apps/v1

  3.  kind: Deployment

  4.  metadata:

  5.  name: java-sample

  6.  spec:

  7.  replicas: 1

  8.  selector:

  9.  matchLabels:

  10.  app: java-sample

  11.  template:

  12.  metadata:

  13.  labels:

  14.  app: java-sample

  15.  annotations:

  16.  instrumentation.opentelemetry.io/inject-java: "true"

  17.  spec:

  18.  containers:

  19.  - name: java-sample

  20.  image: pinakispecial/spring-boot-rest

  21.  ports:

  22.  - containerPort: 8080

  23.  EOF

  可以看到 Otel Operator 向 Pod 中注入了一个 otel 的初始化容器。

  

图片

  以及在 java 容器中注入了一系列的环境变量进行配置。

  

图片

  Go 示例应用

  前面提到 Go 语言的自动注入演示使用半自动的方式,与本文的标题不符,属于嵌入式的。我写了一个 简单的 Go 应用[12],使用手动的方式来安装 Otel 探针,有兴趣的可以查看源码。

  复制

  1.  kubectl apply -f https://raw.githubusercontent.com/addozhang/http-sample/main/manifests/service-v1.yaml

  查看 Pod 同样可以看到通过环境变量的方式注入的 Otel 配置。

  测试

  复制

  1.  pod_name="$(kubectl get pod -n default -l app=service-a -o jsnotallow='{.items[0].metadata.name}')"

  2.  kubectl port-forward $pod_name 8080:8080 &

  3.

      4.  curl localhost:8080

  5.  service-a(version: v1, ip: 10.42.0.68, hostname: service-a-5bf98748f5-l9pjw) -> service-b(version: v1, ip: 10.42.0.70, hostname: service-b-676c56fb98-rjbwv) -> service-c(version: v1, ip: 10.42.0.69, hostname: service-c-79985dc75d-bh68k)

  打开 Jaeger UI。

  复制

  1.  jaeger_pod="$(kubectl get pod -l app=jaeger -o jsnotallow='{.items[0].metadata.name}')"

  2.  kubectl port-forward $jaeger_pod 16686:16686 &

  Bingo!

  访问 Jaeger UI 就可以看到这个访问的链路信息了。

  

图片

  参考资料

  [1] Java 通过 javaagent 实现探针的自动安装: https://opentelemetry.io/docs/instrumentation/java/automatic/

  [2] OpenTelemetry Operator: https://opentelemetry.io/docs/kubernetes/operator/

  [3] OpenTelemetryCollector: https://github.com/open-telemetry/opentelemetry-operator/blob/main/docs/api.md#opentelemetrycollector

  [4] Instrumentation: https://github.com/open-telemetry/opentelemetry-operator/blob/main/docs/api.md#instrumentation

  [5] OpAMPBridge: https://github.com/open-telemetry/opentelemetry-operator/blob/main/docs/api.md#opampbridge

  [6] 多种语言的 instrumentation SDK: https://opentelemetry.io/docs/instrumentation/

  [7] 手动引入 Go instrumentation SDK: https://github.com/addozhang/http-sample/blob/main/otel.go

  [8] 自动注入配置: https://github.com/open-telemetry/opentelemetry-operator/blob/main/README.md#opentelemetry-auto-instrumentation-injection

  [9] OTLP(OpenTelemetry Protocol): https://opentelemetry.io/docs/specs/otlp/

  [10] Collector 部署的四种部署模型: https://github.com/open-telemetry/opentelemetry-operator#deployment-modes

  [11] Instrumentation API 文档: https://github.com/open-telemetry/opentelemetry-operator/blob/main/docs/api.md#instrumentation

  [12] 简单的 Go 应用: https://github.com/addozhang/http-sample

  来源: 云原生指北

    >>>>>>点击进入计算专题

赞(12)
踩(0)
分享到:
华为认证网络工程师 HCIE直播课视频教程