telemetrygenでTail Sampling Processorの挙動をサクッと確認する
テレメトリーデータを効率的に管理するために、Sampling は重要な役割を果たします。Tail Sampling は Sampling の形式の一種で、ユーザーが指定した条件に合致する特別な Trace のみを Observability Backend に送信するという特徴があります。
Tail Sampling の実装は複数存在しますが、その内の 1 つとして、OpenTelemetry Collector (Tail Sampling Processor) が存在します。
今回は、telemetrygen というツールを使用して、Tail Sampling Processor の挙動を簡単に確認する方法をご紹介します。
telemetrygenとは?
telemetrygen は、デモ・検証用に各種テレメトリーデータを生成するためのツールです。
This utility simulates a client generating traces, metrics, and logs. It is useful for testing and demonstration purposes.
https://opentelemetry.io/docs/collector/quick-start/ で紹介されているので、ご存じの方もいらっしゃるかもしれません。
今回は、Tail Sampling Processor の挙動の簡単な確認なので、telemetrygen でサクッと確認してみましょう。
※ アプリケーションの計装を踏まえた Tail Sampling の挙動をローカルで確認する場合は、計装済みのアプリケーションコンテナも起動して確認する方が確実かと思います。
telemetrygenを利用した動作確認
ここからは実際の動作確認の手順になります。
下記のような OpenTelemetry Collector の設定ファイルを用意します。tail_sampling
の箇所には特定の Attribute を確認するポリシーとSpan Status (status code) を確認するポリシー、2 つのポリシーが定義されています。
今回は、ポリシーの評価結果を確認するために、debug exporter を利用しています。
receivers:
otlp:
protocols:
grpc:
endpoint: 0.0.0.0:4317
processors:
tail_sampling:
decision_wait: 10s
num_traces: 10
expected_new_traces_per_sec: 10
policies:
[
{
name: test-policy,
type: string_attribute,
string_attribute: {key: foo, values: [bar, baz]}
},
{
name: test-policy-2,
type: status_code,
status_code: {status_codes: [ERROR, UNSET]}
}
]
exporters:
debug:
verbosity: detailed
extensions:
zpages: {}
service:
telemetry:
logs:
level: "debug"
extensions: [zpages]
pipelines:
traces:
receivers: [otlp]
processors: [tail_sampling]
exporters: [debug]
この設定ファイルを読み込んだ上で、OpenTelemetry Collector を起動します。
$ docker run \
-p 127.0.0.1:4317:4317 \
--rm \
-v ./otel-config.yaml:/etc/otelcol/config.yaml \
otel/opentelemetry-collector-contrib:0.95.0 \
--config=/etc/otelcol/config.yaml
続けて、別のターミナルを開いて、foo=bar
という Attribute を付与した trace を telemetrygen を用いて生成します。
この場合、生成された trace は policies で設定された 1 つ目の条件に合致するはずなので、正常に Sampling されるはずです。また、Span Status (status code) は未設定の時はデフォルトで UNSET
になるので、2 つ目の条件にも合致します。
$ telemetrygen traces --otlp-insecure --traces 3 --telemetry-attributes foo=\"bar\"
OpenTelemetry Collector 側のログを確認すると "sampled": 6
となっており、Sampling されていることがわかります。
生成した trace の数より多い数字がログに出ていますが、これは trace が各ポリシーごとに評価された上で sampled
/ notSampled
がカウントされているためです。
2024-03-03T05:14:36.165Z debug tailsamplingprocessor@v0.95.0/processor.go:202 Sampling Policy Evaluation ticked {"kind": "processor", "name": "tail_sampling", "pipeline": "traces"}
2024-03-03T05:14:36.165Z debug sampling/string_tag_filter.go:95 Evaluting spans in string-tag filter {"kind": "processor", "name": "tail_sampling", "pipeline": "traces", "policy": "string_attribute"}
2024-03-03T05:14:36.165Z debug sampling/status_code.go:54 Evaluating spans in status code filter {"kind": "processor", "name": "tail_sampling", "pipeline": "traces", "policy": "status_code"}
2024-03-03T05:14:36.166Z info TracesExporter {"kind": "exporter", "data_type": "traces", "name": "debug", "resource spans": 1, "spans": 2}
2024-03-03T05:14:36.166Z info ResourceSpans #0
Resource SchemaURL:
Resource attributes:
-> service.name: Str(telemetrygen)
ScopeSpans #0
ScopeSpans SchemaURL:
InstrumentationScope telemetrygen
Span #0
Trace ID : a987128b2b4126afb053543628c7c042
Parent ID : 659af8c8738b4adf
ID : c284897f1e183fb0
Name : okey-dokey-0
Kind : Server
Start time : 2024-03-03 05:14:26.047258 +0000 UTC
End time : 2024-03-03 05:14:26.047381 +0000 UTC
Status code : Unset
Status message :
Attributes:
-> net.peer.ip: Str(1.2.3.4)
-> peer.service: Str(telemetrygen-client)
-> foo: Str(bar)
Span #1
Trace ID : a987128b2b4126afb053543628c7c042
Parent ID :
ID : 659af8c8738b4adf
Name : lets-go
Kind : Client
Start time : 2024-03-03 05:14:26.047258 +0000 UTC
End time : 2024-03-03 05:14:26.047381 +0000 UTC
Status code : Unset
Status message :
Attributes:
-> net.peer.ip: Str(1.2.3.4)
-> peer.service: Str(telemetrygen-server)
-> foo: Str(bar)
{"kind": "exporter", "data_type": "traces", "name": "debug"}
...
2024-03-03T05:14:36.166Z debug tailsamplingprocessor@v0.95.0/processor.go:232 Sampling policy evaluation completed {"kind": "processor", "name": "tail_sampling", "pipeline": "traces", "batch.len": 3, "sampled": 6, "notSampled": 0, "droppedPriorToEvaluation": 0, "policyEvaluationErrors": 0}
1 つ目のポリシー (test-policy
) に合致しない Attribute を定義して trace を生成すると、"sampled": 3, "notSampled": 3
という風にログに出力されます。
$ telemetrygen traces --otlp-insecure --traces 3 --telemetry-attributes foo=\"notSampled\"
2024-03-03T06:12:37.720Z debug sampling/status_code.go:54 Evaluating spans in status code filter {"kind": "processor", "name": "tail_sampling", "pipeline": "traces", "policy": "status_code"}
2024-03-03T06:12:37.721Z info TracesExporter {"kind": "exporter", "data_type": "traces", "name": "debug", "resource spans": 1, "spans": 2}
2024-03-03T06:12:37.721Z info ResourceSpans #0
Resource SchemaURL:
Resource attributes:
-> service.name: Str(telemetrygen)
ScopeSpans #0
ScopeSpans SchemaURL:
InstrumentationScope telemetrygen
Span #0
Trace ID : 4335c416994d3d99e249c9724b9d8e9b
Parent ID : 9c267ca5f50814d4
ID : 670873572e816a65
Name : okey-dokey-0
Kind : Server
Start time : 2024-03-03 06:12:27.354395 +0000 UTC
End time : 2024-03-03 06:12:27.354518 +0000 UTC
Status code : Unset
Status message :
Attributes:
-> net.peer.ip: Str(1.2.3.4)
-> peer.service: Str(telemetrygen-client)
-> foo: Str(notSampled)
Span #1
Trace ID : 4335c416994d3d99e249c9724b9d8e9b
Parent ID :
ID : 9c267ca5f50814d4
Name : lets-go
Kind : Client
Start time : 2024-03-03 06:12:27.354395 +0000 UTC
End time : 2024-03-03 06:12:27.354518 +0000 UTC
Status code : Unset
Status message :
Attributes:
-> net.peer.ip: Str(1.2.3.4)
-> peer.service: Str(telemetrygen-server)
-> foo: Str(notSampled)
{"kind": "exporter", "data_type": "traces", "name": "debug"}
...
2024-03-03T06:12:37.722Z debug tailsamplingprocessor@v0.95.0/processor.go:232 Sampling policy evaluation completed {"kind": "processor", "name": "tail_sampling", "pipeline": "traces", "batch.len": 3, "sampled": 3, "notSampled": 3, "droppedPriorToEvaluation": 0, "policyEvaluationErrors": 0}
いかがだったでしょうか?
今回の検証では簡単なポリシーを定義した上で動作確認を行いましたが、Tail Sampling Processor では正規表現を利用した Attribute のチェックや policy の AND 条件など他にも様々な条件を設定することができます。
複雑なポリシーを定義するとポリシーが意図通りに評価されているか確認したくなると思いますが、そんな時の検証手段として telemetrygen を一考いただけるといいかと思います。
Discussion