Skip to content

Commit

Permalink
feat(tracing): auto flush BatchSpanProcessor on browser (open-telemet…
Browse files Browse the repository at this point in the history
  • Loading branch information
kkruk-sumo committed Sep 16, 2021
1 parent 3b1aa53 commit b25e1bd
Showing 1 changed file with 70 additions and 174 deletions.
244 changes: 70 additions & 174 deletions packages/opentelemetry-tracing/test/common/Tracer.test.ts
Expand Up @@ -13,34 +13,25 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/

import * as assert from 'assert';
import {
context,
createContextKey,
INVALID_TRACEID,
ROOT_CONTEXT,
Sampler,
SamplingDecision,
SpanContext,
trace,
TraceFlags
TraceFlags,
ROOT_CONTEXT,
suppressInstrumentation,
} from '@opentelemetry/api';
import { getSpan } from '@opentelemetry/api/build/src/trace/context-utils';
import {
AlwaysOffSampler,
AlwaysOnSampler,
InstrumentationLibrary,
suppressTracing
AlwaysOnSampler,
AlwaysOffSampler,
} from '@opentelemetry/core';
import * as assert from 'assert';
import { BasicTracerProvider, Span, Tracer } from '../../src';
import { TestStackContextManager } from './export/TestStackContextManager';
import * as sinon from 'sinon';

describe('Tracer', () => {
const tracerProvider = new BasicTracerProvider();
const envSource = (typeof window !== 'undefined'
? window
: process.env) as any;

class TestSampler implements Sampler {
shouldSample() {
Expand All @@ -53,15 +44,10 @@ describe('Tracer', () => {
}
}

beforeEach(() => {
const contextManager = new TestStackContextManager().enable();
context.setGlobalContextManager(contextManager);
});

afterEach(() => {
context.disable();
delete envSource.OTEL_TRACES_SAMPLER;
delete envSource.OTEL_TRACES_SAMPLER_ARG;
if (typeof process !== 'undefined' && process.release.name === 'node') {
delete process.env.OTEL_SAMPLING_PROBABILITY;
}
});

it('should create a Tracer instance', () => {
Expand All @@ -73,16 +59,13 @@ describe('Tracer', () => {
assert.ok(tracer instanceof Tracer);
});

it('should use an ParentBasedSampler by default', () => {
it('should use an AlwaysOnSampler by default', () => {
const tracer = new Tracer(
{ name: 'default', version: '0.0.1' },
{},
tracerProvider
);
assert.strictEqual(
tracer['_sampler'].toString(),
'ParentBased{root=AlwaysOnSampler, remoteParentSampled=AlwaysOnSampler, remoteParentNotSampled=AlwaysOffSampler, localParentSampled=AlwaysOnSampler, localParentNotSampled=AlwaysOffSampler}'
);
assert.strictEqual(tracer['_sampler'].toString(), 'AlwaysOnSampler');
});

it('should respect NO_RECORD sampling result', () => {
Expand Down Expand Up @@ -131,8 +114,8 @@ describe('Tracer', () => {
assert.strictEqual(lib.version, '0.0.1');
});

describe('when suppressTracing true', () => {
const context = suppressTracing(ROOT_CONTEXT);
describe('when suppressInstrumentation true', () => {
const context = suppressInstrumentation(ROOT_CONTEXT);

it('should return cached no-op span ', done => {
const tracer = new Tracer(
Expand All @@ -150,150 +133,63 @@ describe('Tracer', () => {
});
});

it('should use traceId and spanId from parent', () => {
const parent: SpanContext = {
traceId: '00112233445566778899001122334455',
spanId: '0011223344556677',
traceFlags: TraceFlags.SAMPLED,
};
const tracer = new Tracer(
{ name: 'default', version: '0.0.1' },
{},
tracerProvider
);
const span = tracer.startSpan(
'aSpan',
undefined,
trace.setSpanContext(ROOT_CONTEXT, parent)
);
assert.strictEqual((span as Span).parentSpanId, parent.spanId);
assert.strictEqual(span.spanContext().traceId, parent.traceId);
});

it('should not use spanId from invalid parent', () => {
const parent: SpanContext = {
traceId: INVALID_TRACEID,
spanId: '0011223344556677',
traceFlags: TraceFlags.SAMPLED,
};
const tracer = new Tracer(
{ name: 'default', version: '0.0.1' },
{},
tracerProvider
);
const span = tracer.startSpan(
'aSpan',
undefined,
trace.setSpanContext(ROOT_CONTEXT, parent)
);
assert.strictEqual((span as Span).parentSpanId, undefined);
});

it('should sample a trace when OTEL_TRACES_SAMPLER_ARG is unset', () => {
envSource.OTEL_TRACES_SAMPLER = 'traceidratio';
envSource.OTEL_TRACES_SAMPLER_ARG = '';
const tracer = new Tracer(
{ name: 'default', version: '0.0.1' },
{},
tracerProvider
);
const span = tracer.startSpan('my-span');
const context = span.spanContext();
assert.strictEqual(context.traceFlags, TraceFlags.SAMPLED);
span.end();
});

it('should not sample a trace when OTEL_TRACES_SAMPLER_ARG is out of range', () => {
envSource.OTEL_TRACES_SAMPLER = 'traceidratio';
envSource.OTEL_TRACES_SAMPLER_ARG = '2';
const tracer = new Tracer(
{ name: 'default', version: '0.0.1' },
{},
tracerProvider
);
const span = tracer.startSpan('my-span');
const context = span.spanContext();
assert.strictEqual(context.traceFlags, TraceFlags.SAMPLED);
span.end();
});

it('should not sample a trace when OTEL_TRACES_SAMPLER_ARG is 0', () => {
envSource.OTEL_TRACES_SAMPLER = 'traceidratio';
envSource.OTEL_TRACES_SAMPLER_ARG = '0';
const tracer = new Tracer(
{ name: 'default', version: '0.0.1' },
{},
tracerProvider
);
const span = tracer.startSpan('my-span');
const context = span.spanContext();
assert.strictEqual(context.traceFlags, TraceFlags.NONE);
span.end();
});

it('should start an active span with name and function args', () => {
const tracer = new Tracer(
{ name: 'default', version: '0.0.1' },
{ sampler: new TestSampler() },
tracerProvider
);

const spy = sinon.spy(tracer, 'startSpan');

assert.strictEqual(tracer.startActiveSpan('my-span', span => {
try {
assert(spy.calledWith('my-span'))
assert.strictEqual(getSpan(context.active()), span)
return 1
} finally {
span.end();
}
}), 1);
});

it('should start an active span with name, options and function args', () => {

const tracer = new Tracer(
{ name: 'default', version: '0.0.1' },
{ sampler: new TestSampler() },
tracerProvider
);

const spy = sinon.spy(tracer, 'startSpan');

assert.strictEqual(tracer.startActiveSpan('my-span', {attributes: {foo: 'bar'}}, span => {
try {
assert(spy.calledWith('my-span', {attributes: {foo: 'bar'}}))
assert.strictEqual(getSpan(context.active()), span)
return 1
} finally {
span.end();
}
}), 1);
});

it('should start an active span with name, options, context and function args', () => {
const tracer = new Tracer(
{ name: 'default', version: '0.0.1' },
{ sampler: new TestSampler() },
tracerProvider
);

const ctxKey = createContextKey('foo');
if (typeof process !== 'undefined' && process.release.name === 'node') {
it('should sample a trace when OTEL_SAMPLING_PROBABILITY is invalid', () => {
process.env.OTEL_SAMPLING_PROBABILITY = 'invalid value';
const tracer = new Tracer(
{ name: 'default', version: '0.0.1' },
{},
tracerProvider
);
const span = tracer.startSpan('my-span');
const context = span.context();
assert.strictEqual(context.traceFlags, TraceFlags.SAMPLED);
span.end();
});
}

const ctx = context.active().setValue(ctxKey, 'bar')
if (typeof process !== 'undefined' && process.release.name === 'node') {
it('should sample a trace when OTEL_SAMPLING_PROBABILITY is greater than 1', () => {
process.env.OTEL_SAMPLING_PROBABILITY = '2';
const tracer = new Tracer(
{ name: 'default', version: '0.0.1' },
{},
tracerProvider
);
const span = tracer.startSpan('my-span');
const context = span.context();
assert.strictEqual(context.traceFlags, TraceFlags.SAMPLED);
span.end();
});
}

const spy = sinon.spy(tracer, 'startSpan');
if (typeof process !== 'undefined' && process.release.name === 'node') {
it('should not sample a trace when OTEL_SAMPLING_PROBABILITY is 0', () => {
process.env.OTEL_SAMPLING_PROBABILITY = '0';
const tracer = new Tracer(
{ name: 'default', version: '0.0.1' },
{},
tracerProvider
);
const span = tracer.startSpan('my-span');
const context = span.context();
assert.strictEqual(context.traceFlags, TraceFlags.NONE);
span.end();
});
}

assert.strictEqual(tracer.startActiveSpan('my-span', {attributes: {foo: 'bar'}}, ctx, span => {
try {
assert(spy.calledWith('my-span', {attributes: {foo: 'bar'}}, ctx))
assert.strictEqual(getSpan(context.active()), span)
assert.strictEqual(ctx.getValue(ctxKey), 'bar')
return 1
} finally {
span.end();
}
}), 1);
});
if (typeof process !== 'undefined' && process.release.name === 'node') {
it('should not sample a trace when OTEL_SAMPLING_PROBABILITY is less than 0', () => {
process.env.OTEL_SAMPLING_PROBABILITY = '-1';
const tracer = new Tracer(
{ name: 'default', version: '0.0.1' },
{},
tracerProvider
);
const span = tracer.startSpan('my-span');
const context = span.context();
assert.strictEqual(context.traceFlags, TraceFlags.NONE);
span.end();
});
}
});

0 comments on commit b25e1bd

Please sign in to comment.