diff --git a/packages/astro/src/index.server.ts b/packages/astro/src/index.server.ts index e6beabd06e0e..a200ca559f7a 100644 --- a/packages/astro/src/index.server.ts +++ b/packages/astro/src/index.server.ts @@ -87,6 +87,7 @@ export { hapiIntegration, setupHapiErrorHandler, spotlightIntegration, + addOpenTelemetryInstrumentation, } from '@sentry/node'; // We can still leave this for the carrier init and type exports diff --git a/packages/aws-serverless/src/index.ts b/packages/aws-serverless/src/index.ts index 4aef54724236..07cc52b2467a 100644 --- a/packages/aws-serverless/src/index.ts +++ b/packages/aws-serverless/src/index.ts @@ -96,6 +96,7 @@ export { spanToJSON, spanToTraceHeader, trpcMiddleware, + addOpenTelemetryInstrumentation, } from '@sentry/node'; export { diff --git a/packages/bun/src/index.ts b/packages/bun/src/index.ts index 5bfd889e2b3c..329af504f73f 100644 --- a/packages/bun/src/index.ts +++ b/packages/bun/src/index.ts @@ -117,6 +117,7 @@ export { spanToJSON, spanToTraceHeader, trpcMiddleware, + addOpenTelemetryInstrumentation, } from '@sentry/node'; export { diff --git a/packages/google-cloud-serverless/src/index.ts b/packages/google-cloud-serverless/src/index.ts index a2e9653f8a72..0bfd796bb297 100644 --- a/packages/google-cloud-serverless/src/index.ts +++ b/packages/google-cloud-serverless/src/index.ts @@ -96,6 +96,7 @@ export { spanToJSON, spanToTraceHeader, trpcMiddleware, + addOpenTelemetryInstrumentation, } from '@sentry/node'; export { diff --git a/packages/node/src/index.ts b/packages/node/src/index.ts index ac89b8c5b1ca..a44561e969c9 100644 --- a/packages/node/src/index.ts +++ b/packages/node/src/index.ts @@ -39,6 +39,7 @@ export type { NodeOptions } from './types'; export { addRequestDataToEvent, DEFAULT_USER_INCLUDES, extractRequestData } from '@sentry/utils'; export { + addOpenTelemetryInstrumentation, // These are custom variants that need to be used instead of the core one // As they have slightly different implementations continueTrace, diff --git a/packages/node/src/integrations/http.ts b/packages/node/src/integrations/http.ts index 89aa8d90b997..d2d6b2149f9e 100644 --- a/packages/node/src/integrations/http.ts +++ b/packages/node/src/integrations/http.ts @@ -1,8 +1,8 @@ import type { ClientRequest, IncomingMessage, ServerResponse } from 'http'; import type { Span } from '@opentelemetry/api'; import { SpanKind } from '@opentelemetry/api'; -import { registerInstrumentations } from '@opentelemetry/instrumentation'; import { HttpInstrumentation } from '@opentelemetry/instrumentation-http'; +import { addOpenTelemetryInstrumentation } from '@sentry/opentelemetry'; import { addBreadcrumb, @@ -52,7 +52,7 @@ const _httpIntegration = ((options: HttpOptions = {}) => { return { name: 'Http', setupOnce() { - const instrumentations = [ + addOpenTelemetryInstrumentation( new HttpInstrumentation({ ignoreOutgoingRequestHook: request => { const url = getRequestUrl(request); @@ -141,11 +141,7 @@ const _httpIntegration = ((options: HttpOptions = {}) => { } }, }), - ]; - - registerInstrumentations({ - instrumentations, - }); + ); }, }; }) satisfies IntegrationFn; diff --git a/packages/node/src/integrations/node-fetch.ts b/packages/node/src/integrations/node-fetch.ts index 6379b7f04a53..6ade560a4835 100644 --- a/packages/node/src/integrations/node-fetch.ts +++ b/packages/node/src/integrations/node-fetch.ts @@ -1,14 +1,15 @@ import type { Span } from '@opentelemetry/api'; import { SpanKind } from '@opentelemetry/api'; -import type { Instrumentation } from '@opentelemetry/instrumentation'; -import { registerInstrumentations } from '@opentelemetry/instrumentation'; import { addBreadcrumb, defineIntegration } from '@sentry/core'; +import { addOpenTelemetryInstrumentation } from '@sentry/opentelemetry'; import { getRequestSpanData, getSpanKind } from '@sentry/opentelemetry'; import type { IntegrationFn } from '@sentry/types'; import { logger } from '@sentry/utils'; import { DEBUG_BUILD } from '../debug-build'; import { NODE_MAJOR } from '../nodeVersion'; +import type { FetchInstrumentation } from 'opentelemetry-instrumentation-fetch-node'; + import { addOriginToSpan } from '../utils/addOriginToSpan'; interface NodeFetchOptions { @@ -29,7 +30,7 @@ const _nativeNodeFetchIntegration = ((options: NodeFetchOptions = {}) => { const _breadcrumbs = typeof options.breadcrumbs === 'undefined' ? true : options.breadcrumbs; const _ignoreOutgoingRequests = options.ignoreOutgoingRequests; - async function getInstrumentation(): Promise<[Instrumentation] | void> { + async function getInstrumentation(): Promise { // Only add NodeFetch if Node >= 18, as previous versions do not support it if (NODE_MAJOR < 18) { DEBUG_BUILD && logger.log('NodeFetch is not supported on Node < 18, skipping instrumentation...'); @@ -38,22 +39,20 @@ const _nativeNodeFetchIntegration = ((options: NodeFetchOptions = {}) => { try { const pkg = await import('opentelemetry-instrumentation-fetch-node'); - return [ - new pkg.FetchInstrumentation({ - ignoreRequestHook: (request: { origin?: string }) => { - const url = request.origin; - return _ignoreOutgoingRequests && url && _ignoreOutgoingRequests(url); - }, - onRequest: ({ span }: { span: Span }) => { - _updateSpan(span); + return new pkg.FetchInstrumentation({ + ignoreRequestHook: (request: { origin?: string }) => { + const url = request.origin; + return _ignoreOutgoingRequests && url && _ignoreOutgoingRequests(url); + }, + onRequest: ({ span }: { span: Span }) => { + _updateSpan(span); - if (_breadcrumbs) { - _addRequestBreadcrumb(span); - } - }, - // eslint-disable-next-line @typescript-eslint/no-explicit-any - } as any), - ]; + if (_breadcrumbs) { + _addRequestBreadcrumb(span); + } + }, + // eslint-disable-next-line @typescript-eslint/no-explicit-any + } as any); } catch (error) { // Could not load instrumentation DEBUG_BUILD && logger.log('Could not load NodeFetch instrumentation.'); @@ -64,11 +63,9 @@ const _nativeNodeFetchIntegration = ((options: NodeFetchOptions = {}) => { name: 'NodeFetch', setupOnce() { // eslint-disable-next-line @typescript-eslint/no-floating-promises - getInstrumentation().then(instrumentations => { - if (instrumentations) { - registerInstrumentations({ - instrumentations, - }); + getInstrumentation().then(instrumentation => { + if (instrumentation) { + addOpenTelemetryInstrumentation(instrumentation); } }); }, diff --git a/packages/node/src/integrations/tracing/connect.ts b/packages/node/src/integrations/tracing/connect.ts index 7214321be42a..7a65f655679b 100644 --- a/packages/node/src/integrations/tracing/connect.ts +++ b/packages/node/src/integrations/tracing/connect.ts @@ -1,9 +1,10 @@ -import { registerInstrumentations } from '@opentelemetry/instrumentation'; import { ConnectInstrumentation } from '@opentelemetry/instrumentation-connect'; import { captureException, defineIntegration } from '@sentry/core'; +import { addOpenTelemetryInstrumentation } from '@sentry/opentelemetry'; import type { IntegrationFn } from '@sentry/types'; type ConnectApp = { + // eslint-disable-next-line @typescript-eslint/no-explicit-any use: (middleware: any) => void; }; @@ -11,15 +12,14 @@ const _connectIntegration = (() => { return { name: 'Connect', setupOnce() { - registerInstrumentations({ - instrumentations: [new ConnectInstrumentation({})], - }); + addOpenTelemetryInstrumentation(new ConnectInstrumentation({})); }, }; }) satisfies IntegrationFn; export const connectIntegration = defineIntegration(_connectIntegration); +// eslint-disable-next-line @typescript-eslint/no-explicit-any function connectErrorMiddleware(err: any, req: any, res: any, next: any): void { captureException(err); next(err); diff --git a/packages/node/src/integrations/tracing/express.ts b/packages/node/src/integrations/tracing/express.ts index 8d430b939c41..8f0e93771403 100644 --- a/packages/node/src/integrations/tracing/express.ts +++ b/packages/node/src/integrations/tracing/express.ts @@ -1,8 +1,8 @@ import type * as http from 'http'; -import { registerInstrumentations } from '@opentelemetry/instrumentation'; import { ExpressInstrumentation } from '@opentelemetry/instrumentation-express'; import { defineIntegration, getDefaultIsolationScope } from '@sentry/core'; import { captureException, getClient, getIsolationScope } from '@sentry/core'; +import { addOpenTelemetryInstrumentation } from '@sentry/opentelemetry'; import type { IntegrationFn } from '@sentry/types'; import { logger } from '@sentry/utils'; @@ -14,29 +14,27 @@ const _expressIntegration = (() => { return { name: 'Express', setupOnce() { - registerInstrumentations({ - instrumentations: [ - new ExpressInstrumentation({ - requestHook(span) { - addOriginToSpan(span, 'auto.http.otel.express'); - }, - spanNameHook(info, defaultName) { - if (getIsolationScope() === getDefaultIsolationScope()) { - DEBUG_BUILD && - logger.warn('Isolation scope is still default isolation scope - skipping setting transactionName'); - return defaultName; - } - if (info.layerType === 'request_handler') { - // type cast b/c Otel unfortunately types info.request as any :( - const req = info.request as { method?: string }; - const method = req.method ? req.method.toUpperCase() : 'GET'; - getIsolationScope().setTransactionName(`${method} ${info.route}`); - } + addOpenTelemetryInstrumentation( + new ExpressInstrumentation({ + requestHook(span) { + addOriginToSpan(span, 'auto.http.otel.express'); + }, + spanNameHook(info, defaultName) { + if (getIsolationScope() === getDefaultIsolationScope()) { + DEBUG_BUILD && + logger.warn('Isolation scope is still default isolation scope - skipping setting transactionName'); return defaultName; - }, - }), - ], - }); + } + if (info.layerType === 'request_handler') { + // type cast b/c Otel unfortunately types info.request as any :( + const req = info.request as { method?: string }; + const method = req.method ? req.method.toUpperCase() : 'GET'; + getIsolationScope().setTransactionName(`${method} ${info.route}`); + } + return defaultName; + }, + }), + ); }, }; }) satisfies IntegrationFn; diff --git a/packages/node/src/integrations/tracing/fastify.ts b/packages/node/src/integrations/tracing/fastify.ts index aa2b2f275525..59622d826aaa 100644 --- a/packages/node/src/integrations/tracing/fastify.ts +++ b/packages/node/src/integrations/tracing/fastify.ts @@ -1,6 +1,6 @@ -import { registerInstrumentations } from '@opentelemetry/instrumentation'; import { FastifyInstrumentation } from '@opentelemetry/instrumentation-fastify'; import { captureException, defineIntegration, getIsolationScope } from '@sentry/core'; +import { addOpenTelemetryInstrumentation } from '@sentry/opentelemetry'; import type { IntegrationFn } from '@sentry/types'; import { addOriginToSpan } from '../../utils/addOriginToSpan'; @@ -9,15 +9,13 @@ const _fastifyIntegration = (() => { return { name: 'Fastify', setupOnce() { - registerInstrumentations({ - instrumentations: [ - new FastifyInstrumentation({ - requestHook(span) { - addOriginToSpan(span, 'auto.http.otel.fastify'); - }, - }), - ], - }); + addOpenTelemetryInstrumentation( + new FastifyInstrumentation({ + requestHook(span) { + addOriginToSpan(span, 'auto.http.otel.fastify'); + }, + }), + ); }, }; }) satisfies IntegrationFn; diff --git a/packages/node/src/integrations/tracing/graphql.ts b/packages/node/src/integrations/tracing/graphql.ts index a91524ece6bb..498da6c35cb2 100644 --- a/packages/node/src/integrations/tracing/graphql.ts +++ b/packages/node/src/integrations/tracing/graphql.ts @@ -1,6 +1,6 @@ -import { registerInstrumentations } from '@opentelemetry/instrumentation'; import { GraphQLInstrumentation } from '@opentelemetry/instrumentation-graphql'; import { defineIntegration } from '@sentry/core'; +import { addOpenTelemetryInstrumentation } from '@sentry/opentelemetry'; import type { IntegrationFn } from '@sentry/types'; import { addOriginToSpan } from '../../utils/addOriginToSpan'; @@ -9,16 +9,14 @@ const _graphqlIntegration = (() => { return { name: 'Graphql', setupOnce() { - registerInstrumentations({ - instrumentations: [ - new GraphQLInstrumentation({ - ignoreTrivialResolveSpans: true, - responseHook(span) { - addOriginToSpan(span, 'auto.graphql.otel.graphql'); - }, - }), - ], - }); + addOpenTelemetryInstrumentation( + new GraphQLInstrumentation({ + ignoreTrivialResolveSpans: true, + responseHook(span) { + addOriginToSpan(span, 'auto.graphql.otel.graphql'); + }, + }), + ); }, }; }) satisfies IntegrationFn; diff --git a/packages/node/src/integrations/tracing/hapi/index.ts b/packages/node/src/integrations/tracing/hapi/index.ts index c605a6cbd551..e87ff70a0412 100644 --- a/packages/node/src/integrations/tracing/hapi/index.ts +++ b/packages/node/src/integrations/tracing/hapi/index.ts @@ -1,4 +1,3 @@ -import { registerInstrumentations } from '@opentelemetry/instrumentation'; import { HapiInstrumentation } from '@opentelemetry/instrumentation-hapi'; import { SDK_VERSION, @@ -10,6 +9,7 @@ import { getIsolationScope, getRootSpan, } from '@sentry/core'; +import { addOpenTelemetryInstrumentation } from '@sentry/opentelemetry'; import type { IntegrationFn } from '@sentry/types'; import { logger } from '@sentry/utils'; import { DEBUG_BUILD } from '../../../debug-build'; @@ -19,9 +19,7 @@ const _hapiIntegration = (() => { return { name: 'Hapi', setupOnce() { - registerInstrumentations({ - instrumentations: [new HapiInstrumentation()], - }); + addOpenTelemetryInstrumentation(new HapiInstrumentation()); }, }; }) satisfies IntegrationFn; diff --git a/packages/node/src/integrations/tracing/koa.ts b/packages/node/src/integrations/tracing/koa.ts index 7ebb9de48d15..04c2991ba7dc 100644 --- a/packages/node/src/integrations/tracing/koa.ts +++ b/packages/node/src/integrations/tracing/koa.ts @@ -1,4 +1,3 @@ -import { registerInstrumentations } from '@opentelemetry/instrumentation'; import { KoaInstrumentation } from '@opentelemetry/instrumentation-koa'; import { SEMATTRS_HTTP_ROUTE } from '@opentelemetry/semantic-conventions'; import { @@ -8,6 +7,7 @@ import { getIsolationScope, spanToJSON, } from '@sentry/core'; +import { addOpenTelemetryInstrumentation } from '@sentry/opentelemetry'; import type { IntegrationFn } from '@sentry/types'; import { logger } from '@sentry/utils'; import { DEBUG_BUILD } from '../../debug-build'; @@ -16,31 +16,30 @@ const _koaIntegration = (() => { return { name: 'Koa', setupOnce() { - registerInstrumentations({ - instrumentations: [ - new KoaInstrumentation({ - requestHook(span, info) { - if (getIsolationScope() === getDefaultIsolationScope()) { - DEBUG_BUILD && - logger.warn('Isolation scope is default isolation scope - skipping setting transactionName'); - return; - } - const attributes = spanToJSON(span).data; - const route = attributes && attributes[SEMATTRS_HTTP_ROUTE]; - const method = info.context.request.method.toUpperCase() || 'GET'; - if (route) { - getIsolationScope().setTransactionName(`${method} ${route}`); - } - }, - }), - ], - }); + addOpenTelemetryInstrumentation( + new KoaInstrumentation({ + requestHook(span, info) { + if (getIsolationScope() === getDefaultIsolationScope()) { + DEBUG_BUILD && + logger.warn('Isolation scope is default isolation scope - skipping setting transactionName'); + return; + } + const attributes = spanToJSON(span).data; + const route = attributes && attributes[SEMATTRS_HTTP_ROUTE]; + const method = info.context.request.method.toUpperCase() || 'GET'; + if (route) { + getIsolationScope().setTransactionName(`${method} ${route}`); + } + }, + }), + ); }, }; }) satisfies IntegrationFn; export const koaIntegration = defineIntegration(_koaIntegration); +// eslint-disable-next-line @typescript-eslint/no-explicit-any export const setupKoaErrorHandler = (app: { use: (arg0: (ctx: any, next: any) => Promise) => void }): void => { app.use(async (ctx, next) => { try { diff --git a/packages/node/src/integrations/tracing/mongo.ts b/packages/node/src/integrations/tracing/mongo.ts index 9bbfd16a9581..03442df058a6 100644 --- a/packages/node/src/integrations/tracing/mongo.ts +++ b/packages/node/src/integrations/tracing/mongo.ts @@ -1,6 +1,6 @@ -import { registerInstrumentations } from '@opentelemetry/instrumentation'; import { MongoDBInstrumentation } from '@opentelemetry/instrumentation-mongodb'; import { defineIntegration } from '@sentry/core'; +import { addOpenTelemetryInstrumentation } from '@sentry/opentelemetry'; import type { IntegrationFn } from '@sentry/types'; import { addOriginToSpan } from '../../utils/addOriginToSpan'; @@ -9,15 +9,13 @@ const _mongoIntegration = (() => { return { name: 'Mongo', setupOnce() { - registerInstrumentations({ - instrumentations: [ - new MongoDBInstrumentation({ - responseHook(span) { - addOriginToSpan(span, 'auto.db.otel.mongo'); - }, - }), - ], - }); + addOpenTelemetryInstrumentation( + new MongoDBInstrumentation({ + responseHook(span) { + addOriginToSpan(span, 'auto.db.otel.mongo'); + }, + }), + ); }, }; }) satisfies IntegrationFn; diff --git a/packages/node/src/integrations/tracing/mongoose.ts b/packages/node/src/integrations/tracing/mongoose.ts index ba15fc647907..13a11ca46937 100644 --- a/packages/node/src/integrations/tracing/mongoose.ts +++ b/packages/node/src/integrations/tracing/mongoose.ts @@ -1,6 +1,6 @@ -import { registerInstrumentations } from '@opentelemetry/instrumentation'; import { MongooseInstrumentation } from '@opentelemetry/instrumentation-mongoose'; import { defineIntegration } from '@sentry/core'; +import { addOpenTelemetryInstrumentation } from '@sentry/opentelemetry'; import type { IntegrationFn } from '@sentry/types'; import { addOriginToSpan } from '../../utils/addOriginToSpan'; @@ -9,15 +9,13 @@ const _mongooseIntegration = (() => { return { name: 'Mongoose', setupOnce() { - registerInstrumentations({ - instrumentations: [ - new MongooseInstrumentation({ - responseHook(span) { - addOriginToSpan(span, 'auto.db.otel.mongoose'); - }, - }), - ], - }); + addOpenTelemetryInstrumentation( + new MongooseInstrumentation({ + responseHook(span) { + addOriginToSpan(span, 'auto.db.otel.mongoose'); + }, + }), + ); }, }; }) satisfies IntegrationFn; diff --git a/packages/node/src/integrations/tracing/mysql.ts b/packages/node/src/integrations/tracing/mysql.ts index 4f6123c7eed9..4ad0daca2a8b 100644 --- a/packages/node/src/integrations/tracing/mysql.ts +++ b/packages/node/src/integrations/tracing/mysql.ts @@ -1,15 +1,13 @@ -import { registerInstrumentations } from '@opentelemetry/instrumentation'; import { MySQLInstrumentation } from '@opentelemetry/instrumentation-mysql'; import { defineIntegration } from '@sentry/core'; +import { addOpenTelemetryInstrumentation } from '@sentry/opentelemetry'; import type { IntegrationFn } from '@sentry/types'; const _mysqlIntegration = (() => { return { name: 'Mysql', setupOnce() { - registerInstrumentations({ - instrumentations: [new MySQLInstrumentation({})], - }); + addOpenTelemetryInstrumentation(new MySQLInstrumentation({})); }, }; }) satisfies IntegrationFn; diff --git a/packages/node/src/integrations/tracing/mysql2.ts b/packages/node/src/integrations/tracing/mysql2.ts index 14a9e826c332..332560c1d5a1 100644 --- a/packages/node/src/integrations/tracing/mysql2.ts +++ b/packages/node/src/integrations/tracing/mysql2.ts @@ -1,6 +1,6 @@ -import { registerInstrumentations } from '@opentelemetry/instrumentation'; import { MySQL2Instrumentation } from '@opentelemetry/instrumentation-mysql2'; import { defineIntegration } from '@sentry/core'; +import { addOpenTelemetryInstrumentation } from '@sentry/opentelemetry'; import type { IntegrationFn } from '@sentry/types'; import { addOriginToSpan } from '../../utils/addOriginToSpan'; @@ -9,15 +9,13 @@ const _mysql2Integration = (() => { return { name: 'Mysql2', setupOnce() { - registerInstrumentations({ - instrumentations: [ - new MySQL2Instrumentation({ - responseHook(span) { - addOriginToSpan(span, 'auto.db.otel.mysql2'); - }, - }), - ], - }); + addOpenTelemetryInstrumentation( + new MySQL2Instrumentation({ + responseHook(span) { + addOriginToSpan(span, 'auto.db.otel.mysql2'); + }, + }), + ); }, }; }) satisfies IntegrationFn; diff --git a/packages/node/src/integrations/tracing/nest.ts b/packages/node/src/integrations/tracing/nest.ts index 2371c4e93e35..b0b143774d2d 100644 --- a/packages/node/src/integrations/tracing/nest.ts +++ b/packages/node/src/integrations/tracing/nest.ts @@ -1,6 +1,6 @@ -import { registerInstrumentations } from '@opentelemetry/instrumentation'; import { NestInstrumentation } from '@opentelemetry/instrumentation-nestjs-core'; import { captureException, defineIntegration, getDefaultIsolationScope, getIsolationScope } from '@sentry/core'; +import { addOpenTelemetryInstrumentation } from '@sentry/opentelemetry'; import type { IntegrationFn } from '@sentry/types'; import { logger } from '@sentry/utils'; @@ -28,9 +28,7 @@ const _nestIntegration = (() => { return { name: 'Nest', setupOnce() { - registerInstrumentations({ - instrumentations: [new NestInstrumentation({})], - }); + addOpenTelemetryInstrumentation(new NestInstrumentation({})); }, }; }) satisfies IntegrationFn; diff --git a/packages/node/src/integrations/tracing/postgres.ts b/packages/node/src/integrations/tracing/postgres.ts index e57df5b52d21..ad662d123845 100644 --- a/packages/node/src/integrations/tracing/postgres.ts +++ b/packages/node/src/integrations/tracing/postgres.ts @@ -1,6 +1,6 @@ -import { registerInstrumentations } from '@opentelemetry/instrumentation'; import { PgInstrumentation } from '@opentelemetry/instrumentation-pg'; import { defineIntegration } from '@sentry/core'; +import { addOpenTelemetryInstrumentation } from '@sentry/opentelemetry'; import type { IntegrationFn } from '@sentry/types'; import { addOriginToSpan } from '../../utils/addOriginToSpan'; @@ -9,16 +9,14 @@ const _postgresIntegration = (() => { return { name: 'Postgres', setupOnce() { - registerInstrumentations({ - instrumentations: [ - new PgInstrumentation({ - requireParentSpan: true, - requestHook(span) { - addOriginToSpan(span, 'auto.db.otel.postgres'); - }, - }), - ], - }); + addOpenTelemetryInstrumentation( + new PgInstrumentation({ + requireParentSpan: true, + requestHook(span) { + addOriginToSpan(span, 'auto.db.otel.postgres'); + }, + }), + ); }, }; }) satisfies IntegrationFn; diff --git a/packages/node/src/integrations/tracing/prisma.ts b/packages/node/src/integrations/tracing/prisma.ts index e261e95b9196..13e51065dce8 100644 --- a/packages/node/src/integrations/tracing/prisma.ts +++ b/packages/node/src/integrations/tracing/prisma.ts @@ -1,19 +1,17 @@ -import { registerInstrumentations } from '@opentelemetry/instrumentation'; // When importing CJS modules into an ESM module, we cannot import the named exports directly. import * as prismaInstrumentation from '@prisma/instrumentation'; import { defineIntegration } from '@sentry/core'; +import { addOpenTelemetryInstrumentation } from '@sentry/opentelemetry'; import type { IntegrationFn } from '@sentry/types'; const _prismaIntegration = (() => { return { name: 'Prisma', setupOnce() { - registerInstrumentations({ - instrumentations: [ - // does not have a hook to adjust spans & add origin - new prismaInstrumentation.PrismaInstrumentation({}), - ], - }); + addOpenTelemetryInstrumentation( + // does not have a hook to adjust spans & add origin + new prismaInstrumentation.PrismaInstrumentation({}), + ); }, }; }) satisfies IntegrationFn; diff --git a/packages/opentelemetry/package.json b/packages/opentelemetry/package.json index 511158000e67..b037b7fbc8d5 100644 --- a/packages/opentelemetry/package.json +++ b/packages/opentelemetry/package.json @@ -49,6 +49,7 @@ "peerDependencies": { "@opentelemetry/api": "^1.8.0", "@opentelemetry/core": "^1.23.0", + "@opentelemetry/instrumentation": "0.48.0", "@opentelemetry/sdk-trace-base": "^1.23.0", "@opentelemetry/semantic-conventions": "^1.23.0" }, diff --git a/packages/opentelemetry/src/index.ts b/packages/opentelemetry/src/index.ts index db5abb951f4c..e5eee90c623f 100644 --- a/packages/opentelemetry/src/index.ts +++ b/packages/opentelemetry/src/index.ts @@ -39,5 +39,7 @@ export { SentrySampler } from './sampler'; export { openTelemetrySetupCheck } from './utils/setupCheck'; +export { addOpenTelemetryInstrumentation } from './instrumentation'; + // Legacy export { getClient } from '@sentry/core'; diff --git a/packages/opentelemetry/src/instrumentation.ts b/packages/opentelemetry/src/instrumentation.ts new file mode 100644 index 000000000000..324eb6e523c8 --- /dev/null +++ b/packages/opentelemetry/src/instrumentation.ts @@ -0,0 +1,14 @@ +import type { InstrumentationOption } from '@opentelemetry/instrumentation'; +import { registerInstrumentations } from '@opentelemetry/instrumentation'; + +/** + * This method takes an OpenTelemetry instrumentation or + * array of instrumentations and registers them with OpenTelemetry. + */ +export function addOpenTelemetryInstrumentation( + instrumentation: InstrumentationOption | InstrumentationOption[], +): void { + registerInstrumentations({ + instrumentations: Array.isArray(instrumentation) ? instrumentation : [instrumentation], + }); +} diff --git a/packages/remix/src/index.server.ts b/packages/remix/src/index.server.ts index 219d642457e5..28a2c1b37e0d 100644 --- a/packages/remix/src/index.server.ts +++ b/packages/remix/src/index.server.ts @@ -97,6 +97,7 @@ export { trpcMiddleware, spanToJSON, spanToTraceHeader, + addOpenTelemetryInstrumentation, } from '@sentry/node'; // Keeping the `*` exports for backwards compatibility and types diff --git a/packages/sveltekit/src/server/index.ts b/packages/sveltekit/src/server/index.ts index e37efc7d9737..9a6c22b2dfe2 100644 --- a/packages/sveltekit/src/server/index.ts +++ b/packages/sveltekit/src/server/index.ts @@ -71,6 +71,7 @@ export { trpcMiddleware, spanToJSON, spanToTraceHeader, + addOpenTelemetryInstrumentation, } from '@sentry/node'; // We can still leave this for the carrier init and type exports