@nocobase/flow-engine 2.0.0-beta.17 → 2.0.0-beta.19

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.
@@ -78,6 +78,7 @@ var import_registry = require("./runjs-context/registry");
78
78
  var import_createEphemeralContext = require("./utils/createEphemeralContext");
79
79
  var import_dayjs = __toESM(require("dayjs"));
80
80
  var import_runjsLibs = require("./runjsLibs");
81
+ var import_runjsModuleLoader = require("./utils/runjsModuleLoader");
81
82
  var _proxy, _FlowContext_instances, createChildNodes_fn, findMetaByPath_fn, findMetaInDelegatesDeep_fn, findMetaInProperty_fn, resolvePathInMeta_fn, resolvePathInMetaAsync_fn, buildParentTitles_fn, toTreeNode_fn;
82
83
  function isRecordRefLike(val) {
83
84
  return !!(val && typeof val === "object" && "collection" in val && "filterByTk" in val);
@@ -1003,7 +1004,8 @@ const _FlowEngineContext = class _FlowEngineContext extends BaseFlowEngineContex
1003
1004
  user: this.user
1004
1005
  }), "get")
1005
1006
  });
1006
- this.defineMethod("loadCSS", async (url) => {
1007
+ this.defineMethod("loadCSS", async (href) => {
1008
+ const url = (0, import_utils.resolveModuleUrl)(href);
1007
1009
  return new Promise((resolve, reject) => {
1008
1010
  const existingLink = document.querySelector(`link[href="${url}"]`);
1009
1011
  if (existingLink) {
@@ -1019,51 +1021,14 @@ const _FlowEngineContext = class _FlowEngineContext extends BaseFlowEngineContex
1019
1021
  });
1020
1022
  });
1021
1023
  this.defineMethod("requireAsync", async (url) => {
1022
- return new Promise((resolve, reject) => {
1023
- if (!this.requirejs) {
1024
- reject(new Error("requirejs is not available"));
1025
- return;
1026
- }
1027
- this.requirejs(
1028
- [url],
1029
- (...args) => {
1030
- resolve(args[0]);
1031
- },
1032
- reject
1033
- );
1034
- });
1024
+ const u = (0, import_utils.resolveModuleUrl)(url, { raw: true });
1025
+ return await (0, import_runjsModuleLoader.runjsRequireAsync)(this.requirejs, u);
1035
1026
  });
1036
- this.defineMethod("importAsync", async (url) => {
1037
- if (!url || typeof url !== "string") {
1038
- throw new Error("invalid url");
1027
+ this.defineMethod("importAsync", async function(url) {
1028
+ if ((0, import_utils.isCssFile)(url)) {
1029
+ return this.loadCSS(url);
1039
1030
  }
1040
- const u = url.trim();
1041
- const g = globalThis;
1042
- g.__nocobaseImportAsyncCache = g.__nocobaseImportAsyncCache || /* @__PURE__ */ new Map();
1043
- const cache = g.__nocobaseImportAsyncCache;
1044
- if (cache.has(u)) return cache.get(u);
1045
- const nativeImport = /* @__PURE__ */ __name(() => import(
1046
- /* @vite-ignore */
1047
- /* webpackIgnore: true */
1048
- u
1049
- ), "nativeImport");
1050
- const evalImport = /* @__PURE__ */ __name(() => {
1051
- const importer = (0, eval)("u => import(u)");
1052
- return importer(u);
1053
- }, "evalImport");
1054
- const p = (async () => {
1055
- try {
1056
- return await nativeImport();
1057
- } catch (err) {
1058
- try {
1059
- return await evalImport();
1060
- } catch (err2) {
1061
- throw err2 || err;
1062
- }
1063
- }
1064
- })();
1065
- cache.set(u, p);
1066
- return p;
1031
+ return await (0, import_runjsModuleLoader.runjsImportModule)(this, url, { importer: import_runjsModuleLoader.runjsImportAsync });
1067
1032
  });
1068
1033
  this.defineMethod("createJSRunner", async function(options) {
1069
1034
  try {
@@ -1392,6 +1357,7 @@ const _FlowRunJSContext = class _FlowRunJSContext extends FlowContext {
1392
1357
  return this.engine.reactView.createRoot(realContainer, options);
1393
1358
  }, "createRoot")
1394
1359
  };
1360
+ ReactDOMShim.__nbRunjsInternalShim = true;
1395
1361
  this.defineProperty("ReactDOM", { value: ReactDOMShim });
1396
1362
  (0, import_runjsLibs.setupRunJSLibs)(this);
1397
1363
  this.defineMethod(
@@ -1403,39 +1369,64 @@ const _FlowRunJSContext = class _FlowRunJSContext extends FlowContext {
1403
1369
  const globalRef = globalThis;
1404
1370
  globalRef.__nbRunjsRoots = globalRef.__nbRunjsRoots || /* @__PURE__ */ new WeakMap();
1405
1371
  const rootMap = globalRef.__nbRunjsRoots;
1406
- if (typeof vnode === "string") {
1407
- const existingRoot = rootMap.get(containerEl);
1408
- if (existingRoot && typeof existingRoot.unmount === "function") {
1372
+ const disposeEntry = /* @__PURE__ */ __name((entry2) => {
1373
+ if (!entry2) return;
1374
+ if (entry2.disposeTheme && typeof entry2.disposeTheme === "function") {
1409
1375
  try {
1410
- existingRoot.unmount();
1411
- } finally {
1412
- rootMap.delete(containerEl);
1376
+ entry2.disposeTheme();
1377
+ } catch (_2) {
1413
1378
  }
1379
+ entry2.disposeTheme = void 0;
1414
1380
  }
1381
+ const root = entry2.root || entry2;
1382
+ if (root && typeof root.unmount === "function") {
1383
+ try {
1384
+ root.unmount();
1385
+ } catch (_2) {
1386
+ }
1387
+ }
1388
+ }, "disposeEntry");
1389
+ const unmountContainerRoot = /* @__PURE__ */ __name(() => {
1390
+ const existing = rootMap.get(containerEl);
1391
+ if (existing) {
1392
+ disposeEntry(existing);
1393
+ rootMap.delete(containerEl);
1394
+ }
1395
+ }, "unmountContainerRoot");
1396
+ if (typeof vnode === "string") {
1397
+ unmountContainerRoot();
1415
1398
  const proxy = new import_ElementProxy.ElementProxy(containerEl);
1416
1399
  proxy.innerHTML = String(vnode ?? "");
1417
1400
  return null;
1418
1401
  }
1419
1402
  if (vnode && vnode.nodeType && (vnode.nodeType === 1 || vnode.nodeType === 3 || vnode.nodeType === 11)) {
1420
- const existingRoot = rootMap.get(containerEl);
1421
- if (existingRoot && typeof existingRoot.unmount === "function") {
1422
- try {
1423
- existingRoot.unmount();
1424
- } finally {
1425
- rootMap.delete(containerEl);
1426
- }
1427
- }
1403
+ unmountContainerRoot();
1428
1404
  while (containerEl.firstChild) containerEl.removeChild(containerEl.firstChild);
1429
1405
  containerEl.appendChild(vnode);
1430
1406
  return null;
1431
1407
  }
1432
- let root = rootMap.get(containerEl);
1433
- if (!root) {
1434
- root = this.ReactDOM.createRoot(containerEl);
1435
- rootMap.set(containerEl, root);
1408
+ const rendererKey = this.ReactDOM;
1409
+ const ownerKey = this;
1410
+ let entry = rootMap.get(containerEl);
1411
+ if (!entry || entry.rendererKey !== rendererKey || entry.ownerKey !== ownerKey) {
1412
+ if (entry) {
1413
+ disposeEntry(entry);
1414
+ rootMap.delete(containerEl);
1415
+ }
1416
+ const root = this.ReactDOM.createRoot(containerEl);
1417
+ entry = { rendererKey, ownerKey, root, disposeTheme: void 0, lastVnode: void 0 };
1418
+ rootMap.set(containerEl, entry);
1436
1419
  }
1437
- root.render(vnode);
1438
- return root;
1420
+ return (0, import_runjsLibs.externalReactRender)({
1421
+ ctx: this,
1422
+ entry,
1423
+ vnode,
1424
+ containerEl,
1425
+ rootMap,
1426
+ unmountContainerRoot,
1427
+ internalReact: import_react.default,
1428
+ internalAntd: antd
1429
+ });
1439
1430
  }
1440
1431
  );
1441
1432
  }
package/lib/provider.js CHANGED
@@ -79,17 +79,17 @@ const FlowEngineGlobalsContextProvider = /* @__PURE__ */ __name(({ children }) =
79
79
  cache: false,
80
80
  get: /* @__PURE__ */ __name((ctx) => new import_FlowView.FlowViewer(ctx, { drawer, embed, popover, dialog }), "get")
81
81
  });
82
- engine.context.defineProperty("themeToken", {
83
- get: /* @__PURE__ */ __name(() => token, "get"),
84
- observable: true,
85
- cache: true
86
- });
87
82
  for (const item of Object.entries(context)) {
88
83
  const [key, value] = item;
89
84
  if (value) {
90
85
  engine.context.defineProperty(key, { value });
91
86
  }
92
87
  }
88
+ engine.context.defineProperty("themeToken", {
89
+ get: /* @__PURE__ */ __name(() => token, "get"),
90
+ observable: true,
91
+ cache: true
92
+ });
93
93
  engine.reactView.refresh();
94
94
  }, [engine, drawer, modal, message, notification, config, popover, token, dialog, embed]);
95
95
  return /* @__PURE__ */ import_react.default.createElement(import_antd.ConfigProvider, { ...config, locale: (_a = engine.context.locales) == null ? void 0 : _a.antd, popupMatchSelectWidth: false }, children, contextHolder, popoverContextHolder, pageContextHolder, dialogContextHolder);
@@ -13,3 +13,16 @@ export declare function registerRunJSLib(name: string, loader: RunJSLibLoader, o
13
13
  cache?: RunJSLibCache;
14
14
  }): void;
15
15
  export declare function setupRunJSLibs(ctx: FlowContext): void;
16
+ export declare function setRunJSLibOverride(ctx: FlowContext, name: string, value: unknown, options?: {
17
+ topLevelKey?: string | false;
18
+ }): void;
19
+ export declare function externalReactRender(options: {
20
+ ctx: any;
21
+ entry: any;
22
+ vnode: any;
23
+ containerEl: any;
24
+ rootMap: WeakMap<any, any>;
25
+ unmountContainerRoot: () => void;
26
+ internalReact: any;
27
+ internalAntd: any;
28
+ }): any;
package/lib/runjsLibs.js CHANGED
@@ -37,15 +37,19 @@ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__ge
37
37
  var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
38
38
  var runjsLibs_exports = {};
39
39
  __export(runjsLibs_exports, {
40
+ externalReactRender: () => externalReactRender,
40
41
  registerRunJSLib: () => registerRunJSLib,
42
+ setRunJSLibOverride: () => setRunJSLibOverride,
41
43
  setupRunJSLibs: () => setupRunJSLibs
42
44
  });
43
45
  module.exports = __toCommonJS(runjsLibs_exports);
44
46
  var antdIcons = __toESM(require("@ant-design/icons"));
47
+ var import_reactive = require("@formily/reactive");
45
48
  const __runjsLibRegistry = /* @__PURE__ */ new Map();
46
49
  const __runjsLibResolvedCache = /* @__PURE__ */ new Map();
47
50
  const __runjsLibPendingCache = /* @__PURE__ */ new Map();
48
51
  const __runjsLibPendingByCtx = /* @__PURE__ */ new WeakMap();
52
+ const __runjsErrorBoundaryByReact = /* @__PURE__ */ new WeakMap();
49
53
  function __runjsGetPendingMapForCtx(ctx) {
50
54
  let m = __runjsLibPendingByCtx.get(ctx);
51
55
  if (!m) {
@@ -216,8 +220,313 @@ function setupRunJSLibs(ctx) {
216
220
  setupRunJSLibAPIs(ctx);
217
221
  }
218
222
  __name(setupRunJSLibs, "setupRunJSLibs");
223
+ function setRunJSLibOverride(ctx, name, value, options) {
224
+ const topLevelKey = (options == null ? void 0 : options.topLevelKey) === false ? null : (options == null ? void 0 : options.topLevelKey) || name;
225
+ if (topLevelKey) {
226
+ ctx.defineProperty(topLevelKey, { value });
227
+ }
228
+ const libs = ctx.libs;
229
+ Object.defineProperty(libs, name, {
230
+ configurable: true,
231
+ enumerable: true,
232
+ writable: true,
233
+ value
234
+ });
235
+ }
236
+ __name(setRunJSLibOverride, "setRunJSLibOverride");
237
+ function buildMixedReactHint(options) {
238
+ var _a;
239
+ const { ctx, internalReact, internalAntd } = options;
240
+ const lines = [];
241
+ const externalReact = ctx.React && ctx.React !== internalReact;
242
+ const internalReactDOM = !!((_a = ctx.ReactDOM) == null ? void 0 : _a.__nbRunjsInternalShim);
243
+ const usingInternalAntd = ctx.antd === internalAntd;
244
+ const externalAntd = ctx.antd && ctx.antd !== internalAntd;
245
+ if (externalReact && internalReactDOM) {
246
+ const reactInfo = ctx.__runjsExternalReact;
247
+ const v = reactInfo == null ? void 0 : reactInfo.version;
248
+ const domHint = v ? `react-dom@${v}/client` : "react-dom/client";
249
+ lines.push(
250
+ `- You have imported external React, but you're still using the built-in ReactDOM Root; please also run: await ctx.importAsync("${domHint}")`
251
+ );
252
+ }
253
+ if (externalAntd && !externalReact) {
254
+ lines.push(
255
+ `- You have imported external antd, but you're still using the built-in React; please run: await ctx.importAsync("react@18.x")`
256
+ );
257
+ lines.push(`- And make sure ReactDOM matches: await ctx.importAsync("react-dom@18.x/client")`);
258
+ }
259
+ if (externalReact && usingInternalAntd) {
260
+ lines.push(
261
+ `- You have imported external React, but you're still using the built-in antd; please switch to: await ctx.importAsync("antd@5.x")`
262
+ );
263
+ lines.push(`- If you use icon components, also import: await ctx.importAsync("@ant-design/icons@5.x")`);
264
+ }
265
+ return lines.length ? `
266
+
267
+ [RunJS Hint]
268
+ ${lines.join("\n")}` : "";
269
+ }
270
+ __name(buildMixedReactHint, "buildMixedReactHint");
271
+ function isReactHooksDispatcherNullError(err) {
272
+ const msg = String((err == null ? void 0 : err.message) || "");
273
+ if (!msg) return false;
274
+ if (!/Cannot read (?:properties|property) of (?:null|undefined) \(reading 'use[A-Za-z]+'\)/.test(msg)) return false;
275
+ const stack = String((err == null ? void 0 : err.stack) || "");
276
+ if (!stack) return false;
277
+ return /(?:^|\W)react@[^/\s)]+/i.test(stack) || /react\.mjs/i.test(stack) || /react\.(?:development|production)/i.test(stack);
278
+ }
279
+ __name(isReactHooksDispatcherNullError, "isReactHooksDispatcherNullError");
280
+ function extractReactVersionFromStack(err) {
281
+ var _a;
282
+ const stack = String((err == null ? void 0 : err.stack) || "");
283
+ if (!stack) return void 0;
284
+ const m = stack.match(/(?:^|\W)react@([^/\s)]+)/i);
285
+ const v = (_a = m == null ? void 0 : m[1]) == null ? void 0 : _a.trim();
286
+ return v || void 0;
287
+ }
288
+ __name(extractReactVersionFromStack, "extractReactVersionFromStack");
289
+ function buildReactDispatcherNullHint(options) {
290
+ const { ctx, internalReact, internalAntd, err } = options;
291
+ if (!isReactHooksDispatcherNullError(err)) return "";
292
+ const v = extractReactVersionFromStack(err);
293
+ const lines = [];
294
+ lines.push(`- This looks like a React Hooks crash caused by multiple React instances (hook dispatcher is null).`);
295
+ if (v) {
296
+ lines.push(`- Your stack trace includes external React: react@${v}.`);
297
+ lines.push(
298
+ `- Fix: import the same React BEFORE you read ctx.libs.React / call hooks / import React-based libs: await ctx.importAsync("react@${v}")`
299
+ );
300
+ } else {
301
+ lines.push(
302
+ `- Fix: import external React BEFORE you read ctx.libs.React / call hooks / import React-based libs (use the same version shown in the stack trace).`
303
+ );
304
+ }
305
+ const usingInternalAntd = ctx.antd === internalAntd;
306
+ if (usingInternalAntd) {
307
+ lines.push(`- If you use antd components, also switch to external antd: await ctx.importAsync("antd@5.x")`);
308
+ lines.push(`- If you use icon components, also import: await ctx.importAsync("@ant-design/icons@5.x")`);
309
+ }
310
+ return lines.length ? `
311
+
312
+ [RunJS Hint]
313
+ ${lines.join("\n")}` : "";
314
+ }
315
+ __name(buildReactDispatcherNullHint, "buildReactDispatcherNullHint");
316
+ function wrapErrorWithHint(err, messageWithHint) {
317
+ const e = new Error(messageWithHint);
318
+ e.cause = err;
319
+ try {
320
+ const name = typeof (err == null ? void 0 : err.name) === "string" ? err.name : "";
321
+ if (name) e.name = name;
322
+ } catch (_) {
323
+ }
324
+ try {
325
+ const stack = typeof (err == null ? void 0 : err.stack) === "string" ? err.stack : "";
326
+ if (stack) {
327
+ const lines = String(stack).split("\n");
328
+ if (lines.length) {
329
+ lines[0] = `${e.name}: ${messageWithHint}`;
330
+ e.stack = lines.join("\n");
331
+ }
332
+ }
333
+ } catch (_) {
334
+ }
335
+ return e;
336
+ }
337
+ __name(wrapErrorWithHint, "wrapErrorWithHint");
338
+ function getRunjsErrorBoundary(ReactLike) {
339
+ if (!ReactLike) return null;
340
+ const cached = __runjsErrorBoundaryByReact.get(ReactLike);
341
+ if (cached) return cached;
342
+ if (typeof ReactLike.createElement !== "function") return null;
343
+ const Base = ReactLike.Component;
344
+ if (typeof Base !== "function") return null;
345
+ const _RunjsErrorBoundary = class _RunjsErrorBoundary extends Base {
346
+ static getDerivedStateFromError(error) {
347
+ return { error };
348
+ }
349
+ state = {};
350
+ componentDidCatch(error) {
351
+ var _a, _b, _c;
352
+ try {
353
+ const enhance = (_a = this.props) == null ? void 0 : _a.enhanceReactError;
354
+ const enhanced = typeof enhance === "function" ? enhance(error) : error;
355
+ const msg = String((enhanced == null ? void 0 : enhanced.message) || "");
356
+ if (msg && /\[RunJS Hint\]/.test(msg)) {
357
+ console.error(msg);
358
+ const logger = (_c = (_b = this.props) == null ? void 0 : _b.ctx) == null ? void 0 : _c.logger;
359
+ if (logger && typeof logger.error === "function") {
360
+ logger.error(msg);
361
+ }
362
+ }
363
+ } catch (_) {
364
+ }
365
+ }
366
+ componentDidUpdate(prevProps) {
367
+ var _a, _b;
368
+ if ((prevProps == null ? void 0 : prevProps.resetKey) !== ((_a = this.props) == null ? void 0 : _a.resetKey) && ((_b = this.state) == null ? void 0 : _b.error)) {
369
+ this.setState({ error: void 0 });
370
+ }
371
+ }
372
+ render() {
373
+ var _a, _b;
374
+ const error = (_a = this.state) == null ? void 0 : _a.error;
375
+ if (!error) return this.props.children;
376
+ let msg = "";
377
+ try {
378
+ const enhance = (_b = this.props) == null ? void 0 : _b.enhanceReactError;
379
+ const enhanced = typeof enhance === "function" ? enhance(error) : error;
380
+ msg = String((enhanced == null ? void 0 : enhanced.message) || enhanced || (error == null ? void 0 : error.message) || error || "");
381
+ } catch (_) {
382
+ msg = String((error == null ? void 0 : error.message) || error || "");
383
+ }
384
+ const containerStyle = {
385
+ boxSizing: "border-box",
386
+ padding: 12,
387
+ borderRadius: 6,
388
+ border: "1px solid #ffccc7",
389
+ background: "#fff2f0",
390
+ color: "#a8071a",
391
+ fontSize: 12,
392
+ lineHeight: 1.5,
393
+ maxWidth: "100%",
394
+ overflow: "auto"
395
+ };
396
+ const preStyle = {
397
+ margin: 0,
398
+ whiteSpace: "pre-wrap",
399
+ wordBreak: "break-word",
400
+ fontFamily: 'ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, "Liberation Mono", "Courier New", monospace'
401
+ };
402
+ const titleStyle = { fontWeight: 600, marginBottom: 8 };
403
+ return ReactLike.createElement(
404
+ "div",
405
+ { style: containerStyle },
406
+ ReactLike.createElement("div", { style: titleStyle }, "RunJS render error"),
407
+ ReactLike.createElement("pre", { style: preStyle }, msg)
408
+ );
409
+ }
410
+ };
411
+ __name(_RunjsErrorBoundary, "RunjsErrorBoundary");
412
+ let RunjsErrorBoundary = _RunjsErrorBoundary;
413
+ __runjsErrorBoundaryByReact.set(ReactLike, RunjsErrorBoundary);
414
+ return RunjsErrorBoundary;
415
+ }
416
+ __name(getRunjsErrorBoundary, "getRunjsErrorBoundary");
417
+ function wrapVnodeWithRunjsErrorBoundary(options) {
418
+ const { ctx, vnode, enhanceReactError, resetKey } = options;
419
+ const ReactLike = ctx == null ? void 0 : ctx.React;
420
+ const Boundary = getRunjsErrorBoundary(ReactLike);
421
+ if (!Boundary) return vnode;
422
+ return ReactLike.createElement(Boundary, { ctx, enhanceReactError, resetKey }, vnode);
423
+ }
424
+ __name(wrapVnodeWithRunjsErrorBoundary, "wrapVnodeWithRunjsErrorBoundary");
425
+ function tryRenderWithExternalAntdTheme(options) {
426
+ var _a;
427
+ const { ctx, entry, containerEl, rootMap, unmountContainerRoot, enhanceReactError, internalReact, internalAntd } = options;
428
+ const canUseExternalAntd = !((_a = ctx.ReactDOM) == null ? void 0 : _a.__nbRunjsInternalShim) && ctx.React && ctx.React !== internalReact && ctx.antd && ctx.antd !== internalAntd && typeof ctx.antd.ConfigProvider !== "undefined";
429
+ if (!canUseExternalAntd) {
430
+ if (entry.disposeTheme) {
431
+ try {
432
+ entry.disposeTheme();
433
+ } catch (_) {
434
+ }
435
+ entry.disposeTheme = void 0;
436
+ }
437
+ return false;
438
+ }
439
+ const renderWithExternalAntdTheme = /* @__PURE__ */ __name(() => {
440
+ var _a2, _b, _c, _d, _e, _f, _g;
441
+ const themeToken = (_b = (_a2 = ctx == null ? void 0 : ctx.engine) == null ? void 0 : _a2.context) == null ? void 0 : _b.themeToken;
442
+ const appConfig = (_d = (_c = ctx == null ? void 0 : ctx.engine) == null ? void 0 : _c.context) == null ? void 0 : _d.antdConfig;
443
+ const locale = ((_g = (_f = (_e = ctx == null ? void 0 : ctx.engine) == null ? void 0 : _e.context) == null ? void 0 : _f.locales) == null ? void 0 : _g.antd) || (appConfig == null ? void 0 : appConfig.locale);
444
+ const ConfigProvider = ctx.antd.ConfigProvider;
445
+ const App = ctx.antd.App;
446
+ const configProps = {
447
+ popupMatchSelectWidth: false,
448
+ locale: locale || {}
449
+ };
450
+ if (appConfig && typeof appConfig === "object") {
451
+ if (typeof appConfig.direction !== "undefined") configProps.direction = appConfig.direction;
452
+ if (typeof appConfig.prefixCls === "string") configProps.prefixCls = appConfig.prefixCls;
453
+ if (typeof appConfig.iconPrefixCls === "string") configProps.iconPrefixCls = appConfig.iconPrefixCls;
454
+ if (typeof appConfig.getPopupContainer === "function")
455
+ configProps.getPopupContainer = appConfig.getPopupContainer;
456
+ if (appConfig.theme && typeof appConfig.theme === "object") configProps.theme = appConfig.theme;
457
+ }
458
+ const child = entry.lastVnode;
459
+ const wrapped = App ? ctx.React.createElement(ConfigProvider, configProps, ctx.React.createElement(App, null, child)) : ctx.React.createElement(ConfigProvider, configProps, child);
460
+ entry.root.render(wrapped);
461
+ }, "renderWithExternalAntdTheme");
462
+ if (!entry.disposeTheme) {
463
+ entry.disposeTheme = (0, import_reactive.autorun)(() => {
464
+ try {
465
+ if (containerEl && containerEl.nodeType === 1 && typeof containerEl.isConnected === "boolean" && !containerEl.isConnected && entry.wasConnected) {
466
+ queueMicrotask(() => {
467
+ const cur = rootMap.get(containerEl);
468
+ if (cur === entry) unmountContainerRoot();
469
+ });
470
+ return;
471
+ }
472
+ if (containerEl && containerEl.nodeType === 1 && typeof containerEl.isConnected === "boolean" && containerEl.isConnected) {
473
+ entry.wasConnected = true;
474
+ }
475
+ renderWithExternalAntdTheme();
476
+ } catch (e) {
477
+ throw enhanceReactError(e);
478
+ }
479
+ });
480
+ } else {
481
+ renderWithExternalAntdTheme();
482
+ }
483
+ return true;
484
+ }
485
+ __name(tryRenderWithExternalAntdTheme, "tryRenderWithExternalAntdTheme");
486
+ function externalReactRender(options) {
487
+ const { ctx, entry, vnode, containerEl, rootMap, unmountContainerRoot, internalReact, internalAntd } = options;
488
+ const enhanceReactError = /* @__PURE__ */ __name((err) => {
489
+ const msg = String((err == null ? void 0 : err.message) || err || "");
490
+ if (!msg) return err;
491
+ if (/\[RunJS Hint\]/.test(msg)) return err;
492
+ const invalidHookCall = /invalid hook call/i.test(msg);
493
+ const dispatcherNull = isReactHooksDispatcherNullError(err);
494
+ if (!invalidHookCall && !dispatcherNull) return err;
495
+ const hint = buildMixedReactHint({ ctx, internalReact, internalAntd }) || buildReactDispatcherNullHint({ ctx, internalReact, internalAntd, err });
496
+ if (!hint) return err;
497
+ return wrapErrorWithHint(err, `${msg}${hint}`);
498
+ }, "enhanceReactError");
499
+ try {
500
+ entry.__nbRunjsRenderSeq = (entry.__nbRunjsRenderSeq || 0) + 1;
501
+ entry.lastVnode = wrapVnodeWithRunjsErrorBoundary({
502
+ ctx,
503
+ vnode,
504
+ enhanceReactError,
505
+ resetKey: entry.__nbRunjsRenderSeq
506
+ });
507
+ const renderedWithExternalAntdTheme = tryRenderWithExternalAntdTheme({
508
+ ctx,
509
+ entry,
510
+ containerEl,
511
+ rootMap,
512
+ unmountContainerRoot,
513
+ enhanceReactError,
514
+ internalReact,
515
+ internalAntd
516
+ });
517
+ if (!renderedWithExternalAntdTheme) {
518
+ entry.root.render(entry.lastVnode);
519
+ }
520
+ return entry.root;
521
+ } catch (e) {
522
+ throw enhanceReactError(e);
523
+ }
524
+ }
525
+ __name(externalReactRender, "externalReactRender");
219
526
  // Annotate the CommonJS export names for ESM import in node:
220
527
  0 && (module.exports = {
528
+ externalReactRender,
221
529
  registerRunJSLib,
530
+ setRunJSLibOverride,
222
531
  setupRunJSLibs
223
532
  });
@@ -25,3 +25,4 @@ export { prepareRunJsCode, preprocessRunJsTemplates } from './runjsTemplateCompa
25
25
  export { createEphemeralContext } from './createEphemeralContext';
26
26
  export { pruneFilter } from './pruneFilter';
27
27
  export { isBeforeRenderFlow } from './flows';
28
+ export { resolveModuleUrl, isCssFile } from './resolveModuleUrl';
@@ -55,6 +55,7 @@ __export(utils_exports, {
55
55
  getT: () => import_translation.getT,
56
56
  inferRecordRef: () => import_variablesParams.inferRecordRef,
57
57
  isBeforeRenderFlow: () => import_flows.isBeforeRenderFlow,
58
+ isCssFile: () => import_resolveModuleUrl.isCssFile,
58
59
  isInheritedFrom: () => import_inheritance.isInheritedFrom,
59
60
  isVariableExpression: () => import_context.isVariableExpression,
60
61
  parsePathnameToViewParams: () => import_parsePathnameToViewParams.parsePathnameToViewParams,
@@ -64,6 +65,7 @@ __export(utils_exports, {
64
65
  resolveCreateModelOptions: () => import_params_resolvers.resolveCreateModelOptions,
65
66
  resolveDefaultParams: () => import_params_resolvers.resolveDefaultParams,
66
67
  resolveExpressions: () => import_params_resolvers.resolveExpressions,
68
+ resolveModuleUrl: () => import_resolveModuleUrl.resolveModuleUrl,
67
69
  resolveStepUiSchema: () => import_schema_utils.resolveStepUiSchema,
68
70
  resolveUiMode: () => import_schema_utils.resolveUiMode,
69
71
  setAutoFlowError: () => import_autoFlowError.setAutoFlowError,
@@ -91,6 +93,7 @@ var import_runjsTemplateCompat = require("./runjsTemplateCompat");
91
93
  var import_createEphemeralContext = require("./createEphemeralContext");
92
94
  var import_pruneFilter = require("./pruneFilter");
93
95
  var import_flows = require("./flows");
96
+ var import_resolveModuleUrl = require("./resolveModuleUrl");
94
97
  // Annotate the CommonJS export names for ESM import in node:
95
98
  0 && (module.exports = {
96
99
  BLOCK_GROUP_CONFIGS,
@@ -122,6 +125,7 @@ var import_flows = require("./flows");
122
125
  getT,
123
126
  inferRecordRef,
124
127
  isBeforeRenderFlow,
128
+ isCssFile,
125
129
  isInheritedFrom,
126
130
  isVariableExpression,
127
131
  parsePathnameToViewParams,
@@ -131,6 +135,7 @@ var import_flows = require("./flows");
131
135
  resolveCreateModelOptions,
132
136
  resolveDefaultParams,
133
137
  resolveExpressions,
138
+ resolveModuleUrl,
134
139
  resolveStepUiSchema,
135
140
  resolveUiMode,
136
141
  setAutoFlowError,
@@ -0,0 +1,58 @@
1
+ /**
2
+ * This file is part of the NocoBase (R) project.
3
+ * Copyright (c) 2020-2024 NocoBase Co., Ltd.
4
+ * Authors: NocoBase Team.
5
+ *
6
+ * This project is dual-licensed under AGPL-3.0 and NocoBase Commercial License.
7
+ * For more information, please refer to: https://www.nocobase.com/agreement.
8
+ */
9
+ /**
10
+ * 解析模块 URL,将相对路径转换为完整的 CDN URL
11
+ *
12
+ * @param url - 模块地址(支持相对路径或完整 URL)
13
+ * @param options - 可选配置
14
+ * @param options.addSuffix - 是否添加 ESM_CDN_SUFFIX 后缀(如 `+esm`),默认为 `true`
15
+ * @returns 解析后的完整 URL
16
+ *
17
+ * @example
18
+ * ```ts
19
+ * // 相对路径会被拼接上 CDN 前缀和后缀(默认添加)
20
+ * // 如果使用 esm.sh(默认),不需要后缀
21
+ * resolveModuleUrl('vue@3.4.0')
22
+ * // => 'https://esm.sh/vue@3.4.0'
23
+ *
24
+ * // 如果使用 jsdelivr,需要配置 ESM_CDN_SUFFIX='/+esm'
25
+ * // resolveModuleUrl('vue@3.4.0') => 'https://cdn.jsdelivr.net/npm/vue@3.4.0/+esm'
26
+ *
27
+ * // 不添加后缀(适用于 UMD 库或 CSS 文件)
28
+ * resolveModuleUrl('vue@3.4.0', { addSuffix: false })
29
+ * // => 'https://esm.sh/vue@3.4.0' (即使配置了 suffix 也不会添加)
30
+ *
31
+ * // 原始 URL(适用于 UMD 库)
32
+ * resolveModuleUrl('lodash@4.17.21/lodash.js', { raw: true })
33
+ * // => 'https://esm.sh/lodash@4.17.21/lodash.js?raw' (即使配置了 suffix 也不会添加)
34
+ *
35
+ * // 完整 URL 保持不变
36
+ * resolveModuleUrl('https://cdn.jsdelivr.net/npm/vue@3.4.0')
37
+ * // => 'https://cdn.jsdelivr.net/npm/vue@3.4.0'
38
+ * ```
39
+ */
40
+ export declare function resolveModuleUrl(url: string, options?: {
41
+ addSuffix?: boolean;
42
+ raw?: boolean;
43
+ }): string;
44
+ /**
45
+ * 判断 URL 是否为 CSS 文件
46
+ *
47
+ * @param url - 文件 URL(支持带 query 和 hash,如 `example.css?v=123`)
48
+ * @returns 如果是 CSS 文件返回 `true`,否则返回 `false`
49
+ *
50
+ * @example
51
+ * ```ts
52
+ * isCssFile('style.css') // => true
53
+ * isCssFile('style.css?v=123') // => true
54
+ * isCssFile('style.css#section') // => true
55
+ * isCssFile('script.js') // => false
56
+ * ```
57
+ */
58
+ export declare function isCssFile(url: string): boolean;