@trpc/server 9.4.0 → 9.6.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,16 +1,39 @@
1
- import { a as assertNotBrowser, g as getHTTPStatusCodeFromError, n as nodeHTTPRequestHandler } from './nodeHTTPRequestHandler-3c64002f.esm.js';
1
+ import { a as assertNotBrowser, n as nodeHTTPRequestHandler, g as getHTTPStatusCodeFromError } from './nodeHTTPRequestHandler-3c64002f.esm.js';
2
2
  export { a as assertNotBrowser, r as resolveHTTPResponse } from './nodeHTTPRequestHandler-3c64002f.esm.js';
3
+ export { S as Subscription, s as subscriptionPullFactory } from './subscription-fbda2888.esm.js';
3
4
  import { T as TRPCError, g as getErrorFromUnknown } from './transformTRPCResponse-f73dc4a2.esm.js';
4
5
  export { T as TRPCError } from './transformTRPCResponse-f73dc4a2.esm.js';
5
- import { T as TRPC_ERROR_CODES_BY_KEY } from './codes-3dd40769.esm.js';
6
- export { S as Subscription, s as subscriptionPullFactory } from './subscription-fbda2888.esm.js';
7
6
  import { createHTTPServer, createHTTPHandler } from '../adapters/standalone/dist/trpc-server-adapters-standalone.esm.js';
7
+ import { T as TRPC_ERROR_CODES_BY_KEY } from './codes-3dd40769.esm.js';
8
8
  import 'url';
9
9
  import 'events';
10
10
  import 'http';
11
11
 
12
12
  assertNotBrowser();
13
13
 
14
+ // this has been moved to separate package
15
+
16
+ /**
17
+ * @deprecated use `createHTTPServer` from `@trpc/server/adapters/standalone`
18
+ */
19
+ const createHttpServer = createHTTPServer;
20
+ /**
21
+ * @deprecated use `createHTTPHandler` from `@trpc/server/adapters/standalone`
22
+ */
23
+
24
+ const createHttpHandler = createHTTPHandler;
25
+ /**
26
+ * @deprecated use `CreateHTTPHandlerOptions` from `@trpc/server/adapters/standalone`
27
+ */
28
+
29
+ /**
30
+ * @deprecated use `nodeHTTPRequestHandler` from `@trpc/server/adapters/node-http`
31
+ */
32
+ const requestHandler = nodeHTTPRequestHandler;
33
+ /**
34
+ * @deprecated use `NodeHTTPCreateContextFn` from `@trpc/server/adapters/node-http`
35
+ */
36
+
14
37
  const middlewareMarker = /*#__PURE__*/Symbol('middlewareMarker');
15
38
 
