@nocobase/flow-engine 2.0.0-alpha.4 → 2.0.0-alpha.40

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 (462) hide show
  1. package/lib/BlockScopedFlowEngine.d.ts +23 -0
  2. package/lib/BlockScopedFlowEngine.js +90 -0
  3. package/lib/FlowContextProvider.d.ts +2 -2
  4. package/lib/FlowContextProvider.js +3 -3
  5. package/lib/FlowDefinition.d.ts +4 -2
  6. package/lib/JSRunner.js +3 -0
  7. package/lib/ViewScopedFlowEngine.d.ts +1 -1
  8. package/lib/ViewScopedFlowEngine.js +12 -0
  9. package/lib/acl/Acl.d.ts +1 -0
  10. package/lib/acl/Acl.js +11 -0
  11. package/lib/components/FieldModelRenderer.js +14 -6
  12. package/lib/components/FieldSkeleton.d.ts +10 -0
  13. package/lib/components/FieldSkeleton.js +64 -0
  14. package/lib/components/FlowContextSelector.js +7 -2
  15. package/lib/components/FlowModelRenderer.d.ts +3 -6
  16. package/lib/components/FlowModelRenderer.js +16 -47
  17. package/lib/components/FormItem.js +5 -1
  18. package/lib/components/MobilePopup.d.ts +20 -0
  19. package/lib/components/MobilePopup.js +102 -0
  20. package/lib/components/MobilePopup.style.d.ts +17 -0
  21. package/lib/components/MobilePopup.style.js +186 -0
  22. package/lib/components/index.d.ts +1 -0
  23. package/lib/components/index.js +3 -1
  24. package/lib/components/settings/independents/dropdown/FlowsDropdownButton.js +2 -2
  25. package/lib/components/settings/wrappers/contextual/DefaultSettingsIcon.js +17 -5
  26. package/lib/components/settings/wrappers/contextual/FlowsContextMenu.js +2 -2
  27. package/lib/components/settings/wrappers/contextual/FlowsFloatContextMenu.d.ts +2 -2
  28. package/lib/components/settings/wrappers/contextual/FlowsFloatContextMenu.js +35 -6
  29. package/lib/components/settings/wrappers/contextual/StepSettingsDialog.js +7 -1
  30. package/lib/components/variables/VariableInput.js +19 -5
  31. package/lib/components/variables/VariableTag.js +43 -2
  32. package/lib/components/variables/types.d.ts +2 -0
  33. package/lib/data-source/index.d.ts +15 -4
  34. package/lib/data-source/index.js +42 -13
  35. package/lib/data-source/sortCollectionsByInherits.d.ts +10 -0
  36. package/lib/data-source/sortCollectionsByInherits.js +71 -0
  37. package/lib/emitter.d.ts +6 -0
  38. package/lib/emitter.js +12 -0
  39. package/lib/executor/FlowExecutor.d.ts +4 -5
  40. package/lib/executor/FlowExecutor.js +168 -99
  41. package/lib/flow-registry/GlobalFlowRegistry.d.ts +1 -0
  42. package/lib/flow-registry/GlobalFlowRegistry.js +3 -0
  43. package/lib/flow-registry/InstanceFlowRegistry.d.ts +1 -0
  44. package/lib/flow-registry/InstanceFlowRegistry.js +3 -0
  45. package/lib/flowContext.d.ts +37 -5
  46. package/lib/flowContext.js +215 -87
  47. package/lib/flowEngine.d.ts +24 -1
  48. package/lib/flowEngine.js +56 -6
  49. package/lib/flowSettings.d.ts +2 -1
  50. package/lib/flowSettings.js +12 -8
  51. package/lib/hooks/useApplyAutoFlows.js +2 -1
  52. package/lib/index.d.ts +7 -1
  53. package/lib/index.js +32 -3
  54. package/lib/locale/en-US.json +4 -2
  55. package/lib/locale/index.d.ts +4 -0
  56. package/lib/locale/zh-CN.json +4 -2
  57. package/lib/models/CollectionFieldModel.d.ts +3 -0
  58. package/lib/models/CollectionFieldModel.js +48 -5
  59. package/lib/models/flowModel.d.ts +30 -29
  60. package/lib/models/flowModel.js +135 -98
  61. package/lib/models/forkFlowModel.d.ts +8 -4
  62. package/lib/models/forkFlowModel.js +38 -8
  63. package/lib/provider.d.ts +3 -1
  64. package/lib/provider.js +7 -5
  65. package/lib/resources/multiRecordResource.js +25 -1
  66. package/lib/resources/singleRecordResource.js +19 -1
  67. package/lib/resources/sqlResource.d.ts +1 -0
  68. package/lib/resources/sqlResource.js +20 -24
  69. package/lib/runjs-context/contexts/FormJSFieldItemRunJSContext.d.ts +1 -6
  70. package/lib/runjs-context/contexts/FormJSFieldItemRunJSContext.js +27 -20
  71. package/lib/runjs-context/contexts/JSBlockRunJSContext.d.ts +1 -6
  72. package/lib/runjs-context/contexts/JSBlockRunJSContext.js +46 -33
  73. package/lib/runjs-context/contexts/JSCollectionActionRunJSContext.d.ts +1 -2
  74. package/lib/runjs-context/contexts/JSCollectionActionRunJSContext.js +14 -15
  75. package/lib/runjs-context/contexts/{LinkageRunJSContext.d.ts → JSColumnRunJSContext.d.ts} +6 -3
  76. package/lib/runjs-context/contexts/JSColumnRunJSContext.js +78 -0
  77. package/lib/runjs-context/contexts/JSFieldRunJSContext.d.ts +1 -6
  78. package/lib/runjs-context/contexts/JSFieldRunJSContext.js +28 -24
  79. package/lib/runjs-context/contexts/JSItemRunJSContext.d.ts +1 -6
  80. package/lib/runjs-context/contexts/JSItemRunJSContext.js +24 -20
  81. package/lib/runjs-context/contexts/JSRecordActionRunJSContext.d.ts +1 -2
  82. package/lib/runjs-context/contexts/JSRecordActionRunJSContext.js +16 -17
  83. package/lib/runjs-context/contexts/base.d.ts +9 -0
  84. package/lib/runjs-context/contexts/base.js +183 -0
  85. package/lib/runjs-context/helpers.d.ts +5 -2
  86. package/lib/runjs-context/helpers.js +36 -27
  87. package/lib/runjs-context/registry.d.ts +7 -4
  88. package/lib/runjs-context/registry.js +10 -42
  89. package/lib/runjs-context/setup.d.ts +9 -0
  90. package/lib/runjs-context/setup.js +82 -0
  91. package/lib/runjs-context/snippets/global/{copy-record-json.snippet.js → api-request.snippet.js} +25 -10
  92. package/lib/runjs-context/snippets/global/clipboard-copy-text.snippet.js +61 -0
  93. package/lib/runjs-context/snippets/global/{view-navigation-push.snippet.js → import-esm.snippet.js} +26 -12
  94. package/lib/runjs-context/snippets/global/message-error.snippet.js +6 -0
  95. package/lib/runjs-context/snippets/global/message-success.snippet.js +6 -0
  96. package/lib/runjs-context/snippets/global/notification-open.snippet.d.ts +3 -8
  97. package/lib/runjs-context/snippets/global/notification-open.snippet.js +8 -1
  98. package/lib/runjs-context/snippets/global/open-view-dialog.snippet.js +10 -3
  99. package/lib/runjs-context/snippets/global/open-view-drawer.snippet.js +10 -3
  100. package/lib/runjs-context/snippets/global/query-selector.snippet.js +53 -0
  101. package/lib/runjs-context/snippets/global/require-amd.snippet.d.ts +11 -0
  102. package/lib/runjs-context/snippets/global/{requireAsync.snippet.js → require-amd.snippet.js} +16 -13
  103. package/lib/runjs-context/snippets/global/window-open.snippet.d.ts +3 -8
  104. package/lib/runjs-context/snippets/global/window-open.snippet.js +8 -1
  105. package/lib/runjs-context/snippets/index.d.ts +14 -3
  106. package/lib/runjs-context/snippets/index.js +161 -40
  107. package/lib/runjs-context/snippets/scene/block/add-event-listener.snippet.d.ts +11 -0
  108. package/lib/runjs-context/snippets/scene/{jsblock → block}/add-event-listener.snippet.js +11 -2
  109. package/lib/runjs-context/snippets/scene/block/api-fetch-render-list.snippet.d.ts +11 -0
  110. package/lib/runjs-context/snippets/scene/block/api-fetch-render-list.snippet.js +64 -0
  111. package/lib/runjs-context/snippets/scene/block/chartjs-bar.snippet.d.ts +11 -0
  112. package/lib/runjs-context/snippets/scene/block/chartjs-bar.snippet.js +99 -0
  113. package/lib/runjs-context/snippets/{libs → scene/block}/echarts-init.snippet.js +24 -7
  114. package/lib/runjs-context/snippets/scene/block/render-button-handler.snippet.d.ts +11 -0
  115. package/lib/runjs-context/snippets/scene/{jsblock → block}/render-button-handler.snippet.js +17 -9
  116. package/lib/runjs-context/snippets/scene/block/render-iframe.snippet.d.ts +11 -0
  117. package/lib/runjs-context/snippets/scene/block/render-iframe.snippet.js +57 -0
  118. package/lib/runjs-context/snippets/scene/block/render-info-card.snippet.d.ts +11 -0
  119. package/lib/runjs-context/snippets/scene/block/render-info-card.snippet.js +71 -0
  120. package/lib/runjs-context/snippets/scene/block/render-react-jsx.snippet.d.ts +11 -0
  121. package/lib/runjs-context/snippets/scene/{jsblock/render-card.snippet.js → block/render-react-jsx.snippet.js} +26 -13
  122. package/lib/runjs-context/snippets/scene/block/render-react.snippet.d.ts +11 -0
  123. package/lib/runjs-context/snippets/scene/{jsblock → block}/render-react.snippet.js +18 -17
  124. package/lib/runjs-context/snippets/scene/block/render-statistics.snippet.d.ts +11 -0
  125. package/lib/runjs-context/snippets/scene/block/render-statistics.snippet.js +95 -0
  126. package/lib/runjs-context/snippets/scene/block/render-timeline.snippet.d.ts +11 -0
  127. package/lib/runjs-context/snippets/scene/block/render-timeline.snippet.js +84 -0
  128. package/lib/runjs-context/snippets/scene/block/resource-example.snippet.d.ts +11 -0
  129. package/lib/runjs-context/snippets/scene/block/resource-example.snippet.js +60 -0
  130. package/lib/runjs-context/snippets/scene/block/three-users-orbit.snippet.d.ts +11 -0
  131. package/lib/runjs-context/snippets/scene/block/three-users-orbit.snippet.js +283 -0
  132. package/lib/runjs-context/snippets/scene/block/vue-component.snippet.d.ts +11 -0
  133. package/lib/runjs-context/snippets/scene/block/vue-component.snippet.js +124 -0
  134. package/lib/runjs-context/snippets/scene/detail/color-by-value.snippet.d.ts +11 -0
  135. package/lib/runjs-context/snippets/scene/{jsfield → detail}/color-by-value.snippet.js +13 -3
  136. package/lib/runjs-context/snippets/scene/detail/copy-to-clipboard.snippet.d.ts +11 -0
  137. package/lib/runjs-context/snippets/{global → scene/detail}/copy-to-clipboard.snippet.js +28 -6
  138. package/lib/runjs-context/snippets/scene/detail/format-number.snippet.d.ts +11 -0
  139. package/lib/runjs-context/snippets/scene/{jsfield → detail}/format-number.snippet.js +13 -3
  140. package/lib/runjs-context/snippets/scene/detail/innerHTML-value.snippet.d.ts +11 -0
  141. package/lib/runjs-context/snippets/scene/{jsfield → detail}/innerHTML-value.snippet.js +13 -3
  142. package/lib/runjs-context/snippets/scene/detail/percentage-bar.snippet.d.ts +11 -0
  143. package/lib/runjs-context/snippets/scene/detail/percentage-bar.snippet.js +82 -0
  144. package/lib/runjs-context/snippets/scene/detail/relative-time.snippet.d.ts +11 -0
  145. package/lib/runjs-context/snippets/scene/detail/relative-time.snippet.js +80 -0
  146. package/lib/runjs-context/snippets/scene/detail/status-tag.snippet.d.ts +11 -0
  147. package/lib/runjs-context/snippets/scene/detail/status-tag.snippet.js +74 -0
  148. package/lib/runjs-context/snippets/scene/form/calculate-total.snippet.d.ts +11 -0
  149. package/lib/runjs-context/snippets/scene/form/calculate-total.snippet.js +63 -0
  150. package/lib/runjs-context/snippets/scene/form/cascade-select.snippet.d.ts +11 -0
  151. package/lib/runjs-context/snippets/scene/form/cascade-select.snippet.js +81 -0
  152. package/lib/runjs-context/snippets/scene/form/conditional-required.snippet.d.ts +11 -0
  153. package/lib/runjs-context/snippets/scene/form/conditional-required.snippet.js +64 -0
  154. package/lib/runjs-context/snippets/scene/form/copy-field-values.snippet.d.ts +11 -0
  155. package/lib/runjs-context/snippets/scene/form/copy-field-values.snippet.js +74 -0
  156. package/lib/runjs-context/snippets/scene/form/render-basic.snippet.d.ts +11 -0
  157. package/lib/runjs-context/snippets/scene/{jsitem → form}/render-basic.snippet.js +11 -2
  158. package/lib/runjs-context/snippets/scene/form/set-disabled.snippet.d.ts +11 -0
  159. package/lib/runjs-context/snippets/scene/{linkage → form}/set-disabled.snippet.js +12 -3
  160. package/lib/runjs-context/snippets/scene/form/set-field-value.snippet.d.ts +11 -0
  161. package/lib/runjs-context/snippets/scene/{linkage → form}/set-field-value.snippet.js +12 -3
  162. package/lib/runjs-context/snippets/scene/form/set-required.snippet.d.ts +11 -0
  163. package/lib/runjs-context/snippets/scene/{linkage → form}/set-required.snippet.js +12 -3
  164. package/lib/runjs-context/snippets/scene/form/toggle-multiple-fields.snippet.d.ts +11 -0
  165. package/lib/runjs-context/snippets/scene/form/toggle-multiple-fields.snippet.js +67 -0
  166. package/lib/runjs-context/snippets/scene/form/toggle-visible.snippet.d.ts +11 -0
  167. package/lib/runjs-context/snippets/scene/{linkage → form}/toggle-visible.snippet.js +12 -3
  168. package/lib/runjs-context/snippets/scene/table/cell-open-dialog.snippet.d.ts +11 -0
  169. package/lib/runjs-context/snippets/scene/table/cell-open-dialog.snippet.js +64 -0
  170. package/lib/runjs-context/snippets/scene/table/collection-selected-count.snippet.d.ts +11 -0
  171. package/lib/runjs-context/snippets/scene/{actions → table}/collection-selected-count.snippet.js +11 -2
  172. package/lib/runjs-context/snippets/scene/table/concat-fields.snippet.d.ts +11 -0
  173. package/lib/runjs-context/snippets/scene/table/concat-fields.snippet.js +79 -0
  174. package/lib/runjs-context/snippets/scene/table/destroy-selected.snippet.d.ts +11 -0
  175. package/lib/runjs-context/snippets/{global/log-json-record.snippet.js → scene/table/destroy-selected.snippet.js} +24 -11
  176. package/lib/runjs-context/snippets/scene/table/export-selected-json.snippet.d.ts +11 -0
  177. package/lib/runjs-context/snippets/scene/table/export-selected-json.snippet.js +64 -0
  178. package/lib/runjs-context/snippets/scene/table/iterate-selected-rows.snippet.d.ts +11 -0
  179. package/lib/runjs-context/snippets/scene/{actions → table}/iterate-selected-rows.snippet.js +11 -2
  180. package/lib/runjs-context/snippets/types.d.ts +9 -1
  181. package/lib/scheduler/ModelOperationScheduler.d.ts +51 -0
  182. package/lib/scheduler/ModelOperationScheduler.js +262 -0
  183. package/lib/types.d.ts +28 -3
  184. package/lib/types.js +4 -3
  185. package/lib/utils/associationObjectVariable.d.ts +32 -0
  186. package/lib/utils/associationObjectVariable.js +157 -0
  187. package/lib/utils/buildSettingsViewInputArgs.d.ts +19 -0
  188. package/lib/utils/buildSettingsViewInputArgs.js +75 -0
  189. package/lib/utils/createEphemeralContext.d.ts +13 -0
  190. package/lib/utils/createEphemeralContext.js +140 -0
  191. package/lib/utils/flows.d.ts +10 -0
  192. package/lib/{runjs-context/snippets/global/api-request-post.snippet.js → utils/flows.js} +21 -15
  193. package/lib/utils/index.d.ts +7 -2
  194. package/lib/utils/index.js +19 -2
  195. package/lib/utils/jsxTransform.d.ts +15 -0
  196. package/lib/utils/jsxTransform.js +68 -0
  197. package/lib/utils/params-resolvers.js +3 -3
  198. package/lib/utils/parsePathnameToViewParams.d.ts +1 -1
  199. package/lib/utils/parsePathnameToViewParams.js +41 -5
  200. package/lib/utils/pruneFilter.d.ts +21 -0
  201. package/lib/{runjs-context/snippets/global/try-catch-async.snippet.js → utils/pruneFilter.js} +24 -16
  202. package/lib/utils/safeGlobals.d.ts +5 -3
  203. package/lib/utils/safeGlobals.js +40 -0
  204. package/lib/utils/schema-utils.js +2 -2
  205. package/lib/utils/serverContextParams.d.ts +1 -0
  206. package/lib/utils/translation.d.ts +4 -1
  207. package/lib/utils/translation.js +6 -2
  208. package/lib/utils/variablesParams.d.ts +9 -5
  209. package/lib/utils/variablesParams.js +47 -36
  210. package/lib/views/DrawerComponent.js +21 -2
  211. package/lib/views/PageComponent.js +2 -1
  212. package/lib/views/ViewNavigation.d.ts +3 -9
  213. package/lib/views/ViewNavigation.js +16 -2
  214. package/lib/views/createViewMeta.d.ts +29 -1
  215. package/lib/views/createViewMeta.js +338 -72
  216. package/lib/views/index.d.ts +1 -0
  217. package/lib/views/index.js +3 -0
  218. package/lib/views/useDialog.d.ts +8 -8
  219. package/lib/views/useDialog.js +8 -7
  220. package/lib/views/useDrawer.d.ts +8 -8
  221. package/lib/views/useDrawer.js +43 -28
  222. package/lib/views/usePage.d.ts +8 -8
  223. package/lib/views/usePage.js +8 -7
  224. package/package.json +6 -3
  225. package/src/BlockScopedFlowEngine.ts +86 -0
  226. package/src/FlowContextProvider.tsx +4 -2
  227. package/src/JSRunner.ts +3 -0
  228. package/src/ViewScopedFlowEngine.ts +15 -1
  229. package/src/__tests__/JSRunner.test.ts +62 -53
  230. package/src/__tests__/blockScopedFlowEngine.test.ts +154 -0
  231. package/src/__tests__/createViewMeta.popup.test.ts +132 -0
  232. package/src/__tests__/flow-engine.test.ts +3 -0
  233. package/src/__tests__/flowContext.test.ts +52 -0
  234. package/src/__tests__/flowContextCreateJSRunner.test.ts +163 -0
  235. package/src/__tests__/flowEngine.saveModel.test.ts +4 -0
  236. package/src/__tests__/flowRunJSContextDefine.test.ts +508 -0
  237. package/src/__tests__/flowSettings.open.test.tsx +2 -0
  238. package/src/__tests__/flowSettings.test.ts +2 -0
  239. package/src/__tests__/globalFlowRegistry.test.ts +1 -1
  240. package/src/__tests__/modelOperationScheduler.test.ts +346 -0
  241. package/src/__tests__/objectVariable.test.ts +464 -0
  242. package/src/__tests__/runjsContext.test.ts +216 -35
  243. package/src/__tests__/runjsContextImplementations.test.ts +217 -0
  244. package/src/__tests__/runjsContextRuntime.test.ts +269 -0
  245. package/src/__tests__/runjsEdgeCases.test.ts +281 -0
  246. package/src/__tests__/runjsLocales.test.ts +36 -0
  247. package/src/__tests__/runjsRuntimeFeatures.test.ts +449 -0
  248. package/src/__tests__/runjsSnippets.test.ts +140 -0
  249. package/src/__tests__/viewScopedFlowEngine.test.ts +3 -3
  250. package/src/acl/Acl.tsx +14 -0
  251. package/src/acl/__tests__/Acl.test.tsx +43 -0
  252. package/src/components/DynamicFlowsEditor.tsx +3 -4
  253. package/src/components/FieldModelRenderer.tsx +20 -7
  254. package/src/components/FieldSkeleton.tsx +27 -0
  255. package/src/components/FlowContextSelector.tsx +6 -2
  256. package/src/components/FlowModelRenderer.tsx +33 -81
  257. package/src/components/FormItem.tsx +8 -1
  258. package/src/components/MobilePopup.style.ts +220 -0
  259. package/src/components/MobilePopup.tsx +86 -0
  260. package/src/components/__tests__/flow-model-render-error-fallback.test.tsx +6 -6
  261. package/src/components/index.ts +1 -0
  262. package/src/components/settings/independents/dropdown/FlowsDropdownButton.tsx +1 -1
  263. package/src/components/settings/wrappers/contextual/DefaultSettingsIcon.tsx +17 -4
  264. package/src/components/settings/wrappers/contextual/FlowsContextMenu.tsx +1 -1
  265. package/src/components/settings/wrappers/contextual/FlowsFloatContextMenu.tsx +39 -10
  266. package/src/components/settings/wrappers/contextual/StepSettingsDialog.tsx +14 -1
  267. package/src/components/settings/wrappers/contextual/__tests__/DefaultSettingsIcon.test.tsx +425 -0
  268. package/src/components/subModel/__tests__/AddSubModelButton.test.tsx +5 -7
  269. package/src/components/variables/VariableInput.tsx +25 -5
  270. package/src/components/variables/VariableTag.tsx +54 -2
  271. package/src/components/variables/types.ts +2 -0
  272. package/src/data-source/__tests__/sortCollectionsByInherits.test.ts +125 -0
  273. package/src/data-source/index.ts +42 -11
  274. package/src/data-source/sortCollectionsByInherits.ts +61 -0
  275. package/src/emitter.ts +14 -0
  276. package/src/executor/FlowExecutor.ts +213 -119
  277. package/src/executor/__tests__/ctx-defs-injection.test.ts +197 -0
  278. package/src/executor/__tests__/flowExecutor.test.ts +151 -5
  279. package/src/flow-registry/GlobalFlowRegistry.ts +1 -0
  280. package/src/flow-registry/InstanceFlowRegistry.ts +1 -0
  281. package/src/flow-registry/__tests__/globalFlowRegistry.test.ts +54 -0
  282. package/src/flowContext.ts +290 -104
  283. package/src/flowEngine.ts +74 -6
  284. package/src/flowSettings.ts +9 -4
  285. package/src/hooks/useApplyAutoFlows.ts +3 -1
  286. package/src/index.ts +12 -1
  287. package/src/locale/en-US.json +4 -2
  288. package/src/locale/zh-CN.json +4 -2
  289. package/src/models/CollectionFieldModel.tsx +56 -7
  290. package/src/models/__tests__/dispatchEvent.behavior.test.ts +169 -0
  291. package/src/models/__tests__/flowModel.getFlows.sort.test.ts +33 -9
  292. package/src/models/__tests__/flowModel.scheduleModelOperation.test.tsx +129 -0
  293. package/src/models/__tests__/flowModel.test.ts +234 -111
  294. package/src/models/__tests__/forkFlowModel.test.ts +40 -7
  295. package/src/models/flowModel.tsx +180 -132
  296. package/src/models/forkFlowModel.ts +48 -8
  297. package/src/provider.tsx +10 -7
  298. package/src/resources/multiRecordResource.ts +28 -1
  299. package/src/resources/singleRecordResource.ts +19 -1
  300. package/src/resources/sqlResource.ts +20 -25
  301. package/src/runjs-context/contexts/FormJSFieldItemRunJSContext.ts +28 -21
  302. package/src/runjs-context/contexts/JSBlockRunJSContext.ts +46 -34
  303. package/src/runjs-context/contexts/JSCollectionActionRunJSContext.ts +15 -16
  304. package/src/runjs-context/contexts/JSColumnRunJSContext.ts +58 -0
  305. package/src/runjs-context/contexts/JSFieldRunJSContext.ts +30 -25
  306. package/src/runjs-context/contexts/JSItemRunJSContext.ts +25 -21
  307. package/src/runjs-context/contexts/JSRecordActionRunJSContext.ts +17 -18
  308. package/src/runjs-context/contexts/base.ts +171 -0
  309. package/src/runjs-context/helpers.ts +32 -30
  310. package/src/runjs-context/registry.ts +16 -47
  311. package/src/runjs-context/setup.ts +51 -0
  312. package/src/runjs-context/snippets/global/api-request.snippet.ts +38 -0
  313. package/src/runjs-context/snippets/global/clipboard-copy-text.snippet.ts +42 -0
  314. package/src/runjs-context/snippets/global/import-esm.snippet.ts +39 -0
  315. package/src/runjs-context/snippets/global/message-error.snippet.ts +6 -0
  316. package/src/runjs-context/snippets/global/message-success.snippet.ts +6 -0
  317. package/src/runjs-context/snippets/global/notification-open.snippet.ts +11 -1
  318. package/src/runjs-context/snippets/global/open-view-dialog.snippet.ts +10 -3
  319. package/src/runjs-context/snippets/global/open-view-drawer.snippet.ts +10 -3
  320. package/src/runjs-context/snippets/global/query-selector.snippet.ts +34 -0
  321. package/src/runjs-context/snippets/global/require-amd.snippet.ts +30 -0
  322. package/src/runjs-context/snippets/global/window-open.snippet.ts +11 -1
  323. package/src/runjs-context/snippets/index.ts +177 -39
  324. package/src/runjs-context/snippets/scene/{jsblock → block}/add-event-listener.snippet.ts +14 -2
  325. package/src/runjs-context/snippets/scene/block/api-fetch-render-list.snippet.ts +45 -0
  326. package/src/runjs-context/snippets/scene/block/chartjs-bar.snippet.ts +80 -0
  327. package/src/runjs-context/snippets/scene/block/echarts-init.snippet.ts +44 -0
  328. package/src/runjs-context/snippets/scene/block/render-button-handler.snippet.ts +35 -0
  329. package/src/runjs-context/snippets/scene/block/render-iframe.snippet.ts +38 -0
  330. package/src/runjs-context/snippets/scene/block/render-info-card.snippet.ts +52 -0
  331. package/src/runjs-context/snippets/scene/block/render-react-jsx.snippet.ts +39 -0
  332. package/src/runjs-context/snippets/scene/block/render-react.snippet.ts +38 -0
  333. package/src/runjs-context/snippets/scene/block/render-statistics.snippet.ts +76 -0
  334. package/src/runjs-context/snippets/scene/block/render-timeline.snippet.ts +65 -0
  335. package/src/runjs-context/snippets/scene/block/resource-example.snippet.ts +46 -0
  336. package/src/runjs-context/snippets/scene/block/three-users-orbit.snippet.ts +264 -0
  337. package/src/runjs-context/snippets/scene/block/vue-component.snippet.ts +105 -0
  338. package/src/runjs-context/snippets/scene/detail/color-by-value.snippet.ts +33 -0
  339. package/src/runjs-context/snippets/scene/detail/copy-to-clipboard.snippet.ts +45 -0
  340. package/src/runjs-context/snippets/scene/detail/format-number.snippet.ts +32 -0
  341. package/src/runjs-context/snippets/scene/detail/innerHTML-value.snippet.ts +31 -0
  342. package/src/runjs-context/snippets/scene/detail/percentage-bar.snippet.ts +63 -0
  343. package/src/runjs-context/snippets/scene/detail/relative-time.snippet.ts +61 -0
  344. package/src/runjs-context/snippets/scene/detail/status-tag.snippet.ts +55 -0
  345. package/src/runjs-context/snippets/scene/form/calculate-total.snippet.ts +44 -0
  346. package/src/runjs-context/snippets/scene/form/cascade-select.snippet.ts +62 -0
  347. package/src/runjs-context/snippets/scene/form/conditional-required.snippet.ts +45 -0
  348. package/src/runjs-context/snippets/scene/form/copy-field-values.snippet.ts +55 -0
  349. package/src/runjs-context/snippets/scene/{jsitem → form}/render-basic.snippet.ts +14 -2
  350. package/src/runjs-context/snippets/scene/{linkage → form}/set-disabled.snippet.ts +15 -3
  351. package/src/runjs-context/snippets/scene/{linkage → form}/set-field-value.snippet.ts +15 -3
  352. package/src/runjs-context/snippets/scene/{linkage → form}/set-required.snippet.ts +15 -3
  353. package/src/runjs-context/snippets/scene/form/toggle-multiple-fields.snippet.ts +48 -0
  354. package/src/runjs-context/snippets/scene/{linkage → form}/toggle-visible.snippet.ts +15 -3
  355. package/src/runjs-context/snippets/scene/table/cell-open-dialog.snippet.ts +45 -0
  356. package/src/runjs-context/snippets/scene/{actions → table}/collection-selected-count.snippet.ts +14 -2
  357. package/src/runjs-context/snippets/scene/table/concat-fields.snippet.ts +60 -0
  358. package/src/runjs-context/snippets/scene/table/destroy-selected.snippet.ts +36 -0
  359. package/src/runjs-context/snippets/scene/table/export-selected-json.snippet.ts +45 -0
  360. package/src/runjs-context/snippets/scene/{actions → table}/iterate-selected-rows.snippet.ts +14 -2
  361. package/src/runjs-context/snippets/types.ts +5 -1
  362. package/src/scheduler/ModelOperationScheduler.ts +304 -0
  363. package/src/types.ts +34 -0
  364. package/src/utils/__tests__/flows.test.ts +65 -0
  365. package/src/utils/__tests__/jsxTransform.test.ts +38 -0
  366. package/src/utils/__tests__/parsePathnameToViewParams.test.ts +25 -0
  367. package/src/utils/__tests__/pruneFilter.test.ts +38 -0
  368. package/src/utils/__tests__/safeGlobals.test.ts +22 -1
  369. package/src/utils/associationObjectVariable.ts +180 -0
  370. package/src/utils/buildSettingsViewInputArgs.ts +72 -0
  371. package/src/utils/createEphemeralContext.ts +142 -0
  372. package/src/utils/flows.ts +23 -0
  373. package/src/utils/index.ts +10 -2
  374. package/src/utils/jsxTransform.ts +39 -0
  375. package/src/utils/params-resolvers.ts +2 -2
  376. package/src/utils/parsePathnameToViewParams.ts +50 -6
  377. package/src/utils/pruneFilter.ts +41 -0
  378. package/src/utils/safeGlobals.ts +49 -3
  379. package/src/utils/schema-utils.ts +1 -1
  380. package/src/utils/serverContextParams.ts +1 -0
  381. package/src/utils/translation.ts +7 -2
  382. package/src/utils/variablesParams.ts +50 -38
  383. package/src/views/DrawerComponent.tsx +21 -2
  384. package/src/views/PageComponent.tsx +1 -1
  385. package/src/views/ViewNavigation.ts +20 -12
  386. package/src/views/__tests__/ViewNavigation.test.ts +10 -0
  387. package/src/views/createViewMeta.ts +393 -70
  388. package/src/views/index.tsx +1 -0
  389. package/src/views/useDialog.tsx +12 -10
  390. package/src/views/useDrawer.tsx +62 -37
  391. package/src/views/usePage.tsx +13 -10
  392. package/lib/runjs-context/contexts/FlowRunJSContext.d.ts +0 -38
  393. package/lib/runjs-context/contexts/FlowRunJSContext.js +0 -217
  394. package/lib/runjs-context/contexts/LinkageRunJSContext.js +0 -62
  395. package/lib/runjs-context/index.d.ts +0 -19
  396. package/lib/runjs-context/index.js +0 -57
  397. package/lib/runjs-context/snippets/global/api-request-get.snippet.d.ts +0 -16
  398. package/lib/runjs-context/snippets/global/api-request-get.snippet.js +0 -42
  399. package/lib/runjs-context/snippets/global/api-request-post.snippet.d.ts +0 -16
  400. package/lib/runjs-context/snippets/global/console-log-ctx.snippet.d.ts +0 -16
  401. package/lib/runjs-context/snippets/global/console-log-ctx.snippet.js +0 -41
  402. package/lib/runjs-context/snippets/global/requireAsync.snippet.d.ts +0 -16
  403. package/lib/runjs-context/snippets/global/sleep.snippet.d.ts +0 -16
  404. package/lib/runjs-context/snippets/global/sleep.snippet.js +0 -43
  405. package/lib/runjs-context/snippets/global/try-catch-async.snippet.d.ts +0 -16
  406. package/lib/runjs-context/snippets/libs/echarts-init.snippet.d.ts +0 -15
  407. package/lib/runjs-context/snippets/scene/actions/collection-selected-count.snippet.d.ts +0 -15
  408. package/lib/runjs-context/snippets/scene/actions/iterate-selected-rows.snippet.d.ts +0 -15
  409. package/lib/runjs-context/snippets/scene/actions/record-id-message.snippet.d.ts +0 -15
  410. package/lib/runjs-context/snippets/scene/actions/record-id-message.snippet.js +0 -43
  411. package/lib/runjs-context/snippets/scene/actions/run-action-basic.snippet.d.ts +0 -15
  412. package/lib/runjs-context/snippets/scene/actions/run-action-basic.snippet.js +0 -40
  413. package/lib/runjs-context/snippets/scene/jsblock/add-event-listener.snippet.d.ts +0 -15
  414. package/lib/runjs-context/snippets/scene/jsblock/append-style.snippet.d.ts +0 -15
  415. package/lib/runjs-context/snippets/scene/jsblock/append-style.snippet.js +0 -42
  416. package/lib/runjs-context/snippets/scene/jsblock/jsx-mount.snippet.d.ts +0 -15
  417. package/lib/runjs-context/snippets/scene/jsblock/jsx-mount.snippet.js +0 -46
  418. package/lib/runjs-context/snippets/scene/jsblock/jsx-unmount.snippet.d.ts +0 -15
  419. package/lib/runjs-context/snippets/scene/jsblock/jsx-unmount.snippet.js +0 -41
  420. package/lib/runjs-context/snippets/scene/jsblock/render-basic.snippet.d.ts +0 -15
  421. package/lib/runjs-context/snippets/scene/jsblock/render-basic.snippet.js +0 -41
  422. package/lib/runjs-context/snippets/scene/jsblock/render-button-handler.snippet.d.ts +0 -15
  423. package/lib/runjs-context/snippets/scene/jsblock/render-react.snippet.d.ts +0 -15
  424. package/lib/runjs-context/snippets/scene/jsfield/color-by-value.snippet.d.ts +0 -15
  425. package/lib/runjs-context/snippets/scene/jsfield/format-number.snippet.d.ts +0 -15
  426. package/lib/runjs-context/snippets/scene/jsfield/innerHTML-value.snippet.d.ts +0 -15
  427. package/lib/runjs-context/snippets/scene/jsitem/render-basic.snippet.d.ts +0 -15
  428. package/lib/runjs-context/snippets/scene/linkage/set-disabled.snippet.d.ts +0 -15
  429. package/lib/runjs-context/snippets/scene/linkage/set-field-value.snippet.d.ts +0 -15
  430. package/lib/runjs-context/snippets/scene/linkage/set-required.snippet.d.ts +0 -15
  431. package/lib/runjs-context/snippets/scene/linkage/toggle-visible.snippet.d.ts +0 -15
  432. package/src/runjs-context/contexts/FlowRunJSContext.ts +0 -190
  433. package/src/runjs-context/contexts/LinkageRunJSContext.ts +0 -35
  434. package/src/runjs-context/index.ts +0 -20
  435. package/src/runjs-context/snippets/global/api-request-get.snippet.ts +0 -20
  436. package/src/runjs-context/snippets/global/api-request-post.snippet.ts +0 -20
  437. package/src/runjs-context/snippets/global/console-log-ctx.snippet.ts +0 -19
  438. package/src/runjs-context/snippets/global/copy-record-json.snippet.ts +0 -21
  439. package/src/runjs-context/snippets/global/copy-to-clipboard.snippet.ts +0 -21
  440. package/src/runjs-context/snippets/global/log-json-record.snippet.ts +0 -21
  441. package/src/runjs-context/snippets/global/requireAsync.snippet.ts +0 -24
  442. package/src/runjs-context/snippets/global/sleep.snippet.ts +0 -21
  443. package/src/runjs-context/snippets/global/try-catch-async.snippet.ts +0 -22
  444. package/src/runjs-context/snippets/global/view-navigation-push.snippet.ts +0 -23
  445. package/src/runjs-context/snippets/libs/echarts-init.snippet.ts +0 -24
  446. package/src/runjs-context/snippets/scene/actions/record-id-message.snippet.ts +0 -21
  447. package/src/runjs-context/snippets/scene/actions/run-action-basic.snippet.ts +0 -18
  448. package/src/runjs-context/snippets/scene/jsblock/append-style.snippet.ts +0 -20
  449. package/src/runjs-context/snippets/scene/jsblock/jsx-mount.snippet.ts +0 -24
  450. package/src/runjs-context/snippets/scene/jsblock/jsx-unmount.snippet.ts +0 -19
  451. package/src/runjs-context/snippets/scene/jsblock/render-basic.snippet.ts +0 -24
  452. package/src/runjs-context/snippets/scene/jsblock/render-button-handler.snippet.ts +0 -24
  453. package/src/runjs-context/snippets/scene/jsblock/render-card.snippet.ts +0 -30
  454. package/src/runjs-context/snippets/scene/jsblock/render-react.snippet.ts +0 -34
  455. package/src/runjs-context/snippets/scene/jsfield/color-by-value.snippet.ts +0 -20
  456. package/src/runjs-context/snippets/scene/jsfield/format-number.snippet.ts +0 -19
  457. package/src/runjs-context/snippets/scene/jsfield/innerHTML-value.snippet.ts +0 -18
  458. /package/lib/runjs-context/snippets/global/{copy-record-json.snippet.d.ts → api-request.snippet.d.ts} +0 -0
  459. /package/lib/runjs-context/snippets/global/{copy-to-clipboard.snippet.d.ts → clipboard-copy-text.snippet.d.ts} +0 -0
  460. /package/lib/runjs-context/snippets/global/{log-json-record.snippet.d.ts → import-esm.snippet.d.ts} +0 -0
  461. /package/lib/runjs-context/snippets/global/{view-navigation-push.snippet.d.ts → query-selector.snippet.d.ts} +0 -0
  462. /package/lib/runjs-context/snippets/scene/{jsblock/render-card.snippet.d.ts → block/echarts-init.snippet.d.ts} +0 -0
