@fulgurjs/federation 5.2.5 → 5.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (101) hide show
  1. package/CHANGELOG.md +14 -0
  2. package/DESIGN.md +7 -0
  3. package/README.en.md +86 -4
  4. package/README.md +125 -3
  5. package/dist/bridge-app-react.cjs +185 -0
  6. package/dist/bridge-app-react.d.cts +37 -0
  7. package/dist/bridge-app-react.d.ts +37 -0
  8. package/dist/bridge-app-react.js +115 -0
  9. package/dist/bridge-app-vue.cjs +111 -0
  10. package/dist/bridge-app-vue.d.cts +34 -0
  11. package/dist/bridge-app-vue.d.ts +34 -0
  12. package/dist/bridge-app-vue.js +51 -0
  13. package/dist/bridge-core-6uLJiMVa.d.ts +42 -0
  14. package/dist/bridge-core.cjs +224 -0
  15. package/dist/bridge-core.d.cts +51 -0
  16. package/dist/bridge-core.d.ts +51 -0
  17. package/dist/bridge-core.js +21 -0
  18. package/dist/bridge-errors.cjs +114 -0
  19. package/dist/bridge-errors.d.cts +36 -0
  20. package/dist/bridge-errors.d.ts +36 -0
  21. package/dist/bridge-errors.js +15 -0
  22. package/dist/bridge-host-react-C55RmGll.d.ts +35 -0
  23. package/dist/bridge-host-react.cjs +392 -0
  24. package/dist/bridge-host-react.d.cts +45 -0
  25. package/dist/bridge-host-react.d.ts +45 -0
  26. package/dist/bridge-host-react.js +183 -0
  27. package/dist/bridge-host-vue-BAxDKqGH.d.ts +32 -0
  28. package/dist/bridge-host-vue.cjs +426 -0
  29. package/dist/bridge-host-vue.d.cts +39 -0
  30. package/dist/bridge-host-vue.d.ts +39 -0
  31. package/dist/bridge-host-vue.js +211 -0
  32. package/dist/bridge-react.d.ts +12 -0
  33. package/dist/bridge-react.js +3 -0
  34. package/dist/bridge-vue.d.ts +8 -0
  35. package/dist/bridge-vue.js +3 -0
  36. package/dist/bridge.d.ts +16 -0
  37. package/dist/bridge.js +5 -0
  38. package/dist/chunk-E55P4TIY.js +76 -0
  39. package/dist/chunk-EH34L46P.js +207 -0
  40. package/dist/chunk-FVYGSLAQ.js +179 -0
  41. package/dist/chunk-LWJBHUJQ.js +114 -0
  42. package/dist/chunk-OF2JCXTZ.js +15 -0
  43. package/dist/chunk-TSYLDY6H.js +64 -0
  44. package/dist/chunk-UJFCPQGN.js +1210 -0
  45. package/dist/context.js +8 -64
  46. package/dist/index.cjs +84 -8
  47. package/dist/index.js +84 -8
  48. package/dist/react.d.ts +44 -2
  49. package/dist/react.js +2 -0
  50. package/dist/runtime-entry.d.ts +41 -2
  51. package/dist/runtime-entry.js +1 -1
  52. package/dist/runtime.js +1 -1
  53. package/dist/vue.js +2 -0
  54. package/docs/webpack-mf-/345/257/271/347/205/247/344/270/216/347/274/272/345/217/243.md +1 -1
  55. package/docs//350/277/201/347/247/273/346/214/207/345/215/227.md +1 -1
  56. package/examples/README.en.md +20 -0
  57. package/examples/README.md +20 -0
  58. package/examples/bridge/README.md +36 -0
  59. package/examples/bridge/react-host/README.md +23 -0
  60. package/examples/bridge/react-host/fulgurjs.config.ts +20 -0
  61. package/examples/bridge/react-host/index.html +11 -0
  62. package/examples/bridge/react-host/package-lock.json +2457 -0
  63. package/examples/bridge/react-host/package.json +24 -0
  64. package/examples/bridge/react-host/src/env.d.ts +7 -0
  65. package/examples/bridge/react-host/src/host-session.ts +26 -0
  66. package/examples/bridge/react-host/src/main.tsx +62 -0
  67. package/examples/bridge/react-host/tsconfig.json +13 -0
  68. package/examples/bridge/react-host/vite.config.ts +9 -0
  69. package/examples/bridge/react-remote/README.md +20 -0
  70. package/examples/bridge/react-remote/fulgurjs.config.ts +17 -0
  71. package/examples/bridge/react-remote/index.html +11 -0
  72. package/examples/bridge/react-remote/package-lock.json +2382 -0
  73. package/examples/bridge/react-remote/package.json +24 -0
  74. package/examples/bridge/react-remote/src/bridge.tsx +66 -0
  75. package/examples/bridge/react-remote/src/env.d.ts +7 -0
  76. package/examples/bridge/react-remote/src/main.tsx +7 -0
  77. package/examples/bridge/react-remote/tsconfig.json +13 -0
  78. package/examples/bridge/react-remote/vite.config.ts +9 -0
  79. package/examples/bridge/vue-host/README.md +24 -0
  80. package/examples/bridge/vue-host/fulgurjs.config.ts +22 -0
  81. package/examples/bridge/vue-host/index.html +11 -0
  82. package/examples/bridge/vue-host/package-lock.json +1885 -0
  83. package/examples/bridge/vue-host/package.json +24 -0
  84. package/examples/bridge/vue-host/src/App.vue +70 -0
  85. package/examples/bridge/vue-host/src/env.d.ts +7 -0
  86. package/examples/bridge/vue-host/src/host-session.ts +29 -0
  87. package/examples/bridge/vue-host/src/main.ts +4 -0
  88. package/examples/bridge/vue-host/tsconfig.json +13 -0
  89. package/examples/bridge/vue-host/vite.config.ts +9 -0
  90. package/examples/bridge/vue-remote/README.md +19 -0
  91. package/examples/bridge/vue-remote/fulgurjs.config.ts +16 -0
  92. package/examples/bridge/vue-remote/index.html +11 -0
  93. package/examples/bridge/vue-remote/package-lock.json +1856 -0
  94. package/examples/bridge/vue-remote/package.json +21 -0
  95. package/examples/bridge/vue-remote/src/App.vue +12 -0
  96. package/examples/bridge/vue-remote/src/bridge.ts +57 -0
  97. package/examples/bridge/vue-remote/src/env.d.ts +7 -0
  98. package/examples/bridge/vue-remote/src/main.ts +15 -0
  99. package/examples/bridge/vue-remote/tsconfig.json +13 -0
  100. package/examples/bridge/vue-remote/vite.config.ts +9 -0
  101. package/package.json +43 -2
