weaver-e10-builder 1.2.3 → 1.5.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/assets/org-employee-template.xlsx +0 -0
- package/dist/commands/actionflow.d.ts.map +1 -1
- package/dist/commands/actionflow.js +12 -25
- package/dist/commands/actionflow.js.map +1 -1
- package/dist/commands/designer-css.d.ts +15 -0
- package/dist/commands/designer-css.d.ts.map +1 -0
- package/dist/commands/designer-css.js +205 -0
- package/dist/commands/designer-css.js.map +1 -0
- package/dist/commands/form-button.d.ts.map +1 -1
- package/dist/commands/form-button.js +28 -5
- package/dist/commands/form-button.js.map +1 -1
- package/dist/commands/form-field-lang.d.ts.map +1 -1
- package/dist/commands/form-field-lang.js +4 -39
- package/dist/commands/form-field-lang.js.map +1 -1
- package/dist/commands/form-field-linkage.d.ts.map +1 -1
- package/dist/commands/form-field-linkage.js +27 -6
- package/dist/commands/form-field-linkage.js.map +1 -1
- package/dist/commands/form-formula-linkage.d.ts +3 -0
- package/dist/commands/form-formula-linkage.d.ts.map +1 -0
- package/dist/commands/form-formula-linkage.js +434 -0
- package/dist/commands/form-formula-linkage.js.map +1 -0
- package/dist/commands/form-formula.d.ts.map +1 -1
- package/dist/commands/form-formula.js +22 -3
- package/dist/commands/form-formula.js.map +1 -1
- package/dist/commands/form-layout-init.d.ts.map +1 -1
- package/dist/commands/form-layout-init.js +15 -10
- package/dist/commands/form-layout-init.js.map +1 -1
- package/dist/commands/form-layout.js +24 -21
- package/dist/commands/form-layout.js.map +1 -1
- package/dist/commands/form-list-click.d.ts.map +1 -1
- package/dist/commands/form-list-click.js +2 -1
- package/dist/commands/form-list-click.js.map +1 -1
- package/dist/commands/form-native.d.ts.map +1 -1
- package/dist/commands/form-native.js +192 -3
- package/dist/commands/form-native.js.map +1 -1
- package/dist/commands/form-validate.d.ts.map +1 -1
- package/dist/commands/form-validate.js +11 -3
- package/dist/commands/form-validate.js.map +1 -1
- package/dist/commands/form.d.ts.map +1 -1
- package/dist/commands/form.js +323 -192
- package/dist/commands/form.js.map +1 -1
- package/dist/commands/matrix.d.ts.map +1 -1
- package/dist/commands/matrix.js +175 -36
- package/dist/commands/matrix.js.map +1 -1
- package/dist/commands/menu.d.ts.map +1 -1
- package/dist/commands/menu.js +170 -23
- package/dist/commands/menu.js.map +1 -1
- package/dist/commands/org.d.ts +10 -0
- package/dist/commands/org.d.ts.map +1 -0
- package/dist/commands/org.js +278 -0
- package/dist/commands/org.js.map +1 -0
- package/dist/commands/role.d.ts.map +1 -1
- package/dist/commands/role.js +106 -62
- package/dist/commands/role.js.map +1 -1
- package/dist/commands/wf-form.d.ts +1 -0
- package/dist/commands/wf-form.d.ts.map +1 -1
- package/dist/commands/wf-form.js +545 -39
- package/dist/commands/wf-form.js.map +1 -1
- package/dist/commands/workflow-auth-resp.d.ts.map +1 -1
- package/dist/commands/workflow-auth-resp.js +53 -5
- package/dist/commands/workflow-auth-resp.js.map +1 -1
- package/dist/commands/workflow-create-auth-resp.d.ts.map +1 -1
- package/dist/commands/workflow-create-auth-resp.js +5 -1
- package/dist/commands/workflow-create-auth-resp.js.map +1 -1
- package/dist/commands/workflow-node-assign-flow.d.ts.map +1 -1
- package/dist/commands/workflow-node-assign-flow.js +1 -2
- package/dist/commands/workflow-node-assign-flow.js.map +1 -1
- package/dist/commands/workflow-node.d.ts.map +1 -1
- package/dist/commands/workflow-node.js +147 -2
- package/dist/commands/workflow-node.js.map +1 -1
- package/dist/commands/workflow-odoc.d.ts.map +1 -1
- package/dist/commands/workflow-odoc.js +56 -56
- package/dist/commands/workflow-odoc.js.map +1 -1
- package/dist/commands/workflow-setting.d.ts.map +1 -1
- package/dist/commands/workflow-setting.js +77 -1
- package/dist/commands/workflow-setting.js.map +1 -1
- package/dist/commands/workflow.d.ts.map +1 -1
- package/dist/commands/workflow.js +114 -89
- package/dist/commands/workflow.js.map +1 -1
- package/dist/core/client.d.ts +14 -0
- package/dist/core/client.d.ts.map +1 -1
- package/dist/core/client.js +28 -12
- package/dist/core/client.js.map +1 -1
- package/dist/index.js +6 -0
- package/dist/index.js.map +1 -1
- package/dist/services/action-detail.d.ts.map +1 -1
- package/dist/services/action-detail.js +5 -4
- package/dist/services/action-detail.js.map +1 -1
- package/dist/services/actionflow/command_output.d.ts +7 -0
- package/dist/services/actionflow/command_output.d.ts.map +1 -1
- package/dist/services/actionflow/command_output.js +46 -0
- package/dist/services/actionflow/command_output.js.map +1 -1
- package/dist/services/actionflow/components/action_eb_add.d.ts.map +1 -1
- package/dist/services/actionflow/components/action_eb_add.js +14 -4
- package/dist/services/actionflow/components/action_eb_add.js.map +1 -1
- package/dist/services/actionflow/components/action_eb_add_compiler.d.ts.map +1 -1
- package/dist/services/actionflow/components/action_eb_add_compiler.js +29 -0
- package/dist/services/actionflow/components/action_eb_add_compiler.js.map +1 -1
- package/dist/services/actionflow/components/action_eb_update.d.ts.map +1 -1
- package/dist/services/actionflow/components/action_eb_update.js +23 -8
- package/dist/services/actionflow/components/action_eb_update.js.map +1 -1
- package/dist/services/actionflow/components/action_eb_update_compiler.d.ts.map +1 -1
- package/dist/services/actionflow/components/action_eb_update_compiler.js +261 -13
- package/dist/services/actionflow/components/action_eb_update_compiler.js.map +1 -1
- package/dist/services/actionflow/components/approve_create.d.ts.map +1 -1
- package/dist/services/actionflow/components/approve_create.js +6 -3
- package/dist/services/actionflow/components/approve_create.js.map +1 -1
- package/dist/services/actionflow/components/custom_set_form.d.ts +10 -0
- package/dist/services/actionflow/components/custom_set_form.d.ts.map +1 -0
- package/dist/services/actionflow/components/custom_set_form.js +99 -0
- package/dist/services/actionflow/components/custom_set_form.js.map +1 -0
- package/dist/services/actionflow/components/custom_trigger.d.ts +2 -2
- package/dist/services/actionflow/components/custom_trigger.d.ts.map +1 -1
- package/dist/services/actionflow/components/custom_trigger.js +11 -11
- package/dist/services/actionflow/components/custom_trigger.js.map +1 -1
- package/dist/services/actionflow/components/dml_execute.d.ts.map +1 -1
- package/dist/services/actionflow/components/dml_execute.js +7 -3
- package/dist/services/actionflow/components/dml_execute.js.map +1 -1
- package/dist/services/actionflow/components/document_actions.d.ts.map +1 -1
- package/dist/services/actionflow/components/document_actions.js +7 -3
- package/dist/services/actionflow/components/document_actions.js.map +1 -1
- package/dist/services/actionflow/components/enquiry_form.js +1 -1
- package/dist/services/actionflow/components/enquiry_form.js.map +1 -1
- package/dist/services/actionflow/components/hrm_actions.d.ts.map +1 -1
- package/dist/services/actionflow/components/hrm_actions.js +7 -3
- package/dist/services/actionflow/components/hrm_actions.js.map +1 -1
- package/dist/services/actionflow/components/multiple_execution.d.ts.map +1 -1
- package/dist/services/actionflow/components/multiple_execution.js +14 -5
- package/dist/services/actionflow/components/multiple_execution.js.map +1 -1
- package/dist/services/actionflow/components/output.d.ts.map +1 -1
- package/dist/services/actionflow/components/output.js +6 -1
- package/dist/services/actionflow/components/output.js.map +1 -1
- package/dist/services/actionflow/components/send_message.js +2 -2
- package/dist/services/actionflow/components/send_message.js.map +1 -1
- package/dist/services/actionflow/components/workflow_actions.d.ts.map +1 -1
- package/dist/services/actionflow/components/workflow_actions.js +7 -3
- package/dist/services/actionflow/components/workflow_actions.js.map +1 -1
- package/dist/services/actionflow/context_preflight.d.ts.map +1 -1
- package/dist/services/actionflow/context_preflight.js +25 -8
- package/dist/services/actionflow/context_preflight.js.map +1 -1
- package/dist/services/actionflow/context_provider.d.ts.map +1 -1
- package/dist/services/actionflow/context_provider.js +24 -4
- package/dist/services/actionflow/context_provider.js.map +1 -1
- package/dist/services/actionflow/custom_trigger_context.d.ts +10 -0
- package/dist/services/actionflow/custom_trigger_context.d.ts.map +1 -0
- package/dist/services/actionflow/custom_trigger_context.js +46 -0
- package/dist/services/actionflow/custom_trigger_context.js.map +1 -0
- package/dist/services/actionflow/dynamic_resources.d.ts.map +1 -1
- package/dist/services/actionflow/dynamic_resources.js +1 -1
- package/dist/services/actionflow/dynamic_resources.js.map +1 -1
- package/dist/services/actionflow/ebuilder_source.d.ts +19 -0
- package/dist/services/actionflow/ebuilder_source.d.ts.map +1 -0
- package/dist/services/actionflow/ebuilder_source.js +78 -0
- package/dist/services/actionflow/ebuilder_source.js.map +1 -0
- package/dist/services/actionflow/filter_rules.js +2 -2
- package/dist/services/actionflow/filter_rules.js.map +1 -1
- package/dist/services/actionflow/form_source.d.ts +51 -10
- package/dist/services/actionflow/form_source.d.ts.map +1 -1
- package/dist/services/actionflow/form_source.js +173 -29
- package/dist/services/actionflow/form_source.js.map +1 -1
- package/dist/services/actionflow/formula_service.d.ts +13 -2
- package/dist/services/actionflow/formula_service.d.ts.map +1 -1
- package/dist/services/actionflow/formula_service.js +104 -42
- package/dist/services/actionflow/formula_service.js.map +1 -1
- package/dist/services/actionflow/id_generator.d.ts +2 -0
- package/dist/services/actionflow/id_generator.d.ts.map +1 -1
- package/dist/services/actionflow/id_generator.js +13 -0
- package/dist/services/actionflow/id_generator.js.map +1 -1
- package/dist/services/actionflow/preflight_service.d.ts +6 -0
- package/dist/services/actionflow/preflight_service.d.ts.map +1 -1
- package/dist/services/actionflow/preflight_service.js +217 -4
- package/dist/services/actionflow/preflight_service.js.map +1 -1
- package/dist/services/actionflow/workflow_compiler.d.ts.map +1 -1
- package/dist/services/actionflow/workflow_compiler.js +172 -50
- package/dist/services/actionflow/workflow_compiler.js.map +1 -1
- package/dist/services/auth-resp-condition.d.ts +35 -0
- package/dist/services/auth-resp-condition.d.ts.map +1 -0
- package/dist/services/auth-resp-condition.js +111 -0
- package/dist/services/auth-resp-condition.js.map +1 -0
- package/dist/services/condition-rules.d.ts.map +1 -1
- package/dist/services/condition-rules.js +4 -1
- package/dist/services/condition-rules.js.map +1 -1
- package/dist/services/designer-css.d.ts +89 -0
- package/dist/services/designer-css.d.ts.map +1 -0
- package/dist/services/designer-css.js +163 -0
- package/dist/services/designer-css.js.map +1 -0
- package/dist/services/dom-structure.d.ts +42 -0
- package/dist/services/dom-structure.d.ts.map +1 -0
- package/dist/services/dom-structure.js +251 -0
- package/dist/services/dom-structure.js.map +1 -0
- package/dist/services/esb-interface/document-parser.d.ts.map +1 -1
- package/dist/services/esb-interface/document-parser.js +62 -5
- package/dist/services/esb-interface/document-parser.js.map +1 -1
- package/dist/services/form-association.d.ts +19 -0
- package/dist/services/form-association.d.ts.map +1 -1
- package/dist/services/form-association.js +64 -0
- package/dist/services/form-association.js.map +1 -1
- package/dist/services/form-button-action.d.ts +7 -0
- package/dist/services/form-button-action.d.ts.map +1 -1
- package/dist/services/form-button-action.js +11 -1
- package/dist/services/form-button-action.js.map +1 -1
- package/dist/services/form-create.d.ts +4 -0
- package/dist/services/form-create.d.ts.map +1 -1
- package/dist/services/form-create.js +18 -12
- package/dist/services/form-create.js.map +1 -1
- package/dist/services/form-field-patch.d.ts +25 -1
- package/dist/services/form-field-patch.d.ts.map +1 -1
- package/dist/services/form-field-patch.js +52 -9
- package/dist/services/form-field-patch.js.map +1 -1
- package/dist/services/form-formula-linkage.d.ts +349 -0
- package/dist/services/form-formula-linkage.d.ts.map +1 -0
- package/dist/services/form-formula-linkage.js +546 -0
- package/dist/services/form-formula-linkage.js.map +1 -0
- package/dist/services/form-i18n-label.d.ts +48 -0
- package/dist/services/form-i18n-label.d.ts.map +1 -0
- package/dist/services/form-i18n-label.js +91 -0
- package/dist/services/form-i18n-label.js.map +1 -0
- package/dist/services/form-layout-insert.d.ts +84 -0
- package/dist/services/form-layout-insert.d.ts.map +1 -0
- package/dist/services/form-layout-insert.js +244 -0
- package/dist/services/form-layout-insert.js.map +1 -0
- package/dist/services/form-linkage-condition.d.ts +159 -0
- package/dist/services/form-linkage-condition.d.ts.map +1 -0
- package/dist/services/form-linkage-condition.js +307 -0
- package/dist/services/form-linkage-condition.js.map +1 -0
- package/dist/services/form-style-template.d.ts +6 -2
- package/dist/services/form-style-template.d.ts.map +1 -1
- package/dist/services/form-style-template.js +8 -4
- package/dist/services/form-style-template.js.map +1 -1
- package/dist/services/formula-detail.d.ts +98 -6
- package/dist/services/formula-detail.d.ts.map +1 -1
- package/dist/services/formula-detail.js +208 -26
- package/dist/services/formula-detail.js.map +1 -1
- package/dist/services/matrix-rows.d.ts +43 -0
- package/dist/services/matrix-rows.d.ts.map +1 -0
- package/dist/services/matrix-rows.js +104 -0
- package/dist/services/matrix-rows.js.map +1 -0
- package/dist/services/menu-catalog.d.ts +84 -0
- package/dist/services/menu-catalog.d.ts.map +1 -0
- package/dist/services/menu-catalog.js +183 -0
- package/dist/services/menu-catalog.js.map +1 -0
- package/dist/services/org-department.d.ts +114 -0
- package/dist/services/org-department.d.ts.map +1 -0
- package/dist/services/org-department.js +209 -0
- package/dist/services/org-department.js.map +1 -0
- package/dist/services/org-employee.d.ts +87 -0
- package/dist/services/org-employee.d.ts.map +1 -0
- package/dist/services/org-employee.js +219 -0
- package/dist/services/org-employee.js.map +1 -0
- package/dist/services/role-member.d.ts +99 -0
- package/dist/services/role-member.d.ts.map +1 -0
- package/dist/services/role-member.js +206 -0
- package/dist/services/role-member.js.map +1 -0
- package/dist/services/workflow-add-step.d.ts +45 -0
- package/dist/services/workflow-add-step.d.ts.map +1 -0
- package/dist/services/workflow-add-step.js +122 -0
- package/dist/services/workflow-add-step.js.map +1 -0
- package/dist/services/workflow-assign-flow.d.ts +1 -6
- package/dist/services/workflow-assign-flow.d.ts.map +1 -1
- package/dist/services/workflow-assign-flow.js +3 -8
- package/dist/services/workflow-assign-flow.js.map +1 -1
- package/dist/services/workflow-drawback.d.ts +19 -0
- package/dist/services/workflow-drawback.d.ts.map +1 -0
- package/dist/services/workflow-drawback.js +59 -0
- package/dist/services/workflow-drawback.js.map +1 -0
- package/dist/services/workflow-info.d.ts +83 -0
- package/dist/services/workflow-info.d.ts.map +1 -0
- package/dist/services/workflow-info.js +97 -0
- package/dist/services/workflow-info.js.map +1 -0
- package/dist/services/workflow-links.d.ts +51 -0
- package/dist/services/workflow-links.d.ts.map +1 -0
- package/dist/services/workflow-links.js +162 -0
- package/dist/services/workflow-links.js.map +1 -0
- package/dist/services/workflow-node-layout.d.ts +45 -4
- package/dist/services/workflow-node-layout.d.ts.map +1 -1
- package/dist/services/workflow-node-layout.js +142 -41
- package/dist/services/workflow-node-layout.js.map +1 -1
- package/dist/services/workflow-odoc-setting.d.ts +43 -0
- package/dist/services/workflow-odoc-setting.d.ts.map +1 -0
- package/dist/services/workflow-odoc-setting.js +109 -0
- package/dist/services/workflow-odoc-setting.js.map +1 -0
- package/dist/services/workflow-tab-config.d.ts +54 -0
- package/dist/services/workflow-tab-config.d.ts.map +1 -0
- package/dist/services/workflow-tab-config.js +137 -0
- package/dist/services/workflow-tab-config.js.map +1 -0
- package/dist/types.d.ts +5 -1
- package/dist/types.d.ts.map +1 -1
- package/dist/utils/column-name.d.ts +24 -0
- package/dist/utils/column-name.d.ts.map +1 -1
- package/dist/utils/column-name.js +16 -0
- package/dist/utils/column-name.js.map +1 -1
- package/ecodecmd/package.json +1 -2
- package/ecodecmd/src/loaddep.js +19 -9
- package/package.json +48 -48
- package/skill-docs/SKILL.md +15 -11
- package/skill-docs/_catalog.md +85 -79
- package/skill-docs/actionflows/SKILL.md +173 -168
- package/skill-docs/actionflows/references/components/ebuilder/ActionEbAdd.md +38 -1
- package/skill-docs/actionflows/references/components/ebuilder/ActionEbUpdate.md +42 -0
- package/skill-docs/actionflows/references/components/ebuilder/EventButton.md +1 -1
- package/skill-docs/actionflows/references/components/logic/Output.md +2 -0
- package/skill-docs/actionflows/references/components/trigger/CustomTrigger.md +48 -11
- package/skill-docs/actionflows/references/components/workflow/ApproveCreate.md +1 -1
- package/skill-docs/assets/dom-structure/Bar.json +341 -0
- package/skill-docs/assets/dom-structure/BarStack.json +341 -0
- package/skill-docs/assets/dom-structure/Bubble.json +323 -0
- package/skill-docs/assets/dom-structure/Calendar.json +515 -0
- package/skill-docs/assets/dom-structure/Circular.json +337 -0
- package/skill-docs/assets/dom-structure/CollapsePanel.json +289 -0
- package/skill-docs/assets/dom-structure/Comment.json +617 -0
- package/skill-docs/assets/dom-structure/CountDown.json +755 -0
- package/skill-docs/assets/dom-structure/DigitalPanel.json +191 -0
- package/skill-docs/assets/dom-structure/EbButton.json +387 -0
- package/skill-docs/assets/dom-structure/FastCreate.json +242 -0
- package/skill-docs/assets/dom-structure/Gauge.json +282 -0
- package/skill-docs/assets/dom-structure/HBar.json +336 -0
- package/skill-docs/assets/dom-structure/HBarStack.json +337 -0
- package/skill-docs/assets/dom-structure/Line.json +341 -0
- package/skill-docs/assets/dom-structure/NList.json +712 -0
- package/skill-docs/assets/dom-structure/NavBar.json +274 -0
- package/skill-docs/assets/dom-structure/NavPanel.json +390 -0
- package/skill-docs/assets/dom-structure/NewTab.json +606 -0
- package/skill-docs/assets/dom-structure/Nightingale.json +336 -0
- package/skill-docs/assets/dom-structure/PageHeader.json +205 -0
- package/skill-docs/assets/dom-structure/Picture.json +209 -0
- package/skill-docs/assets/dom-structure/Pie.json +338 -0
- package/skill-docs/assets/dom-structure/ProgressChart.json +299 -0
- package/skill-docs/assets/dom-structure/SearchGlobal.json +628 -0
- package/skill-docs/assets/dom-structure/Slide.json +489 -0
- package/skill-docs/assets/dom-structure/Treemap.json +324 -0
- package/skill-docs/references/common/guide-plan-template.md +10 -4
- package/skill-docs/references/common/ref-cli-commands.md +67 -34
- package/skill-docs/references/ebuilder-designer/guide-designer-components.md +12 -1
- package/skill-docs/references/ebuilder-designer/guide-designer-css.md +127 -0
- package/skill-docs/references/ebuilder-designer/guide-designer.md +6 -5
- package/skill-docs/references/esb-interface/guide-import.md +4 -1
- package/skill-docs/references/form/guide-create-form.md +14 -1
- package/skill-docs/references/form/guide-field-linkage.md +2 -0
- package/skill-docs/references/form/guide-form-formula-functions.md +36 -0
- package/skill-docs/references/form/guide-form-layout-incremental.md +75 -0
- package/skill-docs/references/form/guide-form-layout-planning.md +1 -1
- package/skill-docs/references/form/guide-form-linkage.md +89 -5
- package/skill-docs/references/form/guide-formula-linkage.md +250 -0
- package/skill-docs/references/form/ref-form-fields.md +6 -0
- package/skill-docs/references/hrm/guide-matrix.md +79 -16
- package/skill-docs/references/hrm/guide-org-employee.md +56 -0
- package/skill-docs/references/menu/system-menus.md +12 -0
- package/skill-docs/references/workflow/guide-workflow-auth-resp.md +48 -22
- package/skill-docs/references/workflow/guide-workflow-odoc-setting.md +248 -0
- package/skill-docs/references/workflow/guide-workflow-odoc.md +25 -33
- package/skill-docs/references/workflow/guide-workflow.md +18 -3
package/dist/commands/form.js
CHANGED
|
@@ -1,14 +1,17 @@
|
|
|
1
1
|
import { writeFileSync, existsSync, readFileSync } from 'fs';
|
|
2
2
|
import { AuthSession } from '../core/auth.js';
|
|
3
3
|
import { ApiClient } from '../core/client.js';
|
|
4
|
-
import { toColumnName, toTableName } from '../utils/column-name.js';
|
|
5
|
-
import { createCustomPhysicalForm, addInitialFieldsToCustomPhysicalForm, placeholderFromFormat, reapplyGroupLayout } from '../services/form-create.js';
|
|
4
|
+
import { toColumnName, toTableName, resolveFieldKeys } from '../utils/column-name.js';
|
|
5
|
+
import { createCustomPhysicalForm, addInitialFieldsToCustomPhysicalForm, placeholderFromFormat, reapplyGroupLayout, queryFormStorageSetting } from '../services/form-create.js';
|
|
6
6
|
import { FormSubDetailService, resolveDetailTable } from '../services/form-sub-detail.js';
|
|
7
7
|
import { RICH_TYPE_MAP, getRichType, richIdUnits, BROWSER_KINDS } from '../services/rich-types.js';
|
|
8
8
|
import { dropFieldComponents, prepareLayoutForSave } from '../services/form-field-drop.js';
|
|
9
9
|
import { describeEditBaseFailure, resolveEditBase as resolveEditBasePure } from '../services/form-edit-base.js';
|
|
10
|
-
import { applyFieldPatches } from '../services/form-field-patch.js';
|
|
10
|
+
import { applyFieldPatches, platformFieldShape } from '../services/form-field-patch.js';
|
|
11
11
|
import { ensureDisplayColumns } from '../services/form-ebuilder-columns.js';
|
|
12
|
+
import { insertFieldIntoLayout, patchFieldLayout } from '../services/form-layout-insert.js';
|
|
13
|
+
import { buildLinkageAddPayload, addLinkage, resolveEffect, readLinkageConfig } from '../services/form-linkage-condition.js';
|
|
14
|
+
import { createMultilangLabel } from '../services/form-i18n-label.js';
|
|
12
15
|
import { buildFormulaParameters, defaultReturnType } from '../services/formula-detail.js';
|
|
13
16
|
import { registerOptionTemplateCommand } from './form-option-template.js';
|
|
14
17
|
/**
|
|
@@ -20,7 +23,7 @@ import { registerOptionTemplateCommand } from './form-option-template.js';
|
|
|
20
23
|
const CK_CANON = {
|
|
21
24
|
textarea: 'TextArea', ebuilder: 'EBuilder', datetime: 'DateTime',
|
|
22
25
|
idcard: 'IDCard', mobile: 'Mobile', email: 'Email', phone: 'Phone',
|
|
23
|
-
employee: 'Employee', department: 'Department', location: 'Location',
|
|
26
|
+
employee: 'Employee', department: 'Department', subcompany: 'SubCompany', location: 'Location',
|
|
24
27
|
switch: 'Switch', select: 'Select', checkbox: 'CheckBox', radiobox: 'RadioBox',
|
|
25
28
|
money: 'Money', number: 'Number', date: 'Date', text: 'Text',
|
|
26
29
|
daterange: 'DateRange', detailtable: 'DetailTable', city: 'City',
|
|
@@ -354,6 +357,8 @@ export function registerFormCommands(program) {
|
|
|
354
357
|
+ 'valueKey 须为数字、省略则平台生成)')
|
|
355
358
|
.option('--menu', '建表后添加台账菜单(默认不加;漏加可用 `e10-cli menu add-table` 补)')
|
|
356
359
|
.option('--layout <type>', '表单布局类型:FLOW(流式)/EXCEL(表格,缺省)。布局类型建表后不可切换', 'EXCEL')
|
|
360
|
+
.option('--table-name <name>', '自定义数据库表名。平台前缀(如 uf_)由 CLI 自动补,传 uf_xxx 或只传自定义部分都可以;'
|
|
361
|
+
+ '须字母开头、只含字母数字下划线。缺省按表单名拼音首字母 + 随机数生成')
|
|
357
362
|
.action(async (appId, name, cmdOpts) => {
|
|
358
363
|
const opts = program.opts();
|
|
359
364
|
const auth = await AuthSession.fromOptions(opts);
|
|
@@ -560,8 +565,10 @@ export function registerFormCommands(program) {
|
|
|
560
565
|
if (f.formName)
|
|
561
566
|
field.formName = f.formName;
|
|
562
567
|
}
|
|
563
|
-
|
|
564
|
-
|
|
568
|
+
// fields.json 可分别指定 dataKey / columnName;默认同值(都是拼音首字母)
|
|
569
|
+
const fKeys = resolveFieldKeys(f.fieldName, f);
|
|
570
|
+
field.dataKey = fKeys.dataKey;
|
|
571
|
+
field.columnName = fKeys.columnName;
|
|
565
572
|
formFields.push(field);
|
|
566
573
|
// DetailTable occupies 2 rows of layout space
|
|
567
574
|
rowIdx += isDetail ? 2 : 1;
|
|
@@ -592,7 +599,17 @@ export function registerFormCommands(program) {
|
|
|
592
599
|
formValues: { formName: name, formTitle: name, tableName, tableType: 'physical' },
|
|
593
600
|
};
|
|
594
601
|
// Use standard creation flow for controllable table names
|
|
595
|
-
|
|
602
|
+
// --table-name 指定物理表名(uf_ 前缀由服务层 resolveCustomPhysicalTableName 补);缺省按表单名生成
|
|
603
|
+
const customTableName = cmdOpts.tableName?.trim();
|
|
604
|
+
if (customTableName) {
|
|
605
|
+
const setting = await queryFormStorageSetting(client, baseUrl, appId);
|
|
606
|
+
if (!setting.storageSettings.includes('physical')) {
|
|
607
|
+
console.error(`该应用未启用物理表(storageSettings=${setting.storageSettings.join('/') || '空'}),`
|
|
608
|
+
+ '没有独立的数据库表名,--table-name 不适用');
|
|
609
|
+
process.exit(1);
|
|
610
|
+
}
|
|
611
|
+
}
|
|
612
|
+
const requestedTableName = customTableName || toTableName(name);
|
|
596
613
|
const layoutType = String(cmdOpts.layout || 'EXCEL').toUpperCase();
|
|
597
614
|
if (layoutType !== 'FLOW' && layoutType !== 'EXCEL') {
|
|
598
615
|
console.error(`--layout 只支持 FLOW(流式) 或 EXCEL(表格),收到: ${cmdOpts.layout}`);
|
|
@@ -602,7 +619,7 @@ export function registerFormCommands(program) {
|
|
|
602
619
|
let formId = '';
|
|
603
620
|
let fieldGroups = [];
|
|
604
621
|
try {
|
|
605
|
-
const result = await createCustomPhysicalForm(client, baseUrl, appId, name,
|
|
622
|
+
const result = await createCustomPhysicalForm(client, baseUrl, appId, name, requestedTableName, false, layoutType);
|
|
606
623
|
objId = result.objId;
|
|
607
624
|
formId = result.formId;
|
|
608
625
|
console.error(`表单已创建,ID: ${objId}` + (formId ? ` formId: ${formId}` : ''));
|
|
@@ -626,6 +643,9 @@ export function registerFormCommands(program) {
|
|
|
626
643
|
// 文本最大长度(Text 缺省 100、TextArea 缺省 4000)+ 日期精度 format(Date/DateTime)需透传,
|
|
627
644
|
// 否则 fields.json 标注的 maxLen/format 被丢(bug:长度默认 100 不生效、日期精度丢失)。
|
|
628
645
|
maxLen: f.maxLen, format: f.format,
|
|
646
|
+
// 字段编码 dataKey / 数据库列名 columnName —— 两者是两个东西,可分别指定。
|
|
647
|
+
// 这里是**白名单透传**,漏一项就会静默丢(maxLen/format 历史上就漏过)。
|
|
648
|
+
dataKey: f.dataKey, columnName: f.columnName,
|
|
629
649
|
}));
|
|
630
650
|
const fieldResult = await addInitialFieldsToCustomPhysicalForm(client, baseUrl, appId, objId, formId, fieldDefsForStandard, auth.tenantKey, layoutType, systemOverrides);
|
|
631
651
|
fieldGroups = fieldResult.fieldGroups || [];
|
|
@@ -769,7 +789,8 @@ export function registerFormCommands(program) {
|
|
|
769
789
|
const colName = df?.columnName || df?.dataKey || '';
|
|
770
790
|
fieldByName.set(f.fieldName, {
|
|
771
791
|
fieldId: f.fieldId,
|
|
772
|
-
dataKey
|
|
792
|
+
// dataKey 与 columnName 是两个东西,各自保留真值 —— 回写时不能互相顶替
|
|
793
|
+
dataKey: df?.dataKey || colName,
|
|
773
794
|
columnName: colName,
|
|
774
795
|
formTableId: df?.formTableId || formTableId,
|
|
775
796
|
});
|
|
@@ -805,7 +826,7 @@ export function registerFormCommands(program) {
|
|
|
805
826
|
openRelateView: false,
|
|
806
827
|
title: ef.fieldName, type: 'EBuilder',
|
|
807
828
|
dataCount: 0,
|
|
808
|
-
dataKey: finfo.
|
|
829
|
+
dataKey: finfo.dataKey,
|
|
809
830
|
systemField: true,
|
|
810
831
|
columnTypeSwitch: false,
|
|
811
832
|
appId,
|
|
@@ -1041,7 +1062,8 @@ export function registerFormCommands(program) {
|
|
|
1041
1062
|
const colName = df?.columnName || df?.dataKey || '';
|
|
1042
1063
|
rfByName.set(f.fieldName, {
|
|
1043
1064
|
fieldId: f.fieldId,
|
|
1044
|
-
dataKey
|
|
1065
|
+
// dataKey 与 columnName 是两个东西,各自保留真值
|
|
1066
|
+
dataKey: df?.dataKey || colName,
|
|
1045
1067
|
columnName: colName,
|
|
1046
1068
|
formTableId: df?.formTableId || rfFormTableId,
|
|
1047
1069
|
});
|
|
@@ -1066,7 +1088,7 @@ export function registerFormCommands(program) {
|
|
|
1066
1088
|
title: rf.fieldName,
|
|
1067
1089
|
type: rf.componentKey === 'Text' ? 'Text' : rf.componentKey,
|
|
1068
1090
|
dataCount: 0,
|
|
1069
|
-
dataKey: myInfo.
|
|
1091
|
+
dataKey: myInfo.dataKey,
|
|
1070
1092
|
systemField: true,
|
|
1071
1093
|
readonlyTransLink: false,
|
|
1072
1094
|
columnTypeSwitch: false,
|
|
@@ -1111,7 +1133,7 @@ export function registerFormCommands(program) {
|
|
|
1111
1133
|
// (batch/save 初建不带 isSingle 到 layout comp)。之前只对 defaultValue:true 的跑 → 没标默认值
|
|
1112
1134
|
// 的 Employee/Department 漏 isSingle → 平台默认多选(bug:标记单选仍多选)。现对所有 Employee/Department
|
|
1113
1135
|
// 跑设 isSingle;defaultExtend(默认当前用户/部门)仅 defaultValue:true 时加。
|
|
1114
|
-
const personFields = fieldDefs.filter(f => f.componentKey === 'Employee' || f.componentKey === 'Department');
|
|
1136
|
+
const personFields = fieldDefs.filter(f => f.componentKey === 'Employee' || f.componentKey === 'Department' || f.componentKey === 'SubCompany');
|
|
1115
1137
|
if (personFields.length > 0) {
|
|
1116
1138
|
const withDefault = personFields.filter(f => f.defaultValue === true);
|
|
1117
1139
|
console.error(` 配置 ${personFields.length} 个 人员/部门 字段 isSingle${withDefault.length ? `(其中 ${withDefault.length} 个带默认当前用户/部门)` : ''}...`);
|
|
@@ -1140,10 +1162,12 @@ export function registerFormCommands(program) {
|
|
|
1140
1162
|
const colName = perDetail?.columnName || perDetail?.dataKey || '';
|
|
1141
1163
|
const colType = perDetail?.columnType || 'BIGINT';
|
|
1142
1164
|
const isDept = pf.componentKey === 'Department';
|
|
1143
|
-
const
|
|
1144
|
-
const
|
|
1165
|
+
const isSubCompany = pf.componentKey === 'SubCompany';
|
|
1166
|
+
const typeLabel = isSubCompany ? 'SubCompany' : isDept ? 'Department' : 'Employee';
|
|
1167
|
+
const labelCN = isSubCompany ? '分部' : isDept ? '部门' : '人员';
|
|
1145
1168
|
const jsonObj = {
|
|
1146
1169
|
type: typeLabel,
|
|
1170
|
+
...(isSubCompany ? { componentKey: 'Subcompany', defaultExtend: { type: 'custom', relation: 'current' } } : {}),
|
|
1147
1171
|
title: pf.fieldName,
|
|
1148
1172
|
isSingle: pf.multiple ? false : true,
|
|
1149
1173
|
allList: [],
|
|
@@ -1154,7 +1178,8 @@ export function registerFormCommands(program) {
|
|
|
1154
1178
|
pcDisplaySelectedCount: { type: 'default' },
|
|
1155
1179
|
mobileDisplaySelectedCount: { type: 'default' },
|
|
1156
1180
|
formTableId: perDetail?.formTableId || '',
|
|
1157
|
-
dataKey
|
|
1181
|
+
// dataKey 与 columnName 是两个东西,各自保留真值
|
|
1182
|
+
dataKey: perDetail?.dataKey || colName,
|
|
1158
1183
|
columnName: colName,
|
|
1159
1184
|
fieldId: perField.fieldId,
|
|
1160
1185
|
formId: resolvedFormId,
|
|
@@ -1190,7 +1215,7 @@ export function registerFormCommands(program) {
|
|
|
1190
1215
|
const detailPersonDefs = fieldDefs
|
|
1191
1216
|
.filter(f => f.componentKey === 'DetailTable' && Array.isArray(f.formFields))
|
|
1192
1217
|
.flatMap(dt => (dt.formFields || [])
|
|
1193
|
-
.filter(sf => sf.componentKey === 'Employee' || sf.componentKey === 'Department')
|
|
1218
|
+
.filter(sf => sf.componentKey === 'Employee' || sf.componentKey === 'Department' || sf.componentKey === 'SubCompany')
|
|
1194
1219
|
.map(sf => ({ ...sf, __detailTable: dt.fieldName })));
|
|
1195
1220
|
if (detailPersonDefs.length > 0) {
|
|
1196
1221
|
const withDefault = detailPersonDefs.filter(sf => sf.defaultValue === true);
|
|
@@ -1241,14 +1266,16 @@ export function registerFormCommands(program) {
|
|
|
1241
1266
|
continue;
|
|
1242
1267
|
}
|
|
1243
1268
|
const isDept = sfDef.componentKey === 'Department';
|
|
1244
|
-
const
|
|
1245
|
-
const
|
|
1269
|
+
const isSubCompany = sfDef.componentKey === 'SubCompany';
|
|
1270
|
+
const typeLabel = isSubCompany ? 'SubCompany' : isDept ? 'Department' : 'Employee';
|
|
1271
|
+
const labelCN = isSubCompany ? '分部' : isDept ? '部门' : '人员';
|
|
1246
1272
|
// spread cur 全量(保留子字段所有结构,防最小 jsonObj 覆盖破坏)+ 设 isSingle。
|
|
1247
1273
|
// 子字段单/多选由布局 comp 的 isSingle 控制(实测:getFields 的 multiSelect 是 dataset 元数据,
|
|
1248
1274
|
// 不控制渲染;布局 comp isSingle 才是渲染源)。saveFormFieldNew 会同步更新布局 comp 的 isSingle。
|
|
1249
1275
|
const jsonObj = {
|
|
1250
1276
|
...cur,
|
|
1251
1277
|
type: typeLabel,
|
|
1278
|
+
...(isSubCompany ? { componentKey: 'Subcompany', defaultExtend: { type: 'custom', relation: 'current' } } : {}),
|
|
1252
1279
|
title: sfDef.fieldName,
|
|
1253
1280
|
isSingle: sfDef.multiple ? false : true,
|
|
1254
1281
|
formTableId: subFormTableId || cur.formTableId || '',
|
|
@@ -1324,7 +1351,8 @@ export function registerFormCommands(program) {
|
|
|
1324
1351
|
...(dtMinTargetId ? { min: { type: 'dateField', checkValue: String(dtMinTargetId) }, earlyDate: true } : {}),
|
|
1325
1352
|
...(dtMaxTargetId ? { max: { type: 'dateField', checkValue: String(dtMaxTargetId) }, lateDate: true } : {}),
|
|
1326
1353
|
formTableId: dtDetail?.formTableId || '',
|
|
1327
|
-
dataKey
|
|
1354
|
+
// dataKey 与 columnName 是两个东西,各自保留真值
|
|
1355
|
+
dataKey: dtDetail?.dataKey || colName, columnName: colName,
|
|
1328
1356
|
fieldId: dtField.fieldId, formId: resolvedFormId,
|
|
1329
1357
|
showOrder: '0.00', groupId: '-1',
|
|
1330
1358
|
};
|
|
@@ -1814,23 +1842,13 @@ export function registerFormCommands(program) {
|
|
|
1814
1842
|
process.exit(1);
|
|
1815
1843
|
const client = new ApiClient(auth);
|
|
1816
1844
|
const baseUrl = auth.getBaseUrl();
|
|
1817
|
-
// Parse config
|
|
1818
|
-
let configStr = cmdOpts.config;
|
|
1819
|
-
if (configStr.startsWith('@')) {
|
|
1820
|
-
const { readFileSync, existsSync } = await import('fs');
|
|
1821
|
-
const filePath = configStr.slice(1);
|
|
1822
|
-
if (!existsSync(filePath)) {
|
|
1823
|
-
console.error(`配置文件不存在: ${filePath}`);
|
|
1824
|
-
process.exit(1);
|
|
1825
|
-
}
|
|
1826
|
-
configStr = readFileSync(filePath, 'utf-8');
|
|
1827
|
-
}
|
|
1845
|
+
// Parse config(@文件 / 内联 JSON 两种写法与 `wf-form linkage` 共用同一份实现)
|
|
1828
1846
|
let config;
|
|
1829
1847
|
try {
|
|
1830
|
-
config =
|
|
1848
|
+
config = readLinkageConfig(cmdOpts.config);
|
|
1831
1849
|
}
|
|
1832
|
-
catch {
|
|
1833
|
-
console.error(
|
|
1850
|
+
catch (e) {
|
|
1851
|
+
console.error(e.message);
|
|
1834
1852
|
process.exit(1);
|
|
1835
1853
|
}
|
|
1836
1854
|
// 校验联动 prop:必填且平台支持 hide/show/edit/readonly/required/hideLine(隐藏行,抓包实测平台枚举是 hideLine;
|
|
@@ -1859,59 +1877,21 @@ export function registerFormCommands(program) {
|
|
|
1859
1877
|
console.error('无法获取 formId,请确认 appId 和 objId 正确');
|
|
1860
1878
|
process.exit(1);
|
|
1861
1879
|
}
|
|
1862
|
-
//
|
|
1863
|
-
|
|
1864
|
-
|
|
1865
|
-
|
|
1866
|
-
|
|
1867
|
-
|
|
1868
|
-
|
|
1869
|
-
|
|
1870
|
-
|
|
1871
|
-
|
|
1872
|
-
|
|
1873
|
-
|
|
1874
|
-
|
|
1875
|
-
|
|
1876
|
-
|
|
1877
|
-
targetId: c.fieldId,
|
|
1878
|
-
detailSymbol: c.operator || 'EQUAL',
|
|
1879
|
-
sourceType: 'CONSTANT',
|
|
1880
|
-
sourceContent: JSON.stringify({
|
|
1881
|
-
formField: { id: c.fieldId },
|
|
1882
|
-
...(c.options ? { dataOptions: c.options } : { content: c.value }),
|
|
1883
|
-
}),
|
|
1884
|
-
})),
|
|
1885
|
-
formulaId: '',
|
|
1886
|
-
formulaName: '',
|
|
1887
|
-
},
|
|
1888
|
-
linkageDetails: config.actions.map((a) => ({
|
|
1889
|
-
formId,
|
|
1890
|
-
id: '0',
|
|
1891
|
-
linkageObj: 'field',
|
|
1892
|
-
linkageProp: a.prop, // hide, show, edit, readonly, required, hideRow
|
|
1893
|
-
linkageShowValue: a.fields.map((f) => ({
|
|
1894
|
-
dataKey: f.dataKey || '',
|
|
1895
|
-
groupName: '表单字段',
|
|
1896
|
-
address: f.isDetail ? '明细表' : '主表',
|
|
1897
|
-
addressType: f.isDetail ? 'detail' : 'form',
|
|
1898
|
-
groupId: 'formField',
|
|
1899
|
-
name: f.name,
|
|
1900
|
-
descType: f.fieldType || '',
|
|
1901
|
-
id: f.fieldId,
|
|
1902
|
-
content: f.name,
|
|
1903
|
-
desc: f.desc || '',
|
|
1904
|
-
})),
|
|
1905
|
-
detailOptions: [],
|
|
1906
|
-
})),
|
|
1907
|
-
module: 'ebuilderform',
|
|
1908
|
-
formId,
|
|
1909
|
-
refId: formId,
|
|
1910
|
-
enableState: '1',
|
|
1911
|
-
linkageName: name,
|
|
1912
|
-
customParam: { appId, objId },
|
|
1913
|
-
};
|
|
1914
|
-
const data = await client.post(`${baseUrl}/api/ebuilder/form/form/setting/viewlinkage/add?apid=${appId}`, payload, { ebbusinessid: formId });
|
|
1880
|
+
// 报文的拼法(尤其条件的算子与生效维度)收在 services/form-linkage-condition.ts ——
|
|
1881
|
+
// 那里记着「为空要写 NULL 且不能带 sourceContent」「表单布局维度的值取 layoutId」这类
|
|
1882
|
+
// 不看设计器实际报文就想不到的约束。
|
|
1883
|
+
const formName = formInfo?.formName || formInfo?.objName || '表单';
|
|
1884
|
+
const effect = await resolveEffect(client, baseUrl, formId, formName, config.effect);
|
|
1885
|
+
const { payload, warnings } = buildLinkageAddPayload({
|
|
1886
|
+
appId, objId, formId, formName, name,
|
|
1887
|
+
conditions: config.conditions || [],
|
|
1888
|
+
detailType: config.detailType,
|
|
1889
|
+
actions: config.actions || [],
|
|
1890
|
+
effect,
|
|
1891
|
+
});
|
|
1892
|
+
for (const w of warnings)
|
|
1893
|
+
console.error(` ⚠ ${w}`);
|
|
1894
|
+
const data = await addLinkage(client, baseUrl, appId, formId, payload);
|
|
1915
1895
|
if (data?.code === 200 && data?.status) {
|
|
1916
1896
|
const linkageId = data?.data || '';
|
|
1917
1897
|
console.log(opts.json
|
|
@@ -2122,15 +2102,20 @@ export function registerFormCommands(program) {
|
|
|
2122
2102
|
.option('--precision <n>', '小数位数(Number/Money 类型,缺省 Number=0 整数、Money=2、百分比=1)')
|
|
2123
2103
|
.option('--percent', 'Number 百分比显示(numberType=percentage)')
|
|
2124
2104
|
.option('--default <value>', '默认值(Text / TextArea / Number / Money,如 工时单价默认 1000)')
|
|
2125
|
-
.option('--data-key <key>', '
|
|
2105
|
+
.option('--data-key <key>', '字段编码 dataKey(默认按字段名生成拼音;字母数字下划线,不以数字开头)')
|
|
2106
|
+
.option('--column-name <name>', '数据库列名 columnName。**与 dataKey 是两个东西,可分别指定**;'
|
|
2107
|
+
+ '不给时跟随 --data-key(两者都没给则同为拼音首字母)')
|
|
2126
2108
|
.option('--desc <text>', '字段描述(设计器字段属性里的「描述」)')
|
|
2127
2109
|
.option('--delimiter', 'Number/Money 千分位(Money 默认开,--no-delimiter 关闭)')
|
|
2128
2110
|
.option('--capital', 'Number/Money 大写金额显示')
|
|
2129
2111
|
.option('--sub-form-id <id>', '明细表 subFormId(在指定明细表里加字段)')
|
|
2130
|
-
.option('--multiple', '
|
|
2112
|
+
.option('--multiple', '多选(人员/部门/分部/EBuilder/关联类字段/下拉Select;下拉多选=SelectMultiple 类型)')
|
|
2131
2113
|
.option('--max-len <n>', '文本最大长度(Text 缺省 100、TextArea 缺省 4000)')
|
|
2132
2114
|
.option('--single-row', '独占一行显示(布局 singleRow:true,其余字段仍两列)')
|
|
2133
2115
|
.option('--option-template <idOrName>', 'Select 绑定选项预设模板(ID 或名称;选项不内联,options=[])')
|
|
2116
|
+
.option('--required', '设为必填(同时写字段记录与布局组件,两处都写才完整)')
|
|
2117
|
+
.option('--reinit', '整表重建布局(initLayout)而不是增量插入:会换样式模板、重排所有已有位置、'
|
|
2118
|
+
+ '并重建标签组件。只在自己建的表上用;不是自己建的表用默认的增量插入')
|
|
2134
2119
|
.action(async (objId, appId, fieldName, fieldType, title, cmdOptsRaw) => {
|
|
2135
2120
|
// fieldType 大小写归一(与建表一致):用户常传 "Textarea"/"Ebuilder",不归一则 type 存小写
|
|
2136
2121
|
// "Textarea"(FLOW 渲染异常)、TextArea 分支漏跑。
|
|
@@ -2156,25 +2141,33 @@ export function registerFormCommands(program) {
|
|
|
2156
2141
|
// DateRange 需要 3 个字段 ID(主 + 开始 + 结束),普通字段 1 个,富组件按 richIdUnits
|
|
2157
2142
|
const isDateRange = fieldType === 'DateRange' || fieldType === 'DateInterval';
|
|
2158
2143
|
const idCount = isDateRange ? 3 : richIdUnits(fieldType, {});
|
|
2159
|
-
|
|
2144
|
+
// 多要一个:布局里字段占**两个** comp,值组件用 fieldId,标签组件的 `config.fieldId`
|
|
2145
|
+
// 是布局自己另生成的一个雪花 id(与字段定义无关,只需在布局内唯一)。
|
|
2146
|
+
const genData = await client.post(`${baseUrl}/api/form/local/generatorIds?size=${idCount + 1}&apid=${appId}`, {});
|
|
2160
2147
|
const genIds = genData?.data?.generatorIds || [];
|
|
2161
2148
|
const fieldId = genIds[0] || String(Date.now());
|
|
2162
2149
|
const startId = genIds[1] || '';
|
|
2163
2150
|
const endId = genIds[2] || '';
|
|
2151
|
+
const labelFieldId = genIds[idCount] || String(Date.now());
|
|
2164
2152
|
const cmdOpts = cmdOptsRaw || {};
|
|
2165
2153
|
const sformId = cmdOpts.sformId || '';
|
|
2166
2154
|
const dataTitle = cmdOpts.dataTitle || '';
|
|
2167
2155
|
const formName = cmdOpts.formName || '';
|
|
2168
|
-
//
|
|
2169
|
-
|
|
2156
|
+
// dataKey(字段编码)与 columnName(数据库列名)是两个东西,默认同值。
|
|
2157
|
+
// 只给 --data-key 时列名跟随(历史行为);给了 --column-name 才分开。
|
|
2158
|
+
const keys = resolveFieldKeys(fieldName, {
|
|
2159
|
+
dataKey: cmdOpts.dataKey,
|
|
2160
|
+
columnName: cmdOpts.columnName,
|
|
2161
|
+
});
|
|
2162
|
+
const colName = keys.dataKey; // 布局 comp 等仍按字段编码引用
|
|
2170
2163
|
// Build jsonObj based on field type
|
|
2171
2164
|
const jsonObj = {
|
|
2172
2165
|
type: fieldType,
|
|
2173
2166
|
title: title || fieldName,
|
|
2174
2167
|
formTableId, fieldId, groupId: '-1', formId,
|
|
2175
2168
|
showOrder: '0.00',
|
|
2176
|
-
dataKey:
|
|
2177
|
-
columnName:
|
|
2169
|
+
dataKey: keys.dataKey,
|
|
2170
|
+
columnName: keys.columnName,
|
|
2178
2171
|
};
|
|
2179
2172
|
// 明细表字段:--sub-form-id 时 jsonObj 带 subFormId —— **字段落点由它决定**。
|
|
2180
2173
|
// 必须用 resolveDetailTable 而不是直接查 getEbField:后者列不出空明细表,
|
|
@@ -2208,7 +2201,7 @@ export function registerFormCommands(program) {
|
|
|
2208
2201
|
multiple: cmdOpts.multiple,
|
|
2209
2202
|
browserType: cmdOpts.browserType,
|
|
2210
2203
|
browserFormSource: cmdOpts.browserFormSource,
|
|
2211
|
-
}, fieldId, formId, formTableId, dataKey:
|
|
2204
|
+
}, fieldId, formId, formTableId, dataKey: keys.dataKey, columnName: keys.columnName,
|
|
2212
2205
|
showOrder: '0.00', extraIds,
|
|
2213
2206
|
});
|
|
2214
2207
|
Object.assign(jsonObj, extraCfg);
|
|
@@ -2305,6 +2298,19 @@ export function registerFormCommands(program) {
|
|
|
2305
2298
|
delete jsonObj.scan;
|
|
2306
2299
|
delete jsonObj.readonlyTransLink;
|
|
2307
2300
|
}
|
|
2301
|
+
else if (fieldType === 'SubCompany') {
|
|
2302
|
+
Object.assign(jsonObj, {
|
|
2303
|
+
componentKey: 'Subcompany', isSingle: cmdOpts.multiple ? false : true,
|
|
2304
|
+
displayType: 'space', defaultExtend: { type: 'custom', relation: 'current' },
|
|
2305
|
+
viewDataDetail: true, showDimension: true,
|
|
2306
|
+
pcDisplaySelectedCount: { type: 'default' },
|
|
2307
|
+
mobileDisplaySelectedCount: { type: 'default' },
|
|
2308
|
+
});
|
|
2309
|
+
delete jsonObj.maxLen;
|
|
2310
|
+
delete jsonObj.unique;
|
|
2311
|
+
delete jsonObj.scan;
|
|
2312
|
+
delete jsonObj.readonlyTransLink;
|
|
2313
|
+
}
|
|
2308
2314
|
else if (fieldType === 'City') {
|
|
2309
2315
|
// 城市/地区选择(对齐浏览器 payload:region 模式 + 系统级联层级 + 字母索引)
|
|
2310
2316
|
Object.assign(jsonObj, {
|
|
@@ -2522,6 +2528,7 @@ export function registerFormCommands(program) {
|
|
|
2522
2528
|
const patch = applyFieldPatches(jsonObj, {
|
|
2523
2529
|
defaultValue: cmdOpts.default,
|
|
2524
2530
|
dataKey: cmdOpts.dataKey,
|
|
2531
|
+
columnName: cmdOpts.columnName,
|
|
2525
2532
|
desc: cmdOpts.desc,
|
|
2526
2533
|
});
|
|
2527
2534
|
if (patch.errors.length > 0) {
|
|
@@ -2532,6 +2539,23 @@ export function registerFormCommands(program) {
|
|
|
2532
2539
|
}
|
|
2533
2540
|
for (const w of patch.warnings)
|
|
2534
2541
|
console.error(` ⚠ ${w}`);
|
|
2542
|
+
// 必填**只存在于布局 comp 里**(`config.required`)—— 字段记录没有这个键。所以下面那句
|
|
2543
|
+
// 只是形式上的补齐,真正生效的是布局落点:增量插入的 `overrides.required`,
|
|
2544
|
+
// 或 --reinit 时 configs 里那条 newFieldConfig。两处都写全了用户才看不出差别。
|
|
2545
|
+
if (cmdOpts.required === true)
|
|
2546
|
+
jsonObj.required = true;
|
|
2547
|
+
// 字段标题在平台里存的是**多语言标签 id**(字段记录的 `labelObj.title`),不是文本本身。
|
|
2548
|
+
// 不建标签也能显示(设计器退回读 `title`),但只要有谁引用了标签而这个标签不存在,
|
|
2549
|
+
// 标题就会**静默变空** —— 平台既不校验也不报错。所以顺手建一个真的,不留自造 id 的口子。
|
|
2550
|
+
// 建失败只告警:字段本身才是主操作,不该被标签服务拖垮。
|
|
2551
|
+
try {
|
|
2552
|
+
const titleLabelId = await createMultilangLabel(client, baseUrl, title || fieldName, 'ebuilderform');
|
|
2553
|
+
jsonObj.labelObj = { ...(jsonObj.labelObj || {}), title: titleLabelId };
|
|
2554
|
+
jsonObj.titleLabelId = titleLabelId;
|
|
2555
|
+
}
|
|
2556
|
+
catch (e) {
|
|
2557
|
+
console.error(` ⚠ 标题的多语言标签未建立(字段不受影响,设计器会退回用 title 显示): ${e.message}`);
|
|
2558
|
+
}
|
|
2535
2559
|
const payload = {
|
|
2536
2560
|
formId, module: 'ebuilderform',
|
|
2537
2561
|
customParam: { appId, objId },
|
|
@@ -2553,83 +2577,116 @@ export function registerFormCommands(program) {
|
|
|
2553
2577
|
console.error(` 关联显示列设置失败: ${e.message}`);
|
|
2554
2578
|
}
|
|
2555
2579
|
}
|
|
2556
|
-
//
|
|
2557
|
-
|
|
2558
|
-
|
|
2559
|
-
|
|
2560
|
-
|
|
2561
|
-
|
|
2562
|
-
|
|
2563
|
-
|
|
2564
|
-
|
|
2565
|
-
|
|
2566
|
-
|
|
2567
|
-
|
|
2568
|
-
|
|
2569
|
-
|
|
2570
|
-
|
|
2571
|
-
|
|
2572
|
-
|
|
2573
|
-
|
|
2574
|
-
|
|
2575
|
-
|
|
2576
|
-
|
|
2577
|
-
|
|
2578
|
-
|
|
2579
|
-
|
|
2580
|
-
|
|
2581
|
-
|
|
2582
|
-
|
|
2583
|
-
|
|
2584
|
-
|
|
2585
|
-
|
|
2586
|
-
|
|
2587
|
-
|
|
2588
|
-
|
|
2589
|
-
|
|
2590
|
-
|
|
2591
|
-
|
|
2592
|
-
|
|
2593
|
-
|
|
2594
|
-
|
|
2595
|
-
|
|
2580
|
+
// 布局落点:**默认走增量插入** —— 读快照 → 塞一对 comp → saveFormAndLayout,全程不碰
|
|
2581
|
+
// initLayout。initLayout 是整表重建(换样式模板、重排所有位置、把标签组件全换成新 id),
|
|
2582
|
+
// 对不是我们建的表是破坏性的;详见 services/form-layout-insert.ts。
|
|
2583
|
+
//
|
|
2584
|
+
// 增量失败**不自动回落**到 initLayout —— 那等于把「悄悄毁掉别人的布局」变成默认行为。
|
|
2585
|
+
// 把错误讲清楚,让用户自己决定要不要 --reinit。
|
|
2586
|
+
if (!cmdOpts.reinit) {
|
|
2587
|
+
try {
|
|
2588
|
+
const fieldDef = (await fetchFieldPageRecords(client, baseUrl, appId, formId))
|
|
2589
|
+
.find((f) => String(f.fieldId) === String(fieldId));
|
|
2590
|
+
if (!fieldDef)
|
|
2591
|
+
throw new Error('字段已建立,但读回字段定义失败');
|
|
2592
|
+
const placed = await insertFieldIntoLayout(client, baseUrl, formId, {
|
|
2593
|
+
fieldId, labelFieldId, title: title || fieldName, fieldDef,
|
|
2594
|
+
subFormId: cmdOpts.subFormId,
|
|
2595
|
+
// 对齐 initLayout 那条路对新字段的默认:可编辑、显示。
|
|
2596
|
+
// 不写的话会**继承模板字段的状态** —— 模板若恰好是只读的,新字段一出生就只读。
|
|
2597
|
+
overrides: {
|
|
2598
|
+
readOnly: false, disableEdit: false, display: true,
|
|
2599
|
+
required: cmdOpts.required === true,
|
|
2600
|
+
...(cmdOpts.singleRow === true ? { singleRow: true } : {}),
|
|
2601
|
+
},
|
|
2602
|
+
});
|
|
2603
|
+
console.error(` 布局已更新: excel[${placed.row},${placed.col}](增量插入,未重建)`);
|
|
2604
|
+
}
|
|
2605
|
+
catch (e) {
|
|
2606
|
+
console.error(` 布局更新失败: ${e.message}`);
|
|
2607
|
+
console.error(' 字段本身已建立,但没进布局。按上面那条修好重跑本命令即可(重跑不会重复建字段)。');
|
|
2608
|
+
}
|
|
2609
|
+
}
|
|
2610
|
+
else {
|
|
2611
|
+
console.error(' 重新生成布局(整表重建)...');
|
|
2612
|
+
try {
|
|
2613
|
+
const preLayout = await client.post(`${baseUrl}/api/ebuilder/form/builder/getFormLayout`, {
|
|
2614
|
+
formId, module: 'ebuilderform', customParam: {}, formTableIdList: [],
|
|
2615
|
+
designerParam: { onlyLayout: false, convert: false }, form: { id: formId },
|
|
2616
|
+
}, { ebbusinessid: formId });
|
|
2617
|
+
const layoutId = preLayout?.data?.formLayout?.id || '';
|
|
2618
|
+
const layoutMultiId = preLayout?.data?.formLayout?.multipleLayoutId || '';
|
|
2619
|
+
const layoutName = preLayout?.data?.formLayoutMultiple?.name || preLayout?.data?.formLayout?.name || '';
|
|
2620
|
+
const layoutType = preLayout?.data?.formLayoutMultiple?.layoutType || 'EXCEL';
|
|
2621
|
+
const configRes = await client.post(`${baseUrl}/api/ebuilder/form/form/view/relate/getConfig`, {
|
|
2622
|
+
formId, module: 'ebuilderform', apiModule: 'ebuilder/form',
|
|
2623
|
+
layoutId, customParam: { terminal: '', objId: formId },
|
|
2624
|
+
initMode: 5, groupFieldIds: [], designerParam: { sourceModule: 'ebuilderform' },
|
|
2625
|
+
}, { ebbusinessid: formId });
|
|
2626
|
+
const rawConfigs = configRes?.data?.configs || [];
|
|
2627
|
+
// saveFormFieldNew fields may not appear in getConfig — manually append
|
|
2628
|
+
const CK = {
|
|
2629
|
+
Text: 'Text', Textarea: 'TextArea', Number: 'NumberComponent', Money: 'Money',
|
|
2630
|
+
Date: 'DateComponent', DateTime: 'DateComponent', Select: 'Select', CheckBox: 'CheckBox', RadioBox: 'RadioBox',
|
|
2631
|
+
Employee: 'Employee', Department: 'Department', SubCompany: 'Subcompany', EBuilder: 'Ebuilder',
|
|
2632
|
+
Phone: 'Phone', Email: 'Email', Mobile: 'Mobile', Location: 'Location', Switch: 'Switch', IDCard: 'IDCard',
|
|
2633
|
+
};
|
|
2634
|
+
const newFieldConfig = {
|
|
2635
|
+
id: fieldId, name: title || fieldName,
|
|
2636
|
+
componentKey: jsonObj.componentKey || CK[fieldType] || fieldType,
|
|
2637
|
+
display: true, show: true, readOnly: false,
|
|
2638
|
+
required: cmdOpts.required === true, disableEdit: false, singleRow: cmdOpts.singleRow === true,
|
|
2639
|
+
isDelete: false, type: fieldType, dataKey: colName,
|
|
2640
|
+
};
|
|
2641
|
+
const existingIds = new Set(rawConfigs.map((c) => String(c.id)));
|
|
2642
|
+
if (cmdOpts.subFormId) {
|
|
2643
|
+
// 明细字段:加进对应 DetailTable 的 children(明细字段嵌在 DetailTable 里,不是顶层)
|
|
2644
|
+
const dtComp = rawConfigs.find((c) => String(c.id) === String(cmdOpts.subFormId) && c.type === 'DetailTable');
|
|
2645
|
+
if (dtComp) {
|
|
2646
|
+
const childIds = new Set((dtComp.children || []).map((x) => String(x.id)));
|
|
2647
|
+
if (!childIds.has(fieldId)) {
|
|
2648
|
+
dtComp.children = dtComp.children || [];
|
|
2649
|
+
dtComp.children.push({ ...newFieldConfig, showOrder: dtComp.children.length });
|
|
2650
|
+
}
|
|
2651
|
+
}
|
|
2652
|
+
else {
|
|
2653
|
+
console.error(` ⚠ 布局里未找到明细表 subFormId=${cmdOpts.subFormId},字段已加但未进布局`);
|
|
2596
2654
|
}
|
|
2597
2655
|
}
|
|
2598
|
-
else {
|
|
2599
|
-
|
|
2656
|
+
else if (!existingIds.has(fieldId)) {
|
|
2657
|
+
rawConfigs.push({ ...newFieldConfig, showOrder: rawConfigs.length });
|
|
2600
2658
|
}
|
|
2659
|
+
const configs = rawConfigs.map((c) => ({
|
|
2660
|
+
...c,
|
|
2661
|
+
display: c.system ? c.display : true,
|
|
2662
|
+
show: c.system ? c.show : true,
|
|
2663
|
+
// 新加字段 saveFormFieldNew 后 getConfig 返回 readOnly:true(未铺列默认),
|
|
2664
|
+
// existingIds 命中时 newFieldConfig(readOnly:false) 会被丢弃,这里强制覆盖回 false,
|
|
2665
|
+
// 否则任何 add-field 新字段(Text/Employee/EBuilder 都中招)默认不可编辑。
|
|
2666
|
+
...(String(c.id) === String(fieldId)
|
|
2667
|
+
? { readOnly: false, required: cmdOpts.required === true }
|
|
2668
|
+
: {}),
|
|
2669
|
+
}));
|
|
2670
|
+
// DetailTable 置末(对齐 form create / form layout init):getConfig 可能把明细表夹中间,
|
|
2671
|
+
// 重排避免明细跑到普通字段上面。
|
|
2672
|
+
const orderedConfigs = [
|
|
2673
|
+
...configs.filter((c) => c.type !== 'DetailTable' && c.componentKey !== 'DataTable'),
|
|
2674
|
+
...configs.filter((c) => c.type === 'DetailTable' || c.componentKey === 'DataTable'),
|
|
2675
|
+
];
|
|
2676
|
+
await client.post(`${baseUrl}/api/ebuilder/form/form/view/relate/initLayout?apid=${appId}`, {
|
|
2677
|
+
formId, module: 'ebuilderform', apiModule: 'ebuilder/form',
|
|
2678
|
+
layoutId, generateCollapse: true,
|
|
2679
|
+
styleTemplateId: layoutType === 'FLOW' ? '820000000000000001' : '700000000000000008', styleTemplateType: 1,
|
|
2680
|
+
configs: orderedConfigs, addLayout: false, ecodeType: ['js', 'css'],
|
|
2681
|
+
initMode: '1', customParam: { terminal: '', objId: formId },
|
|
2682
|
+
formLayoutMultiple: { isSys: true, id: layoutMultiId, name: layoutName, terminalType: 'PC', layoutType },
|
|
2683
|
+
designerParam: { onlyLayout: false },
|
|
2684
|
+
}, { ebbusinessid: formId });
|
|
2685
|
+
console.error(' 布局已更新');
|
|
2686
|
+
}
|
|
2687
|
+
catch (e) {
|
|
2688
|
+
console.error(` 布局更新失败: ${e.message}`);
|
|
2601
2689
|
}
|
|
2602
|
-
else if (!existingIds.has(fieldId)) {
|
|
2603
|
-
rawConfigs.push({ ...newFieldConfig, showOrder: rawConfigs.length });
|
|
2604
|
-
}
|
|
2605
|
-
const configs = rawConfigs.map((c) => ({
|
|
2606
|
-
...c,
|
|
2607
|
-
display: c.system ? c.display : true,
|
|
2608
|
-
show: c.system ? c.show : true,
|
|
2609
|
-
// 新加字段 saveFormFieldNew 后 getConfig 返回 readOnly:true(未铺列默认),
|
|
2610
|
-
// existingIds 命中时 newFieldConfig(readOnly:false) 会被丢弃,这里强制覆盖回 false,
|
|
2611
|
-
// 否则任何 add-field 新字段(Text/Employee/EBuilder 都中招)默认不可编辑。
|
|
2612
|
-
...(String(c.id) === String(fieldId) ? { readOnly: false } : {}),
|
|
2613
|
-
}));
|
|
2614
|
-
// DetailTable 置末(对齐 form create / form layout init):getConfig 可能把明细表夹中间,
|
|
2615
|
-
// 重排避免明细跑到普通字段上面。
|
|
2616
|
-
const orderedConfigs = [
|
|
2617
|
-
...configs.filter((c) => c.type !== 'DetailTable' && c.componentKey !== 'DataTable'),
|
|
2618
|
-
...configs.filter((c) => c.type === 'DetailTable' || c.componentKey === 'DataTable'),
|
|
2619
|
-
];
|
|
2620
|
-
await client.post(`${baseUrl}/api/ebuilder/form/form/view/relate/initLayout?apid=${appId}`, {
|
|
2621
|
-
formId, module: 'ebuilderform', apiModule: 'ebuilder/form',
|
|
2622
|
-
layoutId, generateCollapse: true,
|
|
2623
|
-
styleTemplateId: layoutType === 'FLOW' ? '820000000000000001' : '700000000000000008', styleTemplateType: 1,
|
|
2624
|
-
configs: orderedConfigs, addLayout: false, ecodeType: ['js', 'css'],
|
|
2625
|
-
initMode: '1', customParam: { terminal: '', objId: formId },
|
|
2626
|
-
formLayoutMultiple: { isSys: true, id: layoutMultiId, name: layoutName, terminalType: 'PC', layoutType },
|
|
2627
|
-
designerParam: { onlyLayout: false },
|
|
2628
|
-
}, { ebbusinessid: formId });
|
|
2629
|
-
console.error(' 布局已更新');
|
|
2630
|
-
}
|
|
2631
|
-
catch (e) {
|
|
2632
|
-
console.error(` 布局更新失败: ${e.message}`);
|
|
2633
2690
|
}
|
|
2634
2691
|
}
|
|
2635
2692
|
else {
|
|
@@ -2645,6 +2702,7 @@ export function registerFormCommands(program) {
|
|
|
2645
2702
|
.option('--title <title>', '修改字段标题')
|
|
2646
2703
|
.option('--type <type>', '修改字段类型(如 Text/Number/Date/Select/Department;取值同 form add-field 的 <fieldType>)。'
|
|
2647
2704
|
+ '⚠ 字段已有数据时平台会拒绝')
|
|
2705
|
+
.option('--format <fmt>', '日期精度格式,配合 --type Date/DateTime(缺省 Date=yyyy-MM-dd、DateTime=yyyy-MM-dd HH:mm)')
|
|
2648
2706
|
.option('--required', '设为必填')
|
|
2649
2707
|
.option('--no-required', '取消必填')
|
|
2650
2708
|
.option('--sform-id <id>', 'EBuilder 关联的目标表单 objId(更新关联)')
|
|
@@ -2657,7 +2715,9 @@ export function registerFormCommands(program) {
|
|
|
2657
2715
|
.option('--max-len <n>', '最大长度(正整数)。日期/时间/省市区/身份证/电子发票/下拉多选这几类没有该属性')
|
|
2658
2716
|
.option('--default <value>', '默认值(Text / TextArea / Number / Money)')
|
|
2659
2717
|
.option('--clear-default', '清空默认值')
|
|
2660
|
-
.option('--data-key <key>', '
|
|
2718
|
+
.option('--data-key <key>', '字段编码 dataKey(字母数字下划线,不以数字开头;字段已有数据时平台会拒绝)')
|
|
2719
|
+
.option('--column-name <name>', '数据库列名 columnName。**与 dataKey 是两个东西,可分别指定**;'
|
|
2720
|
+
+ '不给时跟随 --data-key。字段已有数据时平台会拒绝改列名')
|
|
2661
2721
|
.option('--desc <text>', '字段描述(设计器字段属性里的「描述」)')
|
|
2662
2722
|
.action(async (objId, appId, fieldId, editOpts) => {
|
|
2663
2723
|
const opts = program.opts();
|
|
@@ -2725,16 +2785,10 @@ export function registerFormCommands(program) {
|
|
|
2725
2785
|
console.error(`读到的字段定义里没有 type(fieldId=${fieldId}),拒绝写回 —— 全量覆盖会把它改成默认类型。`);
|
|
2726
2786
|
process.exit(1);
|
|
2727
2787
|
}
|
|
2728
|
-
// 兜底补 componentKey:saveFormFieldNew
|
|
2729
|
-
//
|
|
2788
|
+
// 兜底补 componentKey:saveFormFieldNew 要求非空(getComponentKey() 为 null 直接 500)。
|
|
2789
|
+
// 用平台归一的 componentKey(`platformFieldShape`),不是 CLI 类型名 —— 见下方改类型分支的说明。
|
|
2730
2790
|
if (!jsonObj.componentKey) {
|
|
2731
|
-
|
|
2732
|
-
Date: 'DateComponent', DateTime: 'DateComponent', Text: 'Text', Textarea: 'TextArea', Number: 'NumberComponent',
|
|
2733
|
-
Money: 'Money', Select: 'Select', CheckBox: 'CheckBox', RadioBox: 'RadioBox',
|
|
2734
|
-
Employee: 'Employee', Department: 'Department', EBuilder: 'Ebuilder',
|
|
2735
|
-
Phone: 'Phone', Email: 'Email', Mobile: 'Mobile', Location: 'Location', Switch: 'Switch', IDCard: 'IDCard',
|
|
2736
|
-
};
|
|
2737
|
-
jsonObj.componentKey = CK[jsonObj.type] || jsonObj.type;
|
|
2791
|
+
jsonObj.componentKey = platformFieldShape(String(jsonObj.type)).componentKey;
|
|
2738
2792
|
}
|
|
2739
2793
|
// Apply title change
|
|
2740
2794
|
if (editOpts.title) {
|
|
@@ -2745,6 +2799,7 @@ export function registerFormCommands(program) {
|
|
|
2745
2799
|
// `type` 取值与 add-field 一致(CLI 规范名;富组件换成 platformType + componentKey),
|
|
2746
2800
|
// 回读时对应显示为 `form read` 的 fieldKey(如 Number→NumberComponent)。
|
|
2747
2801
|
// ⚠ 字段**已存在数据**时平台会拒绝改结构(报「此列已存在数据不可修改数据库字段名称」)。
|
|
2802
|
+
let typeChangeApplied = false;
|
|
2748
2803
|
if (editOpts.type) {
|
|
2749
2804
|
const targetType = canonComponentKey(editOpts.type);
|
|
2750
2805
|
assertFieldType(targetType, 'edit-field ');
|
|
@@ -2753,14 +2808,72 @@ export function registerFormCommands(program) {
|
|
|
2753
2808
|
console.error(`改成 ${targetType} 需要同时指定 --sform-id <目标表 objId>(Flow 用流程绑定的表单 objId)`);
|
|
2754
2809
|
process.exit(1);
|
|
2755
2810
|
}
|
|
2756
|
-
|
|
2757
|
-
|
|
2758
|
-
|
|
2759
|
-
|
|
2811
|
+
const richTarget = getRichType(targetType);
|
|
2812
|
+
const shape = platformFieldShape(targetType);
|
|
2813
|
+
const desiredFormat = editOpts.format || shape.format;
|
|
2814
|
+
// 变更判定要按**平台形状**比,不能只比类型名:
|
|
2815
|
+
// 「日期」与「日期时间」在存储层同为 `type=Date` + `componentKey=DateComponent`,
|
|
2816
|
+
// 只有 `format` 不同(yyyy-MM-dd vs yyyy-MM-dd HH:mm)。只比 type 会把
|
|
2817
|
+
// 「DateTime → Date」判成没变化而静默跳过,精度留在原地 —— 命令报成功、字段没动。
|
|
2818
|
+
const typeChanged = richTarget
|
|
2819
|
+
? targetType !== String(jsonObj.componentKey ?? '')
|
|
2820
|
+
: shape.type !== String(jsonObj.type)
|
|
2821
|
+
|| shape.componentKey !== String(jsonObj.componentKey ?? '')
|
|
2822
|
+
|| (shape.format !== undefined && String(desiredFormat) !== String(jsonObj.format ?? ''));
|
|
2823
|
+
if (editOpts.format && shape.format === undefined) {
|
|
2824
|
+
console.error(`--format 只对 Date / DateTime 有意义,${targetType} 没有这个属性,已忽略。`);
|
|
2825
|
+
}
|
|
2826
|
+
typeChangeApplied = typeChanged;
|
|
2827
|
+
if (typeChanged) {
|
|
2828
|
+
if (richTarget) {
|
|
2829
|
+
jsonObj.type = richTarget.platformType;
|
|
2760
2830
|
jsonObj.componentKey = richTarget.platformComponentKey;
|
|
2761
|
-
|
|
2762
|
-
else
|
|
2763
|
-
|
|
2831
|
+
}
|
|
2832
|
+
else {
|
|
2833
|
+
// 非富组件:写**平台归一形状**,不是 CLI 类型名。
|
|
2834
|
+
// 曾经的 bug:这里写的是 `delete jsonObj.componentKey`(想让平台按新 type 推导),
|
|
2835
|
+
// 而上面那段兜底补 componentKey 在**这之前**就执行完了 → 改完没人再补 →
|
|
2836
|
+
// 全量覆盖时缺键 → `getComponentKey() is null` 500「程序异常」,字段改不动。
|
|
2837
|
+
// 而平台的 componentKey 也不是类型名:送 `componentKey=Date` 配 `type=DateTime`
|
|
2838
|
+
// 照样 500,必须是 `DateComponent`。
|
|
2839
|
+
jsonObj.type = shape.type;
|
|
2840
|
+
jsonObj.componentKey = shape.componentKey;
|
|
2841
|
+
// 日期/日期时间/时间:精度全靠 format,平台**不会**补默认值
|
|
2842
|
+
// (只送 type+componentKey 会存成 format 为空)。所以一起写。
|
|
2843
|
+
if (shape.format !== undefined)
|
|
2844
|
+
jsonObj.format = desiredFormat;
|
|
2845
|
+
// 切到用不到 format 的类型时清掉旧值,免得留个说不清来路的精度配置
|
|
2846
|
+
else if (jsonObj.format !== undefined)
|
|
2847
|
+
delete jsonObj.format;
|
|
2848
|
+
// 日期区间还要 `start`/`end` 两个 DateComponent 子对象(各带一个新 fieldId)。
|
|
2849
|
+
// 少了平台直接 500:`DateIntervalFieldDto.getEnd() is null`。
|
|
2850
|
+
// 子 id 对齐 add-field 的建法现取。
|
|
2851
|
+
if (targetType === 'DateRange' || targetType === 'DateInterval') {
|
|
2852
|
+
const idsRes = await client.post(`${baseUrl}/api/form/local/generatorIds?size=2&apid=${appId}`, {});
|
|
2853
|
+
const ids = (idsRes?.data?.generatorIds || []).map(String);
|
|
2854
|
+
if (ids.length < 2) {
|
|
2855
|
+
console.error('日期区间需要两个子字段 ID,服务端未返回,已中止(字段未改动)。');
|
|
2856
|
+
process.exit(1);
|
|
2857
|
+
}
|
|
2858
|
+
const fmt = desiredFormat || 'yyyy-MM-dd';
|
|
2859
|
+
const rangeTitle = String(jsonObj.title || '');
|
|
2860
|
+
const start = {
|
|
2861
|
+
componentKey: 'DateComponent', content: '', describe: '', earlyDate: 'false',
|
|
2862
|
+
format: fmt, isDefault: 'false', lateDate: 'false',
|
|
2863
|
+
placeholder: placeholderFromFormat(fmt),
|
|
2864
|
+
position: '', relateMultiple: 'false', required: 'false', size: 'medium',
|
|
2865
|
+
title: `${rangeTitle}(开始时间)`, fieldId: ids[0],
|
|
2866
|
+
min: { type: 'currentHour' }, max: { type: 'currentHour' },
|
|
2867
|
+
};
|
|
2868
|
+
Object.assign(jsonObj, {
|
|
2869
|
+
isDefault: false,
|
|
2870
|
+
start,
|
|
2871
|
+
end: { ...start, title: `${rangeTitle}(结束时间)`, fieldId: ids[1] },
|
|
2872
|
+
hasDisplayFormat: true,
|
|
2873
|
+
rangeInterval: { limitType: 'max', timeUnit: 'day' },
|
|
2874
|
+
});
|
|
2875
|
+
}
|
|
2876
|
+
}
|
|
2764
2877
|
// 富组件还要补**附加配置**,否则改出来的字段是残缺的:
|
|
2765
2878
|
// add-field 走的是同一张表的 build(),两边不一致会导致「新建的对、改类型的错」
|
|
2766
2879
|
// (实测 Time:改出来缺 minuteStep/timePanelStyle/defaultExtend,earlyDate/lateDate
|
|
@@ -2788,7 +2901,8 @@ export function registerFormCommands(program) {
|
|
|
2788
2901
|
}
|
|
2789
2902
|
}
|
|
2790
2903
|
}
|
|
2791
|
-
//
|
|
2904
|
+
// `required` 不是字段记录的键(整张表的字段记录里都没有),写到 jsonObj 只是**保持与
|
|
2905
|
+
// 既有代码一致的形式**,真正生效的是保存成功之后那段布局 comp 补丁 —— 见下面 `patchFieldLayout`。
|
|
2792
2906
|
if (editOpts.required) {
|
|
2793
2907
|
jsonObj.required = true;
|
|
2794
2908
|
}
|
|
@@ -2936,6 +3050,7 @@ export function registerFormCommands(program) {
|
|
|
2936
3050
|
defaultValue: editOpts.default,
|
|
2937
3051
|
clearDefault: editOpts.clearDefault,
|
|
2938
3052
|
dataKey: editOpts.dataKey,
|
|
3053
|
+
columnName: editOpts.columnName,
|
|
2939
3054
|
desc: editOpts.desc,
|
|
2940
3055
|
});
|
|
2941
3056
|
if (patch.errors.length > 0) {
|
|
@@ -2956,12 +3071,15 @@ export function registerFormCommands(program) {
|
|
|
2956
3071
|
const changes = [];
|
|
2957
3072
|
if (editOpts.title)
|
|
2958
3073
|
changes.push(`title="${editOpts.title}"`);
|
|
2959
|
-
|
|
2960
|
-
|
|
2961
|
-
if (editOpts.
|
|
2962
|
-
changes.push(
|
|
2963
|
-
|
|
2964
|
-
|
|
3074
|
+
// 只有**真的换了形状**才回显类型。原样重跑同一类型(尤其 Date/DateTime 在存储层同为
|
|
3075
|
+
// type=Date)时没做任何改动,回显「type=…」会让人以为写过了。
|
|
3076
|
+
if (editOpts.type) {
|
|
3077
|
+
changes.push(typeChangeApplied ? `type=${editOpts.type}` : `type=${editOpts.type}(未变化)`);
|
|
3078
|
+
}
|
|
3079
|
+
// commander 把 `--no-required` 映射成 `required: false`(不是 `noRequired`),
|
|
3080
|
+
// 所以只判 noRequired 的话反向操作会漏报成「no changes」—— 改了却说没改。
|
|
3081
|
+
if (editOpts.required !== undefined)
|
|
3082
|
+
changes.push(editOpts.required ? 'required' : '!required');
|
|
2965
3083
|
if (editOpts.sformId)
|
|
2966
3084
|
changes.push(`EBuilder→${editOpts.sformId}`);
|
|
2967
3085
|
if (editOpts.dataTitle !== undefined)
|
|
@@ -2971,6 +3089,19 @@ export function registerFormCommands(program) {
|
|
|
2971
3089
|
if (editOpts.multiple !== undefined)
|
|
2972
3090
|
changes.push(editOpts.multiple ? 'multiple' : '!multiple');
|
|
2973
3091
|
changes.push(...patch.applied);
|
|
3092
|
+
// 必填**只存在于布局 comp 里**:字段记录没有 `required` 这个键(整张表的字段记录里都没有),
|
|
3093
|
+
// 所以上面写进 jsonObj 的那一下落不了库。只写字段记录 = 接口回 200、命令报成功、表单上行为
|
|
3094
|
+
// 一点没变。真正生效的是布局 comp 的 `config.required`,这里补上。
|
|
3095
|
+
if (editOpts.required !== undefined) {
|
|
3096
|
+
try {
|
|
3097
|
+
const { updated } = await patchFieldLayout(client, baseUrl, formId, fieldId, { required: editOpts.required === true });
|
|
3098
|
+
if (!updated)
|
|
3099
|
+
console.error(' 警告: 布局里没找到该字段的组件,必填未生效');
|
|
3100
|
+
}
|
|
3101
|
+
catch (e) {
|
|
3102
|
+
console.error(` 警告: 布局里的必填未更新(字段本身已改好): ${e.message}`);
|
|
3103
|
+
}
|
|
3104
|
+
}
|
|
2974
3105
|
// EBuilder 字段的浏览显示列:add-field 建出来的会自动配,edit-field 改出来的此前漏了这一步
|
|
2975
3106
|
// —— 字段能建出来,但浏览弹窗回落平台默认列,会把目标表的系统字段也列出来。
|
|
2976
3107
|
// ensureDisplayColumns 只在「没配过」或「旧列对不上当前目标表」时才写,不会冲掉手工配好的列。
|