OpenTelemetry入門:Node.jsのHTTPトレースをCollectorで確認する

中級 | 12分 で読める | 2026.04.24

公式ドキュメント

OpenTelemetryは、アプリからトレースなどの観測データを作り、共通形式で送る仕組みです。今回はNode.jsのHTTPリクエストを自動計装し、OpenTelemetry Collectorが受け取った1件を確認します。

初出日: 2026-04-24 / 最終確認日: 2026-07-25

今回やること

curl → Node.jsアプリ → OTLP/HTTP → Collector → ターミナル出力
  • Node.jsアプリへ自動計装を読み込む
  • OTLP/HTTPでトレースをCollectorへ送る
  • Collectorのdebug exporterでspanを確認する

メトリクス、ログ、sampling、可視化バックエンドは扱いません。まず一つのリクエストが届く経路を理解します。

最初に知る3つの言葉

言葉この実習での意味
spanHTTPリクエストなど、一つの処理区間の記録
trace同じtrace IDで結ばれたspanのまとまり
Collectorアプリから受け取り、確認先や保存先へ中継するプロセス

OpenTelemetry自体はトレースを長期保存する画面ではありません。アプリはCollectorへ送り、CollectorがJaegerやTempoなどのバックエンドへ渡します。この実習では保存先の代わりにdebug exporterを使います。

自動計装は、対応ライブラリのHTTP処理などをコード変更なしで記録します。業務上重要な「課題を提出した」のような区間は、後から手動spanで補います。最初から両方を混ぜず、今回は自動計装で通信経路が成立することだけを確かめます。

アプリを準備する

空のディレクトリで依存関係を入れます。

npm init -y
npm install express @opentelemetry/sdk-node \
  @opentelemetry/auto-instrumentations-node \
  @opentelemetry/exporter-trace-otlp-proto

app.jsを作ります。

const express = require("express");

const app = express();

app.get("/hello", (_req, res) => {
  res.json({ message: "hello" });
});

app.listen(8080, () => {
  console.log("http://localhost:8080/hello");
});

このアプリだけを普通に起動しても、まだspanは作られません。次の計装ファイルをアプリより先に読み込ませることで、ExpressとNode.jsのHTTP処理を自動計装します。

次にinstrumentation.jsを作ります。計装はアプリより先に読み込む必要があります。

const { NodeSDK } = require("@opentelemetry/sdk-node");
const {
  getNodeAutoInstrumentations,
} = require("@opentelemetry/auto-instrumentations-node");
const {
  OTLPTraceExporter,
} = require("@opentelemetry/exporter-trace-otlp-proto");

const sdk = new NodeSDK({
  traceExporter: new OTLPTraceExporter({
    url: "http://localhost:4318/v1/traces",
  }),
  instrumentations: [getNodeAutoInstrumentations()],
});

sdk.start();

Collectorを起動する

collector-config.yamlを作ります。

receivers:
  otlp:
    protocols:
      http:
        endpoint: 0.0.0.0:4318

exporters:
  debug:
    verbosity: detailed

service:
  pipelines:
    traces:
      receivers: [otlp]
      exporters: [debug]

1つ目のターミナルでCollectorを起動します。

docker run --rm -p 4318:4318 \
  -v "$PWD/collector-config.yaml:/etc/otelcol/config.yaml" \
  otel/opentelemetry-collector:0.153.0

この固定タグは、初出日2026-04-24の記事を最終確認日2026-07-25に検証した版です。後日試す場合は、Collectorのリリースで利用可能な版を確認してください。

トレースを送る

2つ目のターミナルでアプリを起動します。

OTEL_SERVICE_NAME=demo-api \
  node --require ./instrumentation.js app.js

3つ目のターミナルからリクエストします。

curl http://localhost:8080/hello

成功確認

Collector側の出力に、次の内容が含まれれば成功です。

  • service名がdemo-api
  • HTTPリクエストに対応するspan
  • trace_idspan_id
  • HTTP statusが成功を示す値

トレースは「ログを置き換えるもの」ではありません。一つの処理が複数サービスを通る時に、共通のtrace IDで経路を追うための材料です。

もう一度curlを実行すると別のtrace IDが作られます。同じリクエスト内のspanは同じtrace IDを共有し、個々の処理区間は異なるspan IDを持つことも確認してください。

よくあるつまずき

Collectorに何も出ない

アプリをnode app.jsだけで起動すると、計装が先に読み込まれません。--require ./instrumentation.jsを確認します。また、Collectorが4318を公開しているか確認してください。

ESMのプロジェクトで同じコマンドを使う

この例はCommonJSです。ES Modulesでは読み込み方法が異なるため、OpenTelemetry公式のESM手順に従います。

Collectorを本番へそのまま公開する

この設定は認証も保存先もないローカル確認用です。4318をインターネットへ公開せず、本番では通信経路、認証、送信量、保持先を運用設計に合わせて設定します。

URL、header、属性へ認証token、パスワード、個人情報を入れると、トレースの保存先にも複製されます。便利そうな値をすべて記録せず、調査に必要で保存してよい属性だけを選びます。

練習

/users/:idというGETルートを一つ追加し、curl http://localhost:8080/users/42を実行してください。Collectorのspan名やHTTP routeが/helloとどう違うか比べます。

後片付け

アプリとCollectorを起動した各ターミナルでCtrl + Cを押します。Collectorは--rm付きなので、停止後にコンテナが削除されます。

次のステップ

参考リソース

← 一覧に戻る
PR
PR
PR
PR