@trpc/client 10.29.0 → 10.29.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.
- package/dist/index.js +19 -4
- package/dist/index.mjs +19 -4
- package/dist/links/HTTPBatchStreamLinkOptions.d.ts +11 -0
- package/dist/links/HTTPBatchStreamLinkOptions.d.ts.map +1 -0
- package/dist/links/httpBatchLink.d.ts +2 -1
- package/dist/links/httpBatchLink.d.ts.map +1 -1
- package/dist/links/httpBatchStreamLink.d.ts +2 -1
- package/dist/links/httpBatchStreamLink.d.ts.map +1 -1
- package/dist/links/index.d.ts +1 -0
- package/dist/links/index.d.ts.map +1 -1
- package/dist/links/internals/createHTTPBatchLink.d.ts +3 -3
- package/dist/links/internals/createHTTPBatchLink.d.ts.map +1 -1
- package/dist/links/internals/getTextDecoder.d.ts +3 -0
- package/dist/links/internals/getTextDecoder.d.ts.map +1 -0
- package/dist/links/internals/httpUtils.d.ts +2 -0
- package/dist/links/internals/httpUtils.d.ts.map +1 -1
- package/dist/links/internals/parseJSONStream.d.ts +3 -0
- package/dist/links/internals/parseJSONStream.d.ts.map +1 -1
- package/dist/links/internals/streamingUtils.d.ts +7 -0
- package/dist/links/internals/streamingUtils.d.ts.map +1 -0
- package/package.json +4 -4
- package/src/links/HTTPBatchStreamLinkOptions.ts +11 -0
- package/src/links/httpBatchLink.ts +2 -1
- package/src/links/httpBatchStreamLink.ts +7 -1
- package/src/links/index.ts +1 -0
- package/src/links/internals/createHTTPBatchLink.ts +6 -4
- package/src/links/internals/getTextDecoder.ts +19 -0
- package/src/links/internals/httpUtils.ts +2 -0
- package/src/links/internals/parseJSONStream.ts +7 -4
- package/src/links/internals/streamingUtils.ts +6 -0
package/dist/index.js
CHANGED
|
@@ -163,6 +163,19 @@ function createTRPCProxyClient(opts) {
|
|
|
163
163
|
return proxy;
|
|
164
164
|
}
|
|
165
165
|
|
|
166
|
+
function getTextDecoder(customTextDecoder) {
|
|
167
|
+
if (customTextDecoder) {
|
|
168
|
+
return customTextDecoder;
|
|
169
|
+
}
|
|
170
|
+
if (typeof window !== 'undefined' && window.TextDecoder) {
|
|
171
|
+
return new window.TextDecoder();
|
|
172
|
+
}
|
|
173
|
+
if (typeof globalThis !== 'undefined' && globalThis.TextDecoder) {
|
|
174
|
+
return new globalThis.TextDecoder();
|
|
175
|
+
}
|
|
176
|
+
throw new Error('No TextDecoder implementation found');
|
|
177
|
+
}
|
|
178
|
+
|
|
166
179
|
// Stream parsing adapted from https://www.loginradius.com/blog/engineering/guest-post/http-streaming-with-nodejs-and-fetch-api/
|
|
167
180
|
/**
|
|
168
181
|
* @internal
|
|
@@ -190,9 +203,8 @@ function createTRPCProxyClient(opts) {
|
|
|
190
203
|
const text = line.substring(indexOfColon + 1);
|
|
191
204
|
opts.onSingle(Number(indexAsStr), parse(text));
|
|
192
205
|
};
|
|
193
|
-
await readLines(opts.readableStream, onLine);
|
|
206
|
+
await readLines(opts.readableStream, onLine, opts.textDecoder);
|
|
194
207
|
}
|
|
195
|
-
const textDecoder = new TextDecoder();
|
|
196
208
|
/**
|
|
197
209
|
* Handle transforming a stream of bytes into lines of text.
|
|
198
210
|
* To avoid using AsyncIterators / AsyncGenerators,
|
|
@@ -200,7 +212,7 @@ const textDecoder = new TextDecoder();
|
|
|
200
212
|
*
|
|
201
213
|
* @param readableStream can be a NodeJS stream or a WebAPI stream
|
|
202
214
|
* @param onLine will be called for every line ('\n' delimited) in the stream
|
|
203
|
-
*/ async function readLines(readableStream, onLine) {
|
|
215
|
+
*/ async function readLines(readableStream, onLine, textDecoder) {
|
|
204
216
|
let partOfLine = '';
|
|
205
217
|
const onChunk = (chunk)=>{
|
|
206
218
|
const chunkText = textDecoder.decode(chunk);
|
|
@@ -266,7 +278,8 @@ const streamingJsonHttpRequester = (opts, onSingle)=>{
|
|
|
266
278
|
json: JSON.parse(string),
|
|
267
279
|
meta
|
|
268
280
|
}),
|
|
269
|
-
signal: ac?.signal
|
|
281
|
+
signal: ac?.signal,
|
|
282
|
+
textDecoder: opts.textDecoder
|
|
270
283
|
});
|
|
271
284
|
});
|
|
272
285
|
return {
|
|
@@ -276,11 +289,13 @@ const streamingJsonHttpRequester = (opts, onSingle)=>{
|
|
|
276
289
|
};
|
|
277
290
|
|
|
278
291
|
const streamRequester = (requesterOpts)=>{
|
|
292
|
+
const textDecoder = getTextDecoder(requesterOpts.opts.textDecoder);
|
|
279
293
|
return (batchOps, unitResolver)=>{
|
|
280
294
|
const path = batchOps.map((op)=>op.path).join(',');
|
|
281
295
|
const inputs = batchOps.map((op)=>op.input);
|
|
282
296
|
const { cancel , promise } = streamingJsonHttpRequester({
|
|
283
297
|
...requesterOpts,
|
|
298
|
+
textDecoder,
|
|
284
299
|
path,
|
|
285
300
|
inputs,
|
|
286
301
|
headers () {
|
package/dist/index.mjs
CHANGED
|
@@ -164,6 +164,19 @@ function createTRPCProxyClient(opts) {
|
|
|
164
164
|
return proxy;
|
|
165
165
|
}
|
|
166
166
|
|
|
167
|
+
function getTextDecoder(customTextDecoder) {
|
|
168
|
+
if (customTextDecoder) {
|
|
169
|
+
return customTextDecoder;
|
|
170
|
+
}
|
|
171
|
+
if (typeof window !== 'undefined' && window.TextDecoder) {
|
|
172
|
+
return new window.TextDecoder();
|
|
173
|
+
}
|
|
174
|
+
if (typeof globalThis !== 'undefined' && globalThis.TextDecoder) {
|
|
175
|
+
return new globalThis.TextDecoder();
|
|
176
|
+
}
|
|
177
|
+
throw new Error('No TextDecoder implementation found');
|
|
178
|
+
}
|
|
179
|
+
|
|
167
180
|
// Stream parsing adapted from https://www.loginradius.com/blog/engineering/guest-post/http-streaming-with-nodejs-and-fetch-api/
|
|
168
181
|
/**
|
|
169
182
|
* @internal
|
|
@@ -191,9 +204,8 @@ function createTRPCProxyClient(opts) {
|
|
|
191
204
|
const text = line.substring(indexOfColon + 1);
|
|
192
205
|
opts.onSingle(Number(indexAsStr), parse(text));
|
|
193
206
|
};
|
|
194
|
-
await readLines(opts.readableStream, onLine);
|
|
207
|
+
await readLines(opts.readableStream, onLine, opts.textDecoder);
|
|
195
208
|
}
|
|
196
|
-
const textDecoder = new TextDecoder();
|
|
197
209
|
/**
|
|
198
210
|
* Handle transforming a stream of bytes into lines of text.
|
|
199
211
|
* To avoid using AsyncIterators / AsyncGenerators,
|
|
@@ -201,7 +213,7 @@ const textDecoder = new TextDecoder();
|
|
|
201
213
|
*
|
|
202
214
|
* @param readableStream can be a NodeJS stream or a WebAPI stream
|
|
203
215
|
* @param onLine will be called for every line ('\n' delimited) in the stream
|
|
204
|
-
*/ async function readLines(readableStream, onLine) {
|
|
216
|
+
*/ async function readLines(readableStream, onLine, textDecoder) {
|
|
205
217
|
let partOfLine = '';
|
|
206
218
|
const onChunk = (chunk)=>{
|
|
207
219
|
const chunkText = textDecoder.decode(chunk);
|
|
@@ -267,7 +279,8 @@ const streamingJsonHttpRequester = (opts, onSingle)=>{
|
|
|
267
279
|
json: JSON.parse(string),
|
|
268
280
|
meta
|
|
269
281
|
}),
|
|
270
|
-
signal: ac?.signal
|
|
282
|
+
signal: ac?.signal,
|
|
283
|
+
textDecoder: opts.textDecoder
|
|
271
284
|
});
|
|
272
285
|
});
|
|
273
286
|
return {
|
|
@@ -277,11 +290,13 @@ const streamingJsonHttpRequester = (opts, onSingle)=>{
|
|
|
277
290
|
};
|
|
278
291
|
|
|
279
292
|
const streamRequester = (requesterOpts)=>{
|
|
293
|
+
const textDecoder = getTextDecoder(requesterOpts.opts.textDecoder);
|
|
280
294
|
return (batchOps, unitResolver)=>{
|
|
281
295
|
const path = batchOps.map((op)=>op.path).join(',');
|
|
282
296
|
const inputs = batchOps.map((op)=>op.input);
|
|
283
297
|
const { cancel , promise } = streamingJsonHttpRequester({
|
|
284
298
|
...requesterOpts,
|
|
299
|
+
textDecoder,
|
|
285
300
|
path,
|
|
286
301
|
inputs,
|
|
287
302
|
headers () {
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import { HTTPBatchLinkOptions } from './HTTPBatchLinkOptions';
|
|
2
|
+
import { TextDecoderEsque } from './internals/streamingUtils';
|
|
3
|
+
export interface HTTPBatchStreamLinkOptions extends HTTPBatchLinkOptions {
|
|
4
|
+
/**
|
|
5
|
+
* Will default to the webAPI `TextDecoder`,
|
|
6
|
+
* but you can use this option if your client
|
|
7
|
+
* runtime doesn't provide it.
|
|
8
|
+
*/
|
|
9
|
+
textDecoder?: TextDecoderEsque;
|
|
10
|
+
}
|
|
11
|
+
//# sourceMappingURL=HTTPBatchStreamLinkOptions.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"HTTPBatchStreamLinkOptions.d.ts","sourceRoot":"","sources":["../../src/links/HTTPBatchStreamLinkOptions.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,oBAAoB,EAAE,MAAM,wBAAwB,CAAC;AAC9D,OAAO,EAAE,gBAAgB,EAAE,MAAM,4BAA4B,CAAC;AAE9D,MAAM,WAAW,0BAA2B,SAAQ,oBAAoB;IACtE;;;;OAIG;IACH,WAAW,CAAC,EAAE,gBAAgB,CAAC;CAChC"}
|
|
@@ -1,2 +1,3 @@
|
|
|
1
|
-
|
|
1
|
+
import { HTTPBatchLinkOptions } from './HTTPBatchLinkOptions';
|
|
2
|
+
export declare const httpBatchLink: <TRouter extends import("@trpc/server").AnyRouter>(opts: HTTPBatchLinkOptions) => import("./types").TRPCLink<TRouter>;
|
|
2
3
|
//# sourceMappingURL=httpBatchLink.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"httpBatchLink.d.ts","sourceRoot":"","sources":["../../src/links/httpBatchLink.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"httpBatchLink.d.ts","sourceRoot":"","sources":["../../src/links/httpBatchLink.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,oBAAoB,EAAE,MAAM,wBAAwB,CAAC;AAgD9D,eAAO,MAAM,aAAa,uHAAsC,CAAC"}
|
|
@@ -1,2 +1,3 @@
|
|
|
1
|
-
|
|
1
|
+
import { HTTPBatchStreamLinkOptions } from './HTTPBatchStreamLinkOptions';
|
|
2
|
+
export declare const unstable_httpBatchStreamLink: <TRouter extends import("@trpc/server").AnyRouter>(opts: HTTPBatchStreamLinkOptions) => import("./types").TRPCLink<TRouter>;
|
|
2
3
|
//# sourceMappingURL=httpBatchStreamLink.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"httpBatchStreamLink.d.ts","sourceRoot":"","sources":["../../src/links/httpBatchStreamLink.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"httpBatchStreamLink.d.ts","sourceRoot":"","sources":["../../src/links/httpBatchStreamLink.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,0BAA0B,EAAE,MAAM,8BAA8B,CAAC;AAkD1E,eAAO,MAAM,4BAA4B,6HACH,CAAC"}
|
package/dist/links/index.d.ts
CHANGED
|
@@ -2,6 +2,7 @@ export * from './types';
|
|
|
2
2
|
export * from './httpBatchLink';
|
|
3
3
|
export * from './httpBatchStreamLink';
|
|
4
4
|
export * from './HTTPBatchLinkOptions';
|
|
5
|
+
export * from './HTTPBatchStreamLinkOptions';
|
|
5
6
|
export * from './httpLink';
|
|
6
7
|
export * from './loggerLink';
|
|
7
8
|
export * from './splitLink';
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/links/index.ts"],"names":[],"mappings":"AAAA,cAAc,SAAS,CAAC;AAExB,cAAc,iBAAiB,CAAC;AAChC,cAAc,uBAAuB,CAAC;AACtC,cAAc,wBAAwB,CAAC;AACvC,cAAc,YAAY,CAAC;AAC3B,cAAc,cAAc,CAAC;AAC7B,cAAc,aAAa,CAAC;AAC5B,cAAc,UAAU,CAAC;AACzB,cAAc,oBAAoB,CAAC"}
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/links/index.ts"],"names":[],"mappings":"AAAA,cAAc,SAAS,CAAC;AAExB,cAAc,iBAAiB,CAAC;AAChC,cAAc,uBAAuB,CAAC;AACtC,cAAc,wBAAwB,CAAC;AACvC,cAAc,8BAA8B,CAAC;AAC7C,cAAc,YAAY,CAAC;AAC3B,cAAc,cAAc,CAAC;AAC7B,cAAc,aAAa,CAAC;AAC5B,cAAc,UAAU,CAAC;AACzB,cAAc,oBAAoB,CAAC"}
|
|
@@ -5,10 +5,10 @@ import { HTTPResult, ResolvedHTTPLinkOptions } from './httpUtils';
|
|
|
5
5
|
/**
|
|
6
6
|
* @internal
|
|
7
7
|
*/
|
|
8
|
-
export type RequesterFn = (requesterOpts: ResolvedHTTPLinkOptions & {
|
|
8
|
+
export type RequesterFn<TOptions extends HTTPBatchLinkOptions> = (requesterOpts: ResolvedHTTPLinkOptions & {
|
|
9
9
|
runtime: TRPCClientRuntime;
|
|
10
10
|
type: ProcedureType;
|
|
11
|
-
opts:
|
|
11
|
+
opts: TOptions;
|
|
12
12
|
}) => (batchOps: Operation[], unitResolver: (index: number, value: NonNullable<HTTPResult>) => void) => {
|
|
13
13
|
promise: Promise<HTTPResult[]>;
|
|
14
14
|
cancel: CancelFn;
|
|
@@ -16,5 +16,5 @@ export type RequesterFn = (requesterOpts: ResolvedHTTPLinkOptions & {
|
|
|
16
16
|
/**
|
|
17
17
|
* @internal
|
|
18
18
|
*/
|
|
19
|
-
export declare function createHTTPBatchLink(requester: RequesterFn): <TRouter extends AnyRouter>(opts:
|
|
19
|
+
export declare function createHTTPBatchLink<TOptions extends HTTPBatchLinkOptions>(requester: RequesterFn<TOptions>): <TRouter extends AnyRouter>(opts: TOptions) => TRPCLink<TRouter>;
|
|
20
20
|
//# sourceMappingURL=createHTTPBatchLink.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"createHTTPBatchLink.d.ts","sourceRoot":"","sources":["../../../src/links/internals/createHTTPBatchLink.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,aAAa,EAAE,MAAM,cAAc,CAAC;AAKxD,OAAO,EAAE,oBAAoB,EAAE,MAAM,yBAAyB,CAAC;AAC/D,OAAO,EAAE,QAAQ,EAAE,SAAS,EAAE,iBAAiB,EAAE,QAAQ,EAAE,MAAM,UAAU,CAAC;AAC5E,OAAO,EAEL,UAAU,EACV,uBAAuB,EAExB,MAAM,aAAa,CAAC;AAErB;;GAEG;AACH,MAAM,MAAM,WAAW,
|
|
1
|
+
{"version":3,"file":"createHTTPBatchLink.d.ts","sourceRoot":"","sources":["../../../src/links/internals/createHTTPBatchLink.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,aAAa,EAAE,MAAM,cAAc,CAAC;AAKxD,OAAO,EAAE,oBAAoB,EAAE,MAAM,yBAAyB,CAAC;AAC/D,OAAO,EAAE,QAAQ,EAAE,SAAS,EAAE,iBAAiB,EAAE,QAAQ,EAAE,MAAM,UAAU,CAAC;AAC5E,OAAO,EAEL,UAAU,EACV,uBAAuB,EAExB,MAAM,aAAa,CAAC;AAErB;;GAEG;AACH,MAAM,MAAM,WAAW,CAAC,QAAQ,SAAS,oBAAoB,IAAI,CAC/D,aAAa,EAAE,uBAAuB,GAAG;IACvC,OAAO,EAAE,iBAAiB,CAAC;IAC3B,IAAI,EAAE,aAAa,CAAC;IACpB,IAAI,EAAE,QAAQ,CAAC;CAChB,KACE,CACH,QAAQ,EAAE,SAAS,EAAE,EACrB,YAAY,EAAE,CAAC,KAAK,EAAE,MAAM,EAAE,KAAK,EAAE,WAAW,CAAC,UAAU,CAAC,KAAK,IAAI,KAClE;IACH,OAAO,EAAE,OAAO,CAAC,UAAU,EAAE,CAAC,CAAC;IAC/B,MAAM,EAAE,QAAQ,CAAC;CAClB,CAAC;AAEF;;GAEG;AACH,wBAAgB,mBAAmB,CAAC,QAAQ,SAAS,oBAAoB,EACvE,SAAS,EAAE,WAAW,CAAC,QAAQ,CAAC,qCAGxB,QAAQ,uBA4EjB"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"getTextDecoder.d.ts","sourceRoot":"","sources":["../../../src/links/internals/getTextDecoder.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,gBAAgB,EAAE,MAAM,kBAAkB,CAAC;AAEpD,wBAAgB,cAAc,CAC5B,iBAAiB,CAAC,EAAE,gBAAgB,GACnC,gBAAgB,CAclB"}
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { ProcedureType } from '@trpc/server';
|
|
2
2
|
import { TRPCResponse } from '@trpc/server/rpc';
|
|
3
3
|
import { AbortControllerEsque, AbortControllerInstanceEsque, FetchEsque, RequestInitEsque, ResponseEsque } from '../../internals/types';
|
|
4
|
+
import { TextDecoderEsque } from '../internals/streamingUtils';
|
|
4
5
|
import { HTTPHeaders, PromiseAndCancel, TRPCClientRuntime } from '../types';
|
|
5
6
|
/**
|
|
6
7
|
* @internal
|
|
@@ -55,6 +56,7 @@ export type Requester = (opts: HTTPBaseRequestOptions & {
|
|
|
55
56
|
export declare const jsonHttpRequester: Requester;
|
|
56
57
|
export type HTTPRequestOptions = HTTPBaseRequestOptions & ContentOptions & {
|
|
57
58
|
headers: () => HTTPHeaders | Promise<HTTPHeaders>;
|
|
59
|
+
TextDecoder?: TextDecoderEsque;
|
|
58
60
|
};
|
|
59
61
|
export declare function fetchHTTPResponse(opts: HTTPRequestOptions, ac?: AbortControllerInstanceEsque | null): Promise<ResponseEsque>;
|
|
60
62
|
export declare function httpRequest(opts: HTTPRequestOptions): PromiseAndCancel<HTTPResult>;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"httpUtils.d.ts","sourceRoot":"","sources":["../../../src/links/internals/httpUtils.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,aAAa,EAAE,MAAM,cAAc,CAAC;AAC7C,OAAO,EAAE,YAAY,EAAE,MAAM,kBAAkB,CAAC;AAGhD,OAAO,EACL,oBAAoB,EACpB,4BAA4B,EAC5B,UAAU,EACV,gBAAgB,EAChB,aAAa,EACd,MAAM,uBAAuB,CAAC;AAC/B,OAAO,EAAE,WAAW,EAAE,gBAAgB,EAAE,iBAAiB,EAAE,MAAM,UAAU,CAAC;AAE5E;;GAEG;AACH,MAAM,WAAW,mBAAmB;IAClC,GAAG,EAAE,MAAM,CAAC;IACZ;;OAEG;IACH,KAAK,CAAC,EAAE,UAAU,CAAC;IACnB;;OAEG;IACH,eAAe,CAAC,EAAE,oBAAoB,GAAG,IAAI,CAAC;CAC/C;AAED,MAAM,WAAW,uBAAuB;IACtC,GAAG,EAAE,MAAM,CAAC;IACZ,KAAK,EAAE,UAAU,CAAC;IAClB,eAAe,EAAE,oBAAoB,GAAG,IAAI,CAAC;CAC9C;AAED,wBAAgB,sBAAsB,CACpC,IAAI,EAAE,mBAAmB,GACxB,uBAAuB,CAMzB;AAiBD,MAAM,WAAW,UAAU;IACzB,IAAI,EAAE,YAAY,CAAC;IACnB,IAAI,EAAE;QACJ,QAAQ,EAAE,aAAa,CAAC;KACzB,CAAC;CACH;AAED,KAAK,eAAe,GAAG;IACrB,OAAO,EAAE,iBAAiB,CAAC;CAC5B,GAAG,CAAC;IAAE,MAAM,EAAE,OAAO,EAAE,CAAA;CAAE,GAAG;IAAE,KAAK,EAAE,OAAO,CAAA;CAAE,CAAC,CAAC;AAUjD,MAAM,MAAM,sBAAsB,GAAG,uBAAuB,GAC1D,eAAe,GAAG;IAChB,IAAI,EAAE,aAAa,CAAC;IACpB,IAAI,EAAE,MAAM,CAAC;CACd,CAAC;AAEJ,MAAM,MAAM,MAAM,GAAG,CAAC,IAAI,EAAE,sBAAsB,KAAK,MAAM,CAAC;AAC9D,MAAM,MAAM,OAAO,GAAG,CACpB,IAAI,EAAE,sBAAsB,KACzB,gBAAgB,CAAC,MAAM,CAAC,CAAC;AAE9B,MAAM,MAAM,cAAc,GAAG;IAC3B,eAAe,CAAC,EAAE,QAAQ,CAAC;IAC3B,iBAAiB,CAAC,EAAE,MAAM,CAAC;IAC3B,MAAM,EAAE,MAAM,CAAC;IACf,OAAO,EAAE,OAAO,CAAC;CAClB,CAAC;AAEF,eAAO,MAAM,MAAM,EAAE,MAgBpB,CAAC;AAEF,eAAO,MAAM,OAAO,EAAE,OAMrB,CAAC;AAEF,MAAM,MAAM,SAAS,GAAG,CACtB,IAAI,EAAE,sBAAsB,GAAG;IAC7B,OAAO,EAAE,MAAM,WAAW,GAAG,OAAO,CAAC,WAAW,CAAC,CAAC;CACnD,KACE,gBAAgB,CAAC,UAAU,CAAC,CAAC;AAElC,eAAO,MAAM,iBAAiB,EAAE,SAO/B,CAAC;AAEF,MAAM,MAAM,kBAAkB,GAAG,sBAAsB,GACrD,cAAc,GAAG;IACf,OAAO,EAAE,MAAM,WAAW,GAAG,OAAO,CAAC,WAAW,CAAC,CAAC;
|
|
1
|
+
{"version":3,"file":"httpUtils.d.ts","sourceRoot":"","sources":["../../../src/links/internals/httpUtils.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,aAAa,EAAE,MAAM,cAAc,CAAC;AAC7C,OAAO,EAAE,YAAY,EAAE,MAAM,kBAAkB,CAAC;AAGhD,OAAO,EACL,oBAAoB,EACpB,4BAA4B,EAC5B,UAAU,EACV,gBAAgB,EAChB,aAAa,EACd,MAAM,uBAAuB,CAAC;AAC/B,OAAO,EAAE,gBAAgB,EAAE,MAAM,6BAA6B,CAAC;AAC/D,OAAO,EAAE,WAAW,EAAE,gBAAgB,EAAE,iBAAiB,EAAE,MAAM,UAAU,CAAC;AAE5E;;GAEG;AACH,MAAM,WAAW,mBAAmB;IAClC,GAAG,EAAE,MAAM,CAAC;IACZ;;OAEG;IACH,KAAK,CAAC,EAAE,UAAU,CAAC;IACnB;;OAEG;IACH,eAAe,CAAC,EAAE,oBAAoB,GAAG,IAAI,CAAC;CAC/C;AAED,MAAM,WAAW,uBAAuB;IACtC,GAAG,EAAE,MAAM,CAAC;IACZ,KAAK,EAAE,UAAU,CAAC;IAClB,eAAe,EAAE,oBAAoB,GAAG,IAAI,CAAC;CAC9C;AAED,wBAAgB,sBAAsB,CACpC,IAAI,EAAE,mBAAmB,GACxB,uBAAuB,CAMzB;AAiBD,MAAM,WAAW,UAAU;IACzB,IAAI,EAAE,YAAY,CAAC;IACnB,IAAI,EAAE;QACJ,QAAQ,EAAE,aAAa,CAAC;KACzB,CAAC;CACH;AAED,KAAK,eAAe,GAAG;IACrB,OAAO,EAAE,iBAAiB,CAAC;CAC5B,GAAG,CAAC;IAAE,MAAM,EAAE,OAAO,EAAE,CAAA;CAAE,GAAG;IAAE,KAAK,EAAE,OAAO,CAAA;CAAE,CAAC,CAAC;AAUjD,MAAM,MAAM,sBAAsB,GAAG,uBAAuB,GAC1D,eAAe,GAAG;IAChB,IAAI,EAAE,aAAa,CAAC;IACpB,IAAI,EAAE,MAAM,CAAC;CACd,CAAC;AAEJ,MAAM,MAAM,MAAM,GAAG,CAAC,IAAI,EAAE,sBAAsB,KAAK,MAAM,CAAC;AAC9D,MAAM,MAAM,OAAO,GAAG,CACpB,IAAI,EAAE,sBAAsB,KACzB,gBAAgB,CAAC,MAAM,CAAC,CAAC;AAE9B,MAAM,MAAM,cAAc,GAAG;IAC3B,eAAe,CAAC,EAAE,QAAQ,CAAC;IAC3B,iBAAiB,CAAC,EAAE,MAAM,CAAC;IAC3B,MAAM,EAAE,MAAM,CAAC;IACf,OAAO,EAAE,OAAO,CAAC;CAClB,CAAC;AAEF,eAAO,MAAM,MAAM,EAAE,MAgBpB,CAAC;AAEF,eAAO,MAAM,OAAO,EAAE,OAMrB,CAAC;AAEF,MAAM,MAAM,SAAS,GAAG,CACtB,IAAI,EAAE,sBAAsB,GAAG;IAC7B,OAAO,EAAE,MAAM,WAAW,GAAG,OAAO,CAAC,WAAW,CAAC,CAAC;CACnD,KACE,gBAAgB,CAAC,UAAU,CAAC,CAAC;AAElC,eAAO,MAAM,iBAAiB,EAAE,SAO/B,CAAC;AAEF,MAAM,MAAM,kBAAkB,GAAG,sBAAsB,GACrD,cAAc,GAAG;IACf,OAAO,EAAE,MAAM,WAAW,GAAG,OAAO,CAAC,WAAW,CAAC,CAAC;IAClD,WAAW,CAAC,EAAE,gBAAgB,CAAC;CAChC,CAAC;AAEJ,wBAAsB,iBAAiB,CACrC,IAAI,EAAE,kBAAkB,EACxB,EAAE,CAAC,EAAE,4BAA4B,GAAG,IAAI,0BAyBzC;AAED,wBAAgB,WAAW,CACzB,IAAI,EAAE,kBAAkB,GACvB,gBAAgB,CAAC,UAAU,CAAC,CAsB9B"}
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
/// <reference types="node" />
|
|
2
2
|
import { HTTPHeaders } from '../types';
|
|
3
3
|
import { HTTPBaseRequestOptions, HTTPResult } from './httpUtils';
|
|
4
|
+
import { TextDecoderEsque } from './streamingUtils';
|
|
4
5
|
/**
|
|
5
6
|
* @internal
|
|
6
7
|
* @description Take a stream of bytes and call `onLine` with
|
|
@@ -26,9 +27,11 @@ export declare function parseJSONStream<TReturn>(opts: {
|
|
|
26
27
|
*/
|
|
27
28
|
parse?: (text: string) => TReturn;
|
|
28
29
|
signal?: AbortSignal;
|
|
30
|
+
textDecoder: TextDecoderEsque;
|
|
29
31
|
}): Promise<void>;
|
|
30
32
|
export declare const streamingJsonHttpRequester: (opts: HTTPBaseRequestOptions & {
|
|
31
33
|
headers: () => HTTPHeaders | Promise<HTTPHeaders>;
|
|
34
|
+
textDecoder: TextDecoderEsque;
|
|
32
35
|
}, onSingle: (index: number, res: HTTPResult) => void) => {
|
|
33
36
|
cancel: () => void | undefined;
|
|
34
37
|
promise: Promise<void>;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"parseJSONStream.d.ts","sourceRoot":"","sources":["../../../src/links/internals/parseJSONStream.ts"],"names":[],"mappings":";AAGA,OAAO,EAAE,WAAW,EAAE,MAAM,UAAU,CAAC;AACvC,OAAO,EAIL,sBAAsB,EACtB,UAAU,EACX,MAAM,aAAa,CAAC;
|
|
1
|
+
{"version":3,"file":"parseJSONStream.d.ts","sourceRoot":"","sources":["../../../src/links/internals/parseJSONStream.ts"],"names":[],"mappings":";AAGA,OAAO,EAAE,WAAW,EAAE,MAAM,UAAU,CAAC;AACvC,OAAO,EAIL,sBAAsB,EACtB,UAAU,EACX,MAAM,aAAa,CAAC;AACrB,OAAO,EAAE,gBAAgB,EAAE,MAAM,kBAAkB,CAAC;AAEpD;;;;;;;;;;GAUG;AACH,wBAAsB,eAAe,CAAC,OAAO,EAAE,IAAI,EAAE;IACnD;;OAEG;IACH,cAAc,EAAE,cAAc,CAAC,UAAU,CAAC,GAAG,MAAM,CAAC,cAAc,CAAC;IACnE;;OAEG;IACH,QAAQ,EAAE,CAAC,KAAK,EAAE,MAAM,EAAE,GAAG,EAAE,OAAO,KAAK,IAAI,CAAC;IAChD;;OAEG;IACH,KAAK,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,OAAO,CAAC;IAClC,MAAM,CAAC,EAAE,WAAW,CAAC;IACrB,WAAW,EAAE,gBAAgB,CAAC;CAC/B,GAAG,OAAO,CAAC,IAAI,CAAC,CAqBhB;AAwED,eAAO,MAAM,0BAA0B,SAC/B,sBAAsB,GAAG;IAC7B,OAAO,EAAE,MAAM,WAAW,GAAG,QAAQ,WAAW,CAAC,CAAC;IAClD,WAAW,EAAE,gBAAgB,CAAC;CAC/B,oBACiB,MAAM,OAAO,UAAU,KAAK,IAAI;;;CA8BnD,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"streamingUtils.d.ts","sourceRoot":"","sources":["../../../src/links/internals/streamingUtils.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH,MAAM,WAAW,gBAAgB;IAC/B,MAAM,CAAC,KAAK,EAAE,UAAU,GAAG,MAAM,CAAC;CACnC"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@trpc/client",
|
|
3
|
-
"version": "10.29.
|
|
3
|
+
"version": "10.29.1",
|
|
4
4
|
"description": "The tRPC client library",
|
|
5
5
|
"author": "KATT",
|
|
6
6
|
"license": "MIT",
|
|
@@ -76,11 +76,11 @@
|
|
|
76
76
|
"!**/*.test.*"
|
|
77
77
|
],
|
|
78
78
|
"peerDependencies": {
|
|
79
|
-
"@trpc/server": "10.29.
|
|
79
|
+
"@trpc/server": "10.29.1"
|
|
80
80
|
},
|
|
81
81
|
"devDependencies": {
|
|
82
82
|
"@testing-library/dom": "^9.0.0",
|
|
83
|
-
"@trpc/server": "10.29.
|
|
83
|
+
"@trpc/server": "10.29.1",
|
|
84
84
|
"@types/isomorphic-fetch": "^0.0.36",
|
|
85
85
|
"@types/node": "^18.16.16",
|
|
86
86
|
"eslint": "^8.40.0",
|
|
@@ -98,5 +98,5 @@
|
|
|
98
98
|
"funding": [
|
|
99
99
|
"https://trpc.io/sponsor"
|
|
100
100
|
],
|
|
101
|
-
"gitHead": "
|
|
101
|
+
"gitHead": "3dbc7b7e9fff233f89627c21450ba89754bc3e46"
|
|
102
102
|
}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import { HTTPBatchLinkOptions } from './HTTPBatchLinkOptions';
|
|
2
|
+
import { TextDecoderEsque } from './internals/streamingUtils';
|
|
3
|
+
|
|
4
|
+
export interface HTTPBatchStreamLinkOptions extends HTTPBatchLinkOptions {
|
|
5
|
+
/**
|
|
6
|
+
* Will default to the webAPI `TextDecoder`,
|
|
7
|
+
* but you can use this option if your client
|
|
8
|
+
* runtime doesn't provide it.
|
|
9
|
+
*/
|
|
10
|
+
textDecoder?: TextDecoderEsque;
|
|
11
|
+
}
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { NonEmptyArray } from '../internals/types';
|
|
2
|
+
import { HTTPBatchLinkOptions } from './HTTPBatchLinkOptions';
|
|
2
3
|
import {
|
|
3
4
|
createHTTPBatchLink,
|
|
4
5
|
RequesterFn,
|
|
@@ -6,7 +7,7 @@ import {
|
|
|
6
7
|
import { jsonHttpRequester } from './internals/httpUtils';
|
|
7
8
|
import { Operation } from './types';
|
|
8
9
|
|
|
9
|
-
const batchRequester: RequesterFn = (requesterOpts) => {
|
|
10
|
+
const batchRequester: RequesterFn<HTTPBatchLinkOptions> = (requesterOpts) => {
|
|
10
11
|
return (batchOps) => {
|
|
11
12
|
const path = batchOps.map((op) => op.path).join(',');
|
|
12
13
|
const inputs = batchOps.map((op) => op.input);
|
|
@@ -1,12 +1,17 @@
|
|
|
1
1
|
import { NonEmptyArray } from '../internals/types';
|
|
2
|
+
import { HTTPBatchStreamLinkOptions } from './HTTPBatchStreamLinkOptions';
|
|
2
3
|
import {
|
|
3
4
|
createHTTPBatchLink,
|
|
4
5
|
RequesterFn,
|
|
5
6
|
} from './internals/createHTTPBatchLink';
|
|
7
|
+
import { getTextDecoder } from './internals/getTextDecoder';
|
|
6
8
|
import { streamingJsonHttpRequester } from './internals/parseJSONStream';
|
|
7
9
|
import { Operation } from './types';
|
|
8
10
|
|
|
9
|
-
const streamRequester: RequesterFn = (
|
|
11
|
+
const streamRequester: RequesterFn<HTTPBatchStreamLinkOptions> = (
|
|
12
|
+
requesterOpts,
|
|
13
|
+
) => {
|
|
14
|
+
const textDecoder = getTextDecoder(requesterOpts.opts.textDecoder);
|
|
10
15
|
return (batchOps, unitResolver) => {
|
|
11
16
|
const path = batchOps.map((op) => op.path).join(',');
|
|
12
17
|
const inputs = batchOps.map((op) => op.input);
|
|
@@ -14,6 +19,7 @@ const streamRequester: RequesterFn = (requesterOpts) => {
|
|
|
14
19
|
const { cancel, promise } = streamingJsonHttpRequester(
|
|
15
20
|
{
|
|
16
21
|
...requesterOpts,
|
|
22
|
+
textDecoder,
|
|
17
23
|
path,
|
|
18
24
|
inputs,
|
|
19
25
|
headers() {
|
package/src/links/index.ts
CHANGED
|
@@ -3,6 +3,7 @@ export * from './types';
|
|
|
3
3
|
export * from './httpBatchLink';
|
|
4
4
|
export * from './httpBatchStreamLink';
|
|
5
5
|
export * from './HTTPBatchLinkOptions';
|
|
6
|
+
export * from './HTTPBatchStreamLinkOptions';
|
|
6
7
|
export * from './httpLink';
|
|
7
8
|
export * from './loggerLink';
|
|
8
9
|
export * from './splitLink';
|
|
@@ -15,11 +15,11 @@ import {
|
|
|
15
15
|
/**
|
|
16
16
|
* @internal
|
|
17
17
|
*/
|
|
18
|
-
export type RequesterFn = (
|
|
18
|
+
export type RequesterFn<TOptions extends HTTPBatchLinkOptions> = (
|
|
19
19
|
requesterOpts: ResolvedHTTPLinkOptions & {
|
|
20
20
|
runtime: TRPCClientRuntime;
|
|
21
21
|
type: ProcedureType;
|
|
22
|
-
opts:
|
|
22
|
+
opts: TOptions;
|
|
23
23
|
},
|
|
24
24
|
) => (
|
|
25
25
|
batchOps: Operation[],
|
|
@@ -32,9 +32,11 @@ export type RequesterFn = (
|
|
|
32
32
|
/**
|
|
33
33
|
* @internal
|
|
34
34
|
*/
|
|
35
|
-
export function createHTTPBatchLink
|
|
35
|
+
export function createHTTPBatchLink<TOptions extends HTTPBatchLinkOptions>(
|
|
36
|
+
requester: RequesterFn<TOptions>,
|
|
37
|
+
) {
|
|
36
38
|
return function httpBatchLink<TRouter extends AnyRouter>(
|
|
37
|
-
opts:
|
|
39
|
+
opts: TOptions,
|
|
38
40
|
): TRPCLink<TRouter> {
|
|
39
41
|
const resolvedOpts = resolveHTTPLinkOptions(opts);
|
|
40
42
|
const maxURLLength = opts.maxURLLength || Infinity;
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
import { TextDecoderEsque } from './streamingUtils';
|
|
2
|
+
|
|
3
|
+
export function getTextDecoder(
|
|
4
|
+
customTextDecoder?: TextDecoderEsque,
|
|
5
|
+
): TextDecoderEsque {
|
|
6
|
+
if (customTextDecoder) {
|
|
7
|
+
return customTextDecoder;
|
|
8
|
+
}
|
|
9
|
+
|
|
10
|
+
if (typeof window !== 'undefined' && window.TextDecoder) {
|
|
11
|
+
return new window.TextDecoder();
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
if (typeof globalThis !== 'undefined' && globalThis.TextDecoder) {
|
|
15
|
+
return new globalThis.TextDecoder();
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
throw new Error('No TextDecoder implementation found');
|
|
19
|
+
}
|
|
@@ -9,6 +9,7 @@ import {
|
|
|
9
9
|
RequestInitEsque,
|
|
10
10
|
ResponseEsque,
|
|
11
11
|
} from '../../internals/types';
|
|
12
|
+
import { TextDecoderEsque } from '../internals/streamingUtils';
|
|
12
13
|
import { HTTPHeaders, PromiseAndCancel, TRPCClientRuntime } from '../types';
|
|
13
14
|
|
|
14
15
|
/**
|
|
@@ -138,6 +139,7 @@ export const jsonHttpRequester: Requester = (opts) => {
|
|
|
138
139
|
export type HTTPRequestOptions = HTTPBaseRequestOptions &
|
|
139
140
|
ContentOptions & {
|
|
140
141
|
headers: () => HTTPHeaders | Promise<HTTPHeaders>;
|
|
142
|
+
TextDecoder?: TextDecoderEsque;
|
|
141
143
|
};
|
|
142
144
|
|
|
143
145
|
export async function fetchHTTPResponse(
|
|
@@ -9,6 +9,7 @@ import {
|
|
|
9
9
|
HTTPBaseRequestOptions,
|
|
10
10
|
HTTPResult,
|
|
11
11
|
} from './httpUtils';
|
|
12
|
+
import { TextDecoderEsque } from './streamingUtils';
|
|
12
13
|
|
|
13
14
|
/**
|
|
14
15
|
* @internal
|
|
@@ -35,6 +36,7 @@ export async function parseJSONStream<TReturn>(opts: {
|
|
|
35
36
|
*/
|
|
36
37
|
parse?: (text: string) => TReturn;
|
|
37
38
|
signal?: AbortSignal;
|
|
39
|
+
textDecoder: TextDecoderEsque;
|
|
38
40
|
}): Promise<void> {
|
|
39
41
|
const parse = opts.parse ?? JSON.parse;
|
|
40
42
|
|
|
@@ -55,11 +57,9 @@ export async function parseJSONStream<TReturn>(opts: {
|
|
|
55
57
|
opts.onSingle(Number(indexAsStr), parse(text));
|
|
56
58
|
};
|
|
57
59
|
|
|
58
|
-
await readLines(opts.readableStream, onLine);
|
|
60
|
+
await readLines(opts.readableStream, onLine, opts.textDecoder);
|
|
59
61
|
}
|
|
60
62
|
|
|
61
|
-
const textDecoder = new TextDecoder();
|
|
62
|
-
|
|
63
63
|
/**
|
|
64
64
|
* Handle transforming a stream of bytes into lines of text.
|
|
65
65
|
* To avoid using AsyncIterators / AsyncGenerators,
|
|
@@ -71,6 +71,7 @@ const textDecoder = new TextDecoder();
|
|
|
71
71
|
async function readLines(
|
|
72
72
|
readableStream: ReadableStream<Uint8Array> | NodeJS.ReadableStream,
|
|
73
73
|
onLine: (line: string) => void,
|
|
74
|
+
textDecoder: TextDecoderEsque,
|
|
74
75
|
) {
|
|
75
76
|
let partOfLine = '';
|
|
76
77
|
|
|
@@ -132,6 +133,7 @@ async function readStandardChunks(
|
|
|
132
133
|
export const streamingJsonHttpRequester = (
|
|
133
134
|
opts: HTTPBaseRequestOptions & {
|
|
134
135
|
headers: () => HTTPHeaders | Promise<HTTPHeaders>;
|
|
136
|
+
textDecoder: TextDecoderEsque;
|
|
135
137
|
},
|
|
136
138
|
onSingle: (index: number, res: HTTPResult) => void,
|
|
137
139
|
) => {
|
|
@@ -150,7 +152,7 @@ export const streamingJsonHttpRequester = (
|
|
|
150
152
|
const promise = responsePromise.then(async (res) => {
|
|
151
153
|
if (!res.body) throw new Error('Received response without body');
|
|
152
154
|
const meta: HTTPResult['meta'] = { response: res };
|
|
153
|
-
return parseJSONStream({
|
|
155
|
+
return parseJSONStream<HTTPResult>({
|
|
154
156
|
readableStream: res.body,
|
|
155
157
|
onSingle,
|
|
156
158
|
parse: (string) => ({
|
|
@@ -158,6 +160,7 @@ export const streamingJsonHttpRequester = (
|
|
|
158
160
|
meta,
|
|
159
161
|
}),
|
|
160
162
|
signal: ac?.signal,
|
|
163
|
+
textDecoder: opts.textDecoder,
|
|
161
164
|
});
|
|
162
165
|
});
|
|
163
166
|
|