@nocobase/plugin-flow-engine 2.1.0-alpha.3 → 2.1.0-alpha.30

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 (262) hide show
  1. package/LICENSE +201 -661
  2. package/README.md +79 -9
  3. package/dist/ai/ai-employees/nathan/index.d.ts +10 -0
  4. package/dist/ai/ai-employees/nathan/index.js +42 -0
  5. package/dist/ai/ai-employees/nathan/prompt.md +168 -0
  6. package/dist/ai/ai-employees/nathan/skills/frontend-developer/SKILLS.md +86 -0
  7. package/dist/ai/{tools → ai-employees/nathan/skills/frontend-developer/tools}/getContextApis.js +2 -2
  8. package/dist/ai/{tools → ai-employees/nathan/skills/frontend-developer/tools}/getContextEnvs.js +2 -2
  9. package/dist/ai/{tools → ai-employees/nathan/skills/frontend-developer/tools}/getContextVars.js +2 -2
  10. package/dist/ai/{tools → ai-employees/nathan/skills/frontend-developer/tools}/lintAndTestJS.js +6 -4
  11. package/dist/ai/ai-employees/nathan/skills/frontend-developer/tools/patchJSCode.d.ts +10 -0
  12. package/dist/ai/ai-employees/nathan/skills/frontend-developer/tools/patchJSCode.js +65 -0
  13. package/dist/ai/ai-employees/nathan/skills/frontend-developer/tools/readJSCode.d.ts +10 -0
  14. package/dist/ai/ai-employees/nathan/skills/frontend-developer/tools/readJSCode.js +61 -0
  15. package/dist/ai/ai-employees/nathan/skills/frontend-developer/tools/writeJSCode.d.ts +10 -0
  16. package/dist/ai/ai-employees/nathan/skills/frontend-developer/tools/writeJSCode.js +65 -0
  17. package/dist/ai/docs/runjs/context/block-model.md +35 -35
  18. package/dist/ai/docs/runjs/context/collection-field.md +53 -51
  19. package/dist/ai/docs/runjs/context/collection.md +39 -39
  20. package/dist/ai/docs/runjs/context/data-source-manager.md +40 -30
  21. package/dist/ai/docs/runjs/context/data-source.md +52 -44
  22. package/dist/ai/docs/runjs/context/element.md +44 -38
  23. package/dist/ai/docs/runjs/context/exit-all.md +37 -35
  24. package/dist/ai/docs/runjs/context/exit.md +38 -35
  25. package/dist/ai/docs/runjs/context/filter-manager.md +36 -30
  26. package/dist/ai/docs/runjs/context/form.md +57 -57
  27. package/dist/ai/docs/runjs/context/get-model.md +22 -21
  28. package/dist/ai/docs/runjs/context/get-value.md +20 -19
  29. package/dist/ai/docs/runjs/context/get-var.md +61 -55
  30. package/dist/ai/docs/runjs/context/i18n.md +17 -14
  31. package/dist/ai/docs/runjs/context/import-async.md +333 -45
  32. package/dist/ai/docs/runjs/context/init-resource.md +20 -20
  33. package/dist/ai/docs/runjs/context/libs.md +31 -31
  34. package/dist/ai/docs/runjs/context/location.md +34 -31
  35. package/dist/ai/docs/runjs/context/logger.md +41 -40
  36. package/dist/ai/docs/runjs/context/make-resource.md +27 -26
  37. package/dist/ai/docs/runjs/context/message.md +42 -41
  38. package/dist/ai/docs/runjs/context/modal.md +44 -44
  39. package/dist/ai/docs/runjs/context/model.md +36 -33
  40. package/dist/ai/docs/runjs/context/notification.md +41 -40
  41. package/dist/ai/docs/runjs/context/off.md +14 -14
  42. package/dist/ai/docs/runjs/context/on.md +30 -29
  43. package/dist/ai/docs/runjs/context/open-view.md +40 -40
  44. package/dist/ai/docs/runjs/context/render.md +37 -32
  45. package/dist/ai/docs/runjs/context/request.md +46 -45
  46. package/dist/ai/docs/runjs/context/require-async.md +28 -25
  47. package/dist/ai/docs/runjs/context/resource.md +34 -34
  48. package/dist/ai/docs/runjs/context/route.md +36 -34
  49. package/dist/ai/docs/runjs/context/router.md +43 -31
  50. package/dist/ai/docs/runjs/context/set-value.md +18 -17
  51. package/dist/ai/docs/runjs/context/sql.md +7 -15
  52. package/dist/ai/docs/runjs/context/t.md +20 -17
  53. package/dist/ai/docs/runjs/context/view.md +49 -46
  54. package/dist/ai/docs/runjs/document.md +1 -0
  55. package/dist/ai/docs/runjs/import-modules.md +32 -32
  56. package/dist/ai/docs/runjs/index.md +13 -13
  57. package/dist/ai/docs/runjs/jsx.md +19 -19
  58. package/dist/ai/docs/runjs/model/form-block-model.md +1 -3
  59. package/dist/ai/docs/runjs/render.md +15 -15
  60. package/dist/ai/docs/runjs/resource/api-resource.md +53 -53
  61. package/dist/ai/docs/runjs/resource/multi-record-resource.md +64 -64
  62. package/dist/ai/docs/runjs/resource/single-record-resource.md +55 -55
  63. package/dist/ai/docs/runjs/resource/sql-resource.md +57 -57
  64. package/dist/ai/docs/runjs/window.md +5 -5
  65. package/dist/client/index.js +1 -1
  66. package/dist/externalVersion.js +12 -11
  67. package/dist/locale/en-US.json +1 -0
  68. package/dist/locale/index.d.ts +2 -0
  69. package/dist/locale/zh-CN.json +1 -0
  70. package/dist/node_modules/ses/dist/ses.cjs +1 -1
  71. package/dist/node_modules/ses/package.json +1 -1
  72. package/dist/node_modules/zod/index.cjs +1 -1
  73. package/dist/node_modules/zod/package.json +1 -1
  74. package/dist/server/collections/flowsql.js +1 -0
  75. package/dist/server/flow-surfaces/action-scope.d.ts +39 -0
  76. package/dist/server/flow-surfaces/action-scope.js +156 -0
  77. package/dist/server/flow-surfaces/apply/compiler.d.ts +13 -0
  78. package/dist/server/flow-surfaces/apply/compiler.js +971 -0
  79. package/dist/server/flow-surfaces/apply/layout.d.ts +34 -0
  80. package/dist/server/flow-surfaces/apply/layout.js +175 -0
  81. package/dist/server/flow-surfaces/apply/matching.d.ts +16 -0
  82. package/dist/server/flow-surfaces/apply/matching.js +181 -0
  83. package/dist/server/flow-surfaces/approval/blueprint-service.d.ts +84 -0
  84. package/dist/server/flow-surfaces/approval/blueprint-service.js +589 -0
  85. package/dist/server/flow-surfaces/approval/blueprint.d.ts +21 -0
  86. package/dist/server/flow-surfaces/approval/blueprint.js +187 -0
  87. package/dist/server/flow-surfaces/approval/builder.d.ts +225 -0
  88. package/dist/server/flow-surfaces/approval/builder.js +384 -0
  89. package/dist/server/flow-surfaces/approval/catalog-specs.d.ts +33 -0
  90. package/dist/server/flow-surfaces/approval/catalog-specs.js +156 -0
  91. package/dist/server/flow-surfaces/approval/index.d.ts +14 -0
  92. package/dist/server/flow-surfaces/approval/index.js +40 -0
  93. package/dist/server/flow-surfaces/approval/runtime-config.d.ts +44 -0
  94. package/dist/server/flow-surfaces/approval/runtime-config.js +299 -0
  95. package/dist/server/flow-surfaces/approval/semantic-use.d.ts +23 -0
  96. package/dist/server/flow-surfaces/approval/semantic-use.js +155 -0
  97. package/dist/server/flow-surfaces/association-interfaces.d.ts +10 -0
  98. package/dist/server/flow-surfaces/association-interfaces.js +39 -0
  99. package/dist/server/flow-surfaces/association-title-field.d.ts +20 -0
  100. package/dist/server/flow-surfaces/association-title-field.js +192 -0
  101. package/dist/server/flow-surfaces/blueprint/compile-blocks.d.ts +15 -0
  102. package/dist/server/flow-surfaces/blueprint/compile-blocks.js +1251 -0
  103. package/dist/server/flow-surfaces/blueprint/compile-plan.d.ts +14 -0
  104. package/dist/server/flow-surfaces/blueprint/compile-plan.js +308 -0
  105. package/dist/server/flow-surfaces/blueprint/compile-reaction.d.ts +11 -0
  106. package/dist/server/flow-surfaces/blueprint/compile-reaction.js +72 -0
  107. package/dist/server/flow-surfaces/blueprint/defaults.d.ts +26 -0
  108. package/dist/server/flow-surfaces/blueprint/defaults.js +133 -0
  109. package/dist/server/flow-surfaces/blueprint/index.d.ts +12 -0
  110. package/dist/server/flow-surfaces/blueprint/index.js +44 -0
  111. package/dist/server/flow-surfaces/blueprint/normalize-document.d.ts +10 -0
  112. package/dist/server/flow-surfaces/blueprint/normalize-document.js +407 -0
  113. package/dist/server/flow-surfaces/blueprint/private-utils.d.ts +25 -0
  114. package/dist/server/flow-surfaces/blueprint/private-utils.js +179 -0
  115. package/dist/server/flow-surfaces/blueprint/public-types.d.ts +201 -0
  116. package/dist/server/flow-surfaces/blueprint/public-types.js +24 -0
  117. package/dist/server/flow-surfaces/builder.d.ts +238 -0
  118. package/dist/server/flow-surfaces/builder.js +1261 -0
  119. package/dist/server/flow-surfaces/catalog-smart.d.ts +18 -0
  120. package/dist/server/flow-surfaces/catalog-smart.js +239 -0
  121. package/dist/server/flow-surfaces/catalog-smart.projector.d.ts +15 -0
  122. package/dist/server/flow-surfaces/catalog-smart.projector.js +157 -0
  123. package/dist/server/flow-surfaces/catalog-smart.types.d.ts +99 -0
  124. package/dist/server/flow-surfaces/catalog-smart.types.js +24 -0
  125. package/dist/server/flow-surfaces/catalog.d.ts +79 -0
  126. package/dist/server/flow-surfaces/catalog.js +3743 -0
  127. package/dist/server/flow-surfaces/chart-config.d.ts +121 -0
  128. package/dist/server/flow-surfaces/chart-config.js +1394 -0
  129. package/dist/server/flow-surfaces/compose-compiler.d.ts +115 -0
  130. package/dist/server/flow-surfaces/compose-compiler.js +174 -0
  131. package/dist/server/flow-surfaces/compose-runtime.d.ts +94 -0
  132. package/dist/server/flow-surfaces/compose-runtime.js +376 -0
  133. package/dist/server/flow-surfaces/configure-options.d.ts +23 -0
  134. package/dist/server/flow-surfaces/configure-options.js +904 -0
  135. package/dist/server/flow-surfaces/constants.d.ts +351 -0
  136. package/dist/server/flow-surfaces/constants.js +104 -0
  137. package/dist/server/flow-surfaces/context.d.ts +72 -0
  138. package/dist/server/flow-surfaces/context.js +556 -0
  139. package/dist/server/flow-surfaces/contract-guard.d.ts +19 -0
  140. package/dist/server/flow-surfaces/contract-guard.js +410 -0
  141. package/dist/server/flow-surfaces/core-field-default-bindings.d.ts +12 -0
  142. package/dist/server/flow-surfaces/core-field-default-bindings.js +157 -0
  143. package/dist/server/flow-surfaces/default-action-popup.d.ts +63 -0
  144. package/dist/server/flow-surfaces/default-action-popup.js +322 -0
  145. package/dist/server/flow-surfaces/default-block-actions.d.ts +32 -0
  146. package/dist/server/flow-surfaces/default-block-actions.js +210 -0
  147. package/dist/server/flow-surfaces/errors.d.ts +47 -0
  148. package/dist/server/flow-surfaces/errors.js +145 -0
  149. package/dist/server/flow-surfaces/executor.d.ts +23 -0
  150. package/dist/server/flow-surfaces/executor.js +132 -0
  151. package/dist/server/flow-surfaces/field-binding-registry.d.ts +24 -0
  152. package/dist/server/flow-surfaces/field-binding-registry.js +396 -0
  153. package/dist/server/flow-surfaces/field-semantics.d.ts +15 -0
  154. package/dist/server/flow-surfaces/field-semantics.js +84 -0
  155. package/dist/server/flow-surfaces/field-type-resolver.d.ts +45 -0
  156. package/dist/server/flow-surfaces/field-type-resolver.js +312 -0
  157. package/dist/server/flow-surfaces/filter-group.d.ts +15 -0
  158. package/dist/server/flow-surfaces/filter-group.js +94 -0
  159. package/dist/server/flow-surfaces/hidden-popup-calendar.d.ts +86 -0
  160. package/dist/server/flow-surfaces/hidden-popup-calendar.js +554 -0
  161. package/dist/server/flow-surfaces/hidden-popup-contract.d.ts +116 -0
  162. package/dist/server/flow-surfaces/hidden-popup-contract.js +611 -0
  163. package/dist/server/flow-surfaces/hidden-popup-kanban.d.ts +62 -0
  164. package/dist/server/flow-surfaces/hidden-popup-kanban.js +651 -0
  165. package/dist/server/flow-surfaces/index.d.ts +11 -0
  166. package/dist/server/flow-surfaces/index.js +302 -0
  167. package/dist/server/flow-surfaces/locator.d.ts +28 -0
  168. package/dist/server/flow-surfaces/locator.js +240 -0
  169. package/dist/server/flow-surfaces/node-use-sets.d.ts +15 -0
  170. package/dist/server/flow-surfaces/node-use-sets.js +135 -0
  171. package/dist/server/flow-surfaces/payload-shape.d.ts +9 -0
  172. package/dist/server/flow-surfaces/payload-shape.js +61 -0
  173. package/dist/server/flow-surfaces/placement.d.ts +33 -0
  174. package/dist/server/flow-surfaces/placement.js +199 -0
  175. package/dist/server/flow-surfaces/planning/action-specs.d.ts +179 -0
  176. package/dist/server/flow-surfaces/planning/action-specs.js +190 -0
  177. package/dist/server/flow-surfaces/planning/compiler.d.ts +37 -0
  178. package/dist/server/flow-surfaces/planning/compiler.js +376 -0
  179. package/dist/server/flow-surfaces/planning/context.d.ts +30 -0
  180. package/dist/server/flow-surfaces/planning/context.js +139 -0
  181. package/dist/server/flow-surfaces/planning/created-keys.d.ts +34 -0
  182. package/dist/server/flow-surfaces/planning/created-keys.js +375 -0
  183. package/dist/server/flow-surfaces/planning/key-kind.d.ts +11 -0
  184. package/dist/server/flow-surfaces/planning/key-kind.js +88 -0
  185. package/dist/server/flow-surfaces/planning/key-persistence.d.ts +34 -0
  186. package/dist/server/flow-surfaces/planning/key-persistence.js +148 -0
  187. package/dist/server/flow-surfaces/planning/key-registry.d.ts +40 -0
  188. package/dist/server/flow-surfaces/planning/key-registry.js +206 -0
  189. package/dist/server/flow-surfaces/planning/runtime.d.ts +37 -0
  190. package/dist/server/flow-surfaces/planning/runtime.js +259 -0
  191. package/dist/server/flow-surfaces/planning/step-link.d.ts +14 -0
  192. package/dist/server/flow-surfaces/planning/step-link.js +104 -0
  193. package/dist/server/flow-surfaces/planning/types.d.ts +55 -0
  194. package/dist/server/flow-surfaces/planning/types.js +24 -0
  195. package/dist/server/flow-surfaces/public-compatibility.d.ts +28 -0
  196. package/dist/server/flow-surfaces/public-compatibility.js +161 -0
  197. package/dist/server/flow-surfaces/public-data-surface-default-filter.d.ts +24 -0
  198. package/dist/server/flow-surfaces/public-data-surface-default-filter.js +152 -0
  199. package/dist/server/flow-surfaces/reaction/errors.d.ts +20 -0
  200. package/dist/server/flow-surfaces/reaction/errors.js +69 -0
  201. package/dist/server/flow-surfaces/reaction/field-value.d.ts +34 -0
  202. package/dist/server/flow-surfaces/reaction/field-value.js +181 -0
  203. package/dist/server/flow-surfaces/reaction/fingerprint.d.ts +16 -0
  204. package/dist/server/flow-surfaces/reaction/fingerprint.js +71 -0
  205. package/dist/server/flow-surfaces/reaction/linkage.d.ts +136 -0
  206. package/dist/server/flow-surfaces/reaction/linkage.js +882 -0
  207. package/dist/server/flow-surfaces/reaction/meta.d.ts +11 -0
  208. package/dist/server/flow-surfaces/reaction/meta.js +451 -0
  209. package/dist/server/flow-surfaces/reaction/registry.d.ts +156 -0
  210. package/dist/server/flow-surfaces/reaction/registry.js +206 -0
  211. package/dist/server/flow-surfaces/reaction/resolver.d.ts +22 -0
  212. package/dist/server/flow-surfaces/reaction/resolver.js +202 -0
  213. package/dist/server/flow-surfaces/reaction/types.d.ts +241 -0
  214. package/dist/server/flow-surfaces/reaction/types.js +24 -0
  215. package/dist/server/flow-surfaces/reaction/utils.d.ts +17 -0
  216. package/dist/server/flow-surfaces/reaction/utils.js +67 -0
  217. package/dist/server/flow-surfaces/reaction/value-expr.d.ts +15 -0
  218. package/dist/server/flow-surfaces/reaction/value-expr.js +209 -0
  219. package/dist/server/flow-surfaces/reference-guards.d.ts +19 -0
  220. package/dist/server/flow-surfaces/reference-guards.js +103 -0
  221. package/dist/server/flow-surfaces/route-sync.d.ts +47 -0
  222. package/dist/server/flow-surfaces/route-sync.js +392 -0
  223. package/dist/server/flow-surfaces/service-helpers.d.ts +42 -0
  224. package/dist/server/flow-surfaces/service-helpers.js +310 -0
  225. package/dist/server/flow-surfaces/service-utils.d.ts +120 -0
  226. package/dist/server/flow-surfaces/service-utils.js +878 -0
  227. package/dist/server/flow-surfaces/service.d.ts +894 -0
  228. package/dist/server/flow-surfaces/service.js +16200 -0
  229. package/dist/server/flow-surfaces/support-matrix.d.ts +31 -0
  230. package/dist/server/flow-surfaces/support-matrix.js +282 -0
  231. package/dist/server/flow-surfaces/surface-context.d.ts +52 -0
  232. package/dist/server/flow-surfaces/surface-context.js +440 -0
  233. package/dist/server/flow-surfaces/template-compatibility.d.ts +42 -0
  234. package/dist/server/flow-surfaces/template-compatibility.js +189 -0
  235. package/dist/server/flow-surfaces/template-display.d.ts +20 -0
  236. package/dist/server/flow-surfaces/template-display.js +289 -0
  237. package/dist/server/flow-surfaces/template-service-utils.d.ts +62 -0
  238. package/dist/server/flow-surfaces/template-service-utils.js +281 -0
  239. package/dist/server/flow-surfaces/types.d.ts +288 -0
  240. package/dist/server/flow-surfaces/types.js +24 -0
  241. package/dist/server/index.d.ts +1 -0
  242. package/dist/server/index.js +7 -2
  243. package/dist/server/plugin.d.ts +0 -1
  244. package/dist/server/plugin.js +9 -34
  245. package/dist/server/repository.js +0 -5
  246. package/dist/server/variables/resolve.d.ts +21 -0
  247. package/dist/server/variables/resolve.js +79 -0
  248. package/dist/swagger/flow-surfaces.d.ts +6106 -0
  249. package/dist/swagger/flow-surfaces.examples.d.ts +1577 -0
  250. package/dist/swagger/flow-surfaces.examples.js +1816 -0
  251. package/dist/swagger/flow-surfaces.js +5375 -0
  252. package/dist/swagger/flow-surfaces.template-action-docs.d.ts +62 -0
  253. package/dist/swagger/flow-surfaces.template-action-docs.js +121 -0
  254. package/dist/swagger/flow-surfaces.template-schemas.d.ts +239 -0
  255. package/dist/swagger/flow-surfaces.template-schemas.js +255 -0
  256. package/dist/swagger/index.d.ts +6111 -0
  257. package/dist/swagger/index.js +50 -0
  258. package/package.json +3 -3
  259. /package/dist/ai/{tools → ai-employees/nathan/skills/frontend-developer/tools}/getContextApis.d.ts +0 -0
  260. /package/dist/ai/{tools → ai-employees/nathan/skills/frontend-developer/tools}/getContextEnvs.d.ts +0 -0
  261. /package/dist/ai/{tools → ai-employees/nathan/skills/frontend-developer/tools}/getContextVars.d.ts +0 -0
  262. /package/dist/ai/{tools → ai-employees/nathan/skills/frontend-developer/tools}/lintAndTestJS.d.ts +0 -0
