@solidjs/web 2.0.0-beta.20 → 2.0.0-beta.21

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/dev.cjs CHANGED
@@ -662,6 +662,13 @@ function hydrate$1(code, element, options = {}) {
662
662
  }
663
663
  };
664
664
  solidJs.sharedConfig.registry = new Map();
665
+ if (!solidJs.sharedConfig.boundaryScopes) solidJs.sharedConfig.boundaryScopes = new Map();
666
+ solidJs.sharedConfig.captureBoundaryScope = id => {
667
+ if (solidJs.sharedConfig.registry) solidJs.sharedConfig.boundaryScopes.set(id, {
668
+ registry: solidJs.sharedConfig.registry,
669
+ gather: solidJs.sharedConfig.gather
670
+ });
671
+ };
665
672
  solidJs.sharedConfig.hydrating = true;
666
673
  {
667
674
  solidJs.sharedConfig.verifyHydration = () => {
package/dist/dev.js CHANGED
@@ -661,6 +661,13 @@ function hydrate$1(code, element, options = {}) {
661
661
  }
662
662
  };
663
663
  sharedConfig.registry = new Map();
664
+ if (!sharedConfig.boundaryScopes) sharedConfig.boundaryScopes = new Map();
665
+ sharedConfig.captureBoundaryScope = id => {
666
+ if (sharedConfig.registry) sharedConfig.boundaryScopes.set(id, {
667
+ registry: sharedConfig.registry,
668
+ gather: sharedConfig.gather
669
+ });
670
+ };
664
671
  sharedConfig.hydrating = true;
665
672
  {
666
673
  sharedConfig.verifyHydration = () => {
package/dist/web.cjs CHANGED
@@ -657,6 +657,13 @@ function hydrate$1(code, element, options = {}) {
657
657
  }
658
658
  };
659
659
  solidJs.sharedConfig.registry = new Map();
660
+ if (!solidJs.sharedConfig.boundaryScopes) solidJs.sharedConfig.boundaryScopes = new Map();
661
+ solidJs.sharedConfig.captureBoundaryScope = id => {
662
+ if (solidJs.sharedConfig.registry) solidJs.sharedConfig.boundaryScopes.set(id, {
663
+ registry: solidJs.sharedConfig.registry,
664
+ gather: solidJs.sharedConfig.gather
665
+ });
666
+ };
660
667
  solidJs.sharedConfig.hydrating = true;
661
668
  const rootMapping = globalThis._$HY.r && globalThis._$HY.r["_assets"];
662
669
  if (rootMapping && typeof rootMapping === "object") {
package/dist/web.js CHANGED
@@ -656,6 +656,13 @@ function hydrate$1(code, element, options = {}) {
656
656
  }
657
657
  };
658
658
  sharedConfig.registry = new Map();
659
+ if (!sharedConfig.boundaryScopes) sharedConfig.boundaryScopes = new Map();
660
+ sharedConfig.captureBoundaryScope = id => {
661
+ if (sharedConfig.registry) sharedConfig.boundaryScopes.set(id, {
662
+ registry: sharedConfig.registry,
663
+ gather: sharedConfig.gather
664
+ });
665
+ };
659
666
  sharedConfig.hydrating = true;
660
667
  const rootMapping = globalThis._$HY.r && globalThis._$HY.r["_assets"];
661
668
  if (rootMapping && typeof rootMapping === "object") {
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@solidjs/web",
3
3
  "description": "Solid's web runtime: client rendering, hydration, SSR, and DOM-specific control flow (Portal, Dynamic).",
4
- "version": "2.0.0-beta.20",
4
+ "version": "2.0.0-beta.21",
5
5
  "author": "Ryan Carniato",
6
6
  "license": "MIT",
7
7
  "homepage": "https://solidjs.com",
@@ -224,10 +224,10 @@
224
224
  "seroval-plugins": "~1.5.4"
225
225
  },
226
226
  "peerDependencies": {
227
- "solid-js": "^2.0.0-beta.20"
227
+ "solid-js": "^2.0.0-beta.21"
228
228
  },
229
229
  "devDependencies": {
230
- "solid-js": "2.0.0-beta.20"
230
+ "solid-js": "2.0.0-beta.21"
231
231
  },
232
232
  "scripts": {
233
233
  "build": "npm-run-all -nl build:clean types:copy-jsx build:js",
@@ -56,9 +56,38 @@ function configureServerFunctionsCodec(codec) {
56
56
  function getServerFunctionsCodec() {
57
57
  return codecConfig.codec;
58
58
  }
59
+ const flightConfig = {
60
+ consumer: undefined
61
+ };
62
+ function subscribeFlightData(consumer) {
63
+ flightConfig.consumer = consumer;
64
+ return () => {
65
+ if (flightConfig.consumer === consumer) flightConfig.consumer = undefined;
66
+ };
67
+ }
68
+ function getFlightDataConsumer() {
69
+ return flightConfig.consumer;
70
+ }
71
+ const SERVER_FUNCTION_METADATA = Symbol.for("solid.ServerFunctionMetadata");
72
+ function getServerFunctionMetadata(fn) {
73
+ if (typeof fn !== "function") return undefined;
74
+ return fn[SERVER_FUNCTION_METADATA] || undefined;
75
+ }
76
+ function isServerFunction(fn) {
77
+ return typeof fn === "function" && !!fn[SERVER_FUNCTION_METADATA];
78
+ }
79
+ function withMeta(fn, meta) {
80
+ const metadata = getServerFunctionMetadata(fn);
81
+ if (!metadata) {
82
+ throw new Error("withMeta expects a server function reference");
83
+ }
84
+ Object.assign(metadata, meta);
85
+ return fn;
86
+ }
59
87
  const FUNCTION_HEADER = "X-Server-Function-Id";
60
88
  const INSTANCE_HEADER = "X-Server-Function-Instance";
61
89
  const BODY_FORMAT_HEADER = "X-Server-Function-Format";
90
+ const SINGLE_FLIGHT_HEADER = "X-Single-Flight";
62
91
  const FILE_FORM_KEY = "__server_function_file__";
63
92
  const BodyFormat = {
64
93
  Serialized: "0",
@@ -271,30 +300,44 @@ async function decodeResponse(response, codecOptions) {
271
300
  }
272
301
 
273
302
  const config = {
274
- endpoint: "/_server"
303
+ endpoint: "/_server",
304
+ prepareRequest: undefined
275
305
  };
276
306
  function configureServerFunctionsClient({
277
307
  endpoint,
278
- codec
308
+ codec,
309
+ prepareRequest
279
310
  } = {}) {
280
311
  if (endpoint !== undefined) config.endpoint = endpoint;
281
312
  if (codec !== undefined) configureServerFunctionsCodec(codec);
313
+ if (prepareRequest !== undefined) config.prepareRequest = prepareRequest;
282
314
  }
283
315
  let INSTANCE = 0;
284
- function createRequest(base, id, instance, options) {
285
- return fetch(base, {
316
+ async function createRequest(base, id, instance, options, meta) {
317
+ const headers = {
318
+ ...options.headers,
319
+ [FUNCTION_HEADER]: id,
320
+ [INSTANCE_HEADER]: instance
321
+ };
322
+ if (getFlightDataConsumer() && (!options.method || options.method.toUpperCase() !== "GET")) {
323
+ headers[SINGLE_FLIGHT_HEADER] = "true";
324
+ }
325
+ let init = {
286
326
  method: "POST",
287
327
  ...options,
288
- headers: {
289
- ...options.headers,
290
- [FUNCTION_HEADER]: id,
291
- [INSTANCE_HEADER]: instance
292
- }
293
- });
328
+ headers
329
+ };
330
+ if (config.prepareRequest) {
331
+ init = (await config.prepareRequest(init, {
332
+ id,
333
+ meta
334
+ })) || init;
335
+ }
336
+ return fetch(base, init);
294
337
  }
295
- async function initializeResponse(base, id, instance, options, args) {
338
+ async function initializeResponse(base, id, instance, options, args, meta) {
296
339
  if (args.length === 0) {
297
- return createRequest(base, id, instance, options);
340
+ return createRequest(base, id, instance, options, meta);
298
341
  }
299
342
  if (args.length === 1) {
300
343
  const result = getHeadersAndBody(args[0]);
@@ -306,7 +349,7 @@ async function initializeResponse(base, id, instance, options, args) {
306
349
  ...options.headers,
307
350
  ...result.headers
308
351
  }
309
- });
352
+ }, meta);
310
353
  }
311
354
  }
312
355
  return createRequest(base, id, instance, {
@@ -317,12 +360,25 @@ async function initializeResponse(base, id, instance, options, args) {
317
360
  "Content-Type": "text/plain",
318
361
  [BODY_FORMAT_HEADER]: BodyFormat.Serialized
319
362
  }
320
- });
363
+ }, meta);
321
364
  }
