@@ -19,53 +19,25 @@ import * as is from 'is';
1919import * as uuid from 'uuid' ;
2020
2121import { cls , RootContext } from './cls' ;
22+ import { TracePolicy } from './config' ;
2223import { Constants , SpanType } from './constants' ;
2324import { Logger } from './logger' ;
2425import { Func , RootSpan , RootSpanOptions , Span , SpanOptions , Tracer } from './plugin-types' ;
2526import { RootSpanData , UNCORRELATED_CHILD_SPAN , UNCORRELATED_ROOT_SPAN , UNTRACED_CHILD_SPAN , UNTRACED_ROOT_SPAN } from './span-data' ;
2627import { TraceLabels } from './trace-labels' ;
2728import { traceWriter } from './trace-writer' ;
28- import { TracePolicy , TracePolicyConfig } from './tracing-policy' ;
29+ import { neverTrace } from './tracing-policy' ;
2930import * as util from './util' ;
3031
31- /**
32- * An enumeration of the different possible types of behavior when dealing with
33- * incoming trace context. Requests are still subject to local tracing policy.
34- */
35- export enum TraceContextHeaderBehavior {
36- /**
37- * Respect the trace context header if it exists; otherwise, trace the
38- * request as a new trace.
39- */
40- DEFAULT = 'default' ,
41- /**
42- * Respect the trace context header if it exists; otherwise, treat the
43- * request as unsampled and don't trace it.
44- */
45- REQUIRE = 'require' ,
46- /**
47- * Trace every request as a new trace, even if trace context exists.
48- */
49- IGNORE = 'ignore'
50- }
51-
5232/**
5333 * An interface describing configuration fields read by the StackdriverTracer
5434 * object. This includes fields read by the trace policy.
5535 */
5636export interface StackdriverTracerConfig {
5737 enhancedDatabaseReporting : boolean ;
58- contextHeaderBehavior : TraceContextHeaderBehavior ;
5938 rootSpanNameOverride : ( path : string ) => string ;
6039 spansPerTraceSoftLimit : number ;
6140 spansPerTraceHardLimit : number ;
62- tracePolicyConfig : TracePolicyConfig ;
63- }
64-
65- interface IncomingTraceContext {
66- traceId ?: string ;
67- spanId ?: string ;
68- options : number ;
6941}
7042
7143/**
@@ -117,10 +89,10 @@ export class StackdriverTracer implements Tracer {
11789 * @param logger A logger object.
11890 * @private
11991 */
120- enable ( config : StackdriverTracerConfig , logger : Logger ) {
92+ enable ( config : StackdriverTracerConfig , policy : TracePolicy , logger : Logger ) {
12193 this . logger = logger ;
12294 this . config = config ;
123- this . policy = new TracePolicy ( config . tracePolicyConfig ) ;
95+ this . policy = policy ;
12496 this . enabled = true ;
12597 }
12698
@@ -134,7 +106,7 @@ export class StackdriverTracer implements Tracer {
134106 // never generates traces allows persisting wrapped methods (either because
135107 // they are already instantiated or the plugin doesn't unpatch them) to
136108 // short-circuit out of trace generation logic.
137- this . policy = TracePolicy . never ( ) ;
109+ this . policy = neverTrace ( ) ;
138110 this . enabled = false ;
139111 }
140112
@@ -175,48 +147,49 @@ export class StackdriverTracer implements Tracer {
175147 }
176148
177149 // Attempt to read incoming trace context.
178- const incomingTraceContext : IncomingTraceContext = { options : 1 } ;
179- let parsedContext : util . TraceContext | null = null ;
180- if ( isString ( options . traceContext ) &&
181- this . config ! . contextHeaderBehavior !==
182- TraceContextHeaderBehavior . IGNORE ) {
183- parsedContext = util . parseContextFromHeader ( options . traceContext ) ;
184- }
185- if ( parsedContext ) {
186- if ( parsedContext . options === undefined ) {
187- // If there are no incoming option flags, default to 0x1.
188- parsedContext . options = 1 ;
150+ const parseContext = ( stringifiedTraceContext ?: string | null ) => {
151+ const parsedContext = isString ( stringifiedTraceContext ) ?
152+ util . parseContextFromHeader ( stringifiedTraceContext ) :
153+ null ;
154+ if ( parsedContext ) {
155+ if ( parsedContext . options === undefined ) {
156+ // If there are no incoming option flags, default to 0x1.
157+ parsedContext . options = 1 ;
158+ }
189159 }
190- Object . assign ( incomingTraceContext , parsedContext ) ;
191- } else if (
192- this . config ! . contextHeaderBehavior ===
193- TraceContextHeaderBehavior . REQUIRE ) {
194- incomingTraceContext . options = 0 ;
195- }
160+ return parsedContext as Required < util . TraceContext > | null ;
161+ } ;
162+ const traceContext = parseContext ( options . traceContext ) ;
196163
197164 // Consult the trace policy.
198- const locallyAllowed = this . policy ! . shouldTrace ( {
165+ const shouldTrace = this . policy ! . shouldTrace ( {
199166 timestamp : Date . now ( ) ,
200167 url : options . url || '' ,
201- method : options . method || ''
168+ method : options . method || '' ,
169+ traceContext,
170+ options
202171 } ) ;
203- const remotelyAllowed = ! ! (
204- incomingTraceContext . options & Constants . TRACE_OPTIONS_TRACE_ENABLED ) ;
205172
206173 let rootContext : RootSpan & RootContext ;
174+
207175 // Don't create a root span if the trace policy disallows it.
208- if ( ! locallyAllowed || ! remotelyAllowed ) {
176+ if ( ! shouldTrace ) {
209177 rootContext = UNTRACED_ROOT_SPAN ;
210178 } else {
211179 // Create a new root span, and invoke fn with it.
212- const traceId =
213- incomingTraceContext . traceId || ( uuid . v4 ( ) . split ( '-' ) . join ( '' ) ) ;
214- const parentId = incomingTraceContext . spanId || '0' ;
215- const name = this . config ! . rootSpanNameOverride ( options . name ) ;
216180 rootContext = new RootSpanData (
217- { projectId : '' , traceId, spans : [ ] } , /* Trace object */
218- name , /* Span name */
219- parentId , /* Parent's span ID */
181+ // Trace object
182+ {
183+ projectId : '' ,
184+ traceId : traceContext ? traceContext . traceId :
185+ uuid . v4 ( ) . split ( '-' ) . join ( '' ) ,
186+ spans : [ ]
187+ } ,
188+ // Span name
189+ this . config ! . rootSpanNameOverride ( options . name ) ,
190+ // Parent span ID
191+ traceContext ? traceContext . spanId : '0' ,
192+ // Number of stack frames to skip
220193 options . skipFrames || 0 ) ;
221194 }
222195
0 commit comments