@makeswift/runtime 0.29.0-canary.21 → 0.29.0-canary.22

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 (79) hide show
  1. package/dist/cjs/api/graphql-api-client.js +1 -1
  2. package/dist/cjs/api/rest-api-client.js +1 -1
  3. package/dist/cjs/api-handler/handlers/manifest.js +1 -1
  4. package/dist/cjs/api-handler/handlers/merge-translated-data.js +2 -12
  5. package/dist/cjs/api-handler/handlers/merge-translated-data.js.map +1 -1
  6. package/dist/cjs/api-handler/handlers/revalidate.js +2 -12
  7. package/dist/cjs/api-handler/handlers/revalidate.js.map +1 -1
  8. package/dist/cjs/api-handler/handlers/table-record.js +2 -12
  9. package/dist/cjs/api-handler/handlers/table-record.js.map +1 -1
  10. package/dist/cjs/runtimes/react/hooks/use-async-effect.js +4 -3
  11. package/dist/cjs/runtimes/react/hooks/use-async-effect.js.map +1 -1
  12. package/dist/cjs/runtimes/react/hooks/use-server-element-refresh.js +10 -20
  13. package/dist/cjs/runtimes/react/hooks/use-server-element-refresh.js.map +1 -1
  14. package/dist/cjs/runtimes/react/server/components/editable-server-element.js +18 -14
  15. package/dist/cjs/runtimes/react/server/components/editable-server-element.js.map +1 -1
  16. package/dist/cjs/runtimes/react/server/components/server-elements-cache.js +75 -25
  17. package/dist/cjs/runtimes/react/server/components/server-elements-cache.js.map +1 -1
  18. package/dist/cjs/state/actions/internal/read-write-action-types.js +1 -1
  19. package/dist/cjs/state/actions/internal/read-write-action-types.js.map +1 -1
  20. package/dist/cjs/state/actions/internal/read-write-actions.js +4 -4
  21. package/dist/cjs/state/actions/internal/read-write-actions.js.map +1 -1
  22. package/dist/cjs/state/modules/read-write/resolved-value-overrides.js +32 -14
  23. package/dist/cjs/state/modules/read-write/resolved-value-overrides.js.map +1 -1
  24. package/dist/cjs/state/read-write-state.js +5 -0
  25. package/dist/cjs/state/read-write-state.js.map +1 -1
  26. package/dist/cjs/utils/{isErrorWithMessage.js → error-message.js} +12 -5
  27. package/dist/cjs/utils/error-message.js.map +1 -0
  28. package/dist/esm/api/graphql-api-client.js +1 -1
  29. package/dist/esm/api/rest-api-client.js +1 -1
  30. package/dist/esm/api-handler/handlers/manifest.js +1 -1
  31. package/dist/esm/api-handler/handlers/merge-translated-data.js +1 -1
  32. package/dist/esm/api-handler/handlers/merge-translated-data.js.map +1 -1
  33. package/dist/esm/api-handler/handlers/revalidate.js +1 -1
  34. package/dist/esm/api-handler/handlers/revalidate.js.map +1 -1
  35. package/dist/esm/api-handler/handlers/table-record.js +1 -1
  36. package/dist/esm/api-handler/handlers/table-record.js.map +1 -1
  37. package/dist/esm/runtimes/react/hooks/use-async-effect.js +4 -3
  38. package/dist/esm/runtimes/react/hooks/use-async-effect.js.map +1 -1
  39. package/dist/esm/runtimes/react/hooks/use-server-element-refresh.js +11 -21
  40. package/dist/esm/runtimes/react/hooks/use-server-element-refresh.js.map +1 -1
  41. package/dist/esm/runtimes/react/server/components/editable-server-element.js +19 -15
  42. package/dist/esm/runtimes/react/server/components/editable-server-element.js.map +1 -1
  43. package/dist/esm/runtimes/react/server/components/server-elements-cache.js +83 -26
  44. package/dist/esm/runtimes/react/server/components/server-elements-cache.js.map +1 -1
  45. package/dist/esm/state/actions/internal/read-write-action-types.js +1 -1
  46. package/dist/esm/state/actions/internal/read-write-action-types.js.map +1 -1
  47. package/dist/esm/state/actions/internal/read-write-actions.js +3 -3
  48. package/dist/esm/state/actions/internal/read-write-actions.js.map +1 -1
  49. package/dist/esm/state/modules/read-write/resolved-value-overrides.js +31 -14
  50. package/dist/esm/state/modules/read-write/resolved-value-overrides.js.map +1 -1
  51. package/dist/esm/state/read-write-state.js +4 -0
  52. package/dist/esm/state/read-write-state.js.map +1 -1
  53. package/dist/esm/utils/error-message.js +9 -0
  54. package/dist/esm/utils/error-message.js.map +1 -0
  55. package/dist/types/runtimes/react/hooks/use-async-effect.d.ts.map +1 -1
  56. package/dist/types/runtimes/react/hooks/use-server-element-refresh.d.ts +3 -4
  57. package/dist/types/runtimes/react/hooks/use-server-element-refresh.d.ts.map +1 -1
  58. package/dist/types/runtimes/react/server/components/editable-server-element.d.ts.map +1 -1
  59. package/dist/types/runtimes/react/server/components/server-elements-cache.d.ts +2 -2
  60. package/dist/types/runtimes/react/server/components/server-elements-cache.d.ts.map +1 -1
  61. package/dist/types/state/actions/index.d.ts +1 -1
  62. package/dist/types/state/actions/internal/action-types.d.ts +1 -1
  63. package/dist/types/state/actions/internal/read-write-action-types.d.ts +1 -1
  64. package/dist/types/state/actions/internal/read-write-actions.d.ts +6 -5
  65. package/dist/types/state/actions/internal/read-write-actions.d.ts.map +1 -1
  66. package/dist/types/state/modules/read-write/resolved-value-overrides.d.ts +9 -3
  67. package/dist/types/state/modules/read-write/resolved-value-overrides.d.ts.map +1 -1
  68. package/dist/types/state/read-write-state.d.ts +1 -0
  69. package/dist/types/state/read-write-state.d.ts.map +1 -1
  70. package/dist/types/utils/__tests__/error-message.test.d.ts +2 -0
  71. package/dist/types/utils/__tests__/error-message.test.d.ts.map +1 -0
  72. package/dist/types/utils/error-message.d.ts +7 -0
  73. package/dist/types/utils/error-message.d.ts.map +1 -0
  74. package/package.json +1 -1
  75. package/dist/cjs/utils/isErrorWithMessage.js.map +0 -1
  76. package/dist/esm/utils/isErrorWithMessage.js +0 -7
  77. package/dist/esm/utils/isErrorWithMessage.js.map +0 -1
  78. package/dist/types/utils/isErrorWithMessage.d.ts +0 -6
  79. package/dist/types/utils/isErrorWithMessage.d.ts.map +0 -1