@@ -1,18 +1,18 @@
1
1
  # ctx.dataSourceManager
2
2
 
3
- The data source manager (`DataSourceManager` instance) for managing and accessing multiple data sources (e.g. main `main`, logging `logging`). Use when you have multiple data sources or need crossdata-source metadata access.
3
+ The Data Source Manager (`DataSourceManager` instance) is used to manage and access multiple data sources (e.g., the main database `main`, logging database `logging`, etc.). It is used when multiple data sources exist or when cross-data source metadata access is required.
4
4
 
5
5
  ## Use Cases
6
6
 
7
7
  | Scenario | Description |
8
- |----------|-------------|
9
- | **Multiple data sources** | Enumerate all data sources, get one by key |
10
- | **Crossdata-source access** | When context doesn’t know the data source, access by data source key + collection name” |
11
- | **Field by full path** | Get field definition with path format `dataSourceKey.collectionName.fieldPath` |
8
+ |------|------|
9
+ | **Multi-data source** | Enumerate all data sources, or get a specific data source by key. |
10
+ | **Cross-data source access** | Access metadata using the "data source key + collection name" format when the data source of the current context is unknown. |
11
+ | **Get fields by full path** | Use the `dataSourceKey.collectionName.fieldPath` format to retrieve field definitions across different data sources. |
12
12
 
