Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

chore(exporter-zipkin): remove usages of Span constructor #5030

1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ For semantic convention package changes, see the [semconv CHANGELOG](packages/se
[#4992](https://github.com/open-telemetry/opentelemetry-js/pull/4992)
* refactor(sdk-metrics): replace `MetricsAttributes` with `Attributes` [#5021](https://github.com/open-telemetry/opentelemetry-js/pull/5021) @david-luna
* refactor(instrumentation-http): replace `SpanAttributes` and `MetricsAttributes` with `Attributes` [#5023](https://github.com/open-telemetry/opentelemetry-js/pull/5023) @david-luna
* chore(exporter-zipkin): remove usages of Span constructor [#5030](https://github.com/open-telemetry/opentelemetry-js/pull/5030) @david-luna

## 1.26.0

Expand Down
229 changes: 108 additions & 121 deletions packages/opentelemetry-exporter-zipkin/test/common/transform.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -16,17 +16,16 @@

import * as api from '@opentelemetry/api';
import {
hrTime,
hrTimeDuration,
hrTimeToMicroseconds,
millisToHrTime,
VERSION,
} from '@opentelemetry/core';
import { Resource } from '@opentelemetry/resources';
import { BasicTracerProvider, Span } from '@opentelemetry/sdk-trace-base';
import { IResource } from '@opentelemetry/resources';
import { ReadableSpan } from '@opentelemetry/sdk-trace-base';
import * as assert from 'assert';
import {
SEMRESATTRS_SERVICE_NAME,
SEMRESATTRS_TELEMETRY_SDK_LANGUAGE,
} from '@opentelemetry/semantic-conventions';
import { SEMRESATTRS_SERVICE_NAME } from '@opentelemetry/semantic-conventions';
import {
defaultStatusCodeTagName,
defaultStatusErrorTagName,
Expand All @@ -35,43 +34,69 @@ import {
_toZipkinTags,
} from '../../src/transform';
import * as zipkinTypes from '../../src/types';
const tracer = new BasicTracerProvider({
resource: Resource.default().merge(
new Resource({
[SEMRESATTRS_SERVICE_NAME]: 'zipkin-test',
cost: '112.12',
service: 'ui',
version: '1',
})
),
}).getTracer('default');

const language = tracer.resource.attributes[SEMRESATTRS_TELEMETRY_SDK_LANGUAGE];

const resource = {
attributes: {
[SEMRESATTRS_SERVICE_NAME]: 'zipkin-test',
cost: '112.12',
service: 'ui',
version: '1',
'telemetry.sdk.language': 'nodejs',
'telemetry.sdk.name': 'opentelemetry',
'telemetry.sdk.version': VERSION,
},
} as unknown as IResource;
const parentId = '5c1c63257de34c67';
const spanContext: api.SpanContext = {
traceId: 'd4cda95b652f4a1592b449d5929fda1b',
spanId: '6e0c63257de34c92',
traceFlags: api.TraceFlags.SAMPLED,
};
const currentTime = Date.now();
const durationMs = 10;
const startTime = hrTime(currentTime - durationMs);
const endTime = hrTime(currentTime);
const duration = millisToHrTime(durationMs);

function getSpan(options: Partial<ReadableSpan>): ReadableSpan {
const span = {
name: options.name || 'my-span',
kind: typeof options.kind === 'number' ? options.kind : api.SpanKind.SERVER,
startTime: options.startTime || startTime,
endTime: options.endTime || endTime,
duration: options.duration || duration,
spanContext: () => spanContext,
parentSpanId: options.parentSpanId || parentId,
attributes: options.attributes || {},
events: options.events || [],
status: options.status || { code: api.SpanStatusCode.UNSET },
resource,
} as ReadableSpan;

// Expicit `undefined` properties in options will be removed from the
// result span.
Object.keys(options).forEach(k => {
if (options[k as keyof ReadableSpan] === undefined) {
delete span[k as keyof ReadableSpan];
}
});

return span;
}

describe('transform', () => {
describe('toZipkinSpan', () => {
it('should convert an OpenTelemetry span to a Zipkin span', () => {
const span = new Span(
tracer,
api.ROOT_CONTEXT,
'my-span',
spanContext,
api.SpanKind.SERVER,
parentId
);
span.setAttributes({
key1: 'value1',
key2: 'value2',
const span = getSpan({
attributes: { key1: 'value1', key2: 'value2' },
events: [
{
name: 'my-event',
time: hrTime(Date.now() + 5),
attributes: { key3: 'value 3' },
},
],
});
span.addEvent('my-event', { key3: 'value3' });
span.end();

const zipkinSpan = toZipkinSpan(
span,
Expand Down Expand Up @@ -103,7 +128,7 @@ describe('transform', () => {
cost: '112.12',
service: 'ui',
version: '1',
'telemetry.sdk.language': language,
'telemetry.sdk.language': 'nodejs',
'telemetry.sdk.name': 'opentelemetry',
'telemetry.sdk.version': VERSION,
},
Expand All @@ -112,14 +137,9 @@ describe('transform', () => {
});
});
it("should skip parentSpanId if doesn't exist", () => {
const span = new Span(
tracer,
api.ROOT_CONTEXT,
'my-span',
spanContext,
api.SpanKind.SERVER
);
span.end();
const span = getSpan({
parentSpanId: undefined,
});

const zipkinSpan = toZipkinSpan(
span,
Expand All @@ -144,7 +164,7 @@ describe('transform', () => {
cost: '112.12',
service: 'ui',
version: '1',
'telemetry.sdk.language': language,
'telemetry.sdk.language': 'nodejs',
'telemetry.sdk.name': 'opentelemetry',
'telemetry.sdk.version': VERSION,
},
Expand All @@ -163,15 +183,10 @@ describe('transform', () => {
it(`should map OpenTelemetry SpanKind ${
api.SpanKind[item.ot]
} to Zipkin ${item.zipkin}`, () => {
const span = new Span(
tracer,
api.ROOT_CONTEXT,
'my-span',
spanContext,
item.ot
);
span.end();

const span = getSpan({
kind: item.ot,
parentSpanId: undefined,
});
const zipkinSpan = toZipkinSpan(
span,
'my-service',
Expand All @@ -195,7 +210,7 @@ describe('transform', () => {
cost: '112.12',
service: 'ui',
version: '1',
'telemetry.sdk.language': language,
'telemetry.sdk.language': 'nodejs',
'telemetry.sdk.name': 'opentelemetry',
'telemetry.sdk.version': VERSION,
},
Expand All @@ -208,17 +223,12 @@ describe('transform', () => {

describe('_toZipkinTags', () => {
it('should convert OpenTelemetry attributes to Zipkin tags', () => {
const span = new Span(
tracer,
api.ROOT_CONTEXT,
'my-span',
spanContext,
api.SpanKind.SERVER,
parentId
);
span.setAttributes({
key1: 'value1',
key2: 'value2',
const span = getSpan({
parentSpanId: undefined,
attributes: {
key1: 'value1',
key2: 'value2',
},
});
const tags: zipkinTypes.Tags = _toZipkinTags(
span,
Expand All @@ -230,7 +240,7 @@ describe('transform', () => {
key1: 'value1',
key2: 'value2',
[SEMRESATTRS_SERVICE_NAME]: 'zipkin-test',
'telemetry.sdk.language': language,
'telemetry.sdk.language': 'nodejs',
'telemetry.sdk.name': 'opentelemetry',
'telemetry.sdk.version': VERSION,
cost: '112.12',
Expand All @@ -239,21 +249,14 @@ describe('transform', () => {
});
});
it('should map OpenTelemetry constructor attributes to a Zipkin tag', () => {
const span = new Span(
tracer,
api.ROOT_CONTEXT,
'my-span',
spanContext,
api.SpanKind.SERVER,
parentId,
[],
undefined,
undefined,
{
const span = getSpan({
parentSpanId: undefined,
attributes: {
key1: 'value1',
key2: 'value2',
}
);
},
});

const tags: zipkinTypes.Tags = _toZipkinTags(
span,
defaultStatusCodeTagName,
Expand All @@ -264,7 +267,7 @@ describe('transform', () => {
key1: 'value1',
key2: 'value2',
[SEMRESATTRS_SERVICE_NAME]: 'zipkin-test',
'telemetry.sdk.language': language,
'telemetry.sdk.language': 'nodejs',
'telemetry.sdk.name': 'opentelemetry',
'telemetry.sdk.version': VERSION,
cost: '112.12',
Expand All @@ -273,21 +276,13 @@ describe('transform', () => {
});
});
it('should map OpenTelemetry SpanStatus.code to a Zipkin tag', () => {
const span = new Span(
tracer,
api.ROOT_CONTEXT,
'my-span',
spanContext,
api.SpanKind.SERVER,
parentId
);
const status: api.SpanStatus = {
code: api.SpanStatusCode.ERROR,
};
span.setStatus(status);
span.setAttributes({
key1: 'value1',
key2: 'value2',
const span = getSpan({
parentSpanId: undefined,
attributes: {
key1: 'value1',
key2: 'value2',
},
status: { code: api.SpanStatusCode.ERROR },
});
const tags: zipkinTypes.Tags = _toZipkinTags(
span,
Expand All @@ -300,7 +295,7 @@ describe('transform', () => {
key2: 'value2',
[defaultStatusCodeTagName]: 'ERROR',
[SEMRESATTRS_SERVICE_NAME]: 'zipkin-test',
'telemetry.sdk.language': language,
'telemetry.sdk.language': 'nodejs',
'telemetry.sdk.name': 'opentelemetry',
'telemetry.sdk.version': VERSION,
cost: '112.12',
Expand All @@ -309,22 +304,13 @@ describe('transform', () => {
});
});
it('should map OpenTelemetry SpanStatus.message to a Zipkin tag', () => {
const span = new Span(
tracer,
api.ROOT_CONTEXT,
'my-span',
spanContext,
api.SpanKind.SERVER,
parentId
);
const status: api.SpanStatus = {
code: api.SpanStatusCode.ERROR,
message: 'my-message',
};
span.setStatus(status);
span.setAttributes({
key1: 'value1',
key2: 'value2',
const span = getSpan({
parentSpanId: undefined,
attributes: {
key1: 'value1',
key2: 'value2',
},
status: { code: api.SpanStatusCode.ERROR, message: 'my-message' },
});
const tags: zipkinTypes.Tags = _toZipkinTags(
span,
Expand All @@ -336,9 +322,9 @@ describe('transform', () => {
key1: 'value1',
key2: 'value2',
[defaultStatusCodeTagName]: 'ERROR',
[defaultStatusErrorTagName]: status.message,
[defaultStatusErrorTagName]: 'my-message',
[SEMRESATTRS_SERVICE_NAME]: 'zipkin-test',
'telemetry.sdk.language': language,
'telemetry.sdk.language': 'nodejs',
'telemetry.sdk.name': 'opentelemetry',
'telemetry.sdk.version': VERSION,
cost: '112.12',
Expand All @@ -350,16 +336,17 @@ describe('transform', () => {

describe('_toZipkinAnnotations', () => {
it('should convert OpenTelemetry events to Zipkin annotations', () => {
const span = new Span(
tracer,
api.ROOT_CONTEXT,
'my-span',
spanContext,
api.SpanKind.SERVER,
parentId
);
span.addEvent('my-event1');
span.addEvent('my-event2', { key1: 'value1' });
const span = getSpan({
parentSpanId: undefined,
events: [
{ name: 'my-event1', time: hrTime(Date.now()) },
{
name: 'my-event2',
time: hrTime(Date.now()),
attributes: { key1: 'value1' },
},
],
});

const annotations = _toZipkinAnnotations(span.events);
assert.deepStrictEqual(annotations, [
Expand Down
Loading