@trpc/server 11.0.0-alpha-tmp-app-router-example.388 → 11.0.0-alpha-tmp-issues-5851-take-two.451

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (139) hide show
  1. package/dist/@trpc/server/http.d.ts +1 -2
  2. package/dist/@trpc/server/http.d.ts.map +1 -1
  3. package/dist/@trpc/server/index.d.ts +1 -1
  4. package/dist/@trpc/server/index.d.ts.map +1 -1
  5. package/dist/@trpc/server/rpc.d.ts +1 -1
  6. package/dist/@trpc/server/rpc.d.ts.map +1 -1
  7. package/dist/adapters/aws-lambda/getPlanner.d.ts.map +1 -1
  8. package/dist/adapters/aws-lambda/getPlanner.js +19 -2
  9. package/dist/adapters/aws-lambda/getPlanner.mjs +19 -2
  10. package/dist/adapters/next-app-dir/nextAppDirCaller.d.ts.map +1 -1
  11. package/dist/adapters/next-app-dir/nextAppDirCaller.js +1 -1
  12. package/dist/adapters/next-app-dir/nextAppDirCaller.mjs +1 -1
  13. package/dist/adapters/next-app-dir/redirect.d.ts.map +1 -1
  14. package/dist/adapters/next.js +1 -1
  15. package/dist/adapters/next.mjs +1 -1
  16. package/dist/adapters/node-http/incomingMessageToRequest.d.ts +0 -1
  17. package/dist/adapters/node-http/incomingMessageToRequest.d.ts.map +1 -1
  18. package/dist/adapters/node-http/incomingMessageToRequest.js +3 -1
  19. package/dist/adapters/node-http/incomingMessageToRequest.mjs +3 -1
  20. package/dist/adapters/node-http/nodeHTTPRequestHandler.d.ts.map +1 -1
  21. package/dist/adapters/node-http/nodeHTTPRequestHandler.js +30 -7
  22. package/dist/adapters/node-http/nodeHTTPRequestHandler.mjs +30 -7
  23. package/dist/adapters/node-http/types.d.ts +0 -1
  24. package/dist/adapters/node-http/types.d.ts.map +1 -1
  25. package/dist/adapters/standalone.d.ts +0 -1
  26. package/dist/adapters/standalone.d.ts.map +1 -1
  27. package/dist/adapters/ws.d.ts +3 -4
  28. package/dist/adapters/ws.d.ts.map +1 -1
  29. package/dist/adapters/ws.js +172 -114
  30. package/dist/adapters/ws.mjs +172 -114
  31. package/dist/bundle-analysis.json +235 -154
  32. package/dist/http.js +3 -0
  33. package/dist/http.mjs +1 -0
  34. package/dist/index.js +7 -5
  35. package/dist/index.mjs +3 -2
  36. package/dist/observable/observable.d.ts +1 -0
  37. package/dist/observable/observable.d.ts.map +1 -1
  38. package/dist/observable/observable.js +55 -0
  39. package/dist/observable/observable.mjs +55 -1
  40. package/dist/unstable-core-do-not-import/createProxy.d.ts +3 -3
  41. package/dist/unstable-core-do-not-import/createProxy.d.ts.map +1 -1
  42. package/dist/unstable-core-do-not-import/createProxy.js +15 -6
  43. package/dist/unstable-core-do-not-import/createProxy.mjs +15 -6
  44. package/dist/unstable-core-do-not-import/http/contentType.d.ts +7 -4
  45. package/dist/unstable-core-do-not-import/http/contentType.d.ts.map +1 -1
  46. package/dist/unstable-core-do-not-import/http/contentType.js +60 -17
  47. package/dist/unstable-core-do-not-import/http/contentType.mjs +61 -18
  48. package/dist/unstable-core-do-not-import/http/formDataToObject.d.ts.map +1 -0
  49. package/dist/unstable-core-do-not-import/http/formDataToObject.js +40 -0
  50. package/dist/unstable-core-do-not-import/http/formDataToObject.mjs +38 -0
  51. package/dist/unstable-core-do-not-import/http/getHTTPStatusCode.d.ts.map +1 -1
  52. package/dist/unstable-core-do-not-import/http/getHTTPStatusCode.js +4 -4
  53. package/dist/unstable-core-do-not-import/http/getHTTPStatusCode.mjs +4 -4
  54. package/dist/unstable-core-do-not-import/http/parseConnectionParams.d.ts +4 -0
  55. package/dist/unstable-core-do-not-import/http/parseConnectionParams.d.ts.map +1 -0
  56. package/dist/unstable-core-do-not-import/http/parseConnectionParams.js +42 -0
  57. package/dist/unstable-core-do-not-import/http/parseConnectionParams.mjs +39 -0
  58. package/dist/unstable-core-do-not-import/http/resolveResponse.d.ts.map +1 -1
  59. package/dist/unstable-core-do-not-import/http/resolveResponse.js +302 -149
  60. package/dist/unstable-core-do-not-import/http/resolveResponse.mjs +301 -148
  61. package/dist/unstable-core-do-not-import/http/types.d.ts +26 -2
  62. package/dist/unstable-core-do-not-import/http/types.d.ts.map +1 -1
  63. package/dist/unstable-core-do-not-import/initTRPC.d.ts +12 -12
  64. package/dist/unstable-core-do-not-import/initTRPC.d.ts.map +1 -1
  65. package/dist/unstable-core-do-not-import/middleware.d.ts +3 -3
  66. package/dist/unstable-core-do-not-import/middleware.d.ts.map +1 -1
  67. package/dist/unstable-core-do-not-import/procedureBuilder.d.ts +3 -1
  68. package/dist/unstable-core-do-not-import/procedureBuilder.d.ts.map +1 -1
  69. package/dist/unstable-core-do-not-import/rootConfig.d.ts +12 -0
  70. package/dist/unstable-core-do-not-import/rootConfig.d.ts.map +1 -1
  71. package/dist/unstable-core-do-not-import/router.d.ts +2 -2
  72. package/dist/unstable-core-do-not-import/router.d.ts.map +1 -1
  73. package/dist/unstable-core-do-not-import/router.js +7 -2
  74. package/dist/unstable-core-do-not-import/router.mjs +7 -2
  75. package/dist/unstable-core-do-not-import/rpc/envelopes.d.ts +7 -0
  76. package/dist/unstable-core-do-not-import/rpc/envelopes.d.ts.map +1 -1
  77. package/dist/unstable-core-do-not-import/rpc/index.d.ts +1 -1
  78. package/dist/unstable-core-do-not-import/rpc/index.d.ts.map +1 -1
  79. package/dist/unstable-core-do-not-import/stream/{stream.d.ts → jsonl.d.ts} +12 -8
  80. package/dist/unstable-core-do-not-import/stream/jsonl.d.ts.map +1 -0
  81. package/dist/unstable-core-do-not-import/stream/{stream.js → jsonl.js} +158 -119
  82. package/dist/unstable-core-do-not-import/stream/{stream.mjs → jsonl.mjs} +157 -118
  83. package/dist/unstable-core-do-not-import/stream/sse.d.ts +86 -0
  84. package/dist/unstable-core-do-not-import/stream/sse.d.ts.map +1 -0
  85. package/dist/unstable-core-do-not-import/stream/sse.js +178 -0
  86. package/dist/unstable-core-do-not-import/stream/sse.mjs +172 -0
  87. package/dist/unstable-core-do-not-import/stream/utils/createDeferred.d.ts +18 -0
  88. package/dist/unstable-core-do-not-import/stream/utils/createDeferred.d.ts.map +1 -0
  89. package/dist/unstable-core-do-not-import/stream/utils/createDeferred.js +46 -0
  90. package/dist/unstable-core-do-not-import/stream/utils/createDeferred.mjs +43 -0
  91. package/dist/unstable-core-do-not-import/stream/utils/createReadableStream.d.ts +10 -0
  92. package/dist/unstable-core-do-not-import/stream/utils/createReadableStream.d.ts.map +1 -0
  93. package/dist/unstable-core-do-not-import/stream/utils/createReadableStream.js +31 -0
  94. package/dist/unstable-core-do-not-import/stream/utils/createReadableStream.mjs +29 -0
  95. package/dist/unstable-core-do-not-import/stream/utils/createServer.d.ts +7 -0
  96. package/dist/unstable-core-do-not-import/stream/utils/createServer.d.ts.map +1 -0
  97. package/dist/unstable-core-do-not-import/transformer.d.ts +5 -5
  98. package/dist/unstable-core-do-not-import/utils.d.ts +4 -0
  99. package/dist/unstable-core-do-not-import/utils.d.ts.map +1 -1
  100. package/dist/unstable-core-do-not-import/utils.js +4 -0
  101. package/dist/unstable-core-do-not-import/utils.mjs +4 -1
  102. package/dist/unstable-core-do-not-import.d.ts +5 -2
  103. package/dist/unstable-core-do-not-import.d.ts.map +1 -1
  104. package/dist/unstable-core-do-not-import.js +19 -7
  105. package/dist/unstable-core-do-not-import.mjs +6 -3
  106. package/package.json +6 -6
  107. package/src/@trpc/server/http.ts +7 -2
  108. package/src/@trpc/server/index.ts +1 -0
  109. package/src/@trpc/server/rpc.ts +1 -0
  110. package/src/adapters/aws-lambda/getPlanner.ts +21 -2
  111. package/src/adapters/next-app-dir/nextAppDirCaller.ts +2 -1
  112. package/src/adapters/node-http/incomingMessageToRequest.ts +3 -2
  113. package/src/adapters/node-http/nodeHTTPRequestHandler.ts +32 -7
  114. package/src/adapters/ws.ts +193 -107
  115. package/src/observable/observable.ts +63 -0
  116. package/src/unstable-core-do-not-import/createProxy.ts +23 -8
  117. package/src/unstable-core-do-not-import/http/contentType.ts +83 -21
  118. package/src/{adapters/next-app-dir → unstable-core-do-not-import/http}/formDataToObject.ts +18 -10
  119. package/src/unstable-core-do-not-import/http/getHTTPStatusCode.ts +4 -7
  120. package/src/unstable-core-do-not-import/http/parseConnectionParams.ts +49 -0
  121. package/src/unstable-core-do-not-import/http/resolveResponse.ts +333 -164
  122. package/src/unstable-core-do-not-import/http/types.ts +31 -2
  123. package/src/unstable-core-do-not-import/procedureBuilder.ts +8 -1
  124. package/src/unstable-core-do-not-import/rootConfig.ts +12 -0
  125. package/src/unstable-core-do-not-import/router.ts +47 -35
  126. package/src/unstable-core-do-not-import/rpc/envelopes.ts +9 -0
  127. package/src/unstable-core-do-not-import/rpc/index.ts +1 -0
  128. package/src/unstable-core-do-not-import/stream/{stream.ts → jsonl.ts} +186 -127
  129. package/src/unstable-core-do-not-import/stream/sse.ts +288 -0
  130. package/src/unstable-core-do-not-import/stream/utils/createDeferred.ts +48 -0
  131. package/src/unstable-core-do-not-import/stream/utils/createReadableStream.ts +31 -0
  132. package/src/unstable-core-do-not-import/stream/utils/createServer.ts +44 -0
  133. package/src/unstable-core-do-not-import/utils.ts +5 -0
  134. package/src/unstable-core-do-not-import.ts +5 -2
  135. package/dist/adapters/next-app-dir/formDataToObject.d.ts.map +0 -1
  136. package/dist/adapters/next-app-dir/formDataToObject.js +0 -34
  137. package/dist/adapters/next-app-dir/formDataToObject.mjs +0 -32
  138. package/dist/unstable-core-do-not-import/stream/stream.d.ts.map +0 -1
  139. /package/dist/{adapters/next-app-dir → unstable-core-do-not-import/http}/formDataToObject.d.ts +0 -0