13
- > Note: If you only work with the current data source, use `ctx.dataSource`; use `ctx.dataSourceManager` when you need to enumerate or switch data sources.
13
+ > Note: If you are only operating on the current data source, prioritize using `ctx.dataSource`. Use `ctx.dataSourceManager` only when you need to enumerate or switch between data sources.
14
14
 
15
- ## Type
15
+ ## Type Definition
16
16
 
17
17
  ```ts
18
18
  dataSourceManager: DataSourceManager;
@@ -20,64 +20,74 @@ dataSourceManager: DataSourceManager;
20
20
  class DataSourceManager {
21
21
  constructor();
22
22
 
23
+ // Data source management
23
24
  addDataSource(ds: DataSource | DataSourceOptions): void;
24
25
  upsertDataSource(ds: DataSource | DataSourceOptions): void;
25
26
  removeDataSource(key: string): void;
26
27
  clearDataSources(): void;
27
28
 
28
- getDataSources(): DataSource[];
29
- getDataSource(key: string): DataSource | undefined;
29
+ // Read data sources
30
+ getDataSources(): DataSource[]; // Get all data sources
31
+ getDataSource(key: string): DataSource | undefined; // Get data source by key
30
32
 
33
+ // Access metadata directly by data source + collection
31
34
  getCollection(dataSourceKey: string, collectionName: string): Collection | undefined;
32
35
  getCollectionField(fieldPathWithDataSource: string): CollectionField | undefined;
33
36
  }
34
37
  ```
