@farm.js/core 0.1.0-beta.95 → 0.1.0-beta.97
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/after.cjs +1 -1
- package/dist/after.mjs +1 -1
- package/dist/agent-runtime.d.mts +3 -2
- package/dist/agent-runtime.d.ts +3 -2
- package/dist/api/route-manager.cjs +43 -4
- package/dist/api/route-manager.d.mts +4 -3
- package/dist/api/route-manager.d.ts +4 -3
- package/dist/api/route-manager.mjs +7 -7
- package/dist/api/runtime.cjs +43 -4
- package/dist/api/runtime.d.mts +1 -1
- package/dist/api/runtime.d.ts +1 -1
- package/dist/api/runtime.mjs +5 -5
- package/dist/api.cjs +352 -109
- package/dist/api.d.mts +7 -6
- package/dist/api.d.ts +7 -6
- package/dist/api.mjs +19 -12
- package/dist/{app-CIIEvA4r.d.ts → app-CIOx3LvY.d.ts} +4 -4
- package/dist/{app-O4AEC1OH.d.mts → app-DBd6437H.d.mts} +4 -4
- package/dist/app-markdown.d.mts +4 -3
- package/dist/app-markdown.d.ts +4 -3
- package/dist/cache.cjs +42 -4
- package/dist/cache.d.mts +68 -1
- package/dist/cache.d.ts +68 -1
- package/dist/cache.mjs +3 -3
- package/dist/{chunk-AXVJCMVF.mjs → chunk-2HDOV47R.mjs} +3 -3
- package/dist/chunk-2HDOV47R.mjs.map +1 -0
- package/dist/{chunk-RBRLLZL5.mjs → chunk-34IAPZBG.mjs} +16 -3
- package/dist/chunk-34IAPZBG.mjs.map +1 -0
- package/dist/{chunk-VV24CC42.mjs → chunk-35NPLKQJ.mjs} +2 -2
- package/dist/{chunk-D7QH7MDU.mjs → chunk-3TWQERDE.mjs} +5 -4
- package/dist/chunk-3TWQERDE.mjs.map +1 -0
- package/dist/{chunk-RWYRFCLG.mjs → chunk-4X57GXQA.mjs} +2 -2
- package/dist/{chunk-KOTSX5JH.mjs → chunk-52BR7LTX.mjs} +30 -21
- package/dist/chunk-52BR7LTX.mjs.map +1 -0
- package/dist/{chunk-SALMKQXH.mjs → chunk-6EJHNHH4.mjs} +80 -27
- package/dist/chunk-6EJHNHH4.mjs.map +1 -0
- package/dist/{chunk-ZFNK77WN.mjs → chunk-6JNGOC37.mjs} +2 -2
- package/dist/{after.cjs.map → chunk-6JNGOC37.mjs.map} +1 -1
- package/dist/{chunk-MOW47IF5.mjs → chunk-6UYVU46O.mjs} +2 -2
- package/dist/{chunk-7MABZJIM.mjs → chunk-7PYVLJ4J.mjs} +1 -1
- package/dist/chunk-7PYVLJ4J.mjs.map +1 -0
- package/dist/{chunk-FLHLPB57.mjs → chunk-D7F7YZ7L.mjs} +93 -67
- package/dist/chunk-D7F7YZ7L.mjs.map +1 -0
- package/dist/chunk-DU3PKDVQ.mjs +35 -0
- package/dist/chunk-DU3PKDVQ.mjs.map +1 -0
- package/dist/{chunk-SCFX4UTD.mjs → chunk-EHTUKVSW.mjs} +1 -1
- package/dist/chunk-EHTUKVSW.mjs.map +1 -0
- package/dist/{chunk-KWCNQUH5.mjs → chunk-EPDIF432.mjs} +526 -50
- package/dist/chunk-EPDIF432.mjs.map +1 -0
- package/dist/{chunk-A3636IHN.mjs → chunk-FP5Q67FO.mjs} +167 -96
- package/dist/chunk-FP5Q67FO.mjs.map +1 -0
- package/dist/{chunk-HHZAOTQD.mjs → chunk-GJ7W6LNK.mjs} +7 -6
- package/dist/chunk-GJ7W6LNK.mjs.map +1 -0
- package/dist/{chunk-RLGUZ3HS.mjs → chunk-I3OOUWO5.mjs} +3 -3
- package/dist/{chunk-75CGAL6E.mjs → chunk-IZBX2TEU.mjs} +217 -105
- package/dist/chunk-IZBX2TEU.mjs.map +1 -0
- package/dist/{chunk-22VG4DFJ.mjs → chunk-J3MPQ4MQ.mjs} +2 -2
- package/dist/{chunk-22VG4DFJ.mjs.map → chunk-J3MPQ4MQ.mjs.map} +1 -1
- package/dist/{chunk-2LS3KKE7.mjs → chunk-JV7JUD7Q.mjs} +4 -4
- package/dist/{chunk-Q3OX763A.mjs → chunk-LXDASSTE.mjs} +2 -2
- package/dist/{chunk-ZRBCBOEX.mjs → chunk-N2FY2QZ7.mjs} +28 -3
- package/dist/chunk-N2FY2QZ7.mjs.map +1 -0
- package/dist/{chunk-MRVJCLYQ.mjs → chunk-PSQ7N4XP.mjs} +4 -2
- package/dist/chunk-PSQ7N4XP.mjs.map +1 -0
- package/dist/{chunk-HVG3HLQZ.mjs → chunk-Q7WGOOAI.mjs} +3 -3
- package/dist/{chunk-WTYAPO5I.mjs → chunk-RCNWMEBT.mjs} +3 -2
- package/dist/{chunk-WTYAPO5I.mjs.map → chunk-RCNWMEBT.mjs.map} +1 -1
- package/dist/{chunk-3INDBMUU.mjs → chunk-TGDIACZT.mjs} +2 -2
- package/dist/{chunk-WB75GIX2.mjs → chunk-TQTB33JS.mjs} +14 -3
- package/dist/chunk-TQTB33JS.mjs.map +1 -0
- package/dist/{chunk-MH27UH72.mjs → chunk-TT3E2JOF.mjs} +3 -3
- package/dist/{chunk-UWRGX3J3.mjs → chunk-UMUWR5XA.mjs} +2 -2
- package/dist/{chunk-XTLLHCWU.mjs → chunk-V4VRLVLW.mjs} +52 -31
- package/dist/chunk-V4VRLVLW.mjs.map +1 -0
- package/dist/{chunk-EXCGBERG.mjs → chunk-WD2EBM3I.mjs} +79 -17
- package/dist/chunk-WD2EBM3I.mjs.map +1 -0
- package/dist/{chunk-DLBUAJTK.mjs → chunk-WMJGA32P.mjs} +74 -5
- package/dist/chunk-WMJGA32P.mjs.map +1 -0
- package/dist/{chunk-TKQCJMY7.mjs → chunk-X4SFHKFH.mjs} +7 -4
- package/dist/{chunk-TKQCJMY7.mjs.map → chunk-X4SFHKFH.mjs.map} +1 -1
- package/dist/{chunk-Q7GPJZCO.mjs → chunk-YIBV77KZ.mjs} +26 -7
- package/dist/chunk-YIBV77KZ.mjs.map +1 -0
- package/dist/client/lifecycle.mjs +2 -2
- package/dist/{client-mcMC334J.d.mts → client-DWoLZ3QU.d.mts} +52 -5
- package/dist/{client-d5ONQ-Pd.d.ts → client-DuQuQC1h.d.ts} +52 -5
- package/dist/client-cache-BMxuFqwH.d.ts +18 -0
- package/dist/client-cache-CCK-fCe0.d.mts +18 -0
- package/dist/{client-plugins-BvClItiL.d.mts → client-plugins-B6-07YmP.d.mts} +52 -99
- package/dist/{client-plugins-B9Sq-iMg.d.ts → client-plugins-By6MVUX-.d.ts} +52 -99
- package/dist/client-plugins.cjs +1 -1
- package/dist/client-plugins.d.mts +3 -2
- package/dist/client-plugins.d.ts +3 -2
- package/dist/client-plugins.mjs +2 -2
- package/dist/client.cjs +1046 -211
- package/dist/client.d.mts +136 -18
- package/dist/client.d.ts +136 -18
- package/dist/client.mjs +32 -15
- package/dist/config.d.mts +3 -2
- package/dist/config.d.ts +3 -2
- package/dist/{devtools-S52RRRMN.mjs → devtools-XWZX6CCL.mjs} +5 -5
- package/dist/{devtools-client-3XRTBND5.mjs → devtools-client-Z7QQA3Q2.mjs} +56 -17
- package/dist/devtools-client-Z7QQA3Q2.mjs.map +1 -0
- package/dist/{devtools-ui-NJKFORTG.mjs → devtools-ui-2HG5M4EL.mjs} +3 -1
- package/dist/devtools-ui-2HG5M4EL.mjs.map +1 -0
- package/dist/docs.cjs +24 -5
- package/dist/docs.mjs +5 -5
- package/dist/i18n/server.cjs +13 -2
- package/dist/i18n/server.d.mts +2 -2
- package/dist/i18n/server.d.ts +2 -2
- package/dist/i18n/server.mjs +1 -1
- package/dist/index.cjs +1928 -894
- package/dist/index.d.mts +139 -21
- package/dist/index.d.ts +139 -21
- package/dist/index.mjs +57 -34
- package/dist/index.mjs.map +1 -1
- package/dist/integration-api-BT024nuJ.d.mts +97 -0
- package/dist/integration-api-BT024nuJ.d.ts +97 -0
- package/dist/integrations.d.mts +3 -2
- package/dist/integrations.d.ts +3 -2
- package/dist/internal/build-runtime.cjs +764 -547
- package/dist/internal/build-runtime.d.mts +5 -4
- package/dist/internal/build-runtime.d.ts +5 -4
- package/dist/internal/build-runtime.mjs +16 -16
- package/dist/internal/client-runtime.cjs +1 -1
- package/dist/internal/client-runtime.mjs +2 -2
- package/dist/internal/config-runtime.cjs +4 -1
- package/dist/internal/config-runtime.d.mts +4 -3
- package/dist/internal/config-runtime.d.ts +4 -3
- package/dist/internal/config-runtime.mjs +4 -4
- package/dist/internal/product-telemetry-runtime.cjs +1 -1
- package/dist/internal/product-telemetry-runtime.mjs +1 -1
- package/dist/internal/production-runtime.cjs +29 -3
- package/dist/internal/production-runtime.d.mts +8 -7
- package/dist/internal/production-runtime.d.ts +8 -7
- package/dist/internal/production-runtime.mjs +5 -5
- package/dist/{metadata-route-yV4U6X8h.d.ts → metadata-route-8_V3UonT.d.ts} +1 -1
- package/dist/{metadata-route-p4K1l92V.d.mts → metadata-route-CWP_HjGU.d.mts} +1 -1
- package/dist/middleware.cjs +28 -2
- package/dist/middleware.d.mts +5 -4
- package/dist/middleware.d.ts +5 -4
- package/dist/middleware.mjs +4 -4
- package/dist/navigation.cjs +3 -1
- package/dist/navigation.mjs +3 -3
- package/dist/observability.cjs +27 -2
- package/dist/observability.mjs +1 -1
- package/dist/plugin.cjs +528 -349
- package/dist/plugin.d.mts +3 -2
- package/dist/plugin.d.ts +3 -2
- package/dist/plugin.mjs +13 -13
- package/dist/{production-runtime-IkB0Qj4i.d.mts → production-runtime-BGRH1dKG.d.mts} +1 -1
- package/dist/{production-runtime-0JTch4_d.d.ts → production-runtime-CdmzsDax.d.ts} +1 -1
- package/dist/query/client.cjs +68 -29
- package/dist/query/client.mjs +69 -30
- package/dist/query/client.mjs.map +1 -1
- package/dist/{render-plan-Dc8CjNI7.d.ts → render-plan-0GeHiGVZ.d.ts} +1 -1
- package/dist/{render-plan-CU31j-Jk.d.mts → render-plan-DLxJYAA5.d.mts} +1 -1
- package/dist/renderer-client.cjs +169 -26
- package/dist/renderer-client.d.mts +7 -6
- package/dist/renderer-client.d.ts +7 -6
- package/dist/renderer-client.mjs +16 -19
- package/dist/renderer-client.mjs.map +1 -1
- package/dist/{request-BXa1KY8i.d.mts → request-BCNXSXLh.d.mts} +1 -1
- package/dist/{request-CUUBujZt.d.ts → request-BstWbZ6O.d.ts} +1 -1
- package/dist/request.d.mts +4 -3
- package/dist/request.d.ts +4 -3
- package/dist/{route-Y8lfz1wF.d.ts → route-4pd-EVtw.d.ts} +45 -50
- package/dist/{route-Cq3aObmj.d.mts → route-CvEr4Uc9.d.mts} +45 -50
- package/dist/routes.cjs +27 -2
- package/dist/routes.d.mts +3 -2
- package/dist/routes.d.ts +3 -2
- package/dist/routes.mjs +4 -4
- package/dist/{runtime-j1S3sDTh.d.ts → runtime-BgDQzBiu.d.ts} +1 -0
- package/dist/{runtime-DDwvDtS4.d.mts → runtime-CV2UCV-5.d.mts} +1 -0
- package/dist/server-action-security.mjs +2 -2
- package/dist/server-fn-client.cjs +102 -26
- package/dist/server-fn-client.d.mts +6 -0
- package/dist/server-fn-client.d.ts +6 -0
- package/dist/server-fn-client.mjs +2 -1
- package/dist/server-fn.cjs +42 -4
- package/dist/server-fn.mjs +5 -5
- package/dist/server-plugins.d.mts +4 -3
- package/dist/server-plugins.d.ts +4 -3
- package/dist/server-query-client.cjs +195 -34
- package/dist/server-query-client.d.mts +3 -3
- package/dist/server-query-client.d.ts +3 -3
- package/dist/server-query-client.mjs +7 -7
- package/dist/{server-query-runtime-3zAj77yv.d.ts → server-query-runtime-DXRNhX_3.d.ts} +2 -0
- package/dist/{server-query-runtime-B50KAcj5.d.mts → server-query-runtime-aP52iuL5.d.mts} +2 -0
- package/dist/server-query.cjs +44 -5
- package/dist/server-query.d.mts +4 -0
- package/dist/server-query.d.ts +4 -0
- package/dist/server-query.mjs +7 -7
- package/dist/server.cjs +553 -370
- package/dist/server.d.mts +11 -10
- package/dist/server.d.ts +11 -10
- package/dist/server.mjs +17 -17
- package/dist/{spa-router-CyLkwst6.d.mts → spa-router-BeyAVSc6.d.mts} +1 -1
- package/dist/{spa-router-BkqGXaV_.d.ts → spa-router-COgu4txb.d.ts} +1 -1
- package/dist/testing.cjs +27 -2
- package/dist/testing.d.mts +3 -2
- package/dist/testing.d.ts +3 -2
- package/dist/testing.mjs +9 -9
- package/dist/{utils-NKR6SoNv.d.mts → utils-DL2VwDQl.d.mts} +1 -1
- package/dist/{utils-B2OHrb9F.d.ts → utils-DkU2c_1B.d.ts} +1 -1
- package/dist/version.cjs +1 -1
- package/dist/version.mjs +1 -1
- package/dist/vite.cjs +536 -353
- package/dist/vite.d.mts +3 -2
- package/dist/vite.d.ts +3 -2
- package/dist/vite.mjs +17 -13
- package/package.json +17 -17
- package/types/client.d.ts +115 -10
- package/dist/agent-runtime.cjs.map +0 -1
- package/dist/api/route-manager.cjs.map +0 -1
- package/dist/api/runtime.cjs.map +0 -1
- package/dist/api.cjs.map +0 -1
- package/dist/app-markdown.cjs.map +0 -1
- package/dist/cache.cjs.map +0 -1
- package/dist/chunk-75CGAL6E.mjs.map +0 -1
- package/dist/chunk-7MABZJIM.mjs.map +0 -1
- package/dist/chunk-A3636IHN.mjs.map +0 -1
- package/dist/chunk-AXVJCMVF.mjs.map +0 -1
- package/dist/chunk-D7QH7MDU.mjs.map +0 -1
- package/dist/chunk-DLBUAJTK.mjs.map +0 -1
- package/dist/chunk-EXCGBERG.mjs.map +0 -1
- package/dist/chunk-FLHLPB57.mjs.map +0 -1
- package/dist/chunk-HHZAOTQD.mjs.map +0 -1
- package/dist/chunk-KOTSX5JH.mjs.map +0 -1
- package/dist/chunk-KWCNQUH5.mjs.map +0 -1
- package/dist/chunk-MRVJCLYQ.mjs.map +0 -1
- package/dist/chunk-Q7GPJZCO.mjs.map +0 -1
- package/dist/chunk-RBRLLZL5.mjs.map +0 -1
- package/dist/chunk-SALMKQXH.mjs.map +0 -1
- package/dist/chunk-SCFX4UTD.mjs.map +0 -1
- package/dist/chunk-WB75GIX2.mjs.map +0 -1
- package/dist/chunk-XTLLHCWU.mjs.map +0 -1
- package/dist/chunk-ZFNK77WN.mjs.map +0 -1
- package/dist/chunk-ZRBCBOEX.mjs.map +0 -1
- package/dist/client/lifecycle.cjs.map +0 -1
- package/dist/client-cache-CopR_MaI.d.mts +0 -6
- package/dist/client-cache-Djy_TlE8.d.ts +0 -6
- package/dist/client-plugins.cjs.map +0 -1
- package/dist/client.cjs.map +0 -1
- package/dist/config.cjs.map +0 -1
- package/dist/cron.cjs.map +0 -1
- package/dist/deferred.cjs.map +0 -1
- package/dist/deployment.cjs.map +0 -1
- package/dist/devtools-client-3XRTBND5.mjs.map +0 -1
- package/dist/devtools-ui-NJKFORTG.mjs.map +0 -1
- package/dist/docs.cjs.map +0 -1
- package/dist/env-types.cjs.map +0 -1
- package/dist/env.cjs.map +0 -1
- package/dist/environment/vite.cjs.map +0 -1
- package/dist/environment.cjs.map +0 -1
- package/dist/font.cjs.map +0 -1
- package/dist/headers.cjs.map +0 -1
- package/dist/i18n/client.cjs.map +0 -1
- package/dist/i18n/index.cjs.map +0 -1
- package/dist/i18n/server.cjs.map +0 -1
- package/dist/image/server.cjs.map +0 -1
- package/dist/image/sharp.cjs.map +0 -1
- package/dist/image.cjs.map +0 -1
- package/dist/index.cjs.map +0 -1
- package/dist/instrumentation.cjs.map +0 -1
- package/dist/integrations.cjs.map +0 -1
- package/dist/internal/build-runtime.cjs.map +0 -1
- package/dist/internal/client-runtime.cjs.map +0 -1
- package/dist/internal/config-runtime.cjs.map +0 -1
- package/dist/internal/isolated-boundary.cjs.map +0 -1
- package/dist/internal/metadata-image-runtime.cjs.map +0 -1
- package/dist/internal/product-telemetry-runtime.cjs.map +0 -1
- package/dist/internal/production-node-env.cjs.map +0 -1
- package/dist/internal/production-runtime.cjs.map +0 -1
- package/dist/markdown.cjs.map +0 -1
- package/dist/middleware.cjs.map +0 -1
- package/dist/navigation.cjs.map +0 -1
- package/dist/observability.cjs.map +0 -1
- package/dist/plugin.cjs.map +0 -1
- package/dist/query/client.cjs.map +0 -1
- package/dist/query/index.cjs.map +0 -1
- package/dist/query/parsers.cjs.map +0 -1
- package/dist/query/server.cjs.map +0 -1
- package/dist/renderer/react/client.cjs.map +0 -1
- package/dist/renderer/react/server.cjs.map +0 -1
- package/dist/renderer/react/vite.cjs.map +0 -1
- package/dist/renderer-client.cjs.map +0 -1
- package/dist/renderer.cjs.map +0 -1
- package/dist/request.cjs.map +0 -1
- package/dist/router.cjs.map +0 -1
- package/dist/routes.cjs.map +0 -1
- package/dist/server-action-security.cjs.map +0 -1
- package/dist/server-fn-client.cjs.map +0 -1
- package/dist/server-fn.cjs.map +0 -1
- package/dist/server-plugins.cjs.map +0 -1
- package/dist/server-query-client.cjs.map +0 -1
- package/dist/server-query.cjs.map +0 -1
- package/dist/server.cjs.map +0 -1
- package/dist/storage.cjs.map +0 -1
- package/dist/testing.cjs.map +0 -1
- package/dist/theme/client.cjs.map +0 -1
- package/dist/theme/index.cjs.map +0 -1
- package/dist/theme/runtime.cjs.map +0 -1
- package/dist/theme/server.cjs.map +0 -1
- package/dist/version.cjs.map +0 -1
- package/dist/vite.cjs.map +0 -1
- package/dist/workflows.cjs.map +0 -1
- /package/dist/{chunk-VV24CC42.mjs.map → chunk-35NPLKQJ.mjs.map} +0 -0
- /package/dist/{chunk-RWYRFCLG.mjs.map → chunk-4X57GXQA.mjs.map} +0 -0
- /package/dist/{chunk-MOW47IF5.mjs.map → chunk-6UYVU46O.mjs.map} +0 -0
- /package/dist/{chunk-RLGUZ3HS.mjs.map → chunk-I3OOUWO5.mjs.map} +0 -0
- /package/dist/{chunk-2LS3KKE7.mjs.map → chunk-JV7JUD7Q.mjs.map} +0 -0
- /package/dist/{chunk-Q3OX763A.mjs.map → chunk-LXDASSTE.mjs.map} +0 -0
- /package/dist/{chunk-HVG3HLQZ.mjs.map → chunk-Q7WGOOAI.mjs.map} +0 -0
- /package/dist/{chunk-3INDBMUU.mjs.map → chunk-TGDIACZT.mjs.map} +0 -0
- /package/dist/{chunk-MH27UH72.mjs.map → chunk-TT3E2JOF.mjs.map} +0 -0
- /package/dist/{chunk-UWRGX3J3.mjs.map → chunk-UMUWR5XA.mjs.map} +0 -0
- /package/dist/{devtools-S52RRRMN.mjs.map → devtools-XWZX6CCL.mjs.map} +0 -0
package/dist/client.cjs
CHANGED
|
@@ -32,11 +32,15 @@ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: tru
|
|
|
32
32
|
var client_exports = {};
|
|
33
33
|
__export(client_exports, {
|
|
34
34
|
APIClientError: () => APIClientError,
|
|
35
|
+
FARM_CACHE_INVALIDATION_CHANNEL: () => FARM_CACHE_INVALIDATION_CHANNEL,
|
|
36
|
+
FARM_CLIENT_CACHE_PERSIST_VERSION: () => FARM_CLIENT_CACHE_PERSIST_VERSION,
|
|
35
37
|
FarmClientPluginManager: () => FarmClientPluginManager,
|
|
38
|
+
FetcherInputError: () => FetcherInputError,
|
|
36
39
|
IntegrationClientError: () => IntegrationClientError,
|
|
37
40
|
Link: () => Link,
|
|
38
41
|
SPARouter: () => SPARouter,
|
|
39
42
|
api: () => api,
|
|
43
|
+
clearPersistedCache: () => clearPersistedCache,
|
|
40
44
|
createAPIClient: () => createAPIClient,
|
|
41
45
|
createApiClients: () => createApiClients,
|
|
42
46
|
createClientPluginManager: () => createClientPluginManager,
|
|
@@ -47,13 +51,16 @@ __export(client_exports, {
|
|
|
47
51
|
createIntegrations: () => createIntegrations,
|
|
48
52
|
createServerAPIClient: () => createServerAPIClient,
|
|
49
53
|
createStore: () => createStore,
|
|
54
|
+
defineClientCacheAdapter: () => defineClientCacheAdapter,
|
|
50
55
|
defineIntegrationAPI: () => defineIntegrationAPI,
|
|
51
56
|
defineIntegrationAPIOperation: () => defineIntegrationAPIOperation,
|
|
57
|
+
enableCrossTabCacheInvalidation: () => enableCrossTabCacheInvalidation,
|
|
52
58
|
endpoint: () => endpoint,
|
|
53
59
|
fetchServerQuery: () => fetchServerQuery,
|
|
54
60
|
getIntegrationAPIManifest: () => getIntegrationAPIManifest,
|
|
55
61
|
getRouter: () => getRouter2,
|
|
56
62
|
getTheme: () => getTheme,
|
|
63
|
+
initPersistedClientCache: () => initPersistedClientCache,
|
|
57
64
|
installChunkErrorRecovery: () => installChunkErrorRecovery,
|
|
58
65
|
integrationClients: () => integrationClients,
|
|
59
66
|
integrationsClient: () => integrationsClient,
|
|
@@ -66,6 +73,7 @@ __export(client_exports, {
|
|
|
66
73
|
readPageState: () => readPageState,
|
|
67
74
|
replaceState: () => replaceState,
|
|
68
75
|
setTheme: () => setTheme,
|
|
76
|
+
storageClientCacheAdapter: () => storageClientCacheAdapter,
|
|
69
77
|
toggleTheme: () => toggleTheme,
|
|
70
78
|
useAction: () => useAction,
|
|
71
79
|
useBlocker: () => useBlocker,
|
|
@@ -223,10 +231,10 @@ __name(createClientCancellation, "createClientCancellation");
|
|
|
223
231
|
function notifyClientObserver(observer, args, label = "Client lifecycle") {
|
|
224
232
|
if (!observer) return;
|
|
225
233
|
const report = /* @__PURE__ */ __name((error) => {
|
|
226
|
-
const
|
|
227
|
-
if (typeof
|
|
234
|
+
const reportError2 = globalThis.reportError;
|
|
235
|
+
if (typeof reportError2 === "function") {
|
|
228
236
|
try {
|
|
229
|
-
|
|
237
|
+
reportError2.call(globalThis, error);
|
|
230
238
|
return;
|
|
231
239
|
} catch {
|
|
232
240
|
}
|
|
@@ -727,7 +735,8 @@ async function executeServerOperation(operation2, input, options, requestOptions
|
|
|
727
735
|
serverRequestOptions?.baseURL ?? options.baseURL,
|
|
728
736
|
request
|
|
729
737
|
);
|
|
730
|
-
const
|
|
738
|
+
const origin = resolveServerBaseURL(void 0, request);
|
|
739
|
+
const url = new URL(operation2.path, new URL(baseURL, origin));
|
|
731
740
|
appendQuery(url, input.query);
|
|
732
741
|
const headers = new Headers();
|
|
733
742
|
appendHeaders(
|
|
@@ -780,7 +789,9 @@ async function executeServerOperation(operation2, input, options, requestOptions
|
|
|
780
789
|
}
|
|
781
790
|
appendIntegrationClientDataHeader(headers, data);
|
|
782
791
|
const body = createOperationBody(operation2, input.body, headers);
|
|
783
|
-
const
|
|
792
|
+
const httpURL = resolveFarmAPIRequestURL(operation2.path, baseURL, origin);
|
|
793
|
+
appendQuery(httpURL, input.query);
|
|
794
|
+
const response = await (options.fetch ?? fetch)(httpURL.toString(), {
|
|
784
795
|
method: operation2.method,
|
|
785
796
|
headers,
|
|
786
797
|
body,
|
|
@@ -1214,7 +1225,13 @@ function recordFarmEventTrace(event) {
|
|
|
1214
1225
|
activeSpan.addEvent(event.type, toEventAttributes(event), event.timestamp);
|
|
1215
1226
|
}
|
|
1216
1227
|
const error = event.type === "request.error" ? void 0 : getEventError(event);
|
|
1217
|
-
if (error !== void 0)
|
|
1228
|
+
if (error !== void 0) {
|
|
1229
|
+
if (event.type === "render.error") {
|
|
1230
|
+
recordSpanException(activeSpan, error);
|
|
1231
|
+
} else {
|
|
1232
|
+
recordSpanError(activeSpan, error);
|
|
1233
|
+
}
|
|
1234
|
+
}
|
|
1218
1235
|
}
|
|
1219
1236
|
const completedTraceContext = recordCompletedEventSpan(event, activeContext);
|
|
1220
1237
|
return traceContext ?? completedTraceContext;
|
|
@@ -1311,12 +1328,26 @@ function getCompletedSpanDescriptor(event) {
|
|
|
1311
1328
|
}
|
|
1312
1329
|
}
|
|
1313
1330
|
__name(getCompletedSpanDescriptor, "getCompletedSpanDescriptor");
|
|
1331
|
+
function hashFarmCacheKey(value) {
|
|
1332
|
+
let hash = 2166136261;
|
|
1333
|
+
for (let index = 0; index < value.length; index++) {
|
|
1334
|
+
hash ^= value.charCodeAt(index);
|
|
1335
|
+
hash = Math.imul(hash, 16777619);
|
|
1336
|
+
}
|
|
1337
|
+
return (hash >>> 0).toString(16).padStart(8, "0");
|
|
1338
|
+
}
|
|
1339
|
+
__name(hashFarmCacheKey, "hashFarmCacheKey");
|
|
1314
1340
|
function toEventAttributes(event) {
|
|
1315
1341
|
const attributes = {};
|
|
1342
|
+
const redactKey = typeof event.type === "string" && event.type.startsWith("cache.");
|
|
1316
1343
|
for (const [key, value] of Object.entries(event)) {
|
|
1317
1344
|
if (key === "timestamp" || key === "level" || key === "error" || key === "traceId" || key === "spanId" || key === "traceSampled" || value === void 0) {
|
|
1318
1345
|
continue;
|
|
1319
1346
|
}
|
|
1347
|
+
if (redactKey && key === "key" && typeof value === "string") {
|
|
1348
|
+
attributes["farm.key_hash"] = hashFarmCacheKey(value);
|
|
1349
|
+
continue;
|
|
1350
|
+
}
|
|
1320
1351
|
if (typeof value === "string" || typeof value === "number" || typeof value === "boolean") {
|
|
1321
1352
|
attributes[`farm.${key}`] = value;
|
|
1322
1353
|
} else if (Array.isArray(value)) {
|
|
@@ -1336,9 +1367,14 @@ function getEventError(event) {
|
|
|
1336
1367
|
return "error" in event ? event.error : void 0;
|
|
1337
1368
|
}
|
|
1338
1369
|
__name(getEventError, "getEventError");
|
|
1339
|
-
function
|
|
1370
|
+
function recordSpanException(span, error) {
|
|
1340
1371
|
const normalized = error instanceof Error ? error : new Error(String(error));
|
|
1341
1372
|
span.recordException(normalized);
|
|
1373
|
+
return normalized;
|
|
1374
|
+
}
|
|
1375
|
+
__name(recordSpanException, "recordSpanException");
|
|
1376
|
+
function recordSpanError(span, error) {
|
|
1377
|
+
const normalized = recordSpanException(span, error);
|
|
1342
1378
|
span.setStatus({ code: import_api.SpanStatusCode.ERROR, message: normalized.message });
|
|
1343
1379
|
}
|
|
1344
1380
|
__name(recordSpanError, "recordSpanError");
|
|
@@ -1498,10 +1534,19 @@ function getFarmCacheInvalidationState() {
|
|
|
1498
1534
|
});
|
|
1499
1535
|
}
|
|
1500
1536
|
__name(getFarmCacheInvalidationState, "getFarmCacheInvalidationState");
|
|
1537
|
+
function warnFarmCacheListenerError(scope, error) {
|
|
1538
|
+
const detail = error instanceof Error ? error.stack ?? error.message : String(error);
|
|
1539
|
+
console.warn(`[farm:cache] ${scope} listener failed: ${detail}`);
|
|
1540
|
+
}
|
|
1541
|
+
__name(warnFarmCacheListenerError, "warnFarmCacheListenerError");
|
|
1501
1542
|
function notifyFarmCacheInvalidation(key) {
|
|
1502
1543
|
if (typeof key !== "string" || key.length === 0) return;
|
|
1503
1544
|
for (const listener of getFarmCacheInvalidationState().listeners) {
|
|
1504
|
-
|
|
1545
|
+
try {
|
|
1546
|
+
listener(key);
|
|
1547
|
+
} catch (error) {
|
|
1548
|
+
warnFarmCacheListenerError("invalidation", error);
|
|
1549
|
+
}
|
|
1505
1550
|
}
|
|
1506
1551
|
}
|
|
1507
1552
|
__name(notifyFarmCacheInvalidation, "notifyFarmCacheInvalidation");
|
|
@@ -1514,6 +1559,14 @@ function applyFarmCacheInvalidations(keys) {
|
|
|
1514
1559
|
}
|
|
1515
1560
|
}
|
|
1516
1561
|
__name(applyFarmCacheInvalidations, "applyFarmCacheInvalidations");
|
|
1562
|
+
function encodeFarmCacheInvalidations(keys) {
|
|
1563
|
+
const normalized = Array.from(
|
|
1564
|
+
new Set(keys.filter((key) => typeof key === "string" && key.length > 0))
|
|
1565
|
+
);
|
|
1566
|
+
if (normalized.length === 0) return null;
|
|
1567
|
+
return encodeURIComponent(JSON.stringify(normalized));
|
|
1568
|
+
}
|
|
1569
|
+
__name(encodeFarmCacheInvalidations, "encodeFarmCacheInvalidations");
|
|
1517
1570
|
function decodeFarmCacheInvalidations(value) {
|
|
1518
1571
|
if (!value) return [];
|
|
1519
1572
|
try {
|
|
@@ -2193,6 +2246,31 @@ function stableSerialize(value, seen = /* @__PURE__ */ new WeakSet()) {
|
|
|
2193
2246
|
__name(stableSerialize, "stableSerialize");
|
|
2194
2247
|
|
|
2195
2248
|
// src/client-cache.ts
|
|
2249
|
+
var invalidationTrackers = /* @__PURE__ */ new WeakMap();
|
|
2250
|
+
function trackFarmClientCacheInvalidations(cache) {
|
|
2251
|
+
let trackers = invalidationTrackers.get(cache);
|
|
2252
|
+
if (!trackers) {
|
|
2253
|
+
trackers = /* @__PURE__ */ new Set();
|
|
2254
|
+
invalidationTrackers.set(cache, trackers);
|
|
2255
|
+
}
|
|
2256
|
+
const keys = /* @__PURE__ */ new Set();
|
|
2257
|
+
trackers.add(keys);
|
|
2258
|
+
return {
|
|
2259
|
+
has(key) {
|
|
2260
|
+
const resolved = cache.resolveKey(key);
|
|
2261
|
+
for (const invalidated of keys) {
|
|
2262
|
+
if (cache.resolveKey(invalidated) === resolved) return true;
|
|
2263
|
+
}
|
|
2264
|
+
return false;
|
|
2265
|
+
},
|
|
2266
|
+
dispose() {
|
|
2267
|
+
if (!trackers.delete(keys)) return;
|
|
2268
|
+
keys.clear();
|
|
2269
|
+
if (trackers.size === 0) invalidationTrackers.delete(cache);
|
|
2270
|
+
}
|
|
2271
|
+
};
|
|
2272
|
+
}
|
|
2273
|
+
__name(trackFarmClientCacheInvalidations, "trackFarmClientCacheInvalidations");
|
|
2196
2274
|
var cacheFinalizer = typeof FinalizationRegistry === "function" ? new FinalizationRegistry((unsubscribe) => unsubscribe()) : void 0;
|
|
2197
2275
|
function subscribeWeakCache(reference) {
|
|
2198
2276
|
const unsubscribe = subscribeFarmCacheInvalidation((key) => {
|
|
@@ -2208,6 +2286,7 @@ function subscribeWeakCache(reference) {
|
|
|
2208
2286
|
return dispose;
|
|
2209
2287
|
}
|
|
2210
2288
|
__name(subscribeWeakCache, "subscribeWeakCache");
|
|
2289
|
+
var DEFAULT_GC_SWEEP_INTERVAL_MS = 3e4;
|
|
2211
2290
|
var _FarmClientDataCache = class _FarmClientDataCache {
|
|
2212
2291
|
constructor(options = {}) {
|
|
2213
2292
|
this.entries = /* @__PURE__ */ new Map();
|
|
@@ -2215,6 +2294,7 @@ var _FarmClientDataCache = class _FarmClientDataCache {
|
|
|
2215
2294
|
this.invalidatedAt = /* @__PURE__ */ new Map();
|
|
2216
2295
|
this.listeners = /* @__PURE__ */ new Map();
|
|
2217
2296
|
this.inflight = /* @__PURE__ */ new Map();
|
|
2297
|
+
this.gcSweepIntervalMs = options.gcSweepIntervalMs ?? DEFAULT_GC_SWEEP_INTERVAL_MS;
|
|
2218
2298
|
if (options.subscribeToInvalidation !== false) {
|
|
2219
2299
|
if (typeof WeakRef === "function") {
|
|
2220
2300
|
const reference = new WeakRef(this);
|
|
@@ -2231,6 +2311,10 @@ var _FarmClientDataCache = class _FarmClientDataCache {
|
|
|
2231
2311
|
get size() {
|
|
2232
2312
|
return this.entries.size;
|
|
2233
2313
|
}
|
|
2314
|
+
/** @internal Attach or detach the persistence engine's observation sink. */
|
|
2315
|
+
attachPersistence(sink) {
|
|
2316
|
+
this.persistence = sink;
|
|
2317
|
+
}
|
|
2234
2318
|
resolveKey(key) {
|
|
2235
2319
|
let resolved = key;
|
|
2236
2320
|
const seen = /* @__PURE__ */ new Set();
|
|
@@ -2246,6 +2330,7 @@ var _FarmClientDataCache = class _FarmClientDataCache {
|
|
|
2246
2330
|
if (!entry) return void 0;
|
|
2247
2331
|
if (entry.gcAt !== void 0 && now2 >= entry.gcAt) {
|
|
2248
2332
|
this.entries.delete(resolved);
|
|
2333
|
+
this.persistence?.onDelete(resolved);
|
|
2249
2334
|
this.emit(resolved);
|
|
2250
2335
|
return void 0;
|
|
2251
2336
|
}
|
|
@@ -2259,6 +2344,8 @@ var _FarmClientDataCache = class _FarmClientDataCache {
|
|
|
2259
2344
|
this.invalidatedAt.delete(resolved);
|
|
2260
2345
|
}
|
|
2261
2346
|
this.entries.set(resolved, nextEntry);
|
|
2347
|
+
if (nextEntry.gcAt !== void 0) this.scheduleGcSweep();
|
|
2348
|
+
this.persistence?.onSet(resolved, nextEntry);
|
|
2262
2349
|
this.emit(resolved);
|
|
2263
2350
|
return this;
|
|
2264
2351
|
}
|
|
@@ -2266,6 +2353,7 @@ var _FarmClientDataCache = class _FarmClientDataCache {
|
|
|
2266
2353
|
const resolved = this.resolveKey(key);
|
|
2267
2354
|
const deleted = this.entries.delete(resolved);
|
|
2268
2355
|
this.inflight.delete(resolved);
|
|
2356
|
+
if (deleted) this.persistence?.onDelete(resolved);
|
|
2269
2357
|
this.emit(resolved);
|
|
2270
2358
|
return deleted;
|
|
2271
2359
|
}
|
|
@@ -2275,11 +2363,16 @@ var _FarmClientDataCache = class _FarmClientDataCache {
|
|
|
2275
2363
|
this.aliases.clear();
|
|
2276
2364
|
this.invalidatedAt.clear();
|
|
2277
2365
|
this.inflight.clear();
|
|
2366
|
+
this.persistence?.onClear();
|
|
2278
2367
|
for (const key of keys) this.emit(key);
|
|
2279
2368
|
}
|
|
2280
2369
|
dispose() {
|
|
2281
2370
|
this.unsubscribeInvalidation?.();
|
|
2282
2371
|
this.unsubscribeInvalidation = void 0;
|
|
2372
|
+
if (this.gcTimer !== void 0) {
|
|
2373
|
+
clearTimeout(this.gcTimer);
|
|
2374
|
+
this.gcTimer = void 0;
|
|
2375
|
+
}
|
|
2283
2376
|
this.clear();
|
|
2284
2377
|
}
|
|
2285
2378
|
isStale(key, now2 = Date.now()) {
|
|
@@ -2288,6 +2381,7 @@ var _FarmClientDataCache = class _FarmClientDataCache {
|
|
|
2288
2381
|
}
|
|
2289
2382
|
invalidate(key, now2 = Date.now()) {
|
|
2290
2383
|
const resolved = this.resolveKey(key);
|
|
2384
|
+
for (const keys of invalidationTrackers.get(this) ?? []) keys.add(resolved);
|
|
2291
2385
|
this.invalidatedAt.set(resolved, now2);
|
|
2292
2386
|
const entry = this.entries.get(resolved);
|
|
2293
2387
|
if (entry) {
|
|
@@ -2307,8 +2401,9 @@ var _FarmClientDataCache = class _FarmClientDataCache {
|
|
|
2307
2401
|
const resolvedInvalidatedAt = this.invalidatedAt.get(resolved);
|
|
2308
2402
|
if (aliasEntry && !this.entries.has(resolved)) {
|
|
2309
2403
|
this.entries.set(resolved, aliasEntry);
|
|
2404
|
+
this.persistence?.onSet(resolved, aliasEntry);
|
|
2310
2405
|
}
|
|
2311
|
-
this.entries.delete(alias);
|
|
2406
|
+
if (this.entries.delete(alias)) this.persistence?.onDelete(alias);
|
|
2312
2407
|
this.invalidatedAt.delete(alias);
|
|
2313
2408
|
const invalidatedAt = [aliasInvalidatedAt, resolvedInvalidatedAt].reduce(
|
|
2314
2409
|
(latest, value) => value === void 0 ? latest : latest === void 0 ? value : Math.max(latest, value),
|
|
@@ -2348,7 +2443,9 @@ var _FarmClientDataCache = class _FarmClientDataCache {
|
|
|
2348
2443
|
listeners2.add(listener);
|
|
2349
2444
|
return () => {
|
|
2350
2445
|
listeners2.delete(listener);
|
|
2351
|
-
if (listeners2.size === 0
|
|
2446
|
+
if (listeners2.size === 0 && this.listeners.get(key) === listeners2) {
|
|
2447
|
+
this.listeners.delete(key);
|
|
2448
|
+
}
|
|
2352
2449
|
};
|
|
2353
2450
|
}
|
|
2354
2451
|
getInflight(key) {
|
|
@@ -2360,6 +2457,30 @@ var _FarmClientDataCache = class _FarmClientDataCache {
|
|
|
2360
2457
|
deleteInflight(key) {
|
|
2361
2458
|
this.inflight.delete(this.resolveKey(key));
|
|
2362
2459
|
}
|
|
2460
|
+
scheduleGcSweep() {
|
|
2461
|
+
if (this.gcSweepIntervalMs === false || this.gcTimer !== void 0) return;
|
|
2462
|
+
const timer = setTimeout(() => {
|
|
2463
|
+
this.gcTimer = void 0;
|
|
2464
|
+
this.sweepExpiredEntries();
|
|
2465
|
+
}, this.gcSweepIntervalMs);
|
|
2466
|
+
timer.unref?.();
|
|
2467
|
+
this.gcTimer = timer;
|
|
2468
|
+
}
|
|
2469
|
+
sweepExpiredEntries(now2 = Date.now()) {
|
|
2470
|
+
const watched = /* @__PURE__ */ new Set();
|
|
2471
|
+
for (const key of this.listeners.keys()) watched.add(this.resolveKey(key));
|
|
2472
|
+
let remaining = false;
|
|
2473
|
+
for (const [key, entry] of this.entries) {
|
|
2474
|
+
if (entry.gcAt === void 0) continue;
|
|
2475
|
+
if (now2 < entry.gcAt || entry.fetching || this.inflight.has(key) || watched.has(key)) {
|
|
2476
|
+
remaining = true;
|
|
2477
|
+
continue;
|
|
2478
|
+
}
|
|
2479
|
+
this.entries.delete(key);
|
|
2480
|
+
this.persistence?.onDelete(key);
|
|
2481
|
+
}
|
|
2482
|
+
if (remaining) this.scheduleGcSweep();
|
|
2483
|
+
}
|
|
2363
2484
|
emit(key, event) {
|
|
2364
2485
|
this.notifyListeners(key, event);
|
|
2365
2486
|
for (const [alias, target] of this.aliases) {
|
|
@@ -2764,6 +2885,7 @@ function readJSONStream(response) {
|
|
|
2764
2885
|
const decoder = new TextDecoder();
|
|
2765
2886
|
let buffer = "";
|
|
2766
2887
|
let completed = false;
|
|
2888
|
+
let cancelled = false;
|
|
2767
2889
|
let claimed = false;
|
|
2768
2890
|
let released = false;
|
|
2769
2891
|
const releaseReader = /* @__PURE__ */ __name(() => {
|
|
@@ -2783,39 +2905,54 @@ function readJSONStream(response) {
|
|
|
2783
2905
|
throw error;
|
|
2784
2906
|
}
|
|
2785
2907
|
}, "parseLine");
|
|
2786
|
-
const
|
|
2787
|
-
|
|
2788
|
-
|
|
2789
|
-
|
|
2790
|
-
|
|
2791
|
-
|
|
2792
|
-
|
|
2793
|
-
|
|
2794
|
-
|
|
2795
|
-
|
|
2796
|
-
|
|
2797
|
-
|
|
2798
|
-
|
|
2799
|
-
|
|
2800
|
-
releaseReader();
|
|
2801
|
-
return { done: true, value: void 0 };
|
|
2802
|
-
}
|
|
2803
|
-
return { done: false, value: await parseLine(line) };
|
|
2804
|
-
}
|
|
2805
|
-
let chunk;
|
|
2806
|
-
try {
|
|
2807
|
-
chunk = await reader.read();
|
|
2808
|
-
} catch (error) {
|
|
2809
|
-
completed = true;
|
|
2810
|
-
buffer = "";
|
|
2908
|
+
const readNext = /* @__PURE__ */ __name(async () => {
|
|
2909
|
+
while (true) {
|
|
2910
|
+
if (cancelled) return { done: true, value: void 0 };
|
|
2911
|
+
const lineEnd = buffer.indexOf("\n");
|
|
2912
|
+
if (lineEnd >= 0) {
|
|
2913
|
+
const line = buffer.slice(0, lineEnd).trim();
|
|
2914
|
+
buffer = buffer.slice(lineEnd + 1);
|
|
2915
|
+
if (!line) continue;
|
|
2916
|
+
return { done: false, value: await parseLine(line) };
|
|
2917
|
+
}
|
|
2918
|
+
if (completed) {
|
|
2919
|
+
const line = buffer.trim();
|
|
2920
|
+
buffer = "";
|
|
2921
|
+
if (!line) {
|
|
2811
2922
|
releaseReader();
|
|
2812
|
-
|
|
2923
|
+
return { done: true, value: void 0 };
|
|
2813
2924
|
}
|
|
2814
|
-
|
|
2815
|
-
buffer += decoder.decode(chunk.value, { stream: !chunk.done });
|
|
2925
|
+
return { done: false, value: await parseLine(line) };
|
|
2816
2926
|
}
|
|
2927
|
+
let chunk;
|
|
2928
|
+
try {
|
|
2929
|
+
chunk = await reader.read();
|
|
2930
|
+
} catch (error) {
|
|
2931
|
+
if (cancelled) return { done: true, value: void 0 };
|
|
2932
|
+
completed = true;
|
|
2933
|
+
buffer = "";
|
|
2934
|
+
releaseReader();
|
|
2935
|
+
throw error;
|
|
2936
|
+
}
|
|
2937
|
+
if (cancelled) return { done: true, value: void 0 };
|
|
2938
|
+
completed = chunk.done;
|
|
2939
|
+
buffer += decoder.decode(chunk.value, { stream: !chunk.done });
|
|
2940
|
+
}
|
|
2941
|
+
}, "readNext");
|
|
2942
|
+
let readQueue = Promise.resolve();
|
|
2943
|
+
const iterator = {
|
|
2944
|
+
next() {
|
|
2945
|
+
const result = readQueue.then(readNext);
|
|
2946
|
+
readQueue = result.then(
|
|
2947
|
+
() => {
|
|
2948
|
+
},
|
|
2949
|
+
() => {
|
|
2950
|
+
}
|
|
2951
|
+
);
|
|
2952
|
+
return result;
|
|
2817
2953
|
},
|
|
2818
2954
|
async return() {
|
|
2955
|
+
cancelled = true;
|
|
2819
2956
|
completed = true;
|
|
2820
2957
|
buffer = "";
|
|
2821
2958
|
if (!released) {
|
|
@@ -2831,6 +2968,7 @@ function readJSONStream(response) {
|
|
|
2831
2968
|
return {
|
|
2832
2969
|
response,
|
|
2833
2970
|
async cancel(reason) {
|
|
2971
|
+
cancelled = true;
|
|
2834
2972
|
completed = true;
|
|
2835
2973
|
buffer = "";
|
|
2836
2974
|
if (!released) {
|
|
@@ -2980,69 +3118,6 @@ function createAPIClientRuntime(options = {}, transport) {
|
|
|
2980
3118
|
let scopedRequestState;
|
|
2981
3119
|
const routeMeta = transport?.routeMeta ?? /* @__PURE__ */ new WeakMap();
|
|
2982
3120
|
let requestCounter = 0;
|
|
2983
|
-
const applyOptimisticLayer = /* @__PURE__ */ __name((entry, layer) => {
|
|
2984
|
-
let data = entry?.data;
|
|
2985
|
-
for (const updater of layer.updaters) data = updater(data);
|
|
2986
|
-
return {
|
|
2987
|
-
data,
|
|
2988
|
-
updatedAt: layer.updatedAt,
|
|
2989
|
-
staleAt: entry?.staleAt ?? layer.staleAt,
|
|
2990
|
-
gcAt: entry?.gcAt ?? layer.gcAt,
|
|
2991
|
-
invalidatedAt: entry?.invalidatedAt
|
|
2992
|
-
};
|
|
2993
|
-
}, "applyOptimisticLayer");
|
|
2994
|
-
const storeOptimisticEntry = /* @__PURE__ */ __name((cacheState, key, stack, entry) => {
|
|
2995
|
-
if (!entry) {
|
|
2996
|
-
cacheState.delete(key);
|
|
2997
|
-
stack.renderedEntry = void 0;
|
|
2998
|
-
return;
|
|
2999
|
-
}
|
|
3000
|
-
cacheState.set(key, entry);
|
|
3001
|
-
if (stack.invalidatedAt !== void 0) {
|
|
3002
|
-
cacheState.invalidate(key, stack.invalidatedAt);
|
|
3003
|
-
}
|
|
3004
|
-
stack.renderedEntry = cacheState.get(key);
|
|
3005
|
-
}, "storeOptimisticEntry");
|
|
3006
|
-
const reconcileOptimisticInvalidation = /* @__PURE__ */ __name((cacheState, key, stack) => {
|
|
3007
|
-
const current = cacheState.get(key);
|
|
3008
|
-
const rendered = stack.renderedEntry;
|
|
3009
|
-
if (current === rendered) return true;
|
|
3010
|
-
if (!current || !rendered || current.data !== rendered.data || current.updatedAt !== rendered.updatedAt || current.gcAt !== rendered.gcAt || current.status !== rendered.status || current.error !== rendered.error || current.fetching !== rendered.fetching || current.staleAt !== 0 || current.invalidatedAt === void 0) {
|
|
3011
|
-
return false;
|
|
3012
|
-
}
|
|
3013
|
-
stack.invalidatedAt = current.invalidatedAt;
|
|
3014
|
-
stack.renderedEntry = current;
|
|
3015
|
-
return true;
|
|
3016
|
-
}, "reconcileOptimisticInvalidation");
|
|
3017
|
-
const renderOptimisticStack = /* @__PURE__ */ __name((cacheState, key, stack) => {
|
|
3018
|
-
let entry = stack.entry ? { ...stack.entry } : void 0;
|
|
3019
|
-
for (const layer of stack.layers) entry = applyOptimisticLayer(entry, layer);
|
|
3020
|
-
storeOptimisticEntry(cacheState, key, stack, entry);
|
|
3021
|
-
}, "renderOptimisticStack");
|
|
3022
|
-
const settleOptimisticUpdates = /* @__PURE__ */ __name((cacheState, optimisticState, snapshots, outcome) => {
|
|
3023
|
-
const settledKeys = [];
|
|
3024
|
-
for (const snapshot of snapshots) {
|
|
3025
|
-
const stack = optimisticState.get(snapshot.key);
|
|
3026
|
-
if (stack !== snapshot.stack) continue;
|
|
3027
|
-
if (!reconcileOptimisticInvalidation(cacheState, snapshot.key, stack)) {
|
|
3028
|
-
optimisticState.delete(snapshot.key);
|
|
3029
|
-
continue;
|
|
3030
|
-
}
|
|
3031
|
-
if (outcome === "rollback") {
|
|
3032
|
-
stack.layers = stack.layers.filter((layer) => layer !== snapshot.layer);
|
|
3033
|
-
} else {
|
|
3034
|
-
snapshot.layer.committed = true;
|
|
3035
|
-
if (outcome === "invalidate") stack.invalidatedAt = Date.now();
|
|
3036
|
-
}
|
|
3037
|
-
while (stack.layers[0]?.committed) {
|
|
3038
|
-
stack.entry = applyOptimisticLayer(stack.entry, stack.layers.shift());
|
|
3039
|
-
}
|
|
3040
|
-
renderOptimisticStack(cacheState, snapshot.key, stack);
|
|
3041
|
-
if (stack.layers.length === 0) optimisticState.delete(snapshot.key);
|
|
3042
|
-
settledKeys.push(snapshot.key);
|
|
3043
|
-
}
|
|
3044
|
-
return settledKeys;
|
|
3045
|
-
}, "settleOptimisticUpdates");
|
|
3046
3121
|
const fetchClient = /* @__PURE__ */ __name(async (path, requestOptions, defaultHeaders, cancellation) => {
|
|
3047
3122
|
const url = resolveFarmAPIRequestURL(path, baseURL);
|
|
3048
3123
|
const method = String(requestOptions.method || "GET").toUpperCase();
|
|
@@ -3275,6 +3350,9 @@ function createAPIClientRuntime(options = {}, transport) {
|
|
|
3275
3350
|
const executeNetwork = /* @__PURE__ */ __name(async (opts) => {
|
|
3276
3351
|
const release = cancellation.hold();
|
|
3277
3352
|
let unsubscribeInvalidation;
|
|
3353
|
+
let readOwners;
|
|
3354
|
+
let readOwner;
|
|
3355
|
+
const resolvedCacheKey = cacheState.resolveKey(cacheKey);
|
|
3278
3356
|
try {
|
|
3279
3357
|
const dedupeMs = cacheOptions?.dedupeMs ?? 0;
|
|
3280
3358
|
const inflight = inflightState.get(cacheKey);
|
|
@@ -3298,6 +3376,9 @@ function createAPIClientRuntime(options = {}, transport) {
|
|
|
3298
3376
|
}
|
|
3299
3377
|
let invalidatedDuringRequest = false;
|
|
3300
3378
|
if (isCacheEnabled) {
|
|
3379
|
+
readOwners = getCacheReadOwners(cacheState);
|
|
3380
|
+
readOwner = {};
|
|
3381
|
+
readOwners.set(resolvedCacheKey, readOwner);
|
|
3301
3382
|
unsubscribeInvalidation = cacheState.subscribe(cacheKey, (event) => {
|
|
3302
3383
|
if (event === "invalidate") invalidatedDuringRequest = true;
|
|
3303
3384
|
});
|
|
@@ -3405,15 +3486,27 @@ function createAPIClientRuntime(options = {}, transport) {
|
|
|
3405
3486
|
inflightState.set(cacheKey, inflightEntry);
|
|
3406
3487
|
try {
|
|
3407
3488
|
const result2 = await promise;
|
|
3408
|
-
if (inflightState.get(cacheKey) === inflightEntry && !invalidatedDuringRequest && !result2.error && isCacheEnabled && !isFarmAPIStream(result2.data)) {
|
|
3489
|
+
if (inflightState.get(cacheKey) === inflightEntry && readOwners?.get(resolvedCacheKey) === readOwner && !invalidatedDuringRequest && !result2.error && isCacheEnabled && !isFarmAPIStream(result2.data)) {
|
|
3409
3490
|
const updatedAt = Date.now();
|
|
3410
|
-
|
|
3491
|
+
const cached = {
|
|
3411
3492
|
data: result2.data,
|
|
3412
3493
|
updatedAt,
|
|
3413
3494
|
staleAt: updatedAt + staleTime,
|
|
3414
3495
|
gcAt: getGcAt(updatedAt, cacheOptions?.gcTime),
|
|
3415
|
-
invalidatedAt: void 0
|
|
3416
|
-
|
|
3496
|
+
invalidatedAt: void 0,
|
|
3497
|
+
persist: cacheOptions?.persist === true ? true : void 0,
|
|
3498
|
+
[API_CACHE_REFETCH]: createCacheRefetch(
|
|
3499
|
+
request,
|
|
3500
|
+
path,
|
|
3501
|
+
method,
|
|
3502
|
+
input,
|
|
3503
|
+
cacheKey,
|
|
3504
|
+
cacheOptions,
|
|
3505
|
+
clientOptions,
|
|
3506
|
+
options.onError
|
|
3507
|
+
)
|
|
3508
|
+
};
|
|
3509
|
+
cacheState.set(cacheKey, cached);
|
|
3417
3510
|
}
|
|
3418
3511
|
if (result2.error) {
|
|
3419
3512
|
emitStatus("error", { error: result2.error, isBackground: opts?.isBackground });
|
|
@@ -3441,6 +3534,9 @@ function createAPIClientRuntime(options = {}, transport) {
|
|
|
3441
3534
|
}
|
|
3442
3535
|
}
|
|
3443
3536
|
} finally {
|
|
3537
|
+
if (readOwner && readOwners?.get(resolvedCacheKey) === readOwner) {
|
|
3538
|
+
readOwners.delete(resolvedCacheKey);
|
|
3539
|
+
}
|
|
3444
3540
|
unsubscribeInvalidation?.();
|
|
3445
3541
|
release();
|
|
3446
3542
|
}
|
|
@@ -3451,6 +3547,7 @@ function createAPIClientRuntime(options = {}, transport) {
|
|
|
3451
3547
|
targets: clientOptions.invalidate.targets,
|
|
3452
3548
|
refetch: clientOptions.invalidate.refetch ?? false
|
|
3453
3549
|
};
|
|
3550
|
+
const refetches = /* @__PURE__ */ new Set();
|
|
3454
3551
|
for (const target of invalidateOptions.targets) {
|
|
3455
3552
|
const targetKey = resolveTargetKey(
|
|
3456
3553
|
routeMeta,
|
|
@@ -3462,20 +3559,22 @@ function createAPIClientRuntime(options = {}, transport) {
|
|
|
3462
3559
|
);
|
|
3463
3560
|
if (!targetKey) continue;
|
|
3464
3561
|
const existing = cacheState.get(targetKey);
|
|
3562
|
+
const invalidatedAt = Date.now();
|
|
3563
|
+
cacheState.invalidate(targetKey, invalidatedAt);
|
|
3465
3564
|
if (existing) {
|
|
3466
|
-
const invalidatedAt = Date.now();
|
|
3467
3565
|
const stack = optimisticState.get(targetKey);
|
|
3468
|
-
cacheState.invalidate(targetKey, invalidatedAt);
|
|
3469
3566
|
if (stack?.renderedEntry === existing) {
|
|
3470
3567
|
stack.invalidatedAt = invalidatedAt;
|
|
3471
3568
|
stack.renderedEntry = cacheState.get(targetKey);
|
|
3472
3569
|
}
|
|
3473
3570
|
}
|
|
3474
3571
|
emitStatus("invalidated", { key: targetKey });
|
|
3475
|
-
|
|
3476
|
-
|
|
3572
|
+
const refetch = existing?.[API_CACHE_REFETCH];
|
|
3573
|
+
if (invalidateOptions.refetch && refetch) {
|
|
3574
|
+
refetches.add(refetch);
|
|
3477
3575
|
}
|
|
3478
3576
|
}
|
|
3577
|
+
for (const refetch of refetches) refetch();
|
|
3479
3578
|
}, "invalidateTargets");
|
|
3480
3579
|
const optimisticSnapshots = requestContextError ? [] : applyOptimisticUpdates();
|
|
3481
3580
|
if (isCacheEnabled && !requestContextError && !cancellation.signal?.aborted) {
|
|
@@ -3709,7 +3808,31 @@ function createServerAPIClient(endpoints, options = {}) {
|
|
|
3709
3808
|
return endpoints;
|
|
3710
3809
|
}
|
|
3711
3810
|
__name(createServerAPIClient, "createServerAPIClient");
|
|
3811
|
+
var API_CACHE_REFETCH = /* @__PURE__ */ Symbol.for("farm.api.cache-refetch");
|
|
3812
|
+
function createCacheRefetch(request, path, method, input, key, cache, options, onError) {
|
|
3813
|
+
const readOptions = {
|
|
3814
|
+
cache: { ...cache, key, policy: "network-only", dedupeMs: 0 },
|
|
3815
|
+
retry: options?.retry,
|
|
3816
|
+
timeoutMs: options?.timeoutMs
|
|
3817
|
+
};
|
|
3818
|
+
return () => {
|
|
3819
|
+
void request(path, method, input, readOptions).catch((error) => {
|
|
3820
|
+
notifyClientObserver(onError, [normalizeError(error)]);
|
|
3821
|
+
});
|
|
3822
|
+
};
|
|
3823
|
+
}
|
|
3824
|
+
__name(createCacheRefetch, "createCacheRefetch");
|
|
3712
3825
|
var optimisticStates = /* @__PURE__ */ new WeakMap();
|
|
3826
|
+
var cacheReadOwners = /* @__PURE__ */ new WeakMap();
|
|
3827
|
+
function getCacheReadOwners(cache) {
|
|
3828
|
+
let owners = cacheReadOwners.get(cache);
|
|
3829
|
+
if (!owners) {
|
|
3830
|
+
owners = /* @__PURE__ */ new Map();
|
|
3831
|
+
cacheReadOwners.set(cache, owners);
|
|
3832
|
+
}
|
|
3833
|
+
return owners;
|
|
3834
|
+
}
|
|
3835
|
+
__name(getCacheReadOwners, "getCacheReadOwners");
|
|
3713
3836
|
function getOptimisticState(cache) {
|
|
3714
3837
|
let state = optimisticStates.get(cache);
|
|
3715
3838
|
if (!state) {
|
|
@@ -3719,6 +3842,151 @@ function getOptimisticState(cache) {
|
|
|
3719
3842
|
return state;
|
|
3720
3843
|
}
|
|
3721
3844
|
__name(getOptimisticState, "getOptimisticState");
|
|
3845
|
+
function applyOptimisticLayer(entry, layer) {
|
|
3846
|
+
let data = entry?.data;
|
|
3847
|
+
for (const updater of layer.updaters) data = updater(data);
|
|
3848
|
+
return {
|
|
3849
|
+
data,
|
|
3850
|
+
updatedAt: layer.updatedAt,
|
|
3851
|
+
staleAt: entry?.staleAt ?? layer.staleAt,
|
|
3852
|
+
gcAt: entry?.gcAt ?? layer.gcAt,
|
|
3853
|
+
invalidatedAt: entry?.invalidatedAt,
|
|
3854
|
+
[API_CACHE_REFETCH]: entry?.[API_CACHE_REFETCH]
|
|
3855
|
+
};
|
|
3856
|
+
}
|
|
3857
|
+
__name(applyOptimisticLayer, "applyOptimisticLayer");
|
|
3858
|
+
function storeOptimisticEntry(cacheState, key, stack, entry) {
|
|
3859
|
+
if (!entry) {
|
|
3860
|
+
cacheState.delete(key);
|
|
3861
|
+
stack.renderedEntry = void 0;
|
|
3862
|
+
return;
|
|
3863
|
+
}
|
|
3864
|
+
cacheState.set(key, entry);
|
|
3865
|
+
if (stack.invalidatedAt !== void 0) {
|
|
3866
|
+
cacheState.invalidate(key, stack.invalidatedAt);
|
|
3867
|
+
}
|
|
3868
|
+
stack.renderedEntry = cacheState.get(key);
|
|
3869
|
+
}
|
|
3870
|
+
__name(storeOptimisticEntry, "storeOptimisticEntry");
|
|
3871
|
+
function reconcileOptimisticInvalidation(cacheState, key, stack) {
|
|
3872
|
+
const current = cacheState.get(key);
|
|
3873
|
+
const rendered = stack.renderedEntry;
|
|
3874
|
+
if (current === rendered) return true;
|
|
3875
|
+
if (!current || !rendered || current.data !== rendered.data || current.updatedAt !== rendered.updatedAt || current.gcAt !== rendered.gcAt || current.status !== rendered.status || current.error !== rendered.error || current.fetching !== rendered.fetching || current.staleAt !== 0 || current.invalidatedAt === void 0) {
|
|
3876
|
+
return false;
|
|
3877
|
+
}
|
|
3878
|
+
stack.invalidatedAt = current.invalidatedAt;
|
|
3879
|
+
stack.renderedEntry = current;
|
|
3880
|
+
return true;
|
|
3881
|
+
}
|
|
3882
|
+
__name(reconcileOptimisticInvalidation, "reconcileOptimisticInvalidation");
|
|
3883
|
+
function renderOptimisticStack(cacheState, key, stack) {
|
|
3884
|
+
let entry = stack.entry ? { ...stack.entry } : void 0;
|
|
3885
|
+
for (const layer of stack.layers) entry = applyOptimisticLayer(entry, layer);
|
|
3886
|
+
storeOptimisticEntry(cacheState, key, stack, entry);
|
|
3887
|
+
}
|
|
3888
|
+
__name(renderOptimisticStack, "renderOptimisticStack");
|
|
3889
|
+
function settleOptimisticUpdates(cacheState, optimisticState, snapshots, outcome) {
|
|
3890
|
+
const settledKeys = [];
|
|
3891
|
+
for (const snapshot of snapshots) {
|
|
3892
|
+
const stack = optimisticState.get(snapshot.key);
|
|
3893
|
+
if (stack !== snapshot.stack) continue;
|
|
3894
|
+
if (!reconcileOptimisticInvalidation(cacheState, snapshot.key, stack)) {
|
|
3895
|
+
optimisticState.delete(snapshot.key);
|
|
3896
|
+
continue;
|
|
3897
|
+
}
|
|
3898
|
+
if (outcome === "rollback") {
|
|
3899
|
+
stack.layers = stack.layers.filter((layer) => layer !== snapshot.layer);
|
|
3900
|
+
} else {
|
|
3901
|
+
snapshot.layer.committed = true;
|
|
3902
|
+
if (outcome === "invalidate") stack.invalidatedAt = Date.now();
|
|
3903
|
+
}
|
|
3904
|
+
while (stack.layers[0]?.committed) {
|
|
3905
|
+
stack.entry = applyOptimisticLayer(stack.entry, stack.layers.shift());
|
|
3906
|
+
}
|
|
3907
|
+
renderOptimisticStack(cacheState, snapshot.key, stack);
|
|
3908
|
+
if (stack.layers.length === 0) optimisticState.delete(snapshot.key);
|
|
3909
|
+
settledKeys.push(snapshot.key);
|
|
3910
|
+
}
|
|
3911
|
+
return settledKeys;
|
|
3912
|
+
}
|
|
3913
|
+
__name(settleOptimisticUpdates, "settleOptimisticUpdates");
|
|
3914
|
+
function applyServerFnOptimisticUpdates(updates, now2 = Date.now()) {
|
|
3915
|
+
const cacheState = getFarmClientDataCache();
|
|
3916
|
+
const optimisticState = getOptimisticState(cacheState);
|
|
3917
|
+
const snapshots = /* @__PURE__ */ new Map();
|
|
3918
|
+
for (const update of updates) {
|
|
3919
|
+
if (update.length !== 2) continue;
|
|
3920
|
+
const [target, updater] = update;
|
|
3921
|
+
if (typeof updater !== "function") continue;
|
|
3922
|
+
const targetKey = typeof target === "string" || Array.isArray(target) ? normalizeFarmClientCacheKey(target) : null;
|
|
3923
|
+
if (!targetKey) continue;
|
|
3924
|
+
const targetEntry = getValidCacheEntry(cacheState, targetKey, now2);
|
|
3925
|
+
const currentEntry = cacheState.get(targetKey);
|
|
3926
|
+
let stack = optimisticState.get(targetKey);
|
|
3927
|
+
if (stack && !reconcileOptimisticInvalidation(cacheState, targetKey, stack)) {
|
|
3928
|
+
stack = void 0;
|
|
3929
|
+
}
|
|
3930
|
+
if (!stack) {
|
|
3931
|
+
stack = {
|
|
3932
|
+
entry: targetEntry ? { ...targetEntry } : void 0,
|
|
3933
|
+
layers: [],
|
|
3934
|
+
renderedEntry: currentEntry
|
|
3935
|
+
};
|
|
3936
|
+
optimisticState.set(targetKey, stack);
|
|
3937
|
+
}
|
|
3938
|
+
let snapshot = snapshots.get(targetKey);
|
|
3939
|
+
if (!snapshot) {
|
|
3940
|
+
const previousEntry = stack.layers.length === 0 ? stack.entry : stack.renderedEntry;
|
|
3941
|
+
const layer = {
|
|
3942
|
+
updaters: [],
|
|
3943
|
+
updatedAt: now2,
|
|
3944
|
+
// A server function has no cache policy of its own; preserve the
|
|
3945
|
+
// target read's freshness metadata when it exists.
|
|
3946
|
+
staleAt: targetEntry?.staleAt ?? now2,
|
|
3947
|
+
gcAt: targetEntry?.gcAt
|
|
3948
|
+
};
|
|
3949
|
+
stack.layers.push(layer);
|
|
3950
|
+
snapshot = { key: targetKey, stack, layer };
|
|
3951
|
+
snapshots.set(targetKey, snapshot);
|
|
3952
|
+
snapshot.layer.updaters.push(updater);
|
|
3953
|
+
const nextEntry2 = applyOptimisticLayer(previousEntry, {
|
|
3954
|
+
...snapshot.layer,
|
|
3955
|
+
updaters: [updater]
|
|
3956
|
+
});
|
|
3957
|
+
storeOptimisticEntry(cacheState, targetKey, stack, nextEntry2);
|
|
3958
|
+
continue;
|
|
3959
|
+
}
|
|
3960
|
+
snapshot.layer.updaters.push(updater);
|
|
3961
|
+
const nextEntry = applyOptimisticLayer(stack.renderedEntry, {
|
|
3962
|
+
...snapshot.layer,
|
|
3963
|
+
updaters: [updater]
|
|
3964
|
+
});
|
|
3965
|
+
storeOptimisticEntry(cacheState, targetKey, stack, nextEntry);
|
|
3966
|
+
}
|
|
3967
|
+
return Array.from(snapshots.values());
|
|
3968
|
+
}
|
|
3969
|
+
__name(applyServerFnOptimisticUpdates, "applyServerFnOptimisticUpdates");
|
|
3970
|
+
function settleServerFnOptimisticUpdates(snapshots, outcome) {
|
|
3971
|
+
if (snapshots.length === 0) return;
|
|
3972
|
+
const cacheState = getFarmClientDataCache();
|
|
3973
|
+
settleOptimisticUpdates(cacheState, getOptimisticState(cacheState), snapshots, outcome);
|
|
3974
|
+
}
|
|
3975
|
+
__name(settleServerFnOptimisticUpdates, "settleServerFnOptimisticUpdates");
|
|
3976
|
+
function resolveServerFnInvalidateTargets(invalidate) {
|
|
3977
|
+
const targets = Array.isArray(invalidate) ? invalidate : invalidate.targets;
|
|
3978
|
+
const keys = [];
|
|
3979
|
+
for (const target of targets) {
|
|
3980
|
+
if (typeof target === "string" || Array.isArray(target)) {
|
|
3981
|
+
if (Array.isArray(target) && typeof target[0] === "function") continue;
|
|
3982
|
+
keys.push(normalizeFarmClientCacheKey(target));
|
|
3983
|
+
} else if (target && typeof target === "object" && "key" in target) {
|
|
3984
|
+
keys.push(normalizeFarmClientCacheKey(target.key));
|
|
3985
|
+
}
|
|
3986
|
+
}
|
|
3987
|
+
return keys;
|
|
3988
|
+
}
|
|
3989
|
+
__name(resolveServerFnInvalidateTargets, "resolveServerFnInvalidateTargets");
|
|
3722
3990
|
function buildCacheKey(method, path, input, baseURL, defaultHeaders) {
|
|
3723
3991
|
const keyInput = input && typeof input === "object" ? {
|
|
3724
3992
|
query: input.query,
|
|
@@ -3897,65 +4165,176 @@ __name(readEndpointErrorEnvelope, "readEndpointErrorEnvelope");
|
|
|
3897
4165
|
|
|
3898
4166
|
// src/mutation-client.ts
|
|
3899
4167
|
var import_react = require("react");
|
|
4168
|
+
|
|
4169
|
+
// src/client-network-status.ts
|
|
4170
|
+
function isNavigatorOnline() {
|
|
4171
|
+
if (typeof navigator === "undefined" || typeof navigator.onLine !== "boolean") return true;
|
|
4172
|
+
return navigator.onLine;
|
|
4173
|
+
}
|
|
4174
|
+
__name(isNavigatorOnline, "isNavigatorOnline");
|
|
4175
|
+
function subscribeOnline(listener) {
|
|
4176
|
+
if (typeof window === "undefined") return () => {
|
|
4177
|
+
};
|
|
4178
|
+
window.addEventListener("online", listener);
|
|
4179
|
+
return () => window.removeEventListener("online", listener);
|
|
4180
|
+
}
|
|
4181
|
+
__name(subscribeOnline, "subscribeOnline");
|
|
4182
|
+
|
|
4183
|
+
// src/mutation-retry.ts
|
|
4184
|
+
async function invokeMutationWithRetry(invoke, retry, shouldContinue) {
|
|
4185
|
+
const maxRetries = Math.max(0, retry?.count ?? 0);
|
|
4186
|
+
let attempt = 0;
|
|
4187
|
+
while (true) {
|
|
4188
|
+
try {
|
|
4189
|
+
return await invoke();
|
|
4190
|
+
} catch (error) {
|
|
4191
|
+
if (attempt >= maxRetries || !shouldContinue()) throw error;
|
|
4192
|
+
attempt += 1;
|
|
4193
|
+
const delay2 = typeof retry?.delay === "function" ? retry.delay(attempt) : retry?.delay ?? 0;
|
|
4194
|
+
if (delay2 > 0) {
|
|
4195
|
+
await new Promise((resolve) => setTimeout(resolve, delay2));
|
|
4196
|
+
if (!shouldContinue()) throw error;
|
|
4197
|
+
}
|
|
4198
|
+
}
|
|
4199
|
+
}
|
|
4200
|
+
}
|
|
4201
|
+
__name(invokeMutationWithRetry, "invokeMutationWithRetry");
|
|
4202
|
+
|
|
4203
|
+
// src/mutation-client.ts
|
|
3900
4204
|
function useMutation(target, options = {}) {
|
|
4205
|
+
return useMutationLifecycle(target, options).mutation;
|
|
4206
|
+
}
|
|
4207
|
+
__name(useMutation, "useMutation");
|
|
4208
|
+
function useMutationLifecycle(target, options = {}) {
|
|
3901
4209
|
const initialData = options.initialData ?? null;
|
|
3902
4210
|
const optionsRef = (0, import_react.useRef)(options);
|
|
3903
4211
|
const targetRef = (0, import_react.useRef)(target);
|
|
3904
4212
|
const requestIdRef = (0, import_react.useRef)(0);
|
|
4213
|
+
const lastResetIdRef = (0, import_react.useRef)(0);
|
|
3905
4214
|
const initialState = {
|
|
3906
4215
|
pendingCount: 0,
|
|
4216
|
+
pausedCount: 0,
|
|
3907
4217
|
status: "idle",
|
|
3908
4218
|
data: initialData,
|
|
3909
4219
|
error: null,
|
|
3910
4220
|
variables: void 0
|
|
3911
4221
|
};
|
|
3912
4222
|
const stateRef = (0, import_react.useRef)(initialState);
|
|
4223
|
+
const resetWakersRef = (0, import_react.useRef)(/* @__PURE__ */ new Set());
|
|
3913
4224
|
const [state, setState] = (0, import_react.useState)(initialState);
|
|
3914
4225
|
optionsRef.current = options;
|
|
3915
4226
|
targetRef.current = target;
|
|
3916
4227
|
const setMutationState = (0, import_react.useCallback)(
|
|
3917
4228
|
(value) => {
|
|
3918
|
-
|
|
3919
|
-
|
|
3920
|
-
|
|
3921
|
-
return next;
|
|
3922
|
-
});
|
|
4229
|
+
const next = typeof value === "function" ? value(stateRef.current) : value;
|
|
4230
|
+
stateRef.current = next;
|
|
4231
|
+
setState(next);
|
|
3923
4232
|
},
|
|
3924
4233
|
[]
|
|
3925
4234
|
);
|
|
3926
|
-
const
|
|
3927
|
-
async (
|
|
4235
|
+
const waitForReconnect = (0, import_react.useCallback)(
|
|
4236
|
+
async (requestId) => {
|
|
4237
|
+
while (!isNavigatorOnline()) {
|
|
4238
|
+
if (requestId < lastResetIdRef.current) return;
|
|
4239
|
+
setMutationState((current) => ({ ...current, pausedCount: current.pausedCount + 1 }));
|
|
4240
|
+
try {
|
|
4241
|
+
await new Promise((resolve) => {
|
|
4242
|
+
const wake = /* @__PURE__ */ __name(() => {
|
|
4243
|
+
unsubscribe();
|
|
4244
|
+
resetWakersRef.current.delete(wake);
|
|
4245
|
+
resolve();
|
|
4246
|
+
}, "wake");
|
|
4247
|
+
const unsubscribe = subscribeOnline(wake);
|
|
4248
|
+
resetWakersRef.current.add(wake);
|
|
4249
|
+
});
|
|
4250
|
+
} finally {
|
|
4251
|
+
setMutationState((current) => ({
|
|
4252
|
+
...current,
|
|
4253
|
+
pausedCount: Math.max(0, current.pausedCount - 1)
|
|
4254
|
+
}));
|
|
4255
|
+
}
|
|
4256
|
+
}
|
|
4257
|
+
},
|
|
4258
|
+
[setMutationState]
|
|
4259
|
+
);
|
|
4260
|
+
const mutatePreparedAsync = (0, import_react.useCallback)(
|
|
4261
|
+
async (prepare) => {
|
|
3928
4262
|
const requestId = ++requestIdRef.current;
|
|
3929
4263
|
const currentOptions = optionsRef.current;
|
|
3930
4264
|
const previousData = stateRef.current.data;
|
|
3931
|
-
|
|
3932
|
-
|
|
3933
|
-
|
|
3934
|
-
|
|
4265
|
+
let variables;
|
|
4266
|
+
let preparationFailed = false;
|
|
4267
|
+
let preparationError;
|
|
4268
|
+
try {
|
|
4269
|
+
variables = prepare();
|
|
4270
|
+
} catch (error) {
|
|
4271
|
+
preparationFailed = true;
|
|
4272
|
+
preparationError = error;
|
|
4273
|
+
}
|
|
4274
|
+
const optimisticData = preparationFailed ? void 0 : currentOptions.optimistic?.({ variables, current: previousData });
|
|
3935
4275
|
const hasOptimisticData = optimisticData !== void 0;
|
|
3936
|
-
setMutationState((current) =>
|
|
3937
|
-
|
|
3938
|
-
|
|
3939
|
-
|
|
3940
|
-
|
|
3941
|
-
|
|
3942
|
-
|
|
4276
|
+
setMutationState((current) => {
|
|
4277
|
+
if (requestId < lastResetIdRef.current) return current;
|
|
4278
|
+
const pendingCount = current.pendingCount + 1;
|
|
4279
|
+
if (requestId !== requestIdRef.current) return { ...current, pendingCount };
|
|
4280
|
+
return {
|
|
4281
|
+
pendingCount,
|
|
4282
|
+
pausedCount: current.pausedCount,
|
|
4283
|
+
status: "pending",
|
|
4284
|
+
data: hasOptimisticData ? optimisticData : currentOptions.resetOnMutate === false ? current.data : null,
|
|
4285
|
+
error: null,
|
|
4286
|
+
variables
|
|
4287
|
+
};
|
|
4288
|
+
});
|
|
4289
|
+
const mutationTarget = targetRef.current;
|
|
4290
|
+
const isAPITarget = isAPIRouteRef(mutationTarget);
|
|
4291
|
+
const sharedOptimistic = !preparationFailed && !isAPITarget ? currentOptions.request?.optimistic : void 0;
|
|
4292
|
+
const sharedSnapshots = sharedOptimistic?.update?.length ? applyServerFnOptimisticUpdates(sharedOptimistic.update) : [];
|
|
3943
4293
|
try {
|
|
3944
|
-
|
|
3945
|
-
|
|
3946
|
-
|
|
4294
|
+
if (preparationFailed) throw preparationError;
|
|
4295
|
+
let data;
|
|
4296
|
+
while (true) {
|
|
4297
|
+
if (currentOptions.networkMode === "online") {
|
|
4298
|
+
await waitForReconnect(requestId);
|
|
4299
|
+
if (requestId < lastResetIdRef.current) {
|
|
4300
|
+
throw new Error("Mutation reset while waiting for reconnection");
|
|
4301
|
+
}
|
|
4302
|
+
}
|
|
4303
|
+
try {
|
|
4304
|
+
const rawResult = isAPITarget ? await mutationTarget(variables, currentOptions.request) : await invokeMutationWithRetry(
|
|
4305
|
+
() => targetRef.current(variables),
|
|
4306
|
+
currentOptions.request?.retry,
|
|
4307
|
+
// A reset disowns this submission; stop scheduling retries then.
|
|
4308
|
+
() => requestId >= lastResetIdRef.current
|
|
4309
|
+
);
|
|
4310
|
+
data = unwrapMutationResult(rawResult, isAPITarget);
|
|
4311
|
+
break;
|
|
4312
|
+
} catch (cause) {
|
|
4313
|
+
if (currentOptions.networkMode === "online" && !isNavigatorOnline() && requestId >= lastResetIdRef.current) {
|
|
4314
|
+
continue;
|
|
4315
|
+
}
|
|
4316
|
+
throw cause;
|
|
4317
|
+
}
|
|
4318
|
+
}
|
|
4319
|
+
settleServerFnOptimisticUpdates(sharedSnapshots, "commit");
|
|
4320
|
+
if (!isAPITarget && currentOptions.request?.invalidate) {
|
|
4321
|
+
for (const key of resolveServerFnInvalidateTargets(currentOptions.request.invalidate)) {
|
|
4322
|
+
notifyFarmCacheInvalidation(key);
|
|
4323
|
+
}
|
|
4324
|
+
}
|
|
3947
4325
|
const isLatestRequest = requestId === requestIdRef.current;
|
|
3948
4326
|
setMutationState((current) => {
|
|
4327
|
+
if (requestId < lastResetIdRef.current) return current;
|
|
3949
4328
|
const pendingCount = Math.max(0, current.pendingCount - 1);
|
|
3950
4329
|
if (!isLatestRequest) {
|
|
3951
4330
|
return {
|
|
3952
4331
|
...current,
|
|
3953
|
-
pendingCount
|
|
3954
|
-
status: pendingCount > 0 ? "pending" : current.status
|
|
4332
|
+
pendingCount
|
|
3955
4333
|
};
|
|
3956
4334
|
}
|
|
3957
4335
|
return {
|
|
3958
4336
|
pendingCount,
|
|
4337
|
+
pausedCount: current.pausedCount,
|
|
3959
4338
|
status: "success",
|
|
3960
4339
|
data,
|
|
3961
4340
|
error: null,
|
|
@@ -3963,24 +4342,35 @@ function useMutation(target, options = {}) {
|
|
|
3963
4342
|
};
|
|
3964
4343
|
});
|
|
3965
4344
|
if (isLatestRequest) {
|
|
3966
|
-
currentOptions.onSuccess
|
|
3967
|
-
|
|
4345
|
+
notifyClientObserver(currentOptions.onSuccess, [data, variables], "Mutation onSuccess");
|
|
4346
|
+
if (requestId === requestIdRef.current) {
|
|
4347
|
+
notifyClientObserver(
|
|
4348
|
+
currentOptions.onSettled,
|
|
4349
|
+
[data, null, variables],
|
|
4350
|
+
"Mutation onSettled"
|
|
4351
|
+
);
|
|
4352
|
+
}
|
|
3968
4353
|
}
|
|
3969
4354
|
return data;
|
|
3970
4355
|
} catch (cause) {
|
|
4356
|
+
settleServerFnOptimisticUpdates(
|
|
4357
|
+
sharedSnapshots,
|
|
4358
|
+
sharedOptimistic?.rollbackOnError ? "rollback" : "invalidate"
|
|
4359
|
+
);
|
|
3971
4360
|
const error = normalizeMutationError(cause);
|
|
3972
4361
|
const isLatestRequest = requestId === requestIdRef.current;
|
|
3973
4362
|
setMutationState((current) => {
|
|
4363
|
+
if (requestId < lastResetIdRef.current) return current;
|
|
3974
4364
|
const pendingCount = Math.max(0, current.pendingCount - 1);
|
|
3975
4365
|
if (!isLatestRequest) {
|
|
3976
4366
|
return {
|
|
3977
4367
|
...current,
|
|
3978
|
-
pendingCount
|
|
3979
|
-
status: pendingCount > 0 ? "pending" : current.status
|
|
4368
|
+
pendingCount
|
|
3980
4369
|
};
|
|
3981
4370
|
}
|
|
3982
4371
|
return {
|
|
3983
4372
|
pendingCount,
|
|
4373
|
+
pausedCount: current.pausedCount,
|
|
3984
4374
|
status: "error",
|
|
3985
4375
|
data: hasOptimisticData && currentOptions.rollbackOnError ? previousData : currentOptions.resetOnMutate === false ? current.data : null,
|
|
3986
4376
|
error,
|
|
@@ -3988,13 +4378,23 @@ function useMutation(target, options = {}) {
|
|
|
3988
4378
|
};
|
|
3989
4379
|
});
|
|
3990
4380
|
if (isLatestRequest) {
|
|
3991
|
-
currentOptions.onError
|
|
3992
|
-
|
|
4381
|
+
notifyClientObserver(currentOptions.onError, [error, variables], "Mutation onError");
|
|
4382
|
+
if (requestId === requestIdRef.current) {
|
|
4383
|
+
notifyClientObserver(
|
|
4384
|
+
currentOptions.onSettled,
|
|
4385
|
+
[null, error, variables],
|
|
4386
|
+
"Mutation onSettled"
|
|
4387
|
+
);
|
|
4388
|
+
}
|
|
3993
4389
|
}
|
|
3994
4390
|
throw error;
|
|
3995
4391
|
}
|
|
3996
4392
|
},
|
|
3997
|
-
[setMutationState]
|
|
4393
|
+
[setMutationState, waitForReconnect]
|
|
4394
|
+
);
|
|
4395
|
+
const mutateAsync = (0, import_react.useCallback)(
|
|
4396
|
+
(variables) => mutatePreparedAsync(() => variables),
|
|
4397
|
+
[mutatePreparedAsync]
|
|
3998
4398
|
);
|
|
3999
4399
|
const mutate = (0, import_react.useCallback)(
|
|
4000
4400
|
(variables) => {
|
|
@@ -4004,18 +4404,23 @@ function useMutation(target, options = {}) {
|
|
|
4004
4404
|
[mutateAsync]
|
|
4005
4405
|
);
|
|
4006
4406
|
const reset = (0, import_react.useCallback)(() => {
|
|
4007
|
-
|
|
4407
|
+
lastResetIdRef.current = ++requestIdRef.current;
|
|
4008
4408
|
setMutationState({
|
|
4009
4409
|
pendingCount: 0,
|
|
4410
|
+
pausedCount: 0,
|
|
4010
4411
|
status: "idle",
|
|
4011
4412
|
data: optionsRef.current.initialData ?? null,
|
|
4012
4413
|
error: null,
|
|
4013
4414
|
variables: void 0
|
|
4014
4415
|
});
|
|
4416
|
+
const wakers = Array.from(resetWakersRef.current);
|
|
4417
|
+
resetWakersRef.current.clear();
|
|
4418
|
+
for (const wake of wakers) wake();
|
|
4015
4419
|
}, [setMutationState]);
|
|
4016
|
-
|
|
4420
|
+
const mutation = (0, import_react.useMemo)(
|
|
4017
4421
|
() => ({
|
|
4018
4422
|
pending: state.pendingCount > 0,
|
|
4423
|
+
paused: state.pausedCount > 0,
|
|
4019
4424
|
status: state.status,
|
|
4020
4425
|
data: state.data,
|
|
4021
4426
|
error: state.error,
|
|
@@ -4030,13 +4435,15 @@ function useMutation(target, options = {}) {
|
|
|
4030
4435
|
reset,
|
|
4031
4436
|
state.data,
|
|
4032
4437
|
state.error,
|
|
4438
|
+
state.pausedCount,
|
|
4033
4439
|
state.pendingCount,
|
|
4034
4440
|
state.status,
|
|
4035
4441
|
state.variables
|
|
4036
4442
|
]
|
|
4037
4443
|
);
|
|
4444
|
+
return { mutation, mutatePreparedAsync };
|
|
4038
4445
|
}
|
|
4039
|
-
__name(
|
|
4446
|
+
__name(useMutationLifecycle, "useMutationLifecycle");
|
|
4040
4447
|
function unwrapMutationResult(result, apiRoute) {
|
|
4041
4448
|
if (!apiRoute) return result;
|
|
4042
4449
|
const apiResult = result;
|
|
@@ -4056,13 +4463,27 @@ __name(normalizeMutationError, "normalizeMutationError");
|
|
|
4056
4463
|
|
|
4057
4464
|
// src/fetcher-client.tsx
|
|
4058
4465
|
var import_react2 = require("react");
|
|
4466
|
+
var _FetcherInputError = class _FetcherInputError extends Error {
|
|
4467
|
+
constructor(cause) {
|
|
4468
|
+
super(
|
|
4469
|
+
cause instanceof Error ? cause.message : typeof cause === "string" ? cause : "Could not prepare form input"
|
|
4470
|
+
);
|
|
4471
|
+
this.name = "FetcherInputError";
|
|
4472
|
+
this.code = "input_error";
|
|
4473
|
+
this.status = 0;
|
|
4474
|
+
this.data = void 0;
|
|
4475
|
+
this.cause = cause;
|
|
4476
|
+
}
|
|
4477
|
+
};
|
|
4478
|
+
__name(_FetcherInputError, "FetcherInputError");
|
|
4479
|
+
var FetcherInputError = _FetcherInputError;
|
|
4059
4480
|
var formDataContexts = /* @__PURE__ */ new WeakMap();
|
|
4060
4481
|
function useFetcher(target, options = {}) {
|
|
4061
4482
|
const targetRef = (0, import_react2.useRef)(target);
|
|
4062
4483
|
const optionsRef = (0, import_react2.useRef)(options);
|
|
4063
4484
|
const submissionIdRef = (0, import_react2.useRef)(0);
|
|
4064
4485
|
const [formData, setFormData] = (0, import_react2.useState)(null);
|
|
4065
|
-
const mutation =
|
|
4486
|
+
const { mutation, mutatePreparedAsync } = useMutationLifecycle(target, options);
|
|
4066
4487
|
targetRef.current = target;
|
|
4067
4488
|
optionsRef.current = options;
|
|
4068
4489
|
const submitAsync = (0, import_react2.useCallback)(
|
|
@@ -4071,15 +4492,20 @@ function useFetcher(target, options = {}) {
|
|
|
4071
4492
|
const submittedFormData = isFormData2(input) ? input : null;
|
|
4072
4493
|
setFormData(submittedFormData);
|
|
4073
4494
|
try {
|
|
4074
|
-
|
|
4075
|
-
|
|
4495
|
+
return await mutatePreparedAsync(() => {
|
|
4496
|
+
try {
|
|
4497
|
+
return submittedFormData ? mapFetcherFormData(targetRef.current, submittedFormData, optionsRef.current) : input;
|
|
4498
|
+
} catch (error) {
|
|
4499
|
+
throw new FetcherInputError(error);
|
|
4500
|
+
}
|
|
4501
|
+
});
|
|
4076
4502
|
} finally {
|
|
4077
4503
|
if (submissionId === submissionIdRef.current) {
|
|
4078
4504
|
setFormData(null);
|
|
4079
4505
|
}
|
|
4080
4506
|
}
|
|
4081
4507
|
},
|
|
4082
|
-
[
|
|
4508
|
+
[mutatePreparedAsync]
|
|
4083
4509
|
);
|
|
4084
4510
|
const submit = (0, import_react2.useCallback)(
|
|
4085
4511
|
(input) => {
|
|
@@ -4129,6 +4555,7 @@ function useFetcher(target, options = {}) {
|
|
|
4129
4555
|
state: mutation.pending ? "submitting" : "idle",
|
|
4130
4556
|
status: mutation.status,
|
|
4131
4557
|
pending: mutation.pending,
|
|
4558
|
+
paused: mutation.paused,
|
|
4132
4559
|
data: mutation.data,
|
|
4133
4560
|
error: mutation.error,
|
|
4134
4561
|
variables: mutation.variables,
|
|
@@ -4143,6 +4570,7 @@ function useFetcher(target, options = {}) {
|
|
|
4143
4570
|
formData,
|
|
4144
4571
|
mutation.data,
|
|
4145
4572
|
mutation.error,
|
|
4573
|
+
mutation.paused,
|
|
4146
4574
|
mutation.pending,
|
|
4147
4575
|
mutation.status,
|
|
4148
4576
|
mutation.variables,
|
|
@@ -4161,9 +4589,18 @@ function mapFetcherFormData(target, formData, options) {
|
|
|
4161
4589
|
if (!isAPIRouteRef(target)) {
|
|
4162
4590
|
return formData;
|
|
4163
4591
|
}
|
|
4164
|
-
const values = formDataToObject(formData);
|
|
4165
4592
|
const method = getAPIRouteRefMetadata(target)?.method;
|
|
4166
|
-
|
|
4593
|
+
const query = method === "GET" || method === "HEAD";
|
|
4594
|
+
const encoding = context2.submitter?.getAttribute("formenctype") ?? context2.form?.enctype;
|
|
4595
|
+
if (!query && (encoding?.toLowerCase() === "multipart/form-data" || Array.from(formData.values()).some((value) => typeof value !== "string"))) {
|
|
4596
|
+
const body = new FormData();
|
|
4597
|
+
for (const [key, value] of formData) {
|
|
4598
|
+
if (!isUnsafeFormKey(key)) body.append(key, value);
|
|
4599
|
+
}
|
|
4600
|
+
return { body };
|
|
4601
|
+
}
|
|
4602
|
+
const values = formDataToObject(formData);
|
|
4603
|
+
return query ? { query: values } : { body: values };
|
|
4167
4604
|
}
|
|
4168
4605
|
__name(mapFetcherFormData, "mapFetcherFormData");
|
|
4169
4606
|
function resolveFetcherFormAction(target, metadata) {
|
|
@@ -4175,7 +4612,7 @@ __name(resolveFetcherFormAction, "resolveFetcherFormAction");
|
|
|
4175
4612
|
function formDataToObject(formData) {
|
|
4176
4613
|
const output = /* @__PURE__ */ Object.create(null);
|
|
4177
4614
|
for (const [key, value] of formData.entries()) {
|
|
4178
|
-
if (key
|
|
4615
|
+
if (isUnsafeFormKey(key)) continue;
|
|
4179
4616
|
const current = output[key];
|
|
4180
4617
|
if (current === void 0) {
|
|
4181
4618
|
output[key] = value;
|
|
@@ -4188,6 +4625,10 @@ function formDataToObject(formData) {
|
|
|
4188
4625
|
return output;
|
|
4189
4626
|
}
|
|
4190
4627
|
__name(formDataToObject, "formDataToObject");
|
|
4628
|
+
function isUnsafeFormKey(key) {
|
|
4629
|
+
return key === "__proto__" || key === "constructor" || key === "prototype";
|
|
4630
|
+
}
|
|
4631
|
+
__name(isUnsafeFormKey, "isUnsafeFormKey");
|
|
4191
4632
|
function createSubmitterFormData(form, submitter) {
|
|
4192
4633
|
try {
|
|
4193
4634
|
return new FormData(form, submitter);
|
|
@@ -4223,6 +4664,7 @@ function useServerFn(serverFn, options = {}) {
|
|
|
4223
4664
|
const { initialResult = null, resetOnSubmit = true } = options;
|
|
4224
4665
|
const callbacksRef = (0, import_react3.useRef)({});
|
|
4225
4666
|
const requestIdRef = (0, import_react3.useRef)(0);
|
|
4667
|
+
const lastResetIdRef = (0, import_react3.useRef)(0);
|
|
4226
4668
|
const initialState = {
|
|
4227
4669
|
pendingCount: 0,
|
|
4228
4670
|
status: "idle",
|
|
@@ -4233,11 +4675,9 @@ function useServerFn(serverFn, options = {}) {
|
|
|
4233
4675
|
const [state, setState] = (0, import_react3.useState)(initialState);
|
|
4234
4676
|
const setActionState = (0, import_react3.useCallback)(
|
|
4235
4677
|
(value) => {
|
|
4236
|
-
|
|
4237
|
-
|
|
4238
|
-
|
|
4239
|
-
return next;
|
|
4240
|
-
});
|
|
4678
|
+
const next = typeof value === "function" ? value(stateRef.current) : value;
|
|
4679
|
+
stateRef.current = next;
|
|
4680
|
+
setState(next);
|
|
4241
4681
|
},
|
|
4242
4682
|
[]
|
|
4243
4683
|
);
|
|
@@ -4258,63 +4698,88 @@ function useServerFn(serverFn, options = {}) {
|
|
|
4258
4698
|
current: previousResult
|
|
4259
4699
|
});
|
|
4260
4700
|
const hasOptimisticResult = optimisticResult !== void 0;
|
|
4261
|
-
setActionState((current) =>
|
|
4262
|
-
|
|
4263
|
-
|
|
4264
|
-
|
|
4265
|
-
|
|
4266
|
-
|
|
4701
|
+
setActionState((current) => {
|
|
4702
|
+
if (requestId < lastResetIdRef.current) return current;
|
|
4703
|
+
const pendingCount = current.pendingCount + 1;
|
|
4704
|
+
if (requestId !== requestIdRef.current) return { ...current, pendingCount };
|
|
4705
|
+
return {
|
|
4706
|
+
pendingCount,
|
|
4707
|
+
status: "pending",
|
|
4708
|
+
result: hasOptimisticResult ? optimisticResult : resetOnSubmit ? null : current.result,
|
|
4709
|
+
error: null
|
|
4710
|
+
};
|
|
4711
|
+
});
|
|
4267
4712
|
try {
|
|
4268
|
-
const result = await
|
|
4713
|
+
const result = await invokeMutationWithRetry(
|
|
4714
|
+
() => serverFn(input),
|
|
4715
|
+
options.retry,
|
|
4716
|
+
// A reset disowns this submission; stop scheduling retries then.
|
|
4717
|
+
() => requestId >= lastResetIdRef.current
|
|
4718
|
+
);
|
|
4269
4719
|
const isLatestRequest = requestId === requestIdRef.current;
|
|
4270
4720
|
setActionState((current) => {
|
|
4721
|
+
if (requestId < lastResetIdRef.current) return current;
|
|
4271
4722
|
const pendingCount = Math.max(0, current.pendingCount - 1);
|
|
4272
4723
|
if (!isLatestRequest) {
|
|
4273
4724
|
return {
|
|
4274
4725
|
...current,
|
|
4275
|
-
pendingCount
|
|
4276
|
-
status: pendingCount > 0 ? "pending" : current.status
|
|
4726
|
+
pendingCount
|
|
4277
4727
|
};
|
|
4278
4728
|
}
|
|
4279
4729
|
return {
|
|
4280
4730
|
pendingCount,
|
|
4281
|
-
status:
|
|
4731
|
+
status: "success",
|
|
4282
4732
|
result,
|
|
4283
4733
|
error: null
|
|
4284
4734
|
};
|
|
4285
4735
|
});
|
|
4286
4736
|
if (isLatestRequest) {
|
|
4287
|
-
callbacksRef.current.onSuccess
|
|
4288
|
-
|
|
4737
|
+
notifyClientObserver(callbacksRef.current.onSuccess, [result], "Action onSuccess");
|
|
4738
|
+
if (requestId === requestIdRef.current) {
|
|
4739
|
+
notifyClientObserver(
|
|
4740
|
+
callbacksRef.current.onSettled,
|
|
4741
|
+
[result, null],
|
|
4742
|
+
"Action onSettled"
|
|
4743
|
+
);
|
|
4744
|
+
}
|
|
4289
4745
|
}
|
|
4290
4746
|
return result;
|
|
4291
4747
|
} catch (cause) {
|
|
4292
4748
|
const error = normalizeServerFnError(cause);
|
|
4293
4749
|
const isLatestRequest = requestId === requestIdRef.current;
|
|
4294
4750
|
setActionState((current) => {
|
|
4751
|
+
if (requestId < lastResetIdRef.current) return current;
|
|
4295
4752
|
const pendingCount = Math.max(0, current.pendingCount - 1);
|
|
4296
4753
|
if (!isLatestRequest) {
|
|
4297
4754
|
return {
|
|
4298
4755
|
...current,
|
|
4299
|
-
pendingCount
|
|
4300
|
-
status: pendingCount > 0 ? "pending" : current.status
|
|
4756
|
+
pendingCount
|
|
4301
4757
|
};
|
|
4302
4758
|
}
|
|
4303
4759
|
return {
|
|
4304
4760
|
pendingCount,
|
|
4305
|
-
status:
|
|
4761
|
+
status: "error",
|
|
4306
4762
|
result: hasOptimisticResult && options.rollbackOnError ? previousResult : resetOnSubmit ? null : current.result,
|
|
4307
4763
|
error
|
|
4308
4764
|
};
|
|
4309
4765
|
});
|
|
4310
4766
|
if (isLatestRequest) {
|
|
4311
|
-
callbacksRef.current.onError
|
|
4312
|
-
|
|
4767
|
+
notifyClientObserver(callbacksRef.current.onError, [error], "Action onError");
|
|
4768
|
+
if (requestId === requestIdRef.current) {
|
|
4769
|
+
notifyClientObserver(callbacksRef.current.onSettled, [null, error], "Action onSettled");
|
|
4770
|
+
}
|
|
4313
4771
|
}
|
|
4314
4772
|
throw error;
|
|
4315
4773
|
}
|
|
4316
4774
|
},
|
|
4317
|
-
[
|
|
4775
|
+
[
|
|
4776
|
+
options.optimistic,
|
|
4777
|
+
options.retry,
|
|
4778
|
+
options.rollbackOnError,
|
|
4779
|
+
resetOnSubmit,
|
|
4780
|
+
serverFn,
|
|
4781
|
+
setActionState
|
|
4782
|
+
]
|
|
4318
4783
|
);
|
|
4319
4784
|
const formAction = (0, import_react3.useCallback)(
|
|
4320
4785
|
async (formData) => {
|
|
@@ -4329,7 +4794,7 @@ function useServerFn(serverFn, options = {}) {
|
|
|
4329
4794
|
[submit]
|
|
4330
4795
|
);
|
|
4331
4796
|
const reset = (0, import_react3.useCallback)(() => {
|
|
4332
|
-
|
|
4797
|
+
lastResetIdRef.current = ++requestIdRef.current;
|
|
4333
4798
|
setActionState({
|
|
4334
4799
|
pendingCount: 0,
|
|
4335
4800
|
status: "idle",
|
|
@@ -4354,14 +4819,17 @@ __name(useServerFn, "useServerFn");
|
|
|
4354
4819
|
function useAction(target, options = {}) {
|
|
4355
4820
|
const serverFn = resolveServerFnTarget(target);
|
|
4356
4821
|
const action = useServerFn(serverFn, options);
|
|
4822
|
+
const formActionRef = (0, import_react3.useRef)(action.formAction);
|
|
4823
|
+
formActionRef.current = action.formAction;
|
|
4357
4824
|
const Form = (0, import_react3.useMemo)(() => {
|
|
4825
|
+
const submitForm = /* @__PURE__ */ __name((formData) => formActionRef.current(formData), "submitForm");
|
|
4358
4826
|
const ActionForm = /* @__PURE__ */ __name((props) => (0, import_react3.createElement)("form", {
|
|
4359
4827
|
...props,
|
|
4360
|
-
action:
|
|
4828
|
+
action: submitForm
|
|
4361
4829
|
}), "ActionForm");
|
|
4362
4830
|
ActionForm.displayName = "FarmActionForm";
|
|
4363
4831
|
return ActionForm;
|
|
4364
|
-
}, [
|
|
4832
|
+
}, []);
|
|
4365
4833
|
return (0, import_react3.useMemo)(() => {
|
|
4366
4834
|
const call = /* @__PURE__ */ __name(((input) => action.submit(input)), "call");
|
|
4367
4835
|
return Object.assign(call, {
|
|
@@ -4413,6 +4881,21 @@ __name(isFormData3, "isFormData");
|
|
|
4413
4881
|
// src/server-query-client.ts
|
|
4414
4882
|
var import_react4 = require("react");
|
|
4415
4883
|
|
|
4884
|
+
// src/client-revalidation.ts
|
|
4885
|
+
function attachRevalidationListeners(refresh, options = {}) {
|
|
4886
|
+
if (typeof window === "undefined") return () => {
|
|
4887
|
+
};
|
|
4888
|
+
const onFocus = options.refetchOnWindowFocus === false ? void 0 : refresh;
|
|
4889
|
+
const onOnline = options.refetchOnReconnect === false ? void 0 : refresh;
|
|
4890
|
+
if (onFocus) window.addEventListener("focus", onFocus);
|
|
4891
|
+
if (onOnline) window.addEventListener("online", onOnline);
|
|
4892
|
+
return () => {
|
|
4893
|
+
if (onFocus) window.removeEventListener("focus", onFocus);
|
|
4894
|
+
if (onOnline) window.removeEventListener("online", onOnline);
|
|
4895
|
+
};
|
|
4896
|
+
}
|
|
4897
|
+
__name(attachRevalidationListeners, "attachRevalidationListeners");
|
|
4898
|
+
|
|
4416
4899
|
// src/server-query-runtime.ts
|
|
4417
4900
|
var FARM_SERVER_QUERY_CLIENT_STATE = /* @__PURE__ */ Symbol.for("farm.serverQueryClientState");
|
|
4418
4901
|
var serverQueryClientGlobal = globalThis;
|
|
@@ -4420,9 +4903,30 @@ var serverQueryClientState = serverQueryClientGlobal[FARM_SERVER_QUERY_CLIENT_ST
|
|
|
4420
4903
|
functionIds: /* @__PURE__ */ new WeakMap(),
|
|
4421
4904
|
nextFunctionId: 0,
|
|
4422
4905
|
active: [],
|
|
4423
|
-
latestOwners: /* @__PURE__ */ new Map()
|
|
4906
|
+
latestOwners: /* @__PURE__ */ new Map(),
|
|
4907
|
+
owners: /* @__PURE__ */ new Set()
|
|
4424
4908
|
});
|
|
4425
4909
|
serverQueryClientState.latestOwners ?? (serverQueryClientState.latestOwners = /* @__PURE__ */ new Map());
|
|
4910
|
+
serverQueryClientState.owners ?? (serverQueryClientState.owners = /* @__PURE__ */ new Set());
|
|
4911
|
+
function isServerQueryOwnerSuperseded(owner, key) {
|
|
4912
|
+
const cache = getFarmClientDataCache();
|
|
4913
|
+
const resolved = cache.resolveKey(key);
|
|
4914
|
+
for (const superseded of owner.supersededKeys ?? []) {
|
|
4915
|
+
if (cache.resolveKey(superseded) === resolved) return true;
|
|
4916
|
+
}
|
|
4917
|
+
return false;
|
|
4918
|
+
}
|
|
4919
|
+
__name(isServerQueryOwnerSuperseded, "isServerQueryOwnerSuperseded");
|
|
4920
|
+
function claimServerQueryKey(owner, key) {
|
|
4921
|
+
if (isServerQueryOwnerSuperseded(owner, key)) return false;
|
|
4922
|
+
const resolved = getFarmClientDataCache().resolveKey(key);
|
|
4923
|
+
for (const older of serverQueryClientState.owners) {
|
|
4924
|
+
if (older === owner) break;
|
|
4925
|
+
older.supersededKeys.add(resolved);
|
|
4926
|
+
}
|
|
4927
|
+
return true;
|
|
4928
|
+
}
|
|
4929
|
+
__name(claimServerQueryKey, "claimServerQueryKey");
|
|
4426
4930
|
var RAW_SERVER_QUERY_SYMBOL = /* @__PURE__ */ Symbol.for("farm.server-query");
|
|
4427
4931
|
function assertNotRawServerQueryInBrowser(query) {
|
|
4428
4932
|
if (typeof window === "undefined" || typeof document === "undefined") return;
|
|
@@ -4436,6 +4940,10 @@ function assertNotRawServerQueryInBrowser(query) {
|
|
|
4436
4940
|
);
|
|
4437
4941
|
}
|
|
4438
4942
|
__name(assertNotRawServerQueryInBrowser, "assertNotRawServerQueryInBrowser");
|
|
4943
|
+
function isCurrentServerQueryOwner(provisionalKey, owner) {
|
|
4944
|
+
return serverQueryClientState.latestOwners.get(provisionalKey) === owner && !isServerQueryOwnerSuperseded(owner, provisionalKey);
|
|
4945
|
+
}
|
|
4946
|
+
__name(isCurrentServerQueryOwner, "isCurrentServerQueryOwner");
|
|
4439
4947
|
function createServerQueryCallKey(query, input) {
|
|
4440
4948
|
let id = serverQueryClientState.functionIds.get(query);
|
|
4441
4949
|
if (!id) {
|
|
@@ -4451,12 +4959,14 @@ async function fetchServerQuery(query, input, options = {}) {
|
|
|
4451
4959
|
const entry = cache.get(provisionalKey);
|
|
4452
4960
|
const stale = cache.isStale(provisionalKey);
|
|
4453
4961
|
const inflight = cache.getInflight(provisionalKey);
|
|
4454
|
-
if (
|
|
4455
|
-
|
|
4456
|
-
|
|
4457
|
-
|
|
4962
|
+
if (!options.force && entry && stale && (entry.status !== "pending" || entry.updatedAt !== 0) && entry.status !== "error" && (options.swr ?? true)) {
|
|
4963
|
+
if (!inflight) {
|
|
4964
|
+
void executeServerQuery(query, input, provisionalKey, options).catch(() => void 0);
|
|
4965
|
+
}
|
|
4458
4966
|
return entry.data;
|
|
4459
4967
|
}
|
|
4968
|
+
if (inflight && !options.force) return inflight;
|
|
4969
|
+
if (!options.force && entry && !stale && entry.status !== "error") return entry.data;
|
|
4460
4970
|
return executeServerQuery(query, input, provisionalKey, options);
|
|
4461
4971
|
}
|
|
4462
4972
|
__name(fetchServerQuery, "fetchServerQuery");
|
|
@@ -4469,8 +4979,13 @@ async function executeServerQuery(query, input, provisionalKey, options) {
|
|
|
4469
4979
|
const cache = getFarmClientDataCache();
|
|
4470
4980
|
const inflight = cache.getInflight(provisionalKey);
|
|
4471
4981
|
if (inflight && !options.force) return inflight;
|
|
4472
|
-
const owner = {
|
|
4982
|
+
const owner = {
|
|
4983
|
+
invalidations: trackFarmClientCacheInvalidations(cache),
|
|
4984
|
+
supersededKeys: /* @__PURE__ */ new Set()
|
|
4985
|
+
};
|
|
4473
4986
|
serverQueryClientState.latestOwners.set(provisionalKey, owner);
|
|
4987
|
+
serverQueryClientState.owners.add(owner);
|
|
4988
|
+
claimServerQueryKey(owner, provisionalKey);
|
|
4474
4989
|
const previous = cache.get(provisionalKey);
|
|
4475
4990
|
cache.set(provisionalKey, {
|
|
4476
4991
|
data: previous?.data,
|
|
@@ -4495,12 +5010,12 @@ async function executeServerQuery(query, input, provisionalKey, options) {
|
|
|
4495
5010
|
}
|
|
4496
5011
|
const data = await pending;
|
|
4497
5012
|
const transported = cache.get(provisionalKey);
|
|
4498
|
-
if (
|
|
5013
|
+
if (isCurrentServerQueryOwner(provisionalKey, owner) && (!transported || transported.fetching)) {
|
|
4499
5014
|
const updatedAt = Date.now();
|
|
4500
5015
|
cache.set(provisionalKey, {
|
|
4501
5016
|
data,
|
|
4502
5017
|
updatedAt,
|
|
4503
|
-
staleAt: options.staleTime === false ? Number.POSITIVE_INFINITY : updatedAt + (options.staleTime ?? 0),
|
|
5018
|
+
staleAt: owner.invalidations.has(provisionalKey) ? 0 : options.staleTime === false ? Number.POSITIVE_INFINITY : updatedAt + (options.staleTime ?? 0),
|
|
4504
5019
|
status: "success",
|
|
4505
5020
|
error: null,
|
|
4506
5021
|
fetching: false
|
|
@@ -4509,7 +5024,7 @@ async function executeServerQuery(query, input, provisionalKey, options) {
|
|
|
4509
5024
|
return data;
|
|
4510
5025
|
} catch (cause) {
|
|
4511
5026
|
const error = normalizeServerQueryError(cause);
|
|
4512
|
-
if (
|
|
5027
|
+
if (isCurrentServerQueryOwner(provisionalKey, owner)) {
|
|
4513
5028
|
const current = cache.get(provisionalKey);
|
|
4514
5029
|
cache.set(provisionalKey, {
|
|
4515
5030
|
data: current?.data,
|
|
@@ -4524,12 +5039,17 @@ async function executeServerQuery(query, input, provisionalKey, options) {
|
|
|
4524
5039
|
}
|
|
4525
5040
|
throw error;
|
|
4526
5041
|
} finally {
|
|
5042
|
+
const invalidated = isCurrentServerQueryOwner(provisionalKey, owner) && owner.invalidations.has(provisionalKey);
|
|
5043
|
+
owner.invalidations.dispose();
|
|
5044
|
+
serverQueryClientState.owners.delete(owner);
|
|
5045
|
+
owner.supersededKeys.clear();
|
|
4527
5046
|
if (cache.getInflight(provisionalKey) === promise) {
|
|
4528
5047
|
cache.deleteInflight(provisionalKey);
|
|
4529
5048
|
}
|
|
4530
5049
|
if (serverQueryClientState.latestOwners.get(provisionalKey) === owner) {
|
|
4531
5050
|
serverQueryClientState.latestOwners.delete(provisionalKey);
|
|
4532
5051
|
}
|
|
5052
|
+
if (invalidated) cache.invalidate(provisionalKey);
|
|
4533
5053
|
}
|
|
4534
5054
|
})();
|
|
4535
5055
|
cache.setInflight(provisionalKey, promise);
|
|
@@ -4551,19 +5071,29 @@ function useServerQuery(query, input, options = {}) {
|
|
|
4551
5071
|
const inputRef = (0, import_react4.useRef)(input);
|
|
4552
5072
|
const optionsRef = (0, import_react4.useRef)(options);
|
|
4553
5073
|
const mountedKeyRef = (0, import_react4.useRef)(void 0);
|
|
5074
|
+
const pendingInvalidationRef = (0, import_react4.useRef)(false);
|
|
4554
5075
|
inputRef.current = input;
|
|
4555
5076
|
optionsRef.current = options;
|
|
4556
5077
|
const subscribe = (0, import_react4.useCallback)(
|
|
4557
|
-
(listener) => cache.subscribe(key,
|
|
5078
|
+
(listener) => cache.subscribe(key, (event) => {
|
|
5079
|
+
if (event === "invalidate") pendingInvalidationRef.current = true;
|
|
5080
|
+
else if (cache.get(key)?.fetching) {
|
|
5081
|
+
pendingInvalidationRef.current = false;
|
|
5082
|
+
}
|
|
5083
|
+
listener();
|
|
5084
|
+
}),
|
|
4558
5085
|
[cache, key]
|
|
4559
5086
|
);
|
|
4560
5087
|
const getSnapshot = (0, import_react4.useCallback)(() => cache.get(key), [cache, key]);
|
|
4561
5088
|
const entry = (0, import_react4.useSyncExternalStore)(subscribe, getSnapshot, () => void 0);
|
|
4562
5089
|
const run = (0, import_react4.useCallback)(
|
|
4563
|
-
(force = false) =>
|
|
4564
|
-
|
|
4565
|
-
|
|
4566
|
-
|
|
5090
|
+
(force = false) => {
|
|
5091
|
+
pendingInvalidationRef.current = false;
|
|
5092
|
+
return fetchServerQuery(query, inputRef.current, {
|
|
5093
|
+
...optionsRef.current,
|
|
5094
|
+
force
|
|
5095
|
+
});
|
|
5096
|
+
},
|
|
4567
5097
|
[query]
|
|
4568
5098
|
);
|
|
4569
5099
|
(0, import_react4.useEffect)(() => {
|
|
@@ -4573,23 +5103,21 @@ function useServerQuery(query, input, options = {}) {
|
|
|
4573
5103
|
}
|
|
4574
5104
|
const firstReadForKey = mountedKeyRef.current !== key;
|
|
4575
5105
|
if (firstReadForKey) mountedKeyRef.current = key;
|
|
4576
|
-
if (firstReadForKey && (!entry || cache.isStale(key)) || entry?.invalidatedAt !== void 0 && !entry.fetching) {
|
|
5106
|
+
if (firstReadForKey && (!entry || cache.isStale(key)) || pendingInvalidationRef.current && entry?.invalidatedAt !== void 0 && !entry.fetching) {
|
|
4577
5107
|
void run().catch(() => void 0);
|
|
4578
5108
|
}
|
|
4579
5109
|
}, [cache, entry, key, options.enabled, run]);
|
|
4580
5110
|
(0, import_react4.useEffect)(() => {
|
|
4581
|
-
if (options.enabled === false
|
|
4582
|
-
|
|
4583
|
-
|
|
4584
|
-
|
|
4585
|
-
|
|
4586
|
-
|
|
4587
|
-
|
|
4588
|
-
|
|
4589
|
-
|
|
4590
|
-
|
|
4591
|
-
if (onOnline) window.removeEventListener("online", onOnline);
|
|
4592
|
-
};
|
|
5111
|
+
if (options.enabled === false) return;
|
|
5112
|
+
return attachRevalidationListeners(
|
|
5113
|
+
() => {
|
|
5114
|
+
if (cache.isStale(key)) void run().catch(() => void 0);
|
|
5115
|
+
},
|
|
5116
|
+
{
|
|
5117
|
+
refetchOnWindowFocus: options.refetchOnWindowFocus,
|
|
5118
|
+
refetchOnReconnect: options.refetchOnReconnect
|
|
5119
|
+
}
|
|
5120
|
+
);
|
|
4593
5121
|
}, [cache, key, options.enabled, options.refetchOnReconnect, options.refetchOnWindowFocus, run]);
|
|
4594
5122
|
const status = entry?.status ?? (entry ? "success" : "idle");
|
|
4595
5123
|
const fetching = entry?.fetching ?? false;
|
|
@@ -4605,6 +5133,296 @@ function useServerQuery(query, input, options = {}) {
|
|
|
4605
5133
|
}
|
|
4606
5134
|
__name(useServerQuery, "useServerQuery");
|
|
4607
5135
|
|
|
5136
|
+
// src/cache-invalidation-broadcast.ts
|
|
5137
|
+
var FARM_CACHE_INVALIDATION_CHANNEL = "farm:cache-invalidation";
|
|
5138
|
+
var activeBridge;
|
|
5139
|
+
function enableCrossTabCacheInvalidation(options = {}) {
|
|
5140
|
+
if (typeof BroadcastChannel !== "function") return () => {
|
|
5141
|
+
};
|
|
5142
|
+
const channelName = options.channelName ?? FARM_CACHE_INVALIDATION_CHANNEL;
|
|
5143
|
+
if (activeBridge) {
|
|
5144
|
+
if (activeBridge.channelName !== channelName) {
|
|
5145
|
+
throw new Error(
|
|
5146
|
+
`Cross-tab cache invalidation is already enabled on channel "${activeBridge.channelName}".`
|
|
5147
|
+
);
|
|
5148
|
+
}
|
|
5149
|
+
activeBridge.refCount += 1;
|
|
5150
|
+
} else {
|
|
5151
|
+
activeBridge = createBridge(channelName);
|
|
5152
|
+
}
|
|
5153
|
+
let disposed = false;
|
|
5154
|
+
return () => {
|
|
5155
|
+
if (disposed || !activeBridge) return;
|
|
5156
|
+
disposed = true;
|
|
5157
|
+
activeBridge.refCount -= 1;
|
|
5158
|
+
if (activeBridge.refCount === 0) {
|
|
5159
|
+
activeBridge.teardown();
|
|
5160
|
+
activeBridge = void 0;
|
|
5161
|
+
}
|
|
5162
|
+
};
|
|
5163
|
+
}
|
|
5164
|
+
__name(enableCrossTabCacheInvalidation, "enableCrossTabCacheInvalidation");
|
|
5165
|
+
function createBridge(channelName) {
|
|
5166
|
+
const channel = new BroadcastChannel(channelName);
|
|
5167
|
+
let applyingRemote = false;
|
|
5168
|
+
let pending = [];
|
|
5169
|
+
let flushScheduled = false;
|
|
5170
|
+
let closed = false;
|
|
5171
|
+
const flush = /* @__PURE__ */ __name(() => {
|
|
5172
|
+
flushScheduled = false;
|
|
5173
|
+
if (closed || pending.length === 0) return;
|
|
5174
|
+
const encoded = encodeFarmCacheInvalidations(pending);
|
|
5175
|
+
pending = [];
|
|
5176
|
+
if (encoded !== null) channel.postMessage(encoded);
|
|
5177
|
+
}, "flush");
|
|
5178
|
+
const unsubscribe = subscribeFarmCacheInvalidation((key) => {
|
|
5179
|
+
if (applyingRemote || closed) return;
|
|
5180
|
+
pending.push(key);
|
|
5181
|
+
if (!flushScheduled) {
|
|
5182
|
+
flushScheduled = true;
|
|
5183
|
+
queueMicrotask(flush);
|
|
5184
|
+
}
|
|
5185
|
+
});
|
|
5186
|
+
channel.onmessage = (event) => {
|
|
5187
|
+
const keys = decodeFarmCacheInvalidations(
|
|
5188
|
+
typeof event.data === "string" ? event.data : void 0
|
|
5189
|
+
);
|
|
5190
|
+
if (keys.length === 0) return;
|
|
5191
|
+
applyingRemote = true;
|
|
5192
|
+
try {
|
|
5193
|
+
for (const key of keys) notifyFarmCacheInvalidation(key);
|
|
5194
|
+
} finally {
|
|
5195
|
+
applyingRemote = false;
|
|
5196
|
+
}
|
|
5197
|
+
};
|
|
5198
|
+
return {
|
|
5199
|
+
channelName,
|
|
5200
|
+
refCount: 1,
|
|
5201
|
+
teardown() {
|
|
5202
|
+
closed = true;
|
|
5203
|
+
pending = [];
|
|
5204
|
+
unsubscribe();
|
|
5205
|
+
channel.onmessage = null;
|
|
5206
|
+
channel.close();
|
|
5207
|
+
}
|
|
5208
|
+
};
|
|
5209
|
+
}
|
|
5210
|
+
__name(createBridge, "createBridge");
|
|
5211
|
+
|
|
5212
|
+
// src/client-cache-persistence.ts
|
|
5213
|
+
var FARM_CLIENT_CACHE_PERSIST_VERSION = "1";
|
|
5214
|
+
function defineClientCacheAdapter(adapter) {
|
|
5215
|
+
for (const method of ["keys", "get", "set", "delete", "clear"]) {
|
|
5216
|
+
if (typeof adapter?.[method] !== "function") {
|
|
5217
|
+
throw new TypeError(
|
|
5218
|
+
`defineClientCacheAdapter expects a "${method}" method. Implement keys/get/set/delete/clear over your storage.`
|
|
5219
|
+
);
|
|
5220
|
+
}
|
|
5221
|
+
}
|
|
5222
|
+
return adapter;
|
|
5223
|
+
}
|
|
5224
|
+
__name(defineClientCacheAdapter, "defineClientCacheAdapter");
|
|
5225
|
+
function storageClientCacheAdapter(storage, options = {}) {
|
|
5226
|
+
if (!storage || typeof storage.getItem !== "function" || typeof storage.setItem !== "function" || typeof storage.removeItem !== "function") {
|
|
5227
|
+
throw new TypeError("storageClientCacheAdapter expects a compatible key-value client.");
|
|
5228
|
+
}
|
|
5229
|
+
const base = options.base ?? "farm-client-cache";
|
|
5230
|
+
const entryKey = /* @__PURE__ */ __name((key) => `${base}:${key}`, "entryKey");
|
|
5231
|
+
const enumerate = storage.getKeys?.bind(storage) ?? storage.keys?.bind(storage);
|
|
5232
|
+
return {
|
|
5233
|
+
async keys() {
|
|
5234
|
+
if (!enumerate) return [];
|
|
5235
|
+
const keys = await enumerate(base);
|
|
5236
|
+
const prefix = `${base}:`;
|
|
5237
|
+
return keys.filter((key) => key.startsWith(prefix)).map((key) => key.slice(prefix.length));
|
|
5238
|
+
},
|
|
5239
|
+
async get(key) {
|
|
5240
|
+
return await storage.getItem(entryKey(key)) ?? null;
|
|
5241
|
+
},
|
|
5242
|
+
async set(key, entry) {
|
|
5243
|
+
await storage.setItem(entryKey(key), entry);
|
|
5244
|
+
},
|
|
5245
|
+
async delete(key) {
|
|
5246
|
+
await storage.removeItem(entryKey(key));
|
|
5247
|
+
},
|
|
5248
|
+
async clear() {
|
|
5249
|
+
if (storage.clear) {
|
|
5250
|
+
await storage.clear(base);
|
|
5251
|
+
return;
|
|
5252
|
+
}
|
|
5253
|
+
if (!enumerate) return;
|
|
5254
|
+
const prefix = `${base}:`;
|
|
5255
|
+
for (const key of await enumerate(base)) {
|
|
5256
|
+
if (key.startsWith(prefix)) await storage.removeItem(key);
|
|
5257
|
+
}
|
|
5258
|
+
}
|
|
5259
|
+
};
|
|
5260
|
+
}
|
|
5261
|
+
__name(storageClientCacheAdapter, "storageClientCacheAdapter");
|
|
5262
|
+
var activeEngine;
|
|
5263
|
+
function reportPersistenceFailure(error) {
|
|
5264
|
+
const report = typeof reportError === "function" ? reportError : console.error;
|
|
5265
|
+
if (error instanceof Error) {
|
|
5266
|
+
report(error);
|
|
5267
|
+
return;
|
|
5268
|
+
}
|
|
5269
|
+
const normalized = new Error("Client cache persistence failed");
|
|
5270
|
+
normalized.cause = error;
|
|
5271
|
+
report(normalized);
|
|
5272
|
+
}
|
|
5273
|
+
__name(reportPersistenceFailure, "reportPersistenceFailure");
|
|
5274
|
+
function disableEngine(engine, error) {
|
|
5275
|
+
if (engine.disabled) return;
|
|
5276
|
+
engine.disabled = true;
|
|
5277
|
+
engine.pendingSets.clear();
|
|
5278
|
+
engine.pendingDeletes.clear();
|
|
5279
|
+
if (engine.flushTimer !== void 0) {
|
|
5280
|
+
clearTimeout(engine.flushTimer);
|
|
5281
|
+
engine.flushTimer = void 0;
|
|
5282
|
+
}
|
|
5283
|
+
reportPersistenceFailure(error);
|
|
5284
|
+
}
|
|
5285
|
+
__name(disableEngine, "disableEngine");
|
|
5286
|
+
function scheduleFlush(engine) {
|
|
5287
|
+
if (engine.disabled || engine.flushTimer !== void 0) return;
|
|
5288
|
+
const timer = setTimeout(() => {
|
|
5289
|
+
engine.flushTimer = void 0;
|
|
5290
|
+
void flushEngine(engine);
|
|
5291
|
+
}, engine.flushDelayMs);
|
|
5292
|
+
timer.unref?.();
|
|
5293
|
+
engine.flushTimer = timer;
|
|
5294
|
+
}
|
|
5295
|
+
__name(scheduleFlush, "scheduleFlush");
|
|
5296
|
+
async function flushEngine(engine) {
|
|
5297
|
+
if (engine.disabled) return;
|
|
5298
|
+
const sets = Array.from(engine.pendingSets.entries());
|
|
5299
|
+
const deletes = Array.from(engine.pendingDeletes);
|
|
5300
|
+
engine.pendingSets.clear();
|
|
5301
|
+
engine.pendingDeletes.clear();
|
|
5302
|
+
try {
|
|
5303
|
+
if (sets.length > 0) {
|
|
5304
|
+
if (engine.adapter.setMany) await engine.adapter.setMany(sets);
|
|
5305
|
+
else for (const [key, entry] of sets) await engine.adapter.set(key, entry);
|
|
5306
|
+
}
|
|
5307
|
+
for (const key of deletes) await engine.adapter.delete(key);
|
|
5308
|
+
} catch (error) {
|
|
5309
|
+
disableEngine(engine, error);
|
|
5310
|
+
}
|
|
5311
|
+
}
|
|
5312
|
+
__name(flushEngine, "flushEngine");
|
|
5313
|
+
async function hydrateEngine(engine) {
|
|
5314
|
+
const now2 = Date.now();
|
|
5315
|
+
const keys = await engine.adapter.keys();
|
|
5316
|
+
if (keys.length === 0) return;
|
|
5317
|
+
const persisted = engine.adapter.getMany ? await engine.adapter.getMany(keys) : await Promise.all(keys.map((key) => engine.adapter.get(key)));
|
|
5318
|
+
engine.hydrating = true;
|
|
5319
|
+
try {
|
|
5320
|
+
for (let index = 0; index < keys.length; index += 1) {
|
|
5321
|
+
const key = keys[index];
|
|
5322
|
+
const entry = persisted[index];
|
|
5323
|
+
if (engine.disabled) return;
|
|
5324
|
+
if (!entry || entry.version !== engine.version || entry.gcAt !== void 0 && now2 >= entry.gcAt) {
|
|
5325
|
+
engine.pendingDeletes.add(key);
|
|
5326
|
+
continue;
|
|
5327
|
+
}
|
|
5328
|
+
if (engine.cache.get(key, now2)) continue;
|
|
5329
|
+
engine.cache.set(key, {
|
|
5330
|
+
data: entry.data,
|
|
5331
|
+
updatedAt: entry.updatedAt,
|
|
5332
|
+
staleAt: 0,
|
|
5333
|
+
gcAt: entry.gcAt,
|
|
5334
|
+
status: "success",
|
|
5335
|
+
error: null,
|
|
5336
|
+
persist: true
|
|
5337
|
+
});
|
|
5338
|
+
}
|
|
5339
|
+
} finally {
|
|
5340
|
+
engine.hydrating = false;
|
|
5341
|
+
}
|
|
5342
|
+
if (engine.pendingDeletes.size > 0) scheduleFlush(engine);
|
|
5343
|
+
}
|
|
5344
|
+
__name(hydrateEngine, "hydrateEngine");
|
|
5345
|
+
function createSink(engine) {
|
|
5346
|
+
return {
|
|
5347
|
+
onSet(key, entry) {
|
|
5348
|
+
if (engine.disabled || engine.hydrating) return;
|
|
5349
|
+
if (!entry.persist || entry.fetching || entry.error || entry.status === "pending") return;
|
|
5350
|
+
if (engine.persistKey && !engine.persistKey(key)) return;
|
|
5351
|
+
engine.pendingDeletes.delete(key);
|
|
5352
|
+
engine.pendingSets.set(key, {
|
|
5353
|
+
data: entry.data,
|
|
5354
|
+
updatedAt: entry.updatedAt,
|
|
5355
|
+
staleAt: entry.staleAt,
|
|
5356
|
+
gcAt: entry.gcAt,
|
|
5357
|
+
version: engine.version
|
|
5358
|
+
});
|
|
5359
|
+
scheduleFlush(engine);
|
|
5360
|
+
},
|
|
5361
|
+
onDelete(key) {
|
|
5362
|
+
if (engine.disabled) return;
|
|
5363
|
+
engine.pendingSets.delete(key);
|
|
5364
|
+
engine.pendingDeletes.add(key);
|
|
5365
|
+
scheduleFlush(engine);
|
|
5366
|
+
},
|
|
5367
|
+
onClear() {
|
|
5368
|
+
if (engine.disabled) return;
|
|
5369
|
+
engine.pendingSets.clear();
|
|
5370
|
+
engine.pendingDeletes.clear();
|
|
5371
|
+
void engine.adapter.clear().catch((error) => disableEngine(engine, error));
|
|
5372
|
+
}
|
|
5373
|
+
};
|
|
5374
|
+
}
|
|
5375
|
+
__name(createSink, "createSink");
|
|
5376
|
+
function initPersistedClientCache(adapter, options = {}) {
|
|
5377
|
+
defineClientCacheAdapter(adapter);
|
|
5378
|
+
disposePersistedClientCache();
|
|
5379
|
+
const engine = {
|
|
5380
|
+
adapter,
|
|
5381
|
+
cache: getFarmClientDataCache(),
|
|
5382
|
+
version: options.version ? `${FARM_CLIENT_CACHE_PERSIST_VERSION}:${options.version}` : FARM_CLIENT_CACHE_PERSIST_VERSION,
|
|
5383
|
+
persistKey: options.persistKey,
|
|
5384
|
+
flushDelayMs: options.flushDelayMs ?? 300,
|
|
5385
|
+
pendingSets: /* @__PURE__ */ new Map(),
|
|
5386
|
+
pendingDeletes: /* @__PURE__ */ new Set(),
|
|
5387
|
+
flushTimer: void 0,
|
|
5388
|
+
hydrating: false,
|
|
5389
|
+
disabled: false
|
|
5390
|
+
};
|
|
5391
|
+
activeEngine = engine;
|
|
5392
|
+
engine.cache.attachPersistence(createSink(engine));
|
|
5393
|
+
void hydrateEngine(engine).catch((error) => disableEngine(engine, error));
|
|
5394
|
+
return () => {
|
|
5395
|
+
if (activeEngine !== engine) return;
|
|
5396
|
+
disposePersistedClientCache();
|
|
5397
|
+
};
|
|
5398
|
+
}
|
|
5399
|
+
__name(initPersistedClientCache, "initPersistedClientCache");
|
|
5400
|
+
function disposePersistedClientCache() {
|
|
5401
|
+
const engine = activeEngine;
|
|
5402
|
+
if (!engine) return;
|
|
5403
|
+
activeEngine = void 0;
|
|
5404
|
+
engine.cache.attachPersistence(void 0);
|
|
5405
|
+
if (engine.flushTimer !== void 0) {
|
|
5406
|
+
clearTimeout(engine.flushTimer);
|
|
5407
|
+
engine.flushTimer = void 0;
|
|
5408
|
+
}
|
|
5409
|
+
engine.pendingSets.clear();
|
|
5410
|
+
engine.pendingDeletes.clear();
|
|
5411
|
+
}
|
|
5412
|
+
__name(disposePersistedClientCache, "disposePersistedClientCache");
|
|
5413
|
+
async function clearPersistedCache() {
|
|
5414
|
+
const engine = activeEngine;
|
|
5415
|
+
if (!engine) return;
|
|
5416
|
+
engine.pendingSets.clear();
|
|
5417
|
+
engine.pendingDeletes.clear();
|
|
5418
|
+
try {
|
|
5419
|
+
await engine.adapter.clear();
|
|
5420
|
+
} catch (error) {
|
|
5421
|
+
disableEngine(engine, error);
|
|
5422
|
+
}
|
|
5423
|
+
}
|
|
5424
|
+
__name(clearPersistedCache, "clearPersistedCache");
|
|
5425
|
+
|
|
4608
5426
|
// src/integration-api.ts
|
|
4609
5427
|
function defineIntegrationAPIOperation(operation2) {
|
|
4610
5428
|
return {
|
|
@@ -4847,11 +5665,14 @@ function pickState(state, keys) {
|
|
|
4847
5665
|
return slice;
|
|
4848
5666
|
}
|
|
4849
5667
|
__name(pickState, "pickState");
|
|
5668
|
+
function getEnumerableKeys(state) {
|
|
5669
|
+
return Reflect.ownKeys(state).filter(
|
|
5670
|
+
(key) => Object.prototype.propertyIsEnumerable.call(state, key)
|
|
5671
|
+
);
|
|
5672
|
+
}
|
|
5673
|
+
__name(getEnumerableKeys, "getEnumerableKeys");
|
|
4850
5674
|
function getChangedKeys(state, previousState) {
|
|
4851
|
-
const keys = /* @__PURE__ */ new Set([
|
|
4852
|
-
...Object.keys(state),
|
|
4853
|
-
...Object.keys(previousState)
|
|
4854
|
-
]);
|
|
5675
|
+
const keys = /* @__PURE__ */ new Set([...getEnumerableKeys(state), ...getEnumerableKeys(previousState)]);
|
|
4855
5676
|
return [...keys].filter((key) => !Object.is(state[key], previousState[key]));
|
|
4856
5677
|
}
|
|
4857
5678
|
__name(getChangedKeys, "getChangedKeys");
|
|
@@ -4872,7 +5693,11 @@ function createStore(initialState, extend) {
|
|
|
4872
5693
|
let state = cloneState(initialState);
|
|
4873
5694
|
const subscriptions = /* @__PURE__ */ new Set();
|
|
4874
5695
|
const addSubscription = /* @__PURE__ */ __name((keys, notify) => {
|
|
4875
|
-
const subscription = {
|
|
5696
|
+
const subscription = {
|
|
5697
|
+
// Object property enumeration returns numeric keys as strings.
|
|
5698
|
+
keys: keys?.map((key) => typeof key === "number" ? String(key) : key) ?? null,
|
|
5699
|
+
notify
|
|
5700
|
+
};
|
|
4876
5701
|
subscriptions.add(subscription);
|
|
4877
5702
|
return () => {
|
|
4878
5703
|
subscriptions.delete(subscription);
|
|
@@ -4964,7 +5789,7 @@ function createStore(initialState, extend) {
|
|
|
4964
5789
|
getSnapshot
|
|
4965
5790
|
);
|
|
4966
5791
|
}
|
|
4967
|
-
if (
|
|
5792
|
+
if (isStoreKey(keyOrKeys)) {
|
|
4968
5793
|
return (0, import_react5.useSyncExternalStore)(
|
|
4969
5794
|
(notify) => addSubscription([keyOrKeys], () => notify()),
|
|
4970
5795
|
() => state[keyOrKeys],
|
|
@@ -4985,7 +5810,7 @@ function createStore(initialState, extend) {
|
|
|
4985
5810
|
reset: /* @__PURE__ */ __name(() => replaceState2(cloneState(initialSnapshot)), "reset"),
|
|
4986
5811
|
subscribe: subscribeState
|
|
4987
5812
|
};
|
|
4988
|
-
for (const key of
|
|
5813
|
+
for (const key of getEnumerableKeys(initialSnapshot)) {
|
|
4989
5814
|
if (RESERVED_STORE_KEYS.has(key)) {
|
|
4990
5815
|
throw new Error(
|
|
4991
5816
|
`createStore does not allow the reserved key "${String(key)}" in the initial state.`
|
|
@@ -6679,7 +7504,9 @@ var _SPARouter = class _SPARouter {
|
|
|
6679
7504
|
if (this.onNavigate) {
|
|
6680
7505
|
await this.onNavigate(pageData);
|
|
6681
7506
|
}
|
|
6682
|
-
if (
|
|
7507
|
+
if (window.location.hash) {
|
|
7508
|
+
getHashTargetElement(window.location.hash)?.scrollIntoView();
|
|
7509
|
+
} else if (this.options.scrollRestoration) {
|
|
6683
7510
|
this.restoreScrollPosition(window.location.pathname + window.location.search);
|
|
6684
7511
|
}
|
|
6685
7512
|
if (clientNavigation) {
|
|
@@ -7768,7 +8595,7 @@ body {
|
|
|
7768
8595
|
`;
|
|
7769
8596
|
|
|
7770
8597
|
// package.json
|
|
7771
|
-
var version = "0.1.0-beta.
|
|
8598
|
+
var version = "0.1.0-beta.97";
|
|
7772
8599
|
|
|
7773
8600
|
// src/version.ts
|
|
7774
8601
|
var FARM_VERSION = version;
|
|
@@ -9069,11 +9896,15 @@ __name(isObject, "isObject");
|
|
|
9069
9896
|
// Annotate the CommonJS export names for ESM import in node:
|
|
9070
9897
|
0 && (module.exports = {
|
|
9071
9898
|
APIClientError,
|
|
9899
|
+
FARM_CACHE_INVALIDATION_CHANNEL,
|
|
9900
|
+
FARM_CLIENT_CACHE_PERSIST_VERSION,
|
|
9072
9901
|
FarmClientPluginManager,
|
|
9902
|
+
FetcherInputError,
|
|
9073
9903
|
IntegrationClientError,
|
|
9074
9904
|
Link,
|
|
9075
9905
|
SPARouter,
|
|
9076
9906
|
api,
|
|
9907
|
+
clearPersistedCache,
|
|
9077
9908
|
createAPIClient,
|
|
9078
9909
|
createApiClients,
|
|
9079
9910
|
createClientPluginManager,
|
|
@@ -9084,13 +9915,16 @@ __name(isObject, "isObject");
|
|
|
9084
9915
|
createIntegrations,
|
|
9085
9916
|
createServerAPIClient,
|
|
9086
9917
|
createStore,
|
|
9918
|
+
defineClientCacheAdapter,
|
|
9087
9919
|
defineIntegrationAPI,
|
|
9088
9920
|
defineIntegrationAPIOperation,
|
|
9921
|
+
enableCrossTabCacheInvalidation,
|
|
9089
9922
|
endpoint,
|
|
9090
9923
|
fetchServerQuery,
|
|
9091
9924
|
getIntegrationAPIManifest,
|
|
9092
9925
|
getRouter,
|
|
9093
9926
|
getTheme,
|
|
9927
|
+
initPersistedClientCache,
|
|
9094
9928
|
installChunkErrorRecovery,
|
|
9095
9929
|
integrationClients,
|
|
9096
9930
|
integrationsClient,
|
|
@@ -9103,6 +9937,7 @@ __name(isObject, "isObject");
|
|
|
9103
9937
|
readPageState,
|
|
9104
9938
|
replaceState,
|
|
9105
9939
|
setTheme,
|
|
9940
|
+
storageClientCacheAdapter,
|
|
9106
9941
|
toggleTheme,
|
|
9107
9942
|
useAction,
|
|
9108
9943
|
useBlocker,
|