@@ -0,0 +1,51 @@
1
+ import { AppContext } from './context.js';
2
+
3
+ /** 子应用桥接契约(远程 ./bridge 模块的默认导出;任务书 §3.2) */
4
+ interface BridgeApp {
5
+ /** 首次根提交完成时才算挂载成功;同一容器未卸载前重复 mount 是契约违例 */
6
+ mount(el: HTMLElement, props?: Record<string, unknown>): void | Promise<void>;
7
+ /** 同步使当前挂载代次失效并清理已创建的 root;未知容器为 no-op */
8
+ unmount(el: HTMLElement): void;
9
+ }
10
+ /** 远程模块 → 契约校验(默认导出须含函数类型的 mount/unmount,否则 MFU-015) */
11
+ declare function assertBridgeContract(spec: string, mod: unknown): BridgeApp;
12
+ /**
13
+ * 登记一个受控会话代次;页面已有不同 sessionKey 的活跃桥接实例时拒绝(MFU-017)。
14
+ * 同一会话的多实例并存合法(计数递增)。
15
+ */
16
+ declare function acquireBridgeSession(spec: string, sessionKey: string): void;
17
+ /** 释放一个受控会话代次(unmount/换代/失败清理时调用;幂等) */
18
+ declare function releaseBridgeSession(sessionKey: string): void;
19
+ interface BridgeContextResolution {
20
+ /** 校验通过后需要由桥接层写入全局的快照;undefined = 复用现有 AppContext,无需写入 */
21
+ provide?: Partial<AppContext> & Record<string, unknown>;
22
+ }
23
+ /**
24
+ * 挂载前校验会话与上下文快照(同步、无副作用;只在全部通过后由调用方 provide)。
25
+ *
26
+ * - getter 抛错/返回非对象/thenable → MFU-016(phase: getContext);
27
+ * - 受控 sessionKey 与快照或现有 AppContext 不一致 → MFU-017(不写任何全局状态);
28
+ * - 新会话(与全局当前 sessionKey 不同)先 clearAppContext 清旧账号残留,
29
+ * 避免 provideAppContext 顶层 merge 留下旧账号独有字段(BR06)。
30
+ *
31
+ * 会话登记(acquireBridgeSession/releaseBridgeSession)由宿主适配器在代次边界管理,
32
+ * 本函数不重复登记——重试同会话不得叠加计数。
33
+ *
34
+ * controlled 语义:非空字符串 = 受控校验;undefined = 不启用受控校验(快照照常提供,
35
+ * 远程 onSession 由 runtime 按 AppContext.sessionKey 判定);null 由调用方先行短路。
36
+ */
37
+ declare function resolveBridgeContext(spec: string, controlled: string | undefined, getContext: (() => Partial<AppContext> & Record<string, unknown>) | undefined): BridgeContextResolution;
38
+ /** 受控 sessionKey 受控值合法性:只接受 undefined / null / 非空字符串(任务书 BN10) */
39
+ declare function assertControlledSessionKey(spec: string, value: unknown): void;
40
+ /** 适配层参数校验(与 vue/react 适配器同口径:retries 0-10 整数、timeout 正有限数) */
41
+ declare function assertBridgeOptions(source: string, opts: {
42
+ retries?: number;
43
+ timeout?: number;
44
+ }): void;
45
+ /**
46
+ * 桥接加载等待上限(与 React remoteComponent.timeout 同语义):
47
+ * 只结束本次等待,不取消已发出的共享 loadRemote 请求;迟到的成功/失败一律丢弃。
48
+ */
49
+ declare function withBridgeTimeout<T>(p: Promise<T>, ms: number, spec: string): Promise<T>;
50
+
51
+ export { type BridgeApp, type BridgeContextResolution, acquireBridgeSession, assertBridgeContract, assertBridgeOptions, assertControlledSessionKey, releaseBridgeSession, resolveBridgeContext, withBridgeTimeout };
@@ -0,0 +1,21 @@
1
+ import {
2
+ acquireBridgeSession,
3
+ assertBridgeContract,
4
+ assertBridgeOptions,
5
+ assertControlledSessionKey,
6
+ releaseBridgeSession,
7
+ resolveBridgeContext,
8
+ withBridgeTimeout
9
+ } from "./chunk-LWJBHUJQ.js";
10
+ import "./chunk-E55P4TIY.js";
11
+ import "./chunk-TSYLDY6H.js";
12
+ import "./chunk-OF2JCXTZ.js";
13
+ export {
14
+ acquireBridgeSession,
15
+ assertBridgeContract,
16
+ assertBridgeOptions,
17
+ assertControlledSessionKey,
18
+ releaseBridgeSession,
19
+ resolveBridgeContext,
20
+ withBridgeTimeout
21
+ };
@@ -0,0 +1,114 @@
1
+ "use strict";
2
+ var __defProp = Object.defineProperty;
3
+ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
4
+ var __getOwnPropNames = Object.getOwnPropertyNames;
5
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
6
+ var __export = (target, all) => {
7
+ for (var name in all)
8
+ __defProp(target, name, { get: all[name], enumerable: true });
9
+ };
10
+ var __copyProps = (to, from, except, desc) => {
11
+ if (from && typeof from === "object" || typeof from === "function") {
12
+ for (let key of __getOwnPropNames(from))
13
+ if (!__hasOwnProp.call(to, key) && key !== except)
14
+ __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
15
+ }
16
+ return to;
17
+ };
18
+ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
19
+
20
+ // src/bridge-errors.ts
21
+ var bridge_errors_exports = {};
22
+ __export(bridge_errors_exports, {
23
+ BridgeErrorCodes: () => BridgeErrorCodes,
24
+ bridgeLifecycleError: () => bridgeLifecycleError,
25
+ bridgeSessionMismatchError: () => bridgeSessionMismatchError,
26
+ invalidBridgeContractError: () => invalidBridgeContractError,
27
+ invalidSessionKeyError: () => invalidSessionKeyError
28
+ });
29
+ module.exports = __toCommonJS(bridge_errors_exports);
30
+
31
+ // src/runtime/errors.ts
32
+ var FgError = class extends Error {
33
+ code;
34
+ details;
35
+ constructor(code, message, details, options) {
36
+ super(`[fulgurjs:${code}] ${message}`, options);
37
+ this.name = "FgError";
38
+ this.code = code;
39
+ this.details = details;
40
+ }
41
+ };
42
+
43
+ // src/bridge-errors.ts
44
+ var BridgeErrorCodes = {
45
+ /** 桥接契约非法(./bridge 默认导出缺 mount/unmount 或不是函数) */
46
+ BRIDGE_INVALID_CONTRACT: "MFU-015",
47
+ /** 桥接准备或生命周期失败(details.phase = getContext | mount | unmount) */
48
+ BRIDGE_LIFECYCLE_FAILED: "MFU-016",
49
+ /** 桥接会话参数与 AppContext 不一致(受控 sessionKey 与全局会话矛盾) */
50
+ BRIDGE_SESSION_MISMATCH: "MFU-017"
51
+ };
52
+ function invalidBridgeContractError(spec, mod) {
53
+ const actual = mod === null ? "null" : typeof mod;
54
+ const missing = [];
55
+ if (typeof mod?.mount !== "function") missing.push("mount");
56
+ if (typeof mod?.unmount !== "function") missing.push("unmount");
57
+ return new FgError(
58
+ BridgeErrorCodes.BRIDGE_INVALID_CONTRACT,
59
+ `\u73B0\u8C61\uFF1A\u8FDC\u7A0B\u6A21\u5757 "${spec}" \u7684\u9ED8\u8BA4\u5BFC\u51FA\u4E0D\u662F\u5408\u6CD5\u7684\u6865\u63A5\u5951\u7EA6\uFF08BridgeApp\uFF09\u3002
60
+ \u6839\u56E0: \u5BFC\u51FA\u503C\u4E3A ${actual}` + (missing.length ? `\uFF0C\u7F3A\u5C11\u51FD\u6570\u7C7B\u578B\u7684 ${missing.map((m) => `"${m}"`).join(" / ")} \u5BFC\u51FA\u3002` : "\u3002") + `
61
+ \u4FEE\u6CD5: \u8FDC\u7A0B\u4FA7\u7528 defineBridgeApp(...) \u521B\u5EFA\u5951\u7EA6\u5E76\u4F5C\u4E3A\u6A21\u5757\u9ED8\u8BA4\u5BFC\u51FA\u2014\u2014
62
+ Vue \u5B50\u5E94\u7528: import { defineBridgeApp } from '@fulgurjs/federation/runtime'\uFF1B
63
+ React \u5B50\u5E94\u7528: import { defineBridgeApp } from '@fulgurjs/federation/react'\u3002
64
+ \u5951\u7EA6\u5FC5\u987B\u5305\u542B mount(el, props?) \u4E0E unmount(el) \u4E24\u4E2A\u51FD\u6570\u3002`,
65
+ { spec, missing, actual }
66
+ );
67
+ }
68
+ function bridgeLifecycleError(phase, spec, cause, extra) {
69
+ const raw = cause instanceof Error ? cause.message : String(cause ?? "unknown");
70
+ const fixes = {
71
+ getContext: "\u4FEE\u6CD5: \u2460 getContext \u5FC5\u987B\u662F\u540C\u6B65\u3001\u65E0\u526F\u4F5C\u7528\u7684 getter\uFF08\u4E0D\u5F97\u8FD4\u56DE Promise/thenable\uFF09\uFF1B\n \u2461 \u8FD4\u56DE\u503C\u987B\u662F\u5305\u542B\u672C\u6B21\u4F1A\u8BDD\u5FEB\u7167\u7684\u5BF9\u8C61\uFF08\u53D7\u63A7 sessionKey \u65F6\u987B\u542B\u76F8\u540C sessionKey\uFF09\uFF1B\n \u2462 \u5F02\u6B65\u83B7\u53D6\u7528\u6237\u8D44\u6599\u8BF7\u5728\u5BBF\u4E3B\u5B8C\u6210\u540E\u518D\u8BA9\u6865\u63A5\u7EC4\u4EF6\u8FDB\u5165\u53EF\u6302\u8F7D\u72B6\u6001\u3002",
72
+ mount: "\u4FEE\u6CD5: \u2460 \u67E5\u770B\u6839\u56E0\u4E2D\u5B50\u5E94\u7528 mount \u7684\u539F\u59CB\u9519\u8BEF\uFF08\u5DE5\u5382\u629B\u9519\u6216\u9996\u6B21\u6E32\u67D3\u5931\u8D25\uFF09\uFF1B\n \u2461 \u540C\u4E00\u5BB9\u5668\u672A\u5378\u8F7D\u524D\u91CD\u590D mount \u662F\u5951\u7EA6\u8FDD\u4F8B\u2014\u2014\u5148 unmount \u518D mount\uFF1B\n \u2462 \u4FEE\u590D\u540E\u70B9\u51FB\u300C\u91CD\u8BD5\u52A0\u8F7D\u300D\u5728\u540C\u9875\u91CD\u5EFA\u6302\u8F7D\u3002",
73
+ unmount: "\u4FEE\u6CD5: \u2460 \u6839\u56E0\u6765\u81EA\u5B50\u5E94\u7528 unmount \u5B9E\u73B0\uFF08app.unmount/root.unmount \u629B\u9519\uFF09\uFF1B\n \u2461 \u8BE5\u5BB9\u5668\u6E05\u7406\u72B6\u6001\u4E0D\u786E\u5B9A\u2014\u2014\u4E0D\u8981\u76F4\u63A5\u5728\u540C\u4E00 el \u4E0A\u542F\u52A8\u65B0\u5B9E\u4F8B\uFF1B\n \u2462 \u5237\u65B0\u9875\u9762\u53EF\u5F7B\u5E95\u6E05\u7406\uFF0C\u6B8B\u7559\u8D44\u6E90\u8BF7\u5982\u5B9E\u6392\u67E5\uFF08\u4E8B\u4EF6\u8BA2\u9605/\u5B9A\u65F6\u5668/\u5168\u5C40\u526F\u4F5C\u7528\uFF09\u3002"
74
+ };
75
+ return new FgError(
76
+ BridgeErrorCodes.BRIDGE_LIFECYCLE_FAILED,
77
+ `\u73B0\u8C61\uFF1A\u6865\u63A5\u5E94\u7528 "${spec}" \u7684 ${phase} \u9636\u6BB5\u5931\u8D25\u3002
78
+ \u6839\u56E0: ${raw}
79
+ ` + fixes[phase],
80
+ { phase, spec, cause: String(raw), ...extra },
81
+ { cause }
82
+ );
83
+ }
84
+ function bridgeSessionMismatchError(spec, controlled, actual, extra) {
85
+ const actualText = actual === void 0 ? "undefined\uFF08\u9875\u9762\u5C1A\u65E0 AppContext\uFF09" : typeof actual === "string" ? `"${actual}"` : String(actual);
86
+ return new FgError(
87
+ BridgeErrorCodes.BRIDGE_SESSION_MISMATCH,
88
+ `\u73B0\u8C61\uFF1A\u6865\u63A5\u5E94\u7528 "${spec}" \u7684\u53D7\u63A7 sessionKey\uFF08"${controlled}"\uFF09\u4E0E\u5F53\u524D\u4F1A\u8BDD\u4E0D\u4E00\u81F4\uFF08\u5F53\u524D ${actualText}\uFF09\u3002
89
+ \u6839\u56E0: AppContext \u662F\u9875\u9762\u7EA7\u5355\u4F8B\uFF0C\u540C\u9875\u6240\u6709\u6865\u63A5\u5B9E\u4F8B\u5FC5\u987B\u4F7F\u7528\u540C\u4E00\u767B\u5F55\u4EE3\u6B21\uFF1B
90
+ getContext \u5FEB\u7167\u7684 sessionKey\uFF08\u6216\u73B0\u6709 AppContext \u7684 sessionKey\uFF09\u4E0E\u53D7\u63A7\u503C\u4E0D\u540C\u3002
91
+ \u4FEE\u6CD5: \u2460 \u6362\u8D26\u53F7\u65F6\u5148\u8BA9\u53D7\u63A7 prop \u7F6E null \u5E76\u7B49\u5F85\u5378\u8F7D\uFF0C\u518D clearAppContext() \u6E05\u65E7\u8D26\u53F7\u3001
92
+ \u51C6\u5907\u65B0\u8D26\u53F7\u5B8C\u6574\u5FEB\u7167\u540E\u66F4\u65B0\u53D7\u63A7 prop\uFF1B
93
+ \u2461 \u65E0 getContext \u65F6\uFF0C\u5148\u7531\u5BBF\u4E3B\u6865 provideAppContext({...\u65B0\u4F1A\u8BDD, sessionKey}) \u518D\u6302\u8F7D\uFF1B
94
+ \u2462 \u540C\u9875\u4E0D\u8981\u540C\u65F6\u6302\u8F7D\u4E0D\u540C\u8D26\u53F7\u7684\u6865\u63A5\u5B9E\u4F8B\uFF08\u9875\u9762\u7EA7\u5355\u4F1A\u8BDD\u7EA6\u675F\uFF09\u3002`,
95
+ { spec, controlled, actual: String(actual), ...extra }
96
+ );
97
+ }
98
+ function invalidSessionKeyError(spec, value) {
99
+ return new FgError(
100
+ BridgeErrorCodes.BRIDGE_SESSION_MISMATCH,
101
+ `\u73B0\u8C61\uFF1A\u6865\u63A5\u5E94\u7528 "${spec}" \u6536\u5230\u975E\u6CD5\u7684\u53D7\u63A7 sessionKey\uFF1A${typeof value === "string" ? '\u7A7A\u5B57\u7B26\u4E32 ""' : `${typeof value}\uFF08${String(value)}\uFF09`}\u3002
102
+ \u6839\u56E0: sessionKey \u53EA\u63A5\u53D7 undefined\uFF08\u4E0D\u542F\u7528\u53D7\u63A7\u4F1A\u8BDD\uFF09\u3001null\uFF08\u767B\u51FA\u6001\uFF09\u6216\u975E\u7A7A\u5B57\u7B26\u4E32\uFF08\u767B\u5F55\u4EE3\u6B21 ID\uFF09\u3002
103
+ \u4FEE\u6CD5: \u767B\u51FA\u4F20 null \u800C\u4E0D\u662F\u7A7A\u5B57\u7B26\u4E32\uFF1B\u767B\u5F55\u4EE3\u6B21\u7528\u975E\u7A7A\u5B57\u7B26\u4E32\uFF1B\u4E0D\u8981\u4F20\u6570\u5B57/\u5E03\u5C14\u7B49\u5176\u4ED6\u7C7B\u578B\u3002`,
104
+ { spec, value: String(value) }
105
+ );
106
+ }
107
+ // Annotate the CommonJS export names for ESM import in node:
108
+ 0 && (module.exports = {
109
+ BridgeErrorCodes,
110
+ bridgeLifecycleError,
111
+ bridgeSessionMismatchError,
112
+ invalidBridgeContractError,
113
+ invalidSessionKeyError
114
+ });
@@ -0,0 +1,36 @@
1
+ /** 统一错误码体系(对齐 webpack ScriptExternalLoadError 等运行时错误的可诊断性) */
2
+ declare class FgError extends Error {
3
+ code: string;
4
+ details?: Record<string, unknown>;
5
+ constructor(code: string, message: string, details?: Record<string, unknown>, options?: ErrorOptions);
6
+ }
7
+
8
+ /**
9
+ * 桥接层错误码表(MFU-015/016/017,任务书 D3)。
10
+ *
11
+ * 与 runtime.js 解耦:桥接专用分支不进内核 bundle(runtime 内核零改动为首选目标);
12
+ * 码值登记于 src/diagnostics.ts 的 CODE_REGISTRY,由 scripts/check-manual-codes.mjs
13
+ * 做「源码定义 ⊆ 登记表 = README 错误码总表」三方一致性校验。
14
+ * 三段式口径与 runtime/context 一致:现象 → 根因 → 修法。
15
+ */
16
+
17
+ declare const BridgeErrorCodes: {
18
+ /** 桥接契约非法(./bridge 默认导出缺 mount/unmount 或不是函数) */
19
+ readonly BRIDGE_INVALID_CONTRACT: "MFU-015";
20
+ /** 桥接准备或生命周期失败(details.phase = getContext | mount | unmount) */
21
+ readonly BRIDGE_LIFECYCLE_FAILED: "MFU-016";
22
+ /** 桥接会话参数与 AppContext 不一致(受控 sessionKey 与全局会话矛盾) */
23
+ readonly BRIDGE_SESSION_MISMATCH: "MFU-017";
24
+ };
25
+ /** 桥接生命周期阶段(MFU-016 details.phase 取值) */
26
+ type BridgePhase = 'getContext' | 'mount' | 'unmount';
27
+ /** MFU-015:远程 ./bridge 默认导出不是合法契约对象 */
28
+ declare function invalidBridgeContractError(spec: string, mod: unknown): FgError;
29
+ /** MFU-016:桥接准备(getContext)或生命周期(mount/unmount)失败;cause 保留原始错误 */
30
+ declare function bridgeLifecycleError(phase: BridgePhase, spec: string, cause: unknown, extra?: Record<string, unknown>): FgError;
31
+ /** MFU-017:受控 sessionKey 与当前 AppContext / 活跃桥接会话不一致 */
32
+ declare function bridgeSessionMismatchError(spec: string, controlled: string, actual: unknown, extra?: Record<string, unknown>): FgError;
33
+ /** MFU-017:受控 sessionKey 值本身非法(空字符串/数字等,非 undefined/null/非空字符串) */
34
+ declare function invalidSessionKeyError(spec: string, value: unknown): FgError;
35
+
36
+ export { BridgeErrorCodes, type BridgePhase, bridgeLifecycleError, bridgeSessionMismatchError, invalidBridgeContractError, invalidSessionKeyError };
@@ -0,0 +1,36 @@
1
+ /** 统一错误码体系(对齐 webpack ScriptExternalLoadError 等运行时错误的可诊断性) */
2
+ declare class FgError extends Error {
3
+ code: string;
4
+ details?: Record<string, unknown>;
5
+ constructor(code: string, message: string, details?: Record<string, unknown>, options?: ErrorOptions);
6
+ }
7
+
8
+ /**
9
+ * 桥接层错误码表(MFU-015/016/017,任务书 D3)。
10
+ *
11
+ * 与 runtime.js 解耦:桥接专用分支不进内核 bundle(runtime 内核零改动为首选目标);
12
+ * 码值登记于 src/diagnostics.ts 的 CODE_REGISTRY,由 scripts/check-manual-codes.mjs
13
+ * 做「源码定义 ⊆ 登记表 = README 错误码总表」三方一致性校验。
14
+ * 三段式口径与 runtime/context 一致:现象 → 根因 → 修法。
15
+ */
16
+
17
+ declare const BridgeErrorCodes: {
18
+ /** 桥接契约非法(./bridge 默认导出缺 mount/unmount 或不是函数) */
19
+ readonly BRIDGE_INVALID_CONTRACT: "MFU-015";
20
+ /** 桥接准备或生命周期失败(details.phase = getContext | mount | unmount) */
21
+ readonly BRIDGE_LIFECYCLE_FAILED: "MFU-016";
22
+ /** 桥接会话参数与 AppContext 不一致(受控 sessionKey 与全局会话矛盾) */
23
+ readonly BRIDGE_SESSION_MISMATCH: "MFU-017";
24
+ };
25
+ /** 桥接生命周期阶段(MFU-016 details.phase 取值) */
26
+ type BridgePhase = 'getContext' | 'mount' | 'unmount';
27
+ /** MFU-015:远程 ./bridge 默认导出不是合法契约对象 */
28
+ declare function invalidBridgeContractError(spec: string, mod: unknown): FgError;
29
+ /** MFU-016:桥接准备(getContext)或生命周期(mount/unmount)失败;cause 保留原始错误 */
30
+ declare function bridgeLifecycleError(phase: BridgePhase, spec: string, cause: unknown, extra?: Record<string, unknown>): FgError;
31
+ /** MFU-017:受控 sessionKey 与当前 AppContext / 活跃桥接会话不一致 */
32
+ declare function bridgeSessionMismatchError(spec: string, controlled: string, actual: unknown, extra?: Record<string, unknown>): FgError;
33
+ /** MFU-017:受控 sessionKey 值本身非法(空字符串/数字等,非 undefined/null/非空字符串) */
34
+ declare function invalidSessionKeyError(spec: string, value: unknown): FgError;
35
+
36
+ export { BridgeErrorCodes, type BridgePhase, bridgeLifecycleError, bridgeSessionMismatchError, invalidBridgeContractError, invalidSessionKeyError };
@@ -0,0 +1,15 @@
1
+ import {
2
+ BridgeErrorCodes,
3
+ bridgeLifecycleError,
4
+ bridgeSessionMismatchError,
5
+ invalidBridgeContractError,
6
+ invalidSessionKeyError
7
+ } from "./chunk-E55P4TIY.js";
8
+ import "./chunk-OF2JCXTZ.js";
9
+ export {
10
+ BridgeErrorCodes,
11
+ bridgeLifecycleError,
12
+ bridgeSessionMismatchError,
13
+ invalidBridgeContractError,
14
+ invalidSessionKeyError
15
+ };
@@ -0,0 +1,35 @@
1
+ import { ReactNode } from 'react';
2
+ import { A as AppContext } from './bridge-core-6uLJiMVa.js';
3
+
4
+ /**
5
+ * React 宿主桥接工厂(/bridge、/bridge/react 导出 createReactBridgeApp;任务书 §3.4)。
6
+ *
7
+ * 定位:接收注入的 loadRemote(不静态引用运行时内核,dist 壳绑定),返回
8
+ * `ComponentType<{ appProps: P; sessionKey?: string | null }>`,负责:
9
+ * - DOM 所有权(§4.5):只创建并保持稳定的空挂载 el(fragment 的固定子节点);
10
+ * pending/error 占位是它的兄弟节点,宿主重渲染不 patch 子应用 root 内部;
11
+ * - 会话代次(§4.3):受控 sessionKey 驱动 挂载/换会话/登出;同会话重渲染不重挂;
12
+ * - StrictMode 安全(§4.5):双 effect 走 cleanup(作废+卸载)→setup(新代次) 顺序,
13
+ * 顺序 unmount/mount 不产生双实例或残留;
14
+ * - unmount 抛错(BN09):报告 MFU-016(phase: unmount)并封锁该容器的新挂载。
15
+ *
16
+ * appProps 是挂载时浅拷贝快照(顶层替换不追踪,重挂由 key 重建);sessionKey
17
+ * 是桥接控制参数,不混入业务 props。
18
+ */
19
+
20
+ /** 渲染函数形态的错误占位:(error, retry) => ReactNode */
21
+ type BridgeErrorFallback = (error: unknown, retry: () => void) => ReactNode;
22
+ interface ReactBridgeAppOptions {
23
+ /** 加载 pending 占位(默认 null) */
24
+ fallback?: ReactNode;
25
+ /** 加载/挂载失败占位;默认内置中文诊断 + 「重试加载 / 刷新页面重试」 */
26
+ error?: ReactNode | BridgeErrorFallback;
27
+ /** 透传现行 loadRemote 的重试选项(0-10 整数),不另叠自动重试 */
28
+ retries?: number;
29
+ /** 本次桥接加载等待上限 ms;不取消已发出的共享请求,迟到结果一律丢弃 */
30
+ timeout?: number;
31
+ /** 无副作用的同步 getter:首次、重试及换会话的实际加载前返回本次所需上下文快照 */
32
+ getContext?: () => Partial<AppContext> & Record<string, unknown>;
33
+ }
34
+
35
+ export type { BridgeErrorFallback as B, ReactBridgeAppOptions as R };