35
38
 
36
- ## Relation to ctx.dataSource
39
+ ## Relationship with ctx.dataSource
37
40
 
38
- | Need | Recommended |
39
- |------|-------------|
40
- | **Single data source for context** | `ctx.dataSource` |
41
- | **Entry to all data sources** | `ctx.dataSourceManager` |
41
+ | Requirement | Recommended Usage |
42
+ |------|----------|
43
+ | **Single data source bound to the current context** | `ctx.dataSource` (e.g., the data source of the current page/block) |
44
+ | **Entry point for all data sources** | `ctx.dataSourceManager` |
42
45
  | **List or switch data sources** | `ctx.dataSourceManager.getDataSources()` / `getDataSource(key)` |
43
- | **Collection in current data source** | `ctx.dataSource.getCollection(name)` |
44
- | **Collection in another data source** | `ctx.dataSourceManager.getCollection(dataSourceKey, collectionName)` |
45
- | **Field in current data source** | `ctx.dataSource.getCollectionField('users.profile.avatar')` |
46
- | **Field across data sources** | `ctx.dataSourceManager.getCollectionField('main.users.profile.avatar')` |
46
+ | **Get collection within the current data source** | `ctx.dataSource.getCollection(name)` |
47
+ | **Get collection across data sources** | `ctx.dataSourceManager.getCollection(dataSourceKey, collectionName)` |
48
+ | **Get field within the current data source** | `ctx.dataSource.getCollectionField('users.profile.avatar')` |
49
+ | **Get field across data sources** | `ctx.dataSourceManager.getCollectionField('main.users.profile.avatar')` |
47
50
 
48
51
  ## Examples
49
52
 
50
- ### Get a data source
53
+ ### Get a Specific Data Source
51
54
 
52
55
  ```ts
56
+ // Get the data source named 'main'
53
57
  const mainDS = ctx.dataSourceManager.getDataSource('main');
58
+
59
+ // Get all collections under this data source
54
60
  const collections = mainDS?.getCollections();
55
61
  ```
56
62
 
57
- ### Cross–data-source collection metadata
63
+ ### Access Collection Metadata Across Data Sources
58
64
 
59
65
  ```ts
66
+ // Get collection by dataSourceKey + collectionName
60
67
  const users = ctx.dataSourceManager.getCollection('main', 'users');
61
68
  const orders = ctx.dataSourceManager.getCollection('main', 'orders');
62
69
 
70
+ // Get the primary key of the collection
63
71
  const primaryKey = users?.filterTargetKey ?? 'id';
64
72
  ```
65
73
 
66
- ### Field by full path
74
+ ### Get Field Definition by Full Path
67
75
 
68
76
  ```ts
69
77
  // Format: dataSourceKey.collectionName.fieldPath
78
+ // Get field definition by "data source key.collection name.field path"
70
79
  const field = ctx.dataSourceManager.getCollectionField('main.users.profile.avatar');
71
80
 
81
+ // Supports association field paths
72
82
  const userNameField = ctx.dataSourceManager.getCollectionField('main.orders.createdBy.name');
73
83
  ```
74
84
 
75
- ### Iterate all data sources
85
+ ### Iterate Through All Data Sources
76
86
 