16
39
  /**
@@ -87,21 +110,26 @@ class Procedure {
87
110
 
88
111
  async call(opts) {
89
112
  // wrap the actual resolver and treat as the last "middleware"
90
- const middlewaresWithResolver = this.middlewares.concat([async () => {
113
+ const middlewaresWithResolver = this.middlewares.concat([async ({
114
+ ctx
115
+ }) => {
91
116
  const input = this.parseInput(opts.rawInput);
92
117
  const data = await this.resolver({ ...opts,
118
+ ctx,
93
119
  input
94
120
  });
95
121
  return {
96
122
  marker: middlewareMarker,
97
123
  ok: true,
98
- data
124
+ data,
125
+ ctx
99
126
  };
100
127
  }]); // create `next()` calls in resolvers
101
128
 
102
129
  const nextFns = middlewaresWithResolver.map((fn, index) => {
103
- return async () => {
130
+ return async nextOpts => {
104
131
  const res = await wrapCallSafe(() => fn({ ...opts,
132
+ ...nextOpts,
105
133
  next: nextFns[index + 1]
106
134
  }));
107
135
 
@@ -233,6 +261,10 @@ const defaultTransformer = {
233
261
  deserialize: obj => obj
234
262
  }
235
263
  };
264
+
265
+ /**
266
+ * @internal The type signature of this class may change without warning.
267
+ */
236
268
  class Router {
237
269
  constructor(def) {
238
270
  var _def$queries, _def$mutations, _def$subscriptions, _def$middlewares, _def$errorFormatter, _def$transformer;
@@ -394,7 +426,6 @@ class Router {
394
426
  }
395
427
  /**
396
428
  * Function to be called before any procedure is invoked
397
- * Can be async or sync
398
429
  * @link https://trpc.io/docs/middlewares
399
430
  */
400
431
 
@@ -468,31 +499,15 @@ class Router {
468
499
  }
469
500
 
470
501
  }
471
- function router() {
472
- return new Router();
473
- }
474
-
475
- // this has been moved to separate package
476
-
477
- /**
478
- * @deprecated use `createHTTPServer` from `@trpc/server/adapters/standalone`
479
- */
480
- const createHttpServer = createHTTPServer;
481
- /**
482
- * @deprecated use `createHTTPHandler` from `@trpc/server/adapters/standalone`
483
- */
484
-
485
- const createHttpHandler = createHTTPHandler;
486
502
  /**
487
- * @deprecated use `CreateHTTPHandlerOptions` from `@trpc/server/adapters/standalone`
503
+ * Subclass of `VNextRouter` with `TInputContext` and `TContext` set to the same type, for backcompat.
504
+ *
505
+ * @deprecated
488
506
  */
489
507
 
490
- /**
491
- * @deprecated use `nodeHTTPRequestHandler` from `@trpc/server/adapters/node-http`
492
- */
493
- const requestHandler = nodeHTTPRequestHandler;
494
- /**
495
- * @deprecated use `NodeHTTPCreateContextFn` from `@trpc/server/adapters/node-http`
496
- */
508
+ class LegacyRouter extends Router {}
509
+ function router() {
510
+ return new Router();
511
+ }
497
512
 
498
- export { Router, createHttpHandler, createHttpServer, requestHandler, router };
513
+ export { LegacyRouter, LegacyRouter as Router, createHttpHandler, createHttpServer, requestHandler, router };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@trpc/server",
3
- "version": "9.4.0",
3
+ "version": "9.6.1",
4
4
  "description": "tRPC Server",
5
5
  "author": "KATT",
6
6
  "license": "MIT",
@@ -58,12 +58,12 @@
58
58
  "jest": "^27.1.0",
59
59
  "myzod": "^1.3.1",
60
60
  "next": "^11.1.0",
61
- "typescript": "4.4.2",
61
+ "typescript": "4.4.3",
62
62
  "ws": "^8.0.0",
63
63
  "yup": "^0.32.8",
64
64
  "zod": "^3.0.0"
65
65
  },
66
- "gitHead": "44e50cb6530999af5695d3c9301d84de593e1d00",
66
+ "gitHead": "711f122307c9441c16606add544c0810308d3f79",
67
67
  "dependencies": {
68
68
  "tslib": "^2.1.0"
69
69
  }
@@ -15,7 +15,7 @@ export type NodeHTTPCreateContextOption<
15
15
  TRouter extends AnyRouter,
16
16
  TRequest,
17
17
  TResponse,
18
- > = inferRouterContext<TRouter> extends void
18
+ > = unknown extends inferRouterContext<TRouter>
19
19
  ? {
20
20
  /**
21
21
  * @link https://trpc.io/docs/context
@@ -0,0 +1,3 @@
1
+ export * from '../router';
2
+
3
+ export { LegacyRouter as Router } from '../router';
package/src/index.ts CHANGED
@@ -1,6 +1,5 @@
1
1
  export * from './assertNotBrowser';
2
2
  export * from './http';
3
- export * from './router';
4
3
  export * from './subscription';
5
4
  export * from './transformer';
6
5
  export * from './TRPCError';
@@ -9,3 +8,4 @@ export * from './types';
9
8
  // deprecated
10
9
  export * from './deprecated/createHttpServer';
11
10
  export * from './deprecated/requestHandler';
11
+ export * from './deprecated/LegacyRouter';
@@ -2,30 +2,37 @@ import { ProcedureType } from '../router';
2
2
  import { TRPCError } from '../TRPCError';
3
3
 
4
4
  export const middlewareMarker = Symbol('middlewareMarker');
5
- interface MiddlewareResultBase {
5
+ interface MiddlewareResultBase<TContext> {
6
6
  /**
7
7
  * All middlewares should pass through their `next()`'s output.
8
8
  * Requiring this marker makes sure that can't be forgotten at compile-time.
9
9
  */
10
10
  readonly marker: typeof middlewareMarker;
11
+ ctx: TContext;
11
12
  }
12
13
 
