@dxos/observability 0.4.7-next.f4b92be → 0.4.8-main.00e6f19

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (58) hide show
  1. package/dist/lib/browser/{chunk-6KUJPLEH.mjs → chunk-G5DKURIM.mjs} +38 -16
  2. package/dist/lib/browser/chunk-G5DKURIM.mjs.map +7 -0
  3. package/dist/lib/browser/{chunk-XF67HMEA.mjs → chunk-Y66LFYI5.mjs} +161 -36
  4. package/dist/lib/browser/chunk-Y66LFYI5.mjs.map +7 -0
  5. package/dist/lib/browser/index.mjs +2 -1
  6. package/dist/lib/browser/meta.json +1 -1
  7. package/dist/lib/browser/observability-A5P77DUJ.mjs +8 -0
  8. package/dist/lib/browser/segment/index.mjs +1 -1
  9. package/dist/lib/browser/sentry/index.mjs +7 -5
  10. package/dist/lib/node/{chunk-T2S7C5J2.cjs → chunk-3OQ7O6O7.cjs} +157 -39
  11. package/dist/lib/node/chunk-3OQ7O6O7.cjs.map +7 -0
  12. package/dist/lib/node/{chunk-FSAOBKO2.cjs → chunk-VYXPK6C2.cjs} +38 -51
  13. package/dist/lib/node/chunk-VYXPK6C2.cjs.map +7 -0
  14. package/dist/lib/node/datadog/index.cjs +1 -1
  15. package/dist/lib/node/datadog/index.cjs.map +2 -2
  16. package/dist/lib/node/index.cjs +16 -15
  17. package/dist/lib/node/index.cjs.map +2 -2
  18. package/dist/lib/node/meta.json +1 -1
  19. package/dist/lib/node/{observability-M64E2QBA.cjs → observability-T3HIK77L.cjs} +7 -6
  20. package/dist/lib/node/observability-T3HIK77L.cjs.map +7 -0
  21. package/dist/lib/node/segment/index.cjs +2 -2
  22. package/dist/lib/node/sentry/index.cjs +13 -13
  23. package/dist/lib/node/sentry/index.cjs.map +1 -1
  24. package/dist/types/src/datadog/metrics.js +1 -1
  25. package/dist/types/src/datadog/metrics.js.map +1 -1
  26. package/dist/types/src/helpers/node-observability.d.ts.map +1 -1
  27. package/dist/types/src/helpers/node-observability.js +0 -1
  28. package/dist/types/src/helpers/node-observability.js.map +1 -1
  29. package/dist/types/src/observability.d.ts +1 -2
  30. package/dist/types/src/observability.d.ts.map +1 -1
  31. package/dist/types/src/observability.js +21 -20
  32. package/dist/types/src/observability.js.map +1 -1
  33. package/dist/types/src/sentry/browser.d.ts +3 -2
  34. package/dist/types/src/sentry/browser.d.ts.map +1 -1
  35. package/dist/types/src/sentry/browser.js +15 -5
  36. package/dist/types/src/sentry/browser.js.map +1 -1
  37. package/dist/types/src/sentry/node.d.ts +3 -4
  38. package/dist/types/src/sentry/node.d.ts.map +1 -1
  39. package/dist/types/src/sentry/node.js +11 -43
  40. package/dist/types/src/sentry/node.js.map +1 -1
  41. package/dist/types/src/sentry/sentry-log-processor.d.ts +9 -0
  42. package/dist/types/src/sentry/sentry-log-processor.d.ts.map +1 -0
  43. package/dist/types/src/sentry/sentry-log-processor.js +133 -0
  44. package/dist/types/src/sentry/sentry-log-processor.js.map +1 -0
  45. package/package.json +14 -14
  46. package/src/datadog/metrics.ts +1 -1
  47. package/src/helpers/node-observability.ts +0 -1
  48. package/src/observability.ts +23 -21
  49. package/src/sentry/browser.ts +17 -4
  50. package/src/sentry/node.ts +11 -48
  51. package/src/sentry/sentry-log-processor.ts +144 -0
  52. package/dist/lib/browser/chunk-6KUJPLEH.mjs.map +0 -7
  53. package/dist/lib/browser/chunk-XF67HMEA.mjs.map +0 -7
  54. package/dist/lib/browser/observability-MK4LFDOW.mjs +0 -7
  55. package/dist/lib/node/chunk-FSAOBKO2.cjs.map +0 -7
  56. package/dist/lib/node/chunk-T2S7C5J2.cjs.map +0 -7
  57. package/dist/lib/node/observability-M64E2QBA.cjs.map +0 -7
  58. /package/dist/lib/browser/{observability-MK4LFDOW.mjs.map → observability-A5P77DUJ.mjs.map} +0 -0