77
87
  ```ts
78
88
  const dataSources = ctx.dataSourceManager.getDataSources();
79
89
  for (const ds of dataSources) {
80
- ctx.logger.info(`Data source: ${ds.key}, display: ${ds.displayName}`);
90
+ ctx.logger.info(`Data Source: ${ds.key}, Display Name: ${ds.displayName}`);
81
91
  const collections = ds.getCollections();
82
92
  for (const col of collections) {
83
93
  ctx.logger.info(` - Collection: ${col.name}`);
@@ -85,7 +95,7 @@ for (const ds of dataSources) {
85
95
  }
86
96
  ```
87
97
 
88
- ### Dynamic data source from variable
98
+ ### Dynamically Select Data Source Based on Variables
89
99
 
90
100
  ```ts
91
101
  const dsKey = ctx.getVar('dataSourceKey') ?? 'main';
@@ -99,12 +109,12 @@ if (col) {
99
109
 
100
110
  ## Notes
101
111
 
102
- - `getCollectionField` path format is `dataSourceKey.collectionName.fieldPath`; first segment is data source key, then collection name and field path.
103
- - `getDataSource(key)` returns `undefined` if the data source doesn’t existcheck before use.
104
- - `addDataSource` throws if key already exists; `upsertDataSource` overwrites or adds.
112
+ - The path format for `getCollectionField` is `dataSourceKey.collectionName.fieldPath`, where the first segment is the data source key, followed by the collection name and the field path.
113
+ - `getDataSource(key)` returns `undefined` if the data source does not exist; it is recommended to perform a null check before use.
114
+ - `addDataSource` will throw an exception if the key already exists; `upsertDataSource` will either overwrite the existing one or add a new one.
105
115
 
106
116
  ## Related
107
117
 
108
- - [ctx.dataSource](./data-source.md): current data source instance
109
- - [ctx.collection](./collection.md): collection for current context
110
- - [ctx.collectionField](./collection-field.md): current field’s collection field definition
118
+ - [ctx.dataSource](./data-source.md): Current data source instance
119
+ - [ctx.collection](./collection.md): Collection associated with the current context
120
+ - [ctx.collectionField](./collection-field.md): Collection field definition for the current field
@@ -1,18 +1,18 @@
1
1
  # ctx.dataSource
2
2
 
3
- The data source instance (`DataSource`) bound to the current RunJS context; used to access collections, field metadata, and collection config **within that data source**. Usually the current page/block’s data source (e.g. main `main`).
3
+ The `DataSource` instance bound to the current RunJS execution context, used to access collections, field metadata, and manage collection configurations **within the current data source**. It usually corresponds to the data source selected for the current page or block (e.g., the main database `main`).
4
4
 
5
5
  ## Use Cases
6
6
 
7
7
  | Scenario | Description |
8
- |----------|-------------|
9
- | **Single data source** | Get collections, field metadata when the current data source is known |
10
- | **Collection management** | Get/add/update/remove collections in the current data source |
11
- | **Field by path** | Get field definition by `collectionName.fieldPath` (supports association path) |
8
+ |------|------|
9
+ | **Single Data Source Operations** | Get collection and field metadata when the current data source is known. |
10
+ | **Collection Management** | Get, add, update, or delete collections under the current data source. |
11
+ | **Get Fields by Path** | Use the `collectionName.fieldPath` format to get field definitions (supports association paths). |
12
12
 
13
- > Note: `ctx.dataSource` is the single data source for the current context; to enumerate or access other data sources use [ctx.dataSourceManager](./data-source-manager.md).
13
+ > Note: `ctx.dataSource` represents a single data source for the current context. To enumerate or access other data sources, please use [ctx.dataSourceManager](./data-source-manager.md).
14
14
 
15
- ## Type
15
+ ## Type Definition
16
16
 
17
17
  ```ts
18
18
  dataSource: DataSource;
