@@ -25,7 +25,7 @@ import {
2525import { SentryNonRecordingSpan } from '../../../src/tracing/sentryNonRecordingSpan' ;
2626import { startNewTrace } from '../../../src/tracing/trace' ;
2727import type { Event , Span , StartSpanOptions } from '../../../src/types-hoist' ;
28- import { _setSpanForScope } from '../../../src/utils/spanOnScope' ;
28+ import { _getSpanForScope , _setSpanForScope } from '../../../src/utils/spanOnScope' ;
2929import { getActiveSpan , getRootSpan , getSpanDescendants , spanIsSampled } from '../../../src/utils/spanUtils' ;
3030import { TestClient , getDefaultTestClientOptions } from '../../mocks/client' ;
3131
@@ -251,20 +251,44 @@ describe('startSpan', () => {
251251 expect ( getActiveSpan ( ) ) . toBe ( undefined ) ;
252252 } ) ;
253253
254- it ( 'allows to pass a scope' , ( ) => {
254+ it ( 'starts the span on the fork of a passed custom scope' , ( ) => {
255255 const initialScope = getCurrentScope ( ) ;
256256
257- const manualScope = initialScope . clone ( ) ;
257+ const customScope = initialScope . clone ( ) ;
258+ customScope . setTag ( 'dogs' , 'great' ) ;
259+
258260 const parentSpan = new SentrySpan ( { spanId : 'parent-span-id' , sampled : true } ) ;
259- _setSpanForScope ( manualScope , parentSpan ) ;
261+ _setSpanForScope ( customScope , parentSpan ) ;
260262
261- startSpan ( { name : 'GET users/[id]' , scope : manualScope } , span => {
263+ startSpan ( { name : 'GET users/[id]' , scope : customScope } , span => {
264+ // current scope is forked from the customScope
262265 expect ( getCurrentScope ( ) ) . not . toBe ( initialScope ) ;
263- expect ( getCurrentScope ( ) ) . toBe ( manualScope ) ;
266+ expect ( getCurrentScope ( ) ) . not . toBe ( customScope ) ;
267+ expect ( getCurrentScope ( ) . getScopeData ( ) . tags ) . toEqual ( { dogs : 'great' } ) ;
268+
269+ // active span is set correctly
264270 expect ( getActiveSpan ( ) ) . toBe ( span ) ;
271+
272+ // span has the correct parent span
265273 expect ( spanToJSON ( span ) . parent_span_id ) . toBe ( 'parent-span-id' ) ;
274+
275+ // scope data modifications
276+ getCurrentScope ( ) . setTag ( 'cats' , 'great' ) ;
277+ customScope . setTag ( 'bears' , 'great' ) ;
278+
279+ expect ( getCurrentScope ( ) . getScopeData ( ) . tags ) . toEqual ( { dogs : 'great' , cats : 'great' } ) ;
280+ expect ( customScope . getScopeData ( ) . tags ) . toEqual ( { dogs : 'great' , bears : 'great' } ) ;
266281 } ) ;
267282
283+ // customScope modifications are persisted
284+ expect ( customScope . getScopeData ( ) . tags ) . toEqual ( { dogs : 'great' , bears : 'great' } ) ;
285+
286+ // span is parent span again on customScope
287+ withScope ( customScope , ( ) => {
288+ expect ( getActiveSpan ( ) ) . toBe ( parentSpan ) ;
289+ } ) ;
290+
291+ // but activeSpan and currentScope are reset, since customScope was never active
268292 expect ( getCurrentScope ( ) ) . toBe ( initialScope ) ;
269293 expect ( getActiveSpan ( ) ) . toBe ( undefined ) ;
270294 } ) ;
@@ -273,29 +297,35 @@ describe('startSpan', () => {
273297 it ( 'with parent span' , ( ) => {
274298 const initialScope = getCurrentScope ( ) ;
275299
276- const manualScope = initialScope . clone ( ) ;
300+ const customScope = initialScope . clone ( ) ;
277301 const parentSpan = new SentrySpan ( { spanId : 'parent-span-id' , sampled : true } ) ;
278- _setSpanForScope ( manualScope , parentSpan ) ;
302+ _setSpanForScope ( customScope , parentSpan ) ;
279303
280- startSpan ( { name : 'span 1' , scope : manualScope } , span1 => {
304+ startSpan ( { name : 'span 1' , scope : customScope } , span1 => {
305+ // current scope is forked from the customScope
281306 expect ( getCurrentScope ( ) ) . not . toBe ( initialScope ) ;
282- expect ( getCurrentScope ( ) ) . toBe ( manualScope ) ;
307+ expect ( getCurrentScope ( ) ) . not . toBe ( customScope ) ;
308+
283309 expect ( getActiveSpan ( ) ) . toBe ( span1 ) ;
284310 expect ( spanToJSON ( span1 ) . parent_span_id ) . toBe ( 'parent-span-id' ) ;
285311 } ) ;
286312
287- withScope ( manualScope , ( ) => {
313+ // active span on customScope is reset
314+ withScope ( customScope , ( ) => {
288315 expect ( getActiveSpan ( ) ) . toBe ( parentSpan ) ;
289316 } ) ;
290317
291- startSpan ( { name : 'span 2' , scope : manualScope } , span2 => {
318+ startSpan ( { name : 'span 2' , scope : customScope } , span2 => {
319+ // current scope is forked from the customScope
292320 expect ( getCurrentScope ( ) ) . not . toBe ( initialScope ) ;
293- expect ( getCurrentScope ( ) ) . toBe ( manualScope ) ;
321+ expect ( getCurrentScope ( ) ) . not . toBe ( customScope ) ;
322+
294323 expect ( getActiveSpan ( ) ) . toBe ( span2 ) ;
324+ // both, span1 and span2 are children of the parent span
295325 expect ( spanToJSON ( span2 ) . parent_span_id ) . toBe ( 'parent-span-id' ) ;
296326 } ) ;
297327
298- withScope ( manualScope , ( ) => {
328+ withScope ( customScope , ( ) => {
299329 expect ( getActiveSpan ( ) ) . toBe ( parentSpan ) ;
300330 } ) ;
301331
@@ -305,31 +335,35 @@ describe('startSpan', () => {
305335
306336 it ( 'without parent span' , ( ) => {
307337 const initialScope = getCurrentScope ( ) ;
308- const manualScope = initialScope . clone ( ) ;
338+ const customScope = initialScope . clone ( ) ;
309339
310- const traceId = manualScope . getPropagationContext ( ) ?. traceId ;
340+ const traceId = customScope . getPropagationContext ( ) ?. traceId ;
311341
312- startSpan ( { name : 'span 1' , scope : manualScope } , span1 => {
342+ startSpan ( { name : 'span 1' , scope : customScope } , span1 => {
313343 expect ( getCurrentScope ( ) ) . not . toBe ( initialScope ) ;
314- expect ( getCurrentScope ( ) ) . toBe ( manualScope ) ;
344+ expect ( getCurrentScope ( ) ) . not . toBe ( customScope ) ;
345+
315346 expect ( getActiveSpan ( ) ) . toBe ( span1 ) ;
316- expect ( spanToJSON ( span1 ) . parent_span_id ) . toBe ( undefined ) ;
347+ expect ( getRootSpan ( getActiveSpan ( ) ! ) ) . toBe ( span1 ) ;
348+
317349 expect ( span1 . spanContext ( ) . traceId ) . toBe ( traceId ) ;
318350 } ) ;
319351
320- withScope ( manualScope , ( ) => {
352+ withScope ( customScope , ( ) => {
321353 expect ( getActiveSpan ( ) ) . toBe ( undefined ) ;
322354 } ) ;
323355
324- startSpan ( { name : 'span 2' , scope : manualScope } , span2 => {
356+ startSpan ( { name : 'span 2' , scope : customScope } , span2 => {
325357 expect ( getCurrentScope ( ) ) . not . toBe ( initialScope ) ;
326- expect ( getCurrentScope ( ) ) . toBe ( manualScope ) ;
358+ expect ( getCurrentScope ( ) ) . not . toBe ( customScope ) ;
359+
327360 expect ( getActiveSpan ( ) ) . toBe ( span2 ) ;
328- expect ( spanToJSON ( span2 ) . parent_span_id ) . toBe ( undefined ) ;
361+ expect ( getRootSpan ( getActiveSpan ( ) ! ) ) . toBe ( span2 ) ;
362+
329363 expect ( span2 . spanContext ( ) . traceId ) . toBe ( traceId ) ;
330364 } ) ;
331365
332- withScope ( manualScope , ( ) => {
366+ withScope ( customScope , ( ) => {
333367 expect ( getActiveSpan ( ) ) . toBe ( undefined ) ;
334368 } ) ;
335369
0 commit comments