@@ -1,6 +1,6 @@
1
1
  // packages/sdk/observability/src/sentry/browser.ts
2
- import { init as naturalInit, setTag, addBreadcrumb as naturalAddBreadcrumb, captureException as naturalCaptureException, BrowserTracing, replayIntegration } from "@sentry/browser";
3
- import { captureConsoleIntegration, httpClientIntegration } from "@sentry/integrations";
2
+ import { init as naturalInit, setTag, addBreadcrumb as naturalAddBreadcrumb, captureException as naturalCaptureException, captureMessage as naturalCaptureMessage, withScope as naturalWithScope, BrowserTracing, replayIntegration, breadcrumbsIntegration } from "@sentry/browser";
3
+ import { httpClientIntegration } from "@sentry/integrations";
4
4
  import { log as log2 } from "@dxos/log";
5
5
 
6
6
  // packages/sdk/observability/src/sentry/tracing.ts
@@ -178,7 +178,7 @@ var init = (options) => {
178
178
  try {
179
179
  log2("sentry init", options, {
180
180
  F: __dxlog_file2,
181
- L: 33,
181
+ L: 36,
182
182
  S: void 0,
183
183
  C: (f, a) => f(...a)
184
184
  });
@@ -188,11 +188,9 @@ var init = (options) => {
188
188
  release: options.release,
189
189
  environment: options.environment,
190
190
  integrations: [
191
- captureConsoleIntegration({
192
- levels: [
193
- "error",
194
- "warn"
195
- ]
191
+ breadcrumbsIntegration({
192
+ console: false,
193
+ fetch: false
196
194
  }),
197
195
  httpClientIntegration({
198
196
  failedRequestStatusCodes: [
@@ -227,7 +225,7 @@ var init = (options) => {
227
225
  } catch (err) {
228
226
  log2.catch("Failed to initialize sentry", err, {
229
227
  F: __dxlog_file2,
230
- L: 59,
228
+ L: 62,
231
229
  S: void 0,
232
230
  C: (f, a) => f(...a)
233
231
  });
@@ -238,14 +236,14 @@ var addBreadcrumb = (breadcrumb) => {
238
236
  naturalAddBreadcrumb(breadcrumb);
239
237
  log2("add breadcrumb", breadcrumb, {
240
238
  F: __dxlog_file2,
241
- L: 75,
239
+ L: 78,
242
240
  S: void 0,
243
241
  C: (f, a) => f(...a)
244
242
  });
245
243
  } catch (err) {
246
244
  log2.catch("Failed to add breadcrumb", err, {
247
245
  F: __dxlog_file2,
248
- L: 77,
246
+ L: 80,
249
247
  S: void 0,
250
248
  C: (f, a) => f(...a)
251
249
  });
@@ -260,7 +258,7 @@ var captureException = (exception, captureContext) => {
260
258
  ...captureContext
261
259
  }, {
262
260
  F: __dxlog_file2,
263
- L: 91,
261
+ L: 94,
264
262
  S: void 0,
265
263
  C: (f, a) => f(...a)
266
264
  });
@@ -268,15 +266,38 @@ var captureException = (exception, captureContext) => {
268
266
  } catch (err) {
269
267
  log2.catch("Failed to capture exception", err, {
270
268
  F: __dxlog_file2,
271
- L: 94,
269
+ L: 97,
272
270
  S: void 0,
273
271
  C: (f, a) => f(...a)
274
272
  });
275
273
  return "unknown";
276
274
  }
277
275
  };
278
- var enableSentryLogProcessor = () => {
276
+ var captureMessage = (exception, captureContext) => {
277
+ try {
278
+ const eventId = naturalCaptureMessage(exception, captureContext);
279
+ log2("capture message", {
280
+ exception,
281
+ eventId,
282
+ captureContext
283
+ }, {
284
+ F: __dxlog_file2,
285
+ L: 105,
286
+ S: void 0,
287
+ C: (f, a) => f(...a)
288
+ });
289
+ return eventId;
290
+ } catch (err) {
291
+ log2.catch("Failed to capture message", err, {
292
+ F: __dxlog_file2,
293
+ L: 108,
294
+ S: void 0,
295
+ C: (f, a) => f(...a)
296
+ });
297
+ return "unknown";
298
+ }
279
299
  };
300
+ var withScope = naturalWithScope;
280
301
 
281
302
  export {
282
303
  configureTracing,
@@ -285,9 +306,10 @@ export {
285
306
  init,
286
307
  addBreadcrumb,
287
308
  captureException,
288
- enableSentryLogProcessor,
309
+ captureMessage,
310
+ withScope,
289
311
  setTag2 as setTag,
290
312
  setTags,
291
313
  setUser
292
314
  };
293
- //# sourceMappingURL=chunk-6KUJPLEH.mjs.map
315
+ //# sourceMappingURL=chunk-G5DKURIM.mjs.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../../src/sentry/browser.ts", "../../../src/sentry/tracing.ts"],
4
+ "sourcesContent": ["//\n// Copyright 2022 DXOS.org\n//\n\nimport {\n init as naturalInit,\n setTag,\n addBreadcrumb as naturalAddBreadcrumb,\n captureException as naturalCaptureException,\n captureMessage as naturalCaptureMessage,\n withScope as naturalWithScope,\n BrowserTracing,\n replayIntegration,\n breadcrumbsIntegration,\n} from '@sentry/browser';\nimport { httpClientIntegration } from '@sentry/integrations';\n\nimport { log } from '@dxos/log';\n\nimport { type InitOptions } from './types';\n\n// Browser only feature.\nexport * from './tracing';\n\n// Polyfill export.\nexport { setTag, setTags, setUser } from '@sentry/browser';\n\n/**\n * To use this SDK, call the init function as early as possible when loading the web page.\n * To set context information or send manual events, use the provided methods.\n *\n * @param options {InitOptions}\n */\nexport const init = (options: InitOptions) => {\n try {\n log('sentry init', options);\n naturalInit({\n enabled: options.enable ?? true,\n dsn: options.destination,\n release: options.release,\n environment: options.environment,\n integrations: [\n breadcrumbsIntegration({ console: false, fetch: false }),\n httpClientIntegration({ failedRequestStatusCodes: [[400, 599]] }),\n ...(options.tracing ? [new BrowserTracing()] : []),\n ...(options.replay ? [replayIntegration({ blockAllMedia: true, maskAllText: true })] : []),\n ],\n replaysSessionSampleRate: options.replaySampleRate,\n replaysOnErrorSampleRate: options.replaySampleRateOnError,\n tracesSampleRate: options.sampleRate,\n transport: options.transport,\n beforeSend: (event) => {\n options.onError?.(event);\n return event;\n },\n });\n\n Object.entries(options.properties ?? {}).forEach(([key, value]) => {\n setTag(key, value);\n });\n } catch (err) {\n log.catch('Failed to initialize sentry', err);\n }\n};\n\n/**\n * Records a new breadcrumb which will be attached to future events.\n *\n * Breadcrumbs will be added to subsequent events to provide more context on user's actions prior to an error or crash.\n *\n * https://docs.sentry.io/platforms/javascript/enriching-events/breadcrumbs/\n *\n * @param breadcrumb — The breadcrumb to record.\n */\nexport const addBreadcrumb: typeof naturalAddBreadcrumb = (breadcrumb) => {\n try {\n naturalAddBreadcrumb(breadcrumb);\n log('add breadcrumb', breadcrumb);\n } catch (err) {\n log.catch('Failed to add breadcrumb', err);\n }\n};\n\n/**\n * Captures an exception event and sends it to Sentry.\n *\n * @param exception — An exception-like object.\n * @param captureContext — Additional scope data to apply to exception event.\n * @returns — The generated eventId.\n */\nexport const captureException: typeof naturalCaptureException = (exception, captureContext) => {\n try {\n const eventId = naturalCaptureException(exception, captureContext);\n log('capture exception', { exception, eventId, ...captureContext });\n return eventId;\n } catch (err) {\n log.catch('Failed to capture exception', err);\n return 'unknown';\n }\n};\n\nexport const captureMessage: typeof naturalCaptureMessage = (exception, captureContext) => {\n try {\n const eventId = naturalCaptureMessage(exception, captureContext);\n log('capture message', { exception, eventId, captureContext });\n return eventId;\n } catch (err) {\n log.catch('Failed to capture message', err);\n return 'unknown';\n }\n};\n\nexport const withScope = naturalWithScope;\n", "//\n// Copyright 2023 DXOS.org\n//\n\n// NOTE: Browser only API. There is no node polyfill.\n\nimport { getCurrentHub } from '@sentry/browser';\nimport { type Transaction, type Span } from '@sentry/types';\n\nimport { runInContext, scheduleMicroTask, Trigger } from '@dxos/async';\nimport { Context } from '@dxos/context';\nimport { invariant } from '@dxos/invariant';\nimport { getContextFromEntry, log, LogLevel, type LogProcessor } from '@dxos/log';\n\nconst REPORT_SPANS = false;\n\nlet TX!: Transaction;\nconst SPAN_MAP = new Map<string, Span>();\nconst SENTRY_INITIALIZED = new Trigger();\nconst ctx = new Context({ onError: (err) => log.warn('Unhandled error in Sentry context', err) });\nctx.maxSafeDisposeCallbacks = 10_000;\n\nlet tracingConfigured = false;\n\nexport const configureTracing = () => {\n tracingConfigured = true;\n runInContext(ctx, () => {\n // Configure root transaction.\n TX = getCurrentHub().startTransaction({\n name: 'DXOS Core Tracing',\n op: 'dxos',\n });\n invariant(TX, 'Failed to create trace');\n if (typeof window !== 'undefined') {\n window.addEventListener('beforeunload', () => {\n finish();\n });\n }\n if (typeof process !== 'undefined') {\n process.on('exit', () => {\n finish();\n });\n }\n\n SENTRY_INITIALIZED.wake();\n });\n};\n\nexport const finish = () => {\n for (const span of Array.from(SPAN_MAP.values()).reverse()) {\n try {\n span.finish();\n } catch (err) {\n log.warn('Failed to finish span', err);\n }\n }\n TX.finish();\n};\n\nexport const SENTRY_PROCESSOR: LogProcessor = (config, entry) => {\n if (!tracingConfigured) {\n return;\n }\n\n const { message, level, error } = entry;\n const context = getContextFromEntry(entry);\n\n if (level !== LogLevel.TRACE) {\n return;\n }\n\n // NOTE: Make sure `entry` is not captured in this closure to avoid a memory leak.\n scheduleMicroTask(ctx, async () => {\n await SENTRY_INITIALIZED.wait();\n\n if (REPORT_SPANS && context?.span) {\n switch (context.span.command) {\n case 'begin': {\n const id = context.span.id;\n\n if (!id || SPAN_MAP.has(id)) {\n log.warn('Cannot begin span', id);\n return;\n }\n\n let parentSpan: Span = TX;\n if (context.span.parent) {\n parentSpan = SPAN_MAP.get(context.span.parent) ?? TX;\n }\n\n let logContext: string;\n try {\n logContext = JSON.stringify({ ...context, message, level, error });\n } catch (err) {\n logContext = JSON.stringify(context);\n }\n\n const span = parentSpan.startChild({\n op: message,\n data: {\n ...context.span.data,\n '@dxos/log': logContext,\n },\n });\n SPAN_MAP.set(context.span.id, span);\n break;\n }\n\n case 'end': {\n const span = SPAN_MAP.get(context.span.id);\n if (span) {\n span.setStatus(getSpanStatus(context.span.status));\n context.span.data && Object.entries(context.span.data).forEach(([key, value]) => span.setData(key, value));\n span.finish();\n SPAN_MAP.delete(context.span.id);\n } else {\n log.warn('Cannot end span', context.span.id);\n }\n break;\n }\n\n case 'update': {\n const span = SPAN_MAP.get(context.span.id);\n if (span) {\n context.span.data && Object.entries(context.span.data).forEach(([key, value]) => span.setData(key, value));\n } else {\n log.warn('Cannot update span', context.span.id);\n }\n break;\n }\n\n default: {\n log.warn('Unknown span command', context.span.command);\n }\n }\n }\n });\n};\n\nlog.runtimeConfig.processors.push(SENTRY_PROCESSOR);\n\n/**\n * @see https://develop.sentry.dev/sdk/event-payloads/span/#:~:text=this%20value%20explicitly.-,status,-Optional.%20Describes%20the\n */\nconst getSpanStatus = (status?: 'ok' | 'error') => {\n switch (status) {\n case 'ok':\n return 'ok';\n case 'error':\n return 'not_found';\n }\n return status ?? 'ok';\n};\n"],
5
+ "mappings": "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",
6
+ "names": ["init", "naturalInit", "setTag", "addBreadcrumb", "naturalAddBreadcrumb", "captureException", "naturalCaptureException", "captureMessage", "naturalCaptureMessage", "withScope", "naturalWithScope", "BrowserTracing", "replayIntegration", "breadcrumbsIntegration", "httpClientIntegration", "log", "getCurrentHub", "runInContext", "scheduleMicroTask", "Trigger", "Context", "invariant", "getContextFromEntry", "log", "LogLevel", "REPORT_SPANS", "TX", "SPAN_MAP", "Map", "SENTRY_INITIALIZED", "ctx", "onError", "err", "warn", "maxSafeDisposeCallbacks", "tracingConfigured", "configureTracing", "startTransaction", "name", "op", "window", "addEventListener", "finish", "process", "on", "wake", "span", "Array", "from", "values", "reverse", "SENTRY_PROCESSOR", "config", "entry", "message", "level", "error", "context", "TRACE", "wait", "command", "id", "has", "parentSpan", "parent", "get", "logContext", "JSON", "stringify", "startChild", "data", "set", "setStatus", "getSpanStatus", "status", "Object", "entries", "forEach", "key", "value", "setData", "delete", "runtimeConfig", "processors", "push", "setTag", "setTags", "setUser", "init", "options", "log", "naturalInit", "enabled", "enable", "dsn", "destination", "release", "environment", "integrations", "breadcrumbsIntegration", "console", "fetch", "httpClientIntegration", "failedRequestStatusCodes", "tracing", "BrowserTracing", "replay", "replayIntegration", "blockAllMedia", "maskAllText", "replaysSessionSampleRate", "replaySampleRate", "replaysOnErrorSampleRate", "replaySampleRateOnError", "tracesSampleRate", "sampleRate", "transport", "beforeSend", "event", "onError", "Object", "entries", "properties", "forEach", "key", "value", "err", "catch", "addBreadcrumb", "breadcrumb", "naturalAddBreadcrumb", "captureException", "exception", "captureContext", "eventId", "naturalCaptureException", "captureMessage", "naturalCaptureMessage", "withScope", "naturalWithScope"]
7
+ }
@@ -1,3 +1,9 @@
1
+ import {
2
+ captureException,
3
+ captureMessage,
4
+ withScope
5
+ } from "./chunk-G5DKURIM.mjs";
6
+
1
7
  // packages/sdk/observability/src/observability.ts
2
8
  import { Event, scheduleTaskInterval } from "@dxos/async";
3
9
  import { Context } from "@dxos/context";
@@ -84,7 +90,7 @@ var initializeAppObservability = async ({ namespace, config, mode = "basic", tra
84
90
  const release = `${namespace}@${config.get("runtime.app.build.version")}`;
85
91
  const environment = config.get("runtime.app.env.DX_ENVIRONMENT");
86
92
  const observabilityDisabled = await isObservabilityDisabled(namespace);
87
- const { Observability: Observability2 } = await import("./observability-MK4LFDOW.mjs");
93
+ const { Observability: Observability2 } = await import("./observability-A5P77DUJ.mjs");
88
94
  const observability = new Observability2({
89
95
  namespace,
90
96
  release,
@@ -252,8 +258,7 @@ var initializeNodeObservability = async ({ namespace, version, config, installat
252
258
  release,
253
259
  // TODO(wittjosiah): Configure this.
254
260
  sampleRate: 1
255
- },
256
- logProcessor: true
261
+ }
257
262
  }
258
263
  });
259
264
  observability.setTag("installationId", installationId);
@@ -376,10 +381,129 @@ var setupTelemetryListeners = (namespace, client, observability) => {
376
381
  };
377
382
  };
378
383
 
384
+ // packages/sdk/observability/src/sentry/sentry-log-processor.ts
385
+ import { LogLevel, shouldLog } from "@dxos/log";
386
+ import { CircularBuffer, getDebugName } from "@dxos/util";
387
+ var MAX_LOG_BREADCRUMBS = 80;
388
+ var SentryLogProcessor = class {
389
+ constructor() {
390
+ this._breadcrumbs = new CircularBuffer(MAX_LOG_BREADCRUMBS);
391
+ this.logProcessor = (config, entry) => {
392
+ const { level, meta, error } = entry;
393
+ if (!shouldLog(entry, config.captureFilters)) {
394
+ return;
395
+ }
396
+ if (entry.level !== LogLevel.WARN && entry.level !== LogLevel.ERROR) {
397
+ return;
398
+ }
399
+ withScope((scope) => {
400
+ const severity = convertLevel(level);
401
+ scope.setLevel(severity);
402
+ scope.setContext("dxoslog", entry.context ?? null);
403
+ if (meta) {
404
+ scope.setTag("transaction", `${getRelativeFilename(meta.F)}:${meta.L}`);
405
+ if (meta.S?.hostSessionId) {
406
+ scope.setTags({
407
+ service_host_issue: true,
408
+ service_host_session: meta.S?.hostSessionId
409
+ });
410
+ }
411
+ if (!Number.isNaN(meta.S?.uptimeSeconds)) {
412
+ scope.setExtra("uptime_seconds", meta.S?.uptimeSeconds);
413
+ }
414
+ }
415
+ const extendedMessage = formatMessageForSentry(entry);
416
+ let capturedError = error;
417
+ if (capturedError == null && entry.level === LogLevel.ERROR) {
418
+ capturedError = Object.values(entry.context ?? {}).find((v) => v instanceof Error);
419
+ }
420
+ if (capturedError) {
421
+ const isMessageDifferentFromStackTrace = error == null;
422
+ if (isMessageDifferentFromStackTrace) {
423
+ scope.setExtra("message", extendedMessage);
424
+ }
425
+ const eventId2 = captureException(capturedError);
426
+ this._addBreadcrumb(eventId2, extendedMessage, severity, entry.context);
427
+ return;
428
+ }
429
+ scope.setFingerprint([
430
+ entry.message
431
+ ]);
432
+ const eventId = captureMessage(extendedMessage);
433
+ this._addBreadcrumb(eventId, extendedMessage, severity, entry.context);
434
+ });
435
+ };
436
+ }
437
+ addLogBreadcrumbsTo(event) {
438
+ event.breadcrumbs ??= [];
439
+ for (const breadcrumb of this._breadcrumbs) {
440
+ event.breadcrumbs.push(breadcrumb);
441
+ }
442
+ event.breadcrumbs.sort((b1, b2) => {
443
+ if (b1.timestamp === void 0 || b2.timestamp === void 0) {
444
+ return b1.timestamp === b2.timestamp ? 0 : b1.timestamp === void 0 ? -1 : 1;
445
+ }
446
+ return b1.timestamp - b2.timestamp;
447
+ });
448
+ }
449
+ _addBreadcrumb(eventId, message, severity, context) {
450
+ const breadcrumb = {
451
+ type: "console",
452
+ level: severity,
453
+ event_id: eventId,
454
+ category: "log",
455
+ message,
456
+ data: context,
457
+ timestamp: Math.floor(Date.now() / 1e3)
458
+ };
459
+ const lastRecorded = this._breadcrumbs.getLast();
460
+ if (lastRecorded && lastRecorded.message === breadcrumb.message) {
461
+ const firstBreadcrumbData = lastRecorded.data?.firstBreadcrumbData ?? lastRecorded.data ?? {};
462
+ const mergedBreadcrumbCount = Number.isNaN(lastRecorded.data?.mergedBreadcrumbCount) ? 1 : Number(lastRecorded.data?.mergedBreadcrumbCount);
463
+ lastRecorded.data = {
464
+ mergedBreadcrumbCount: mergedBreadcrumbCount + 1,
465
+ firstBreadcrumbData,
466
+ lastBreadcrumbData: breadcrumb.data
467
+ };
468
+ return;
469
+ }
470
+ this._breadcrumbs.push(breadcrumb);
471
+ }
472
+ };
473
+ var formatMessageForSentry = (entry) => {
474
+ let scopePrefix;
475
+ if (entry.meta?.S) {
476
+ const scope = entry.meta?.S;
477
+ scopePrefix = scope.name || getDebugName(scope);
478
+ }
479
+ if (scopePrefix == null) {
480
+ return entry.message;
481
+ }
482
+ const workerPrefix = entry.meta?.S?.hostSessionId ? "[worker] " : "";
483
+ return `${workerPrefix}${scopePrefix} ${entry.message}`;
484
+ };
485
+ var convertLevel = (level) => {
486
+ if (level === LogLevel.TRACE) {
487
+ return "debug";
488
+ }
489
+ if (level === LogLevel.WARN) {
490
+ return "warning";
491
+ }
492
+ return LogLevel[level].toLowerCase();
493
+ };
494
+ var getRelativeFilename = (filename) => {
495
+ const match = filename.match(/.+\/(packages\/.+\/.+)/);
496
+ if (match) {
497
+ const [, filePath] = match;
498
+ return filePath;
499
+ }
500
+ return filename;
501
+ };
502
+
379
503
  // packages/sdk/observability/src/observability.ts
380
504
  var __dxlog_file3 = "/home/runner/work/dxos/dxos/packages/sdk/observability/src/observability.ts";
381
505
  var SPACE_METRICS_MIN_INTERVAL = 1e3 * 60;
382
- var DATADOG_IDLE_INTERVAL = 1e3 * 60 * 1;
506
+ var NETWORK_METRICS_MIN_INTERVAL = 1e3 * 60 * 5;
383
507
  var Observability = class {
384
508
  // TODO(nf): make platform a required extension?
385
509
  constructor({ namespace, environment, release, config, secrets, group, mode, telemetry, errorLog }) {
@@ -400,7 +524,6 @@ var Observability = class {
400
524
  this._secrets = this._loadSecrets(config, secrets);
401
525
  this._telemetryBatchSize = telemetry?.batchSize ?? 30;
402
526
  this._errorReportingOptions = errorLog?.sentryInitOptions;
403
- this._errorLogProcessor = errorLog?.logProcessor ?? false;
404
527
  if (this._group) {
405
528
  this.setTag("group", this._group);
406
529
  }
@@ -429,7 +552,7 @@ var Observability = class {
429
552
  config
430
553
  }, {
431
554
  F: __dxlog_file3,
432
- L: 134,
555
+ L: 132,
433
556
  S: this,
434
557
  C: (f, a) => f(...a)
435
558
  });
@@ -491,7 +614,7 @@ var Observability = class {
491
614
  idqr
492
615
  }, {
493
616
  F: __dxlog_file3,
494
- L: 206,
617
+ L: 204,
495
618
  S: this,
496
619
  C: (f, a) => f(...a)
497
620
  });
@@ -505,7 +628,7 @@ var Observability = class {
505
628
  device: dqr
506
629
  }, {
507
630
  F: __dxlog_file3,
508
- L: 215,
631
+ L: 213,
509
632
  S: this,
510
633
  C: (f, a) => f(...a)
511
634
  });
@@ -513,7 +636,7 @@ var Observability = class {
513
636
  }
514
637
  invariant(dqr, "empty response from device service", {
515
638
  F: __dxlog_file3,
516
- L: 218,
639
+ L: 216,
517
640
  S: this,
518
641
  A: [
519
642
  "dqr",
@@ -526,7 +649,7 @@ var Observability = class {
526
649
  device: dqr
527
650
  }, {
528
651
  F: __dxlog_file3,
529
- L: 222,
652
+ L: 220,
530
653
  S: this,
531
654
  C: (f, a) => f(...a)
532
655
  });
@@ -552,13 +675,13 @@ var Observability = class {
552
675
  key,
553
676
  value.value
554
677
  ])),
555
- // TODO(nf): move/refactor from telementryContext, needed to read CORS proxy
678
+ // TODO(nf): move/refactor from telemetryContext, needed to read CORS proxy
556
679
  config: this._config
557
680
  });
558
681
  } else {
559
682
  log3("datadog disabled", void 0, {
560
683
  F: __dxlog_file3,
561
- L: 253,
684
+ L: 251,
562
685
  S: this,
563
686
  C: (f, a) => f(...a)
564
687
  });
@@ -574,15 +697,15 @@ var Observability = class {
574
697
  }
575
698
  // TODO(nf): Refactor into ObservabilityExtensions.
576
699
  startNetworkMetrics(client) {
577
- const updateSignalMetrics = new Event();
578
- updateSignalMetrics.on(this._ctx, async (networkStatus) => {
700
+ const updateSignalMetrics = new Event().debounce(NETWORK_METRICS_MIN_INTERVAL);
701
+ updateSignalMetrics.on(this._ctx, async () => {
579
702
  log3("send signal metrics", void 0, {
580
703
  F: __dxlog_file3,
581
- L: 273,
704
+ L: 270,
582
705
  S: this,
583
706
  C: (f, a) => f(...a)
584
707
  });
585
- networkStatus.signaling.forEach(({ server, state }) => {
708
+ (this._lastNetworkStatus?.signaling).forEach(({ server, state }) => {
586
709
  this.gauge("dxos.client.network.signal.connectionState", state, {
587
710
  server
588
711
  });
@@ -595,7 +718,7 @@ var Observability = class {
595
718
  let totalReadBufferSize = 0;
596
719
  let totalWriteBufferSize = 0;
597
720
  let totalChannelBufferSize = 0;
598
- networkStatus.connectionInfo?.forEach((connectionInfo) => {
721
+ this._lastNetworkStatus?.connectionInfo?.forEach((connectionInfo) => {
599
722
  swarmCount++;
600
723
  for (const conn of connectionInfo.connections ?? []) {
601
724
  connectionStates.set(conn.state, (connectionStates.get(conn.state) ?? 0) + 1);
@@ -611,14 +734,16 @@ var Observability = class {
611
734
  state
612
735
  });
613
736
  }
614
- this.gauge("dxox.client.network.totalReadBufferSize", totalReadBufferSize);
737
+ this.gauge("dxos.client.network.totalReadBufferSize", totalReadBufferSize);
615
738
  this.gauge("dxos.client.network.totalWriteBufferSize", totalWriteBufferSize);
616
739
  this.gauge("dxos.client.network.totalChannelBufferSize", totalChannelBufferSize);
617
740
  });
618
741
  });
619
742
  client.services.services.NetworkService?.queryStatus().subscribe((networkStatus) => {
620
- updateSignalMetrics.emit(networkStatus);
743
+ this._lastNetworkStatus = networkStatus;
744
+ updateSignalMetrics.emit();
621
745
  });
746
+ scheduleTaskInterval(this._ctx, async () => updateSignalMetrics.emit(), NETWORK_METRICS_MIN_INTERVAL);
622
747
  }
623
748
  startSpacesMetrics(client, namespace) {
624
749
  const spaces = client.spaces.get();
@@ -628,7 +753,7 @@ var Observability = class {
628
753
  updateSpaceMetrics.on(this._ctx, async () => {
629
754
  log3("send space update", void 0, {
630
755
  F: __dxlog_file3,
631
- L: 325,
756
+ L: 324,
632
757
  S: this,
633
758
  C: (f, a) => f(...a)
634
759
  });
@@ -669,13 +794,13 @@ var Observability = class {
669
794
  });
670
795
  }
671
796
  });
672
- scheduleTaskInterval(this._ctx, async () => updateSpaceMetrics.emit(), DATADOG_IDLE_INTERVAL);
797
+ scheduleTaskInterval(this._ctx, async () => updateSpaceMetrics.emit(), NETWORK_METRICS_MIN_INTERVAL);
673
798
  }
674
- async startRuntimeMetrics(client, frequency = DATADOG_IDLE_INTERVAL) {
799
+ async startRuntimeMetrics(client, frequency = NETWORK_METRICS_MIN_INTERVAL) {
675
800
  const platform = await client.services.services.SystemService?.getPlatform();
676
801
  invariant(platform, "platform is required", {
677
802
  F: __dxlog_file3,
678
- L: 368,
803
+ L: 367,
679
804
  S: this,
680
805
  A: [
681
806
  "platform",
@@ -697,7 +822,7 @@ var Observability = class {
697
822
  scheduleTaskInterval(this._ctx, async () => {
698
823
  log3("platform", void 0, {
699
824
  F: __dxlog_file3,
700
- L: 386,
825
+ L: 385,
701
826
  S: this,
702
827
  C: (f, a) => f(...a)
703
828
  });
@@ -706,7 +831,7 @@ var Observability = class {
706
831
  platform: platform2
707
832
  }, {
708
833
  F: __dxlog_file3,
709
- L: 389,
834
+ L: 388,
710
835
  S: this,
711
836
  C: (f, a) => f(...a)
712
837
  });
@@ -719,7 +844,7 @@ var Observability = class {
719
844
  error
720
845
  }, {
721
846
  F: __dxlog_file3,
722
- L: 396,
847
+ L: 395,
723
848
  S: this,
724
849
  C: (f, a) => f(...a)
725
850
  }));
@@ -744,7 +869,7 @@ var Observability = class {
744
869
  } else {
745
870
  log3("segment disabled", void 0, {
746
871
  F: __dxlog_file3,
747
- L: 422,
872
+ L: 421,
748
873
  S: this,
749
874
  C: (f, a) => f(...a)
750
875
  });
@@ -771,29 +896,29 @@ var Observability = class {
771
896
  //
772
897
  async _initErrorLogs() {
773
898
  if (this._secrets.SENTRY_DESTINATION && this._mode !== "disabled") {
774
- const { captureException, enableSentryLogProcessor, configureTracing, init, setTag } = await import("./sentry/index.mjs");
775
- this._captureException = captureException;
899
+ const { captureException: captureException2, configureTracing, init, setTag } = await import("./sentry/index.mjs");
900
+ this._captureException = captureException2;
776
901
  this._setTag = setTag;
777
902
  log3.info("Initializing Sentry", {
778
903
  dest: this._secrets.SENTRY_DESTINATION,
779
904
  options: this._errorReportingOptions
780
905
  }, {
781
906
  F: __dxlog_file3,
782
- L: 455,
907
+ L: 454,
783
908
  S: this,
784
909
  C: (f, a) => f(...a)
785
910
  });
911
+ const logProcessor = new SentryLogProcessor();
786
912
  init({
787
913
  ...this._errorReportingOptions,
788
914
  destination: this._secrets.SENTRY_DESTINATION,
789
- scrubFilenames: this._mode !== "full"
915
+ scrubFilenames: this._mode !== "full",
916
+ onError: (event) => logProcessor.addLogBreadcrumbsTo(event)
790
917
  });
791
918
  if (this._errorReportingOptions?.tracing) {
792
919
  configureTracing();
793
920
  }
794
- if (this._errorLogProcessor) {
795
- enableSentryLogProcessor();
796
- }
921
+ log3.runtimeConfig.processors.push(logProcessor.logProcessor);
797
922
  this._tags.forEach((v, k) => {
798
923
  if (v.scope === "all" || v.scope === "errors") {
799
924
  setTag(k, v.value);
@@ -802,7 +927,7 @@ var Observability = class {
802
927
  } else {
803
928
  log3("sentry disabled", void 0, {
804
929
  F: __dxlog_file3,
805
- L: 478,
930
+ L: 480,
806
931
  S: this,
807
932
  C: (f, a) => f(...a)
808
933
  });
@@ -836,4 +961,4 @@ export {
836
961
  mapSpaces,
837
962
  setupTelemetryListeners
838
963
  };
839
- //# sourceMappingURL=chunk-XF67HMEA.mjs.map
964
+ //# sourceMappingURL=chunk-Y66LFYI5.mjs.map