13
- interface MiddlewareOKResult extends MiddlewareResultBase {
14
+ interface MiddlewareOKResult<TContext> extends MiddlewareResultBase<TContext> {
14
15
  ok: true;
15
16
  data: unknown;
16
17
  // this could be extended with `input`/`rawInput` later
17
18
  }
18
- interface MiddlewareErrorResult extends MiddlewareResultBase {
19
+ interface MiddlewareErrorResult<TContext>
20
+ extends MiddlewareResultBase<TContext> {
19
21
  ok: false;
20
22
  error: TRPCError;
21
23
  // we could guarantee it's always of this type
22
24
  }
23
25
 
24
- export type MiddlewareResult = MiddlewareOKResult | MiddlewareErrorResult;
26
+ export type MiddlewareResult<TContext> =
27
+ | MiddlewareOKResult<TContext>
28
+ | MiddlewareErrorResult<TContext>;
25
29
 
26
- export type MiddlewareFunction<TContext> = (opts: {
27
- ctx: TContext;
30
+ export type MiddlewareFunction<TInputContext, TContext> = (opts: {
31
+ ctx: TInputContext;
28
32
  type: ProcedureType;
29
33
  path: string;
30
- next: () => Promise<MiddlewareResult>;
31
- }) => Promise<MiddlewareResult>;
34
+ next: {
35
+ (): Promise<MiddlewareResult<TInputContext>>;
36
+ <T>(opts: { ctx: T }): Promise<MiddlewareResult<T>>;
37
+ };
38
+ }) => Promise<MiddlewareResult<TContext>>;
@@ -34,7 +34,7 @@ export type ProcedureResolver<
34
34
  }) => Promise<TOutput> | TOutput;
35
35
 
36
36
  interface ProcedureOptions<TContext, TInput, TOutput> {
37
- middlewares: MiddlewareFunction<TContext>[];
37
+ middlewares: Array<MiddlewareFunction<any, any>>;
38
38
  resolver: ProcedureResolver<TContext, TInput, TOutput>;
39
39
  inputParser: ProcedureInputParser<TInput>;
40
40
  }
