# OpenTelemetry Setup (/sdks/nodejs/how-to/observability/opentelemetry-setup)



## Overview [#overview]

**OpenTelemetry integration** wires the SDK's messaging operations into your tracing and metrics pipeline without hand-instrumenting every call site. In a distributed system where a message might be published by one service, queued, and consumed by three others, per-call logging tells you almost nothing — you need spans that correlate across process boundaries and metrics broken out by channel and operation. Instrumenting that by hand around every `sendEvent` or `subscribeToEvents` call is tedious and easy to get inconsistent; letting the client do it guarantees uniform coverage.

Pass a `tracerProvider` in `ClientOptions` to activate instrumentation; once set, every SDK operation emits a span named `kubemq.<operation>` (e.g., `kubemq.sendEvent`) tagged with OpenTelemetry Semantic Conventions for messaging (`messaging.system`, `messaging.destination`, `messaging.operation`). The provider must come from a Node OTel SDK you configure in your own application before creating the client. &#x2A;*Gotchas:** the global `NodeSDK` setup must run and call `.start()` *before* `KubeMQClient.create()`, or the first several operations are created without a tracer and go unrecorded; a configured provider still exports nowhere until you attach a real exporter (OTLP, Jaeger); and without a `tracerProvider`, the SDK runs with zero OTel overhead — instrumentation is opt-in, so silence usually means the option was never passed, not that something broke.

## Prerequisites [#prerequisites]

* KubeMQ server running on `localhost:50000`
* Node.js SDK installed (`npm install kubemq-js`)

## Code [#code]

```typescript title="opentelemetry-setup.ts"
/**
 * Example: OpenTelemetry Tracing Setup
 *
 * Demonstrates integrating OpenTelemetry tracing with the KubeMQ SDK.
 * When a TracerProvider is configured, the SDK automatically creates
 * spans for all operations and propagates W3C Trace Context headers.
 *
 * Prerequisites:
 *   - KubeMQ server running on localhost:50000
 *   - OpenTelemetry dependencies installed:
 *     npm install @opentelemetry/api @opentelemetry/sdk-node @opentelemetry/exporter-trace-otlp-grpc
 *
 * Run: npx tsx examples/observability/opentelemetry-setup.ts
 */
import { KubeMQClient, createEventMessage } from 'kubemq-js';

// In a real application, set up the OTel SDK before creating the KubeMQ client:
//
//   import { NodeSDK } from '@opentelemetry/sdk-node';
//   import { OTLPTraceExporter } from '@opentelemetry/exporter-trace-otlp-grpc';
//
//   const sdk = new NodeSDK({
//     traceExporter: new OTLPTraceExporter({ url: 'http://localhost:4317' }),
//     serviceName: 'my-service',
//   });
//   sdk.start();

async function main(): Promise<void> {
  // Pass the tracerProvider to enable automatic span creation.
  // The SDK creates spans for: sendEvent, sendQueueMessage, sendCommand,
  // sendQuery, subscribeToEvents, and all other client operations.
  const client = await KubeMQClient.create({
    address: 'localhost:50000',
    clientId: 'js-observability-opentelemetry-setup-client',
    // tracerProvider: trace.getTracerProvider(),  // Uncomment with real OTel setup
  });

  try {
    // This operation will create a span named "kubemq.sendEvent"
    // with attributes: messaging.system, messaging.destination, etc.
    await client.sendEvent(
      createEventMessage({
        channel: 'js-observability.opentelemetry-setup',
        body: JSON.stringify({ orderId: 'ORD-001', total: 99.99 }),
        tags: { source: 'checkout-service' },
      }),
    );

    console.log('Event published with OTel tracing enabled');
    console.log('Check your OTel collector/backend for the trace');
  } finally {
    await client.close();
  }
}

main().catch(console.error);

```

## How It Works [#how-it-works]

* Pass `tracerProvider: trace.getTracerProvider()` in `ClientOptions` to activate OTel instrumentation; every SDK operation then emits a span named `kubemq.<operation>` (e.g. `kubemq.sendEvent`, `kubemq.sendQueueMessage`).
* The commented-out `NodeSDK` setup must run before `KubeMQClient.create()` so the global tracer provider is installed before the first gRPC call.
* Span attributes follow the OpenTelemetry Semantic Conventions for messaging: `messaging.system`, `messaging.destination`, `messaging.operation`, and KubeMQ-specific tags.
* Without a `tracerProvider`, the SDK operates normally with zero OTel overhead — the instrumentation is opt-in and tree-shakeable.

## Related [#related]

* [Node.js SDK Reference](/sdks/nodejs/reference)