@@ -11,14 +11,16 @@ import { ISchema } from '@formily/json-schema';
11
11
  import { observable } from '@formily/reactive';
12
12
  import { APIClient } from '@nocobase/sdk';
13
13
  import type { Router } from '@remix-run/router';
14
- import * as antd from 'antd';
15
14
  import { MessageInstance } from 'antd/es/message/interface';
15
+ import * as antd from 'antd';
16
16
  import type { HookAPI } from 'antd/es/modal/useModal';
17
17
  import { NotificationInstance } from 'antd/es/notification/interface';
18
18
  import _ from 'lodash';
19
19
  import pino from 'pino';
20
20
  import qs from 'qs';
21
21
  import React, { createRef } from 'react';
22
+ import * as ReactDOMClient from 'react-dom/client';
23
+ import { ElementProxy } from './ElementProxy';
22
24
  import type { Location } from 'react-router-dom';
23
25
  import { ACL } from './acl/Acl';
24
26
  import { ContextPathProxy } from './ContextPathProxy';
@@ -26,21 +28,11 @@ import { DataSource, DataSourceManager } from './data-source';
26
28
  import { FlowEngine } from './flowEngine';
27
29
  import { FlowI18n } from './flowI18n';
28
30
  import { JSRunner, JSRunnerOptions } from './JSRunner';