@@ -20,15 +20,18 @@ dataSource: DataSource;
20
20
  class DataSource {
21
21
  constructor(options?: Record<string, any>);
22
22
 
23
- get flowEngine(): FlowEngine;
24
- get displayName(): string;
25
- get key(): string;
26
- get name(): string;
23
+ // Read-only properties
24
+ get flowEngine(): FlowEngine; // Current FlowEngine instance
25
+ get displayName(): string; // Display name (supports i18n)
26
+ get key(): string; // Data source key, e.g., 'main'
27
+ get name(): string; // Same as key
27
28
 
28
- getCollections(): Collection[];
29
- getCollection(name: string): Collection | undefined;
30
- getAssociation(associationName: string): CollectionField | undefined;
29
+ // Collection reading
30
+ getCollections(): Collection[]; // Get all collections
31
+ getCollection(name: string): Collection | undefined; // Get collection by name
32
+ getAssociation(associationName: string): CollectionField | undefined; // Get association field (e.g., users.roles)
31
33
 
34
+ // Collection management
32
35
  addCollection(collection: Collection | CollectionOptions): void;
33
36
  updateCollection(newOptions: CollectionOptions): void;
34
37
  upsertCollection(options: CollectionOptions): Collection | undefined;
@@ -36,6 +39,7 @@ class DataSource {
36
39
  removeCollection(name: string): void;
37
40
  clearCollections(): void;
38
41
 
42
+ // Field metadata
39
43
  getCollectionField(fieldPath: string): CollectionField | undefined;
40
44
  }
41
45
  ```
@@ -43,57 +47,61 @@ class DataSource {
43
47
  ## Common Properties
44
48
 
45
49
  | Property | Type | Description |
46
- |----------|------|-------------|
47
- | `key` | `string` | Data source key (e.g. `main`) |
50
+ |------|------|------|
51
+ | `key` | `string` | Data source key, e.g., `'main'` |
48
52
  | `name` | `string` | Same as key |
49
- | `displayName` | `string` | Display name (i18n) |
53
+ | `displayName` | `string` | Display name (supports i18n) |
50
54
  | `flowEngine` | `FlowEngine` | Current FlowEngine instance |
51
55
 
52
56
  ## Common Methods
53
57
 
54
58
  | Method | Description |
55
- |--------|-------------|
56
- | `getCollections()` | All collections in this data source (sorted, hidden filtered) |
57
- | `getCollection(name)` | Collection by name; `name` can be `collectionName.fieldName` for association target |
58
- | `getAssociation(associationName)` | Association field by `collectionName.fieldName` |
59
- | `getCollectionField(fieldPath)` | Field by `collectionName.fieldPath`; supports paths like `users.profile.avatar` |
59
+ |------|------|
60
+ | `getCollections()` | Gets all collections under the current data source (sorted, with hidden ones filtered). |
61
+ | `getCollection(name)` | Gets a collection by name; `name` can be `collectionName.fieldName` to get the target collection of an association. |
62
+ | `getAssociation(associationName)` | Gets an association field definition by `collectionName.fieldName`. |
63
+ | `getCollectionField(fieldPath)` | Gets a field definition by `collectionName.fieldPath`, supporting association paths like `users.profile.avatar`. |
60
64
 
61
- ## Relation to ctx.dataSourceManager
65
+ ## Relationship with ctx.dataSourceManager
62
66
 
63
- | Need | Recommended |
64
- |------|-------------|
65
- | **Single data source for context** | `ctx.dataSource` |
66
- | **Entry to all data sources** | `ctx.dataSourceManager` |
67
- | **Collection in current data source** | `ctx.dataSource.getCollection(name)` |
68
- | **Collection in another data source** | `ctx.dataSourceManager.getCollection(dataSourceKey, collectionName)` |
69
- | **Field in current data source** | `ctx.dataSource.getCollectionField('users.profile.avatar')` |
70
- | **Field across data sources** | `ctx.dataSourceManager.getCollectionField('main.users.profile.avatar')` |
67
+ | Requirement | Recommended Usage |
68
+ |------|----------|
69
+ | **Single data source bound to current context** | `ctx.dataSource` |
70
+ | **Entry point for all data sources** | `ctx.dataSourceManager` |
71
+ | **Get collection within current data source** | `ctx.dataSource.getCollection(name)` |
72
+ | **Get collection across data sources** | `ctx.dataSourceManager.getCollection(dataSourceKey, collectionName)` |
73
+ | **Get field within current data source** | `ctx.dataSource.getCollectionField('users.profile.avatar')` |
74
+ | **Get field across data sources** | `ctx.dataSourceManager.getCollectionField('main.users.profile.avatar')` |
71
75
 
72
- ## Examples
76
+ ## Example
73
77
 
74
- ### Get collections and fields
78
+ ### Get Collections and Fields
75
79
 
76
80
  ```ts
81
+ // Get all collections
77
82
  const collections = ctx.dataSource.getCollections();
78
83
 
84
+ // Get collection by name
79
85
  const users = ctx.dataSource.getCollection('users');
80
86
  const primaryKey = users?.filterTargetKey ?? 'id';
81
87
 
88
+ // Get field definition by "collectionName.fieldPath" (supports associations)
82
89
  const field = ctx.dataSource.getCollectionField('users.profile.avatar');
83
90
  const userNameField = ctx.dataSource.getCollectionField('orders.createdBy.name');
84
91
  ```
85
92
 
86
- ### Get association field
93
+ ### Get Association Fields
87
94
 
88
95
  ```ts
96
+ // Get association field definition by collectionName.fieldName
89
97
  const rolesField = ctx.dataSource.getAssociation('users.roles');
90
98
  if (rolesField?.isAssociationField()) {
91
99
  const targetCol = rolesField.targetCollection;
92
- // ...
100
+ // Process based on target collection structure
93
101
  }
94
102
  ```
95
103
 
96
- ### Iterate collections
104
+ ### Iterate Through Collections for Dynamic Processing
97
105
 
98
106
  ```ts
99
107
  const collections = ctx.dataSource.getCollections();
@@ -104,25 +112,25 @@ for (const col of collections) {
104
112
  }
105
113
  ```
106
114
 
107
- ### Validation or dynamic UI from field metadata
115
+ ### Perform Validation or Dynamic UI Based on Field Metadata
108
116
 
109
117
  ```ts
110
118
  const field = ctx.dataSource.getCollectionField('users.status');
111
119
  if (field) {
112
120
  const options = field.enum ?? [];
113
121
  const operators = field.getFilterOperators();
114
- // ...
122
+ // Perform UI logic or validation based on interface, enum, validation, etc.
115
123
  }
116
124
  ```
117
125
 
118
126
  ## Notes
119
127
 
120
- - `getCollectionField(fieldPath)` uses path format `collectionName.fieldPath`; first segment is collection name, rest is field path (supports association, e.g. `user.name`).
121
- - `getCollection(name)` supports `collectionName.fieldName` and returns the association target collection.
122
- - In RunJS, `ctx.dataSource` is usually determined by the current block/page; if there is no bound data source it may be `undefined`—check before use.
128
+ - The path format for `getCollectionField(fieldPath)` is `collectionName.fieldPath`, where the first segment is the collection name and the subsequent segments are the field path (supports associations, e.g., `user.name`).
129
+ - `getCollection(name)` supports the `collectionName.fieldName` format, returning the target collection of the association field.
130
+ - In the RunJS context, `ctx.dataSource` is usually determined by the data source of the current block or page. If no data source is bound to the context, it may be `undefined`; it is recommended to perform a null check before use.
123
131
 
124
132
  ## Related
125
133
 
126
- - [ctx.dataSourceManager](./data-source-manager.md): manager for all data sources
127
- - [ctx.collection](./collection.md): collection for current context
128
- - [ctx.collectionField](./collection-field.md): current field’s collection field definition
134
+ - [ctx.dataSourceManager](./data-source-manager.md): Data source manager, manages all data sources.
135
+ - [ctx.collection](./collection.md): The collection associated with the current context.
136
+ - [ctx.collectionField](./collection-field.md): The collection field definition for the current field.
@@ -1,57 +1,60 @@
1
1
  # ctx.element
2
2
 
3
- The ElementProxy instance for the sandbox DOM container; it is the default render target of `ctx.render()`. Available in JSBlock, JSField, JSItem, JSColumn, and other contexts that have a render container.
3
+ An `ElementProxy` instance pointing to the sandbox DOM container, serving as the default rendering target for `ctx.render()`. It is available in scenarios where a rendering container exists, such as `JSBlock`, `JSField`, `JSItem`, and `JSColumn`.
4
4
 
5
- ## Use Cases
5
+ ## Applicable Scenarios
6
6
 
7
7
  | Scenario | Description |
8
- |----------|-------------|
9
- | **JSBlock** | Block’s DOM container for custom content |
10
- | **JSField / JSItem / FormJSFieldItem** | Field/item render container (often a `<span>`) |
11
- | **JSColumn** | Table cell DOM container for custom column content |
8
+ |------|------|
9
+ | **JSBlock** | The DOM container for the block, used to render custom block content. |
10
+ | **JSField / JSItem / FormJSFieldItem** | The rendering container for a field or form item (usually a `<span>`). |
11
+ | **JSColumn** | The DOM container for a table cell, used to render custom column content. |
12
12
 
13
- > Note: `ctx.element` is only available in RunJS contexts that have a render container; in contexts without UI (e.g. pure backend) it may be `undefined`—check before use.
13
+ > Note: `ctx.element` is only available in RunJS contexts that have a rendering container. In contexts without a UI (such as pure backend logic), it may be `undefined`. It is recommended to perform a null check before use.
14
14
 
15
- ## Type
15
+ ## Type Definition
16
16
 
17
17
  ```typescript
18
18
  element: ElementProxy | undefined;
19
19
 
20
+ // ElementProxy is a proxy for the raw HTMLElement, exposing a secure API
20
21
  class ElementProxy {
21
- __el: HTMLElement; // Internal native DOM (only for specific cases)
22
- innerHTML: string; // Read/write sanitized with DOMPurify
23
- outerHTML: string;
22
+ __el: HTMLElement; // The internal raw DOM element (accessible only in specific scenarios)
23
+ innerHTML: string; // Sanitized via DOMPurify during read/write
24
+ outerHTML: string; // Same as above
24
25
  appendChild(child: HTMLElement | string): void;
25
- // Other HTMLElement methods passed through (not recommended)
26
+ // Other HTMLElement methods are passed through (direct use is not recommended)
26
27
  }
27
28
  ```
28
29
 
29
- ## Security
30
+ ## Security Requirements
30
31
 
31
- **Recommended: do all rendering via `ctx.render()`.** Do not use `ctx.element`’s DOM APIs directly (e.g. `innerHTML`, `appendChild`, `querySelector`).
32
+ **Recommended: All rendering should be performed via `ctx.render()`.** Avoid using the DOM APIs of `ctx.element` directly (e.g., `innerHTML`, `appendChild`, `querySelector`, etc.).
32
33
 
33
- ### Why use ctx.render()
34
+ ### Why ctx.render() is Recommended
34
35
 
35
- | Benefit | Description |
36
- |---------|-------------|
37
- | **Security** | Centralized control, avoids XSS and unsafe DOM use |
38
- | **React** | Full JSX, components, and lifecycle |
39
- | **Context** | Inherits app ConfigProvider, theme, etc. |
40
- | **Conflicts** | Manages React root create/unmount, avoids multiple instances |
36
+ | Advantage | Description |
37
+ |------|------|
38
+ | **Security** | Centralized security control to prevent XSS and improper DOM operations. |
39
+ | **React Support** | Full support for JSX, React components, and lifecycles. |
40
+ | **Context Inheritance** | Automatically inherits the application's `ConfigProvider`, themes, etc. |
41
+ | **Conflict Handling** | Automatically manages React root creation/unmounting to avoid multi-instance conflicts. |
41
42
 
42
- ### ❌ Not recommended: direct ctx.element use
43
+ ### ❌ Not Recommended: Direct Manipulation of ctx.element
43
44
 
44
45
  ```ts
46
+ // ❌ Not recommended: Using ctx.element APIs directly
45
47
  ctx.element.innerHTML = '<div>Content</div>';
46
48
  ctx.element.appendChild(node);
47
49
  ctx.element.querySelector('.class');
48
50
  ```
49
51
 
50
- > `ctx.element.innerHTML` is deprecated; use `ctx.render()` instead.
52
+ > `ctx.element.innerHTML` is deprecated. Please use `ctx.render()` instead.
51
53
 
52
- ### ✅ Recommended: ctx.render()
54
+ ### ✅ Recommended: Using ctx.render()
53
55
 
54
56
  ```ts
57
+ // ✅ Rendering a React component
55
58
  const { Button, Card } = ctx.libs.antd;
56
59
  ctx.render(
57
60
  <Card title={ctx.t('Welcome')}>
@@ -59,40 +62,43 @@ ctx.render(
59
62
  </Card>
60
63
  );
61
64
 
65
+ // ✅ Rendering an HTML string
62
66
  ctx.render('<div style="padding:16px;">' + ctx.t('Content') + '</div>');
63
67
 
68
+ // ✅ Rendering a DOM node
64
69
  const div = document.createElement('div');
65
70
  div.textContent = ctx.t('Hello');
66
71
  ctx.render(div);
67
72
  ```
68
73
 
69
- ## Exception: popover anchor
74
+ ## Special Case: As a Popover Anchor
70
75
 
71
- When you need the current element as a popover anchor, use `ctx.element?.__el` as the native DOM `target`:
76
+ When you need to open a Popover using the current element as an anchor, you can access `ctx.element?.__el` to get the raw DOM as the `target`:
72
77
 
73
78
  ```ts
79
+ // ctx.viewer.popover requires a raw DOM as the target
74
80
  await ctx.viewer.popover({
75
81
  target: ctx.element?.__el,
76
- content: <div>Popover content</div>,
82
+ content: <div>Popup Content</div>,
77
83
  });
78
84
  ```
79
85
 
80
- > Use `__el` only for this current container as anchor” case; do not touch DOM otherwise.
86
+ > Use `__el` only in scenarios like "using the current container as an anchor"; do not manipulate the DOM directly in other cases.
81
87
 
82
- ## Relation to ctx.render
88
+ ## Relationship with ctx.render
83
89
 
84
- - `ctx.render(vnode)` without a `container` argument renders into `ctx.element`.
85
- - If there is no `ctx.element` and no `container`, an error is thrown.
86
- - You can pass a container: `ctx.render(vnode, customContainer)`.
90
+ - If `ctx.render(vnode)` is called without a `container` argument, it renders into the `ctx.element` container by default.
91
+ - If both `ctx.element` is missing and no `container` is provided, an error will be thrown.
92
+ - You can explicitly specify a container: `ctx.render(vnode, customContainer)`.
87
93
 
88
94
  ## Notes
89
95
 
90
- - Treat `ctx.element` as the internal container for `ctx.render()`; avoid reading or mutating it directly.
91
- - In contexts without a render container, `ctx.element` is `undefined`; ensure a container exists or pass `container` to `ctx.render()`.
92
- - ElementProxy’s `innerHTML`/`outerHTML` are sanitized with DOMPurify, but prefer `ctx.render()` for all rendering.
96
+ - `ctx.element` is intended for internal use by `ctx.render()`. Directly accessing or modifying its properties/methods is not recommended.
97
+ - In contexts without a rendering container, `ctx.element` will be `undefined`. Ensure the container is available or pass a `container` manually before calling `ctx.render()`.
98
+ - Although `innerHTML`/`outerHTML` in `ElementProxy` are sanitized via DOMPurify, it is still recommended to use `ctx.render()` for unified rendering management.
93
99
 
94
100
  ## Related
95
101
 
96
- - [ctx.render](./render.md): render into container
97
- - [ctx.view](./view.md): current view controller
98
- - [ctx.modal](./modal.md): modal APIs
102
+ - [ctx.render](./render.md): Rendering content into a container
103
+ - [ctx.view](./view.md): Current view controller
104
+ - [ctx.modal](./modal.md): Shortcut API for modals
@@ -1,94 +1,96 @@
1
1
  # ctx.exitAll()
2
2
 
3
- Stops the current event flow and all **subsequent** event flows that were triggered in the same event dispatch. Use when a global error or permission check requires stopping every flow for that event.
3
+ Terminates the current event flow and all subsequent event flows triggered in the same event dispatch. It is commonly used when all event flows under the current event need to be aborted immediately due to a global error or permission validation failure.
4
4
 
5
5
  ## Use Cases
6
6
 
7
- Use `ctx.exitAll()` in JS-capable contexts when you need to **stop both the current flow and any later flows for the same event**:
7
+ `ctx.exitAll()` is generally used in JS-executable contexts where it is necessary to **simultaneously abort the current event flow and subsequent event flows triggered by that event**:
8
8
 
9
9
  | Scenario | Description |
10
- |----------|-------------|
11
- | **Event flow** | Main flow fails (e.g. no permission); stop it and any subsequent flows for that event |
12
- | **Linkage rules** | When linkage validation fails and you want to stop current and subsequent linkage |
13
- | **Action events** | Pre-action check fails (e.g. delete permission); block the action and later steps |
10
+ |------|------|
11
+ | **Event Flow** | Main event flow validation fails (e.g., insufficient permissions), requiring the termination of the main flow and any subsequent flows under the same event that have not yet executed. |
12
+ | **Linkage Rules** | When linkage validation fails, the current linkage and subsequent linkages triggered by the same event must be terminated. |
13
+ | **Action Events** | Pre-action validation fails (e.g., permission check before deletion), requiring the prevention of the main action and subsequent steps. |
14
14
 
15
- > Difference from `ctx.exit()`: `ctx.exit()` only stops the current flow; `ctx.exitAll()` also stops **subsequent** flows for that event.
15
+ > Difference from `ctx.exit()`: `ctx.exit()` only terminates the current event flow; `ctx.exitAll()` terminates the current event flow and any **unexecuted** subsequent event flows in the same event dispatch.
16
16
 
17
- ## Type
17
+ ## Type Definition
18
18
 
19
19
  ```ts
20
20
  exitAll(): never;
21
21
  ```
22
22
 
23
- Calling `ctx.exitAll()` throws an internal `FlowExitAllException`, which the engine uses to stop the current flow instance and subsequent flows for the same event. The rest of the current JS does not run.
23
+ Calling `ctx.exitAll()` throws an internal `FlowExitAllException`, which is caught by the FlowEngine to stop the current event flow instance and subsequent event flows under the same event. Once called, the remaining statements in the current JS code will not be executed.
24
24
 
25
25
  ## Comparison with ctx.exit()
26
26
 
27
27
  | Method | Scope |
28
- |--------|--------|
29
- | `ctx.exit()` | Stops only the current flow; later flows still run |
30
- | `ctx.exitAll()` | Stops the current flow and **subsequent** flows for the same event |
28
+ |------|----------|
29
+ | `ctx.exit()` | Only terminates the current event flow; subsequent event flows are unaffected. |
30
+ | `ctx.exitAll()` | Terminates the current event flow and aborts subsequent event flows executed **sequentially** under the same event. |
31
31
 
32
- ## Execution mode
32
+ ## Execution Mode
33
33
 
34
- - **Sequential**: flows for the same event run one after another; after any flow calls `ctx.exitAll()`, later flows do not run.
35
- - **Parallel**: flows run in parallel; one flow calling `ctx.exitAll()` does not stop other already-running flows.
34
+ - **Sequential Execution**: Event flows under the same event are executed in order. After any event flow calls `ctx.exitAll()`, subsequent event flows will not execute.
35
+ - **Parallel Execution**: Event flows under the same event are executed in parallel. Calling `ctx.exitAll()` in one event flow will not interrupt other concurrent event flows (as they are independent).
36
36
 
37
37
  ## Examples
38
38
 
39
- ### Stop all flows on permission failure
39
+ ### Terminate all event flows when permission validation fails
40
40
 
41
41
  ```ts
42
+ // Abort the main event flow and subsequent event flows when permissions are insufficient
42
43
  if (!hasPermission(ctx)) {
43
- ctx.notification.error({ message: 'No permission' });
44
+ ctx.notification.error({ message: 'No operation permission' });
44
45
  ctx.exitAll();
45
46
  }
46
47
  ```
47
48
 
48
- ### Stop on global pre-check failure
49
+ ### Terminate when global pre-validation fails
49
50
 
50
51
  ```ts
52
+ // Example: If associated data is found to be non-deletable before deletion, prevent the main event flow and subsequent actions
51
53
  const canDelete = await checkDeletable(ctx.model?.getValue?.());
52
54
  if (!canDelete) {
53
- ctx.message.error('Cannot delete: related data exists');
55
+ ctx.message.error('Cannot delete: associated data exists');
54
56
  ctx.exitAll();
55
57
  }
56
58
  ```
57
59
 
58
- ### When to use ctx.exit() vs ctx.exitAll()
60
+ ### Choosing between ctx.exit() and ctx.exitAll()
59
61
 
60
62
  ```ts
61
- // Only this flow ctx.exit()
63
+ // Only the current event flow needs to exit -> Use ctx.exit()
62
64
  if (!params.valid) {
63
- ctx.message.error('Invalid params');
64
- ctx.exit();
65
+ ctx.message.error('Invalid parameters');
66
+ ctx.exit(); // Subsequent event flows are unaffected
65
67
  }
66
68
 
67
- // This and all subsequent flows ctx.exitAll()
69
+ // Need to terminate all subsequent event flows under the current event -> Use ctx.exitAll()
68
70
  if (!ctx.model?.context?.getPermission?.()) {
69
- ctx.notification.warning({ message: 'No permission' });
70
- ctx.exitAll();
71
+ ctx.notification.warning({ message: 'Insufficient permissions' });
72
+ ctx.exitAll(); // Both the main event flow and subsequent event flows under the same event are terminated
71
73
  }
72
74
  ```
73
75
 
74
- ### Message then exit
76
+ ### Prompt before terminating
75
77
 
76
78
  ```ts
77
79
  if (!isValidInput(ctx.form?.getValues?.())) {
78
- ctx.message.warning('Please fix form errors first');
80
+ ctx.message.warning('Please correct the errors in the form first');
79
81
  ctx.exitAll();
80
82
  }
81
83
  ```
82
84
 
83
85
  ## Notes
84
86
 
85
- - After `ctx.exitAll()`, the rest of the current JS does not run; explain to the user with `ctx.message`, `ctx.notification`, or a dialog before calling.
86
- - You usually do not need to catch `FlowExitAllException`; the engine handles it.
87
- - To stop only the current flow, use `ctx.exit()`.
88
- - In parallel mode, `ctx.exitAll()` only stops the current flow; it does not cancel other concurrent flows.
87
+ - After calling `ctx.exitAll()`, subsequent code in the current JS will not execute. It is recommended to explain the reason to the user via `ctx.message`, `ctx.notification`, or a modal before calling it.
88
+ - Business code usually does not need to catch `FlowExitAllException`; let the FlowEngine handle it.
89
+ - If you only need to stop the current event flow without affecting subsequent ones, use `ctx.exit()`.
90
+ - In parallel mode, `ctx.exitAll()` only terminates the current event flow and does not interrupt other concurrent event flows.
89
91
 
90
92
  ## Related
91
93
 
92
- - [ctx.exit()](./exit.md): stop only the current flow
93
- - [ctx.message](./message.md): message API
94
- - [ctx.modal](./modal.md): confirm dialog
94
+ - [ctx.exit()](./exit.md): Terminates only the current event flow
95
+ - [ctx.message](./message.md): Message prompts
96
+ - [ctx.modal](./modal.md): Confirmation modal