opentelemetry-js: Using OTLPTraceExporter and OTLPMetricExporter together causes empty data

What version of OpenTelemetry are you using?

   "@opentelemetry/api": "^1.0.4",
    "@opentelemetry/api-metrics": "^0.27.0",
    "@opentelemetry/auto-instrumentations-node": "^0.27.3",
    "@opentelemetry/exporter-metrics-otlp-proto": "^0.27.0",
    "@opentelemetry/exporter-trace-otlp-proto": "^0.27.0",
    "@opentelemetry/instrumentation-express": "^0.27.1",
    "@opentelemetry/instrumentation-http": "^0.27.0",
    "@opentelemetry/sdk-node": "^0.27.0",
    "@opentelemetry/sdk-trace-base": "^1.0.1",
    "@opentelemetry/sdk-trace-node": "^1.0.1",
    "@opentelemetry/semantic-conventions": "^1.0.1"

What version of Node are you using?

v12.22.1

Please provide the code you used to setup the OpenTelemetry SDK

// Config
import { SemanticResourceAttributes } from "@opentelemetry/semantic-conventions";
import { Resource } from '@opentelemetry/resources'
import { v4 as uuidv4 } from 'uuid';

// Metrics
import { ConsoleMetricExporter, MeterProvider } from '@opentelemetry/sdk-metrics-base';
import { OTLPMetricExporter } from "@opentelemetry/exporter-metrics-otlp-proto";

// Traces
import { BasicTracerProvider, BatchSpanProcessor, SimpleSpanProcessor } from "@opentelemetry/sdk-trace-base";
import { OTLPTraceExporter } from '@opentelemetry/exporter-trace-otlp-proto';
import { getNodeAutoInstrumentations } from '@opentelemetry/auto-instrumentations-node'

const OpenTelemetry = require("@opentelemetry/sdk-node");

// OpenTelemetry Exporter Config
export const exporterConfig = {
  headers: {
    'api-key': process.env.NR_TOKEN,
    'Content-Type': 'application/x-protobuf'
  }
};

export const OTEL_SERVICE_RESOURCE = new Resource({
  [SemanticResourceAttributes.SERVICE_NAME]: 'otel-express-node',
  [SemanticResourceAttributes.SERVICE_VERSION]: '1.0.0',
  [SemanticResourceAttributes.SERVICE_INSTANCE_ID]: uuidv4()
});

// Create our OTLP exporters
const traceExporter = new OTLPTraceExporter(exporterConfig);
const metricExporter = new OTLPMetricExporter(exporterConfig); // <- Adding this line causes Traces to not be ingested correctly

export function registerTraceProvider() {
    const traceProvider = new BasicTracerProvider({
        resource: OTEL_SERVICE_RESOURCE
    })

    traceProvider.addSpanProcessor(new SimpleSpanProcessor(traceExporter));
    traceProvider.register();
    return traceProvider;
}

export async function otelSetupInstrumentation() {

    // 1. Create and register a Trace Provider
    registerTraceProvider();

    // 2. Create an instance of the OpenTelemetry SDK, passing in our exporter and Resource config
    const sdk = new OpenTelemetry.NodeSDK({
        resource: OTEL_SERVICE_RESOURCE,
        traceExporter: traceExporter,
        // metricExporter: metricExporter,
        instrumentations: [getNodeAutoInstrumentations()]
    });

    sdk.start()
}

What did you do?

Tried to send OTLP trace data to NewRelic.

What did you expect to see?

My trace data to be created and ingested correctly.

What did you see instead?

The following error: One or more OTLP payload(s) was dropped because it was empty.

Additional context

If I remove the line const metricExporter = new OTLPMetricExporter(exporterConfig); everything works fine. My traces are ingested correctly and displayed in the UI.

I am also able to send metric data fine, just not when I try and do both at the same time.

I am confused why simply instantiating an instance of the OTLPMetricExporter would cause my traces to not be sent/formatted properly even though I don’t even pass it into the SDK.

About this issue

  • Original URL
  • State: closed
  • Created 2 years ago
  • Comments: 16 (5 by maintainers)

Commits related to this issue

Most upvoted comments

I’ve also been pulling my hair out on this one including going on a wild goose chase with the gRPC exporters for a couple weeks (my brain skipped right over the fact this is the proto exporters😩). Imagine my surprise when I tracked the issue down finally in my outdated local copy, then a git pull fixed it in front of my eyes 😂)

Marking p2 since this is not crashing the app but is causing telemetry not to be emitted. I’m looking into this.

did you find any solution? I have the same problem

No, sorry.

I found a solution, Adding OTPL urls for both tracing and metrics fixed the issue. I had to create separate exporterConfig for both tracing and metrics:

const headers = {
    'api-key': process.env.NR_TOKEN,
    'Content-Type': 'application/x-protobuf'
  }

export const exporterConfigForTracing = {
  url:   process.env.OTPL_TRACE_URL
  headers, 
};


export const exporterConfigForMetrics = {
  url:   process.env.OTPL_METRICS_URL
  headers,
};

then use it like:

const traceExporter = new OTLPTraceExporter(exporterConfigForTracing);

const metricExporter = new OTLPMetricExporter(exporterConfigForMetrics);

Note* make sure the OTPL urls are in the same region as to where you store your new relic data.