@nocobase/flow-engine 2.0.0-beta.9 → 2.0.1
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/lib/BlockScopedFlowEngine.js +0 -1
- package/lib/FlowDefinition.d.ts +2 -0
- package/lib/JSRunner.d.ts +6 -0
- package/lib/JSRunner.js +32 -2
- package/lib/ViewScopedFlowEngine.js +3 -0
- package/lib/acl/Acl.js +13 -3
- package/lib/components/FlowContextSelector.js +155 -10
- package/lib/components/settings/wrappers/component/SwitchWithTitle.js +2 -1
- package/lib/components/settings/wrappers/contextual/DefaultSettingsIcon.js +76 -15
- package/lib/components/settings/wrappers/contextual/FlowsContextMenu.js +24 -4
- package/lib/components/settings/wrappers/contextual/StepSettingsDialog.js +5 -1
- package/lib/components/variables/VariableInput.js +9 -4
- package/lib/components/variables/VariableTag.js +46 -39
- package/lib/components/variables/utils.d.ts +7 -0
- package/lib/components/variables/utils.js +42 -2
- package/lib/data-source/index.d.ts +7 -27
- package/lib/data-source/index.js +81 -51
- package/lib/executor/FlowExecutor.d.ts +2 -1
- package/lib/executor/FlowExecutor.js +163 -22
- package/lib/flowContext.d.ts +230 -7
- package/lib/flowContext.js +2267 -148
- package/lib/flowEngine.d.ts +21 -0
- package/lib/flowEngine.js +56 -8
- package/lib/flowI18n.js +6 -4
- package/lib/flowSettings.js +17 -11
- package/lib/index.d.ts +7 -1
- package/lib/index.js +21 -0
- package/lib/locale/en-US.json +9 -2
- package/lib/locale/index.d.ts +14 -0
- package/lib/locale/zh-CN.json +8 -1
- package/lib/models/CollectionFieldModel.d.ts +1 -0
- package/lib/models/CollectionFieldModel.js +3 -2
- package/lib/models/flowModel.js +12 -1
- package/lib/provider.js +5 -5
- package/lib/resources/baseRecordResource.d.ts +5 -0
- package/lib/resources/baseRecordResource.js +24 -0
- package/lib/resources/multiRecordResource.d.ts +1 -0
- package/lib/resources/multiRecordResource.js +11 -4
- package/lib/resources/singleRecordResource.js +2 -0
- package/lib/resources/sqlResource.d.ts +4 -3
- package/lib/resources/sqlResource.js +8 -3
- package/lib/runjs-context/contexts/FormJSFieldItemRunJSContext.js +12 -2
- package/lib/runjs-context/contexts/JSBlockRunJSContext.js +2 -2
- package/lib/runjs-context/contexts/JSEditableFieldRunJSContext.d.ts +16 -0
- package/lib/runjs-context/contexts/JSEditableFieldRunJSContext.js +125 -0
- package/lib/runjs-context/contexts/JSItemRunJSContext.js +12 -2
- package/lib/runjs-context/contexts/base.js +706 -41
- package/lib/runjs-context/contributions.d.ts +33 -0
- package/lib/runjs-context/contributions.js +88 -0
- package/lib/runjs-context/helpers.js +12 -1
- package/lib/runjs-context/setup.js +6 -0
- package/lib/runjs-context/snippets/global/api-request.snippet.js +3 -3
- package/lib/runjs-context/snippets/global/import-esm.snippet.js +2 -3
- package/lib/runjs-context/snippets/global/query-selector.snippet.js +8 -3
- package/lib/runjs-context/snippets/global/require-amd.snippet.js +1 -1
- package/lib/runjs-context/snippets/index.d.ts +11 -1
- package/lib/runjs-context/snippets/index.js +61 -40
- package/lib/runjs-context/snippets/scene/block/add-event-listener.snippet.js +10 -7
- package/lib/runjs-context/snippets/scene/block/api-fetch-render-list.snippet.js +3 -3
- package/lib/runjs-context/snippets/scene/block/chartjs-bar.snippet.js +2 -2
- package/lib/runjs-context/snippets/scene/block/echarts-init.snippet.js +2 -2
- package/lib/runjs-context/snippets/scene/block/render-iframe.snippet.js +2 -2
- package/lib/runjs-context/snippets/scene/block/render-react.snippet.js +1 -1
- package/lib/runjs-context/snippets/scene/block/render-statistics.snippet.js +1 -1
- package/lib/runjs-context/snippets/scene/block/render-timeline.snippet.js +1 -1
- package/lib/runjs-context/snippets/scene/block/resource-example.snippet.js +5 -5
- package/lib/runjs-context/snippets/scene/block/three-users-orbit.snippet.js +6 -6
- package/lib/runjs-context/snippets/scene/block/vue-component.snippet.js +3 -4
- package/lib/runjs-context/snippets/scene/detail/color-by-value.snippet.js +1 -1
- package/lib/runjs-context/snippets/scene/detail/copy-to-clipboard.snippet.js +20 -3
- package/lib/runjs-context/snippets/scene/detail/format-number.snippet.js +1 -1
- package/lib/runjs-context/snippets/scene/detail/innerHTML-value.snippet.js +1 -1
- package/lib/runjs-context/snippets/scene/detail/percentage-bar.snippet.js +3 -3
- package/lib/runjs-context/snippets/scene/detail/relative-time.snippet.js +3 -3
- package/lib/runjs-context/snippets/scene/detail/status-tag.snippet.js +2 -2
- package/lib/runjs-context/snippets/scene/form/cascade-select.snippet.js +1 -1
- package/lib/runjs-context/snippets/scene/form/render-basic.snippet.js +2 -2
- package/lib/runjs-context/snippets/scene/table/cell-open-dialog.snippet.js +6 -3
- package/lib/runjs-context/snippets/scene/table/concat-fields.snippet.js +3 -1
- package/lib/runjsLibs.d.ts +28 -0
- package/lib/runjsLibs.js +532 -0
- package/lib/scheduler/ModelOperationScheduler.d.ts +2 -0
- package/lib/scheduler/ModelOperationScheduler.js +25 -21
- package/lib/types.d.ts +27 -0
- package/lib/utils/associationObjectVariable.d.ts +2 -2
- package/lib/utils/createCollectionContextMeta.js +1 -0
- package/lib/utils/createEphemeralContext.js +2 -2
- package/lib/utils/dateVariable.d.ts +16 -0
- package/lib/utils/dateVariable.js +380 -0
- package/lib/utils/exceptions.d.ts +7 -0
- package/lib/utils/exceptions.js +10 -0
- package/lib/utils/index.d.ts +8 -3
- package/lib/utils/index.js +45 -0
- package/lib/utils/params-resolvers.js +16 -9
- package/lib/utils/resolveModuleUrl.d.ts +58 -0
- package/lib/utils/resolveModuleUrl.js +65 -0
- package/lib/utils/resolveRunJSObjectValues.d.ts +16 -0
- package/lib/utils/resolveRunJSObjectValues.js +61 -0
- package/lib/utils/runjsModuleLoader.d.ts +58 -0
- package/lib/utils/runjsModuleLoader.js +422 -0
- package/lib/utils/runjsTemplateCompat.d.ts +35 -0
- package/lib/utils/runjsTemplateCompat.js +743 -0
- package/lib/utils/runjsValue.d.ts +29 -0
- package/lib/utils/runjsValue.js +275 -0
- package/lib/utils/safeGlobals.d.ts +18 -8
- package/lib/utils/safeGlobals.js +164 -17
- package/lib/utils/schema-utils.d.ts +10 -0
- package/lib/utils/schema-utils.js +61 -0
- package/lib/views/createViewMeta.d.ts +0 -7
- package/lib/views/createViewMeta.js +19 -70
- package/lib/views/index.d.ts +1 -2
- package/lib/views/index.js +4 -3
- package/lib/views/useDialog.js +7 -2
- package/lib/views/useDrawer.js +7 -2
- package/lib/views/usePage.d.ts +4 -0
- package/lib/views/usePage.js +43 -6
- package/lib/views/usePopover.js +4 -1
- package/lib/views/viewEvents.d.ts +17 -0
- package/lib/views/viewEvents.js +90 -0
- package/package.json +4 -4
- package/src/BlockScopedFlowEngine.ts +2 -5
- package/src/JSRunner.ts +44 -2
- package/src/ViewScopedFlowEngine.ts +4 -0
- package/src/__tests__/JSRunner.test.ts +64 -0
- package/src/__tests__/createViewMeta.popup.test.ts +62 -1
- package/src/__tests__/flowContext.test.ts +693 -1
- package/src/__tests__/flowEngine.dataSourceDirty.test.ts +63 -0
- package/src/__tests__/flowModel.openView.navigation.test.ts +28 -0
- package/src/__tests__/flowRunJSContextDefine.test.ts +63 -0
- package/src/__tests__/flowRuntimeContext.test.ts +2 -1
- package/src/__tests__/flowSettings.open.test.tsx +123 -19
- package/src/__tests__/runjsContext.test.ts +10 -7
- package/src/__tests__/runjsContextImplementations.test.ts +34 -3
- package/src/__tests__/runjsContextRuntime.test.ts +3 -3
- package/src/__tests__/runjsContributions.test.ts +89 -0
- package/src/__tests__/runjsExternalLibs.test.ts +242 -0
- package/src/__tests__/runjsLibsLazyLoading.test.ts +44 -0
- package/src/__tests__/runjsLocales.test.ts +4 -1
- package/src/__tests__/runjsPreprocessDefault.test.ts +49 -0
- package/src/__tests__/runjsRuntimeFeatures.test.ts +166 -0
- package/src/__tests__/runjsSnippets.test.ts +40 -3
- package/src/acl/Acl.tsx +3 -3
- package/src/components/FlowContextSelector.tsx +208 -12
- package/src/components/settings/wrappers/component/SwitchWithTitle.tsx +2 -1
- package/src/components/settings/wrappers/component/__tests__/InlineControls.test.tsx +74 -0
- package/src/components/settings/wrappers/contextual/DefaultSettingsIcon.tsx +109 -16
- package/src/components/settings/wrappers/contextual/FlowsContextMenu.tsx +41 -7
- package/src/components/settings/wrappers/contextual/StepSettingsDialog.tsx +13 -2
- package/src/components/settings/wrappers/contextual/__tests__/DefaultSettingsIcon.test.tsx +157 -5
- package/src/components/variables/VariableInput.tsx +12 -4
- package/src/components/variables/VariableTag.tsx +54 -45
- package/src/components/variables/__tests__/FlowContextSelector.test.tsx +260 -3
- package/src/components/variables/__tests__/VariableTag.test.tsx +50 -0
- package/src/components/variables/__tests__/utils.test.ts +81 -3
- package/src/components/variables/utils.ts +67 -6
- package/src/data-source/index.ts +85 -110
- package/src/executor/FlowExecutor.ts +200 -23
- package/src/executor/__tests__/flowExecutor.test.ts +66 -0
- package/src/flowContext.ts +2986 -211
- package/src/flowEngine.ts +59 -8
- package/src/flowI18n.ts +7 -5
- package/src/flowSettings.ts +18 -12
- package/src/index.ts +14 -1
- package/src/locale/en-US.json +9 -2
- package/src/locale/zh-CN.json +8 -1
- package/src/models/CollectionFieldModel.tsx +3 -1
- package/src/models/__tests__/dispatchEvent.when.test.ts +554 -0
- package/src/models/__tests__/flowModel.test.ts +20 -4
- package/src/models/flowModel.tsx +13 -1
- package/src/provider.tsx +7 -6
- package/src/resources/__tests__/multiRecordResource.test.ts +44 -0
- package/src/resources/__tests__/sqlResource.test.ts +60 -0
- package/src/resources/baseRecordResource.ts +31 -0
- package/src/resources/multiRecordResource.ts +11 -4
- package/src/resources/singleRecordResource.ts +3 -0
- package/src/resources/sqlResource.ts +11 -6
- package/src/runjs-context/contexts/FormJSFieldItemRunJSContext.ts +10 -0
- package/src/runjs-context/contexts/JSBlockRunJSContext.ts +6 -2
- package/src/runjs-context/contexts/JSEditableFieldRunJSContext.ts +106 -0
- package/src/runjs-context/contexts/JSItemRunJSContext.ts +10 -0
- package/src/runjs-context/contexts/base.ts +715 -44
- package/src/runjs-context/contributions.ts +88 -0
- package/src/runjs-context/helpers.ts +11 -1
- package/src/runjs-context/setup.ts +6 -0
- package/src/runjs-context/snippets/global/api-request.snippet.ts +3 -3
- package/src/runjs-context/snippets/global/import-esm.snippet.ts +2 -3
- package/src/runjs-context/snippets/global/query-selector.snippet.ts +8 -3
- package/src/runjs-context/snippets/global/require-amd.snippet.ts +1 -1
- package/src/runjs-context/snippets/index.ts +75 -41
- package/src/runjs-context/snippets/scene/block/add-event-listener.snippet.ts +11 -13
- package/src/runjs-context/snippets/scene/block/api-fetch-render-list.snippet.ts +3 -3
- package/src/runjs-context/snippets/scene/block/chartjs-bar.snippet.ts +2 -2
- package/src/runjs-context/snippets/scene/block/echarts-init.snippet.ts +2 -2
- package/src/runjs-context/snippets/scene/block/render-iframe.snippet.ts +2 -2
- package/src/runjs-context/snippets/scene/block/render-react.snippet.ts +1 -1
- package/src/runjs-context/snippets/scene/block/render-statistics.snippet.ts +1 -1
- package/src/runjs-context/snippets/scene/block/render-timeline.snippet.ts +1 -1
- package/src/runjs-context/snippets/scene/block/resource-example.snippet.ts +6 -11
- package/src/runjs-context/snippets/scene/block/three-users-orbit.snippet.ts +6 -6
- package/src/runjs-context/snippets/scene/block/vue-component.snippet.ts +3 -4
- package/src/runjs-context/snippets/scene/detail/color-by-value.snippet.ts +1 -1
- package/src/runjs-context/snippets/scene/detail/copy-to-clipboard.snippet.ts +20 -3
- package/src/runjs-context/snippets/scene/detail/format-number.snippet.ts +1 -1
- package/src/runjs-context/snippets/scene/detail/innerHTML-value.snippet.ts +1 -1
- package/src/runjs-context/snippets/scene/detail/percentage-bar.snippet.ts +3 -3
- package/src/runjs-context/snippets/scene/detail/relative-time.snippet.ts +3 -3
- package/src/runjs-context/snippets/scene/detail/status-tag.snippet.ts +2 -2
- package/src/runjs-context/snippets/scene/form/cascade-select.snippet.ts +1 -1
- package/src/runjs-context/snippets/scene/form/render-basic.snippet.ts +3 -8
- package/src/runjs-context/snippets/scene/table/cell-open-dialog.snippet.ts +6 -3
- package/src/runjs-context/snippets/scene/table/concat-fields.snippet.ts +3 -1
- package/src/runjsLibs.ts +622 -0
- package/src/scheduler/ModelOperationScheduler.ts +27 -21
- package/src/types.ts +38 -1
- package/src/utils/__tests__/dateVariable.test.ts +101 -0
- package/src/utils/__tests__/params-resolvers.test.ts +40 -0
- package/src/utils/__tests__/runjsRequireAsyncAutoWhitelist.test.ts +38 -0
- package/src/utils/__tests__/runjsTemplateCompat.test.ts +159 -0
- package/src/utils/__tests__/runjsValue.test.ts +44 -0
- package/src/utils/__tests__/safeGlobals.test.ts +57 -2
- package/src/utils/__tests__/utils.test.ts +95 -0
- package/src/utils/associationObjectVariable.ts +2 -2
- package/src/utils/createCollectionContextMeta.ts +1 -0
- package/src/utils/createEphemeralContext.ts +5 -4
- package/src/utils/dateVariable.ts +397 -0
- package/src/utils/exceptions.ts +11 -0
- package/src/utils/index.ts +37 -3
- package/src/utils/params-resolvers.ts +23 -9
- package/src/utils/resolveModuleUrl.ts +91 -0
- package/src/utils/resolveRunJSObjectValues.ts +46 -0
- package/src/utils/runjsModuleLoader.ts +553 -0
- package/src/utils/runjsTemplateCompat.ts +828 -0
- package/src/utils/runjsValue.ts +287 -0
- package/src/utils/safeGlobals.ts +188 -17
- package/src/utils/schema-utils.ts +79 -0
- package/src/views/__tests__/FlowView.usePage.test.tsx +54 -1
- package/src/views/__tests__/useDialog.closeDestroy.test.tsx +35 -8
- package/src/views/__tests__/viewEvents.resolveOpenerEngine.test.ts +28 -0
- package/src/views/createViewMeta.ts +22 -75
- package/src/views/index.tsx +1 -2
- package/src/views/useDialog.tsx +8 -1
- package/src/views/useDrawer.tsx +8 -1
- package/src/views/usePage.tsx +51 -5
- package/src/views/usePopover.tsx +4 -1
- package/src/views/viewEvents.ts +55 -0
|
@@ -409,8 +409,13 @@ export async function preprocessExpression(expression: string, ctx: FlowContext)
|
|
|
409
409
|
async function compileExpression<TModel extends FlowModel = FlowModel>(expression: string, ctx: FlowContext) {
|
|
410
410
|
// 仅点号路径匹配:ctx.a.b.c(不支持括号/函数/索引),用于数组聚合取值
|
|
411
411
|
const matchDotOnly = (expr: string): string | null => {
|
|
412
|
-
|
|
413
|
-
|
|
412
|
+
// 顶层变量名仍使用 JS 标识符规则(与 ctx.defineProperty 保持一致);
|
|
413
|
+
// 子路径允许包含 '-'(例如 formValues.oho-test.o2m-users)。
|
|
414
|
+
const m = expr
|
|
415
|
+
.trim()
|
|
416
|
+
.match(/^ctx\.([a-zA-Z_$][a-zA-Z0-9_$]*)(?:\.([a-zA-Z_$][a-zA-Z0-9_$-]*(?:\.[a-zA-Z_$][a-zA-Z0-9_$-]*)*))?$/);
|
|
417
|
+
if (!m) return null;
|
|
418
|
+
return m[2] ? `${m[1]}.${m[2]}` : m[1];
|
|
414
419
|
};
|
|
415
420
|
|
|
416
421
|
// 基于 getValuesByPath 的聚合取值:支持数组扁平化,仅支持 '.' 访问
|
|
@@ -423,6 +428,20 @@ async function compileExpression<TModel extends FlowModel = FlowModel>(expressio
|
|
|
423
428
|
return getValuesByPath(base as object, segs.join('.'));
|
|
424
429
|
};
|
|
425
430
|
|
|
431
|
+
const resolveInnerExpression = async (innerExpr: string): Promise<any> => {
|
|
432
|
+
const dotPath = matchDotOnly(innerExpr);
|
|
433
|
+
if (dotPath) {
|
|
434
|
+
const resolved = await resolveDotOnlyPath(dotPath);
|
|
435
|
+
// 当 dotPath 含 '-' 时可能与减号运算符存在歧义,例如:ctx.aa.bb-ctx.cc。
|
|
436
|
+
// 若按 path 解析未取到值,则回退到 JS 表达式解析,尽量保持兼容。
|
|
437
|
+
if (resolved === undefined && dotPath.includes('-')) {
|
|
438
|
+
return await processExpression(innerExpr, ctx);
|
|
439
|
+
}
|
|
440
|
+
return resolved;
|
|
441
|
+
}
|
|
442
|
+
return await processExpression(innerExpr, ctx);
|
|
443
|
+
};
|
|
444
|
+
|
|
426
445
|
/**
|
|
427
446
|
* 单个表达式模式匹配
|
|
428
447
|
*
|
|
@@ -443,11 +462,7 @@ async function compileExpression<TModel extends FlowModel = FlowModel>(expressio
|
|
|
443
462
|
const singleMatch = expression.match(/^\s*\{\{\s*([^{}]+?)\s*\}\}\s*$/);
|
|
444
463
|
if (singleMatch) {
|
|
445
464
|
const inner = singleMatch[1];
|
|
446
|
-
|
|
447
|
-
if (dotPath) {
|
|
448
|
-
return await resolveDotOnlyPath(dotPath);
|
|
449
|
-
}
|
|
450
|
-
return await processExpression(inner, ctx);
|
|
465
|
+
return await resolveInnerExpression(inner);
|
|
451
466
|
}
|
|
452
467
|
|
|
453
468
|
/**
|
|
@@ -470,8 +485,7 @@ async function compileExpression<TModel extends FlowModel = FlowModel>(expressio
|
|
|
470
485
|
let result = expression;
|
|
471
486
|
|
|
472
487
|
for (const [fullMatch, innerExpr] of matches) {
|
|
473
|
-
const
|
|
474
|
-
const value = dotPath ? await resolveDotOnlyPath(dotPath) : await processExpression(innerExpr, ctx);
|
|
488
|
+
const value = await resolveInnerExpression(innerExpr);
|
|
475
489
|
if (value !== undefined) {
|
|
476
490
|
const replacement = typeof value === 'object' && value !== null ? JSON.stringify(value) : String(value);
|
|
477
491
|
result = result.replace(fullMatch, replacement);
|
|
@@ -0,0 +1,91 @@
|
|
|
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
|
+
/**
|
|
11
|
+
* 解析模块 URL,将相对路径转换为完整的 CDN URL
|
|
12
|
+
*
|
|
13
|
+
* @param url - 模块地址(支持相对路径或完整 URL)
|
|
14
|
+
* @param options - 可选配置
|
|
15
|
+
* @param options.addSuffix - 是否添加 ESM_CDN_SUFFIX 后缀(如 `+esm`),默认为 `true`
|
|
16
|
+
* @returns 解析后的完整 URL
|
|
17
|
+
*
|
|
18
|
+
* @example
|
|
19
|
+
* ```ts
|
|
20
|
+
* // 相对路径会被拼接上 CDN 前缀和后缀(默认添加)
|
|
21
|
+
* // 如果使用 esm.sh(默认),不需要后缀
|
|
22
|
+
* resolveModuleUrl('vue@3.4.0')
|
|
23
|
+
* // => 'https://esm.sh/vue@3.4.0'
|
|
24
|
+
*
|
|
25
|
+
* // 如果使用 jsdelivr,需要配置 ESM_CDN_SUFFIX='/+esm'
|
|
26
|
+
* // resolveModuleUrl('vue@3.4.0') => 'https://cdn.jsdelivr.net/npm/vue@3.4.0/+esm'
|
|
27
|
+
*
|
|
28
|
+
* // 不添加后缀(适用于 UMD 库或 CSS 文件)
|
|
29
|
+
* resolveModuleUrl('vue@3.4.0', { addSuffix: false })
|
|
30
|
+
* // => 'https://esm.sh/vue@3.4.0' (即使配置了 suffix 也不会添加)
|
|
31
|
+
*
|
|
32
|
+
* // 原始 URL(适用于 UMD 库)
|
|
33
|
+
* resolveModuleUrl('lodash@4.17.21/lodash.js', { raw: true })
|
|
34
|
+
* // => 'https://esm.sh/lodash@4.17.21/lodash.js?raw' (即使配置了 suffix 也不会添加)
|
|
35
|
+
*
|
|
36
|
+
* // 完整 URL 保持不变
|
|
37
|
+
* resolveModuleUrl('https://cdn.jsdelivr.net/npm/vue@3.4.0')
|
|
38
|
+
* // => 'https://cdn.jsdelivr.net/npm/vue@3.4.0'
|
|
39
|
+
* ```
|
|
40
|
+
*/
|
|
41
|
+
export function resolveModuleUrl(url: string, options?: { addSuffix?: boolean; raw?: boolean }): string {
|
|
42
|
+
if (!url || typeof url !== 'string') {
|
|
43
|
+
throw new Error('invalid url');
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
const u = url.trim();
|
|
47
|
+
|
|
48
|
+
// 如果是完整 URL(http:// 或 https://),直接返回
|
|
49
|
+
if (u.startsWith('http://') || u.startsWith('https://')) {
|
|
50
|
+
return u;
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
// 相对路径:拼接 CDN 前缀和后缀
|
|
54
|
+
const ESM_CDN_BASE_URL = (window as any)['__esm_cdn_base_url__'] || 'https://esm.sh';
|
|
55
|
+
const ESM_CDN_SUFFIX = options?.addSuffix ? (window as any)['__esm_cdn_suffix__'] || '' : '';
|
|
56
|
+
|
|
57
|
+
// 移除 base URL 末尾的斜杠,移除相对路径开头的斜杠
|
|
58
|
+
const base = ESM_CDN_BASE_URL.replace(/\/$/, '');
|
|
59
|
+
const path = u.replace(/^\//, '');
|
|
60
|
+
|
|
61
|
+
if (options?.raw) {
|
|
62
|
+
const sep = path.includes('?') ? '&' : '?';
|
|
63
|
+
return `${base}/${path}${sep}raw`;
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
return `${base}/${path}${ESM_CDN_SUFFIX}`;
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
/**
|
|
70
|
+
* 判断 URL 是否为 CSS 文件
|
|
71
|
+
*
|
|
72
|
+
* @param url - 文件 URL(支持带 query 和 hash,如 `example.css?v=123`)
|
|
73
|
+
* @returns 如果是 CSS 文件返回 `true`,否则返回 `false`
|
|
74
|
+
*
|
|
75
|
+
* @example
|
|
76
|
+
* ```ts
|
|
77
|
+
* isCssFile('style.css') // => true
|
|
78
|
+
* isCssFile('style.css?v=123') // => true
|
|
79
|
+
* isCssFile('style.css#section') // => true
|
|
80
|
+
* isCssFile('script.js') // => false
|
|
81
|
+
* ```
|
|
82
|
+
*/
|
|
83
|
+
export function isCssFile(url: string): boolean {
|
|
84
|
+
if (!url || typeof url !== 'string') {
|
|
85
|
+
return false;
|
|
86
|
+
}
|
|
87
|
+
|
|
88
|
+
// 去掉 query 和 hash 后判断文件扩展名
|
|
89
|
+
const pathPart = url.split('?')[0].split('#')[0];
|
|
90
|
+
return pathPart.endsWith('.css');
|
|
91
|
+
}
|
|
@@ -0,0 +1,46 @@
|
|
|
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
|
+
import { isRunJSValue, normalizeRunJSValue } from './runjsValue';
|
|
11
|
+
import { runjsWithSafeGlobals } from './safeGlobals';
|
|
12
|
+
|
|
13
|
+
/**
|
|
14
|
+
* Resolve an object's values, executing any RunJSValue entries via ctx.runjs.
|
|
15
|
+
*
|
|
16
|
+
* - Skips `undefined` values
|
|
17
|
+
* - Skips empty RunJS code (treated as not configured)
|
|
18
|
+
* - Throws when a RunJS execution fails
|
|
19
|
+
*/
|
|
20
|
+
export async function resolveRunJSObjectValues(ctx: unknown, raw: unknown): Promise<Record<string, any>> {
|
|
21
|
+
const out: Record<string, any> = {};
|
|
22
|
+
|
|
23
|
+
if (!raw || typeof raw !== 'object') return out;
|
|
24
|
+
if (Array.isArray(raw)) return out;
|
|
25
|
+
|
|
26
|
+
for (const [key, value] of Object.entries(raw as Record<string, any>)) {
|
|
27
|
+
if (typeof value === 'undefined') continue;
|
|
28
|
+
|
|
29
|
+
if (isRunJSValue(value)) {
|
|
30
|
+
const { code, version } = normalizeRunJSValue(value);
|
|
31
|
+
if (!code.trim()) continue;
|
|
32
|
+
const ret = await runjsWithSafeGlobals(ctx, code, { version });
|
|
33
|
+
if (!ret?.success) {
|
|
34
|
+
throw new Error(`RunJS execution failed for "${key}"`);
|
|
35
|
+
}
|
|
36
|
+
if (typeof ret.value !== 'undefined') {
|
|
37
|
+
out[key] = ret.value;
|
|
38
|
+
}
|
|
39
|
+
continue;
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
out[key] = value;
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
return out;
|
|
46
|
+
}
|