diff --git a/.craft.yml b/.craft.yml index 44efac4303c8..5efdae48aa01 100644 --- a/.craft.yml +++ b/.craft.yml @@ -176,3 +176,7 @@ targets: onlyIfPresent: /^sentry-sveltekit-\d.*\.tgz$/ 'npm:@sentry/opentelemetry-node': onlyIfPresent: /^sentry-opentelemetry-node-\d.*\.tgz$/ + 'npm:@sentry/bun': + onlyIfPresent: /^sentry-bun-\d.*\.tgz$/ + 'npm:@sentry/vercel-edge': + onlyIfPresent: /^sentry-vercel-edge-\d.*\.tgz$/ diff --git a/CHANGELOG.md b/CHANGELOG.md index 819c17ef6f5a..724c0730ee83 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,6 +4,18 @@ - "You miss 100 percent of the chances you don't take. — Wayne Gretzky" — Michael Scott +## 7.71.0 + +- feat(bun): Instrument Bun.serve (#9080) +- fix(core): Ensure global event processors are always applied to event (#9064) +- fix(core): Run client eventProcessors before global ones (#9032) +- fix(nextjs): Use webpack module paths to attempt to resolve internal request async storage module (#9100) +- fix(react): Add actual error name to boundary error name (#9065) +- fix(react): Compare location against `basename`-prefixed route. (#9076) +- ref(browser): Refactor browser integrations to use `processEvent` (#9022) + +Work in this release contributed by @jorrit. Thank you for your contribution! + ## 7.70.0 ### Important Changes diff --git a/packages/browser/src/integrations/dedupe.ts b/packages/browser/src/integrations/dedupe.ts index 673ded6484cb..c7a5cb5470b3 100644 --- a/packages/browser/src/integrations/dedupe.ts +++ b/packages/browser/src/integrations/dedupe.ts @@ -1,4 +1,4 @@ -import type { Event, EventProcessor, Exception, Hub, Integration, StackFrame } from '@sentry/types'; +import type { Event, Exception, Integration, StackFrame } from '@sentry/types'; import { logger } from '@sentry/utils'; /** Deduplication filter */ @@ -22,36 +22,30 @@ export class Dedupe implements Integration { this.name = Dedupe.id; } + /** @inheritDoc */ + public setupOnce(_addGlobaleventProcessor: unknown, _getCurrentHub: unknown): void { + // noop + } + /** * @inheritDoc */ - public setupOnce(addGlobalEventProcessor: (callback: EventProcessor) => void, getCurrentHub: () => Hub): void { - const eventProcessor: EventProcessor = currentEvent => { - // We want to ignore any non-error type events, e.g. transactions or replays - // These should never be deduped, and also not be compared against as _previousEvent. - if (currentEvent.type) { - return currentEvent; - } + public processEvent(currentEvent: Event): Event | null { + // We want to ignore any non-error type events, e.g. transactions or replays + // These should never be deduped, and also not be compared against as _previousEvent. + if (currentEvent.type) { + return currentEvent; + } - const self = getCurrentHub().getIntegration(Dedupe); - if (self) { - // Juuust in case something goes wrong - try { - if (_shouldDropEvent(currentEvent, self._previousEvent)) { - __DEBUG_BUILD__ && logger.warn('Event dropped due to being a duplicate of previously captured event.'); - return null; - } - } catch (_oO) { - return (self._previousEvent = currentEvent); - } - - return (self._previousEvent = currentEvent); + // Juuust in case something goes wrong + try { + if (_shouldDropEvent(currentEvent, this._previousEvent)) { + __DEBUG_BUILD__ && logger.warn('Event dropped due to being a duplicate of previously captured event.'); + return null; } - return currentEvent; - }; + } catch (_oO) {} // eslint-disable-line no-empty - eventProcessor.id = this.name; - addGlobalEventProcessor(eventProcessor); + return (this._previousEvent = currentEvent); } } diff --git a/packages/browser/src/integrations/httpcontext.ts b/packages/browser/src/integrations/httpcontext.ts index f37963b46619..34e7029e504d 100644 --- a/packages/browser/src/integrations/httpcontext.ts +++ b/packages/browser/src/integrations/httpcontext.ts @@ -1,4 +1,3 @@ -import { addGlobalEventProcessor, getCurrentHub } from '@sentry/core'; import type { Event, Integration } from '@sentry/types'; import { WINDOW } from '../helpers'; @@ -23,28 +22,28 @@ export class HttpContext implements Integration { * @inheritDoc */ public setupOnce(): void { - addGlobalEventProcessor((event: Event) => { - if (getCurrentHub().getIntegration(HttpContext)) { - // if none of the information we want exists, don't bother - if (!WINDOW.navigator && !WINDOW.location && !WINDOW.document) { - return event; - } - - // grab as much info as exists and add it to the event - const url = (event.request && event.request.url) || (WINDOW.location && WINDOW.location.href); - const { referrer } = WINDOW.document || {}; - const { userAgent } = WINDOW.navigator || {}; - - const headers = { - ...(event.request && event.request.headers), - ...(referrer && { Referer: referrer }), - ...(userAgent && { 'User-Agent': userAgent }), - }; - const request = { ...event.request, ...(url && { url }), headers }; - - return { ...event, request }; - } - return event; - }); + // noop + } + + /** @inheritDoc */ + public preprocessEvent(event: Event): void { + // if none of the information we want exists, don't bother + if (!WINDOW.navigator && !WINDOW.location && !WINDOW.document) { + return; + } + + // grab as much info as exists and add it to the event + const url = (event.request && event.request.url) || (WINDOW.location && WINDOW.location.href); + const { referrer } = WINDOW.document || {}; + const { userAgent } = WINDOW.navigator || {}; + + const headers = { + ...(event.request && event.request.headers), + ...(referrer && { Referer: referrer }), + ...(userAgent && { 'User-Agent': userAgent }), + }; + const request = { ...event.request, ...(url && { url }), headers }; + + event.request = request; } } diff --git a/packages/browser/src/profiling/integration.ts b/packages/browser/src/profiling/integration.ts index 0d506b7493cd..dc7cb4d15120 100644 --- a/packages/browser/src/profiling/integration.ts +++ b/packages/browser/src/profiling/integration.ts @@ -35,7 +35,7 @@ export class BrowserProfilingIntegration implements Integration { /** * @inheritDoc */ - public setupOnce(addGlobalEventProcessor: (callback: EventProcessor) => void, getCurrentHub: () => Hub): void { + public setupOnce(_addGlobalEventProcessor: (callback: EventProcessor) => void, getCurrentHub: () => Hub): void { this.getCurrentHub = getCurrentHub; const client = this.getCurrentHub().getClient() as BrowserClient; diff --git a/packages/bun/README.md b/packages/bun/README.md index 170059f193f5..56c795793532 100644 --- a/packages/bun/README.md +++ b/packages/bun/README.md @@ -23,9 +23,9 @@ To use this SDK, call `init(options)` as early as possible in the main entry mod hook into the environment. Note that you can turn off almost all side effects using the respective options. ```javascript -// ES5 Syntax +// CJS Syntax const Sentry = require('@sentry/bun'); -// ES6 Syntax +// ESM Syntax import * as Sentry from '@sentry/bun'; Sentry.init({ diff --git a/packages/bun/src/index.ts b/packages/bun/src/index.ts index 7be879568dec..d1c4a69f0ae5 100644 --- a/packages/bun/src/index.ts +++ b/packages/bun/src/index.ts @@ -69,9 +69,12 @@ export { defaultIntegrations, init } from './sdk'; import { Integrations as CoreIntegrations } from '@sentry/core'; import { Integrations as NodeIntegrations } from '@sentry/node'; +import * as BunIntegrations from './integrations'; + const INTEGRATIONS = { ...CoreIntegrations, ...NodeIntegrations, + ...BunIntegrations, }; export { INTEGRATIONS as Integrations }; diff --git a/packages/bun/src/integrations/bunserver.ts b/packages/bun/src/integrations/bunserver.ts new file mode 100644 index 000000000000..915856f473db --- /dev/null +++ b/packages/bun/src/integrations/bunserver.ts @@ -0,0 +1,132 @@ +import { captureException, getCurrentHub, runWithAsyncContext, startSpan, Transaction } from '@sentry/core'; +import type { Integration } from '@sentry/types'; +import { addExceptionMechanism, getSanitizedUrlString, parseUrl, tracingContextFromHeaders } from '@sentry/utils'; + +function sendErrorToSentry(e: unknown): unknown { + captureException(e, scope => { + scope.addEventProcessor(event => { + addExceptionMechanism(event, { + type: 'bun', + handled: false, + data: { + function: 'serve', + }, + }); + return event; + }); + + return scope; + }); + + return e; +} + +/** + * Instruments `Bun.serve` to automatically create transactions and capture errors. + */ +export class BunServer implements Integration { + /** + * @inheritDoc + */ + public static id: string = 'BunServer'; + + /** + * @inheritDoc + */ + public name: string = BunServer.id; + + /** + * @inheritDoc + */ + public setupOnce(): void { + instrumentBunServe(); + } +} + +/** + * Instruments Bun.serve by patching it's options. + */ +export function instrumentBunServe(): void { + Bun.serve = new Proxy(Bun.serve, { + apply(serveTarget, serveThisArg, serveArgs: Parameters) { + instrumentBunServeOptions(serveArgs[0]); + return serveTarget.apply(serveThisArg, serveArgs); + }, + }); +} + +/** + * Instruments Bun.serve `fetch` option to automatically create spans and capture errors. + */ +function instrumentBunServeOptions(serveOptions: Parameters[0]): void { + serveOptions.fetch = new Proxy(serveOptions.fetch, { + apply(fetchTarget, fetchThisArg, fetchArgs: Parameters) { + return runWithAsyncContext(() => { + const hub = getCurrentHub(); + + const request = fetchArgs[0]; + const upperCaseMethod = request.method.toUpperCase(); + if (upperCaseMethod === 'OPTIONS' || upperCaseMethod === 'HEAD') { + return fetchTarget.apply(fetchThisArg, fetchArgs); + } + + const sentryTrace = request.headers.get('sentry-trace') || ''; + const baggage = request.headers.get('baggage'); + const { traceparentData, dynamicSamplingContext, propagationContext } = tracingContextFromHeaders( + sentryTrace, + baggage, + ); + hub.getScope().setPropagationContext(propagationContext); + + const parsedUrl = parseUrl(request.url); + const data: Record = { + 'http.request.method': request.method || 'GET', + }; + if (parsedUrl.search) { + data['http.query'] = parsedUrl.search; + } + + const url = getSanitizedUrlString(parsedUrl); + return startSpan( + { + op: 'http.server', + name: `${request.method} ${parsedUrl.path || '/'}`, + origin: 'auto.http.bun.serve', + ...traceparentData, + data, + metadata: { + source: 'url', + dynamicSamplingContext: traceparentData && !dynamicSamplingContext ? {} : dynamicSamplingContext, + request: { + url, + method: request.method, + headers: request.headers.toJSON(), + }, + }, + }, + async span => { + try { + const response = await (fetchTarget.apply(fetchThisArg, fetchArgs) as ReturnType< + typeof serveOptions.fetch + >); + if (response && response.status) { + span?.setHttpStatus(response.status); + span?.setData('http.response.status_code', response.status); + if (span instanceof Transaction) { + span.setContext('response', { + headers: response.headers.toJSON(), + status_code: response.status, + }); + } + } + return response; + } catch (e) { + sendErrorToSentry(e); + throw e; + } + }, + ); + }); + }, + }); +} diff --git a/packages/bun/src/integrations/index.ts b/packages/bun/src/integrations/index.ts new file mode 100644 index 000000000000..95d17cf80e66 --- /dev/null +++ b/packages/bun/src/integrations/index.ts @@ -0,0 +1 @@ +export { BunServer } from './bunserver'; diff --git a/packages/bun/src/sdk.ts b/packages/bun/src/sdk.ts index 11c7827b3faf..d512e7208bf5 100644 --- a/packages/bun/src/sdk.ts +++ b/packages/bun/src/sdk.ts @@ -3,6 +3,7 @@ import { Integrations as CoreIntegrations } from '@sentry/core'; import { init as initNode, Integrations as NodeIntegrations } from '@sentry/node'; import { BunClient } from './client'; +import { BunServer } from './integrations'; import { makeFetchTransport } from './transports'; import type { BunOptions } from './types'; @@ -25,6 +26,8 @@ export const defaultIntegrations = [ new NodeIntegrations.RequestData(), // Misc new NodeIntegrations.LinkedErrors(), + // Bun Specific + new BunServer(), ]; /** diff --git a/packages/bun/test/helpers.ts b/packages/bun/test/helpers.ts new file mode 100644 index 000000000000..32d4e4d716ac --- /dev/null +++ b/packages/bun/test/helpers.ts @@ -0,0 +1,14 @@ +import { createTransport } from '@sentry/core'; +import { resolvedSyncPromise } from '@sentry/utils'; + +import type { BunClientOptions } from '../src/types'; + +export function getDefaultBunClientOptions(options: Partial = {}): BunClientOptions { + return { + integrations: [], + transport: () => createTransport({ recordDroppedEvent: () => undefined }, _ => resolvedSyncPromise({})), + stackParser: () => [], + instrumenter: 'sentry', + ...options, + }; +} diff --git a/packages/bun/test/integrations/bunserver.test.ts b/packages/bun/test/integrations/bunserver.test.ts new file mode 100644 index 000000000000..23253c729590 --- /dev/null +++ b/packages/bun/test/integrations/bunserver.test.ts @@ -0,0 +1,126 @@ +import { Hub, makeMain } from '@sentry/core'; +// eslint-disable-next-line import/no-unresolved +import { beforeAll, beforeEach, describe, expect, test } from 'bun:test'; + +import { BunClient } from '../../src/client'; +import { instrumentBunServe } from '../../src/integrations/bunserver'; +import { getDefaultBunClientOptions } from '../helpers'; + +// Fun fact: Bun = 2 21 14 :) +const DEFAULT_PORT = 22114; + +describe('Bun Serve Integration', () => { + let hub: Hub; + let client: BunClient; + + beforeAll(() => { + instrumentBunServe(); + }); + + beforeEach(() => { + const options = getDefaultBunClientOptions({ tracesSampleRate: 1, debug: true }); + client = new BunClient(options); + hub = new Hub(client); + makeMain(hub); + }); + + test('generates a transaction around a request', async () => { + client.on('finishTransaction', transaction => { + expect(transaction.status).toBe('ok'); + expect(transaction.tags).toEqual({ + 'http.status_code': '200', + }); + expect(transaction.op).toEqual('http.server'); + expect(transaction.name).toEqual('GET /'); + }); + + const server = Bun.serve({ + async fetch(_req) { + return new Response('Bun!'); + }, + port: DEFAULT_PORT, + }); + + await fetch('http://localhost:22114/'); + + server.stop(); + }); + + test('generates a post transaction', async () => { + client.on('finishTransaction', transaction => { + expect(transaction.status).toBe('ok'); + expect(transaction.tags).toEqual({ + 'http.status_code': '200', + }); + expect(transaction.op).toEqual('http.server'); + expect(transaction.name).toEqual('POST /'); + }); + + const server = Bun.serve({ + async fetch(_req) { + return new Response('Bun!'); + }, + port: DEFAULT_PORT, + }); + + await fetch('http://localhost:22114/', { + method: 'POST', + }); + + server.stop(); + }); + + test('continues a trace', async () => { + const TRACE_ID = '12312012123120121231201212312012'; + const PARENT_SPAN_ID = '1121201211212012'; + const PARENT_SAMPLED = '1'; + + const SENTRY_TRACE_HEADER = `${TRACE_ID}-${PARENT_SPAN_ID}-${PARENT_SAMPLED}`; + const SENTRY_BAGGAGE_HEADER = 'sentry-version=1.0,sentry-environment=production'; + + client.on('finishTransaction', transaction => { + expect(transaction.traceId).toBe(TRACE_ID); + expect(transaction.parentSpanId).toBe(PARENT_SPAN_ID); + expect(transaction.sampled).toBe(true); + + expect(transaction.metadata?.dynamicSamplingContext).toStrictEqual({ version: '1.0', environment: 'production' }); + }); + + const server = Bun.serve({ + async fetch(_req) { + return new Response('Bun!'); + }, + port: DEFAULT_PORT, + }); + + await fetch('http://localhost:22114/', { + headers: { 'sentry-trace': SENTRY_TRACE_HEADER, baggage: SENTRY_BAGGAGE_HEADER }, + }); + + server.stop(); + }); + + test('does not create transactions for OPTIONS or HEAD requests', async () => { + client.on('finishTransaction', () => { + // This will never run, but we want to make sure it doesn't run. + expect(false).toEqual(true); + }); + + const server = Bun.serve({ + async fetch(_req) { + return new Response('Bun!'); + }, + port: DEFAULT_PORT, + }); + + await fetch('http://localhost:22114/', { + method: 'OPTIONS', + }); + + await fetch('http://localhost:22114/', { + method: 'HEAD', + }); + + server.stop(); + }); +}); diff --git a/packages/bun/tsconfig.test.json b/packages/bun/tsconfig.test.json index 87f6afa06b86..e5d8bb0fb535 100644 --- a/packages/bun/tsconfig.test.json +++ b/packages/bun/tsconfig.test.json @@ -5,7 +5,7 @@ "compilerOptions": { // should include all types from `./tsconfig.json` plus types for all test frameworks used - "types": ["node", "jest"] + "types": ["bun-types", "jest"] // other package-specific, test-specific options } diff --git a/packages/core/src/scope.ts b/packages/core/src/scope.ts index ba4ccac23adb..48e1701ab3cb 100644 --- a/packages/core/src/scope.ts +++ b/packages/core/src/scope.ts @@ -467,7 +467,11 @@ export class Scope implements ScopeInterface { * @param hint Object containing additional information about the original exception, for use by the event processors. * @hidden */ - public applyToEvent(event: Event, hint: EventHint = {}): PromiseLike { + public applyToEvent( + event: Event, + hint: EventHint = {}, + additionalEventProcessors?: EventProcessor[], + ): PromiseLike { if (this._extra && Object.keys(this._extra).length) { event.extra = { ...this._extra, ...event.extra }; } @@ -517,7 +521,12 @@ export class Scope implements ScopeInterface { propagationContext: this._propagationContext, }; - return notifyEventProcessors([...getGlobalEventProcessors(), ...this._eventProcessors], event, hint); + // TODO (v8): Update this order to be: Global > Client > Scope + return notifyEventProcessors( + [...(additionalEventProcessors || []), ...getGlobalEventProcessors(), ...this._eventProcessors], + event, + hint, + ); } /** diff --git a/packages/core/src/utils/prepareEvent.ts b/packages/core/src/utils/prepareEvent.ts index 13a164dbaf76..6e473a9b1cb1 100644 --- a/packages/core/src/utils/prepareEvent.ts +++ b/packages/core/src/utils/prepareEvent.ts @@ -2,7 +2,7 @@ import type { Client, ClientOptions, Event, EventHint, StackFrame, StackParser } import { dateTimestampInSeconds, GLOBAL_OBJ, normalize, resolvedSyncPromise, truncate, uuid4 } from '@sentry/utils'; import { DEFAULT_ENVIRONMENT } from '../constants'; -import { notifyEventProcessors } from '../eventProcessors'; +import { getGlobalEventProcessors, notifyEventProcessors } from '../eventProcessors'; import { Scope } from '../scope'; /** @@ -55,6 +55,8 @@ export function prepareEvent( // We prepare the result here with a resolved Event. let result = resolvedSyncPromise(prepared); + const clientEventProcessors = client && client.getEventProcessors ? client.getEventProcessors() : []; + // This should be the last thing called, since we want that // {@link Hub.addEventProcessor} gets the finished prepared event. // @@ -73,28 +75,27 @@ export function prepareEvent( } // In case we have a hub we reassign it. - result = finalScope.applyToEvent(prepared, hint); + result = finalScope.applyToEvent(prepared, hint, clientEventProcessors); + } else { + // Apply client & global event processors even if there is no scope + // TODO (v8): Update the order to be Global > Client + result = notifyEventProcessors([...clientEventProcessors, ...getGlobalEventProcessors()], prepared, hint); } - return result - .then(evt => { - // Process client-scoped event processors - return client && client.getEventProcessors ? notifyEventProcessors(client.getEventProcessors(), evt, hint) : evt; - }) - .then(evt => { - if (evt) { - // We apply the debug_meta field only after all event processors have ran, so that if any event processors modified - // file names (e.g.the RewriteFrames integration) the filename -> debug ID relationship isn't destroyed. - // This should not cause any PII issues, since we're only moving data that is already on the event and not adding - // any new data - applyDebugMeta(evt); - } + return result.then(evt => { + if (evt) { + // We apply the debug_meta field only after all event processors have ran, so that if any event processors modified + // file names (e.g.the RewriteFrames integration) the filename -> debug ID relationship isn't destroyed. + // This should not cause any PII issues, since we're only moving data that is already on the event and not adding + // any new data + applyDebugMeta(evt); + } - if (typeof normalizeDepth === 'number' && normalizeDepth > 0) { - return normalizeEvent(evt, normalizeDepth, normalizeMaxBreadth); - } - return evt; - }); + if (typeof normalizeDepth === 'number' && normalizeDepth > 0) { + return normalizeEvent(evt, normalizeDepth, normalizeMaxBreadth); + } + return evt; + }); } /** diff --git a/packages/nextjs/src/config/loaders/wrappingLoader.ts b/packages/nextjs/src/config/loaders/wrappingLoader.ts index ebeb6c90294b..7fc882794e5c 100644 --- a/packages/nextjs/src/config/loaders/wrappingLoader.ts +++ b/packages/nextjs/src/config/loaders/wrappingLoader.ts @@ -15,9 +15,6 @@ const SENTRY_WRAPPER_MODULE_NAME = 'sentry-wrapper-module'; // Needs to end in .cjs in order for the `commonjs` plugin to pick it up const WRAPPING_TARGET_MODULE_NAME = '__SENTRY_WRAPPING_TARGET_FILE__.cjs'; -// This module is non-public API and may break -const nextjsRequestAsyncStorageModulePath = getRequestAsyncLocalStorageModule(); - const apiWrapperTemplatePath = path.resolve(__dirname, '..', 'templates', 'apiWrapperTemplate.js'); const apiWrapperTemplateCode = fs.readFileSync(apiWrapperTemplatePath, { encoding: 'utf8' }); @@ -51,32 +48,9 @@ type LoaderOptions = { wrappingTargetKind: 'page' | 'api-route' | 'middleware' | 'server-component' | 'sentry-init' | 'route-handler'; sentryConfigFilePath?: string; vercelCronsConfig?: VercelCronsConfig; + nextjsRequestAsyncStorageModulePath?: string; }; -function getRequestAsyncLocalStorageModule(): string | undefined { - try { - // Original location of that module - // https://github.com/vercel/next.js/blob/46151dd68b417e7850146d00354f89930d10b43b/packages/next/src/client/components/request-async-storage.ts - const location = 'next/dist/client/components/request-async-storage'; - require.resolve(location); - return location; - } catch { - // noop - } - - try { - // Introduced in Next.js 13.4.20 - // https://github.com/vercel/next.js/blob/e1bc270830f2fc2df3542d4ef4c61b916c802df3/packages/next/src/client/components/request-async-storage.external.ts - const location = 'next/dist/client/components/request-async-storage.external'; - require.resolve(location); - return location; - } catch { - // noop - } - - return undefined; -} - /** * Replace the loaded file with a wrapped version the original file. In the wrapped version, the original file is loaded, * any data-fetching functions (`getInitialProps`, `getStaticProps`, and `getServerSideProps`) or API routes it contains @@ -98,6 +72,7 @@ export default function wrappingLoader( wrappingTargetKind, sentryConfigFilePath, vercelCronsConfig, + nextjsRequestAsyncStorageModulePath, } = 'getOptions' in this ? this.getOptions() : this.query; this.async(); diff --git a/packages/nextjs/src/config/types.ts b/packages/nextjs/src/config/types.ts index cd82a3290c1e..7b439a3c5d44 100644 --- a/packages/nextjs/src/config/types.ts +++ b/packages/nextjs/src/config/types.ts @@ -163,6 +163,7 @@ export type WebpackConfigObject = { target: string; context: string; resolve?: { + modules?: string[]; alias?: { [key: string]: string | boolean }; }; module?: { diff --git a/packages/nextjs/src/config/webpack.ts b/packages/nextjs/src/config/webpack.ts index 5ca49b798aca..dc8a77a4494c 100644 --- a/packages/nextjs/src/config/webpack.ts +++ b/packages/nextjs/src/config/webpack.ts @@ -126,6 +126,7 @@ export function constructWebpackConfigFunction( pageExtensionRegex, excludeServerRoutes: userSentryOptions.excludeServerRoutes, sentryConfigFilePath: getUserConfigFilePath(projectDir, runtime), + nextjsRequestAsyncStorageModulePath: getRequestAsyncLocalStorageModuleLocation(rawNewConfig.resolve?.modules), }; const normalizeLoaderResourcePath = (resourcePath: string): string => { @@ -975,3 +976,31 @@ function addValueInjectionLoader( }, ); } + +function getRequestAsyncLocalStorageModuleLocation(modules: string[] | undefined): string | undefined { + if (modules === undefined) { + return undefined; + } + + try { + // Original location of that module + // https://github.com/vercel/next.js/blob/46151dd68b417e7850146d00354f89930d10b43b/packages/next/src/client/components/request-async-storage.ts + const location = 'next/dist/client/components/request-async-storage'; + require.resolve(location, { paths: modules }); + return location; + } catch { + // noop + } + + try { + // Introduced in Next.js 13.4.20 + // https://github.com/vercel/next.js/blob/e1bc270830f2fc2df3542d4ef4c61b916c802df3/packages/next/src/client/components/request-async-storage.external.ts + const location = 'next/dist/client/components/request-async-storage.external'; + require.resolve(location, { paths: modules }); + return location; + } catch { + // noop + } + + return undefined; +} diff --git a/packages/node-experimental/README.md b/packages/node-experimental/README.md index 461a04f28bfb..5bebaa336e17 100644 --- a/packages/node-experimental/README.md +++ b/packages/node-experimental/README.md @@ -30,9 +30,9 @@ yarn add @sentry/node-experimental ## Usage ```js -// ES5 Syntax +// CJS Syntax const Sentry = require('@sentry/node-experimental'); -// ES6 Syntax +// ESM Syntax import * as Sentry from '@sentry/node-experimental'; Sentry.init({ diff --git a/packages/node-experimental/package.json b/packages/node-experimental/package.json index 83ec589d8e4d..be0370637f3d 100644 --- a/packages/node-experimental/package.json +++ b/packages/node-experimental/package.json @@ -23,22 +23,22 @@ "access": "public" }, "dependencies": { - "@opentelemetry/api": "~1.4.1", - "@opentelemetry/context-async-hooks": "~1.15.0", - "@opentelemetry/instrumentation": "~0.41.0", - "@opentelemetry/instrumentation-express": "~0.33.0", - "@opentelemetry/instrumentation-fastify": "~0.32.0", - "@opentelemetry/instrumentation-graphql": "~0.35.0", - "@opentelemetry/instrumentation-http": "~0.41.0", - "@opentelemetry/instrumentation-mongodb": "~0.36.0", - "@opentelemetry/instrumentation-mongoose": "~0.33.0", - "@opentelemetry/instrumentation-mysql": "~0.34.0", - "@opentelemetry/instrumentation-mysql2": "~0.34.0", - "@opentelemetry/instrumentation-nestjs-core": "~0.33.0", - "@opentelemetry/instrumentation-pg": "~0.36.0", - "@opentelemetry/sdk-trace-node": "~1.15.0", - "@opentelemetry/semantic-conventions": "~1.15.0", - "@prisma/instrumentation": "~5.0.0", + "@opentelemetry/api": "~1.6.0", + "@opentelemetry/context-async-hooks": "~1.17.0", + "@opentelemetry/instrumentation": "~0.43.0", + "@opentelemetry/instrumentation-express": "~0.33.1", + "@opentelemetry/instrumentation-fastify": "~0.32.2", + "@opentelemetry/instrumentation-graphql": "~0.35.1", + "@opentelemetry/instrumentation-http": "~0.43.0", + "@opentelemetry/instrumentation-mongodb": "~0.37.0", + "@opentelemetry/instrumentation-mongoose": "~0.33.1", + "@opentelemetry/instrumentation-mysql": "~0.34.1", + "@opentelemetry/instrumentation-mysql2": "~0.34.1", + "@opentelemetry/instrumentation-nestjs-core": "~0.33.1", + "@opentelemetry/instrumentation-pg": "~0.36.1", + "@opentelemetry/sdk-trace-base": "~1.17.0", + "@opentelemetry/semantic-conventions": "~1.17.0", + "@prisma/instrumentation": "~5.3.1", "@sentry/core": "7.70.0", "@sentry/node": "7.70.0", "@sentry/opentelemetry-node": "7.70.0", diff --git a/packages/node-experimental/src/constants.ts b/packages/node-experimental/src/constants.ts new file mode 100644 index 000000000000..dc714590556a --- /dev/null +++ b/packages/node-experimental/src/constants.ts @@ -0,0 +1,3 @@ +import { createContextKey } from '@opentelemetry/api'; + +export const OTEL_CONTEXT_HUB_KEY = createContextKey('sentry_hub'); diff --git a/packages/node-experimental/src/integrations/http.ts b/packages/node-experimental/src/integrations/http.ts index 2b1fc465049b..d2a3e35397be 100644 --- a/packages/node-experimental/src/integrations/http.ts +++ b/packages/node-experimental/src/integrations/http.ts @@ -2,7 +2,6 @@ import type { Attributes } from '@opentelemetry/api'; import { SpanKind } from '@opentelemetry/api'; import { registerInstrumentations } from '@opentelemetry/instrumentation'; import { HttpInstrumentation } from '@opentelemetry/instrumentation-http'; -import type { Span as OtelSpan } from '@opentelemetry/sdk-trace-node'; import { SemanticAttributes } from '@opentelemetry/semantic-conventions'; import { hasTracingEnabled, Transaction } from '@sentry/core'; import { getCurrentHub } from '@sentry/node'; @@ -10,7 +9,7 @@ import { _INTERNAL_getSentrySpan } from '@sentry/opentelemetry-node'; import type { EventProcessor, Hub, Integration } from '@sentry/types'; import type { ClientRequest, IncomingMessage, ServerResponse } from 'http'; -import type { NodeExperimentalClient } from '../types'; +import type { NodeExperimentalClient, OtelSpan } from '../types'; import { getRequestSpanData } from '../utils/getRequestSpanData'; interface TracingOptions { diff --git a/packages/node-experimental/src/sdk/otelContextManager.ts b/packages/node-experimental/src/opentelemetry/contextManager.ts similarity index 91% rename from packages/node-experimental/src/sdk/otelContextManager.ts rename to packages/node-experimental/src/opentelemetry/contextManager.ts index c8eadfb85f65..438a2c49fac7 100644 --- a/packages/node-experimental/src/sdk/otelContextManager.ts +++ b/packages/node-experimental/src/opentelemetry/contextManager.ts @@ -1,11 +1,9 @@ import type { Context } from '@opentelemetry/api'; -import * as api from '@opentelemetry/api'; import { AsyncLocalStorageContextManager } from '@opentelemetry/context-async-hooks'; import type { Carrier, Hub } from '@sentry/core'; -import { ensureHubOnCarrier, getCurrentHub, getHubFromCarrier } from './hub'; - -export const OTEL_CONTEXT_HUB_KEY = api.createContextKey('sentry_hub'); +import { OTEL_CONTEXT_HUB_KEY } from '../constants'; +import { ensureHubOnCarrier, getCurrentHub, getHubFromCarrier } from './../sdk/hub'; function createNewHub(parent: Hub | undefined): Hub { const carrier: Carrier = {}; diff --git a/packages/node-experimental/src/sdk/initOtel.ts b/packages/node-experimental/src/sdk/initOtel.ts index 44ae76329dd2..b58eec81880e 100644 --- a/packages/node-experimental/src/sdk/initOtel.ts +++ b/packages/node-experimental/src/sdk/initOtel.ts @@ -1,11 +1,11 @@ import { diag, DiagLogLevel } from '@opentelemetry/api'; -import { AlwaysOnSampler, NodeTracerProvider } from '@opentelemetry/sdk-trace-node'; +import { AlwaysOnSampler, BasicTracerProvider } from '@opentelemetry/sdk-trace-base'; import { getCurrentHub } from '@sentry/core'; import { SentryPropagator, SentrySpanProcessor } from '@sentry/opentelemetry-node'; import { logger } from '@sentry/utils'; import type { NodeExperimentalClient } from '../types'; -import { SentryContextManager } from './otelContextManager'; +import { SentryContextManager } from './../opentelemetry/contextManager'; /** * Initialize OpenTelemetry for Node. @@ -26,14 +26,13 @@ export function initOtel(): () => void { } // Create and configure NodeTracerProvider - const provider = new NodeTracerProvider({ + const provider = new BasicTracerProvider({ sampler: new AlwaysOnSampler(), }); provider.addSpanProcessor(new SentrySpanProcessor()); // We use a custom context manager to keep context in sync with sentry scope const contextManager = new SentryContextManager(); - contextManager.enable(); // Initialize the provider provider.register({ diff --git a/packages/node-experimental/src/sdk/otelAsyncContextStrategy.ts b/packages/node-experimental/src/sdk/otelAsyncContextStrategy.ts index 455dc4717422..7e4ca5cd4da0 100644 --- a/packages/node-experimental/src/sdk/otelAsyncContextStrategy.ts +++ b/packages/node-experimental/src/sdk/otelAsyncContextStrategy.ts @@ -2,7 +2,7 @@ import * as api from '@opentelemetry/api'; import type { Hub, RunWithAsyncContextOptions } from '@sentry/core'; import { setAsyncContextStrategy } from '@sentry/core'; -import { OTEL_CONTEXT_HUB_KEY } from './otelContextManager'; +import { OTEL_CONTEXT_HUB_KEY } from '../constants'; /** * Sets the async context strategy to use follow the OTEL context under the hood. diff --git a/packages/node-experimental/src/types.ts b/packages/node-experimental/src/types.ts index 65e3d905be72..0fd9a6922a78 100644 --- a/packages/node-experimental/src/types.ts +++ b/packages/node-experimental/src/types.ts @@ -1,4 +1,5 @@ import type { Tracer } from '@opentelemetry/api'; +import type { Span as OtelSpan } from '@opentelemetry/sdk-trace-base'; import type { NodeClient, NodeOptions } from '@sentry/node'; import type { Breadcrumb, Transaction } from '@sentry/types'; @@ -24,3 +25,5 @@ export interface TransactionWithBreadcrumbs extends Transaction { /** Add a breadcrumb to this transaction. */ addBreadcrumb(breadcrumb: Breadcrumb, maxBreadcrumbs?: number): void; } + +export type { OtelSpan }; diff --git a/packages/node-experimental/src/utils/addOriginToSpan.ts b/packages/node-experimental/src/utils/addOriginToSpan.ts index c327043f0816..4320d31d7fce 100644 --- a/packages/node-experimental/src/utils/addOriginToSpan.ts +++ b/packages/node-experimental/src/utils/addOriginToSpan.ts @@ -1,3 +1,4 @@ +// We are using the broader OtelSpan type from api here, as this is also what integrations etc. use import type { Span as OtelSpan } from '@opentelemetry/api'; import { _INTERNAL_getSentrySpan } from '@sentry/opentelemetry-node'; import type { SpanOrigin } from '@sentry/types'; diff --git a/packages/node-experimental/src/utils/getRequestSpanData.ts b/packages/node-experimental/src/utils/getRequestSpanData.ts index d238077bd9df..ca89f5a2b976 100644 --- a/packages/node-experimental/src/utils/getRequestSpanData.ts +++ b/packages/node-experimental/src/utils/getRequestSpanData.ts @@ -1,8 +1,9 @@ -import type { Span as OtelSpan } from '@opentelemetry/sdk-trace-base'; import { SemanticAttributes } from '@opentelemetry/semantic-conventions'; import type { SanitizedRequestData } from '@sentry/types'; import { getSanitizedUrlString, parseUrl } from '@sentry/utils'; +import type { OtelSpan } from '../types'; + /** * Get sanitizied request data from an OTEL span. */ diff --git a/packages/node/README.md b/packages/node/README.md index e6ef857edc8a..cab92a553d25 100644 --- a/packages/node/README.md +++ b/packages/node/README.md @@ -21,9 +21,9 @@ To use this SDK, call `init(options)` as early as possible in the main entry mod hook into the environment. Note that you can turn off almost all side effects using the respective options. ```javascript -// ES5 Syntax +// CJS syntax const Sentry = require('@sentry/node'); -// ES6 Syntax +// ESM syntax import * as Sentry from '@sentry/node'; Sentry.init({ diff --git a/packages/node/test/manual/release-health/runner.js b/packages/node/test/manual/release-health/runner.js index c8ecab182859..713ae5d10c3f 100644 --- a/packages/node/test/manual/release-health/runner.js +++ b/packages/node/test/manual/release-health/runner.js @@ -15,7 +15,7 @@ for (const dir of scenariosDirs) { const processes = scenarios.map(([filename, filepath]) => { return new Promise(resolve => { - const scenarioProcess = spawn('node', [filepath]); + const scenarioProcess = spawn('node', [filepath], { timeout: 10000 }); const output = []; const errors = []; diff --git a/packages/node/test/manual/release-health/session-aggregates/aggregates-disable-single-session.js b/packages/node/test/manual/release-health/session-aggregates/aggregates-disable-single-session.js index dc6aa4485dcb..a9a16809ad41 100644 --- a/packages/node/test/manual/release-health/session-aggregates/aggregates-disable-single-session.js +++ b/packages/node/test/manual/release-health/session-aggregates/aggregates-disable-single-session.js @@ -12,6 +12,9 @@ function cleanUpAndExitSuccessfully() { } function assertSessionAggregates(session, expected) { + if (!session.aggregates) { + return; + } // For loop is added here just in the rare occasion that the session count do not land in the same aggregate // bucket session.aggregates.forEach(function (_, idx) { diff --git a/packages/opentelemetry-node/package.json b/packages/opentelemetry-node/package.json index 516c8db5856b..9c1e54430fb5 100644 --- a/packages/opentelemetry-node/package.json +++ b/packages/opentelemetry-node/package.json @@ -34,11 +34,11 @@ "@opentelemetry/semantic-conventions": "1.x" }, "devDependencies": { - "@opentelemetry/api": "^1.4.1", + "@opentelemetry/api": "^1.6.0", "@opentelemetry/core": "^1.7.0", - "@opentelemetry/sdk-trace-base": "^1.15.0", - "@opentelemetry/sdk-trace-node": "^1.15.0", - "@opentelemetry/semantic-conventions": "^1.7.0", + "@opentelemetry/sdk-trace-base": "^1.17.0", + "@opentelemetry/sdk-trace-node": "^1.17.0", + "@opentelemetry/semantic-conventions": "^1.17.0", "@sentry/node": "7.70.0" }, "scripts": { diff --git a/packages/opentelemetry-node/src/spanprocessor.ts b/packages/opentelemetry-node/src/spanprocessor.ts index 7adc0ee31e5f..5a0b47358ed2 100644 --- a/packages/opentelemetry-node/src/spanprocessor.ts +++ b/packages/opentelemetry-node/src/spanprocessor.ts @@ -1,12 +1,12 @@ import type { Context } from '@opentelemetry/api'; import { SpanKind, trace } from '@opentelemetry/api'; import type { Span as OtelSpan, SpanProcessor as OtelSpanProcessor } from '@opentelemetry/sdk-trace-base'; -import { SemanticAttributes } from '@opentelemetry/semantic-conventions'; import { addGlobalEventProcessor, addTracingExtensions, getCurrentHub, Transaction } from '@sentry/core'; import type { DynamicSamplingContext, Span as SentrySpan, TraceparentData, TransactionContext } from '@sentry/types'; -import { isString, logger } from '@sentry/utils'; +import { logger } from '@sentry/utils'; import { SENTRY_DYNAMIC_SAMPLING_CONTEXT_KEY, SENTRY_TRACE_PARENT_CONTEXT_KEY } from './constants'; +import { maybeCaptureExceptionForTimedEvent } from './utils/captureExceptionForTimedEvent'; import { isSentryRequestSpan } from './utils/isSentryRequest'; import { mapOtelStatus } from './utils/mapOtelStatus'; import { parseSpanDescription } from './utils/parseOtelSpanDescription'; @@ -109,44 +109,9 @@ export class SentrySpanProcessor implements OtelSpanProcessor { return; } + const hub = getCurrentHub(); otelSpan.events.forEach(event => { - if (event.name !== 'exception') { - return; - } - - const attributes = event.attributes; - if (!attributes) { - return; - } - - const message = attributes[SemanticAttributes.EXCEPTION_MESSAGE]; - const syntheticError = new Error(message as string | undefined); - - const stack = attributes[SemanticAttributes.EXCEPTION_STACKTRACE]; - if (isString(stack)) { - syntheticError.stack = stack; - } - - const type = attributes[SemanticAttributes.EXCEPTION_TYPE]; - if (isString(type)) { - syntheticError.name = type; - } - - getCurrentHub().captureException(syntheticError, { - captureContext: { - contexts: { - otel: { - attributes: otelSpan.attributes, - resource: otelSpan.resource.attributes, - }, - trace: { - trace_id: otelSpan.spanContext().traceId, - span_id: otelSpan.spanContext().spanId, - parent_span_id: otelSpan.parentSpanId, - }, - }, - }, - }); + maybeCaptureExceptionForTimedEvent(hub, event, otelSpan); }); if (sentrySpan instanceof Transaction) { diff --git a/packages/opentelemetry-node/src/utils/captureExceptionForTimedEvent.ts b/packages/opentelemetry-node/src/utils/captureExceptionForTimedEvent.ts new file mode 100644 index 000000000000..3dde27e49e9f --- /dev/null +++ b/packages/opentelemetry-node/src/utils/captureExceptionForTimedEvent.ts @@ -0,0 +1,55 @@ +import type { Span as OtelSpan, TimedEvent } from '@opentelemetry/sdk-trace-base'; +import { SemanticAttributes } from '@opentelemetry/semantic-conventions'; +import type { Hub } from '@sentry/types'; +import { isString } from '@sentry/utils'; + +/** + * Maybe capture a Sentry exception for an OTEL timed event. + * This will check if the event is exception-like and in that case capture it as an exception. + */ +export function maybeCaptureExceptionForTimedEvent(hub: Hub, event: TimedEvent, otelSpan?: OtelSpan): void { + if (event.name !== 'exception') { + return; + } + + const attributes = event.attributes; + if (!attributes) { + return; + } + + const message = attributes[SemanticAttributes.EXCEPTION_MESSAGE]; + + if (typeof message !== 'string') { + return; + } + + const syntheticError = new Error(message); + + const stack = attributes[SemanticAttributes.EXCEPTION_STACKTRACE]; + if (isString(stack)) { + syntheticError.stack = stack; + } + + const type = attributes[SemanticAttributes.EXCEPTION_TYPE]; + if (isString(type)) { + syntheticError.name = type; + } + + hub.captureException(syntheticError, { + captureContext: otelSpan + ? { + contexts: { + otel: { + attributes: otelSpan.attributes, + resource: otelSpan.resource.attributes, + }, + trace: { + trace_id: otelSpan.spanContext().traceId, + span_id: otelSpan.spanContext().spanId, + parent_span_id: otelSpan.parentSpanId, + }, + }, + } + : undefined, + }); +} diff --git a/packages/opentelemetry-node/test/spanprocessor.test.ts b/packages/opentelemetry-node/test/spanprocessor.test.ts index 3b87068c76f7..ea6e0833a395 100644 --- a/packages/opentelemetry-node/test/spanprocessor.test.ts +++ b/packages/opentelemetry-node/test/spanprocessor.test.ts @@ -275,7 +275,7 @@ describe('SentrySpanProcessor', () => { 'service.name': 'test-service', 'telemetry.sdk.language': 'nodejs', 'telemetry.sdk.name': 'opentelemetry', - 'telemetry.sdk.version': '1.15.0', + 'telemetry.sdk.version': '1.17.0', }, }, }); @@ -300,7 +300,7 @@ describe('SentrySpanProcessor', () => { 'service.name': 'test-service', 'telemetry.sdk.language': 'nodejs', 'telemetry.sdk.name': 'opentelemetry', - 'telemetry.sdk.version': '1.15.0', + 'telemetry.sdk.version': '1.17.0', }, }, }); diff --git a/packages/opentelemetry-node/test/utils/captureExceptionForTimedEvent.test.ts b/packages/opentelemetry-node/test/utils/captureExceptionForTimedEvent.test.ts new file mode 100644 index 000000000000..4d0c39b3a8b9 --- /dev/null +++ b/packages/opentelemetry-node/test/utils/captureExceptionForTimedEvent.test.ts @@ -0,0 +1,147 @@ +import type { Span as OtelSpan, TimedEvent } from '@opentelemetry/sdk-trace-base'; +import { SemanticAttributes } from '@opentelemetry/semantic-conventions'; +import type { Hub } from '@sentry/types'; + +import { maybeCaptureExceptionForTimedEvent } from '../../src/utils/captureExceptionForTimedEvent'; + +describe('maybeCaptureExceptionForTimedEvent', () => { + it('ignores non-exception events', async () => { + const event: TimedEvent = { + time: [12345, 0], + name: 'test event', + }; + + const captureException = jest.fn(); + const hub = { + captureException, + } as unknown as Hub; + + maybeCaptureExceptionForTimedEvent(hub, event); + + expect(captureException).not.toHaveBeenCalled(); + }); + + it('ignores exception events without EXCEPTION_MESSAGE', async () => { + const event: TimedEvent = { + time: [12345, 0], + name: 'exception', + }; + + const captureException = jest.fn(); + const hub = { + captureException, + } as unknown as Hub; + + maybeCaptureExceptionForTimedEvent(hub, event); + + expect(captureException).not.toHaveBeenCalled(); + }); + + it('captures exception from event with EXCEPTION_MESSAGE', async () => { + const event: TimedEvent = { + time: [12345, 0], + name: 'exception', + attributes: { + [SemanticAttributes.EXCEPTION_MESSAGE]: 'test-message', + }, + }; + + const captureException = jest.fn(); + const hub = { + captureException, + } as unknown as Hub; + + maybeCaptureExceptionForTimedEvent(hub, event); + + expect(captureException).toHaveBeenCalledTimes(1); + expect(captureException).toHaveBeenCalledWith(expect.objectContaining({ message: 'test-message' }), { + captureContext: undefined, + }); + expect(captureException).toHaveBeenCalledWith(expect.any(Error), { + captureContext: undefined, + }); + }); + + it('captures stack and type, if available', async () => { + const event: TimedEvent = { + time: [12345, 0], + name: 'exception', + attributes: { + [SemanticAttributes.EXCEPTION_MESSAGE]: 'test-message', + [SemanticAttributes.EXCEPTION_STACKTRACE]: 'test-stack', + [SemanticAttributes.EXCEPTION_TYPE]: 'test-type', + }, + }; + + const captureException = jest.fn(); + const hub = { + captureException, + } as unknown as Hub; + + maybeCaptureExceptionForTimedEvent(hub, event); + + expect(captureException).toHaveBeenCalledTimes(1); + expect(captureException).toHaveBeenCalledWith( + expect.objectContaining({ message: 'test-message', name: 'test-type', stack: 'test-stack' }), + { + captureContext: undefined, + }, + ); + expect(captureException).toHaveBeenCalledWith(expect.any(Error), { + captureContext: undefined, + }); + }); + + it('captures span context, if available', async () => { + const event: TimedEvent = { + time: [12345, 0], + name: 'exception', + attributes: { + [SemanticAttributes.EXCEPTION_MESSAGE]: 'test-message', + }, + }; + + const span = { + parentSpanId: 'test-parent-span-id', + attributes: { + 'test-attr1': 'test-value1', + }, + resource: { + attributes: { + 'test-attr2': 'test-value2', + }, + }, + spanContext: () => { + return { spanId: 'test-span-id', traceId: 'test-trace-id' }; + }, + } as unknown as OtelSpan; + + const captureException = jest.fn(); + const hub = { + captureException, + } as unknown as Hub; + + maybeCaptureExceptionForTimedEvent(hub, event, span); + + expect(captureException).toHaveBeenCalledTimes(1); + expect(captureException).toHaveBeenCalledWith(expect.objectContaining({ message: 'test-message' }), { + captureContext: { + contexts: { + otel: { + attributes: { + 'test-attr1': 'test-value1', + }, + resource: { + 'test-attr2': 'test-value2', + }, + }, + trace: { + trace_id: 'test-trace-id', + span_id: 'test-span-id', + parent_span_id: 'test-parent-span-id', + }, + }, + }, + }); + }); +}); diff --git a/packages/react/src/errorboundary.tsx b/packages/react/src/errorboundary.tsx index 3d894fc699a8..66006b06d7b6 100644 --- a/packages/react/src/errorboundary.tsx +++ b/packages/react/src/errorboundary.tsx @@ -128,7 +128,7 @@ class ErrorBoundary extends React.ComponentProduct} /> @@ -108,9 +110,9 @@ function getNormalizedName( // We should not count wildcard operators in the url segments calculation pathBuilder.slice(-2) !== '/*' ) { - return [newPath, 'route']; + return [basename + newPath, 'route']; } - return [pathBuilder, 'route']; + return [basename + pathBuilder, 'route']; } } } @@ -131,7 +133,7 @@ function updatePageloadTransaction( : (_matchRoutes(routes, location, basename) as unknown as RouteMatch[]); if (activeTransaction && branches) { - activeTransaction.setName(...getNormalizedName(routes, location, branches)); + activeTransaction.setName(...getNormalizedName(routes, location, branches, basename)); } } @@ -149,7 +151,7 @@ function handleNavigation( activeTransaction.finish(); } - const [name, source] = getNormalizedName(routes, location, branches); + const [name, source] = getNormalizedName(routes, location, branches, basename); activeTransaction = _customStartTransaction({ name, op: 'navigation', diff --git a/packages/react/test/reactrouterv6.4.test.tsx b/packages/react/test/reactrouterv6.4.test.tsx index 19a714f853a3..a5c35169c283 100644 --- a/packages/react/test/reactrouterv6.4.test.tsx +++ b/packages/react/test/reactrouterv6.4.test.tsx @@ -307,7 +307,51 @@ describe('React Router v6.4', () => { op: 'navigation', origin: 'auto.navigation.react.reactrouterv6', tags: { 'routing.instrumentation': 'react-router-v6' }, - metadata: { source: 'url' }, + metadata: { source: 'route' }, + }); + }); + + it('works with parameterized paths and `basename`', () => { + const [mockStartTransaction] = createInstrumentation(); + const sentryCreateBrowserRouter = wrapCreateBrowserRouter(createMemoryRouter as CreateRouterFunction); + + const router = sentryCreateBrowserRouter( + [ + { + path: '/', + element: , + }, + { + path: ':orgId', + children: [ + { + path: 'users', + children: [ + { + path: ':userId', + element:
User
, + }, + ], + }, + ], + }, + ], + { + initialEntries: ['/admin'], + basename: '/admin', + }, + ); + + // @ts-expect-error router is fine + render(); + + expect(mockStartTransaction).toHaveBeenCalledTimes(2); + expect(mockStartTransaction).toHaveBeenLastCalledWith({ + name: '/admin/:orgId/users/:userId', + op: 'navigation', + origin: 'auto.navigation.react.reactrouterv6', + tags: { 'routing.instrumentation': 'react-router-v6' }, + metadata: { source: 'route' }, }); }); }); diff --git a/packages/replay/src/coreHandlers/handleGlobalEvent.ts b/packages/replay/src/coreHandlers/handleGlobalEvent.ts index 539845dc40fc..c2e134a86acb 100644 --- a/packages/replay/src/coreHandlers/handleGlobalEvent.ts +++ b/packages/replay/src/coreHandlers/handleGlobalEvent.ts @@ -16,51 +16,54 @@ export function handleGlobalEventListener( ): (event: Event, hint: EventHint) => Event | null { const afterSendHandler = includeAfterSendEventHandling ? handleAfterSendEvent(replay) : undefined; - return (event: Event, hint: EventHint) => { - // Do nothing if replay has been disabled - if (!replay.isEnabled()) { - return event; - } + return Object.assign( + (event: Event, hint: EventHint) => { + // Do nothing if replay has been disabled + if (!replay.isEnabled()) { + return event; + } - if (isReplayEvent(event)) { - // Replays have separate set of breadcrumbs, do not include breadcrumbs - // from core SDK - delete event.breadcrumbs; - return event; - } + if (isReplayEvent(event)) { + // Replays have separate set of breadcrumbs, do not include breadcrumbs + // from core SDK + delete event.breadcrumbs; + return event; + } - // We only want to handle errors & transactions, nothing else - if (!isErrorEvent(event) && !isTransactionEvent(event)) { - return event; - } + // We only want to handle errors & transactions, nothing else + if (!isErrorEvent(event) && !isTransactionEvent(event)) { + return event; + } - // Unless `captureExceptions` is enabled, we want to ignore errors coming from rrweb - // As there can be a bunch of stuff going wrong in internals there, that we don't want to bubble up to users - if (isRrwebError(event, hint) && !replay.getOptions()._experiments.captureExceptions) { - __DEBUG_BUILD__ && logger.log('[Replay] Ignoring error from rrweb internals', event); - return null; - } + // Unless `captureExceptions` is enabled, we want to ignore errors coming from rrweb + // As there can be a bunch of stuff going wrong in internals there, that we don't want to bubble up to users + if (isRrwebError(event, hint) && !replay.getOptions()._experiments.captureExceptions) { + __DEBUG_BUILD__ && logger.log('[Replay] Ignoring error from rrweb internals', event); + return null; + } - // When in buffer mode, we decide to sample here. - // Later, in `handleAfterSendEvent`, if the replayId is set, we know that we sampled - // And convert the buffer session to a full session - const isErrorEventSampled = shouldSampleForBufferEvent(replay, event); + // When in buffer mode, we decide to sample here. + // Later, in `handleAfterSendEvent`, if the replayId is set, we know that we sampled + // And convert the buffer session to a full session + const isErrorEventSampled = shouldSampleForBufferEvent(replay, event); - // Tag errors if it has been sampled in buffer mode, or if it is session mode - // Only tag transactions if in session mode - const shouldTagReplayId = isErrorEventSampled || replay.recordingMode === 'session'; + // Tag errors if it has been sampled in buffer mode, or if it is session mode + // Only tag transactions if in session mode + const shouldTagReplayId = isErrorEventSampled || replay.recordingMode === 'session'; - if (shouldTagReplayId) { - event.tags = { ...event.tags, replayId: replay.getSessionId() }; - } + if (shouldTagReplayId) { + event.tags = { ...event.tags, replayId: replay.getSessionId() }; + } - // In cases where a custom client is used that does not support the new hooks (yet), - // we manually call this hook method here - if (afterSendHandler) { - // Pretend the error had a 200 response so we always capture it - afterSendHandler(event, { statusCode: 200 }); - } + // In cases where a custom client is used that does not support the new hooks (yet), + // we manually call this hook method here + if (afterSendHandler) { + // Pretend the error had a 200 response so we always capture it + afterSendHandler(event, { statusCode: 200 }); + } - return event; - }; + return event; + }, + { id: 'Replay' }, + ); } diff --git a/packages/replay/src/util/addGlobalListeners.ts b/packages/replay/src/util/addGlobalListeners.ts index 6e73b270bb93..0948561f7852 100644 --- a/packages/replay/src/util/addGlobalListeners.ts +++ b/packages/replay/src/util/addGlobalListeners.ts @@ -26,7 +26,12 @@ export function addGlobalListeners(replay: ReplayContainer): void { // Tag all (non replay) events that get sent to Sentry with the current // replay ID so that we can reference them later in the UI - addGlobalEventProcessor(handleGlobalEventListener(replay, !hasHooks(client))); + const eventProcessor = handleGlobalEventListener(replay, !hasHooks(client)); + if (client && client.addEventProcessor) { + client.addEventProcessor(eventProcessor); + } else { + addGlobalEventProcessor(eventProcessor); + } // If a custom client has no hooks yet, we continue to use the "old" implementation if (hasHooks(client)) { diff --git a/packages/vercel-edge/README.md b/packages/vercel-edge/README.md index d3e7849ffdab..e6e893bc5044 100644 --- a/packages/vercel-edge/README.md +++ b/packages/vercel-edge/README.md @@ -23,9 +23,9 @@ To use this SDK, call `init(options)` as early as possible in the main entry mod hook into the environment. Note that you can turn off almost all side effects using the respective options. ```javascript -// ES5 Syntax +// CJS Syntax const Sentry = require('@sentry/vercel-edge'); -// ES6 Syntax +// ESM Syntax import * as Sentry from '@sentry/vercel-edge'; Sentry.init({ diff --git a/yarn.lock b/yarn.lock index d283d72b7ad2..774b6abcc4dd 100644 --- a/yarn.lock +++ b/yarn.lock @@ -3802,7 +3802,7 @@ dependencies: "@opentelemetry/context-base" "^0.14.0" -"@opentelemetry/api@1.4.1", "@opentelemetry/api@^1.4.1", "@opentelemetry/api@~1.4.1": +"@opentelemetry/api@1.4.1": version "1.4.1" resolved "https://registry.yarnpkg.com/@opentelemetry/api/-/api-1.4.1.tgz#ff22eb2e5d476fbc2450a196e40dd243cc20c28f" integrity sha512-O2yRJce1GOc6PAy3QxFM4NzFiWzvScDC1/5ihYBL6BUEVdq0XMWN01sppE+H6bBXbaFYipjwFLEWLg5PaSOThA== @@ -3814,17 +3814,15 @@ dependencies: "@opentelemetry/context-base" "^0.12.0" -"@opentelemetry/context-async-hooks@1.15.0": - version "1.15.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/context-async-hooks/-/context-async-hooks-1.15.0.tgz#134ecbe9096227f72e3178a15287a420a13746a0" - integrity sha512-sfxQOyAyV3WsKswGX0Yx3P+e7t3EtxpF/PC+6e4+rqs88oUfTaP3214iz4GQuuzV9yCG8DRWTZ96J6E/iD0qeA== - dependencies: - tslib "^2.3.1" +"@opentelemetry/api@^1.6.0", "@opentelemetry/api@~1.6.0": + version "1.6.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/api/-/api-1.6.0.tgz#de2c6823203d6f319511898bb5de7e70f5267e19" + integrity sha512-OWlrQAnWn9577PhVgqjUvMr1pg57Bc4jv0iL4w0PRuOSRvq67rvHW9Ie/dZVMvCzhSCB+UxhcY/PmCmFj33Q+g== -"@opentelemetry/context-async-hooks@~1.15.0": - version "1.15.2" - resolved "https://registry.yarnpkg.com/@opentelemetry/context-async-hooks/-/context-async-hooks-1.15.2.tgz#116bd5fef231137198d5bf551e8c0521fbdfe928" - integrity sha512-VAMHG67srGFQDG/N2ns5AyUT9vUcoKpZ/NpJ5fDQIPfJd7t3ju+aHwvDsMcrYBWuCh03U3Ky6o16+872CZchBg== +"@opentelemetry/context-async-hooks@1.17.0", "@opentelemetry/context-async-hooks@~1.17.0": + version "1.17.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/context-async-hooks/-/context-async-hooks-1.17.0.tgz#d198319785bc81533f1a096e86d7f81ce57346ed" + integrity sha512-bDIRCgpKniSyhORU0fTL9ISW6ucU9nruKyXKwYrEBep/2f3uLz8LFyF51ZUK9QxIwBHw6WJudK/2UqttWzER4w== "@opentelemetry/context-base@^0.12.0": version "0.12.0" @@ -3836,20 +3834,19 @@ resolved "https://registry.yarnpkg.com/@opentelemetry/context-base/-/context-base-0.14.0.tgz#c67fc20a4d891447ca1a855d7d70fa79a3533001" integrity sha512-sDOAZcYwynHFTbLo6n8kIbLiVF3a3BLkrmehJUyEbT9F+Smbi47kLGS2gG2g0fjBLR/Lr1InPD7kXL7FaTqEkw== -"@opentelemetry/core@1.14.0": - version "1.14.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/core/-/core-1.14.0.tgz#64e876b29cb736c984d54164cd47433f513eafd3" - integrity sha512-MnMZ+sxsnlzloeuXL2nm5QcNczt/iO82UOeQQDHhV83F2fP3sgntW2evvtoxJki0MBLxEsh5ADD7PR/Hn5uzjw== +"@opentelemetry/core@1.15.2": + version "1.15.2" + resolved "https://registry.yarnpkg.com/@opentelemetry/core/-/core-1.15.2.tgz#5b170bf223a2333884bbc2d29d95812cdbda7c9f" + integrity sha512-+gBv15ta96WqkHZaPpcDHiaz0utiiHZVfm2YOYSqFGrUaJpPkMoSuLBB58YFQGi6Rsb9EHos84X6X5+9JspmLw== dependencies: - "@opentelemetry/semantic-conventions" "1.14.0" + "@opentelemetry/semantic-conventions" "1.15.2" -"@opentelemetry/core@1.15.0", "@opentelemetry/core@^1.1.0", "@opentelemetry/core@^1.8.0": - version "1.15.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/core/-/core-1.15.0.tgz#2ba928df0443732825a72a766c2edae9a7f9863f" - integrity sha512-GGTS6BytfaN8OgbCUOnxg/a9WVsVUj0484zXHZuBzvIXx7V4Tmkb0IHnnhS7Q0cBLNLgjNuvrCpQaP8fIvO4bg== +"@opentelemetry/core@1.17.0", "@opentelemetry/core@^1.1.0", "@opentelemetry/core@^1.7.0", "@opentelemetry/core@^1.8.0": + version "1.17.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/core/-/core-1.17.0.tgz#6a72425f5f953dc68b4c7c66d947c018173d30d2" + integrity sha512-tfnl3h+UefCgx1aeN2xtrmr6BmdWGKXypk0pflQR0urFS40aE88trnkOMc2HTJZbMrqEEl4HsaBeFhwLVXsrJg== dependencies: - "@opentelemetry/semantic-conventions" "1.15.0" - tslib "^2.3.1" + "@opentelemetry/semantic-conventions" "1.17.0" "@opentelemetry/core@^0.12.0": version "0.12.0" @@ -3860,180 +3857,149 @@ "@opentelemetry/context-base" "^0.12.0" semver "^7.1.3" -"@opentelemetry/core@^1.7.0": - version "1.7.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/core/-/core-1.7.0.tgz#83bdd1b7a4ceafcdffd6590420657caec5f7b34c" - integrity sha512-AVqAi5uc8DrKJBimCTFUT4iFI+5eXpo4sYmGbQ0CypG0piOTHE2g9c5aSoTGYXu3CzOmJZf7pT6Xh+nwm5d6yQ== - dependencies: - "@opentelemetry/semantic-conventions" "1.7.0" - -"@opentelemetry/instrumentation-express@~0.33.0": - version "0.33.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation-express/-/instrumentation-express-0.33.0.tgz#d972ef43420759761f7dbfe78a6ae159cd925a69" - integrity sha512-Cem3AssubzUoBK5ab89rBt2kY90i/FFyQwMC9wPjBQldkOaT4cR+5ufvWritXRfoPltqEeX2imLavujNH6EzCw== +"@opentelemetry/instrumentation-express@~0.33.1": + version "0.33.1" + resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation-express/-/instrumentation-express-0.33.1.tgz#0710f839d2a395014d2ffef9390074bb60009841" + integrity sha512-awrpiTZWnLOCJ4TeDMTrs6/gH/oXbNipoPx3WUKQlA1yfMlpNynqokTyCYv1n10Zu9Y2P/nIhoNnUw0ywp61nA== dependencies: "@opentelemetry/core" "^1.8.0" - "@opentelemetry/instrumentation" "^0.41.0" + "@opentelemetry/instrumentation" "^0.41.2" "@opentelemetry/semantic-conventions" "^1.0.0" - "@types/express" "4.17.13" - tslib "^2.3.1" + "@types/express" "4.17.17" -"@opentelemetry/instrumentation-fastify@~0.32.0": - version "0.32.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation-fastify/-/instrumentation-fastify-0.32.0.tgz#9f0846282f5f428b3ec9a749c1111cf2f153986d" - integrity sha512-M0zRI5+FfA2UnNk9YSeofhZkM5X46w2lDW/1pVahpIlfyPoEbOdRO2YrfR6Y9t9emR62IKk4tN/IcSgXIK2RRg== +"@opentelemetry/instrumentation-fastify@~0.32.2": + version "0.32.2" + resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation-fastify/-/instrumentation-fastify-0.32.2.tgz#4af882938d3c05f7c7f5f860095e568728a2d838" + integrity sha512-DKa7SgxTtZ0O1ngGtAdwr/g8XguYw6KvLNME+J8rt6QpWQM+xytS0bg4atZAyt6aeYr/kO1sMrGXSlHEEYWIhg== dependencies: "@opentelemetry/core" "^1.8.0" - "@opentelemetry/instrumentation" "^0.41.0" + "@opentelemetry/instrumentation" "^0.41.2" "@opentelemetry/semantic-conventions" "^1.0.0" - tslib "^2.3.1" -"@opentelemetry/instrumentation-graphql@~0.35.0": - version "0.35.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation-graphql/-/instrumentation-graphql-0.35.0.tgz#45d2df2be320c7289aff49cabfbbfa8791670b19" - integrity sha512-hKuOXTzB8UBaxVteKU2nMRGnUPt6bD9SSBBLYaDOGGPF1Gs4XsiuMMRuyXomMIudelM7flPpbuqiP9YoSJuXQQ== +"@opentelemetry/instrumentation-graphql@~0.35.1": + version "0.35.1" + resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation-graphql/-/instrumentation-graphql-0.35.1.tgz#e49ec2256bcc4820458688abac0212ac781864c0" + integrity sha512-bAM4W5wU0lZ1UIKK/5b4p8LEU8N6W+VgpcnUIK7GTTDxdhcWTd3Q6oyS6nauhZSzEnAEmmJVXaLQAGIU4sEkyA== dependencies: - "@opentelemetry/instrumentation" "^0.41.0" - tslib "^2.3.1" + "@opentelemetry/instrumentation" "^0.41.2" -"@opentelemetry/instrumentation-http@~0.41.0": - version "0.41.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation-http/-/instrumentation-http-0.41.0.tgz#c92ffcb9581544d76d17540f7df442fad8601035" - integrity sha512-O/YTVH4xE96rxRYoo14vayM9s0MUTtMASMAtYS3yvXMJETgc5aFnTrWezKQ6VJ2Lew5qfm1ZISzFURLSUM0qTw== +"@opentelemetry/instrumentation-http@~0.43.0": + version "0.43.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation-http/-/instrumentation-http-0.43.0.tgz#c21cf8b407e26c912448b110f340ad1eb657a316" + integrity sha512-Ho3IFQFuD0xmcVc0Uq9AvYvROSOuydn4XWRT/h/GO0VCwOeYz/WCwUJvRdS3m1B3AZ4iGJ0q/nhsATp2JX3/gA== dependencies: - "@opentelemetry/core" "1.15.0" - "@opentelemetry/instrumentation" "0.41.0" - "@opentelemetry/semantic-conventions" "1.15.0" - semver "^7.5.1" - tslib "^2.3.1" + "@opentelemetry/core" "1.17.0" + "@opentelemetry/instrumentation" "0.43.0" + "@opentelemetry/semantic-conventions" "1.17.0" + semver "^7.5.2" -"@opentelemetry/instrumentation-mongodb@~0.36.0": - version "0.36.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation-mongodb/-/instrumentation-mongodb-0.36.0.tgz#2ee2acffb1869d9dc3a89e9b879be987e18c1b11" - integrity sha512-bisDLBO0JqydPh4rkgrbYhnFOd4T2ZAnFAnBFll9TB1jJEHTeeobdBThuwxvur5q5ZfbjevreUcMydG6UBNMaA== +"@opentelemetry/instrumentation-mongodb@~0.37.0": + version "0.37.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation-mongodb/-/instrumentation-mongodb-0.37.0.tgz#a7cf4bd9cd5b1053182ec1458c91456812432f55" + integrity sha512-Fwuwf7Fsx/F3QXtU6hbxU4D6DtT33YkAr0+fjtR7qTEcAU0YOxCZfy4tlX2jxjxR1ze8tKfaAWhXBxXwLMWT3g== dependencies: - "@opentelemetry/instrumentation" "^0.41.0" + "@opentelemetry/instrumentation" "^0.41.2" "@opentelemetry/sdk-metrics" "^1.9.1" "@opentelemetry/semantic-conventions" "^1.0.0" - tslib "^2.3.1" -"@opentelemetry/instrumentation-mongoose@~0.33.0": - version "0.33.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation-mongoose/-/instrumentation-mongoose-0.33.0.tgz#8063740274120105f559bcf663125d3f7cc00cb4" - integrity sha512-IB4zCJ7vsiILx5hjPH7PtlvKIVN84m3rER8zu7xeaMpfpzD5/khj6et0x1aE+KzPS49nIOZx3qmH67MocSNevg== +"@opentelemetry/instrumentation-mongoose@~0.33.1": + version "0.33.1" + resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation-mongoose/-/instrumentation-mongoose-0.33.1.tgz#0e37eed215fb7fbf8adc0e70199bb8992cb1ea21" + integrity sha512-IzYcEZSmlaOlkyACt8gTl0z3eEQafxzEAt/+W+FdNBiUdm81qpVx/1bpzJwSgIsgcLf27Dl5WsPmrSAi4+Bcng== dependencies: "@opentelemetry/core" "^1.8.0" - "@opentelemetry/instrumentation" "^0.41.0" + "@opentelemetry/instrumentation" "^0.41.2" "@opentelemetry/semantic-conventions" "^1.0.0" - tslib "^2.3.1" -"@opentelemetry/instrumentation-mysql2@~0.34.0": - version "0.34.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation-mysql2/-/instrumentation-mysql2-0.34.0.tgz#48f560b7169128195d19114451c3a5c907b7833a" - integrity sha512-wEJ9BcZTT/60a69V5GS/XlQx+JyoOKKYYR/kdZ2p/XY/UI+kELPSWiLZAR00YLYi33g0zVZlKG3gfHU1KFn5sQ== +"@opentelemetry/instrumentation-mysql2@~0.34.1": + version "0.34.1" + resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation-mysql2/-/instrumentation-mysql2-0.34.1.tgz#d7ce741a7d9a7da270fa791e1c64d8cedd58b5b7" + integrity sha512-SPwgLI2H+gH+GP7b5cWQlFqO/7UeHvw6ZzFKxwLr4vy8wmxYF4aBMLc8qVO8bdXFHd114v0IzOIAvpG6sl/zYQ== dependencies: - "@opentelemetry/instrumentation" "^0.41.0" + "@opentelemetry/instrumentation" "^0.41.2" "@opentelemetry/semantic-conventions" "^1.0.0" - tslib "^2.3.1" + "@opentelemetry/sql-common" "^0.40.0" -"@opentelemetry/instrumentation-mysql@~0.34.0": - version "0.34.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation-mysql/-/instrumentation-mysql-0.34.0.tgz#437294f3c8b02ad76b3d56e77f28d9af6cf19c91" - integrity sha512-muBzhaSk3to1XK2aSMFTP9lW6YALebQ8ick9raDBESiLf8JREZDJWVlhfaigeJGBk53tUBZ3Ty1g1Cfe15+OhQ== +"@opentelemetry/instrumentation-mysql@~0.34.1": + version "0.34.1" + resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation-mysql/-/instrumentation-mysql-0.34.1.tgz#9703d21615dd5ee6b9eda1d74029ba75eec46c9a" + integrity sha512-zQq7hN3ILm1vIJCGeKHRc4pTK8LOmkTt8oKWf0v+whFs7axieIhXZMoCqIBm6BigLy3Trg5iaKyuSrx7kO6q2g== dependencies: - "@opentelemetry/instrumentation" "^0.41.0" + "@opentelemetry/instrumentation" "^0.41.2" "@opentelemetry/semantic-conventions" "^1.0.0" - "@types/mysql" "2.15.19" - tslib "^2.3.1" + "@types/mysql" "2.15.21" -"@opentelemetry/instrumentation-nestjs-core@~0.33.0": - version "0.33.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation-nestjs-core/-/instrumentation-nestjs-core-0.33.0.tgz#f2d64f033f9a84c2ba4ce85c0ec1381ec542b452" - integrity sha512-/c1nipi2XLt2TQlFpKNof44o99H7BmdOWiZBAdIATJpvOKPbn+Ggt4OQQdtmxFyzMX13dTxgtpQ5RX2Orvxz2Q== +"@opentelemetry/instrumentation-nestjs-core@~0.33.1": + version "0.33.1" + resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation-nestjs-core/-/instrumentation-nestjs-core-0.33.1.tgz#a6e0175bcda25e455339a5527268e746be969297" + integrity sha512-Y5Khvp8ODA6TuDcZKAc63cYDeeZAA/n0ceF0pcVCJwA2NBeD0hmTrCJXES2cvt7wVbHV/SYCu7OpYDQkNjbBWw== dependencies: - "@opentelemetry/instrumentation" "^0.41.0" + "@opentelemetry/instrumentation" "^0.41.2" "@opentelemetry/semantic-conventions" "^1.0.0" - tslib "^2.3.1" -"@opentelemetry/instrumentation-pg@~0.36.0": - version "0.36.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation-pg/-/instrumentation-pg-0.36.0.tgz#43270d2849a0e074ec6eb705dc12216e5c7cc84c" - integrity sha512-S9RmzTILWTl7AVfdp/e8lWQTlpwrpoPbpxAfEJ1ENzTlPMmdw0jWPAQTgrTLQa6cpzhiypDHts3g2b6hc1zFYQ== +"@opentelemetry/instrumentation-pg@~0.36.1": + version "0.36.1" + resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation-pg/-/instrumentation-pg-0.36.1.tgz#66e3aa10948c6e3188d04676dbf304ae8571ce2f" + integrity sha512-k8L7RSRTQ6e+DbHEXZB8Tmf/efkQnWKeClpZb3TEdb34Pvme4PmcpG2zb6JtM99nNrshNlVDLCZ90U3xDneTbw== dependencies: "@opentelemetry/core" "^1.8.0" - "@opentelemetry/instrumentation" "^0.41.0" + "@opentelemetry/instrumentation" "^0.41.2" "@opentelemetry/semantic-conventions" "^1.0.0" "@opentelemetry/sql-common" "^0.40.0" "@types/pg" "8.6.1" "@types/pg-pool" "2.0.3" - tslib "^2.3.1" -"@opentelemetry/instrumentation@0.40.0": - version "0.40.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation/-/instrumentation-0.40.0.tgz#13d5f2d60c3fafef124ab6961a32204f7ef8bb25" - integrity sha512-23TzBKPflUS1uEq5SXymnQKQDSda35KvHjnvxdcDQGE+wg6hwDHgScUCWiBmZW4sxAaPcANfs+Wc9B7yDuyT6Q== - dependencies: - "@types/shimmer" "^1.0.2" - import-in-the-middle "1.3.5" - require-in-the-middle "^7.1.0" - semver "^7.3.2" - shimmer "^1.2.1" - -"@opentelemetry/instrumentation@0.41.0": - version "0.41.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation/-/instrumentation-0.41.0.tgz#a67a7f6d215d8802c2e956907a913b793037e04d" - integrity sha512-Ut9SnZfi7MexOk+GHCMjEtYHogIb6v1dfbnq+oTbQj0lOQUSNLtlO6bXwUdtmPhbvrx6bC0AGr1L6g3rNimv9w== +"@opentelemetry/instrumentation@0.41.2", "@opentelemetry/instrumentation@^0.41.2": + version "0.41.2" + resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation/-/instrumentation-0.41.2.tgz#cae11fa64485dcf03dae331f35b315b64bc6189f" + integrity sha512-rxU72E0pKNH6ae2w5+xgVYZLzc5mlxAbGzF4shxMVK8YC2QQsfN38B2GPbj0jvrKWWNUElfclQ+YTykkNg/grw== dependencies: "@types/shimmer" "^1.0.2" - import-in-the-middle "1.4.1" + import-in-the-middle "1.4.2" require-in-the-middle "^7.1.1" semver "^7.5.1" shimmer "^1.2.1" - tslib "^2.3.1" -"@opentelemetry/instrumentation@^0.41.0", "@opentelemetry/instrumentation@~0.41.0": - version "0.41.2" - resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation/-/instrumentation-0.41.2.tgz#cae11fa64485dcf03dae331f35b315b64bc6189f" - integrity sha512-rxU72E0pKNH6ae2w5+xgVYZLzc5mlxAbGzF4shxMVK8YC2QQsfN38B2GPbj0jvrKWWNUElfclQ+YTykkNg/grw== +"@opentelemetry/instrumentation@0.43.0", "@opentelemetry/instrumentation@~0.43.0": + version "0.43.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/instrumentation/-/instrumentation-0.43.0.tgz#749521415df03396f969bf42341fcb4acd2e9c7b" + integrity sha512-S1uHE+sxaepgp+t8lvIDuRgyjJWisAb733198kwQTUc9ZtYQ2V2gmyCtR1x21ePGVLoMiX/NWY7WA290hwkjJQ== dependencies: "@types/shimmer" "^1.0.2" import-in-the-middle "1.4.2" require-in-the-middle "^7.1.1" - semver "^7.5.1" + semver "^7.5.2" shimmer "^1.2.1" -"@opentelemetry/propagator-b3@1.15.0": - version "1.15.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/propagator-b3/-/propagator-b3-1.15.0.tgz#502c3b7030646e7654ce243ae24b67aeac405a53" - integrity sha512-YafSIITpCmo76VdlJ/GvS5x+uuRWCU5BqCOV9CITi11Tk4aqTxMR3pXlMoPYQWstUUgacQf4dGcdvdS+1rkDWQ== +"@opentelemetry/propagator-b3@1.17.0": + version "1.17.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/propagator-b3/-/propagator-b3-1.17.0.tgz#32509a8214b7ced7709fd06c0ee5a0d86adcc51f" + integrity sha512-oklstXImtaly4vDaL+rGtX41YXZR50jp5a7CSEPMcStp1B7ozdZ5G2I5wftrDvOlOcLt/TIkGWDCr/OkVN7kWg== dependencies: - "@opentelemetry/core" "1.15.0" - tslib "^2.3.1" + "@opentelemetry/core" "1.17.0" -"@opentelemetry/propagator-jaeger@1.15.0": - version "1.15.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/propagator-jaeger/-/propagator-jaeger-1.15.0.tgz#098cfebe885f8c0f4ed3073aa9a7c0aa253086c8" - integrity sha512-OU6WNxuqjxNZoRcIBCsmvTBktAPuBUj1bh+DI+oYAvzwP2NXLavSDJWjVMGTJQDgZuR7lFijmx9EfwyAO9x37Q== +"@opentelemetry/propagator-jaeger@1.17.0": + version "1.17.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/propagator-jaeger/-/propagator-jaeger-1.17.0.tgz#a89dbc34447db0b5029b719baaa111f268b52265" + integrity sha512-iZzu8K0QkZZ16JH9yox6hZk7/Rxc4SPeGU37pvlB9DtzfNxAEX1FMK9zvowv3ve7r2uzZNpa7JGVUwpy5ewdHQ== dependencies: - "@opentelemetry/core" "1.15.0" - tslib "^2.3.1" + "@opentelemetry/core" "1.17.0" -"@opentelemetry/resources@1.14.0": - version "1.14.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/resources/-/resources-1.14.0.tgz#d6b0a4e71c2706d33c8c6ec7a7b8fea6ad27ddea" - integrity sha512-qRfWIgBxxl3z47E036Aey0Lj2ZjlFb27Q7Xnj1y1z/P293RXJZGLtcfn/w8JF7v1Q2hs3SDGxz7Wb9Dko1YUQA== +"@opentelemetry/resources@1.15.2": + version "1.15.2" + resolved "https://registry.yarnpkg.com/@opentelemetry/resources/-/resources-1.15.2.tgz#0c9e26cb65652a1402834a3c030cce6028d6dd9d" + integrity sha512-xmMRLenT9CXmm5HMbzpZ1hWhaUowQf8UB4jMjFlAxx1QzQcsD3KFNAVX/CAWzFPtllTyTplrA4JrQ7sCH3qmYw== dependencies: - "@opentelemetry/core" "1.14.0" - "@opentelemetry/semantic-conventions" "1.14.0" + "@opentelemetry/core" "1.15.2" + "@opentelemetry/semantic-conventions" "1.15.2" -"@opentelemetry/resources@1.15.0": - version "1.15.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/resources/-/resources-1.15.0.tgz#748a6ae9017636b8b30f5dee1fff3e166e51f63d" - integrity sha512-Sb8A6ZXHXDlgHv32UNRE3y8McWE3vkb5dsSttYArYa5ZpwjiF5ge0vnnKUUnG7bY0AgF9VBIOORZE8gsrnD2WA== +"@opentelemetry/resources@1.17.0": + version "1.17.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/resources/-/resources-1.17.0.tgz#ee29144cfd7d194c69698c8153dbadec7fe6819f" + integrity sha512-+u0ciVnj8lhuL/qGRBPeVYvk7fL+H/vOddfvmOeJaA1KC+5/3UED1c9KoZQlRsNT5Kw1FaK8LkY2NVLYfOVZQw== dependencies: - "@opentelemetry/core" "1.15.0" - "@opentelemetry/semantic-conventions" "1.15.0" - tslib "^2.3.1" + "@opentelemetry/core" "1.17.0" + "@opentelemetry/semantic-conventions" "1.17.0" "@opentelemetry/resources@^0.12.0": version "0.12.0" @@ -4044,63 +4010,53 @@ "@opentelemetry/core" "^0.12.0" "@opentelemetry/sdk-metrics@^1.9.1": - version "1.15.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/sdk-metrics/-/sdk-metrics-1.15.0.tgz#e47ad688882fc2daedcbbe3db16a5c110feb23e8" - integrity sha512-fFUnAcPvlXO39nlIduGuaeCuiZyFtSLCn9gW/0djFRO5DFst4m4gcT6+llXvNWuUvtGB49s56NP10B9IZRN0Rw== + version "1.17.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/sdk-metrics/-/sdk-metrics-1.17.0.tgz#e51d39e0bb749780d17f9b1df12f0490438dec1a" + integrity sha512-HlWM27yGmYuwCoVRe3yg2PqKnIsq0kEF0HQgvkeDWz2NYkq9fFaSspR6kvjxUTbghAlZrabiqbgyKoYpYaXS3w== dependencies: - "@opentelemetry/core" "1.15.0" - "@opentelemetry/resources" "1.15.0" + "@opentelemetry/core" "1.17.0" + "@opentelemetry/resources" "1.17.0" lodash.merge "^4.6.2" - tslib "^2.3.1" -"@opentelemetry/sdk-trace-base@1.14.0": - version "1.14.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/sdk-trace-base/-/sdk-trace-base-1.14.0.tgz#831af08f002228a11e577ff860eb6059c8b80fb7" - integrity sha512-NzRGt3PS+HPKfQYMb6Iy8YYc5OKA73qDwci/6ujOIvyW9vcqBJSWbjZ8FeLEAmuatUB5WrRhEKu9b0sIiIYTrQ== - dependencies: - "@opentelemetry/core" "1.14.0" - "@opentelemetry/resources" "1.14.0" - "@opentelemetry/semantic-conventions" "1.14.0" - -"@opentelemetry/sdk-trace-base@1.15.0", "@opentelemetry/sdk-trace-base@^1.15.0": - version "1.15.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/sdk-trace-base/-/sdk-trace-base-1.15.0.tgz#92340ded8f9fec1aaa63afb40c6e7e01769c2852" - integrity sha512-udt1c9VHipbZwvCPIQR1VLg25Z4AMR/g0X8KmcInbFruGWQ/lptVPkz3yvWAsGSta5yHNQ3uoPwcyCygGnQ6Lg== - dependencies: - "@opentelemetry/core" "1.15.0" - "@opentelemetry/resources" "1.15.0" - "@opentelemetry/semantic-conventions" "1.15.0" - tslib "^2.3.1" - -"@opentelemetry/sdk-trace-node@^1.15.0", "@opentelemetry/sdk-trace-node@~1.15.0": - version "1.15.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/sdk-trace-node/-/sdk-trace-node-1.15.0.tgz#2d49eafb070a6a53e8df7e91dab30ec2370ba310" - integrity sha512-TKBx9oThZUVKkoGpXhFT/XUgpjq28TWwc6j3JlsL+cJX77DKBnVC+2H+kdVVJHRzyfqDx4LEJJVCwQO3K+cbXA== - dependencies: - "@opentelemetry/context-async-hooks" "1.15.0" - "@opentelemetry/core" "1.15.0" - "@opentelemetry/propagator-b3" "1.15.0" - "@opentelemetry/propagator-jaeger" "1.15.0" - "@opentelemetry/sdk-trace-base" "1.15.0" - semver "^7.5.1" - tslib "^2.3.1" - -"@opentelemetry/semantic-conventions@1.14.0": - version "1.14.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/semantic-conventions/-/semantic-conventions-1.14.0.tgz#6a729b7f372ce30f77a3f217c09bc216f863fccb" - integrity sha512-rJfCY8rCWz3cb4KI6pEofnytvMPuj3YLQwoscCCYZ5DkdiPjo15IQ0US7+mjcWy9H3fcZIzf2pbJZ7ck/h4tug== - -"@opentelemetry/semantic-conventions@1.15.0", "@opentelemetry/semantic-conventions@^1.0.0", "@opentelemetry/semantic-conventions@~1.15.0": - version "1.15.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/semantic-conventions/-/semantic-conventions-1.15.0.tgz#e6173daa5fd61f353b02c858001388bf26e9d059" - integrity sha512-f3wwFrFyCpGrFBrFs7lCUJSCSCGyeKG52c+EKeobs3Dd29M75yO6GYkt6PkYPfDawxSlV5p+4yJPPk8tPObzTQ== - dependencies: - tslib "^2.3.1" +"@opentelemetry/sdk-trace-base@1.15.2": + version "1.15.2" + resolved "https://registry.yarnpkg.com/@opentelemetry/sdk-trace-base/-/sdk-trace-base-1.15.2.tgz#4821f94033c55a6c8bbd35ae387b715b6108517a" + integrity sha512-BEaxGZbWtvnSPchV98qqqqa96AOcb41pjgvhfzDij10tkBhIu9m0Jd6tZ1tJB5ZHfHbTffqYVYE0AOGobec/EQ== + dependencies: + "@opentelemetry/core" "1.15.2" + "@opentelemetry/resources" "1.15.2" + "@opentelemetry/semantic-conventions" "1.15.2" + +"@opentelemetry/sdk-trace-base@1.17.0", "@opentelemetry/sdk-trace-base@^1.17.0", "@opentelemetry/sdk-trace-base@~1.17.0": + version "1.17.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/sdk-trace-base/-/sdk-trace-base-1.17.0.tgz#05a21763c9efa72903c20b8930293cdde344b681" + integrity sha512-2T5HA1/1iE36Q9eg6D4zYlC4Y4GcycI1J6NsHPKZY9oWfAxWsoYnRlkPfUqyY5XVtocCo/xHpnJvGNHwzT70oQ== + dependencies: + "@opentelemetry/core" "1.17.0" + "@opentelemetry/resources" "1.17.0" + "@opentelemetry/semantic-conventions" "1.17.0" + +"@opentelemetry/sdk-trace-node@^1.17.0": + version "1.17.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/sdk-trace-node/-/sdk-trace-node-1.17.0.tgz#c2f23665e5a6878a7ad6a372dac72e7ab05c4eb5" + integrity sha512-Twlaje+t16b5j62CfcaKU869rP9oyBG/sVQWBI5+kDaWuP/YIFnF4LbovaEahK9GwAnW8vPIn6iYLAl/jZBidA== + dependencies: + "@opentelemetry/context-async-hooks" "1.17.0" + "@opentelemetry/core" "1.17.0" + "@opentelemetry/propagator-b3" "1.17.0" + "@opentelemetry/propagator-jaeger" "1.17.0" + "@opentelemetry/sdk-trace-base" "1.17.0" + semver "^7.5.2" + +"@opentelemetry/semantic-conventions@1.15.2": + version "1.15.2" + resolved "https://registry.yarnpkg.com/@opentelemetry/semantic-conventions/-/semantic-conventions-1.15.2.tgz#3bafb5de3e20e841dff6cb3c66f4d6e9694c4241" + integrity sha512-CjbOKwk2s+3xPIMcd5UNYQzsf+v94RczbdNix9/kQh38WiQkM90sUOi3if8eyHFgiBjBjhwXrA7W3ydiSQP9mw== -"@opentelemetry/semantic-conventions@1.7.0", "@opentelemetry/semantic-conventions@^1.7.0": - version "1.7.0" - resolved "https://registry.yarnpkg.com/@opentelemetry/semantic-conventions/-/semantic-conventions-1.7.0.tgz#af80a1ef7cf110ea3a68242acd95648991bcd763" - integrity sha512-FGBx/Qd09lMaqQcogCHyYrFEpTx4cAjeS+48lMIR12z7LdH+zofGDVQSubN59nL6IpubfKqTeIDu9rNO28iHVA== +"@opentelemetry/semantic-conventions@1.17.0", "@opentelemetry/semantic-conventions@^1.0.0", "@opentelemetry/semantic-conventions@^1.17.0", "@opentelemetry/semantic-conventions@~1.17.0": + version "1.17.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/semantic-conventions/-/semantic-conventions-1.17.0.tgz#af10baa9f05ce1e64a14065fc138b5739bfb65f6" + integrity sha512-+fguCd2d8d2qruk0H0DsCEy2CTK3t0Tugg7MhZ/UQMvmewbZLNnJ6heSYyzIZWG5IPfAXzoj4f4F/qpM7l4VBA== "@opentelemetry/semantic-conventions@^0.12.0": version "0.12.0" @@ -4170,14 +4126,14 @@ resolved "https://registry.yarnpkg.com/@prisma/engines-version/-/engines-version-3.15.1-1.461d6a05159055555eb7dfb337c9fb271cbd4d7e.tgz#bf5e2373ca68ce7556b967cb4965a7095e93fe53" integrity sha512-e3k2Vd606efd1ZYy2NQKkT4C/pn31nehyLhVug6To/q8JT8FpiMrDy7zmm3KLF0L98NOQQcutaVtAPhzKhzn9w== -"@prisma/instrumentation@~5.0.0": - version "5.0.0" - resolved "https://registry.yarnpkg.com/@prisma/instrumentation/-/instrumentation-5.0.0.tgz#6112461d0ffa401b9278c26d3fef027b0b42820d" - integrity sha512-GUt9ztQXriBmxPIDBd20eBHOX+LaF3zj4ot6mpMB/2YkceU4MvicdEoaX2VkF3r/xM7TatCF9IR2d35wOIv2GA== +"@prisma/instrumentation@~5.3.1": + version "5.3.1" + resolved "https://registry.yarnpkg.com/@prisma/instrumentation/-/instrumentation-5.3.1.tgz#438b8f1b8b14b190dd7bf1bbc903af4c40856648" + integrity sha512-g4epN9WdsyvX24nuoY7ie9uEsLuNUvYA2ShY9D1Ouz0STMltq1iCWAHugKXYKdKFRtoNP8Vo/QtVLQEEqvNQJQ== dependencies: "@opentelemetry/api" "1.4.1" - "@opentelemetry/instrumentation" "0.40.0" - "@opentelemetry/sdk-trace-base" "1.14.0" + "@opentelemetry/instrumentation" "0.41.2" + "@opentelemetry/sdk-trace-base" "1.15.2" "@protobufjs/aspromise@^1.1.1", "@protobufjs/aspromise@^1.1.2": version "1.1.2" @@ -5235,15 +5191,15 @@ "@types/qs" "*" "@types/range-parser" "*" -"@types/express@4.17.13": - version "4.17.13" - resolved "https://registry.yarnpkg.com/@types/express/-/express-4.17.13.tgz#a76e2995728999bab51a33fabce1d705a3709034" - integrity sha512-6bSZTPaTIACxn48l50SR+axgrqm6qXFIxrdAKaG6PaJk3+zuUr35hBlgT7vOmJcum+OEaIBLtHV/qloEAFITeA== +"@types/express-serve-static-core@^4.17.33": + version "4.17.36" + resolved "https://registry.yarnpkg.com/@types/express-serve-static-core/-/express-serve-static-core-4.17.36.tgz#baa9022119bdc05a4adfe740ffc97b5f9360e545" + integrity sha512-zbivROJ0ZqLAtMzgzIUC4oNqDG9iF0lSsAqpOD9kbs5xcIM3dTiyuHvBc7R8MtWBp3AAWGaovJa+wzWPjLYW7Q== dependencies: - "@types/body-parser" "*" - "@types/express-serve-static-core" "^4.17.18" + "@types/node" "*" "@types/qs" "*" - "@types/serve-static" "*" + "@types/range-parser" "*" + "@types/send" "*" "@types/express@4.17.14", "@types/express@^4.17.14", "@types/express@^4.17.2": version "4.17.14" @@ -5255,6 +5211,16 @@ "@types/qs" "*" "@types/serve-static" "*" +"@types/express@4.17.17": + version "4.17.17" + resolved "https://registry.yarnpkg.com/@types/express/-/express-4.17.17.tgz#01d5437f6ef9cfa8668e616e13c2f2ac9a491ae4" + integrity sha512-Q4FmmuLGBG58btUnfS1c1r/NQdlp3DMfGDGig8WhfpA2YRUtEkxAjkZb0yvplJGYdF1fsQ81iMDcH24sSCNC/Q== + dependencies: + "@types/body-parser" "*" + "@types/express-serve-static-core" "^4.17.33" + "@types/qs" "*" + "@types/serve-static" "*" + "@types/fs-extra@^5.0.5": version "5.1.0" resolved "https://registry.yarnpkg.com/@types/fs-extra/-/fs-extra-5.1.0.tgz#2a325ef97901504a3828718c390d34b8426a10a1" @@ -5419,14 +5385,7 @@ "@types/bson" "*" "@types/node" "*" -"@types/mysql@2.15.19": - version "2.15.19" - resolved "https://registry.yarnpkg.com/@types/mysql/-/mysql-2.15.19.tgz#d158927bb7c1a78f77e56de861a3b15cae0e7aed" - integrity sha512-wSRg2QZv14CWcZXkgdvHbbV2ACufNy5EgI8mBBxnJIptchv7DBy/h53VMa2jDhyo0C9MO4iowE6z9vF8Ja1DkQ== - dependencies: - "@types/node" "*" - -"@types/mysql@^2.15.21": +"@types/mysql@2.15.21", "@types/mysql@^2.15.21": version "2.15.21" resolved "https://registry.yarnpkg.com/@types/mysql/-/mysql-2.15.21.tgz#7516cba7f9d077f980100c85fd500c8210bd5e45" integrity sha512-NPotx5CVful7yB+qZbWtXL2fA4e7aEHkihHLjklc6ID8aq7bhguHgeIoC1EmSNTAuCgI6ZXrjt2ZSaXnYX0EUg== @@ -5627,6 +5586,14 @@ resolved "https://registry.yarnpkg.com/@types/semver/-/semver-7.3.13.tgz#da4bfd73f49bd541d28920ab0e2bf0ee80f71c91" integrity sha512-21cFJr9z3g5dW8B0CVI9g2O9beqaThGQ6ZFBqHfwhzLDKUxaqTIy3vnfah/UPkfOiF2pLq+tGz+W8RyCskuslw== +"@types/send@*": + version "0.17.1" + resolved "https://registry.yarnpkg.com/@types/send/-/send-0.17.1.tgz#ed4932b8a2a805f1fe362a70f4e62d0ac994e301" + integrity sha512-Cwo8LE/0rnvX7kIIa3QHCkcuF21c05Ayb0ZfxPiv0W8VRiZiNW/WuRupHKpqqGVGf7SUA44QSOUKaEd9lIrd/Q== + dependencies: + "@types/mime" "^1" + "@types/node" "*" + "@types/serve-static@*": version "1.13.9" resolved "https://registry.yarnpkg.com/@types/serve-static/-/serve-static-1.13.9.tgz#aacf28a85a05ee29a11fb7c3ead935ac56f33e4e" @@ -15109,9 +15076,9 @@ graphql-tag@^2.11.0: tslib "^2.1.0" graphql@^16.3.0: - version "16.3.0" - resolved "https://registry.yarnpkg.com/graphql/-/graphql-16.3.0.tgz#a91e24d10babf9e60c706919bb182b53ccdffc05" - integrity sha512-xm+ANmA16BzCT5pLjuXySbQVFwH3oJctUVdy81w1sV0vBU0KgDdBGtxQOUd5zqOBk/JayAFeG8Dlmeq74rjm/A== + version "16.8.1" + resolved "https://registry.yarnpkg.com/graphql/-/graphql-16.8.1.tgz#1930a965bef1170603702acdb68aedd3f3cf6f07" + integrity sha512-59LZHPdGZVh695Ud9lRzPBVTtlX9ZCV150Er2W43ro37wVof0ctenSaskPPjN7lVTIN8mSZt8PHUNKZuNQUuxw== graphviz@0.0.9: version "0.0.9" @@ -15903,23 +15870,6 @@ import-from@^2.1.0: dependencies: resolve-from "^3.0.0" -import-in-the-middle@1.3.5: - version "1.3.5" - resolved "https://registry.yarnpkg.com/import-in-the-middle/-/import-in-the-middle-1.3.5.tgz#78384fbcfc7c08faf2b1f61cb94e7dd25651df9c" - integrity sha512-yzHlBqi1EBFrkieAnSt8eTgO5oLSl+YJ7qaOpUH/PMqQOMZoQ/RmDlwnTLQrwYto+gHYjRG+i/IbsB1eDx32NQ== - dependencies: - module-details-from-path "^1.0.3" - -import-in-the-middle@1.4.1: - version "1.4.1" - resolved "https://registry.yarnpkg.com/import-in-the-middle/-/import-in-the-middle-1.4.1.tgz#31b25123bc35d556986a172bb398a3e6c32af9be" - integrity sha512-hGG0PcCsykVo8MBVH8l0uEWLWW6DXMgJA9jvC0yps6M3uIJ8L/tagTCbyF8Ud5TtqJ8/jmZL1YkyySyeVkVQrA== - dependencies: - acorn "^8.8.2" - acorn-import-assertions "^1.9.0" - cjs-module-lexer "^1.2.2" - module-details-from-path "^1.0.3" - import-in-the-middle@1.4.2: version "1.4.2" resolved "https://registry.yarnpkg.com/import-in-the-middle/-/import-in-the-middle-1.4.2.tgz#2a266676e3495e72c04bbaa5ec14756ba168391b" @@ -24266,7 +24216,7 @@ require-from-string@^2.0.2: resolved "https://registry.yarnpkg.com/require-from-string/-/require-from-string-2.0.2.tgz#89a7fdd938261267318eafe14f9c32e598c36909" integrity sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw== -require-in-the-middle@^7.1.0, require-in-the-middle@^7.1.1: +require-in-the-middle@^7.1.1: version "7.2.0" resolved "https://registry.yarnpkg.com/require-in-the-middle/-/require-in-the-middle-7.2.0.tgz#b539de8f00955444dc8aed95e17c69b0a4f10fcf" integrity sha512-3TLx5TGyAY6AOqLBoXmHkNql0HIf2RGbuMgCDT2WO/uGVAPJs6h7Kl+bN6TIZGd9bWhWPwnDnTHGtW8Iu77sdw== @@ -25049,7 +24999,7 @@ semver@7.5.3: dependencies: lru-cache "^6.0.0" -semver@7.x, semver@^7.0.0, semver@^7.1.1, semver@^7.1.3, semver@^7.2.1, semver@^7.3.2, semver@^7.3.4, semver@^7.3.5, semver@^7.3.7, semver@^7.3.8, semver@^7.5.1, semver@^7.5.3: +semver@7.x, semver@^7.0.0, semver@^7.1.1, semver@^7.1.3, semver@^7.2.1, semver@^7.3.2, semver@^7.3.4, semver@^7.3.5, semver@^7.3.7, semver@^7.3.8, semver@^7.5.1, semver@^7.5.2, semver@^7.5.3: version "7.5.4" resolved "https://registry.yarnpkg.com/semver/-/semver-7.5.4.tgz#483986ec4ed38e1c6c48c34894a9182dbff68a6e" integrity sha512-1bCSESV6Pv+i21Hvpxp3Dx+pSD8lIPt8uVjRrxAUt/nbswYc+tK6Y2btiULjd4+fnq15PX+nqQDC7Oft7WkwcA==