Skip to content

Commit 3d16a07

Browse files
authored
feat(core): Allow for nested trpc context (#15379)
As reported in https://discord.com/channels/621778831602221064/1339165240482463816/1339165240482463816 we are not capturing trpc input deeply.
1 parent 7c8f0cd commit 3d16a07

File tree

3 files changed

+23
-4
lines changed

3 files changed

+23
-4
lines changed

dev-packages/e2e-tests/test-applications/node-express/src/app.ts

+5-3
Original file line numberDiff line numberDiff line change
@@ -115,9 +115,11 @@ export const appRouter = t.router({
115115
await new Promise(resolve => setTimeout(resolve, 400));
116116
return { success: true };
117117
}),
118-
crashSomething: procedure.mutation(() => {
119-
throw new Error('I crashed in a trpc handler');
120-
}),
118+
crashSomething: procedure
119+
.input(z.object({ nested: z.object({ nested: z.object({ nested: z.string() }) }) }))
120+
.mutation(() => {
121+
throw new Error('I crashed in a trpc handler');
122+
}),
121123
dontFindSomething: procedure.mutation(() => {
122124
throw new TRPCError({ code: 'NOT_FOUND', cause: new Error('Page not found') });
123125
}),

dev-packages/e2e-tests/test-applications/node-express/tests/trpc.test.ts

+10-1
Original file line numberDiff line numberDiff line change
@@ -87,13 +87,22 @@ test('Should record transaction and error for a crashing trpc handler', async ({
8787
],
8888
});
8989

90-
await expect(trpcClient.crashSomething.mutate()).rejects.toBeDefined();
90+
await expect(trpcClient.crashSomething.mutate({ nested: { nested: { nested: 'foobar' } } })).rejects.toBeDefined();
9191

9292
await expect(transactionEventPromise).resolves.toBeDefined();
9393
await expect(errorEventPromise).resolves.toBeDefined();
9494

9595
expect((await errorEventPromise).contexts?.trpc?.['procedure_type']).toBe('mutation');
9696
expect((await errorEventPromise).contexts?.trpc?.['procedure_path']).toBe('crashSomething');
97+
98+
// Should record nested context
99+
expect((await errorEventPromise).contexts?.trpc?.['input']).toEqual({
100+
nested: {
101+
nested: {
102+
nested: 'foobar',
103+
},
104+
},
105+
});
97106
});
98107

99108
test('Should record transaction and error for a trpc handler that returns a status code', async ({ baseURL }) => {

packages/core/src/trpc.ts

+8
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@ import { getClient, withScope } from './currentScopes';
22
import { captureException } from './exports';
33
import { SEMANTIC_ATTRIBUTE_SENTRY_ORIGIN, SEMANTIC_ATTRIBUTE_SENTRY_SOURCE } from './semanticAttributes';
44
import { startSpanManual } from './tracing';
5+
import { addNonEnumerableProperty } from './utils-hoist';
56
import { normalize } from './utils-hoist/normalize';
67

78
interface SentryTrpcMiddlewareOptions {
@@ -51,6 +52,13 @@ export function trpcMiddleware(options: SentryTrpcMiddlewareOptions = {}) {
5152
procedure_type: type,
5253
};
5354

55+
addNonEnumerableProperty(
56+
trpcContext,
57+
'__sentry_override_normalization_depth__',
58+
1 + // 1 for context.input + the normal normalization depth
59+
(clientOptions?.normalizeDepth ?? 5), // 5 is a sane depth
60+
);
61+
5462
if (options.attachRpcInput !== undefined ? options.attachRpcInput : clientOptions?.sendDefaultPii) {
5563
if (rawInput !== undefined) {
5664
trpcContext.input = normalize(rawInput);

0 commit comments

Comments
 (0)