@@ -10,7 +10,7 @@ test.describe('distributed tracing', () => {
10
10
} ) ;
11
11
12
12
const serverTxnEventPromise = waitForTransaction ( 'nuxt-4' , txnEvent => {
13
- return txnEvent . transaction . includes ( 'GET /test-param/' ) ;
13
+ return txnEvent . transaction ? .includes ( 'GET /test-param/' ) ?? false ;
14
14
} ) ;
15
15
16
16
const [ _ , clientTxnEvent , serverTxnEvent ] = await Promise . all ( [
@@ -67,66 +67,87 @@ test.describe('distributed tracing', () => {
67
67
expect ( serverTxnEvent . contexts ?. trace ?. trace_id ) . toBe ( metaTraceId ) ;
68
68
} ) ;
69
69
70
- test ( 'capture a distributed server request with parametrization ' , async ( { page } ) => {
70
+ test ( 'capture a distributed trace from a client-side API request with parametrized routes ' , async ( { page } ) => {
71
71
const clientTxnEventPromise = waitForTransaction ( 'nuxt-4' , txnEvent => {
72
- return txnEvent . transaction === '/test-param/:param()' ;
72
+ return txnEvent . transaction === '/test-param/fetch-api/ :param()' ;
73
73
} ) ;
74
-
75
74
const ssrTxnEventPromise = waitForTransaction ( 'nuxt-4' , txnEvent => {
76
- return txnEvent . transaction . includes ( 'GET /test-param/' ) ;
75
+ return txnEvent . transaction ? .includes ( 'GET /test-param/fetch-api' ) ?? false ;
77
76
} ) ;
78
-
79
77
const serverReqTxnEventPromise = waitForTransaction ( 'nuxt-4' , txnEvent => {
80
- return txnEvent . transaction . includes ( 'GET /api/test-param/' ) ;
78
+ return txnEvent . transaction ? .includes ( 'GET /api/test-param/' ) ?? false ;
81
79
} ) ;
82
80
83
- const [ , clientTxnEvent , ssrTxnEvent , , , serverReqTxnEvent ] = await Promise . all ( [
84
- page . goto ( `/test-param/${ PARAM } ` ) ,
81
+ // Navigate to the page which will trigger an API call from the client-side
82
+ await page . goto ( `/test-param/fetch-api/${ PARAM } ` ) ;
83
+
84
+ const [ clientTxnEvent , ssrTxnEvent , serverReqTxnEvent ] = await Promise . all ( [
85
85
clientTxnEventPromise ,
86
86
ssrTxnEventPromise ,
87
- expect ( page . getByText ( `Param: ${ PARAM } ` ) ) . toBeVisible ( ) ,
88
- page . getByText ( 'Fetch Server Data' , { exact : true } ) . click ( ) ,
89
87
serverReqTxnEventPromise ,
90
88
] ) ;
91
89
92
90
const httpClientSpan = clientTxnEvent ?. spans ?. find ( span => span . description === `GET /api/test-param/${ PARAM } ` ) ;
93
91
94
- expect ( ssrTxnEvent ) . toMatchObject ( {
95
- transaction : `GET /test-param/${ PARAM } ` , // todo: parametrize (nitro)
96
- transaction_info : { source : 'url' } ,
97
- type : 'transaction' ,
98
- contexts : {
99
- trace : {
100
- op : 'http.server' ,
101
- origin : 'auto.http.otel.http' ,
102
- } ,
103
- } ,
104
- } ) ;
105
-
106
- expect ( httpClientSpan ) . toMatchObject ( {
107
- description : `GET /api/test-param/${ PARAM } ` , // todo: parametrize (nitro)
108
- parent_span_id : clientTxnEvent . contexts ?. trace ?. span_id , // pageload span is parent
109
- data : expect . objectContaining ( {
110
- 'sentry.op' : 'http.client' ,
111
- 'sentry.origin' : 'auto.http.browser' ,
112
- 'http.request_method' : 'GET' ,
92
+ expect ( clientTxnEvent ) . toEqual (
93
+ expect . objectContaining ( {
94
+ type : 'transaction' ,
95
+ transaction : '/test-param/fetch-api/:param()' , // parametrized route
96
+ transaction_info : { source : 'route' } ,
97
+ contexts : expect . objectContaining ( {
98
+ trace : expect . objectContaining ( {
99
+ op : 'pageload' ,
100
+ origin : 'auto.pageload.vue' ,
101
+ } ) ,
102
+ } ) ,
113
103
} ) ,
114
- } ) ;
115
-
116
- expect ( serverReqTxnEvent ) . toMatchObject ( {
117
- transaction : `GET /api/test-param/${ PARAM } ` , // todo: parametrize (nitro)
118
- transaction_info : { source : 'url' } ,
119
- type : 'transaction' ,
120
- contexts : {
121
- trace : {
122
- op : 'http.server' ,
123
- origin : 'auto.http.otel.http' ,
124
- parent_span_id : httpClientSpan ?. span_id , // http.client span is parent
125
- } ,
126
- } ,
127
- } ) ;
104
+ ) ;
105
+
106
+ expect ( httpClientSpan ) . toBeDefined ( ) ;
107
+ expect ( httpClientSpan ) . toEqual (
108
+ expect . objectContaining ( {
109
+ description : `GET /api/test-param/${ PARAM } ` , // fixme: parametrize
110
+ parent_span_id : clientTxnEvent . contexts ?. trace ?. span_id , // pageload span is parent
111
+ data : expect . objectContaining ( {
112
+ url : `/api/test-param/${ PARAM } ` , // fixme: parametrize
113
+ type : 'fetch' ,
114
+ 'sentry.op' : 'http.client' ,
115
+ 'sentry.origin' : 'auto.http.browser' ,
116
+ 'http.method' : 'GET' ,
117
+ } ) ,
118
+ } ) ,
119
+ ) ;
120
+
121
+ expect ( ssrTxnEvent ) . toEqual (
122
+ expect . objectContaining ( {
123
+ type : 'transaction' ,
124
+ transaction : `GET /test-param/fetch-api/${ PARAM } ` , // fixme: parametrize (nitro)
125
+ transaction_info : { source : 'url' } ,
126
+ contexts : expect . objectContaining ( {
127
+ trace : expect . objectContaining ( {
128
+ op : 'http.server' ,
129
+ origin : 'auto.http.otel.http' ,
130
+ } ) ,
131
+ } ) ,
132
+ } ) ,
133
+ ) ;
134
+
135
+ expect ( serverReqTxnEvent ) . toEqual (
136
+ expect . objectContaining ( {
137
+ type : 'transaction' ,
138
+ transaction : `GET /api/test-param/${ PARAM } ` ,
139
+ transaction_info : { source : 'url' } ,
140
+ contexts : expect . objectContaining ( {
141
+ trace : expect . objectContaining ( {
142
+ op : 'http.server' ,
143
+ origin : 'auto.http.otel.http' ,
144
+ parent_span_id : httpClientSpan ?. span_id , // http.client span is parent
145
+ } ) ,
146
+ } ) ,
147
+ } ) ,
148
+ ) ;
128
149
129
- // All share the same trace_id
150
+ // All 3 transactions and the http.client span should share the same trace_id
130
151
expect ( clientTxnEvent . contexts ?. trace ?. trace_id ) . toBeDefined ( ) ;
131
152
expect ( clientTxnEvent . contexts ?. trace ?. trace_id ) . toBe ( httpClientSpan ?. trace_id ) ;
132
153
expect ( clientTxnEvent . contexts ?. trace ?. trace_id ) . toBe ( ssrTxnEvent . contexts ?. trace ?. trace_id ) ;
0 commit comments