@@ -72,11 +72,12 @@ function getParseFn<TInput>(
72
72
  * @internal
73
73
  */
74
74
  export abstract class Procedure<
75
- TContext = unknown,
76
- TInput = unknown,
77
- TOutput = unknown,
75
+ TInputContext, //
76
+ TContext,
77
+ TInput,
78
+ TOutput,
78
79
  > {
79
- private middlewares: Readonly<MiddlewareFunction<TContext>[]>;
80
+ private middlewares: Readonly<Array<MiddlewareFunction<any, any>>>;
80
81
  private resolver: ProcedureResolver<TContext, TInput, TOutput>;
81
82
  private readonly inputParser: ProcedureInputParser<TInput>;
82
83
  private parse: ParseFn<TInput>;
@@ -103,25 +104,32 @@ export abstract class Procedure<
103
104
  * Trigger middlewares in order, parse raw input & call resolver
104
105
  * @internal
105
106
  */
106
- public async call(opts: ProcedureCallOptions<TContext>): Promise<TOutput> {
107
+ public async call(
108
+ opts: ProcedureCallOptions<TInputContext>,
109
+ ): Promise<TOutput> {
107
110
  // wrap the actual resolver and treat as the last "middleware"
108
111
  const middlewaresWithResolver = this.middlewares.concat([
109
- async () => {
112
+ async ({ ctx }: { ctx: TContext }) => {
110
113
  const input = this.parseInput(opts.rawInput);
111
- const data = await this.resolver({ ...opts, input });
114
+ const data = await this.resolver({ ...opts, ctx, input });
112
115
  return {
113
116
  marker: middlewareMarker,
114
117
  ok: true,
115
118
  data,
116
- };
119
+ ctx,
120
+ } as const;
117
121
  },
118
122
  ]);
119
123
 
120
124
  // create `next()` calls in resolvers
121
125
  const nextFns = middlewaresWithResolver.map((fn, index) => {
122
- return async () => {
126
+ return async (nextOpts?: { ctx: TContext }) => {
123
127
  const res = await wrapCallSafe(() =>
124
- fn({ ...opts, next: nextFns[index + 1] }),
128
+ fn({
129
+ ...(opts as any),
130
+ ...(nextOpts as any),
131
+ next: nextFns[index + 1],
132
+ }),
125
133
  );
126
134
  if (res.ok) {
127
135
  return res.data;
@@ -154,9 +162,12 @@ export abstract class Procedure<
154
162
  * Create new procedure with passed middlewares
155
163
  * @param middlewares
156
164
  */
157
- public inheritMiddlewares(middlewares: MiddlewareFunction<TContext>[]): this {
165
+ public inheritMiddlewares(
166
+ middlewares: MiddlewareFunction<TInputContext, TContext>[],
167
+ ): this {
158
168
  const Constructor: {
159
169
  new (opts: ProcedureOptions<TContext, TInput, TOutput>): Procedure<
170
+ TInputContext,
160
171
  TContext,
161
172
  TInput,
162
173
  TOutput
@@ -173,17 +184,18 @@ export abstract class Procedure<
173
184
  }
174
185
  }
175
186
 
176
- export class ProcedureWithoutInput<TContext, TOutput> extends Procedure<
187
+ export class ProcedureWithoutInput<
188
+ TInputContext,
177
189
  TContext,
178
- undefined,
179
- TOutput
180
- > {}
190
+ TOutput,
191
+ > extends Procedure<TInputContext, TContext, undefined, TOutput> {}
181
192
 
182
- export class ProcedureWithInput<TContext, TInput, TOutput> extends Procedure<
193
+ export class ProcedureWithInput<
194
+ TInputContext,
183
195
  TContext,
184
196
  TInput,
185
- TOutput
186
- > {}
197
+ TOutput,
198
+ > extends Procedure<TInputContext, TContext, TInput, TOutput> {}
187
199
 
188
200
  export type CreateProcedureWithInput<TContext, TInput, TOutput> = {
189
201
  input: ProcedureInputParser<TInput>;
@@ -206,15 +218,15 @@ function isProcedureWithInput<TContext, TInput, TOutput>(
206
218
  ): opts is CreateProcedureWithInput<TContext, TInput, TOutput> {
207
219
  return !!opts.input;
208
220
  }
209
- export function createProcedure<TContext, TInput, TOutput>(
221
+ export function createProcedure<TInputContext, TContext, TInput, TOutput>(
210
222
  opts: CreateProcedureWithInput<TContext, TInput, TOutput>,
211
- ): ProcedureWithInput<TContext, TInput, TOutput>;
212
- export function createProcedure<TContext, TOutput>(
223
+ ): ProcedureWithInput<TInputContext, TContext, TInput, TOutput>;
224
+ export function createProcedure<TInputContext, TContext, TOutput>(
213
225
  opts: CreateProcedureWithoutInput<TContext, TOutput>,
214
- ): ProcedureWithoutInput<TContext, TOutput>;
215
- export function createProcedure<TContext, TInput, TOutput>(
226
+ ): ProcedureWithoutInput<TInputContext, TContext, TOutput>;
227
+ export function createProcedure<TInputContext, TContext, TInput, TOutput>(
216
228
  opts: CreateProcedureOptions<TContext, TInput, TOutput>,
217
- ): Procedure<TContext, TInput, TOutput>;
229
+ ): Procedure<TInputContext, TContext, TInput, TOutput>;
218
230
  export function createProcedure<TContext, TInput, TOutput>(
219
231
  opts: CreateProcedureOptions<TContext, TInput, TOutput>,
220
232
  ) {
@@ -241,17 +253,18 @@ export function createProcedure<TContext, TInput, TOutput>(
241
253
  }
242
254
 
243
255
  export type inferProcedureFromOptions<
256
+ TInputContext,
244
257
  TOptions extends CreateProcedureOptions<any, any, any>,
245
258
  > = TOptions extends CreateProcedureWithInput<
246
259
  infer TContext,
247
260
  infer TInput,
248
261
  infer TOutput
249
262
  >
250
- ? ProcedureWithInput<TContext, TInput, TOutput>
263
+ ? ProcedureWithInput<TInputContext, TContext, TInput, TOutput>
251
264
  : TOptions extends CreateProcedureWithoutInput<
252
265
  //
253
266
  infer TContext,
254
267
  infer TOutput
255
268
  >
256
- ? ProcedureWithoutInput<TContext, TOutput>
257
- : Procedure<unknown, unknown>;
269
+ ? ProcedureWithoutInput<TInputContext, TContext, TOutput>
270
+ : Procedure<unknown, unknown, unknown, unknown>;
package/src/router.ts CHANGED
@@ -23,7 +23,7 @@ import {
23
23
  import { Subscription } from './subscription';
24
24
  import { CombinedDataTransformer, DataTransformerOptions } from './transformer';
25
25
  import { TRPCError } from './TRPCError';
26
- import { flatten, Prefixer, ThenArg } from './types';
26
+ import { flatten, format, Prefixer, ThenArg } from './types';
27
27
 
28
28
  assertNotBrowser();
29
29
 
@@ -36,18 +36,20 @@ export type ProcedureType = 'query' | 'mutation' | 'subscription';
36
36
  * @internal
37
37
  */
38
38
  export type ProcedureRecord<
39
+ TInputContext = any,
39
40
  TContext = any,
40
41
  TInput = any,
41
42
  TOutput = any,
42
- > = Record<string, Procedure<TContext, TInput, TOutput>>;
43
+ > = Record<string, Procedure<TInputContext, TContext, TInput, TOutput>>;
43
44
 
44
45
  /**
45
46
  * @public
46
47
  */
47
- export type inferProcedureInput<TProcedure extends Procedure<any, any, any>> =
48
- TProcedure extends ProcedureWithInput<any, infer Input, any>
49
- ? Input
50
- : undefined;
48
+ export type inferProcedureInput<
49
+ TProcedure extends Procedure<any, any, any, any>,
50
+ > = TProcedure extends ProcedureWithInput<any, any, infer Input, any>
51
+ ? Input
52
+ : undefined;
51
53
 
52
54
  /**
53
55
  * @public
@@ -58,8 +60,9 @@ export type inferAsyncReturnType<TFunction extends (...args: any) => any> =
58
60
  /**
59
61
  * @public
60
62
  */
61
- export type inferProcedureOutput<TProcedure extends Procedure> =
62
- inferAsyncReturnType<TProcedure['call']>;
63
+ export type inferProcedureOutput<
64
+ TProcedure extends Procedure<any, any, any, any>,
65
+ > = inferAsyncReturnType<TProcedure['call']>;
63
66
 
64
67
  /**
65
68
  * @public
@@ -82,18 +85,18 @@ function getDataTransformer(
82
85
  }
83
86
  return { input: transformer, output: transformer };
84
87
  }
85
-
86
88
  /**
87
89
  * @internal
88
90
  */
89
- export type inferHandlerInput<TProcedure extends Procedure> =
90
- TProcedure extends ProcedureWithInput<any, infer TInput, any>
91
- ? undefined extends TInput // ? is input optional
92
- ? unknown extends TInput // ? is input unset
93
- ? [(null | undefined)?] // -> there is no input
94
- : [(TInput | null | undefined)?] // -> there is optional input
95
- : [TInput] // -> input is required
96
- : [(undefined | null)?]; // -> there is no input
91
+ export type inferHandlerInput<
92
+ TProcedure extends Procedure<any, any, any, any>,
93
+ > = TProcedure extends ProcedureWithInput<any, any, infer TInput, any>
94
+ ? undefined extends TInput // ? is input optional
95
+ ? unknown extends TInput // ? is input unset
96
+ ? [(null | undefined)?] // -> there is no input
97
+ : [(TInput | null | undefined)?] // -> there is optional input
98
+ : [TInput] // -> input is required
99
+ : [(undefined | null)?]; // -> there is no input
97
100
 
98
101
  type inferHandlerFn<TProcedures extends ProcedureRecord> = <
99
102
  TProcedure extends TProcedures[TPath],
@@ -113,7 +116,14 @@ export type inferRouterContext<TRouter extends AnyRouter> = Parameters<
113
116
  /**
114
117
  * @public
115
118
  */
116
- export type AnyRouter<TContext = any> = Router<TContext, any, any, any, any>;
119
+ export type AnyRouter<TContext = any> = Router<
120
+ any,
121
+ TContext,
122
+ any,
123
+ any,
124
+ any,
125
+ any
126
+ >;
117
127
 
118
128
  /**
119
129
  * @internal
@@ -192,11 +202,36 @@ const defaultTransformer: CombinedDataTransformer = {
192
202
  output: { serialize: (obj) => obj, deserialize: (obj) => obj },
193
203
  };
194
204
 
205
+ type SwapProcedureContext<
206
+ TProcedure extends Procedure<any, any, any, any>,
207
+ TNewContext,
208
+ > = TProcedure extends ProcedureWithInput<
209
+ infer TInputContext,
210
+ // eslint-disable-next-line @typescript-eslint/no-unused-vars
211
+ infer _TOldContext,
212
+ infer TInput,
213
+ infer TOutput
214
+ >
215
+ ? ProcedureWithInput<TInputContext, TNewContext, TInput, TOutput>
216
+ : never;
217
+
218
+ type SwapContext<
219
+ TObj extends ProcedureRecord<any, any, any, any>,
220
+ TNewContext,
221
+ > = format<{
222
+ [P in keyof TObj]: SwapProcedureContext<TObj[P], TNewContext>;
223
+ }>;
224
+
225
+ /**
226
+ * @internal The type signature of this class may change without warning.
227
+ */
195
228
  export class Router<
229
+ TInputContext,
196
230
  TContext,
197
- TQueries extends ProcedureRecord<TContext>,
198
- TMutations extends ProcedureRecord<TContext>,
231
+ TQueries extends ProcedureRecord<TInputContext, TContext>,
232
+ TMutations extends ProcedureRecord<TInputContext, TContext>,
199
233
  TSubscriptions extends ProcedureRecord<
234
+ TInputContext,
200
235
  TContext,
201
236
  unknown,
202
237
  Subscription<unknown>
@@ -207,7 +242,7 @@ export class Router<
207
242
  queries: Readonly<TQueries>;
208
243
  mutations: Readonly<TMutations>;
209
244
  subscriptions: Readonly<TSubscriptions>;
210
- middlewares: MiddlewareFunction<TContext>[];
245
+ middlewares: MiddlewareFunction<TInputContext, TContext>[];
211
246
  errorFormatter: ErrorFormatter<TContext, TErrorShape>;
212
247
  transformer: CombinedDataTransformer;
213
248
  }>;
@@ -216,7 +251,7 @@ export class Router<
216
251
  queries?: TQueries;
217
252
  mutations?: TMutations;
218
253
  subscriptions?: TSubscriptions;
219
- middlewares?: MiddlewareFunction<TContext>[];
254
+ middlewares?: MiddlewareFunction<TInputContext, TContext>[];
220
255
  errorFormatter?: ErrorFormatter<TContext, TErrorShape>;
221
256
  transformer?: CombinedDataTransformer;
222
257
  }) {
@@ -245,10 +280,11 @@ export class Router<
245
280
  path: TPath,
246
281
  procedure: CreateProcedureWithInput<TContext, TInput, TOutput>,
247
282
  ): Router<
283
+ TInputContext,
248
284
  TContext,
249
285
  flatten<
250
286
  TQueries,
251
- Record<TPath, inferProcedureFromOptions<typeof procedure>>
287
+ Record<TPath, inferProcedureFromOptions<TInputContext, typeof procedure>>
252
288
  >,
253
289
  TMutations,
254
290
  TSubscriptions,
@@ -258,10 +294,11 @@ export class Router<
258
294
  path: TPath,
259
295
  procedure: CreateProcedureWithoutInput<TContext, TOutput>,
260
296
  ): Router<
297
+ TInputContext,
261
298
  TContext,
262
299
  flatten<
263
300
  TQueries,
264
- Record<TPath, inferProcedureFromOptions<typeof procedure>>
301
+ Record<TPath, inferProcedureFromOptions<TInputContext, typeof procedure>>
265
302
  >,
266
303
  TMutations,
267
304
  TSubscriptions,
@@ -271,24 +308,25 @@ export class Router<
271
308
  path: TPath,
272
309
  procedure: CreateProcedureOptions<TContext, TInput, TOutput>,
273
310
  ) {
274
- const router = new Router<TContext, any, {}, {}, any>({
311
+ const router = new Router<TContext, TContext, any, {}, {}, any>({
275
312
  queries: safeObject({
276
313
  [path]: createProcedure(procedure),
277
314
  }),
278
315
  });
279
316
 
280
- return this.merge(router) as any;
317
+ return this.merge(router);
281
318
  }
282
319
 
283
320
  public mutation<TPath extends string, TInput, TOutput>(
284
321
  path: TPath,
285
322
  procedure: CreateProcedureWithInput<TContext, TInput, TOutput>,
286
323
  ): Router<
324
+ TInputContext,
287
325
  TContext,
288
326
  TQueries,
289
327
  flatten<
290
328
  TMutations,
291
- Record<TPath, inferProcedureFromOptions<typeof procedure>>
329
+ Record<TPath, inferProcedureFromOptions<TInputContext, typeof procedure>>
292
330
  >,
293
331
  TSubscriptions,
294
332
  TErrorShape
@@ -297,11 +335,12 @@ export class Router<
297
335
  path: TPath,
298
336
  procedure: CreateProcedureWithoutInput<TContext, TOutput>,
299
337
  ): Router<
338
+ TInputContext,
300
339
  TContext,
301
340
  TQueries,
302
341
  flatten<
303
342
  TMutations,
304
- Record<TPath, inferProcedureFromOptions<typeof procedure>>
343
+ Record<TPath, inferProcedureFromOptions<TInputContext, typeof procedure>>
305
344
  >,
306
345
  TSubscriptions,
307
346
  TErrorShape
@@ -310,13 +349,13 @@ export class Router<
310
349
  path: TPath,
311
350
  procedure: CreateProcedureOptions<TContext, TInput, TOutput>,
312
351
  ) {
313
- const router = new Router<TContext, {}, any, {}, any>({
352
+ const router = new Router<TContext, TContext, {}, any, {}, any>({
314
353
  mutations: safeObject({
315
354
  [path]: createProcedure(procedure),
316
355
  }),
317
356
  });
318
357
 
319
- return this.merge(router) as any;
358
+ return this.merge(router);
320
359
  }
321
360
  /**
322
361
  * @beta Might change without a major version bump
@@ -329,10 +368,12 @@ export class Router<
329
368
  path: TPath,
330
369
  procedure: CreateProcedureWithInput<TContext, TInput, TOutput>,
331
370
  ): Router<
371
+ TInputContext,
332
372
  TContext,
333
373
  TQueries,
334
374
  TMutations,
335
- TSubscriptions & Record<TPath, inferProcedureFromOptions<typeof procedure>>,
375
+ TSubscriptions &
376
+ Record<TPath, inferProcedureFromOptions<TInputContext, typeof procedure>>,
336
377
  TErrorShape
337
378
  >;
338
379
  /**
@@ -345,10 +386,12 @@ export class Router<
345
386
  path: TPath,
346
387
  procedure: CreateProcedureWithoutInput<TContext, TOutput>,
347
388
  ): Router<
389
+ TInputContext,
348
390
  TContext,
349
391
  TQueries,
350
392
  TMutations,
351
- TSubscriptions & Record<TPath, inferProcedureFromOptions<typeof procedure>>,
393
+ TSubscriptions &
394
+ Record<TPath, inferProcedureFromOptions<TInputContext, typeof procedure>>,
352
395
  TErrorShape
353
396
  >;
354
397
  /**
@@ -359,7 +402,7 @@ export class Router<
359
402
  TInput,
360
403
  TOutput extends Subscription<unknown>,
361
404
  >(path: TPath, procedure: CreateProcedureOptions<TContext, TInput, TOutput>) {
362
- const router = new Router<TContext, {}, {}, any, any>({
405
+ const router = new Router<TContext, TContext, {}, {}, any, any>({
363
406
  subscriptions: safeObject({
364
407
  [path]: createProcedure(procedure),
365
408
  }),
@@ -372,10 +415,11 @@ export class Router<
372
415
  * Merge router with other router
373
416
  * @param router
374
417
  */
375
- public merge<TChildRouter extends AnyRouter<TContext>>(
418
+ public merge<TChildRouter extends Router<TContext, any, any, any, any, any>>(
376
419
  router: TChildRouter,
377
420
  ): Router<
378
- TContext,
421
+ TInputContext,
422
+ inferRouterContext<TChildRouter>,
379
423
  flatten<TQueries, TChildRouter['_def']['queries']>,
380
424
  flatten<TMutations, TChildRouter['_def']['mutations']>,
381
425
  flatten<TSubscriptions, TChildRouter['_def']['subscriptions']>,
@@ -387,11 +431,15 @@ export class Router<
387
431
  * @param prefix Prefix that this router should live under
388
432
  * @param router
389
433
  */
390
- public merge<TPath extends string, TChildRouter extends AnyRouter<TContext>>(
434
+ public merge<
435
+ TPath extends string,
436
+ TChildRouter extends Router<TContext, any, any, any, any, any>,
437
+ >(
391
438
  prefix: TPath,
392
439
  router: TChildRouter,
393
440
  ): Router<
394
- TContext,
441
+ TInputContext,
442
+ inferRouterContext<TChildRouter>,
395
443
  flatten<TQueries, Prefixer<TChildRouter['_def']['queries'], `${TPath}`>>,
396
444
  flatten<
397
445
  TMutations,
@@ -437,7 +485,7 @@ export class Router<
437
485
  throw new Error(`Duplicate endpoint(s): ${duplicates.join(', ')}`);
438
486
  }
439
487
 
440
- const mergeProcedures = (defs: ProcedureRecord<any>) => {
488
+ const mergeProcedures = (defs: ProcedureRecord) => {
441
489
  const newDefs = safeObject() as typeof defs;
442
490
  for (const key in defs) {
443
491
  const procedure = defs[key];
@@ -450,7 +498,7 @@ export class Router<
450
498
  return Router.prefixProcedures(newDefs, prefix);
451
499
  };
452
500
 
453
- return new Router<TContext, any, any, any, TErrorShape>({
501
+ return new Router<TInputContext, any, any, any, any, TErrorShape>({
454
502
  ...this._def,
455
503
  queries: safeObject(
456
504
  this._def.queries,
@@ -470,11 +518,15 @@ export class Router<
470
518
  /**
471
519
  * Invoke procedure. Only for internal use within library.
472
520
  */
473
- private async call(opts: ProcedureCallOptions<TContext>): Promise<unknown> {
521
+ private async call(
522
+ opts: ProcedureCallOptions<TInputContext>,
523
+ ): Promise<unknown> {
474
524
  const { type, path } = opts;
475
525
  const defTarget = PROCEDURE_DEFINITION_MAP[type];
476
526
  const defs = this._def[defTarget];
477
- const procedure = defs[path] as Procedure<TContext> | undefined;
527
+ const procedure = defs[path] as
528
+ | Procedure<TInputContext, TContext, any, any>
529
+ | undefined;
478
530
 
479
531
  if (!procedure) {
480
532
  throw new TRPCError({
@@ -486,7 +538,7 @@ export class Router<
486
538
  return procedure.call(opts);
487
539
  }
488
540
 
489
- public createCaller(ctx: TContext): {
541
+ public createCaller(ctx: TInputContext): {
490
542
  query: inferHandlerFn<TQueries>;
491
543
  mutation: inferHandlerFn<TMutations>;
492
544
  subscription: inferHandlerFn<TSubscriptions>;
@@ -518,22 +570,25 @@ export class Router<
518
570
  },
519
571
  };
520
572
  }
573
+
521
574
  /**
522
575
  * Function to be called before any procedure is invoked
523
- * Can be async or sync
524
576
  * @link https://trpc.io/docs/middlewares
525
577
  */
526
- public middleware(middleware: MiddlewareFunction<TContext>) {
527
- return new Router<
528
- TContext,
529
- TQueries,
530
- TMutations,
531
- TSubscriptions,
532
- TErrorShape
533
- >({
578
+ public middleware<TNewContext>(
579
+ middleware: MiddlewareFunction<TContext, TNewContext>,
580
+ ): Router<
581
+ TInputContext,
582
+ TNewContext,
583
+ SwapContext<TQueries, TNewContext>,
584
+ SwapContext<TMutations, TNewContext>,
585
+ SwapContext<TSubscriptions, TNewContext>,
586
+ TErrorShape
587
+ > {
588
+ return new Router({
534
589
  ...this._def,
535
- middlewares: [...this._def.middlewares, middleware],
536
- });
590
+ middlewares: [...this._def.middlewares, middleware as any],
591
+ } as any);
537
592
  }
538
593
 
539
594
  /**
@@ -548,8 +603,14 @@ export class Router<
548
603
  'You seem to have double `formatError()`-calls in your router tree',
549
604
  );
550
605
  }
551
- type TShape = ReturnType<TErrorFormatter>;
552
- return new Router<TContext, TQueries, TMutations, TSubscriptions, TShape>({
606
+ return new Router<
607
+ TInputContext,
608
+ TContext,
609
+ TQueries,
610
+ TMutations,
611
+ TSubscriptions,
612
+ ReturnType<TErrorFormatter>
613
+ >({
553
614
  ...this._def,
554
615
  errorFormatter: errorFormatter as any,
555
616
  });
@@ -597,6 +658,7 @@ export class Router<
597
658
  );
598
659
  }
599
660
  return new Router<
661
+ TInputContext,
600
662
  TContext,
601
663
  TQueries,
602
664
  TMutations,
@@ -609,6 +671,31 @@ export class Router<
609
671
  }
610
672
  }
611
673
 
612
- export function router<TContext = void>() {
613
- return new Router<TContext, {}, {}, {}, DefaultErrorShape>();
674
+ /**
675
+ * Subclass of `VNextRouter` with `TInputContext` and `TContext` set to the same type, for backcompat.
676
+ *
677
+ * @deprecated
678
+ */
679
+ export class LegacyRouter<
680
+ TContext,
681
+ TQueries extends ProcedureRecord<TContext, TContext>,
682
+ TMutations extends ProcedureRecord<TContext, TContext>,
683
+ TSubscriptions extends ProcedureRecord<
684
+ TContext,
685
+ TContext,
686
+ unknown,
687
+ Subscription<unknown>
688
+ >,
689
+ TErrorShape extends TRPCErrorShape<number>,
690
+ > extends Router<
691
+ TContext,
692
+ TContext,
693
+ TQueries,
694
+ TMutations,
695
+ TSubscriptions,
696
+ TErrorShape
697
+ > {}
698
+
699
+ export function router<TContext>() {
700
+ return new Router<TContext, TContext, {}, {}, {}, DefaultErrorShape>();
614
701
  }