@sveltejs/kit 2.60.1 → 2.61.0
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/package.json +8 -9
- package/src/core/postbuild/analyse.js +1 -3
- package/src/core/sync/create_manifest_data/conflict.js +72 -0
- package/src/core/sync/create_manifest_data/index.js +1 -65
- package/src/core/sync/write_non_ambient.js +2 -2
- package/src/core/sync/write_types/index.js +1 -1
- package/src/exports/public.d.ts +23 -30
- package/src/exports/vite/build/build_server.js +36 -13
- package/src/exports/vite/dev/index.js +4 -2
- package/src/exports/vite/index.js +18 -16
- package/src/runtime/app/server/index.js +1 -2
- package/src/runtime/app/server/remote/form.js +10 -0
- package/src/runtime/app/server/remote/query.js +100 -36
- package/src/runtime/client/client.js +13 -8
- package/src/runtime/client/remote-functions/cache.svelte.js +157 -0
- package/src/runtime/client/remote-functions/form.svelte.js +235 -196
- package/src/runtime/client/remote-functions/index.js +2 -2
- package/src/runtime/client/remote-functions/prerender.svelte.js +1 -2
- package/src/runtime/client/remote-functions/query/cache.js +4 -0
- package/src/runtime/client/remote-functions/query/index.js +48 -0
- package/src/runtime/client/remote-functions/query/instance.svelte.js +249 -0
- package/src/runtime/client/remote-functions/query/proxy.js +156 -0
- package/src/runtime/client/remote-functions/query-batch.svelte.js +1 -1
- package/src/runtime/client/remote-functions/query-live/cache.js +4 -0
- package/src/runtime/client/remote-functions/query-live/index.js +31 -0
- package/src/runtime/client/remote-functions/{query-live.svelte.js → query-live/instance.svelte.js} +61 -310
- package/src/runtime/client/remote-functions/query-live/iterator.js +91 -0
- package/src/runtime/client/remote-functions/query-live/proxy.js +144 -0
- package/src/runtime/client/remote-functions/shared.svelte.js +53 -6
- package/src/runtime/client/utils.js +1 -1
- package/src/runtime/form-utils.js +7 -16
- package/src/runtime/server/index.js +2 -3
- package/src/runtime/server/page/actions.js +2 -9
- package/src/runtime/server/page/csp.js +3 -4
- package/src/runtime/server/page/render.js +13 -14
- package/src/runtime/server/respond.js +60 -36
- package/src/runtime/server/utils.js +23 -3
- package/src/types/global-private.d.ts +5 -0
- package/src/types/internal.d.ts +29 -6
- package/src/utils/routing.js +3 -1
- package/src/utils/shared-iterator.js +213 -0
- package/src/version.js +1 -1
- package/types/index.d.ts +27 -31
- package/types/index.d.ts.map +1 -1
- package/src/runtime/client/remote-functions/query.svelte.js +0 -512
|
@@ -1,512 +0,0 @@
|
|
|
1
|
-
/** @import { RemoteQueryFunction } from '@sveltejs/kit' */
|
|
2
|
-
import { app_dir, base } from '$app/paths/internal/client';
|
|
3
|
-
import { app, query_map, query_responses } from '../client.js';
|
|
4
|
-
import {
|
|
5
|
-
get_remote_request_headers,
|
|
6
|
-
is_in_effect,
|
|
7
|
-
QUERY_FUNCTION_ID,
|
|
8
|
-
QUERY_OVERRIDE_KEY,
|
|
9
|
-
QUERY_RESOURCE_KEY,
|
|
10
|
-
remote_request
|
|
11
|
-
} from './shared.svelte.js';
|
|
12
|
-
import * as devalue from 'devalue';
|
|
13
|
-
import { DEV } from 'esm-env';
|
|
14
|
-
import { noop } from '../../../utils/functions.js';
|
|
15
|
-
import { with_resolvers } from '../../../utils/promise.js';
|
|
16
|
-
import { tick, untrack } from 'svelte';
|
|
17
|
-
import { create_remote_key, stringify_remote_arg, unfriendly_hydratable } from '../../shared.js';
|
|
18
|
-
|
|
19
|
-
/**
|
|
20
|
-
* @template T
|
|
21
|
-
* @typedef {{
|
|
22
|
-
* count: number;
|
|
23
|
-
* resource: Query<T>;
|
|
24
|
-
* cleanup: () => void;
|
|
25
|
-
* }} RemoteQueryCacheEntry
|
|
26
|
-
*/
|
|
27
|
-
|
|
28
|
-
/**
|
|
29
|
-
* @param {string} id
|
|
30
|
-
* @returns {RemoteQueryFunction<any, any>}
|
|
31
|
-
*/
|
|
32
|
-
export function query(id) {
|
|
33
|
-
if (DEV) {
|
|
34
|
-
// If this reruns as part of HMR, refresh the query
|
|
35
|
-
const entries = query_map.get(id);
|
|
36
|
-
|
|
37
|
-
if (entries) {
|
|
38
|
-
for (const entry of entries.values()) {
|
|
39
|
-
void entry.resource.refresh();
|
|
40
|
-
}
|
|
41
|
-
}
|
|
42
|
-
}
|
|
43
|
-
|
|
44
|
-
/** @type {RemoteQueryFunction<any, any>} */
|
|
45
|
-
const wrapper = (arg) => {
|
|
46
|
-
return new QueryProxy(id, arg, async (key, payload) => {
|
|
47
|
-
const url = `${base}/${app_dir}/remote/${id}${payload ? `?payload=${payload}` : ''}`;
|
|
48
|
-
|
|
49
|
-
const serialized = await unfriendly_hydratable(key, () =>
|
|
50
|
-
remote_request(url, get_remote_request_headers())
|
|
51
|
-
);
|
|
52
|
-
|
|
53
|
-
return devalue.parse(serialized, app.decoders);
|
|
54
|
-
});
|
|
55
|
-
};
|
|
56
|
-
|
|
57
|
-
Object.defineProperty(wrapper, QUERY_FUNCTION_ID, { value: id });
|
|
58
|
-
|
|
59
|
-
return wrapper;
|
|
60
|
-
}
|
|
61
|
-
|
|
62
|
-
/**
|
|
63
|
-
* The actual query instance. There should only ever be one active query instance per key.
|
|
64
|
-
*
|
|
65
|
-
* @template T
|
|
66
|
-
* @implements {Promise<T>}
|
|
67
|
-
*/
|
|
68
|
-
export class Query {
|
|
69
|
-
/** @type {string} */
|
|
70
|
-
#key;
|
|
71
|
-
|
|
72
|
-
/** @type {() => Promise<T>} */
|
|
73
|
-
#fn;
|
|
74
|
-
#loading = $state(true);
|
|
75
|
-
/** @type {Array<(value: undefined) => void>} */
|
|
76
|
-
#latest = [];
|
|
77
|
-
|
|
78
|
-
/** @type {boolean} */
|
|
79
|
-
#ready = $state(false);
|
|
80
|
-
/** @type {T | undefined} */
|
|
81
|
-
#raw = $state.raw();
|
|
82
|
-
/** @type {Promise<void> | null} */
|
|
83
|
-
#promise = $state.raw(null);
|
|
84
|
-
/** @type {Array<(old: T) => T>} */
|
|
85
|
-
#overrides = $state([]);
|
|
86
|
-
|
|
87
|
-
/** @type {T | undefined} */
|
|
88
|
-
#current = $derived.by(() => {
|
|
89
|
-
// don't reduce undefined value
|
|
90
|
-
if (!this.#ready) return undefined;
|
|
91
|
-
|
|
92
|
-
return this.#overrides.reduce((v, r) => r(v), /** @type {T} */ (this.#raw));
|
|
93
|
-
});
|
|
94
|
-
|
|
95
|
-
/** @type {any} */
|
|
96
|
-
#error = $state.raw(undefined);
|
|
97
|
-
|
|
98
|
-
/** @type {Promise<T>['then']} */
|
|
99
|
-
// @ts-expect-error TS doesn't understand that the promise returns something
|
|
100
|
-
#then = $derived.by(() => {
|
|
101
|
-
const p = this.#get_promise();
|
|
102
|
-
this.#overrides.length;
|
|
103
|
-
|
|
104
|
-
return (resolve, reject) => {
|
|
105
|
-
const result = p.then(tick).then(() => /** @type {T} */ (this.#current));
|
|
106
|
-
|
|
107
|
-
if (resolve || reject) {
|
|
108
|
-
return result.then(resolve, reject);
|
|
109
|
-
}
|
|
110
|
-
|
|
111
|
-
return result;
|
|
112
|
-
};
|
|
113
|
-
});
|
|
114
|
-
|
|
115
|
-
/**
|
|
116
|
-
* @param {string} key
|
|
117
|
-
* @param {() => Promise<T>} fn
|
|
118
|
-
*/
|
|
119
|
-
constructor(key, fn) {
|
|
120
|
-
this.#key = key;
|
|
121
|
-
this.#fn = fn;
|
|
122
|
-
}
|
|
123
|
-
|
|
124
|
-
#get_promise() {
|
|
125
|
-
void untrack(() => (this.#promise ??= this.#run()));
|
|
126
|
-
return /** @type {Promise<T>} */ (this.#promise);
|
|
127
|
-
}
|
|
128
|
-
|
|
129
|
-
#start() {
|
|
130
|
-
// there is a really weird bug with untrack and writes and initializations
|
|
131
|
-
// every time you see this comment, try removing the `tick.then` here and see
|
|
132
|
-
// if all the tests still pass with the latest svelte version
|
|
133
|
-
// if they do, congrats, you can remove tick.then
|
|
134
|
-
void tick().then(() => this.#get_promise());
|
|
135
|
-
}
|
|
136
|
-
|
|
137
|
-
#clear_pending() {
|
|
138
|
-
this.#latest.forEach((r) => r(undefined));
|
|
139
|
-
this.#latest.length = 0;
|
|
140
|
-
}
|
|
141
|
-
|
|
142
|
-
#run() {
|
|
143
|
-
this.#loading = true;
|
|
144
|
-
|
|
145
|
-
const { promise, resolve, reject } = with_resolvers();
|
|
146
|
-
|
|
147
|
-
this.#latest.push(resolve);
|
|
148
|
-
|
|
149
|
-
Promise.resolve(this.#fn())
|
|
150
|
-
.then((value) => {
|
|
151
|
-
// Skip the response if resource was refreshed with a later promise while we were waiting for this one to resolve
|
|
152
|
-
const idx = this.#latest.indexOf(resolve);
|
|
153
|
-
if (idx === -1) return;
|
|
154
|
-
|
|
155
|
-
// Untrack this to not trigger mutation validation errors which can occur if you do e.g. $derived({ a: await queryA(), b: await queryB() })
|
|
156
|
-
untrack(() => {
|
|
157
|
-
this.#latest.splice(0, idx).forEach((r) => r(undefined));
|
|
158
|
-
this.#ready = true;
|
|
159
|
-
this.#loading = false;
|
|
160
|
-
this.#raw = value;
|
|
161
|
-
this.#error = undefined;
|
|
162
|
-
});
|
|
163
|
-
|
|
164
|
-
resolve(undefined);
|
|
165
|
-
})
|
|
166
|
-
.catch((e) => {
|
|
167
|
-
// TODO: Our behavior here could be better:
|
|
168
|
-
// - We should not reject on redirects, but should hook into the router
|
|
169
|
-
// to ensure the query is properly refreshed before the navigation completes
|
|
170
|
-
// - Instead of failing on transport-level errors, we should probably do what
|
|
171
|
-
// LiveQuery does and preserve the last known good value and retry the connection
|
|
172
|
-
const idx = this.#latest.indexOf(resolve);
|
|
173
|
-
if (idx === -1) return;
|
|
174
|
-
|
|
175
|
-
untrack(() => {
|
|
176
|
-
this.#latest.splice(0, idx).forEach((r) => r(undefined));
|
|
177
|
-
this.#error = e;
|
|
178
|
-
this.#loading = false;
|
|
179
|
-
});
|
|
180
|
-
|
|
181
|
-
reject(e);
|
|
182
|
-
});
|
|
183
|
-
|
|
184
|
-
return promise;
|
|
185
|
-
}
|
|
186
|
-
|
|
187
|
-
get then() {
|
|
188
|
-
// TODO this should be unnecessary but due to the bug described
|
|
189
|
-
// in #start, we need to do this in some circumstances
|
|
190
|
-
this.#start();
|
|
191
|
-
return this.#then;
|
|
192
|
-
}
|
|
193
|
-
|
|
194
|
-
get catch() {
|
|
195
|
-
this.#start();
|
|
196
|
-
this.#then;
|
|
197
|
-
return (/** @type {any} */ reject) => {
|
|
198
|
-
return this.#then(undefined, reject);
|
|
199
|
-
};
|
|
200
|
-
}
|
|
201
|
-
|
|
202
|
-
get finally() {
|
|
203
|
-
this.#start();
|
|
204
|
-
this.#then;
|
|
205
|
-
return (/** @type {any} */ fn) => {
|
|
206
|
-
return this.#then(
|
|
207
|
-
(value) => {
|
|
208
|
-
fn();
|
|
209
|
-
return value;
|
|
210
|
-
},
|
|
211
|
-
(error) => {
|
|
212
|
-
fn();
|
|
213
|
-
throw error;
|
|
214
|
-
}
|
|
215
|
-
);
|
|
216
|
-
};
|
|
217
|
-
}
|
|
218
|
-
|
|
219
|
-
get current() {
|
|
220
|
-
this.#start();
|
|
221
|
-
return this.#current;
|
|
222
|
-
}
|
|
223
|
-
|
|
224
|
-
get error() {
|
|
225
|
-
this.#start();
|
|
226
|
-
return this.#error;
|
|
227
|
-
}
|
|
228
|
-
|
|
229
|
-
/**
|
|
230
|
-
* Returns true if the resource is loading or reloading.
|
|
231
|
-
*/
|
|
232
|
-
get loading() {
|
|
233
|
-
this.#start();
|
|
234
|
-
return this.#loading;
|
|
235
|
-
}
|
|
236
|
-
|
|
237
|
-
/**
|
|
238
|
-
* Returns true once the resource has been loaded for the first time.
|
|
239
|
-
*/
|
|
240
|
-
get ready() {
|
|
241
|
-
this.#start();
|
|
242
|
-
return this.#ready;
|
|
243
|
-
}
|
|
244
|
-
|
|
245
|
-
/**
|
|
246
|
-
* @returns {Promise<void>}
|
|
247
|
-
*/
|
|
248
|
-
refresh() {
|
|
249
|
-
delete query_responses[this.#key];
|
|
250
|
-
return (this.#promise = this.#run());
|
|
251
|
-
}
|
|
252
|
-
|
|
253
|
-
/**
|
|
254
|
-
* @param {T} value
|
|
255
|
-
*/
|
|
256
|
-
set(value) {
|
|
257
|
-
this.#clear_pending();
|
|
258
|
-
this.#ready = true;
|
|
259
|
-
this.#loading = false;
|
|
260
|
-
this.#error = undefined;
|
|
261
|
-
this.#raw = value;
|
|
262
|
-
this.#promise = Promise.resolve();
|
|
263
|
-
}
|
|
264
|
-
|
|
265
|
-
/**
|
|
266
|
-
* @param {unknown} error
|
|
267
|
-
*/
|
|
268
|
-
fail(error) {
|
|
269
|
-
this.#clear_pending();
|
|
270
|
-
this.#loading = false;
|
|
271
|
-
this.#error = error;
|
|
272
|
-
|
|
273
|
-
const promise = Promise.reject(error);
|
|
274
|
-
|
|
275
|
-
promise.catch(noop);
|
|
276
|
-
this.#promise = promise;
|
|
277
|
-
}
|
|
278
|
-
|
|
279
|
-
/**
|
|
280
|
-
* @param {(old: T) => T} fn
|
|
281
|
-
* @returns {(() => void) & { [QUERY_OVERRIDE_KEY]: string }}
|
|
282
|
-
*/
|
|
283
|
-
withOverride(fn) {
|
|
284
|
-
this.#overrides.push(fn);
|
|
285
|
-
|
|
286
|
-
const release = /** @type {(() => void) & { [QUERY_OVERRIDE_KEY]: string }} */ (
|
|
287
|
-
() => {
|
|
288
|
-
const i = this.#overrides.indexOf(fn);
|
|
289
|
-
|
|
290
|
-
if (i !== -1) {
|
|
291
|
-
this.#overrides.splice(i, 1);
|
|
292
|
-
}
|
|
293
|
-
}
|
|
294
|
-
);
|
|
295
|
-
|
|
296
|
-
Object.defineProperty(release, QUERY_OVERRIDE_KEY, { value: this.#key });
|
|
297
|
-
|
|
298
|
-
return release;
|
|
299
|
-
}
|
|
300
|
-
|
|
301
|
-
get [Symbol.toStringTag]() {
|
|
302
|
-
return 'Query';
|
|
303
|
-
}
|
|
304
|
-
}
|
|
305
|
-
|
|
306
|
-
/**
|
|
307
|
-
* Manages the caching layer between the user and the actual {@link Query} instance. This is the thing
|
|
308
|
-
* the developer actually gets to interact with in their application code.
|
|
309
|
-
*
|
|
310
|
-
* @template T
|
|
311
|
-
* @implements {Promise<T>}
|
|
312
|
-
*/
|
|
313
|
-
export class QueryProxy {
|
|
314
|
-
#id;
|
|
315
|
-
#key;
|
|
316
|
-
#payload;
|
|
317
|
-
#fn;
|
|
318
|
-
#active = true;
|
|
319
|
-
/**
|
|
320
|
-
* Whether this proxy was created in a tracking context.
|
|
321
|
-
* @readonly
|
|
322
|
-
*/
|
|
323
|
-
#tracking = is_in_effect();
|
|
324
|
-
|
|
325
|
-
/**
|
|
326
|
-
* @param {string} id
|
|
327
|
-
* @param {any} arg
|
|
328
|
-
* @param {(key: string, payload: string) => Promise<T>} fn
|
|
329
|
-
*/
|
|
330
|
-
constructor(id, arg, fn) {
|
|
331
|
-
this.#id = id;
|
|
332
|
-
this.#payload = stringify_remote_arg(arg, app.hooks.transport);
|
|
333
|
-
this.#key = create_remote_key(id, this.#payload);
|
|
334
|
-
Object.defineProperty(this, QUERY_RESOURCE_KEY, { value: this.#key });
|
|
335
|
-
this.#fn = fn;
|
|
336
|
-
|
|
337
|
-
if (!this.#tracking) {
|
|
338
|
-
this.#active = false;
|
|
339
|
-
return;
|
|
340
|
-
}
|
|
341
|
-
|
|
342
|
-
const entry = this.#get_or_create_cache_entry();
|
|
343
|
-
|
|
344
|
-
$effect.pre(() => () => {
|
|
345
|
-
const die = this.#release(entry);
|
|
346
|
-
void tick().then(die);
|
|
347
|
-
});
|
|
348
|
-
}
|
|
349
|
-
|
|
350
|
-
/** @returns {RemoteQueryCacheEntry<T>} */
|
|
351
|
-
#get_or_create_cache_entry() {
|
|
352
|
-
let query_instances = query_map.get(this.#id);
|
|
353
|
-
|
|
354
|
-
if (!query_instances) {
|
|
355
|
-
query_instances = new Map();
|
|
356
|
-
query_map.set(this.#id, query_instances);
|
|
357
|
-
}
|
|
358
|
-
|
|
359
|
-
let this_instance = query_instances.get(this.#payload);
|
|
360
|
-
|
|
361
|
-
if (!this_instance) {
|
|
362
|
-
const c = (this_instance = {
|
|
363
|
-
count: 0,
|
|
364
|
-
resource: /** @type {Query<T>} */ (/** @type {unknown} */ (null)),
|
|
365
|
-
cleanup: /** @type {() => void} */ (/** @type {unknown} */ (null))
|
|
366
|
-
});
|
|
367
|
-
|
|
368
|
-
c.cleanup = $effect.root(() => {
|
|
369
|
-
c.resource = new Query(this.#key, () => this.#fn(this.#key, this.#payload));
|
|
370
|
-
});
|
|
371
|
-
|
|
372
|
-
query_instances.set(this.#payload, this_instance);
|
|
373
|
-
}
|
|
374
|
-
|
|
375
|
-
this_instance.count += 1;
|
|
376
|
-
|
|
377
|
-
return this_instance;
|
|
378
|
-
}
|
|
379
|
-
|
|
380
|
-
/**
|
|
381
|
-
* @param {RemoteQueryCacheEntry<T>} entry
|
|
382
|
-
* @param {boolean} [deactivate]
|
|
383
|
-
* @returns
|
|
384
|
-
*/
|
|
385
|
-
#release(entry, deactivate = true) {
|
|
386
|
-
this.#active &&= !deactivate;
|
|
387
|
-
entry.count -= 1;
|
|
388
|
-
|
|
389
|
-
return () => {
|
|
390
|
-
const query_instances = query_map.get(this.#id);
|
|
391
|
-
const this_instance = query_instances?.get(this.#payload);
|
|
392
|
-
|
|
393
|
-
if (this_instance?.count === 0) {
|
|
394
|
-
this_instance.cleanup();
|
|
395
|
-
query_instances?.delete(this.#payload);
|
|
396
|
-
}
|
|
397
|
-
if (query_instances?.size === 0) {
|
|
398
|
-
query_map.delete(this.#id);
|
|
399
|
-
}
|
|
400
|
-
};
|
|
401
|
-
}
|
|
402
|
-
|
|
403
|
-
#safe_get_cached_query() {
|
|
404
|
-
return query_map.get(this.#id)?.get(this.#payload)?.resource;
|
|
405
|
-
}
|
|
406
|
-
|
|
407
|
-
get current() {
|
|
408
|
-
return this.#safe_get_cached_query()?.current;
|
|
409
|
-
}
|
|
410
|
-
|
|
411
|
-
get error() {
|
|
412
|
-
return this.#safe_get_cached_query()?.error;
|
|
413
|
-
}
|
|
414
|
-
|
|
415
|
-
get loading() {
|
|
416
|
-
return this.#safe_get_cached_query()?.loading ?? false;
|
|
417
|
-
}
|
|
418
|
-
|
|
419
|
-
get ready() {
|
|
420
|
-
return this.#safe_get_cached_query()?.ready ?? false;
|
|
421
|
-
}
|
|
422
|
-
|
|
423
|
-
run() {
|
|
424
|
-
if (is_in_effect()) {
|
|
425
|
-
throw new Error(
|
|
426
|
-
'On the client, .run() can only be called outside render, e.g. in universal `load` functions and event handlers. In render, await the query directly'
|
|
427
|
-
);
|
|
428
|
-
}
|
|
429
|
-
|
|
430
|
-
if (Object.hasOwn(query_responses, this.#key)) {
|
|
431
|
-
return Promise.resolve(query_responses[this.#key]);
|
|
432
|
-
}
|
|
433
|
-
return this.#fn(this.#key, this.#payload);
|
|
434
|
-
}
|
|
435
|
-
|
|
436
|
-
refresh() {
|
|
437
|
-
return this.#safe_get_cached_query()?.refresh() ?? Promise.resolve();
|
|
438
|
-
}
|
|
439
|
-
|
|
440
|
-
/** @type {Query<T>['set']} */
|
|
441
|
-
set(value) {
|
|
442
|
-
this.#safe_get_cached_query()?.set(value);
|
|
443
|
-
}
|
|
444
|
-
|
|
445
|
-
/** @type {Query<T>['withOverride']} */
|
|
446
|
-
withOverride(fn) {
|
|
447
|
-
const entry = this.#get_or_create_cache_entry();
|
|
448
|
-
const override = /** @type {Query<T>} */ (entry.resource).withOverride(fn);
|
|
449
|
-
|
|
450
|
-
const release = /** @type {(() => void) & { [QUERY_OVERRIDE_KEY]: string }} */ (
|
|
451
|
-
() => {
|
|
452
|
-
override();
|
|
453
|
-
this.#release(entry, false)();
|
|
454
|
-
}
|
|
455
|
-
);
|
|
456
|
-
|
|
457
|
-
Object.defineProperty(release, QUERY_OVERRIDE_KEY, { value: override[QUERY_OVERRIDE_KEY] });
|
|
458
|
-
|
|
459
|
-
return release;
|
|
460
|
-
}
|
|
461
|
-
|
|
462
|
-
#get_cached_query() {
|
|
463
|
-
// TODO iterate on error messages
|
|
464
|
-
if (!this.#tracking) {
|
|
465
|
-
throw new Error(
|
|
466
|
-
'This query was not created in a reactive context and cannot be awaited. Use `.run()` to execute the query instead.'
|
|
467
|
-
);
|
|
468
|
-
}
|
|
469
|
-
|
|
470
|
-
if (!this.#active) {
|
|
471
|
-
throw new Error(
|
|
472
|
-
'This query instance is no longer active and can no longer be awaited. ' +
|
|
473
|
-
'This typically means you created the query in a tracking context and stashed it somewhere outside of a tracking context.'
|
|
474
|
-
);
|
|
475
|
-
}
|
|
476
|
-
|
|
477
|
-
const cached = query_map.get(this.#id)?.get(this.#payload);
|
|
478
|
-
|
|
479
|
-
if (!cached) {
|
|
480
|
-
// The only case where `this.#active` can be `true` is when we've added an entry to `query_map`, and the
|
|
481
|
-
// only way that entry can get removed is if this instance (and all others) have been deactivated.
|
|
482
|
-
// So if we get here, someone (us, check git blame and point fingers) did `entry.count -= 1` improperly.
|
|
483
|
-
throw new Error(
|
|
484
|
-
'No cached query found. This should be impossible. Please file a bug report.'
|
|
485
|
-
);
|
|
486
|
-
}
|
|
487
|
-
|
|
488
|
-
return cached.resource;
|
|
489
|
-
}
|
|
490
|
-
|
|
491
|
-
/** @type {Query<T>['then']} */
|
|
492
|
-
get then() {
|
|
493
|
-
const cached = this.#get_cached_query();
|
|
494
|
-
return cached.then.bind(cached);
|
|
495
|
-
}
|
|
496
|
-
|
|
497
|
-
/** @type {Query<T>['catch']} */
|
|
498
|
-
get catch() {
|
|
499
|
-
const cached = this.#get_cached_query();
|
|
500
|
-
return cached.catch.bind(cached);
|
|
501
|
-
}
|
|
502
|
-
|
|
503
|
-
/** @type {Query<T>['finally']} */
|
|
504
|
-
get finally() {
|
|
505
|
-
const cached = this.#get_cached_query();
|
|
506
|
-
return cached.finally.bind(cached);
|
|
507
|
-
}
|
|
508
|
-
|
|
509
|
-
get [Symbol.toStringTag]() {
|
|
510
|
-
return 'QueryProxy';
|
|
511
|
-
}
|
|
512
|
-
}
|