29
- import { createJSRunnerWithVersion } from './runjs-context';
30
- import { FlowModel, ForkFlowModel } from './models';
31
- import {
32
- APIResource,
33
- BaseRecordResource,
34
- FlowResource,
35
- FlowSQLRepository,
36
- MultiRecordResource,
37
- SingleRecordResource,
38
- SQLResource,
39
- } from './resources';
31
+ import type { FlowModel } from './models/flowModel';
32
+ import type { ForkFlowModel } from './models/forkFlowModel';
33
+ import { FlowResource, FlowSQLRepository } from './resources';
40
34
  import type { ActionDefinition, EventDefinition, ResourceType } from './types';
41
35
  import {
42
- createSafeDocument,
43
- createSafeWindow,
44
36
  escapeT,
45
37
  extractPropertyPath,
46
38
  extractUsedVariablePaths,
@@ -53,6 +45,9 @@ import { enqueueVariablesResolve, JSONValue } from './utils/params-resolvers';
53
45
  import type { RecordRef } from './utils/serverContextParams';
54
46
  import { buildServerContextParams as _buildServerContextParams } from './utils/serverContextParams';
55
47
  import { FlowView, FlowViewer } from './views/FlowView';
48
+ import { RunJSContextRegistry, getModelClassName } from './runjs-context/registry';
49
+ import { createEphemeralContext } from './utils/createEphemeralContext';
50
+ import dayjs from 'dayjs';
56
51
 
57
52
  // Helper: detect a RecordRef-like object
58
53
  function isRecordRefLike(val: any): boolean {
@@ -142,6 +137,10 @@ export interface PropertyOptions {
142
137
  // - boolean: true 表示整个顶层变量交给服务端;false 表示仅前端解析
143
138
  // - function: 根据子路径决定是否交给服务端(子路径示例:'record.roles[0].name'、'id'、'')
144
139
  resolveOnServer?: boolean | ((subPath: string) => boolean);
140
+ // 优化:当需要服务端解析但本属性在 buildVariablesParams 返回空时,是否跳过调用服务端。
141
+ // - 典型场景:formValues / currentObject 仅在“已选关联值”存在时才需要服务端;否则没有必要请求。
142
+ // - 默认 false:保持兼容,其他变量即使没有 contextParams 也可选择调用服务端。
143
+ serverOnlyWhenContextParams?: boolean;
145
144
  }
146
145
 
147
146
  type RouteOptions = {
@@ -892,46 +891,19 @@ export class FlowContext {
892
891
  }
893
892
  }
894
893
 
895
- export class FlowRunjsContext extends FlowContext {
896
- constructor(delegate: FlowContext) {
897
- super();
898
- this.addDelegate(delegate);
899
- // Expose React and antd only within runjs context
900
- // This keeps the scope minimal while enabling React/AntD rendering in scripts
901
- this.defineProperty('React', { value: React });
902
- this.defineProperty('antd', { value: antd });
903
- this.defineMethod(
904
- 'dispatchModelEvent',
905
- async (modelOrUid: FlowModel | string, eventName: string, inputArgs?: Record<string, any>) => {
906
- let model: FlowModel | null = null;
907
- if (typeof modelOrUid === 'string') {
908
- model = await this.engine.loadModel({ uid: modelOrUid });
909
- } else if (modelOrUid instanceof FlowModel) {
910
- model = modelOrUid;
911
- }
912
- if (model) {
913
- model.context.addDelegate(this);
914
- model.dispatchEvent(eventName, { navigation: false, ...this.model?.['getInputArgs']?.(), ...inputArgs });
915
- } else {
916
- this.message.error(this.t('Model with ID {{uid}} not found', { uid: modelOrUid }));
917
- }
918
- },
919
- );
920
- }
921
- }
922
-
923
894
  class BaseFlowEngineContext extends FlowContext {
924
895
  declare router: Router;
925
896
  declare dataSourceManager: DataSourceManager;
926
897
  declare requireAsync: (url: string) => Promise<any>;
898
+ declare importAsync: (url: string) => Promise<any>;
927
899
  declare createJSRunner: (options?: JSRunnerOptions) => JSRunner;
900
+ declare pageInfo: { version?: 'v1' | 'v2' };
928
901
  /**
929
902
  * @deprecated use `resolveJsonTemplate` instead
930
903
  */
931
904
  declare renderJson: (template: JSONValue) => Promise<any>;
932
905
  declare resolveJsonTemplate: (template: JSONValue) => Promise<any>;
933
906
  declare runjs: (code: string, variables?: Record<string, any>, options?: JSRunnerOptions) => Promise<any>;
934
- declare copyToClipboard: (text: string) => Promise<void>;
935
907
  declare getAction: <TModel extends FlowModel = FlowModel, TCtx extends FlowContext = FlowContext>(
936
908
  name: string,
937
909
  ) => ActionDefinition<TModel, TCtx> | undefined;
@@ -1005,10 +977,10 @@ export class FlowEngineContext extends BaseFlowEngineContext {
1005
977
  });
1006
978
  this.defineMethod('runjs', async (code, variables, options?: JSRunnerOptions) => {
1007
979
  const mergedGlobals = { ...(options?.globals || {}), ...(variables || {}) };
1008
- const runner = this.createJSRunner({
980
+ const runner = (await (this as any).createJSRunner({
1009
981
  ...(options || {}),
1010
982
  globals: mergedGlobals,
1011
- });
983
+ })) as JSRunner;
1012
984
  return runner.run(code);
1013
985
  });
1014
986
  this.defineMethod('renderJson', function (template: any) {
@@ -1090,6 +1062,17 @@ export class FlowEngineContext extends BaseFlowEngineContext {
1090
1062
  ? _buildServerContextParams(this, autoInput)
1091
1063
  : undefined;
1092
1064
 
1065
+ // 优化:若所有需要服务端解析的变量都声明了 “仅当有 contextParams 时才请求服务端”,
1066
+ // 且本次未能构建出任何 contextParams,则跳过服务端请求,回退到前端解析。
1067
+ if (!autoContextParams) {
1068
+ const keys = Object.keys(serverVarPaths);
1069
+ const allOptional =
1070
+ keys.length > 0 && keys.every((k) => this.getPropertyOptions(k)?.serverOnlyWhenContextParams);
1071
+ if (allOptional) {
1072
+ return resolveExpressions(template, this);
1073
+ }
1074
+ }
1075
+
1093
1076
  if (this.api) {
1094
1077
  try {
1095
1078
  serverResolved = await enqueueVariablesResolve(this as FlowRuntimeContext<FlowModel>, {
@@ -1218,50 +1201,60 @@ export class FlowEngineContext extends BaseFlowEngineContext {
1218
1201
  );
1219
1202
  });
1220
1203
  });
1221
- this.defineMethod('createJSRunner', function (options?: JSRunnerOptions) {
1222
- // return createJSRunnerWithVersion.call(this, options as any);
1223
- const runCtx = new FlowRunjsContext(this.createProxy());
1224
- return new JSRunner({
1225
- ...options,
1226
- globals: {
1227
- ctx: runCtx,
1228
- window: createSafeWindow(),
1229
- document: createSafeDocument(),
1230
- ...options?.globals,
1231
- },
1232
- });
1233
- });
1234
- // 复制文本到剪贴板(优先使用 Clipboard API,降级到 execCommand)
1235
- this.defineMethod('copyToClipboard', async (text: string) => {
1236
- const content = String(text ?? '');
1237
- try {
1238
- if (typeof navigator !== 'undefined' && navigator.clipboard && navigator.clipboard.writeText) {
1239
- await navigator.clipboard.writeText(content);
1240
- return;
1241
- }
1242
- } catch (e) {
1243
- // 忽略,尝试降级方案
1204
+ // 动态按 URL 加载 ESM 模块
1205
+ // - 使用 Vite / Webpack ignore 注释,避免被预打包或重写
1206
+ // - 返回模块命名空间对象(包含 default 与命名导出)
1207
+ this.defineMethod('importAsync', async (url: string) => {
1208
+ if (!url || typeof url !== 'string') {
1209
+ throw new Error('invalid url');
1244
1210
  }
1245
-
1246
- // 降级方案:创建临时 textarea + execCommand('copy')
1247
- return new Promise<void>((resolve, reject) => {
1211
+ const u = url.trim();
1212
+ const g = globalThis as any;
1213
+ g.__nocobaseImportAsyncCache = g.__nocobaseImportAsyncCache || new Map<string, Promise<any>>();
1214
+ const cache: Map<string, Promise<any>> = g.__nocobaseImportAsyncCache;
1215
+ if (cache.has(u)) return cache.get(u)!;
1216
+ // 尝试使用原生 dynamic import(加上 vite/webpack 的 ignore 注释)
1217
+ const nativeImport = () => import(/* @vite-ignore */ /* webpackIgnore: true */ u);
1218
+ // 兜底方案:通过 eval 在运行时构造 import,避免被打包器接管
1219
+ const evalImport = () => {
1220
+ const importer = (0, eval)('u => import(u)');
1221
+ return importer(u);
1222
+ };
1223
+ const p = (async () => {
1248
1224
  try {
1249
- const ta = document.createElement('textarea');
1250
- ta.value = content;
1251
- ta.setAttribute('readonly', '');
1252
- ta.style.position = 'fixed';
1253
- ta.style.top = '-9999px';
1254
- document.body.appendChild(ta);
1255
- ta.focus();
1256
- ta.select();
1257
- const ok = document.execCommand('copy');
1258
- document.body.removeChild(ta);
1259
- if (ok) resolve();
1260
- else reject(new Error('execCommand copy failed'));
1261
- } catch (err) {
1262
- reject(err);
1225
+ return await nativeImport();
1226
+ } catch (err: any) {
1227
+ // 常见于打包产物仍然拦截了 dynamic import 或开发态插件未识别 ignore 注释
1228
+ try {
1229
+ return await evalImport();
1230
+ } catch (err2) {
1231
+ throw err2 || err;
1232
+ }
1263
1233
  }
1264
- });
1234
+ })();
1235
+ cache.set(u, p);
1236
+ return p;
1237
+ });
1238
+ this.defineMethod('createJSRunner', async function (options?: JSRunnerOptions) {
1239
+ try {
1240
+ const mod: any = await import('./runjs-context/setup');
1241
+ if (typeof mod?.setupRunJSContexts === 'function') await mod.setupRunJSContexts();
1242
+ } catch (_) {
1243
+ // ignore if setup is not available
1244
+ }
1245
+ const version = (options?.version as any) || 'v1';
1246
+ const modelClass = getModelClassName(this);
1247
+ const Ctor =
1248
+ (RunJSContextRegistry.resolve(version, modelClass) as any) ||
1249
+ (RunJSContextRegistry.resolve(version, '*') as any) ||
1250
+ FlowRunJSContext;
1251
+ let runCtx: any;
1252
+ if (Ctor) {
1253
+ runCtx = new Ctor(this);
1254
+ }
1255
+ const globals: Record<string, any> = { ctx: runCtx, ...(options?.globals || {}) };
1256
+ const { timeoutMs } = options || {};
1257
+ return new JSRunner({ globals, timeoutMs });
1265
1258
  });
1266
1259
  // Helper: build server contextParams for variables:resolve
1267
1260
  this.defineMethod('buildServerContextParams', function (this: BaseFlowEngineContext, input?: any) {
@@ -1332,7 +1325,8 @@ export class FlowEngineContext extends BaseFlowEngineContext {
1332
1325
  'runAction',
1333
1326
  async function (this: BaseFlowEngineContext, actionName: string, params?: Record<string, any>) {
1334
1327
  const def = this.engine.getAction<FlowModel, FlowEngineContext>(actionName);
1335
- const ctx = this.createProxy() as unknown as FlowEngineContext;
1328
+ // 使用“临时作用域”上下文,避免将临时定义污染到引擎级上下文,并在创建时应用定义
1329
+ const ctx = await createEphemeralContext(this as unknown as FlowEngineContext, def);
1336
1330
  if (!def) {
1337
1331
  throw new Error(`Action '${actionName}' not found.`);
1338
1332
  }
@@ -1346,7 +1340,7 @@ export class FlowEngineContext extends BaseFlowEngineContext {
1346
1340
  }
1347
1341
  if (!useRawParams) {
1348
1342
  // 先服务端解析,再前端补齐
1349
- combinedParams = await (ctx as any).resolveJsonTemplate(combinedParams);
1343
+ combinedParams = await ctx.resolveJsonTemplate(combinedParams);
1350
1344
  }
1351
1345
 
1352
1346
  if (!def.handler) {
@@ -1369,12 +1363,25 @@ export class FlowEngineContext extends BaseFlowEngineContext {
1369
1363
  context: this.createProxy(),
1370
1364
  });
1371
1365
  });
1366
+ // Provide useResource in base engine context so RunJS can call it directly
1367
+ this.defineMethod(
1368
+ 'useResource',
1369
+ function (
1370
+ this: BaseFlowEngineContext,
1371
+ className: 'APIResource' | 'SingleRecordResource' | 'MultiRecordResource' | 'SQLResource',
1372
+ ) {
1373
+ if (this.has('resource')) return;
1374
+ this.defineProperty('resource', {
1375
+ get: () => this.createResource(className),
1376
+ });
1377
+ },
1378
+ );
1372
1379
  }
1373
1380
  }
1374
1381
 
1375
1382
  export class FlowModelContext extends BaseFlowModelContext {
1376
1383
  constructor(model: FlowModel) {
1377
- if (!(model instanceof FlowModel)) {
1384
+ if (!model || typeof model !== 'object') {
1378
1385
  throw new Error('Invalid FlowModel instance');
1379
1386
  }
1380
1387
  super();
@@ -1383,7 +1390,7 @@ export class FlowModelContext extends BaseFlowModelContext {
1383
1390
  this.engine.reactView.onRefReady(ref, cb, timeout);
1384
1391
  });
1385
1392
  this.defineMethod('runjs', async (code, variables, options?: { version?: string }) => {
1386
- const runner = this.createJSRunner({
1393
+ const runner = await this.createJSRunner({
1387
1394
  globals: variables,
1388
1395
  version: options?.version,
1389
1396
  });
@@ -1417,21 +1424,24 @@ export class FlowModelContext extends BaseFlowModelContext {
1417
1424
  stepParams: {
1418
1425
  popupSettings: {
1419
1426
  openView: {
1420
- ..._.pick(opts, ['dataSourceKey', 'collectionName', 'associationName']),
1427
+ // 持久化首次传入的关键展示/数据参数,供后续路由与再次打开复用
1428
+ ..._.pick(opts, ['dataSourceKey', 'collectionName', 'associationName', 'mode', 'size']),
1421
1429
  },
1422
1430
  },
1423
1431
  },
1424
1432
  });
1425
1433
  await model.save();
1426
1434
  }
1427
- if (model.getStepParams('popupSettings')?.openView?.dataSourceKey) {
1428
- model.setStepParams('popupSettings', {
1429
- openView: {
1430
- ...model.getStepParams('popupSettings')?.openView,
1431
- ..._.pick(opts, ['dataSourceKey', 'collectionName', 'associationName']),
1432
- },
1433
- });
1434
- await model.save();
1435
+ // 若已存在 openView 配置,则按需合并更新(仅覆盖本次显式传入的字段)
1436
+ if (model.getStepParams('popupSettings')?.openView) {
1437
+ const prevOpenView = model.getStepParams('popupSettings')?.openView || {};
1438
+ const incoming = _.pick(opts, ['dataSourceKey', 'collectionName', 'associationName', 'mode', 'size']);
1439
+ const nextOpenView = { ...prevOpenView, ...incoming };
1440
+ // 仅当有变更时才保存,避免不必要的写入
1441
+ if (!_.isEqual(prevOpenView, nextOpenView)) {
1442
+ model.setStepParams('popupSettings', { openView: nextOpenView });
1443
+ await model.save();
1444
+ }
1435
1445
  }
1436
1446
 
1437
1447
  // 路由层级的 viewUid:优先使用 routeViewUid(仅用于路由展示);
@@ -1477,7 +1487,8 @@ export class FlowModelContext extends BaseFlowModelContext {
1477
1487
  'runAction',
1478
1488
  async function (this: BaseFlowModelContext, actionName: string, params?: Record<string, any>) {
1479
1489
  const def = this.model.getAction<FlowModel, FlowModelContext>(actionName);
1480
- const ctx = this.createProxy() as unknown as FlowModelContext;
1490
+ // 使用“临时作用域”上下文,避免将临时定义污染到模型级上下文,并在创建时应用定义
1491
+ const ctx = await createEphemeralContext(this as unknown as FlowModelContext, def);
1481
1492
  if (!def) {
1482
1493
  throw new Error(`Action '${actionName}' not found.`);
1483
1494
  }
@@ -1490,7 +1501,7 @@ export class FlowModelContext extends BaseFlowModelContext {
1490
1501
  useRawParams = await useRawParams(ctx);
1491
1502
  }
1492
1503
  if (!useRawParams) {
1493
- combinedParams = await (ctx as any).resolveJsonTemplate(combinedParams);
1504
+ combinedParams = await ctx.resolveJsonTemplate(combinedParams);
1494
1505
  }
1495
1506
 
1496
1507
  if (!def.handler) {
@@ -1507,7 +1518,7 @@ export class FlowForkModelContext extends BaseFlowModelContext {
1507
1518
  public master: FlowModel,
1508
1519
  public fork: ForkFlowModel,
1509
1520
  ) {
1510
- if (!(master instanceof FlowModel)) {
1521
+ if (!master || typeof master !== 'object') {
1511
1522
  throw new Error('Invalid FlowModel instance');
1512
1523
  }
1513
1524
  super();
@@ -1527,7 +1538,7 @@ export class FlowForkModelContext extends BaseFlowModelContext {
1527
1538
  },
1528
1539
  });
1529
1540
  this.defineMethod('runjs', async (code, variables, options?: { version?: string }) => {
1530
- const runner = this.createJSRunner({
1541
+ const runner = await this.createJSRunner({
1531
1542
  globals: variables,
1532
1543
  version: options?.version,
1533
1544
  });
@@ -1588,7 +1599,7 @@ export class FlowRuntimeContext<
1588
1599
  this.engine.reactView.onRefReady(ref, cb, timeout);
1589
1600
  });
1590
1601
  this.defineMethod('runjs', async (code, variables, options?: { version?: string }) => {
1591
- const runner = this.createJSRunner({
1602
+ const runner = await this.createJSRunner({
1592
1603
  globals: variables,
1593
1604
  version: options?.version,
1594
1605
  });
@@ -1641,3 +1652,178 @@ export class FlowRuntimeContext<
1641
1652
 
1642
1653
  // 类型别名,方便使用
1643
1654
  export type FlowSettingsContext<TModel extends FlowModel = FlowModel> = FlowRuntimeContext<TModel, 'settings'>;
1655
+
1656
+ export type RunJSDocCompletionDoc = {
1657
+ insertText?: string;
1658
+ };
1659
+
1660
+ export type RunJSDocPropertyDoc =
1661
+ | string
1662
+ | {
1663
+ description?: string;
1664
+ detail?: string;
1665
+ type?: string;
1666
+ examples?: string[];
1667
+ completion?: RunJSDocCompletionDoc;
1668
+ properties?: Record<string, RunJSDocPropertyDoc>;
1669
+ };
1670
+
1671
+ export type RunJSDocMethodDoc =
1672
+ | string
1673
+ | {
1674
+ description?: string;
1675
+ detail?: string;
1676
+ examples?: string[];
1677
+ completion?: RunJSDocCompletionDoc;
1678
+ };
1679
+
1680
+ export type RunJSDocMeta = {
1681
+ label?: string;
1682
+ properties?: Record<string, RunJSDocPropertyDoc>;
1683
+ methods?: Record<string, RunJSDocMethodDoc>;
1684
+ snippets?: Record<string, any>;
1685
+ };
1686
+
1687
+ const __runjsClassDefaultMeta = new WeakMap<Function, RunJSDocMeta>();
1688
+ const __runjsClassLocaleMeta = new WeakMap<Function, Map<string, RunJSDocMeta>>();
1689
+ const __runjsDocCache = new WeakMap<Function, Map<string, RunJSDocMeta>>();
1690
+
1691
+ function __runjsDeepMerge(base: any, patch: any) {
1692
+ if (patch === null) return undefined;
1693
+ if (Array.isArray(base) || Array.isArray(patch) || typeof base !== 'object' || typeof patch !== 'object') {
1694
+ return patch ?? base;
1695
+ }
1696
+ const out: any = { ...base };
1697
+ for (const k of Object.keys(patch)) {
1698
+ const v = __runjsDeepMerge(base?.[k], patch[k]);
1699
+ if (typeof v === 'undefined') delete out[k];
1700
+ else out[k] = v;
1701
+ }
1702
+ return out;
1703
+ }
1704
+ export class FlowRunJSContext extends FlowContext {
1705
+ constructor(delegate: FlowContext) {
1706
+ super();
1707
+ this.addDelegate(delegate);
1708
+ this.defineProperty('React', { value: React });
1709
+ this.defineProperty('antd', { value: antd });
1710
+ this.defineProperty('dayjs', { value: dayjs });
1711
+ // 为 JS 运行时代码提供带有 antd/App/ConfigProvider 包裹的 React 根
1712
+ // 保持与 ReactDOMClient 接口一致,优先覆盖 createRoot,其余方法透传
1713
+ const ReactDOMShim: any = {
1714
+ ...ReactDOMClient,
1715
+ createRoot: (container: Element | DocumentFragment, options?: any) => {
1716
+ // 兼容 ElementProxy:若传入的是代理对象,取其底层原生元素
1717
+ const realContainer: any = (container as any)?.__el || container;
1718
+ // 使用引擎自带的 reactView.createRoot,以继承应用内的 ConfigProvider/App 上下文与主题
1719
+ return this.engine.reactView.createRoot(realContainer as HTMLElement, options);
1720
+ },
1721
+ };
1722
+ this.defineProperty('ReactDOM', { value: ReactDOMShim });
1723
+
1724
+ // Convenience: ctx.render(<App />[, container])
1725
+ // - container defaults to ctx.element if available
1726
+ // - internally uses engine.reactView.createRoot to inherit app context
1727
+ // - caches root per container via global WeakMap
1728
+ this.defineMethod(
1729
+ 'render',
1730
+ function (
1731
+ this: any,
1732
+ vnode: React.ReactElement | Node | DocumentFragment | string,
1733
+ container?: Element | DocumentFragment,
1734
+ ) {
1735
+ const el = (container as any) || (this.element as any);
1736
+ if (!el) throw new Error('ctx.render: container not provided and ctx.element is not available');
1737
+ const containerEl: any = (el as any)?.__el || el; // unwrap ElementProxy
1738
+ const globalRef: any = globalThis as any;
1739
+ globalRef.__nbRunjsRoots = globalRef.__nbRunjsRoots || new WeakMap<any, any>();
1740
+ const rootMap: WeakMap<any, any> = globalRef.__nbRunjsRoots;
1741
+
1742
+ // If vnode is string (HTML), unmount react root and set sanitized HTML
1743
+ if (typeof vnode === 'string') {
1744
+ const existingRoot = rootMap.get(containerEl);
1745
+ if (existingRoot && typeof existingRoot.unmount === 'function') {
1746
+ try {
1747
+ existingRoot.unmount();
1748
+ } finally {
1749
+ rootMap.delete(containerEl);
1750
+ }
1751
+ }
1752
+ const proxy: any = new ElementProxy(containerEl);
1753
+ proxy.innerHTML = String(vnode ?? '');
1754
+ return null;
1755
+ }
1756
+
1757
+ // If vnode is a DOM Node or DocumentFragment, unmount and replace content
1758
+ if (
1759
+ vnode &&
1760
+ (vnode as any).nodeType &&
1761
+ ((vnode as any).nodeType === 1 || (vnode as any).nodeType === 3 || (vnode as any).nodeType === 11)
1762
+ ) {
1763
+ const existingRoot = rootMap.get(containerEl);
1764
+ if (existingRoot && typeof existingRoot.unmount === 'function') {
1765
+ try {
1766
+ existingRoot.unmount();
1767
+ } finally {
1768
+ rootMap.delete(containerEl);
1769
+ }
1770
+ }
1771
+ while (containerEl.firstChild) containerEl.removeChild(containerEl.firstChild);
1772
+ containerEl.appendChild(vnode as any);
1773
+ return null;
1774
+ }
1775
+
1776
+ let root = rootMap.get(containerEl);
1777
+ if (!root) {
1778
+ root = this.ReactDOM.createRoot(containerEl);
1779
+ rootMap.set(containerEl, root);
1780
+ }
1781
+ root.render(vnode as any);
1782
+ return root;
1783
+ },
1784
+ );
1785
+ }
1786
+ static define(meta: RunJSDocMeta, options?: { locale?: string }) {
1787
+ const locale = options?.locale;
1788
+ if (locale) {
1789
+ const map = __runjsClassLocaleMeta.get(this) || new Map<string, RunJSDocMeta>();
1790
+ const prev = map.get(locale) || {};
1791
+ map.set(locale, __runjsDeepMerge(prev, meta));
1792
+ __runjsClassLocaleMeta.set(this, map);
1793
+ } else {
1794
+ const prev = __runjsClassDefaultMeta.get(this) || {};
1795
+ __runjsClassDefaultMeta.set(this, __runjsDeepMerge(prev, meta));
1796
+ }
1797
+ __runjsDocCache.delete(this);
1798
+ }
1799
+ static getDoc(locale?: string): RunJSDocMeta {
1800
+ const self = this as any as Function;
1801
+ let cacheForClass = __runjsDocCache.get(self);
1802
+ const cacheKey = String(locale || 'default');
1803
+ if (cacheForClass && cacheForClass.has(cacheKey)) return cacheForClass.get(cacheKey)!;
1804
+ const chain: Function[] = [];
1805
+ let cur: any = self;
1806
+ while (cur && cur.prototype) {
1807
+ chain.unshift(cur);
1808
+ cur = Object.getPrototypeOf(cur);
1809
+ }
1810
+ let merged: RunJSDocMeta = {};
1811
+ for (const cls of chain) {
1812
+ merged = __runjsDeepMerge(merged, __runjsClassDefaultMeta.get(cls) || {});
1813
+ }
1814
+ if (locale) {
1815
+ for (const cls of chain) {
1816
+ const lmap = __runjsClassLocaleMeta.get(cls);
1817
+ if (lmap && lmap.has(locale)) {
1818
+ merged = __runjsDeepMerge(merged, lmap.get(locale));
1819
+ }
1820
+ }
1821
+ }
1822
+ if (!cacheForClass) {
1823
+ cacheForClass = new Map<string, RunJSDocMeta>();
1824
+ __runjsDocCache.set(self, cacheForClass);
1825
+ }
1826
+ cacheForClass.set(cacheKey, merged);
1827
+ return merged;
1828
+ }
1829
+ }