322
- async function fetchServerFunction(base, id, options, args) {
365
+ async function fetchServerFunction(base, id, options, args, meta) {
323
366
  const instance = `server-function:${INSTANCE++}`;
324
- const response = await initializeResponse(base, id, instance, options, args);
325
- if (response.headers.has("Location") || response.headers.has("X-Revalidate") || response.headers.has("X-Single-Flight")) {
367
+ const response = await initializeResponse(base, id, instance, options, args, meta);
368
+ if (response.headers.has(SINGLE_FLIGHT_HEADER)) {
369
+ const consumer = getFlightDataConsumer();
370
+ if (consumer) {
371
+ const payload = await decodeResponse(response);
372
+ await consumer(payload.data, {
373
+ response
374
+ });
375
+ if (response.headers.has("X-Server-Function-Error") && !response.headers.has("Location") && !response.headers.has("X-Revalidate")) {
376
+ throw payload.value;
377
+ }
378
+ return payload.value;
379
+ }
380
+ }
381
+ if (response.headers.has("Location") || response.headers.has("X-Revalidate") || response.headers.has(SINGLE_FLIGHT_HEADER)) {
326
382
  return response;
327
383
  }
328
384
  const result = await decodeResponse(response.clone());
@@ -331,40 +387,62 @@ async function fetchServerFunction(base, id, options, args) {
331
387
  }
332
388
  return result;
333
389
  }
334
- function createServerReference(id) {
335
- const fn = (...args) => fetchServerFunction(config.endpoint, id, {}, args);
390
+ function createServerReference(id, name) {
391
+ const metadata = name === undefined ? {} : {
392
+ name
393
+ };
394
+ const fn = (...args) => fetchServerFunction(config.endpoint, id, {}, args, metadata);
395
+ fn[SERVER_FUNCTION_METADATA] = metadata;
336
396
  return new Proxy(fn, {
337
- get(target, prop, receiver) {
397
+ get(target, prop) {
398
+ if (prop === "id") return id;
338
399
  if (prop === "url") {
339
400
  return `${config.endpoint}?id=${encodeURIComponent(id)}`;
340
401
  }
341
- if (prop === "GET") {
342
- return receiver.withOptions({
343
- method: "GET"
344
- });
345
- }
346
- if (prop === "withOptions") {
347
- const url = `${config.endpoint}?id=${encodeURIComponent(id)}`;
348
- return options => {
349
- const wrapped = async (...args) => {
350
- const encodeArgs = options.method && options.method.toUpperCase() === "GET";
351
- return fetchServerFunction(encodeArgs ? url + (args.length ? `&args=${encodeURIComponent(await serializeString(args, getServerFunctionsCodec()))}` : "") : config.endpoint, id, options, encodeArgs ? [] : args);
352
- };
353
- wrapped.url = url;
354
- return wrapped;
355
- };
356
- }
357
402
  return target[prop];
358
403
  }
359
404
  });
360
405
  }
406
+ function GET(fn) {
407
+ if (!isServerFunction(fn)) {
408
+ throw new Error("GET expects a server function reference");
409
+ }
410
+ const id = fn.id;
411
+ const metadata = {
412
+ ...getServerFunctionMetadata(fn)
413
+ };
414
+ const wrapped = async (...args) => {
415
+ let base = `${config.endpoint}?id=${encodeURIComponent(id)}`;
416
+ if (args.length) {
417
+ base += `&args=${encodeURIComponent(await serializeString(args, getServerFunctionsCodec()))}`;
418
+ }
419
+ return fetchServerFunction(base, id, {
420
+ method: "GET"
421
+ }, [], metadata);
422
+ };
423
+ wrapped[SERVER_FUNCTION_METADATA] = metadata;
424
+ wrapped.id = id;
425
+ Object.defineProperty(wrapped, "url", {
426
+ get: () => `${config.endpoint}?id=${encodeURIComponent(id)}`,
427
+ configurable: true
428
+ });
429
+ return withMeta(wrapped, {
430
+ method: "GET"
431
+ });
432
+ }
361
433
  function registerServerReference() {
362
434
  throw new Error("registerServerReference must not be called in the client build");
363
435
  }
364
436
 
365
437
  exports.FUNCTION_HEADER = FUNCTION_HEADER;
438
+ exports.GET = GET;
366
439
  exports.INSTANCE_HEADER = INSTANCE_HEADER;
440
+ exports.SINGLE_FLIGHT_HEADER = SINGLE_FLIGHT_HEADER;
367
441
  exports.configureServerFunctionsClient = configureServerFunctionsClient;
368
442
  exports.createServerReference = createServerReference;
369
443
  exports.decodeResponse = decodeResponse;
444
+ exports.getServerFunctionMetadata = getServerFunctionMetadata;
445
+ exports.isServerFunction = isServerFunction;
370
446
  exports.registerServerReference = registerServerReference;
447
+ exports.subscribeFlightData = subscribeFlightData;
448
+ exports.withMeta = withMeta;
@@ -54,9 +54,38 @@ function configureServerFunctionsCodec(codec) {
54
54
  function getServerFunctionsCodec() {
55
55
  return codecConfig.codec;
56
56
  }
57
+ const flightConfig = {
58
+ consumer: undefined
59
+ };
60
+ function subscribeFlightData(consumer) {
61
+ flightConfig.consumer = consumer;
62
+ return () => {
63
+ if (flightConfig.consumer === consumer) flightConfig.consumer = undefined;
64
+ };
65
+ }
66
+ function getFlightDataConsumer() {
67
+ return flightConfig.consumer;
68
+ }
69
+ const SERVER_FUNCTION_METADATA = Symbol.for("solid.ServerFunctionMetadata");
70
+ function getServerFunctionMetadata(fn) {
71
+ if (typeof fn !== "function") return undefined;
72
+ return fn[SERVER_FUNCTION_METADATA] || undefined;
73
+ }
74
+ function isServerFunction(fn) {
75
+ return typeof fn === "function" && !!fn[SERVER_FUNCTION_METADATA];
76
+ }
77
+ function withMeta(fn, meta) {
78
+ const metadata = getServerFunctionMetadata(fn);
79
+ if (!metadata) {
80
+ throw new Error("withMeta expects a server function reference");
81
+ }
82
+ Object.assign(metadata, meta);
83
+ return fn;
84
+ }
57
85
  const FUNCTION_HEADER = "X-Server-Function-Id";
58
86
  const INSTANCE_HEADER = "X-Server-Function-Instance";
59
87
  const BODY_FORMAT_HEADER = "X-Server-Function-Format";
88
+ const SINGLE_FLIGHT_HEADER = "X-Single-Flight";
60
89
  const FILE_FORM_KEY = "__server_function_file__";
61
90
  const BodyFormat = {
62
91
  Serialized: "0",
@@ -269,30 +298,44 @@ async function decodeResponse(response, codecOptions) {
269
298
  }
270
299
 
271
300
  const config = {
272
- endpoint: "/_server"
301
+ endpoint: "/_server",
302
+ prepareRequest: undefined
273
303
  };
274
304
  function configureServerFunctionsClient({
275
305
  endpoint,
276
- codec
306
+ codec,
307
+ prepareRequest
277
308
  } = {}) {
278
309
  if (endpoint !== undefined) config.endpoint = endpoint;
279
310
  if (codec !== undefined) configureServerFunctionsCodec(codec);
311
+ if (prepareRequest !== undefined) config.prepareRequest = prepareRequest;
280
312
  }
281
313
  let INSTANCE = 0;
282
- function createRequest(base, id, instance, options) {
283
- return fetch(base, {
314
+ async function createRequest(base, id, instance, options, meta) {
315
+ const headers = {
316
+ ...options.headers,
317
+ [FUNCTION_HEADER]: id,
318
+ [INSTANCE_HEADER]: instance
319
+ };
320
+ if (getFlightDataConsumer() && (!options.method || options.method.toUpperCase() !== "GET")) {
321
+ headers[SINGLE_FLIGHT_HEADER] = "true";
322
+ }
323
+ let init = {
284
324
  method: "POST",
285
325
  ...options,
286
- headers: {
287
- ...options.headers,
288
- [FUNCTION_HEADER]: id,
289
- [INSTANCE_HEADER]: instance
290
- }
291
- });
326
+ headers
327
+ };
328
+ if (config.prepareRequest) {
329
+ init = (await config.prepareRequest(init, {
330
+ id,
331
+ meta
332
+ })) || init;
333
+ }
334
+ return fetch(base, init);
292
335
  }
293
- async function initializeResponse(base, id, instance, options, args) {
336
+ async function initializeResponse(base, id, instance, options, args, meta) {
294
337
  if (args.length === 0) {
295
- return createRequest(base, id, instance, options);
338
+ return createRequest(base, id, instance, options, meta);
296
339
  }
297
340
  if (args.length === 1) {
298
341
  const result = getHeadersAndBody(args[0]);
@@ -304,7 +347,7 @@ async function initializeResponse(base, id, instance, options, args) {
304
347
  ...options.headers,
305
348
  ...result.headers
306
349
  }
307
- });
350
+ }, meta);
308
351
  }
309
352
  }
310
353
  return createRequest(base, id, instance, {
@@ -315,12 +358,25 @@ async function initializeResponse(base, id, instance, options, args) {
315
358
  "Content-Type": "text/plain",
316
359
  [BODY_FORMAT_HEADER]: BodyFormat.Serialized
317
360
  }
318
- });
361
+ }, meta);
319
362
  }
320
- async function fetchServerFunction(base, id, options, args) {
363
+ async function fetchServerFunction(base, id, options, args, meta) {
321
364
  const instance = `server-function:${INSTANCE++}`;
322
- const response = await initializeResponse(base, id, instance, options, args);
323
- if (response.headers.has("Location") || response.headers.has("X-Revalidate") || response.headers.has("X-Single-Flight")) {
365
+ const response = await initializeResponse(base, id, instance, options, args, meta);
366
+ if (response.headers.has(SINGLE_FLIGHT_HEADER)) {
367
+ const consumer = getFlightDataConsumer();
368
+ if (consumer) {
369
+ const payload = await decodeResponse(response);
370
+ await consumer(payload.data, {
371
+ response
372
+ });
373
+ if (response.headers.has("X-Server-Function-Error") && !response.headers.has("Location") && !response.headers.has("X-Revalidate")) {
374
+ throw payload.value;
375
+ }
376
+ return payload.value;
377
+ }
378
+ }
379
+ if (response.headers.has("Location") || response.headers.has("X-Revalidate") || response.headers.has(SINGLE_FLIGHT_HEADER)) {
324
380
  return response;
325
381
  }
326
382
  const result = await decodeResponse(response.clone());
@@ -329,35 +385,51 @@ async function fetchServerFunction(base, id, options, args) {
329
385
  }
330
386
  return result;
331
387
  }
332
- function createServerReference(id) {
333
- const fn = (...args) => fetchServerFunction(config.endpoint, id, {}, args);
388
+ function createServerReference(id, name) {
389
+ const metadata = name === undefined ? {} : {
390
+ name
391
+ };
392
+ const fn = (...args) => fetchServerFunction(config.endpoint, id, {}, args, metadata);
393
+ fn[SERVER_FUNCTION_METADATA] = metadata;
334
394
  return new Proxy(fn, {
335
- get(target, prop, receiver) {
395
+ get(target, prop) {
396
+ if (prop === "id") return id;
336
397
  if (prop === "url") {
337
398
  return `${config.endpoint}?id=${encodeURIComponent(id)}`;
338
399
  }
339
- if (prop === "GET") {
340
- return receiver.withOptions({
341
- method: "GET"
342
- });
343
- }
344
- if (prop === "withOptions") {
345
- const url = `${config.endpoint}?id=${encodeURIComponent(id)}`;
346
- return options => {
347
- const wrapped = async (...args) => {
348
- const encodeArgs = options.method && options.method.toUpperCase() === "GET";
349
- return fetchServerFunction(encodeArgs ? url + (args.length ? `&args=${encodeURIComponent(await serializeString(args, getServerFunctionsCodec()))}` : "") : config.endpoint, id, options, encodeArgs ? [] : args);
350
- };
351
- wrapped.url = url;
352
- return wrapped;
353
- };
354
- }
355
400
  return target[prop];
356
401
  }
357
402
  });
358
403
  }
404
+ function GET(fn) {
405
+ if (!isServerFunction(fn)) {
406
+ throw new Error("GET expects a server function reference");
407
+ }
408
+ const id = fn.id;
409
+ const metadata = {
410
+ ...getServerFunctionMetadata(fn)
411
+ };
412
+ const wrapped = async (...args) => {
413
+ let base = `${config.endpoint}?id=${encodeURIComponent(id)}`;
414
+ if (args.length) {
415
+ base += `&args=${encodeURIComponent(await serializeString(args, getServerFunctionsCodec()))}`;
416
+ }
417
+ return fetchServerFunction(base, id, {
418
+ method: "GET"
419
+ }, [], metadata);
420
+ };
421
+ wrapped[SERVER_FUNCTION_METADATA] = metadata;
422
+ wrapped.id = id;
423
+ Object.defineProperty(wrapped, "url", {
424
+ get: () => `${config.endpoint}?id=${encodeURIComponent(id)}`,
425
+ configurable: true
426
+ });
427
+ return withMeta(wrapped, {
428
+ method: "GET"
429
+ });
430
+ }
359
431
  function registerServerReference() {
360
432
  throw new Error("registerServerReference must not be called in the client build");
361
433
  }
362
434
 
363
- export { FUNCTION_HEADER, INSTANCE_HEADER, configureServerFunctionsClient, createServerReference, decodeResponse, registerServerReference };
435
+ export { FUNCTION_HEADER, GET, INSTANCE_HEADER, SINGLE_FLIGHT_HEADER, configureServerFunctionsClient, createServerReference, decodeResponse, getServerFunctionMetadata, isServerFunction, registerServerReference, subscribeFlightData, withMeta };