0
# Envelope System
1
2
**DEPRECATED**: Import all functions from `@sentry/core` instead of `@sentry/utils`.
3
4
Data packaging system for structuring and transmitting telemetry data to Sentry servers with metadata, headers, and efficient serialization.
5
6
## Capabilities
7
8
### Envelope Structure
9
10
Core envelope data structures and type definitions.
11
12
```typescript { .api }
13
/**
14
* Envelope item types supported by Sentry
15
*/
16
type EnvelopeItemType =
17
| 'event'
18
| 'transaction'
19
| 'session'
20
| 'attachment'
21
| 'user_report'
22
| 'profile'
23
| 'replay_event'
24
| 'client_report'
25
| 'span';
26
27
/**
28
* Header information for envelope items
29
*/
30
interface EnvelopeItemHeader {
31
type: EnvelopeItemType;
32
length?: number;
33
filename?: string;
34
content_type?: string;
35
attachment_type?: string;
36
}
37
38
/**
39
* Envelope item containing header and payload
40
*/
41
interface EnvelopeItem<T = any> {
42
0: EnvelopeItemHeader;
43
1: T;
44
}
45
46
/**
47
* Envelope header with metadata
48
*/
49
interface EnvelopeHeader {
50
event_id?: string;
51
sent_at?: string;
52
sdk?: {
53
name: string;
54
version: string;
55
};
56
trace?: {
57
trace_id: string;
58
public_key?: string;
59
};
60
}
61
62
/**
63
* Complete envelope structure
64
*/
65
interface Envelope {
66
0: EnvelopeHeader;
67
1: EnvelopeItem[];
68
}
69
```
70
71
### Envelope Creation
72
73
Functions for creating and assembling envelopes.
74
75
```typescript { .api }
76
/**
77
* Creates a new envelope with headers and optional items
78
* @param headers - Envelope headers
79
* @param items - Optional array of envelope items
80
* @returns New envelope
81
*/
82
function createEnvelope<E extends Envelope>(
83
headers: E[0],
84
items?: E[1]
85
): E;
86
87
/**
88
* Creates headers for event envelopes
89
* @param event - Event data
90
* @param tunnel - Optional tunnel configuration
91
* @param dsn - Data source name
92
* @returns Envelope headers
93
*/
94
function createEventEnvelopeHeaders(
95
event: Event,
96
tunnel?: string,
97
dsn?: string
98
): EnvelopeHeader;
99
100
/**
101
* Gets SDK metadata for envelope headers
102
* @param sdk - SDK information
103
* @returns SDK metadata object
104
*/
105
function getSdkMetadataForEnvelopeHeader(sdk: {
106
name: string;
107
version: string;
108
integrations?: string[];
109
packages?: Array<{ name: string; version: string }>;
110
}): { name: string; version: string };
111
```
112
113
### Envelope Items
114
115
Functions for creating specific types of envelope items.
116
117
```typescript { .api }
118
/**
119
* Creates an attachment envelope item
120
* @param attachment - Attachment data
121
* @returns Envelope item for the attachment
122
*/
123
function createAttachmentEnvelopeItem(
124
attachment: {
125
data: string | Uint8Array;
126
filename: string;
127
content_type?: string;
128
attachment_type?: string;
129
}
130
): EnvelopeItem;
131
132
/**
133
* Creates a span envelope item for performance monitoring
134
* @param span - Span data
135
* @returns Envelope item for the span
136
*/
137
function createSpanEnvelopeItem(span: any): EnvelopeItem;
138
139
/**
140
* Creates a client report envelope for SDK metrics
141
* @param discardedEvents - Array of discarded event information
142
* @param dsn - Data source name
143
* @param timestamp - Report timestamp
144
* @returns Complete client report envelope
145
*/
146
function createClientReportEnvelope(
147
discardedEvents: Array<{
148
reason: string;
149
category: string;
150
quantity: number;
151
}>,
152
dsn: string,
153
timestamp?: number
154
): Envelope;
155
```
156
157
### Envelope Manipulation
158
159
Functions for modifying and querying envelopes.
160
161
```typescript { .api }
162
/**
163
* Adds an item to an existing envelope
164
* @param envelope - Target envelope
165
* @param newItem - Item to add
166
* @returns Modified envelope
167
*/
168
function addItemToEnvelope<E extends Envelope>(
169
envelope: E,
170
newItem: E[1][number]
171
): E;
172
173
/**
174
* Iterates over all items in an envelope
175
* @param envelope - Envelope to iterate
176
* @param callback - Function called for each item
177
* @returns True if iteration completed, false if callback returned false
178
*/
179
function forEachEnvelopeItem<E extends Envelope>(
180
envelope: E,
181
callback: (item: E[1][number], type?: EnvelopeItemType) => boolean | void,
182
): boolean;
183
184
/**
185
* Checks if envelope contains items of a specific type
186
* @param envelope - Envelope to check
187
* @param itemType - Item type to look for
188
* @returns True if envelope contains the specified item type
189
*/
190
function envelopeContainsItemType(
191
envelope: Envelope,
192
itemType: EnvelopeItemType
193
): boolean;
194
195
/**
196
* Converts envelope item type to data category for rate limiting
197
* @param itemType - Envelope item type
198
* @returns Corresponding data category
199
*/
200
function envelopeItemTypeToDataCategory(
201
itemType: EnvelopeItemType
202
): string;
203
```
204
205
### Envelope Serialization
206
207
Functions for serializing and parsing envelope data for transmission.
208
209
```typescript { .api }
210
/**
211
* Serializes an envelope to string format for transmission
212
* @param envelope - Envelope to serialize
213
* @returns Serialized envelope string
214
*/
215
function serializeEnvelope(envelope: Envelope): string;
216
217
/**
218
* Parses a serialized envelope string back to envelope object
219
* @param env - Serialized envelope string
220
* @returns Parsed envelope object
221
*/
222
function parseEnvelope(env: string): Envelope;
223
```
224
225
**Usage Examples:**
226
227
```typescript
228
import {
229
createEnvelope,
230
createEventEnvelopeHeaders,
231
addItemToEnvelope,
232
createAttachmentEnvelopeItem,
233
serializeEnvelope,
234
parseEnvelope
235
} from "@sentry/core";
236
237
// Create an envelope for an error event
238
const event = {
239
event_id: 'abc123',
240
message: 'Something went wrong',
241
level: 'error',
242
timestamp: Date.now() / 1000
243
};
244
245
const headers = createEventEnvelopeHeaders(event, undefined, 'https://key@sentry.io/project');
246
const envelope = createEnvelope(headers, [
247
[{ type: 'event' }, event]
248
]);
249
250
// Add an attachment to the envelope
251
const attachment = createAttachmentEnvelopeItem({
252
data: 'log file contents',
253
filename: 'app.log',
254
content_type: 'text/plain',
255
attachment_type: 'event.attachment'
256
});
257
258
const envelopeWithAttachment = addItemToEnvelope(envelope, attachment);
259
260
// Serialize for transmission
261
const serialized = serializeEnvelope(envelopeWithAttachment);
262
console.log('Serialized envelope:', serialized);
263
264
// Parse received envelope
265
const parsed = parseEnvelope(serialized);
266
console.log('Parsed envelope:', parsed);
267
```
268
269
## Envelope Processing Patterns
270
271
### Event Processing Pipeline
272
273
Complete pipeline for processing events into envelopes:
274
275
```typescript
276
import {
277
createEnvelope,
278
createEventEnvelopeHeaders,
279
addItemToEnvelope,
280
createAttachmentEnvelopeItem,
281
serializeEnvelope,
282
forEachEnvelopeItem
283
} from "@sentry/core";
284
285
class EventProcessor {
286
processEvent(event: any, attachments: any[] = []): string {
287
// Create envelope headers
288
const headers = createEventEnvelopeHeaders(event);
289
290
// Create initial envelope with event
291
let envelope = createEnvelope(headers, [
292
[{ type: 'event' }, event]
293
]);
294
295
// Add attachments if present
296
for (const attachment of attachments) {
297
const attachmentItem = createAttachmentEnvelopeItem(attachment);
298
envelope = addItemToEnvelope(envelope, attachmentItem);
299
}
300
301
// Log envelope contents for debugging
302
forEachEnvelopeItem(envelope, (item, type) => {
303
console.log(`Envelope contains: ${type}`);
304
});
305
306
// Serialize for transmission
307
return serializeEnvelope(envelope);
308
}
309
}
310
```
311
312
### Batch Processing
313
314
Processing multiple events in a single envelope:
315
316
```typescript
317
import {
318
createEnvelope,
319
addItemToEnvelope,
320
envelopeContainsItemType,
321
serializeEnvelope
322
} from "@sentry/core";
323
324
class BatchProcessor {
325
createBatchEnvelope(events: any[]): Envelope {
326
// Create envelope with first event's headers
327
const firstEvent = events[0];
328
const headers = createEventEnvelopeHeaders(firstEvent);
329
330
let envelope = createEnvelope(headers);
331
332
// Add all events to the envelope
333
for (const event of events) {
334
envelope = addItemToEnvelope(envelope, [
335
{ type: 'event' },
336
event
337
]);
338
}
339
340
return envelope;
341
}
342
343
validateEnvelope(envelope: Envelope): boolean {
344
// Check that envelope has at least one event
345
if (!envelopeContainsItemType(envelope, 'event')) {
346
console.warn('Envelope contains no events');
347
return false;
348
}
349
350
// Additional validation logic
351
return true;
352
}
353
}
354
```
355
356
### Client Report Generation
357
358
Creating client reports for SDK metrics:
359
360
```typescript
361
import { createClientReportEnvelope, serializeEnvelope } from "@sentry/core";
362
363
class MetricsReporter {
364
private discardedEvents: Array<{
365
reason: string;
366
category: string;
367
quantity: number;
368
}> = [];
369
370
recordDiscardedEvent(reason: string, category: string, quantity = 1) {
371
const existing = this.discardedEvents.find(
372
e => e.reason === reason && e.category === category
373
);
374
375
if (existing) {
376
existing.quantity += quantity;
377
} else {
378
this.discardedEvents.push({ reason, category, quantity });
379
}
380
}
381
382
generateReport(dsn: string): string {
383
const envelope = createClientReportEnvelope(
384
this.discardedEvents,
385
dsn,
386
Date.now()
387
);
388
389
// Clear the recorded events
390
this.discardedEvents.length = 0;
391
392
return serializeEnvelope(envelope);
393
}
394
}
395
396
// Usage
397
const reporter = new MetricsReporter();
398
reporter.recordDiscardedEvent('rate_limit', 'error', 5);
399
reporter.recordDiscardedEvent('invalid_data', 'transaction', 2);
400
401
const report = reporter.generateReport('https://key@sentry.io/project');
402
```
403
404
### Envelope Filtering
405
406
Filtering envelope contents based on criteria:
407
408
```typescript
409
import {
410
forEachEnvelopeItem,
411
createEnvelope,
412
envelopeItemTypeToDataCategory
413
} from "@sentry/core";
414
415
class EnvelopeFilter {
416
filterByCategory(envelope: Envelope, allowedCategories: string[]): Envelope {
417
const filteredItems: EnvelopeItem[] = [];
418
419
forEachEnvelopeItem(envelope, (item, type) => {
420
if (type) {
421
const category = envelopeItemTypeToDataCategory(type);
422
if (allowedCategories.includes(category)) {
423
filteredItems.push(item);
424
}
425
}
426
return true; // Continue iteration
427
});
428
429
return createEnvelope(envelope[0], filteredItems);
430
}
431
432
removeAttachments(envelope: Envelope): Envelope {
433
const filteredItems: EnvelopeItem[] = [];
434
435
forEachEnvelopeItem(envelope, (item, type) => {
436
if (type !== 'attachment') {
437
filteredItems.push(item);
438
}
439
return true;
440
});
441
442
return createEnvelope(envelope[0], filteredItems);
443
}
444
}
445
```
446
447
## Types
448
449
```typescript { .api }
450
interface Event {
451
event_id?: string;
452
message?: string;
453
level?: string;
454
timestamp?: number;
455
platform?: string;
456
logger?: string;
457
server_name?: string;
458
release?: string;
459
environment?: string;
460
fingerprint?: string[];
461
[key: string]: any;
462
}
463
464
type DataCategory =
465
| 'default'
466
| 'error'
467
| 'transaction'
468
| 'security'
469
| 'attachment'
470
| 'session'
471
| 'profile'
472
| 'replay'
473
| 'internal';
474
```
475
476
**Migration Note**: All envelope functions have been moved from `@sentry/utils` to `@sentry/core`. Update your imports accordingly.