@@ -1,15 +1,19 @@
1
- import { TRPCError, getTRPCErrorFromUnknown } from '../unstable-core-do-not-import/error/TRPCError.mjs';
2
1
  import { getErrorShape } from '../unstable-core-do-not-import/error/getErrorShape.mjs';
2
+ import { TRPCError, getTRPCErrorFromUnknown } from '../unstable-core-do-not-import/error/TRPCError.mjs';
3
+ import { run, isAsyncIterable, isObject } from '../unstable-core-do-not-import/utils.mjs';
4
+ import { parseConnectionParamsFromUnknown } from '../unstable-core-do-not-import/http/parseConnectionParams.mjs';
3
5
  import { parseTRPCMessage } from '../unstable-core-do-not-import/rpc/parseTRPCMessage.mjs';
4
- import { callProcedure } from '../unstable-core-do-not-import/router.mjs';
6
+ import { isObservable, observableToAsyncIterable } from '../observable/observable.mjs';
5
7
  import { transformTRPCResponse } from '../unstable-core-do-not-import/transformer.mjs';
8
+ import { toURL } from '../unstable-core-do-not-import/http/toURL.mjs';
6
9
  import '../unstable-core-do-not-import/rootConfig.mjs';
7
- import { isObservable } from '../observable/observable.mjs';
10
+ import { callProcedure } from '../unstable-core-do-not-import/router.mjs';
8
11
 