@@ -27,7 +27,7 @@ class MakeswiftGraphQLApiClient {
27
27
  graphqlClient;
28
28
  constructor({ endpoint }) {
29
29
  this.graphqlClient = new import_client.GraphQLClient(endpoint, {
30
- "makeswift-runtime-version": "0.29.0-canary.21"
30
+ "makeswift-runtime-version": "0.29.0-canary.22"
31
31
  });
32
32
  }
33
33
  async getUnversionedResources({
@@ -223,7 +223,7 @@ class MakeswiftRestAPIClient {
223
223
  const requestHeaders = new Headers({
224
224
  "x-api-key": this.apiKey,
225
225
  "makeswift-site-api-key": this.apiKey,
226
- "makeswift-runtime-version": "0.29.0-canary.21"
226
+ "makeswift-runtime-version": "0.29.0-canary.22"
227
227
  });
228
228
  if (siteVersion?.token) {
229
229
  requestUrl.searchParams.set("version", siteVersion.version);
@@ -28,7 +28,7 @@ async function manifestHandler(req, { apiKey, manifest }) {
28
28
  return import_request_response.ApiResponse.json({ message: "Unauthorized" }, { status: 401 });
29
29
  }
30
30
  return import_request_response.ApiResponse.json({
31
- version: "0.29.0-canary.21",
31
+ version: "0.29.0-canary.22",
32
32
  interactionMode: true,
33
33
  clientSideNavigation: false,
34
34
  elementFromPoint: false,
@@ -1,9 +1,7 @@
1
1
  "use strict";
2
- var __create = Object.create;
3
2
  var __defProp = Object.defineProperty;
4
3
  var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
5
4
  var __getOwnPropNames = Object.getOwnPropertyNames;
6
- var __getProtoOf = Object.getPrototypeOf;
7
5
  var __hasOwnProp = Object.prototype.hasOwnProperty;
8
6
  var __export = (target, all) => {
9
7
  for (var name in all)
@@ -17,14 +15,6 @@ var __copyProps = (to, from, except, desc) => {
17
15
  }
18
16
  return to;
19
17
  };
20
- var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(
21
- // If the importer is in node compatibility mode or this is not an ESM
22
- // file that has been converted to a CommonJS file using a Babel-
23
- // compatible transform (i.e. "__esModule" has not been set), then set
24
- // "default" to the CommonJS "module.exports" for node compatibility.
25
- isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target,
26
- mod
27
- ));
28
18
  var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
29
19
  var merge_translated_data_exports = {};
30
20
  __export(merge_translated_data_exports, {
@@ -32,7 +22,7 @@ __export(merge_translated_data_exports, {
32
22
  });
33
23
  module.exports = __toCommonJS(merge_translated_data_exports);
34
24
  var import_request_response = require("../request-response");
35
- var import_isErrorWithMessage = __toESM(require("../../utils/isErrorWithMessage"));
25
+ var import_error_message = require("../../utils/error-message");
36
26
  async function mergeTranslatedDataHandler(req, { client }) {
37
27
  const body = await req.json();
38
28
  const { translatedData, elementTree } = body;
@@ -46,7 +36,7 @@ async function mergeTranslatedDataHandler(req, { client }) {
46
36
  const translatedElementTree = client.mergeTranslatedData(elementTree, translatedData);
47
37
  return import_request_response.ApiResponse.json({ elementTree: translatedElementTree });
48
38
  } catch (error) {
49
- if ((0, import_isErrorWithMessage.default)(error)) {
39
+ if ((0, import_error_message.isErrorWithMessage)(error)) {
50
40
  return import_request_response.ApiResponse.json({ message: error.message }, { status: 500 });
51
41
  }
52
42
  return import_request_response.ApiResponse.json({ message: "Error merging translated data" }, { status: 500 });
@@ -1 +1 @@
1
- {"version":3,"sources":["../../../../src/api-handler/handlers/merge-translated-data.ts"],"sourcesContent":["import { type Element } from '../../state/read-only-state'\nimport { MakeswiftClient } from '../../client'\nimport { type ApiRequest, ApiResponse, type ErrorResponseBody } from '../request-response'\nimport isErrorWithMessage from '../../utils/isErrorWithMessage'\n\ntype TranslatedData = { elementTree: Element }\n\nexport async function mergeTranslatedDataHandler(\n req: ApiRequest,\n { client }: { client: MakeswiftClient },\n): Promise<ApiResponse<TranslatedData | ErrorResponseBody>> {\n const body = await req.json()\n const { translatedData, elementTree } = body\n\n if (translatedData == null) {\n return ApiResponse.json({ message: 'translatedData must be defined' }, { status: 400 })\n }\n\n if (elementTree == null) {\n return ApiResponse.json({ message: 'elementTree must be defined' }, { status: 400 })\n }\n\n try {\n const translatedElementTree = client.mergeTranslatedData(elementTree, translatedData)\n return ApiResponse.json({ elementTree: translatedElementTree })\n } catch (error) {\n if (isErrorWithMessage(error)) {\n return ApiResponse.json({ message: error.message }, { status: 500 })\n }\n return ApiResponse.json({ message: 'Error merging translated data' }, { status: 500 })\n }\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAEA,8BAAqE;AACrE,gCAA+B;AAI/B,eAAsB,2BACpB,KACA,EAAE,OAAO,GACiD;AAC1D,QAAM,OAAO,MAAM,IAAI,KAAK;AAC5B,QAAM,EAAE,gBAAgB,YAAY,IAAI;AAExC,MAAI,kBAAkB,MAAM;AAC1B,WAAO,oCAAY,KAAK,EAAE,SAAS,iCAAiC,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,EACxF;AAEA,MAAI,eAAe,MAAM;AACvB,WAAO,oCAAY,KAAK,EAAE,SAAS,8BAA8B,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,EACrF;AAEA,MAAI;AACF,UAAM,wBAAwB,OAAO,oBAAoB,aAAa,cAAc;AACpF,WAAO,oCAAY,KAAK,EAAE,aAAa,sBAAsB,CAAC;AAAA,EAChE,SAAS,OAAO;AACd,YAAI,0BAAAA,SAAmB,KAAK,GAAG;AAC7B,aAAO,oCAAY,KAAK,EAAE,SAAS,MAAM,QAAQ,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,IACrE;AACA,WAAO,oCAAY,KAAK,EAAE,SAAS,gCAAgC,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,EACvF;AACF;","names":["isErrorWithMessage"]}
1
+ {"version":3,"sources":["../../../../src/api-handler/handlers/merge-translated-data.ts"],"sourcesContent":["import { type Element } from '../../state/read-only-state'\nimport { MakeswiftClient } from '../../client'\nimport { type ApiRequest, ApiResponse, type ErrorResponseBody } from '../request-response'\nimport { isErrorWithMessage } from '../../utils/error-message'\n\ntype TranslatedData = { elementTree: Element }\n\nexport async function mergeTranslatedDataHandler(\n req: ApiRequest,\n { client }: { client: MakeswiftClient },\n): Promise<ApiResponse<TranslatedData | ErrorResponseBody>> {\n const body = await req.json()\n const { translatedData, elementTree } = body\n\n if (translatedData == null) {\n return ApiResponse.json({ message: 'translatedData must be defined' }, { status: 400 })\n }\n\n if (elementTree == null) {\n return ApiResponse.json({ message: 'elementTree must be defined' }, { status: 400 })\n }\n\n try {\n const translatedElementTree = client.mergeTranslatedData(elementTree, translatedData)\n return ApiResponse.json({ elementTree: translatedElementTree })\n } catch (error) {\n if (isErrorWithMessage(error)) {\n return ApiResponse.json({ message: error.message }, { status: 500 })\n }\n return ApiResponse.json({ message: 'Error merging translated data' }, { status: 500 })\n }\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAEA,8BAAqE;AACrE,2BAAmC;AAInC,eAAsB,2BACpB,KACA,EAAE,OAAO,GACiD;AAC1D,QAAM,OAAO,MAAM,IAAI,KAAK;AAC5B,QAAM,EAAE,gBAAgB,YAAY,IAAI;AAExC,MAAI,kBAAkB,MAAM;AAC1B,WAAO,oCAAY,KAAK,EAAE,SAAS,iCAAiC,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,EACxF;AAEA,MAAI,eAAe,MAAM;AACvB,WAAO,oCAAY,KAAK,EAAE,SAAS,8BAA8B,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,EACrF;AAEA,MAAI;AACF,UAAM,wBAAwB,OAAO,oBAAoB,aAAa,cAAc;AACpF,WAAO,oCAAY,KAAK,EAAE,aAAa,sBAAsB,CAAC;AAAA,EAChE,SAAS,OAAO;AACd,YAAI,yCAAmB,KAAK,GAAG;AAC7B,aAAO,oCAAY,KAAK,EAAE,SAAS,MAAM,QAAQ,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,IACrE;AACA,WAAO,oCAAY,KAAK,EAAE,SAAS,gCAAgC,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,EACvF;AACF;","names":[]}
@@ -1,9 +1,7 @@
1
1
  "use strict";
2
- var __create = Object.create;
3
2
  var __defProp = Object.defineProperty;
4
3
  var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
5
4
  var __getOwnPropNames = Object.getOwnPropertyNames;
6
- var __getProtoOf = Object.getPrototypeOf;
7
5
  var __hasOwnProp = Object.prototype.hasOwnProperty;
8
6
  var __export = (target, all) => {
9
7
  for (var name in all)
@@ -17,21 +15,13 @@ var __copyProps = (to, from, except, desc) => {
17
15
  }
18
16
  return to;
19
17
  };
20
- var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(
21
- // If the importer is in node compatibility mode or this is not an ESM
22
- // file that has been converted to a CommonJS file using a Babel-
23
- // compatible transform (i.e. "__esModule" has not been set), then set
24
- // "default" to the CommonJS "module.exports" for node compatibility.
25
- isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target,
26
- mod
27
- ));
28
18
  var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
29
19
  var revalidate_exports = {};
30
20
  __export(revalidate_exports, {
31
21
  revalidateHandler: () => revalidateHandler
32
22
  });
33
23
  module.exports = __toCommonJS(revalidate_exports);
34
- var import_isErrorWithMessage = __toESM(require("../../utils/isErrorWithMessage"));
24
+ var import_error_message = require("../../utils/error-message");
35
25
  var import_request_response = require("../request-response");
36
26
  async function revalidateHandler(req, { apiKey, revalidatePath }) {
37
27
  const params = (0, import_request_response.searchParams)(req);
@@ -47,7 +37,7 @@ async function revalidateHandler(req, { apiKey, revalidatePath }) {
47
37
  await revalidatePath(path);
48
38
  return import_request_response.ApiResponse.json({ revalidated: true });
49
39
  } catch (error) {
50
- if ((0, import_isErrorWithMessage.default)(error)) {
40
+ if ((0, import_error_message.isErrorWithMessage)(error)) {
51
41
  return import_request_response.ApiResponse.json({ message: error.message }, { status: 500 });
52
42
  }
53
43
  return import_request_response.ApiResponse.json({ message: "Error Revalidating" }, { status: 500 });
@@ -1 +1 @@
1
- {"version":3,"sources":["../../../../src/api-handler/handlers/revalidate.ts"],"sourcesContent":["import isErrorWithMessage from '../../utils/isErrorWithMessage'\nimport {\n type ApiRequest,\n type ErrorResponseBody,\n ApiResponse,\n searchParams,\n} from '../request-response'\n\ntype RevalidationResult = { revalidated: boolean }\n\nexport async function revalidateHandler(\n req: ApiRequest,\n { apiKey, revalidatePath }: { apiKey: string; revalidatePath: (path: string) => Promise<void> },\n): Promise<ApiResponse<RevalidationResult | ErrorResponseBody>> {\n const params = searchParams(req)\n\n const secret = params.get('secret')\n if (secret !== apiKey) {\n return ApiResponse.json({ message: 'Unauthorized' }, { status: 401 })\n }\n\n const path = params.get('path')\n if (typeof path !== 'string') {\n return ApiResponse.json({ message: 'Bad Request' }, { status: 400 })\n }\n\n try {\n await revalidatePath(path)\n return ApiResponse.json({ revalidated: true })\n } catch (error) {\n if (isErrorWithMessage(error)) {\n return ApiResponse.json({ message: error.message }, { status: 500 })\n }\n\n return ApiResponse.json({ message: 'Error Revalidating' }, { status: 500 })\n }\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,gCAA+B;AAC/B,8BAKO;AAIP,eAAsB,kBACpB,KACA,EAAE,QAAQ,eAAe,GACqC;AAC9D,QAAM,aAAS,sCAAa,GAAG;AAE/B,QAAM,SAAS,OAAO,IAAI,QAAQ;AAClC,MAAI,WAAW,QAAQ;AACrB,WAAO,oCAAY,KAAK,EAAE,SAAS,eAAe,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,EACtE;AAEA,QAAM,OAAO,OAAO,IAAI,MAAM;AAC9B,MAAI,OAAO,SAAS,UAAU;AAC5B,WAAO,oCAAY,KAAK,EAAE,SAAS,cAAc,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,EACrE;AAEA,MAAI;AACF,UAAM,eAAe,IAAI;AACzB,WAAO,oCAAY,KAAK,EAAE,aAAa,KAAK,CAAC;AAAA,EAC/C,SAAS,OAAO;AACd,YAAI,0BAAAA,SAAmB,KAAK,GAAG;AAC7B,aAAO,oCAAY,KAAK,EAAE,SAAS,MAAM,QAAQ,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,IACrE;AAEA,WAAO,oCAAY,KAAK,EAAE,SAAS,qBAAqB,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,EAC5E;AACF;","names":["isErrorWithMessage"]}
1
+ {"version":3,"sources":["../../../../src/api-handler/handlers/revalidate.ts"],"sourcesContent":["import { isErrorWithMessage } from '../../utils/error-message'\nimport {\n type ApiRequest,\n type ErrorResponseBody,\n ApiResponse,\n searchParams,\n} from '../request-response'\n\ntype RevalidationResult = { revalidated: boolean }\n\nexport async function revalidateHandler(\n req: ApiRequest,\n { apiKey, revalidatePath }: { apiKey: string; revalidatePath: (path: string) => Promise<void> },\n): Promise<ApiResponse<RevalidationResult | ErrorResponseBody>> {\n const params = searchParams(req)\n\n const secret = params.get('secret')\n if (secret !== apiKey) {\n return ApiResponse.json({ message: 'Unauthorized' }, { status: 401 })\n }\n\n const path = params.get('path')\n if (typeof path !== 'string') {\n return ApiResponse.json({ message: 'Bad Request' }, { status: 400 })\n }\n\n try {\n await revalidatePath(path)\n return ApiResponse.json({ revalidated: true })\n } catch (error) {\n if (isErrorWithMessage(error)) {\n return ApiResponse.json({ message: error.message }, { status: 500 })\n }\n\n return ApiResponse.json({ message: 'Error Revalidating' }, { status: 500 })\n }\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,2BAAmC;AACnC,8BAKO;AAIP,eAAsB,kBACpB,KACA,EAAE,QAAQ,eAAe,GACqC;AAC9D,QAAM,aAAS,sCAAa,GAAG;AAE/B,QAAM,SAAS,OAAO,IAAI,QAAQ;AAClC,MAAI,WAAW,QAAQ;AACrB,WAAO,oCAAY,KAAK,EAAE,SAAS,eAAe,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,EACtE;AAEA,QAAM,OAAO,OAAO,IAAI,MAAM;AAC9B,MAAI,OAAO,SAAS,UAAU;AAC5B,WAAO,oCAAY,KAAK,EAAE,SAAS,cAAc,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,EACrE;AAEA,MAAI;AACF,UAAM,eAAe,IAAI;AACzB,WAAO,oCAAY,KAAK,EAAE,aAAa,KAAK,CAAC;AAAA,EAC/C,SAAS,OAAO;AACd,YAAI,yCAAmB,KAAK,GAAG;AAC7B,aAAO,oCAAY,KAAK,EAAE,SAAS,MAAM,QAAQ,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,IACrE;AAEA,WAAO,oCAAY,KAAK,EAAE,SAAS,qBAAqB,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,EAC5E;AACF;","names":[]}
@@ -1,9 +1,7 @@
1
1
  "use strict";
2
- var __create = Object.create;
3
2
  var __defProp = Object.defineProperty;
4
3
  var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
5
4
  var __getOwnPropNames = Object.getOwnPropertyNames;
6
- var __getProtoOf = Object.getPrototypeOf;
7
5
  var __hasOwnProp = Object.prototype.hasOwnProperty;
8
6
  var __export = (target, all) => {
9
7
  for (var name in all)
@@ -17,14 +15,6 @@ var __copyProps = (to, from, except, desc) => {
17
15
  }
18
16
  return to;
19
17
  };
20
- var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(
21
- // If the importer is in node compatibility mode or this is not an ESM
22
- // file that has been converted to a CommonJS file using a Babel-
23
- // compatible transform (i.e. "__esModule" has not been set), then set
24
- // "default" to the CommonJS "module.exports" for node compatibility.
25
- isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target,
26
- mod
27
- ));
28
18
  var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
29
19
  var table_record_exports = {};
30
20
  __export(table_record_exports, {
@@ -33,7 +23,7 @@ __export(table_record_exports, {
33
23
  module.exports = __toCommonJS(table_record_exports);
34
24
  var import_rest_api_client = require("../../api/rest-api-client");
35
25
  var import_request_response = require("../request-response");
36
- var import_isErrorWithMessage = __toESM(require("../../utils/isErrorWithMessage"));
26
+ var import_error_message = require("../../utils/error-message");
37
27
  async function tableRecordHandler(req, { client }) {
38
28
  const body = await req.json();
39
29
  const { tableId, columns } = body;
@@ -50,7 +40,7 @@ async function tableRecordHandler(req, { client }) {
50
40
  if (error instanceof import_rest_api_client.RestApiClientError) {
51
41
  return import_request_response.ApiResponse.json({ message: error.message }, { status: error.status });
52
42
  }
53
- if ((0, import_isErrorWithMessage.default)(error)) {
43
+ if ((0, import_error_message.isErrorWithMessage)(error)) {
54
44
  return import_request_response.ApiResponse.json({ message: error.message }, { status: 500 });
55
45
  }
56
46
  return import_request_response.ApiResponse.json({ message: "Error creating table record" }, { status: 500 });
@@ -1 +1 @@
1
- {"version":3,"sources":["../../../../src/api-handler/handlers/table-record.ts"],"sourcesContent":["import { MakeswiftClient } from '../../client'\nimport { RestApiClientError } from '../../api/rest-api-client'\nimport { type ApiRequest, ApiResponse, type ErrorResponseBody } from '../request-response'\nimport isErrorWithMessage from '../../utils/isErrorWithMessage'\n\nexport async function tableRecordHandler(\n req: ApiRequest,\n { client }: { client: MakeswiftClient },\n): Promise<ApiResponse<ErrorResponseBody> | Response> {\n const body = await req.json()\n const { tableId, columns } = body\n\n if (typeof tableId !== 'string') {\n return ApiResponse.json({ message: 'tableId must be a string' }, { status: 400 })\n }\n\n if (!Array.isArray(columns)) {\n return ApiResponse.json({ message: 'columns must be an array' }, { status: 400 })\n }\n\n try {\n await client.createTableRecord(tableId, columns)\n return new Response(null, { status: 204 })\n } catch (error) {\n if (error instanceof RestApiClientError) {\n return ApiResponse.json({ message: error.message }, { status: error.status })\n }\n\n if (isErrorWithMessage(error)) {\n return ApiResponse.json({ message: error.message }, { status: 500 })\n }\n\n return ApiResponse.json({ message: 'Error creating table record' }, { status: 500 })\n }\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AACA,6BAAmC;AACnC,8BAAqE;AACrE,gCAA+B;AAE/B,eAAsB,mBACpB,KACA,EAAE,OAAO,GAC2C;AACpD,QAAM,OAAO,MAAM,IAAI,KAAK;AAC5B,QAAM,EAAE,SAAS,QAAQ,IAAI;AAE7B,MAAI,OAAO,YAAY,UAAU;AAC/B,WAAO,oCAAY,KAAK,EAAE,SAAS,2BAA2B,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,EAClF;AAEA,MAAI,CAAC,MAAM,QAAQ,OAAO,GAAG;AAC3B,WAAO,oCAAY,KAAK,EAAE,SAAS,2BAA2B,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,EAClF;AAEA,MAAI;AACF,UAAM,OAAO,kBAAkB,SAAS,OAAO;AAC/C,WAAO,IAAI,SAAS,MAAM,EAAE,QAAQ,IAAI,CAAC;AAAA,EAC3C,SAAS,OAAO;AACd,QAAI,iBAAiB,2CAAoB;AACvC,aAAO,oCAAY,KAAK,EAAE,SAAS,MAAM,QAAQ,GAAG,EAAE,QAAQ,MAAM,OAAO,CAAC;AAAA,IAC9E;AAEA,YAAI,0BAAAA,SAAmB,KAAK,GAAG;AAC7B,aAAO,oCAAY,KAAK,EAAE,SAAS,MAAM,QAAQ,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,IACrE;AAEA,WAAO,oCAAY,KAAK,EAAE,SAAS,8BAA8B,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,EACrF;AACF;","names":["isErrorWithMessage"]}
1
+ {"version":3,"sources":["../../../../src/api-handler/handlers/table-record.ts"],"sourcesContent":["import { MakeswiftClient } from '../../client'\nimport { RestApiClientError } from '../../api/rest-api-client'\nimport { type ApiRequest, ApiResponse, type ErrorResponseBody } from '../request-response'\nimport { isErrorWithMessage } from '../../utils/error-message'\n\nexport async function tableRecordHandler(\n req: ApiRequest,\n { client }: { client: MakeswiftClient },\n): Promise<ApiResponse<ErrorResponseBody> | Response> {\n const body = await req.json()\n const { tableId, columns } = body\n\n if (typeof tableId !== 'string') {\n return ApiResponse.json({ message: 'tableId must be a string' }, { status: 400 })\n }\n\n if (!Array.isArray(columns)) {\n return ApiResponse.json({ message: 'columns must be an array' }, { status: 400 })\n }\n\n try {\n await client.createTableRecord(tableId, columns)\n return new Response(null, { status: 204 })\n } catch (error) {\n if (error instanceof RestApiClientError) {\n return ApiResponse.json({ message: error.message }, { status: error.status })\n }\n\n if (isErrorWithMessage(error)) {\n return ApiResponse.json({ message: error.message }, { status: 500 })\n }\n\n return ApiResponse.json({ message: 'Error creating table record' }, { status: 500 })\n }\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AACA,6BAAmC;AACnC,8BAAqE;AACrE,2BAAmC;AAEnC,eAAsB,mBACpB,KACA,EAAE,OAAO,GAC2C;AACpD,QAAM,OAAO,MAAM,IAAI,KAAK;AAC5B,QAAM,EAAE,SAAS,QAAQ,IAAI;AAE7B,MAAI,OAAO,YAAY,UAAU;AAC/B,WAAO,oCAAY,KAAK,EAAE,SAAS,2BAA2B,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,EAClF;AAEA,MAAI,CAAC,MAAM,QAAQ,OAAO,GAAG;AAC3B,WAAO,oCAAY,KAAK,EAAE,SAAS,2BAA2B,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,EAClF;AAEA,MAAI;AACF,UAAM,OAAO,kBAAkB,SAAS,OAAO;AAC/C,WAAO,IAAI,SAAS,MAAM,EAAE,QAAQ,IAAI,CAAC;AAAA,EAC3C,SAAS,OAAO;AACd,QAAI,iBAAiB,2CAAoB;AACvC,aAAO,oCAAY,KAAK,EAAE,SAAS,MAAM,QAAQ,GAAG,EAAE,QAAQ,MAAM,OAAO,CAAC;AAAA,IAC9E;AAEA,YAAI,yCAAmB,KAAK,GAAG;AAC7B,aAAO,oCAAY,KAAK,EAAE,SAAS,MAAM,QAAQ,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,IACrE;AAEA,WAAO,oCAAY,KAAK,EAAE,SAAS,8BAA8B,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,EACrF;AACF;","names":[]}
@@ -22,6 +22,7 @@ __export(use_async_effect_exports, {
22
22
  });
23
23
  module.exports = __toCommonJS(use_async_effect_exports);
24
24
  var import_react = require("react");
25
+ var import_error_message = require("../../../utils/error-message");
25
26
  function useAsyncEffect(effect, deps) {
26
27
  (0, import_react.useEffect)(() => {
27
28
  let cancelled = false;
@@ -34,16 +35,16 @@ function useAsyncEffect(effect, deps) {
34
35
  cleanup = null;
35
36
  }
36
37
  } catch (error) {
37
- console.error("Async effect error:", { error, deps });
38
+ console.error(`Async effect error: ${(0, import_error_message.errorMessage)(error)}`, { error, deps });
38
39
  }
39
40
  };
40
- runAsyncEffect();
41
+ void runAsyncEffect();
41
42
  return () => {
42
43
  cancelled = true;
43
44
  try {
44
45
  cleanup?.();
45
46
  } catch (error) {
46
- console.error("Async effect cleanup error:", { error, deps });
47
+ console.error(`Async effect cleanup error: ${(0, import_error_message.errorMessage)(error)}`, { error, deps });
47
48
  }
48
49
  };
49
50
  }, deps);
@@ -1 +1 @@
1
- {"version":3,"sources":["../../../../../src/runtimes/react/hooks/use-async-effect.ts"],"sourcesContent":["import { type DependencyList, useEffect } from 'react'\n\nexport function useAsyncEffect(effect: () => Promise<void | (() => void)>, deps: DependencyList) {\n useEffect(() => {\n let cancelled = false\n let cleanup: void | (() => void) | null = null\n\n const runAsyncEffect = async () => {\n try {\n cleanup = await effect()\n\n if (cancelled) {\n cleanup?.()\n cleanup = null\n }\n } catch (error) {\n console.error('Async effect error:', { error, deps })\n }\n }\n\n runAsyncEffect()\n\n return () => {\n cancelled = true\n try {\n cleanup?.()\n } catch (error) {\n console.error('Async effect cleanup error:', { error, deps })\n }\n }\n }, deps)\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,mBAA+C;AAExC,SAAS,eAAe,QAA4C,MAAsB;AAC/F,8BAAU,MAAM;AACd,QAAI,YAAY;AAChB,QAAI,UAAsC;AAE1C,UAAM,iBAAiB,YAAY;AACjC,UAAI;AACF,kBAAU,MAAM,OAAO;AAEvB,YAAI,WAAW;AACb,oBAAU;AACV,oBAAU;AAAA,QACZ;AAAA,MACF,SAAS,OAAO;AACd,gBAAQ,MAAM,uBAAuB,EAAE,OAAO,KAAK,CAAC;AAAA,MACtD;AAAA,IACF;AAEA,mBAAe;AAEf,WAAO,MAAM;AACX,kBAAY;AACZ,UAAI;AACF,kBAAU;AAAA,MACZ,SAAS,OAAO;AACd,gBAAQ,MAAM,+BAA+B,EAAE,OAAO,KAAK,CAAC;AAAA,MAC9D;AAAA,IACF;AAAA,EACF,GAAG,IAAI;AACT;","names":[]}
1
+ {"version":3,"sources":["../../../../../src/runtimes/react/hooks/use-async-effect.ts"],"sourcesContent":["import { type DependencyList, useEffect } from 'react'\n\nimport { errorMessage } from '../../../utils/error-message'\n\nexport function useAsyncEffect(effect: () => Promise<void | (() => void)>, deps: DependencyList) {\n useEffect(() => {\n let cancelled = false\n let cleanup: void | (() => void) | null = null\n\n const runAsyncEffect = async () => {\n try {\n cleanup = await effect()\n\n if (cancelled) {\n cleanup?.()\n cleanup = null\n }\n } catch (error) {\n console.error(`Async effect error: ${errorMessage(error)}`, { error, deps })\n }\n }\n\n void runAsyncEffect()\n\n return () => {\n cancelled = true\n try {\n cleanup?.()\n } catch (error) {\n console.error(`Async effect cleanup error: ${errorMessage(error)}`, { error, deps })\n }\n }\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, deps)\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,mBAA+C;AAE/C,2BAA6B;AAEtB,SAAS,eAAe,QAA4C,MAAsB;AAC/F,8BAAU,MAAM;AACd,QAAI,YAAY;AAChB,QAAI,UAAsC;AAE1C,UAAM,iBAAiB,YAAY;AACjC,UAAI;AACF,kBAAU,MAAM,OAAO;AAEvB,YAAI,WAAW;AACb,oBAAU;AACV,oBAAU;AAAA,QACZ;AAAA,MACF,SAAS,OAAO;AACd,gBAAQ,MAAM,2BAAuB,mCAAa,KAAK,CAAC,IAAI,EAAE,OAAO,KAAK,CAAC;AAAA,MAC7E;AAAA,IACF;AAEA,SAAK,eAAe;AAEpB,WAAO,MAAM;AACX,kBAAY;AACZ,UAAI;AACF,kBAAU;AAAA,MACZ,SAAS,OAAO;AACd,gBAAQ,MAAM,mCAA+B,mCAAa,KAAK,CAAC,IAAI,EAAE,OAAO,KAAK,CAAC;AAAA,MACrF;AAAA,IACF;AAAA,EAEF,GAAG,IAAI;AACT;","names":[]}
@@ -29,36 +29,31 @@ var import_use_api_resources_client = require("./use-api-resources-client");
29
29
  const useServerElementRefresh = ({
30
30
  elementKey
31
31
  }) => {
32
- const requestIdRef = (0, import_react.useRef)(0);
33
- const lastAppliedRequestId = (0, import_react.useRef)(0);
34
32
  const { renderRSCElement } = (0, import_use_framework_context.useFrameworkContext)();
35
- const { updateElement } = (0, import_server_elements_cache.useServerElementsCache)();
33
+ const { beginRefresh } = (0, import_server_elements_cache.useServerElementsCache)();
36
34
  const documentKey = (0, import_use_document_context.useDocumentKey)();
37
35
  const documentLocale = (0, import_use_document_context.useDocumentLocale)();
38
36
  const apiResourcesClient = (0, import_use_api_resources_client.useApiResourcesClient)();
39
- (0, import_react.useEffect)(() => {
40
- return () => {
41
- lastAppliedRequestId.current = ++requestIdRef.current;
42
- };
43
- }, []);
44
37
  return (0, import_react.useCallback)(
45
- async (elementData) => {
38
+ async (elementData, onCommitted) => {
46
39
  if (!documentKey)
47
- return false;
40
+ return;
48
41
  if (elementData.key !== elementKey) {
49
42
  console.error(
50
43
  `Cannot refresh server element: mismatching element key '${elementData.key}' != '${elementKey}'`
51
44
  );
52
- return false;
45
+ return;
53
46
  }
54
47
  if (!renderRSCElement) {
55
48
  console.error(
56
49
  `Cannot refresh server element '${elementKey}' of type '${elementData.type}': \`renderRSCElement\` callback is null`
57
50
  );
58
- return false;
51
+ return;
59
52
  }
60
53
  try {
61
- const requestId = ++requestIdRef.current;
54
+ const commit = beginRefresh(elementKey, onCommitted);
55
+ if (commit == null)
56
+ return;
62
57
  const reactNode = await renderRSCElement({
63
58
  elementData,
64
59
  cacheData: apiResourcesClient.cacheData,
@@ -67,20 +62,15 @@ const useServerElementRefresh = ({
67
62
  locale: documentLocale ?? void 0
68
63
  }
69
64
  });
70
- if (requestId > lastAppliedRequestId.current) {
71
- updateElement(elementKey, reactNode);
72
- lastAppliedRequestId.current = requestId;
73
- return true;
74
- }
65
+ commit(reactNode);
75
66
  } catch (error) {
76
67
  console.error(
77
68
  `Failed to refresh server element '${elementKey}' of type '${elementData.type}'`,
78
69
  error
79
70
  );
80
71
  }
81
- return false;
82
72
  },
83
- [renderRSCElement, documentKey, documentLocale, elementKey, apiResourcesClient, updateElement]
73
+ [renderRSCElement, documentKey, documentLocale, elementKey, apiResourcesClient, beginRefresh]
84
74
  );
85
75
  };
86
76
  // Annotate the CommonJS export names for ESM import in node:
@@ -1 +1 @@
1
- {"version":3,"sources":["../../../../../src/runtimes/react/hooks/use-server-element-refresh.tsx"],"sourcesContent":["import { useCallback, useEffect, useRef } from 'react'\n\nimport { type ElementData } from '../../../state/read-only-state'\n\nimport { useFrameworkContext } from '../components/hooks/use-framework-context'\nimport { useServerElementsCache } from '../server/components/server-elements-cache'\n\nimport { useDocumentKey, useDocumentLocale } from './use-document-context'\nimport { useApiResourcesClient } from './use-api-resources-client'\n\n/**\n * Returns a element-scoped callback that renders the provided element data on\n * the server and stores the result in the server element cache under the\n * provided element key.\n *\n * The callback returns true only if the element render succeeds and is committed\n * to the cache. Returns false when rendering is unavailable, fails, or produces a\n * stale/out-of-order result.\n */\nexport const useServerElementRefresh = ({\n elementKey,\n}: {\n elementKey: string\n}): ((elementData: ElementData) => Promise<boolean>) => {\n const requestIdRef = useRef(0)\n const lastAppliedRequestId = useRef(0)\n\n const { renderRSCElement } = useFrameworkContext()\n const { updateElement } = useServerElementsCache()\n\n const documentKey = useDocumentKey()\n const documentLocale = useDocumentLocale()\n const apiResourcesClient = useApiResourcesClient()\n\n useEffect(() => {\n // Invalidate all in-flight requests on unmount so they cannot update the cache\n return () => {\n // eslint-disable-next-line react-hooks/exhaustive-deps\n lastAppliedRequestId.current = ++requestIdRef.current\n }\n }, [])\n\n return useCallback(\n async (elementData: ElementData): Promise<boolean> => {\n if (!documentKey) return false\n if (elementData.key !== elementKey) {\n console.error(\n `Cannot refresh server element: mismatching element key '${elementData.key}' != '${elementKey}'`,\n )\n return false\n }\n\n if (!renderRSCElement) {\n console.error(\n `Cannot refresh server element '${elementKey}' of type '${elementData.type}': \\`renderRSCElement\\` callback is null`,\n )\n return false\n }\n\n try {\n // Assign each server refresh a sequential ID so we can track response\n // arrival and ignore out-of-order results\n const requestId = ++requestIdRef.current\n const reactNode = await renderRSCElement({\n elementData,\n cacheData: apiResourcesClient.cacheData,\n documentContext: {\n key: documentKey,\n locale: documentLocale ?? undefined,\n },\n })\n\n if (requestId > lastAppliedRequestId.current) {\n updateElement(elementKey, reactNode)\n lastAppliedRequestId.current = requestId\n return true\n }\n } catch (error) {\n console.error(\n `Failed to refresh server element '${elementKey}' of type '${elementData.type}'`,\n error,\n )\n }\n\n return false\n },\n [renderRSCElement, documentKey, documentLocale, elementKey, apiResourcesClient, updateElement],\n )\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,mBAA+C;AAI/C,mCAAoC;AACpC,mCAAuC;AAEvC,kCAAkD;AAClD,sCAAsC;AAW/B,MAAM,0BAA0B,CAAC;AAAA,EACtC;AACF,MAEwD;AACtD,QAAM,mBAAe,qBAAO,CAAC;AAC7B,QAAM,2BAAuB,qBAAO,CAAC;AAErC,QAAM,EAAE,iBAAiB,QAAI,kDAAoB;AACjD,QAAM,EAAE,cAAc,QAAI,qDAAuB;AAEjD,QAAM,kBAAc,4CAAe;AACnC,QAAM,qBAAiB,+CAAkB;AACzC,QAAM,yBAAqB,uDAAsB;AAEjD,8BAAU,MAAM;AAEd,WAAO,MAAM;AAEX,2BAAqB,UAAU,EAAE,aAAa;AAAA,IAChD;AAAA,EACF,GAAG,CAAC,CAAC;AAEL,aAAO;AAAA,IACL,OAAO,gBAA+C;AACpD,UAAI,CAAC;AAAa,eAAO;AACzB,UAAI,YAAY,QAAQ,YAAY;AAClC,gBAAQ;AAAA,UACN,2DAA2D,YAAY,GAAG,SAAS,UAAU;AAAA,QAC/F;AACA,eAAO;AAAA,MACT;AAEA,UAAI,CAAC,kBAAkB;AACrB,gBAAQ;AAAA,UACN,kCAAkC,UAAU,cAAc,YAAY,IAAI;AAAA,QAC5E;AACA,eAAO;AAAA,MACT;AAEA,UAAI;AAGF,cAAM,YAAY,EAAE,aAAa;AACjC,cAAM,YAAY,MAAM,iBAAiB;AAAA,UACvC;AAAA,UACA,WAAW,mBAAmB;AAAA,UAC9B,iBAAiB;AAAA,YACf,KAAK;AAAA,YACL,QAAQ,kBAAkB;AAAA,UAC5B;AAAA,QACF,CAAC;AAED,YAAI,YAAY,qBAAqB,SAAS;AAC5C,wBAAc,YAAY,SAAS;AACnC,+BAAqB,UAAU;AAC/B,iBAAO;AAAA,QACT;AAAA,MACF,SAAS,OAAO;AACd,gBAAQ;AAAA,UACN,qCAAqC,UAAU,cAAc,YAAY,IAAI;AAAA,UAC7E;AAAA,QACF;AAAA,MACF;AAEA,aAAO;AAAA,IACT;AAAA,IACA,CAAC,kBAAkB,aAAa,gBAAgB,YAAY,oBAAoB,aAAa;AAAA,EAC/F;AACF;","names":[]}
1
+ {"version":3,"sources":["../../../../../src/runtimes/react/hooks/use-server-element-refresh.tsx"],"sourcesContent":["import { useCallback } from 'react'\n\nimport { type ElementData } from '../../../state/read-only-state'\n\nimport { useFrameworkContext } from '../components/hooks/use-framework-context'\nimport { useServerElementsCache } from '../server/components/server-elements-cache'\n\nimport { useDocumentKey, useDocumentLocale } from './use-document-context'\nimport { useApiResourcesClient } from './use-api-resources-client'\n\n/**\n * Returns a element-scoped callback that renders the provided element data on\n * the server and stores the result in the server element cache under the\n * provided element key.\n *\n * Calls the `onCommitted` callback once after a successfully rendered node is\n * committed to the current React tree.\n */\nexport const useServerElementRefresh = ({\n elementKey,\n}: {\n elementKey: string\n}): ((elementData: ElementData, onCommitted?: () => void) => Promise<void>) => {\n const { renderRSCElement } = useFrameworkContext()\n const { beginRefresh } = useServerElementsCache()\n\n const documentKey = useDocumentKey()\n const documentLocale = useDocumentLocale()\n const apiResourcesClient = useApiResourcesClient()\n\n return useCallback(\n async (elementData: ElementData, onCommitted?: () => void): Promise<void> => {\n if (!documentKey) return\n if (elementData.key !== elementKey) {\n console.error(\n `Cannot refresh server element: mismatching element key '${elementData.key}' != '${elementKey}'`,\n )\n return\n }\n\n if (!renderRSCElement) {\n console.error(\n `Cannot refresh server element '${elementKey}' of type '${elementData.type}': \\`renderRSCElement\\` callback is null`,\n )\n return\n }\n\n try {\n const commit = beginRefresh(elementKey, onCommitted)\n if (commit == null) return\n\n const reactNode = await renderRSCElement({\n elementData,\n cacheData: apiResourcesClient.cacheData,\n documentContext: {\n key: documentKey,\n locale: documentLocale ?? undefined,\n },\n })\n\n commit(reactNode)\n } catch (error) {\n console.error(\n `Failed to refresh server element '${elementKey}' of type '${elementData.type}'`,\n error,\n )\n }\n },\n [renderRSCElement, documentKey, documentLocale, elementKey, apiResourcesClient, beginRefresh],\n )\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,mBAA4B;AAI5B,mCAAoC;AACpC,mCAAuC;AAEvC,kCAAkD;AAClD,sCAAsC;AAU/B,MAAM,0BAA0B,CAAC;AAAA,EACtC;AACF,MAE+E;AAC7E,QAAM,EAAE,iBAAiB,QAAI,kDAAoB;AACjD,QAAM,EAAE,aAAa,QAAI,qDAAuB;AAEhD,QAAM,kBAAc,4CAAe;AACnC,QAAM,qBAAiB,+CAAkB;AACzC,QAAM,yBAAqB,uDAAsB;AAEjD,aAAO;AAAA,IACL,OAAO,aAA0B,gBAA4C;AAC3E,UAAI,CAAC;AAAa;AAClB,UAAI,YAAY,QAAQ,YAAY;AAClC,gBAAQ;AAAA,UACN,2DAA2D,YAAY,GAAG,SAAS,UAAU;AAAA,QAC/F;AACA;AAAA,MACF;AAEA,UAAI,CAAC,kBAAkB;AACrB,gBAAQ;AAAA,UACN,kCAAkC,UAAU,cAAc,YAAY,IAAI;AAAA,QAC5E;AACA;AAAA,MACF;AAEA,UAAI;AACF,cAAM,SAAS,aAAa,YAAY,WAAW;AACnD,YAAI,UAAU;AAAM;AAEpB,cAAM,YAAY,MAAM,iBAAiB;AAAA,UACvC;AAAA,UACA,WAAW,mBAAmB;AAAA,UAC9B,iBAAiB;AAAA,YACf,KAAK;AAAA,YACL,QAAQ,kBAAkB;AAAA,UAC5B;AAAA,QACF,CAAC;AAED,eAAO,SAAS;AAAA,MAClB,SAAS,OAAO;AACd,gBAAQ;AAAA,UACN,qCAAqC,UAAU,cAAc,YAAY,IAAI;AAAA,UAC7E;AAAA,QACF;AAAA,MACF;AAAA,IACF;AAAA,IACA,CAAC,kBAAkB,aAAa,gBAAgB,YAAY,oBAAoB,YAAY;AAAA,EAC9F;AACF;","names":[]}
@@ -24,6 +24,8 @@ __export(editable_server_element_exports, {
24
24
  module.exports = __toCommonJS(editable_server_element_exports);
25
25
  var import_jsx_runtime = require("react/jsx-runtime");
26
26
  var import_react = require("react");
27
+ var import_read_write_state = require("../../../../state/read-write-state");
28
+ var import_unified_state = require("../../../../state/unified-state");
27
29
  var import_read_write_actions = require("../../../../state/actions/internal/read-write-actions");
28
30
  var import_use_server_element_refresh = require("../../hooks/use-server-element-refresh");
29
31
  var import_use_element_data = require("../../hooks/use-element-data");
@@ -31,6 +33,7 @@ var import_use_control_defs = require("../../hooks/use-control-defs");
31
33
  var import_use_resolved_props = require("../../hooks/use-resolved-props");
32
34
  var import_control_instances_context = require("../../components/control-instances-context");
33
35
  var import_use_dispatch = require("../../hooks/use-dispatch");
36
+ var import_use_store = require("../../hooks/use-store");
34
37
  var import_use_document_context = require("../../hooks/use-document-context");
35
38
  var import_prop_by_path = require("../../../../utils/prop-by-path");
36
39
  var import_set = require("../../../../utils/set");
@@ -52,6 +55,7 @@ const EditableServerElementWrapper = ({
52
55
  children
53
56
  }) => {
54
57
  const elementKey = initialElementData.key;
58
+ const store = (0, import_use_store.useStore)();
55
59
  const dispatch = (0, import_use_dispatch.useDispatch)();
56
60
  const documentKey = (0, import_use_document_context.useDocumentKey)();
57
61
  const [_legacyDefs, definitions] = (0, import_use_control_defs.useControlDefs)({ elementType: initialElementData.type });
@@ -70,17 +74,18 @@ const EditableServerElementWrapper = ({
70
74
  );
71
75
  const serverRefresh = (0, import_use_server_element_refresh.useServerElementRefresh)({ elementKey });
72
76
  const applyServerRefresh = (0, import_react.useCallback)(
73
- (elementData2, leafInstances, documentKey2) => (0, import_react.startTransition)(async () => {
74
- const applied = await serverRefresh(elementData2);
75
- if (!applied)
76
- return;
77
- (0, import_react.startTransition)(() => {
78
- leafInstances.forEach(
79
- (c) => dispatch((0, import_read_write_actions.clearResolvedValueOverride)({ documentKey: documentKey2, instanceKey: c.instanceKey }))
80
- );
77
+ (elementData2, documentKey2) => (0, import_react.startTransition)(async () => {
78
+ const state = store.getState();
79
+ const generation = (0, import_unified_state.isReadWriteState)(state) ? (0, import_read_write_state.getResolvedValueOverridesGeneration)(state) : null;
80
+ await serverRefresh(elementData2, () => {
81
+ if (generation == null)
82
+ return;
83
+ (0, import_react.startTransition)(() => {
84
+ dispatch((0, import_read_write_actions.clearStaleResolvedValueOverrides)({ documentKey: documentKey2, elementKey, generation }));
85
+ });
81
86
  });
82
87
  }),
83
- [serverRefresh, dispatch]
88
+ [serverRefresh, dispatch, store, elementKey]
84
89
  );
85
90
  const applyResolvedValueOverrides = (0, import_react.useCallback)(
86
91
  (instances, props, documentKey2) => instances.forEach(
@@ -98,21 +103,21 @@ const EditableServerElementWrapper = ({
98
103
  if (documentKey == null)
99
104
  return;
100
105
  if (children == null) {
101
- const { leafInstances, leafProps } = getLeafPropsAndInstances(resolvedProps, controlInstances);
102
- applyServerRefresh(elementData, leafInstances, documentKey);
106
+ const { leafProps } = getLeafPropsAndInstances(resolvedProps, controlInstances);
107
+ applyServerRefresh(elementData, documentKey);
103
108
  prevPropsRef.current = resolvedProps;
104
109
  prevLeafPropsRef.current = leafProps;
105
110
  return;
106
111
  }
107
112
  if (resolvedProps !== prevPropsRef.current) {
108
- const { needsRefresh, leafInstances, leafProps, reactNodeInstances } = needsServerRefresh({
113
+ const { needsRefresh, leafProps, reactNodeInstances } = needsServerRefresh({
109
114
  resolvedProps,
110
115
  controlInstances,
111
116
  prevProps: prevPropsRef.current,
112
117
  prevLeafProps: prevLeafPropsRef.current
113
118
  });
114
119
  if (needsRefresh) {
115
- applyServerRefresh(elementData, leafInstances, documentKey);
120
+ applyServerRefresh(elementData, documentKey);
116
121
  } else {
117
122
  applyResolvedValueOverrides(reactNodeInstances, resolvedProps, documentKey);
118
123
  }
@@ -155,7 +160,6 @@ const needsServerRefresh = ({
155
160
  const needsRefresh = (0, import_set.setDifference)(updatedLeafProps, reactNodePropKeys).size > 0 || newlyAddedLeafProps.size > 0;
156
161
  return {
157
162
  needsRefresh,
158
- leafInstances,
159
163
  leafProps,
160
164
  reactNodeInstances
161
165
  };
@@ -1 +1 @@
1
- {"version":3,"sources":["../../../../../../src/runtimes/react/server/components/editable-server-element.tsx"],"sourcesContent":["'use client'\n\nimport { type PropsWithChildren, useEffect, useRef, startTransition, useCallback } from 'react'\n\nimport { ControlInstance } from '@makeswift/controls'\n\nimport { type ElementData } from '../../../../state/read-only-state'\nimport {\n setResolvedValueOverride,\n clearResolvedValueOverride,\n} from '../../../../state/actions/internal/read-write-actions'\n\nimport { useServerElementRefresh } from '../../hooks/use-server-element-refresh'\nimport { useElementData } from '../../hooks/use-element-data'\nimport { useControlDefs } from '../../hooks/use-control-defs'\nimport { useResolvedProps } from '../../hooks/use-resolved-props'\nimport { useControlInstances } from '../../components/control-instances-context'\nimport { useDispatch } from '../../hooks/use-dispatch'\nimport { useDocumentKey } from '../../hooks/use-document-context'\n\nimport { getProp } from '../../../../utils/prop-by-path'\nimport { setUnion, setDifference } from '../../../../utils/set'\nimport { useControlledStyles } from '../../css-runtime/hooks/use-controlled-styles'\n\nexport const EditableServerElement = ({\n initialElementData,\n children,\n}: PropsWithChildren<{ initialElementData: ElementData }>) => {\n const elementKey = initialElementData.key\n const elementData = useElementData({ elementKey })\n if (elementData == null) {\n // Element has been deleted\n return null\n }\n\n return (\n <EditableServerElementWrapper {...{ initialElementData, elementData }}>\n {children}\n </EditableServerElementWrapper>\n )\n}\n\n/**\n * Reflects edits to `elementData.props` in the server-rendered `children`.\n * Changes limited to existing `ReactNode` props are applied through client-side\n * overrides. Style prop changes are handled by the stylesheet engine during\n * prop resolution. All other prop changes trigger a server refresh.\n */\nconst EditableServerElementWrapper = ({\n initialElementData,\n elementData,\n children,\n}: PropsWithChildren<{ initialElementData: ElementData; elementData: ElementData }>) => {\n const elementKey = initialElementData.key\n const dispatch = useDispatch()\n const documentKey = useDocumentKey()\n\n const [_legacyDefs, definitions] = useControlDefs({ elementType: initialElementData.type })\n const { getStylesheet, styleElements } = useControlledStyles({ namespace: elementKey })\n\n const controlInstances = useControlInstances(elementKey)\n const resolvedProps = useResolvedProps({\n elementKey,\n propDefs: definitions,\n propData: elementData.props,\n controlInstances,\n getStylesheet,\n })\n\n const prevPropsRef = useRef(resolvedProps)\n const prevLeafPropsRef = useRef(\n getLeafPropsAndInstances(resolvedProps, controlInstances).leafProps,\n )\n\n const serverRefresh = useServerElementRefresh({ elementKey })\n const applyServerRefresh = useCallback(\n (elementData: ElementData, leafInstances: ControlInstance[], documentKey: string) =>\n startTransition(async () => {\n const applied = await serverRefresh(elementData)\n if (!applied) return\n\n // need a nested `startTransition` here, see\n // https://react.dev/reference/react/useTransition#react-doesnt-treat-my-state-update-after-await-as-a-transition\n startTransition(() => {\n // reset instance overrides, if any\n leafInstances.forEach(c =>\n dispatch(clearResolvedValueOverride({ documentKey, instanceKey: c.instanceKey })),\n )\n })\n }),\n [serverRefresh, dispatch],\n )\n\n const applyResolvedValueOverrides = useCallback(\n (instances: ControlInstance[], props: Record<string, unknown>, documentKey: string) =>\n instances.forEach(c =>\n dispatch(\n setResolvedValueOverride({\n documentKey,\n instanceKey: c.instanceKey,\n value: getProp(props, c.propPath),\n }),\n ),\n ),\n [dispatch],\n )\n\n useEffect(() => {\n if (documentKey == null) return\n\n if (children == null) {\n // If we don't have a server-rendered node (i.e. user just dropped the element to the page),\n // trigger a server re-render\n const { leafInstances, leafProps } = getLeafPropsAndInstances(resolvedProps, controlInstances)\n\n applyServerRefresh(elementData, leafInstances, documentKey)\n\n prevPropsRef.current = resolvedProps\n prevLeafPropsRef.current = leafProps\n return\n }\n\n if (resolvedProps !== prevPropsRef.current) {\n // If there was a change in resolved value, check if any of the changed props necessitate\n // a server refresh.\n //\n // Note that style props have stable class names and updating a style prop will not result\n // in a change to the resolved value, which is what we want. Dynamic style updates are handled\n // through a subscription mechanism that listens for changes to controlled style data in the\n // styles registry.\n const { needsRefresh, leafInstances, leafProps, reactNodeInstances } = needsServerRefresh({\n resolvedProps,\n controlInstances,\n prevProps: prevPropsRef.current,\n prevLeafProps: prevLeafPropsRef.current,\n })\n\n if (needsRefresh) {\n applyServerRefresh(elementData, leafInstances, documentKey)\n } else {\n applyResolvedValueOverrides(reactNodeInstances, resolvedProps, documentKey)\n }\n\n prevPropsRef.current = resolvedProps\n prevLeafPropsRef.current = leafProps\n }\n }, [\n children,\n resolvedProps,\n documentKey,\n elementData,\n controlInstances,\n applyServerRefresh,\n applyResolvedValueOverrides,\n ])\n\n return (\n <>\n {children}\n {styleElements}\n </>\n )\n}\n\n/**\n * Determines whether resolved prop changes require a server refresh and returns\n * the control-instance state needed to apply the update.\n */\nconst needsServerRefresh = ({\n resolvedProps,\n controlInstances,\n prevProps,\n prevLeafProps,\n}: {\n resolvedProps: Record<string, unknown>\n controlInstances: Record<string, ControlInstance> | null\n prevProps: Record<string, unknown>\n prevLeafProps: Set<string>\n}): {\n needsRefresh: boolean\n leafInstances: ControlInstance[]\n leafProps: Set<string>\n reactNodeInstances: ControlInstance[]\n} => {\n const { leafInstances, leafProps } = getLeafPropsAndInstances(resolvedProps, controlInstances)\n\n const combinedLeafProps = setUnion(leafProps, prevLeafProps).values()\n const updatedLeafProps = new Set(\n [...combinedLeafProps].filter(\n propName => getProp(resolvedProps, propName) !== getProp(prevProps, propName),\n ),\n )\n\n const updatedLeafInstances = leafInstances.filter(instance =>\n updatedLeafProps.has(instance.propPath),\n )\n\n const reactNodeInstances = updatedLeafInstances.filter(c => c.resolvesToRenderableNode())\n\n const reactNodePropKeys = new Set(reactNodeInstances.map(c => c.propPath))\n const newlyAddedLeafProps = setDifference(leafProps, prevLeafProps)\n\n // A server refresh is needed if some of the updated props are not `ReactNode` props, or we\n // have newly observed props (typically `List` items). Even when newly observed props are\n // `ReactNode` props, we have to first render them on the server to get them in the element\n // tree before they can be updated client-side.\n const needsRefresh =\n setDifference(updatedLeafProps, reactNodePropKeys).size > 0 || newlyAddedLeafProps.size > 0\n\n return {\n needsRefresh,\n leafInstances,\n leafProps,\n reactNodeInstances,\n }\n}\n\n/**\n * Returns terminal prop paths with the corresponding control instances.\n */\nconst getLeafPropsAndInstances = (\n props: Record<string, unknown>,\n controlInstances: Record<string, ControlInstance> | null,\n): {\n leafProps: Set<string>\n leafInstances: ControlInstance[]\n} => {\n const topLevelInstances = Object.keys(props)\n .map(prop => controlInstances?.[prop])\n .filter(inst => inst != null)\n\n const leafInstances = getLeafInstances(topLevelInstances)\n const leafProps = new Set(leafInstances.map(c => c.propPath))\n return { leafProps, leafInstances }\n}\n\n/**\n * Flattens a control instance tree to its leaf (terminal) instances.\n */\nconst getLeafInstances = (instances: ControlInstance[]): ControlInstance[] =>\n instances.flatMap(instance =>\n instance.isCompositeProp() ? getLeafInstances(instance.children()) : [instance],\n )\n"],"mappings":"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","names":["elementData","documentKey"]}
1
+ {"version":3,"sources":["../../../../../../src/runtimes/react/server/components/editable-server-element.tsx"],"sourcesContent":["'use client'\n\nimport { type PropsWithChildren, useEffect, useRef, startTransition, useCallback } from 'react'\n\nimport { ControlInstance } from '@makeswift/controls'\n\nimport { type ElementData } from '../../../../state/read-only-state'\nimport { getResolvedValueOverridesGeneration } from '../../../../state/read-write-state'\nimport { isReadWriteState } from '../../../../state/unified-state'\nimport {\n setResolvedValueOverride,\n clearStaleResolvedValueOverrides,\n} from '../../../../state/actions/internal/read-write-actions'\n\nimport { useServerElementRefresh } from '../../hooks/use-server-element-refresh'\nimport { useElementData } from '../../hooks/use-element-data'\nimport { useControlDefs } from '../../hooks/use-control-defs'\nimport { useResolvedProps } from '../../hooks/use-resolved-props'\nimport { useControlInstances } from '../../components/control-instances-context'\nimport { useDispatch } from '../../hooks/use-dispatch'\nimport { useStore } from '../../hooks/use-store'\nimport { useDocumentKey } from '../../hooks/use-document-context'\n\nimport { getProp } from '../../../../utils/prop-by-path'\nimport { setUnion, setDifference } from '../../../../utils/set'\nimport { useControlledStyles } from '../../css-runtime/hooks/use-controlled-styles'\n\nexport const EditableServerElement = ({\n initialElementData,\n children,\n}: PropsWithChildren<{ initialElementData: ElementData }>) => {\n const elementKey = initialElementData.key\n const elementData = useElementData({ elementKey })\n if (elementData == null) {\n // Element has been deleted\n return null\n }\n\n return (\n <EditableServerElementWrapper {...{ initialElementData, elementData }}>\n {children}\n </EditableServerElementWrapper>\n )\n}\n\n/**\n * Reflects edits to `elementData.props` in the server-rendered `children`.\n * Changes limited to existing `ReactNode` props are applied through client-side\n * overrides. Style prop changes are handled by the stylesheet engine during\n * prop resolution. All other prop changes trigger a server refresh.\n */\nconst EditableServerElementWrapper = ({\n initialElementData,\n elementData,\n children,\n}: PropsWithChildren<{ initialElementData: ElementData; elementData: ElementData }>) => {\n const elementKey = initialElementData.key\n const store = useStore()\n const dispatch = useDispatch()\n const documentKey = useDocumentKey()\n\n const [_legacyDefs, definitions] = useControlDefs({ elementType: initialElementData.type })\n const { getStylesheet, styleElements } = useControlledStyles({ namespace: elementKey })\n\n const controlInstances = useControlInstances(elementKey)\n const resolvedProps = useResolvedProps({\n elementKey,\n propDefs: definitions,\n propData: elementData.props,\n controlInstances,\n getStylesheet,\n })\n\n const prevPropsRef = useRef(resolvedProps)\n const prevLeafPropsRef = useRef(\n getLeafPropsAndInstances(resolvedProps, controlInstances).leafProps,\n )\n\n const serverRefresh = useServerElementRefresh({ elementKey })\n const applyServerRefresh = useCallback(\n (elementData: ElementData, documentKey: string) =>\n startTransition(async () => {\n const state = store.getState()\n // Capture the overrides generation prior to initiating server refresh so that we\n // only clear the overrides that haven't been updated while the refresh is in flight\n const generation = isReadWriteState(state)\n ? getResolvedValueOverridesGeneration(state)\n : null\n\n await serverRefresh(elementData, () => {\n if (generation == null) return\n // need a nested `startTransition` here, see\n // https://react.dev/reference/react/useTransition#react-doesnt-treat-my-state-update-after-await-as-a-transition\n startTransition(() => {\n dispatch(clearStaleResolvedValueOverrides({ documentKey, elementKey, generation }))\n })\n })\n }),\n [serverRefresh, dispatch, store, elementKey],\n )\n\n const applyResolvedValueOverrides = useCallback(\n (instances: ControlInstance[], props: Record<string, unknown>, documentKey: string) =>\n instances.forEach(c =>\n dispatch(\n setResolvedValueOverride({\n documentKey,\n instanceKey: c.instanceKey,\n value: getProp(props, c.propPath),\n }),\n ),\n ),\n [dispatch],\n )\n\n useEffect(() => {\n if (documentKey == null) return\n\n if (children == null) {\n // If we don't have a server-rendered node (i.e. user just dropped the element to the page),\n // trigger a server re-render\n const { leafProps } = getLeafPropsAndInstances(resolvedProps, controlInstances)\n\n applyServerRefresh(elementData, documentKey)\n\n prevPropsRef.current = resolvedProps\n prevLeafPropsRef.current = leafProps\n return\n }\n\n if (resolvedProps !== prevPropsRef.current) {\n // If there was a change in resolved value, check if any of the changed props necessitate\n // a server refresh.\n //\n // Note that style props have stable class names and updating a style prop will not result\n // in a change to the resolved value, which is what we want. Dynamic style updates are handled\n // through a subscription mechanism that listens for changes to controlled style data in the\n // styles registry.\n const { needsRefresh, leafProps, reactNodeInstances } = needsServerRefresh({\n resolvedProps,\n controlInstances,\n prevProps: prevPropsRef.current,\n prevLeafProps: prevLeafPropsRef.current,\n })\n\n if (needsRefresh) {\n applyServerRefresh(elementData, documentKey)\n } else {\n applyResolvedValueOverrides(reactNodeInstances, resolvedProps, documentKey)\n }\n\n prevPropsRef.current = resolvedProps\n prevLeafPropsRef.current = leafProps\n }\n }, [\n children,\n resolvedProps,\n documentKey,\n elementData,\n controlInstances,\n applyServerRefresh,\n applyResolvedValueOverrides,\n ])\n\n return (\n <>\n {children}\n {styleElements}\n </>\n )\n}\n\n/**\n * Determines whether resolved prop changes require a server refresh and returns\n * the control-instance state needed to apply the update.\n */\nconst needsServerRefresh = ({\n resolvedProps,\n controlInstances,\n prevProps,\n prevLeafProps,\n}: {\n resolvedProps: Record<string, unknown>\n controlInstances: Record<string, ControlInstance> | null\n prevProps: Record<string, unknown>\n prevLeafProps: Set<string>\n}): {\n needsRefresh: boolean\n leafProps: Set<string>\n reactNodeInstances: ControlInstance[]\n} => {\n const { leafInstances, leafProps } = getLeafPropsAndInstances(resolvedProps, controlInstances)\n\n const combinedLeafProps = setUnion(leafProps, prevLeafProps).values()\n const updatedLeafProps = new Set(\n [...combinedLeafProps].filter(\n propName => getProp(resolvedProps, propName) !== getProp(prevProps, propName),\n ),\n )\n\n const updatedLeafInstances = leafInstances.filter(instance =>\n updatedLeafProps.has(instance.propPath),\n )\n\n const reactNodeInstances = updatedLeafInstances.filter(c => c.resolvesToRenderableNode())\n\n const reactNodePropKeys = new Set(reactNodeInstances.map(c => c.propPath))\n const newlyAddedLeafProps = setDifference(leafProps, prevLeafProps)\n\n // A server refresh is needed if some of the updated props are not `ReactNode` props, or we\n // have newly observed props (typically `List` items). Even when newly observed props are\n // `ReactNode` props, we have to first render them on the server to get them in the element\n // tree before they can be updated client-side.\n const needsRefresh =\n setDifference(updatedLeafProps, reactNodePropKeys).size > 0 || newlyAddedLeafProps.size > 0\n\n return {\n needsRefresh,\n leafProps,\n reactNodeInstances,\n }\n}\n\n/**\n * Returns terminal prop paths with the corresponding control instances.\n */\nconst getLeafPropsAndInstances = (\n props: Record<string, unknown>,\n controlInstances: Record<string, ControlInstance> | null,\n): {\n leafProps: Set<string>\n leafInstances: ControlInstance[]\n} => {\n const topLevelInstances = Object.keys(props)\n .map(prop => controlInstances?.[prop])\n .filter(inst => inst != null)\n\n const leafInstances = getLeafInstances(topLevelInstances)\n const leafProps = new Set(leafInstances.map(c => c.propPath))\n return { leafProps, leafInstances }\n}\n\n/**\n * Flattens a control instance tree to its leaf (terminal) instances.\n */\nconst getLeafInstances = (instances: ControlInstance[]): ControlInstance[] =>\n instances.flatMap(instance =>\n instance.isCompositeProp() ? getLeafInstances(instance.children()) : [instance],\n )\n"],"mappings":"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","names":["elementData","documentKey"]}
@@ -26,41 +26,91 @@ __export(server_elements_cache_exports, {
26
26
  module.exports = __toCommonJS(server_elements_cache_exports);
27
27
  var import_jsx_runtime = require("react/jsx-runtime");
28
28
  var import_react = require("react");
29
+ var import_useIsomorphicLayoutEffect = require("../../../../components/hooks/useIsomorphicLayoutEffect");
30
+ const createCacheState = (initialElements) => ({
31
+ initialElements,
32
+ elements: new Map(Array.from(initialElements, ([key, node]) => [key, { node }])),
33
+ refreshScope: {
34
+ active: false,
35
+ requestsByElement: /* @__PURE__ */ new Map()
36
+ }
37
+ });
29
38
  const Context = (0, import_react.createContext)({
30
39
  getElement: () => null,
31
- updateElement: () => {
32
- },
33
- removeElement: () => {
34
- }
40
+ beginRefresh: () => null
35
41
  });
36
42
  const ServerElementsCache = ({
37
43
  children,
38
44
  value
39
45
  }) => {
40
- const [nodes, setNodes] = (0, import_react.useState)(value);
41
- const [previousValue, setPreviousValue] = (0, import_react.useState)(value);
42
- if (value !== previousValue) {
43
- setPreviousValue(value);
44
- setNodes(value);
46
+ const [state, setState] = (0, import_react.useState)(() => createCacheState(value));
47
+ if (state.initialElements !== value) {
48
+ setState(createCacheState(value));
45
49
  }
46
- const getElement = (0, import_react.useCallback)((elementKey) => nodes.get(elementKey), [nodes]);
47
- const updateElement = (0, import_react.useCallback)(
48
- (elementKey, node) => setNodes((prev) => new Map(prev).set(elementKey, node)),
49
- []
50
- );
51
- const removeElement = (0, import_react.useCallback)(
52
- (elementKey) => setNodes((prev) => {
53
- const next = new Map(prev);
54
- next.delete(elementKey);
55
- return next;
56
- }),
57
- []
50
+ const { elements, refreshScope } = state;
51
+ (0, import_useIsomorphicLayoutEffect.useIsomorphicLayoutEffect)(() => {
52
+ refreshScope.active = true;
53
+ return () => {
54
+ refreshScope.active = false;
55
+ };
56
+ }, [refreshScope]);
57
+ const getElement = (0, import_react.useCallback)(
58
+ // Always wrap the node in `<RefreshCommitObserver>` so adding a commit callback
59
+ // during refresh doesn't change the tree shape and remount the refreshed node
60
+ (elementKey) => {
61
+ const entry = elements.get(elementKey);
62
+ if (entry == null)
63
+ return null;
64
+ return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(RefreshCommitObserver, { onCommitted: entry.onCommitted, children: entry.node });
65
+ },
66
+ [elements]
58
67
  );
59
- const cache = (0, import_react.useMemo)(
60
- () => ({ getElement, updateElement, removeElement }),
61
- [getElement, updateElement, removeElement]
68
+ const beginRefresh = (0, import_react.useCallback)(
69
+ (elementKey, onCommitted) => {
70
+ const { requestsByElement } = refreshScope;
71
+ const elementRequests = requestsByElement.get(elementKey) ?? {
72
+ lastIssued: 0,
73
+ lastAccepted: 0,
74
+ lastCommitted: 0
75
+ };
76
+ requestsByElement.set(elementKey, elementRequests);
77
+ const requestId = ++elementRequests.lastIssued;
78
+ return (node) => {
79
+ if (!refreshScope.active || requestId <= elementRequests.lastAccepted)
80
+ return;
81
+ elementRequests.lastAccepted = requestId;
82
+ const notifyCommitted = () => {
83
+ if (requestId <= elementRequests.lastCommitted)
84
+ return;
85
+ elementRequests.lastCommitted = requestId;
86
+ const callback = onCommitted;
87
+ onCommitted = void 0;
88
+ callback?.();
89
+ };
90
+ setState((prev) => {
91
+ if (prev.refreshScope !== refreshScope)
92
+ return prev;
93
+ return {
94
+ ...prev,
95
+ elements: new Map(prev.elements).set(elementKey, {
96
+ node,
97
+ onCommitted: notifyCommitted
98
+ })
99
+ };
100
+ });
101
+ };
102
+ },
103
+ [refreshScope]
62
104
  );
63
- return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(Context.Provider, { value: cache, children });
105
+ const result = (0, import_react.useMemo)(() => ({ getElement, beginRefresh }), [getElement, beginRefresh]);
106
+ return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(Context.Provider, { value: result, children });
107
+ };
108
+ const RefreshCommitObserver = ({
109
+ children,
110
+ onCommitted
111
+ }) => {
112
+ (0, import_react.useEffect)(() => onCommitted?.(), [onCommitted]);
113
+ return children;
64
114
  };
65
115
  const ServerElementsProvider = ({
66
116
  children,