9
12
  /**
10
13
  * Importing ws causes a build error
11
14
  * @link https://github.com/trpc/trpc/pull/5279
12
15
  */ const WEBSOCKET_OPEN = 1; /* ws.WebSocket.OPEN */
16
+ const unsetContextSymbol = Symbol('unsetContext');
13
17
  function getWSConnectionHandler(opts) {
14
18
  const { createContext , router } = opts;
15
19
  const { transformer } = router._def._config;
@@ -18,20 +22,54 @@ function getWSConnectionHandler(opts) {
18
22
  function respond(untransformedJSON) {
19
23
  client.send(JSON.stringify(transformTRPCResponse(router._def._config, untransformedJSON)));
20
24
  }
21
- function stopSubscription(subscription, { id , jsonrpc }) {
22
- subscription.unsubscribe();
23
- respond({
24
- id,
25
- jsonrpc,
26
- result: {
27
- type: 'stopped'
28
- }
25
+ function createCtxPromise(getConnectionParams) {
26
+ return run(async ()=>{
27
+ ctx = await createContext?.({
28
+ req,
29
+ res: client,
30
+ info: {
31
+ connectionParams: getConnectionParams(),
32
+ calls: [],
33
+ isBatchCall: false,
34
+ accept: null,
35
+ type: 'unknown'
36
+ }
37
+ });
38
+ return ctx;
39
+ }).catch((cause)=>{
40
+ const error = getTRPCErrorFromUnknown(cause);
41
+ opts.onError?.({
42
+ error,
43
+ path: undefined,
44
+ type: 'unknown',
45
+ ctx,
46
+ req,
47
+ input: undefined
48
+ });
49
+ respond({
50
+ id: null,
51
+ error: getErrorShape({
52
+ config: router._def._config,
53
+ error,
54
+ type: 'unknown',
55
+ path: undefined,
56
+ input: undefined,
57
+ ctx
58
+ })
59
+ });
60
+ // close in next tick
61
+ (global.setImmediate ?? global.setTimeout)(()=>{
62
+ client.close();
63
+ });
64
+ throw error;
29
65
  });
30
66
  }
31
- const ctxPromise = createContext?.({
32
- req,
33
- res: client
34
- });
67
+ /**
68
+ * promise for initializing the context
69
+ *
70
+ * - the context promise will be created immediately on connection if no connectionParams are expected
71
+ * - if connection params are expected, they will be created once received
72
+ */ let ctxPromise = toURL(req.url ?? '').searchParams.get('connectionParams') === '1' ? unsetContextSymbol : createCtxPromise(()=>null);
35
73
  let ctx = undefined;
36
74
  async function handleRequest(msg) {
37
75
  const { id , jsonrpc } = msg;
@@ -42,14 +80,7 @@ function getWSConnectionHandler(opts) {
42
80
  });
43
81
  }
44
82
  if (msg.method === 'subscription.stop') {
45
- const sub = clientSubscriptions.get(id);
46
- if (sub) {
47
- stopSubscription(sub, {
48
- id,
49
- jsonrpc
50
- });
51
- }
52
- clientSubscriptions.delete(id);
83
+ clientSubscriptions.get(id)?.abort();
53
84
  return;
54
85
  }
55
86
  const { path , input } = msg.params;
@@ -63,14 +94,7 @@ function getWSConnectionHandler(opts) {
63
94
  ctx,
64
95
  type
65
96
  });
66
- if (type === 'subscription') {
67
- if (!isObservable(result)) {
68
- throw new TRPCError({
69
- message: `Subscription ${path} did not return an observable`,
70
- code: 'INTERNAL_SERVER_ERROR'
71
- });
72
- }
73
- } else {
97
+ if (type !== 'subscription') {
74
98
  // send the value as data if the method is not a subscription
75
99
  respond({
76
100
  id,
@@ -82,69 +106,110 @@ function getWSConnectionHandler(opts) {
82
106
  });
83
107
  return;
84
108
  }
85
- const observable = result;
86
- const sub1 = observable.subscribe({
87
- next (data) {
88
- respond({
89
- id,
90
- jsonrpc,
91
- result: {
92
- type: 'data',
93
- data
94
- }
95
- });
96
- },
97
- error (err) {
98
- const error = getTRPCErrorFromUnknown(err);
99
- opts.onError?.({
100
- error,
101
- path,
102
- type,
103
- ctx,
104
- req,
105
- input
106
- });
107
- respond({
108
- id,
109
- jsonrpc,
110
- error: getErrorShape({
111
- config: router._def._config,
112
- error,
113
- type,
114
- path,
115
- input,
116
- ctx
117
- })
118
- });
119
- },
120
- complete () {
121
- respond({
122
- id,
123
- jsonrpc,
124
- result: {
125
- type: 'stopped'
126
- }
127
- });
128
- }
129
- });
109
+ if (!isObservable(result) && !isAsyncIterable(result)) {
110
+ throw new TRPCError({
111
+ message: `Subscription ${path} did not return an observable or a AsyncGenerator`,
112
+ code: 'INTERNAL_SERVER_ERROR'
113
+ });
114
+ }
130
115
  /* istanbul ignore next -- @preserve */ if (client.readyState !== WEBSOCKET_OPEN) {
131
116
  // if the client got disconnected whilst initializing the subscription
132
117
  // no need to send stopped message if the client is disconnected
133
- sub1.unsubscribe();
134
118
  return;
135
119
  }
136
120
  /* istanbul ignore next -- @preserve */ if (clientSubscriptions.has(id)) {
137
121
  // duplicate request ids for client
138
- stopSubscription(sub1, {
139
- id,
140
- jsonrpc
141
- });
142
122
  throw new TRPCError({
143
123
  message: `Duplicate id ${id}`,
144
124
  code: 'BAD_REQUEST'
145
125
  });
146
126
  }
147
- clientSubscriptions.set(id, sub1);
127
+ const iterable = isObservable(result) ? observableToAsyncIterable(result) : result;
128
+ const iterator = iterable[Symbol.asyncIterator]();
129
+ const abortController = new AbortController();
130
+ const abortPromise = new Promise((resolve)=>{
131
+ abortController.signal.onabort = ()=>resolve('abort');
132
+ });
133
+ run(async ()=>{
134
+ while(true){
135
+ const next = await Promise.race([
136
+ iterator.next().catch(getTRPCErrorFromUnknown),
137
+ abortPromise
138
+ ]);
139
+ if (next === 'abort') {
140
+ await iterator.return?.();
141
+ break;
142
+ }
143
+ if (next instanceof Error) {
144
+ const error = getTRPCErrorFromUnknown(next);
145
+ opts.onError?.({
146
+ error,
147
+ path,
148
+ type,
149
+ ctx,
150
+ req,
151
+ input
152
+ });
153
+ respond({
154
+ id,
155
+ jsonrpc,
156
+ error: getErrorShape({
157
+ config: router._def._config,
158
+ error,
159
+ type,
160
+ path,
161
+ input,
162
+ ctx
163
+ })
164
+ });
165
+ break;
166
+ }
167
+ if (next.done) {
168
+ break;
169
+ }
170
+ respond({
171
+ id,
172
+ jsonrpc,
173
+ result: {
174
+ type: 'data',
175
+ data: next.value
176
+ }
177
+ });
178
+ }
179
+ await iterator.return?.();
180
+ respond({
181
+ id,
182
+ jsonrpc,
183
+ result: {
184
+ type: 'stopped'
185
+ }
186
+ });
187
+ clientSubscriptions.delete(id);
188
+ }).catch((cause)=>{
189
+ const error = getTRPCErrorFromUnknown(cause);
190
+ opts.onError?.({
191
+ error,
192
+ path,
193
+ type,
194
+ ctx,
195
+ req,
196
+ input
197
+ });
198
+ respond({
199
+ id,
200
+ jsonrpc,
201
+ error: getErrorShape({
202
+ config: router._def._config,
203
+ error,
204
+ type,
205
+ path,
206
+ input,
207
+ ctx
208
+ })
209
+ });
210
+ abortController.abort();
211
+ });
212
+ clientSubscriptions.set(id, abortController);
148
213
  respond({
149
214
  id,
150
215
  jsonrpc,
@@ -178,8 +243,28 @@ function getWSConnectionHandler(opts) {
178
243
  }
179
244
  }
180
245
  client.on('message', async (message)=>{
246
+ if (ctxPromise === unsetContextSymbol) {
247
+ // If the ctxPromise wasn't created immediately, we're expecting the first message to be a TRPCConnectionParamsMessage
248
+ ctxPromise = createCtxPromise(()=>{
249
+ let msg;
250
+ try {
251
+ msg = JSON.parse(message.toString());
252
+ if (!isObject(msg)) {
253
+ throw new Error('Message was not an object');
254
+ }
255
+ } catch (cause) {
256
+ throw new TRPCError({
257
+ code: 'PARSE_ERROR',
258
+ message: `Malformed TRPCConnectionParamsMessage`,
259
+ cause
260
+ });
261
+ }
262
+ const connectionParams = parseConnectionParamsFromUnknown(msg.data);
263
+ return connectionParams;
264
+ });
265
+ return;
266
+ }
181
267
  try {
182
- // eslint-disable-next-line @typescript-eslint/no-base-to-string
183
268
  const msgJSON = JSON.parse(message.toString());
184
269
  const msgs = Array.isArray(msgJSON) ? msgJSON : [
185
270
  msgJSON
@@ -220,41 +305,14 @@ function getWSConnectionHandler(opts) {
220
305
  });
221
306
  client.once('close', ()=>{
222
307
  for (const sub of clientSubscriptions.values()){
223
- sub.unsubscribe();
308
+ sub.abort();
224
309
  }
225
310
  clientSubscriptions.clear();
226
311
  });
227
- async function createContextAsync() {
228
- try {
229
- ctx = await ctxPromise;
230
- } catch (cause) {
231
- const error = getTRPCErrorFromUnknown(cause);
232
- opts.onError?.({
233
- error,
234
- path: undefined,
235
- type: 'unknown',
236
- ctx,
237
- req,
238
- input: undefined
239
- });
240
- respond({
241
- id: null,
242
- error: getErrorShape({
243
- config: router._def._config,
244
- error,
245
- type: 'unknown',
246
- path: undefined,
247
- input: undefined,
248
- ctx
249
- })
250
- });
251
- // close in next tick
252
- (global.setImmediate ?? global.setTimeout)(()=>{
253
- client.close();
254
- });
255
- }
312
+ if (ctxPromise !== unsetContextSymbol) {
313
+ // prevent unhandled promise rejection errors
314
+ await ctxPromise.catch(()=>null);
256
315
  }
257
- await createContextAsync();
258
316
  };
259
317
  }
260
318
  /**