openxiangda 2.44.0 → 2.55.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/dist/browser/AuthoritativeSelector.d.ts +3 -2
- package/dist/browser/AuthoritativeSelector.d.ts.map +1 -1
- package/dist/browser/AuthoritativeSelector.js +32 -11
- package/dist/browser/AuthoritativeSelector.js.map +1 -1
- package/dist/browser/FilePreviewPage.d.ts.map +1 -1
- package/dist/browser/FilePreviewPage.js +4 -0
- package/dist/browser/FilePreviewPage.js.map +1 -1
- package/dist/browser/components/administration/RoleMembershipManager.d.ts.map +1 -1
- package/dist/browser/components/administration/RoleMembershipManager.js +5 -5
- package/dist/browser/components/administration/RoleMembershipManager.js.map +1 -1
- package/dist/browser/components/administration/scope-applicability.d.ts +3 -0
- package/dist/browser/components/administration/scope-applicability.d.ts.map +1 -0
- package/dist/browser/components/administration/scope-applicability.js +7 -0
- package/dist/browser/components/administration/scope-applicability.js.map +1 -0
- package/dist/browser/components/platform-fields/ConstrainedUserField.d.ts +16 -0
- package/dist/browser/components/platform-fields/ConstrainedUserField.d.ts.map +1 -0
- package/dist/browser/components/platform-fields/ConstrainedUserField.js +140 -0
- package/dist/browser/components/platform-fields/ConstrainedUserField.js.map +1 -0
- package/dist/browser/components/platform-fields/JsonField.d.ts.map +1 -1
- package/dist/browser/components/platform-fields/JsonField.js +6 -1
- package/dist/browser/components/platform-fields/JsonField.js.map +1 -1
- package/dist/browser/components/platform-fields/ManagedMediaPlayer.d.ts +19 -0
- package/dist/browser/components/platform-fields/ManagedMediaPlayer.d.ts.map +1 -0
- package/dist/browser/components/platform-fields/ManagedMediaPlayer.js +42 -0
- package/dist/browser/components/platform-fields/ManagedMediaPlayer.js.map +1 -0
- package/dist/browser/components/platform-fields/MobileManagedFileField.d.ts.map +1 -1
- package/dist/browser/components/platform-fields/MobileManagedFileField.js +6 -1
- package/dist/browser/components/platform-fields/MobileManagedFileField.js.map +1 -1
- package/dist/browser/components/platform-fields/MobileSelection.d.ts +3 -1
- package/dist/browser/components/platform-fields/MobileSelection.d.ts.map +1 -1
- package/dist/browser/components/platform-fields/MobileSelection.js +2 -2
- package/dist/browser/components/platform-fields/MobileSelection.js.map +1 -1
- package/dist/browser/components/platform-fields/MobileSubtableValidation.d.ts +2 -1
- package/dist/browser/components/platform-fields/MobileSubtableValidation.d.ts.map +1 -1
- package/dist/browser/components/platform-fields/MobileSubtableValidation.js +3 -1
- package/dist/browser/components/platform-fields/MobileSubtableValidation.js.map +1 -1
- package/dist/browser/components/platform-fields/ResourceReferenceField.d.ts +3 -2
- package/dist/browser/components/platform-fields/ResourceReferenceField.d.ts.map +1 -1
- package/dist/browser/components/platform-fields/ResourceReferenceField.js +2 -2
- package/dist/browser/components/platform-fields/ResourceReferenceField.js.map +1 -1
- package/dist/browser/components/platform-fields/RichTextField.d.ts +3 -2
- package/dist/browser/components/platform-fields/RichTextField.d.ts.map +1 -1
- package/dist/browser/components/platform-fields/RichTextField.js +96 -44
- package/dist/browser/components/platform-fields/RichTextField.js.map +1 -1
- package/dist/browser/components/platform-fields/SignatureField.d.ts +5 -4
- package/dist/browser/components/platform-fields/SignatureField.d.ts.map +1 -1
- package/dist/browser/components/platform-fields/SignatureField.js +69 -16
- package/dist/browser/components/platform-fields/SignatureField.js.map +1 -1
- package/dist/browser/components/platform-fields/SubtableField.d.ts +18 -2
- package/dist/browser/components/platform-fields/SubtableField.d.ts.map +1 -1
- package/dist/browser/components/platform-fields/SubtableField.js +146 -57
- package/dist/browser/components/platform-fields/SubtableField.js.map +1 -1
- package/dist/browser/components/platform-fields/managed-media-read.d.ts +19 -0
- package/dist/browser/components/platform-fields/managed-media-read.d.ts.map +1 -0
- package/dist/browser/components/platform-fields/managed-media-read.js +32 -0
- package/dist/browser/components/platform-fields/managed-media-read.js.map +1 -0
- package/dist/browser/components/platform-fields/subtable-pagination.d.ts +20 -0
- package/dist/browser/components/platform-fields/subtable-pagination.d.ts.map +1 -0
- package/dist/browser/components/platform-fields/subtable-pagination.js +39 -0
- package/dist/browser/components/platform-fields/subtable-pagination.js.map +1 -0
- package/dist/browser/components/platform-fields/subtable-value.d.ts.map +1 -1
- package/dist/browser/components/platform-fields/subtable-value.js +2 -1
- package/dist/browser/components/platform-fields/subtable-value.js.map +1 -1
- package/dist/browser/components/platform-fields/surface-field-validation.d.ts +31 -0
- package/dist/browser/components/platform-fields/surface-field-validation.d.ts.map +1 -0
- package/dist/browser/components/platform-fields/surface-field-validation.js +36 -0
- package/dist/browser/components/platform-fields/surface-field-validation.js.map +1 -0
- package/dist/browser/components/platform-fields/user-candidate-context.d.ts +51 -0
- package/dist/browser/components/platform-fields/user-candidate-context.d.ts.map +1 -0
- package/dist/browser/components/platform-fields/user-candidate-context.js +62 -0
- package/dist/browser/components/platform-fields/user-candidate-context.js.map +1 -0
- package/dist/browser/components/resource/GeneratedResourceCrud.d.ts.map +1 -1
- package/dist/browser/components/resource/GeneratedResourceCrud.js +26 -2
- package/dist/browser/components/resource/GeneratedResourceCrud.js.map +1 -1
- package/dist/browser/components/resource/GeneratedResourceForm.js +1 -1
- package/dist/browser/components/resource/GeneratedResourceForm.js.map +1 -1
- package/dist/browser/components/resource/RecordDetailFrame.d.ts +3 -1
- package/dist/browser/components/resource/RecordDetailFrame.d.ts.map +1 -1
- package/dist/browser/components/resource/RecordDetailFrame.js +2 -2
- package/dist/browser/components/resource/RecordDetailFrame.js.map +1 -1
- package/dist/browser/components/resource/ResourceFormFrame.d.ts +2 -1
- package/dist/browser/components/resource/ResourceFormFrame.d.ts.map +1 -1
- package/dist/browser/components/resource/ResourceFormFrame.js +2 -2
- package/dist/browser/components/resource/ResourceFormFrame.js.map +1 -1
- package/dist/browser/components/resource/ResourceRecordComments.d.ts +13 -0
- package/dist/browser/components/resource/ResourceRecordComments.d.ts.map +1 -0
- package/dist/browser/components/resource/ResourceRecordComments.js +75 -0
- package/dist/browser/components/resource/ResourceRecordComments.js.map +1 -0
- package/dist/browser/components/resource/ResourceRecordDeletion.d.ts +7 -0
- package/dist/browser/components/resource/ResourceRecordDeletion.d.ts.map +1 -0
- package/dist/browser/components/resource/ResourceRecordDeletion.js +53 -0
- package/dist/browser/components/resource/ResourceRecordDeletion.js.map +1 -0
- package/dist/browser/components/resource/ResourceRecordPrintPreview.d.ts +16 -0
- package/dist/browser/components/resource/ResourceRecordPrintPreview.d.ts.map +1 -0
- package/dist/browser/components/resource/ResourceRecordPrintPreview.js +92 -0
- package/dist/browser/components/resource/ResourceRecordPrintPreview.js.map +1 -0
- package/dist/browser/components/resource/SurfaceFields.d.ts +9 -4
- package/dist/browser/components/resource/SurfaceFields.d.ts.map +1 -1
- package/dist/browser/components/resource/SurfaceFields.js +54 -72
- package/dist/browser/components/resource/SurfaceFields.js.map +1 -1
- package/dist/browser/components/resource/generated-resource-definition.d.ts +13 -0
- package/dist/browser/components/resource/generated-resource-definition.d.ts.map +1 -1
- package/dist/browser/components/resource/record-comment-session.d.ts +17 -0
- package/dist/browser/components/resource/record-comment-session.d.ts.map +1 -0
- package/dist/browser/components/resource/record-comment-session.js +64 -0
- package/dist/browser/components/resource/record-comment-session.js.map +1 -0
- package/dist/browser/components/resource/record-deletion-session.d.ts +19 -0
- package/dist/browser/components/resource/record-deletion-session.d.ts.map +1 -0
- package/dist/browser/components/resource/record-deletion-session.js +64 -0
- package/dist/browser/components/resource/record-deletion-session.js.map +1 -0
- package/dist/browser/components/resource/record-print-session.d.ts +12 -0
- package/dist/browser/components/resource/record-print-session.d.ts.map +1 -0
- package/dist/browser/components/resource/record-print-session.js +32 -0
- package/dist/browser/components/resource/record-print-session.js.map +1 -0
- package/dist/browser/components/resource/resource-field-selection.d.ts +1 -0
- package/dist/browser/components/resource/resource-field-selection.d.ts.map +1 -1
- package/dist/browser/components/resource/resource-form-operations.d.ts.map +1 -1
- package/dist/browser/components/resource/resource-form-operations.js +5 -1
- package/dist/browser/components/resource/resource-form-operations.js.map +1 -1
- package/dist/browser/components/resource/useResourceFormDrafts.d.ts.map +1 -1
- package/dist/browser/components/workflow/StandardWorkflowPages.d.ts +13 -2
- package/dist/browser/components/workflow/StandardWorkflowPages.d.ts.map +1 -1
- package/dist/browser/components/workflow/StandardWorkflowPages.js +96 -47
- package/dist/browser/components/workflow/StandardWorkflowPages.js.map +1 -1
- package/dist/browser/components/workflow/WorkflowDiagram.d.ts.map +1 -1
- package/dist/browser/components/workflow/WorkflowDiagram.js +14 -1
- package/dist/browser/components/workflow/WorkflowDiagram.js.map +1 -1
- package/dist/browser/components/workflow/WorkflowFlowCanvas.d.ts.map +1 -1
- package/dist/browser/components/workflow/WorkflowFlowCanvas.js +27 -8
- package/dist/browser/components/workflow/WorkflowFlowCanvas.js.map +1 -1
- package/dist/browser/components/workflow/WorkflowNodeCard.js +2 -2
- package/dist/browser/components/workflow/WorkflowNodeCard.js.map +1 -1
- package/dist/browser/components/workflow/WorkflowNodeConfigurationEditor.d.ts.map +1 -1
- package/dist/browser/components/workflow/WorkflowNodeConfigurationEditor.js +4 -4
- package/dist/browser/components/workflow/WorkflowNodeConfigurationEditor.js.map +1 -1
- package/dist/browser/components/workflow/WorkflowRecordEditor.js +1 -1
- package/dist/browser/components/workflow/WorkflowRecordEditor.js.map +1 -1
- package/dist/browser/components/workflow/WorkflowRecordHistoryPanel.d.ts +9 -0
- package/dist/browser/components/workflow/WorkflowRecordHistoryPanel.d.ts.map +1 -0
- package/dist/browser/components/workflow/WorkflowRecordHistoryPanel.js +50 -0
- package/dist/browser/components/workflow/WorkflowRecordHistoryPanel.js.map +1 -0
- package/dist/browser/components/workflow/WorkflowTaskFiles.d.ts +5 -3
- package/dist/browser/components/workflow/WorkflowTaskFiles.d.ts.map +1 -1
- package/dist/browser/components/workflow/WorkflowTaskFiles.js +67 -27
- package/dist/browser/components/workflow/WorkflowTaskFiles.js.map +1 -1
- package/dist/browser/components/workflow/WorkflowTaskForm.d.ts +6 -1
- package/dist/browser/components/workflow/WorkflowTaskForm.d.ts.map +1 -1
- package/dist/browser/components/workflow/WorkflowTaskForm.js +65 -16
- package/dist/browser/components/workflow/WorkflowTaskForm.js.map +1 -1
- package/dist/browser/components/workflow/standard-process-values.d.ts +10 -0
- package/dist/browser/components/workflow/standard-process-values.d.ts.map +1 -0
- package/dist/browser/components/workflow/standard-process-values.js +25 -0
- package/dist/browser/components/workflow/standard-process-values.js.map +1 -0
- package/dist/browser/components/workflow/workflow-graph-presentation.d.ts +19 -0
- package/dist/browser/components/workflow/workflow-graph-presentation.d.ts.map +1 -0
- package/dist/browser/components/workflow/workflow-graph-presentation.js +28 -0
- package/dist/browser/components/workflow/workflow-graph-presentation.js.map +1 -0
- package/dist/browser/components/workflow/workflow-submission-form.d.ts +18 -0
- package/dist/browser/components/workflow/workflow-submission-form.d.ts.map +1 -0
- package/dist/browser/components/workflow/workflow-submission-form.js +44 -0
- package/dist/browser/components/workflow/workflow-submission-form.js.map +1 -0
- package/dist/browser/components/workflow/workflow-task-field-codec.d.ts +4 -0
- package/dist/browser/components/workflow/workflow-task-field-codec.d.ts.map +1 -0
- package/dist/browser/components/workflow/workflow-task-field-codec.js +9 -0
- package/dist/browser/components/workflow/workflow-task-field-codec.js.map +1 -0
- package/dist/browser/components/workflow/workflow-task-required-errors.d.ts +10 -0
- package/dist/browser/components/workflow/workflow-task-required-errors.d.ts.map +1 -0
- package/dist/browser/components/workflow/workflow-task-required-errors.js +28 -0
- package/dist/browser/components/workflow/workflow-task-required-errors.js.map +1 -0
- package/dist/browser/components/workflow/workflow-task-subtable.d.ts +7 -0
- package/dist/browser/components/workflow/workflow-task-subtable.d.ts.map +1 -0
- package/dist/browser/components/workflow/workflow-task-subtable.js +58 -0
- package/dist/browser/components/workflow/workflow-task-subtable.js.map +1 -0
- package/dist/browser/durable-command.d.ts.map +1 -1
- package/dist/browser/durable-command.js +6 -1
- package/dist/browser/durable-command.js.map +1 -1
- package/dist/browser/mobile-fields.css +4 -0
- package/dist/browser/platform-client.d.ts +30 -1
- package/dist/browser/platform-client.d.ts.map +1 -1
- package/dist/browser/platform-client.js +161 -5
- package/dist/browser/platform-client.js.map +1 -1
- package/dist/browser/record-comments.css +14 -0
- package/dist/browser/record-deletion.css +11 -0
- package/dist/browser/record-detail.css +4 -2
- package/dist/browser/record-print.css +31 -0
- package/dist/browser/styles.css +41 -0
- package/dist/browser/workflow-operation-input.d.ts +15 -0
- package/dist/browser/workflow-operation-input.d.ts.map +1 -0
- package/dist/browser/workflow-operation-input.js +64 -0
- package/dist/browser/workflow-operation-input.js.map +1 -0
- package/dist/browser/workflow-task-file-upload.d.ts.map +1 -1
- package/dist/browser/workflow-task-file-upload.js +1 -0
- package/dist/browser/workflow-task-file-upload.js.map +1 -1
- package/dist/core.d.ts +2 -2
- package/dist/core.d.ts.map +1 -1
- package/dist/core.js +1 -1
- package/dist/core.js.map +1 -1
- package/dist/field-kit.d.ts +3 -0
- package/dist/field-kit.d.ts.map +1 -1
- package/dist/field-kit.js +3 -0
- package/dist/field-kit.js.map +1 -1
- package/dist/nest.d.ts +1 -1
- package/dist/nest.d.ts.map +1 -1
- package/dist/nest.js.map +1 -1
- package/dist/react.d.ts +6 -2
- package/dist/react.d.ts.map +1 -1
- package/dist/react.js +5 -1
- package/dist/react.js.map +1 -1
- package/dist/testing.d.ts +1 -1
- package/dist/testing.d.ts.map +1 -1
- package/dist/testing.js +1 -1
- package/dist/testing.js.map +1 -1
- package/documentation/administration.md +7 -1
- package/documentation/backend.md +72 -1
- package/documentation/data-authz.md +42 -2
- package/documentation/declarations-cheatsheet.md +9 -0
- package/documentation/field-components.md +45 -1
- package/documentation/frontend.md +8 -0
- package/documentation/getting-started.md +7 -7
- package/documentation/managed-concurrency-frontend.md +1 -1
- package/documentation/manifest.json +11 -11
- package/documentation/testing.md +17 -0
- package/documentation/workflow-events.md +221 -6
- package/package.json +22 -25
- package/releases/2.51.0.json +32 -0
- package/releases/2.54.4.json +30 -0
- package/releases/2.54.6.json +30 -0
- package/releases/2.55.0.json +34 -0
- package/releases/2.55.1.json +32 -0
- package/skills/manifest.json +1 -1
- package/skills/openxiangda-v2/SKILL.md +4 -4
- package/skills/openxiangda-v2/references/administration.md +7 -1
- package/skills/openxiangda-v2/references/backend.md +72 -1
- package/skills/openxiangda-v2/references/data-authz.md +42 -2
- package/skills/openxiangda-v2/references/declarations-cheatsheet.md +9 -0
- package/skills/openxiangda-v2/references/field-components.md +45 -1
- package/skills/openxiangda-v2/references/frontend.md +8 -0
- package/skills/openxiangda-v2/references/getting-started.md +7 -7
- package/skills/openxiangda-v2/references/managed-concurrency-frontend.md +1 -1
- package/skills/openxiangda-v2/references/testing.md +17 -0
- package/skills/openxiangda-v2/references/workflow-events.md +221 -6
- package/dist/browser/components/platform-fields/MobileRichTextField.d.ts +0 -4
- package/dist/browser/components/platform-fields/MobileRichTextField.d.ts.map +0 -1
- package/dist/browser/components/platform-fields/MobileRichTextField.js +0 -38
- package/dist/browser/components/platform-fields/MobileRichTextField.js.map +0 -1
- package/releases/2.43.0.json +0 -38
- package/releases/2.44.0.json +0 -36
|
@@ -3,6 +3,7 @@ import { applicationCode } from '../../runtime-meta';
|
|
|
3
3
|
import { readPendingWorkflowSubmission, writePendingWorkflowSubmission, clearPendingWorkflowSubmission, workflowSubmissionScope, submissionLocatorStorage, standardProcessWasRejected } from '../../workflow-submission-recovery';
|
|
4
4
|
import { readPendingWorkflowTaskCommand, writePendingWorkflowTaskCommand, clearPendingWorkflowTaskCommand, workflowTaskCommandScope, workflowCommandTokenDigest, workflowTaskCommandWasRejected } from '../../workflow-task-command-recovery';
|
|
5
5
|
import { WorkflowTaskForm, useWorkflowTaskForm } from './WorkflowTaskForm';
|
|
6
|
+
import { retainedWorkflowOperation, workflowOperationSignature, workflowOperationStringError, workflowOperationInputFailure } from '../../workflow-operation-input';
|
|
6
7
|
import { WorkflowPendingCommandGuard, WorkflowTaskCommandReceipt } from './WorkflowTaskCommandReceipt';
|
|
7
8
|
import { PresentationTime, usePresentationTimeZone } from '../../presentation-time';
|
|
8
9
|
import { ArrowLeftOutlined, ClockCircleOutlined, EllipsisOutlined, ReloadOutlined, CloseOutlined, ExpandOutlined, CompressOutlined, ExportOutlined, } from '@ant-design/icons';
|
|
@@ -25,6 +26,10 @@ import { RecordChangeHistory } from '../resource/RecordChangeHistory';
|
|
|
25
26
|
import { ResourceFormContent } from '../resource/ResourceFormFrame';
|
|
26
27
|
import { WorkflowRecordEditor } from './WorkflowRecordEditor';
|
|
27
28
|
import { PlatformAvatar } from '../PlatformAvatar';
|
|
29
|
+
import { SubtableField } from '../platform-fields/SubtableField';
|
|
30
|
+
import { standardProcessFormValues } from './standard-process-values';
|
|
31
|
+
import { fieldWritable } from '../resource/resource-page-helpers';
|
|
32
|
+
import { workflowSubmissionFormProjection, workflowSubmissionPrefill } from './workflow-submission-form';
|
|
28
33
|
/**
|
|
29
34
|
* An advanced task command has completed the current task and may have
|
|
30
35
|
* created a new task. Reading the old task Surface in that case is expected
|
|
@@ -84,6 +89,7 @@ function workflowStatus(status) {
|
|
|
84
89
|
running: { label: '审批中', color: 'processing' },
|
|
85
90
|
returned: { label: '已退回', color: 'orange' },
|
|
86
91
|
completed: { label: '已完成', color: 'success' },
|
|
92
|
+
skipped: { label: '已跳过', color: 'default' },
|
|
87
93
|
approved: { label: '已同意', color: 'success' },
|
|
88
94
|
rejected: { label: '已拒绝', color: 'error' },
|
|
89
95
|
withdrawn: { label: '已撤回', color: 'default' },
|
|
@@ -129,32 +135,8 @@ function workflowSurfaceMatchesInstance(surface, instanceId) {
|
|
|
129
135
|
function surfaceBusinessDetail(surface) {
|
|
130
136
|
return normalizeWorkflowBusinessDetail(surface.presentation.businessDetail);
|
|
131
137
|
}
|
|
132
|
-
function workflowOperationSignature(operation) {
|
|
133
|
-
return JSON.stringify({
|
|
134
|
-
key: operation.key,
|
|
135
|
-
kind: operation.kind,
|
|
136
|
-
label: operation.label,
|
|
137
|
-
placement: operation.placement,
|
|
138
|
-
group: operation.group,
|
|
139
|
-
audience: operation.audience,
|
|
140
|
-
emphasis: operation.emphasis,
|
|
141
|
-
tone: operation.tone,
|
|
142
|
-
visible: operation.visible,
|
|
143
|
-
enabled: operation.enabled,
|
|
144
|
-
disabledReason: operation.disabledReason,
|
|
145
|
-
inputSchema: operation.inputSchema,
|
|
146
|
-
uiSchema: operation.uiSchema,
|
|
147
|
-
execute: operation.execute,
|
|
148
|
-
refresh: operation.refresh,
|
|
149
|
-
});
|
|
150
|
-
}
|
|
151
138
|
const WORKFLOW_APP_ACTION_DISABLED_REASON = '应用动作由应用页面负责';
|
|
152
139
|
function standardWorkflowOperations(surface) {
|
|
153
|
-
if (!surface.commandToken ||
|
|
154
|
-
!surface.commandTokenExpiresAt ||
|
|
155
|
-
new Date(surface.commandTokenExpiresAt).getTime() <= Date.now()) {
|
|
156
|
-
return [];
|
|
157
|
-
}
|
|
158
140
|
return surface.operations
|
|
159
141
|
.filter((operation) => operation.visible)
|
|
160
142
|
.map((operation) => {
|
|
@@ -322,7 +304,7 @@ export function WorkflowTimelineSection({ timeline, }) {
|
|
|
322
304
|
const operations = item.operations || [];
|
|
323
305
|
const visiblePeople = visibleWorkflowTimelinePeople(item, operations);
|
|
324
306
|
const businessStep = item.nodeKind === 'action' ? item.result.businessStep : undefined;
|
|
325
|
-
return (_jsxs("div", { className: timelineTone(item.status), children: [_jsx("span", { className: "oxa-workflow-timeline-dot", children: _jsx(WorkflowStatusIcon, { status: item.status }) }), _jsxs("div", { children: [_jsxs("div", { className: "oxa-workflow-timeline-title", children: [_jsx("strong", { children: item.title }), businessStep?.status === 'waiting' ? _jsx(Tag, { color: "processing", children: "\u7B49\u5F85\u4E1A\u52A1\u7ED3\u679C" }) : businessStep?.status === 'result_ready' ? _jsx(Tag, { color: "warning", children: "\u63A8\u8FDB\u53D7\u963B" }) : _jsx(StatusTag, { status: item.status })] }), businessStep?.status === 'result_ready' && _jsx(Typography.Text, { type: "secondary", children: "\u8BA1\u7B97\u7ED3\u679C\u5DF2\u6536\u5230\uFF0C\u540E\u7EED\u6D41\u8F6C\u7B49\u5F85\u4FEE\u590D\u3002" }), visiblePeople.length > 0 && (_jsx("div", { className: "oxa-workflow-timeline-assignees", children: visiblePeople.map((person, index) => (_jsxs("div", { children: [_jsx(PlatformAvatar, { avatarUrl: person.avatarUrl, size: 20 }), _jsxs("span", { children: [_jsx(Typography.Text, { children: person.displayName }), person.departmentDisplayName && (_jsx("small", { children: person.departmentDisplayName }))] })] }, `${person.userId || person.displayName}:${index}`))) })), operations.length > 0 && (_jsx("div", { className: "oxa-workflow-timeline-operations", children: operations.map((operation) => (_jsxs("div", { children: [_jsx(PlatformAvatar, { avatarUrl: operation.actor.avatarUrl, size: 20 }), _jsxs("span", { className: "oxa-workflow-operation-content", children: [_jsxs("span", { children: [_jsx(Typography.Text, { children: operation.actor.displayName }), _jsx("strong", { children: operation.operationLabel })] }), operation.reason && (_jsxs("span", { className: "oxa-workflow-operation-opinion", children: [_jsx(Typography.Text, { type: "secondary", children: "\u610F\u89C1" }), _jsx(Typography.Text, { children: operation.reason })] }))] })] }, operation.id))) })), item.terminalReason && !operations.some(operation => operation.reason) && (_jsxs(Typography.Text, { type: "secondary", children: ["\u539F\u56E0\uFF1A", item.terminalReason] })), item.primaryDisplayTime && (_jsx("time", { className: "oxa-workflow-primary-time", children: formatTime(item.primaryDisplayTime) }))] })] }, item.key));
|
|
307
|
+
return (_jsxs("div", { className: timelineTone(item.status), children: [_jsx("span", { className: "oxa-workflow-timeline-dot", children: _jsx(WorkflowStatusIcon, { status: item.status }) }), _jsxs("div", { children: [_jsxs("div", { className: "oxa-workflow-timeline-title", children: [_jsx("strong", { children: item.title }), businessStep?.status === 'waiting' ? _jsx(Tag, { color: "processing", children: "\u7B49\u5F85\u4E1A\u52A1\u7ED3\u679C" }) : businessStep?.status === 'result_ready' ? _jsx(Tag, { color: "warning", children: "\u63A8\u8FDB\u53D7\u963B" }) : _jsx(StatusTag, { status: item.status })] }), item.status === 'skipped' && _jsx(Typography.Text, { type: "secondary", children: "\u65E0\u5BA1\u6279\u4EBA\uFF0C\u6309\u6B64\u8282\u70B9\u7684\u89C4\u5219\u81EA\u52A8\u7EE7\u7EED\u3002" }), businessStep?.status === 'result_ready' && _jsx(Typography.Text, { type: "secondary", children: "\u8BA1\u7B97\u7ED3\u679C\u5DF2\u6536\u5230\uFF0C\u540E\u7EED\u6D41\u8F6C\u7B49\u5F85\u4FEE\u590D\u3002" }), visiblePeople.length > 0 && (_jsx("div", { className: "oxa-workflow-timeline-assignees", children: visiblePeople.map((person, index) => (_jsxs("div", { children: [_jsx(PlatformAvatar, { avatarUrl: person.avatarUrl, size: 20 }), _jsxs("span", { children: [_jsx(Typography.Text, { children: person.displayName }), person.departmentDisplayName && (_jsx("small", { children: person.departmentDisplayName }))] })] }, `${person.userId || person.displayName}:${index}`))) })), operations.length > 0 && (_jsx("div", { className: "oxa-workflow-timeline-operations", children: operations.map((operation) => (_jsxs("div", { children: [_jsx(PlatformAvatar, { avatarUrl: operation.actor.avatarUrl, size: 20 }), _jsxs("span", { className: "oxa-workflow-operation-content", children: [_jsxs("span", { children: [_jsx(Typography.Text, { children: operation.actor.displayName }), _jsx("strong", { children: operation.operationLabel })] }), operation.reason && (_jsxs("span", { className: "oxa-workflow-operation-opinion", children: [_jsx(Typography.Text, { type: "secondary", children: "\u610F\u89C1" }), _jsx(Typography.Text, { children: operation.reason })] }))] })] }, operation.id))) })), item.terminalReason && !operations.some(operation => operation.reason) && (_jsxs(Typography.Text, { type: "secondary", children: ["\u539F\u56E0\uFF1A", item.terminalReason] })), item.primaryDisplayTime && (_jsx("time", { className: "oxa-workflow-primary-time", children: formatTime(item.primaryDisplayTime) }))] })] }, item.key));
|
|
326
308
|
}) })) : (_jsx(Empty, { description: "\u6682\u65E0\u6D41\u7A0B\u8F68\u8FF9", image: Empty.PRESENTED_IMAGE_SIMPLE })) }));
|
|
327
309
|
}
|
|
328
310
|
function WorkflowMemberPicker({ id, placeholder, value, onChange, multiple = false, variant }) {
|
|
@@ -349,6 +331,11 @@ function OperationFields({ operation, variant, }) {
|
|
|
349
331
|
return (_jsx(_Fragment, { children: schemaProperties(operation).map(({ key, property, required, ui }) => {
|
|
350
332
|
const rules = [
|
|
351
333
|
...(required ? [{ required: true, message: `请填写${property.title || key}` }] : []),
|
|
334
|
+
...(property.type === 'string' ? [{ validator: async (_rule, value) => {
|
|
335
|
+
const error = workflowOperationStringError(property, value, required, property.title || key);
|
|
336
|
+
if (error)
|
|
337
|
+
throw new Error(error);
|
|
338
|
+
} }] : []),
|
|
352
339
|
...(property.type === 'array' ? [{ validator: async (_rule, value) => {
|
|
353
340
|
if (value == null && !required)
|
|
354
341
|
return;
|
|
@@ -372,7 +359,7 @@ function OperationFields({ operation, variant, }) {
|
|
|
372
359
|
else if (property.format === 'date-time') {
|
|
373
360
|
control = _jsx(Input, { type: "datetime-local" });
|
|
374
361
|
}
|
|
375
|
-
return (_jsx(Form.Item, { initialValue: property.default, label: property.title || key, name: key, rules: rules, children: control }, key));
|
|
362
|
+
return (_jsx(Form.Item, { initialValue: property.default, label: property.title || key, name: key, rules: rules, validateFirst: true, children: control }, key));
|
|
376
363
|
}) }));
|
|
377
364
|
}
|
|
378
365
|
function OperationDialog({ error, operation, submitting, variant, onCancel, onSubmit, }) {
|
|
@@ -394,6 +381,7 @@ function WorkflowOperations({ surface, variant, onRefresh, onCommandSuccess, pen
|
|
|
394
381
|
const [selectedState, setSelectedState] = useState(null);
|
|
395
382
|
const [moreOpen, setMoreOpen] = useState(false);
|
|
396
383
|
const [operationError, setOperationError] = useState('');
|
|
384
|
+
const [retainRefusedInput, setRetainRefusedInput] = useState(false);
|
|
397
385
|
const [submitting, setSubmitting] = useState(false);
|
|
398
386
|
const [draftLocked, setDraftLocked] = useState(false);
|
|
399
387
|
const [fileLocked, setFileLocked] = useState(false);
|
|
@@ -414,16 +402,31 @@ function WorkflowOperations({ surface, variant, onRefresh, onCommandSuccess, pen
|
|
|
414
402
|
setSelectedState(null);
|
|
415
403
|
}, [settlement]);
|
|
416
404
|
const operations = standardWorkflowOperations(surface);
|
|
417
|
-
const
|
|
418
|
-
|
|
419
|
-
|
|
420
|
-
|
|
421
|
-
|
|
405
|
+
const [, setCommandClock] = useState(0);
|
|
406
|
+
const commandExpiresAt = Date.parse(surface.commandTokenExpiresAt || '');
|
|
407
|
+
const commandNeedsRefresh = operations.some(operation => operation.kind === 'workflow_command') &&
|
|
408
|
+
(!surface.commandToken || !Number.isFinite(commandExpiresAt) || commandExpiresAt <= Date.now());
|
|
409
|
+
useEffect(() => {
|
|
410
|
+
if (!surface.commandToken || !Number.isFinite(commandExpiresAt) || commandExpiresAt <= Date.now())
|
|
411
|
+
return;
|
|
412
|
+
let timer;
|
|
413
|
+
const tick = () => {
|
|
414
|
+
setCommandClock(value => value + 1);
|
|
415
|
+
const remaining = commandExpiresAt - Date.now();
|
|
416
|
+
if (remaining > 0)
|
|
417
|
+
timer = setTimeout(tick, Math.min(remaining, 2_147_483_647));
|
|
418
|
+
};
|
|
419
|
+
timer = setTimeout(tick, Math.min(commandExpiresAt - Date.now(), 2_147_483_647));
|
|
420
|
+
return () => clearTimeout(timer);
|
|
421
|
+
}, [surface.commandToken, commandExpiresAt]);
|
|
422
|
+
const selected = commandNeedsRefresh ? null
|
|
423
|
+
: retainedWorkflowOperation(selectedState, surface, operations, retainRefusedInput);
|
|
422
424
|
useEffect(() => {
|
|
423
425
|
if (selectedState && !selected && !submitting && !unknown)
|
|
424
426
|
setSelectedState(null);
|
|
425
427
|
}, [selected, selectedState, submitting, unknown]);
|
|
426
428
|
const selectOperation = (operation) => {
|
|
429
|
+
setRetainRefusedInput(false);
|
|
427
430
|
setOperationError('');
|
|
428
431
|
setSelectedState({
|
|
429
432
|
operation,
|
|
@@ -447,9 +450,9 @@ function WorkflowOperations({ surface, variant, onRefresh, onCommandSuccess, pen
|
|
|
447
450
|
await onRefresh();
|
|
448
451
|
throw new Error('WORKFLOW_FRESH_COMMAND_TOKEN_REQUIRED');
|
|
449
452
|
}
|
|
450
|
-
if (
|
|
453
|
+
if (!Number.isFinite(commandExpiresAt) || commandExpiresAt <= Date.now()) {
|
|
451
454
|
await onRefresh();
|
|
452
|
-
throw new Error('
|
|
455
|
+
throw new Error('操作已刷新,请保留当前输入并重新确认。');
|
|
453
456
|
}
|
|
454
457
|
const input = { ...values };
|
|
455
458
|
if (surface.taskForm && ['save_form', 'approve', 'resubmit'].includes(selected.key)) {
|
|
@@ -504,13 +507,13 @@ function WorkflowOperations({ surface, variant, onRefresh, onCommandSuccess, pen
|
|
|
504
507
|
if (rejected) {
|
|
505
508
|
clearLocator(wire.key);
|
|
506
509
|
request.current = null;
|
|
507
|
-
|
|
510
|
+
setRetainRefusedInput(true);
|
|
508
511
|
}
|
|
509
512
|
else {
|
|
510
513
|
setUnknown(true);
|
|
511
514
|
setSelectedState(null);
|
|
512
515
|
}
|
|
513
|
-
const failure = errorMessage(error, '任务操作尚未完成');
|
|
516
|
+
const failure = workflowOperationInputFailure(error) || errorMessage(error, '任务操作尚未完成');
|
|
514
517
|
setOperationError(failure);
|
|
515
518
|
if (rejected) {
|
|
516
519
|
message.error(failure);
|
|
@@ -588,16 +591,16 @@ function WorkflowOperations({ surface, variant, onRefresh, onCommandSuccess, pen
|
|
|
588
591
|
.sort((left, right) => {
|
|
589
592
|
if (variant !== 'mobile')
|
|
590
593
|
return 0;
|
|
591
|
-
const order = { reject: 0, approve: 1 };
|
|
594
|
+
const order = { reject: 0, approve: 1, resubmit: 1 };
|
|
592
595
|
return (order[left.key] ?? 10) - (order[right.key] ?? 10);
|
|
593
596
|
});
|
|
594
597
|
const secondary = operations.filter((operation) => operation.placement !== 'primary');
|
|
595
|
-
const content = surface.taskForm || ((submitting || unknown) && !pendingLocator) || unknown || refreshFailure ? (_jsxs(_Fragment, { children: [surface.taskForm && _jsx(WorkflowTaskForm, { controller: taskForm, disabled: locked, variant: variant, taskId: surface.task?.id ? String(surface.task.id) : undefined, draftDisabled: commandLocked, onRefresh: onRefresh, onDraftBusyChange: busy => { setDraftLocked(busy); onBusyChange(busy || fileLocked || busyRef.current); }, onFileBusyChange: busy => { setFileLocked(busy); onBusyChange(busy || draftLocked || busyRef.current); }, resourceCode: surface.presentation.businessDetail.resourceCode || undefined, recordId: surface.presentation.businessDetail.recordId || undefined }), (submitting || unknown) && !pendingLocator && _jsx(WorkflowPendingCommandGuard, {}), unknown && _jsx(Alert, { type: "warning", showIcon: true, title: "\u4FDD\u7559\u4E86\u539F\u63D0\u4EA4\u8BF7\u6C42", description: operationError || '提交结果待确认,请重试原请求或查询原结果。', action: _jsx(Button, { disabled: submitting, loading: submitting, onClick: () => void sendRequest(true), children: "\u91CD\u8BD5\u539F\u8BF7\u6C42" }) }), refreshFailure && _jsx(Alert, { type: "warning", showIcon: true, title: refreshFailure.outcome === 'succeeded'
|
|
598
|
+
const content = surface.taskForm || commandNeedsRefresh || ((submitting || unknown) && !pendingLocator) || unknown || refreshFailure ? (_jsxs(_Fragment, { children: [commandNeedsRefresh && !unknown && !pendingLocator && !refreshFailure && _jsx(Alert, { type: "info", showIcon: true, title: "\u8BF7\u5237\u65B0\u64CD\u4F5C\u540E\u7EE7\u7EED\u529E\u7406", description: "\u9875\u9762\u505C\u7559\u8F83\u4E45\uFF0C\u9700\u91CD\u65B0\u786E\u8BA4\u5F53\u524D\u529E\u7406\u6743\u9650\u3002\u5237\u65B0\u4F1A\u4FDD\u7559\u5C1A\u672A\u4FDD\u5B58\u7684\u8F93\u5165\u3002", action: _jsx(Button, { disabled: locked, loading: submitting, onClick: () => void refreshConfirmed(), children: "\u5237\u65B0\u64CD\u4F5C" }) }), surface.taskForm && _jsx(WorkflowTaskForm, { controller: taskForm, disabled: locked, variant: variant, taskVersion: surface.task?.version ? Number(surface.task.version) : undefined, taskId: surface.task?.id ? String(surface.task.id) : undefined, draftDisabled: commandLocked, onRefresh: onRefresh, onDraftBusyChange: busy => { setDraftLocked(busy); onBusyChange(busy || fileLocked || busyRef.current); }, onFileBusyChange: busy => { setFileLocked(busy); onBusyChange(busy || draftLocked || busyRef.current); }, resourceCode: surface.presentation.businessDetail.resourceCode || undefined, recordId: surface.presentation.businessDetail.recordId || undefined }), (submitting || unknown) && !pendingLocator && _jsx(WorkflowPendingCommandGuard, {}), unknown && _jsx(Alert, { type: "warning", showIcon: true, title: "\u4FDD\u7559\u4E86\u539F\u63D0\u4EA4\u8BF7\u6C42", description: operationError || '提交结果待确认,请重试原请求或查询原结果。', action: _jsx(Button, { disabled: submitting, loading: submitting, onClick: () => void sendRequest(true), children: "\u91CD\u8BD5\u539F\u8BF7\u6C42" }) }), refreshFailure && _jsx(Alert, { type: "warning", showIcon: true, title: refreshFailure.outcome === 'succeeded'
|
|
596
599
|
? '任务操作已成功,但资料刷新失败' : '本次未提交,最新资料读取失败', description: refreshFailure.message, action: _jsx(Button, { disabled: submitting, onClick: () => void refreshConfirmed(), children: "\u5237\u65B0\u8D44\u6599" }) })] })) : null;
|
|
597
|
-
const actions = (_jsxs(_Fragment, { children: [_jsxs("div", { className: `oxa-workflow-actions oxa-workflow-actions-${variant}`, children: [primary.map((operation) => (_jsx(Button, { danger: operation.emphasis === 'danger', disabled: locked || taskForm.stale || taskForm.draftNeedsSave || !operation.enabled, onClick: () => selectOperation(operation), title: operation.disabledReason, type: operation.emphasis === 'primary' ? 'primary' : 'default', children: operation.label }, operation.key))), secondary.length > 0 && (_jsx(Button, { className: "oxa-workflow-more-trigger", disabled: locked || taskForm.stale || taskForm.draftNeedsSave, icon: _jsx(EllipsisOutlined, {}), onClick: () => setMoreOpen((value) => !value), children: "\u66F4\u591A\u64CD\u4F5C" })), secondary.length > 0 && moreOpen && (_jsx("div", { className: "oxa-workflow-more-actions", children: secondary.map((operation) => (_jsx(Button, { disabled: locked || taskForm.stale || taskForm.draftNeedsSave || !operation.enabled, onClick: () => {
|
|
600
|
+
const actions = (_jsxs(_Fragment, { children: [_jsxs("div", { className: `oxa-workflow-actions oxa-workflow-actions-${variant}`, children: [primary.map((operation) => (_jsx(Button, { danger: operation.emphasis === 'danger', disabled: locked || commandNeedsRefresh || taskForm.stale || taskForm.draftNeedsSave || !operation.enabled, onClick: () => selectOperation(operation), title: operation.disabledReason, type: operation.emphasis === 'primary' ? 'primary' : 'default', children: operation.label }, operation.key))), secondary.length > 0 && (_jsx(Button, { className: "oxa-workflow-more-trigger", disabled: locked || commandNeedsRefresh || taskForm.stale || taskForm.draftNeedsSave, icon: _jsx(EllipsisOutlined, {}), onClick: () => setMoreOpen((value) => !value), children: "\u66F4\u591A\u64CD\u4F5C" })), secondary.length > 0 && moreOpen && (_jsx("div", { className: "oxa-workflow-more-actions", children: secondary.map((operation) => (_jsx(Button, { disabled: locked || commandNeedsRefresh || taskForm.stale || taskForm.draftNeedsSave || !operation.enabled, onClick: () => {
|
|
598
601
|
setMoreOpen(false);
|
|
599
602
|
selectOperation(operation);
|
|
600
|
-
}, type: "text", title: operation.disabledReason, children: operation.label }, operation.key))) }))] }), _jsx(OperationDialog, { error: operationError, onCancel: () => setSelectedState(null), onSubmit: (values) => void submit(values), operation: selected, submitting: submitting, variant: variant })] }));
|
|
603
|
+
}, type: "text", title: operation.disabledReason, children: operation.label }, operation.key))) }))] }), _jsx(OperationDialog, { error: operationError, onCancel: () => { setRetainRefusedInput(false); setSelectedState(null); }, onSubmit: (values) => void submit(values), operation: selected, submitting: submitting, variant: variant })] }));
|
|
601
604
|
return renderLayout({ content, actions });
|
|
602
605
|
}
|
|
603
606
|
/**
|
|
@@ -935,7 +938,8 @@ function StandardWorkflowDetailRenderer({ surface, timeline, warning, operations
|
|
|
935
938
|
const titleField = workflowDetailGroups(business).flatMap(group => group.fields).find(field => field.type === 'text.short');
|
|
936
939
|
const title = titleField && business.record[titleField.key] ? String(business.record[titleField.key]) : summary.title;
|
|
937
940
|
const activeNode = timeline?.display?.entries.find(entry => entry.status === 'active');
|
|
938
|
-
const
|
|
941
|
+
const activeFlow = activeNode && timeline?.flow.find(entry => entry.key === activeNode.key && entry.status === 'active');
|
|
942
|
+
const people = activeFlow?.assignees.filter(person => person.status === 'active').map(person => person.displayName).filter(Boolean).join('、');
|
|
939
943
|
const statusTone = workflowStatus(instance.status).color;
|
|
940
944
|
const bannerTone = statusTone === 'error' ? 'error' : 'active';
|
|
941
945
|
const edit = workflowHasEnded(instance) ? onEdit : undefined;
|
|
@@ -1239,7 +1243,7 @@ async function workflowContextPrefillValue(field, rawValue, resources) {
|
|
|
1239
1243
|
}
|
|
1240
1244
|
return workflowContextScalarValue(field, value);
|
|
1241
1245
|
}
|
|
1242
|
-
export function WorkflowSubmissionPage({ instancePath, workflowCode: declaredWorkflowCode, variant = 'desktop', onDismiss, onCompleted, } = {}) {
|
|
1246
|
+
export function WorkflowSubmissionPage({ instancePath, workflowCode: declaredWorkflowCode, variant = 'desktop', onDismiss, onCompleted, formOptions, } = {}) {
|
|
1243
1247
|
const { workflowCode: routeWorkflowCode = '' } = useParams();
|
|
1244
1248
|
const workflowCode = declaredWorkflowCode || routeWorkflowCode;
|
|
1245
1249
|
const definition = useWorkflowDefinition(workflowCode);
|
|
@@ -1250,6 +1254,9 @@ export function WorkflowSubmissionPage({ instancePath, workflowCode: declaredWor
|
|
|
1250
1254
|
const { message } = App.useApp();
|
|
1251
1255
|
const [subjectForm] = Form.useForm();
|
|
1252
1256
|
const [requirementForm] = Form.useForm();
|
|
1257
|
+
const watchedFormValues = Form.useWatch([], { form: subjectForm, preserve: true });
|
|
1258
|
+
const [prefillError, setPrefillError] = useState(false);
|
|
1259
|
+
const prefill = useRef({ context: '', applied: new Set() });
|
|
1253
1260
|
const [loading, setLoading] = useState(false);
|
|
1254
1261
|
const [launchSurface, setLaunchSurface] = useState(null);
|
|
1255
1262
|
const [launchError, setLaunchError] = useState(null);
|
|
@@ -1342,6 +1349,41 @@ export function WorkflowSubmissionPage({ instancePath, workflowCode: declaredWor
|
|
|
1342
1349
|
namedIntent,
|
|
1343
1350
|
subjectDefinition,
|
|
1344
1351
|
]);
|
|
1352
|
+
const formProjection = useMemo(() => {
|
|
1353
|
+
try {
|
|
1354
|
+
const values = subjectDefinition ? normalizeFormValues(watchedFormValues || {}, subjectDefinition.surface) : {};
|
|
1355
|
+
return { ...workflowSubmissionFormProjection(fields, values, formOptions?.fieldState?.(values)), error: false };
|
|
1356
|
+
}
|
|
1357
|
+
catch {
|
|
1358
|
+
return { fields, values: {}, hiddenValues: {}, error: true };
|
|
1359
|
+
}
|
|
1360
|
+
}, [fields, formOptions?.fieldState, subjectDefinition, watchedFormValues]);
|
|
1361
|
+
const prefillContext = JSON.stringify([recoveryScope, identity.environment.activeAppVersionId, submissionMode, subjectId]);
|
|
1362
|
+
useEffect(() => {
|
|
1363
|
+
if (!launchSurface || commandId || pendingSubmission || formOptions?.preparation || mutationMode !== 'create' || !subjectDefinition ||
|
|
1364
|
+
launchSurface.environmentId !== identity.environment.id || (generatedNamedSubmission && !namedIntent))
|
|
1365
|
+
return;
|
|
1366
|
+
if (prefill.current.context !== prefillContext)
|
|
1367
|
+
prefill.current = { context: prefillContext, applied: new Set() };
|
|
1368
|
+
try {
|
|
1369
|
+
const values = workflowSubmissionPrefill(fields, formOptions?.initialValues || {}, prefill.current.applied, key => subjectForm.isFieldTouched(key));
|
|
1370
|
+
const normalized = normalizeRecordForForm(values, subjectDefinition.surface);
|
|
1371
|
+
subjectForm.setFields(Object.entries(normalized).map(([name, value]) => ({ name, value, touched: false })));
|
|
1372
|
+
setPrefillError(false);
|
|
1373
|
+
}
|
|
1374
|
+
catch {
|
|
1375
|
+
setPrefillError(true);
|
|
1376
|
+
}
|
|
1377
|
+
}, [commandId, fields, formOptions?.initialValues, formOptions?.preparation, generatedNamedSubmission, identity.environment.id,
|
|
1378
|
+
launchSurface, mutationMode, namedIntent, pendingSubmission, prefillContext, subjectDefinition, subjectForm]);
|
|
1379
|
+
useEffect(() => {
|
|
1380
|
+
if (loading || commandId || pendingSubmission || !launchSurface || formProjection.error || !subjectDefinition)
|
|
1381
|
+
return;
|
|
1382
|
+
const values = normalizeRecordForForm(formProjection.hiddenValues, subjectDefinition.surface);
|
|
1383
|
+
const changes = Object.entries(values).filter(([key, value]) => JSON.stringify(subjectForm.getFieldValue(key)) !== JSON.stringify(value));
|
|
1384
|
+
if (changes.length)
|
|
1385
|
+
subjectForm.setFields(changes.map(([name, value]) => ({ name, value, errors: [] })));
|
|
1386
|
+
}, [commandId, formProjection, launchSurface, loading, pendingSubmission, subjectDefinition, subjectForm]);
|
|
1345
1387
|
useEffect(() => {
|
|
1346
1388
|
let active = true;
|
|
1347
1389
|
setLaunchSurface(null);
|
|
@@ -1676,6 +1718,8 @@ export function WorkflowSubmissionPage({ instancePath, workflowCode: declaredWor
|
|
|
1676
1718
|
: '当前部署版本未声明 launch 配置;请升级工具链后为 workflows.definitions[].launch 显式声明 mode' }));
|
|
1677
1719
|
if (!subjectDefinition)
|
|
1678
1720
|
return frame(_jsx(Result, { status: "500", title: "\u6807\u51C6\u6D41\u7A0B\u5408\u540C\u4E0D\u5B8C\u6574" }));
|
|
1721
|
+
if (!commandId && formOptions?.preparation)
|
|
1722
|
+
return frame(formOptions.preparation);
|
|
1679
1723
|
if (launchError && !commandId)
|
|
1680
1724
|
return frame(_jsx(Result, { status: "error", title: "\u53D1\u8D77\u9875\u9762\u5F53\u524D\u4E0D\u53EF\u7528", subTitle: launchError }));
|
|
1681
1725
|
if (!launchSurface && !commandId)
|
|
@@ -1691,11 +1735,11 @@ export function WorkflowSubmissionPage({ instancePath, workflowCode: declaredWor
|
|
|
1691
1735
|
launchSurface?.submission.kind !== 'standard-process')) {
|
|
1692
1736
|
return frame(_jsx(Result, { status: "500", title: "\u6807\u51C6\u6D41\u7A0B\u5408\u540C\u4E0D\u5B8C\u6574" }));
|
|
1693
1737
|
}
|
|
1694
|
-
if (!commandId && fields.some(field => field.type === 'subtable')) {
|
|
1738
|
+
if (!commandId && namedIntent && fields.some(field => field.type === 'subtable')) {
|
|
1695
1739
|
return frame(_jsx(Result, { status: "error", title: "\u6807\u51C6\u6D41\u7A0B\u4E0D\u652F\u6301\u5305\u542B\u53EF\u5199\u5B50\u8868\u7684\u4E3B\u4F53\u8868\u5355", subTitle: "\u5F53\u524D\u6807\u51C6\u63D0\u4EA4 Surface \u5C1A\u672A\u58F0\u660E\u53EF\u5199\u5B50\u8868\u6E32\u67D3\u5668\u3002" }));
|
|
1696
1740
|
}
|
|
1697
1741
|
const submit = async (values) => {
|
|
1698
|
-
if (submitInFlight.current || commandId || completion || !launchSurface)
|
|
1742
|
+
if (submitInFlight.current || commandId || completion || !launchSurface || formOptions?.preparation || prefillError || formProjection.error)
|
|
1699
1743
|
return;
|
|
1700
1744
|
const unresolved = readPendingWorkflowSubmission(submissionLocatorStorage(), recoveryScope);
|
|
1701
1745
|
if (pendingSubmission || unresolved) {
|
|
@@ -1715,8 +1759,9 @@ export function WorkflowSubmissionPage({ instancePath, workflowCode: declaredWor
|
|
|
1715
1759
|
setRecoveryObservedAbsent(false);
|
|
1716
1760
|
};
|
|
1717
1761
|
try {
|
|
1718
|
-
const encoded = normalizeFormValues(values, subjectDefinition.surface)
|
|
1719
|
-
|
|
1762
|
+
const encoded = namedIntent ? normalizeFormValues(values, subjectDefinition.surface)
|
|
1763
|
+
: standardProcessFormValues(values, subjectDefinition.surface, resources, (field, mode) => fieldWritable(field, mode === 'create' ? 'create' : 'edit', hasCapability, identity.isAppSuperAdmin));
|
|
1764
|
+
const data = workflowSubmissionFormProjection(fields, encoded, formOptions?.fieldState?.(encoded)).values;
|
|
1720
1765
|
const signature = JSON.stringify({ workflowCode, subjectId, environmentKey: identity.environment.key, submissionMode, data });
|
|
1721
1766
|
if (submissionAttempt.current?.signature !== signature) {
|
|
1722
1767
|
submissionAttempt.current = { signature, idempotencyKey: randomId(`process:${workflowCode}`), requestedAt: new Date().toISOString() };
|
|
@@ -1904,6 +1949,7 @@ export function WorkflowSubmissionPage({ instancePath, workflowCode: declaredWor
|
|
|
1904
1949
|
const uploadOperationCode = namedIntent?.operationCode || definition.processOperationCode;
|
|
1905
1950
|
const fieldRenderers = uploadOperationCode
|
|
1906
1951
|
? {
|
|
1952
|
+
...(!namedIntent ? { renderSubtable: ({ field, disabled, operation, recordId }) => _jsx(SubtableField, { field: field, disabled: disabled, operation: operation, parentRecordId: recordId, mobile: variant === 'mobile' }) } : {}),
|
|
1907
1953
|
...(namedIntent ? { referenceLaunch: { workflowCode: definition.code, operationCode: namedIntent.operationCode } } : {}),
|
|
1908
1954
|
upload: async (field, file) => await uploadOperationManagedFile({
|
|
1909
1955
|
operationCode: uploadOperationCode,
|
|
@@ -1928,7 +1974,7 @@ export function WorkflowSubmissionPage({ instancePath, workflowCode: declaredWor
|
|
|
1928
1974
|
(namedIntent
|
|
1929
1975
|
? '业务操作将在服务端完成校验、幂等提交,并按规则决定是否进入审批'
|
|
1930
1976
|
: '业务数据和流程发起意图将原子提交'),
|
|
1931
|
-
fields,
|
|
1977
|
+
fields: formProjection.fields,
|
|
1932
1978
|
subjectDefinition,
|
|
1933
1979
|
subjectForm,
|
|
1934
1980
|
requirementForm,
|
|
@@ -1942,7 +1988,10 @@ export function WorkflowSubmissionPage({ instancePath, workflowCode: declaredWor
|
|
|
1942
1988
|
completion,
|
|
1943
1989
|
embedded: Boolean(onDismiss),
|
|
1944
1990
|
fieldRenderers,
|
|
1991
|
+
formIntro: formOptions?.intro,
|
|
1992
|
+
formError: prefillError || formProjection.error ? '表单规则暂不可用,请联系管理员。' : undefined,
|
|
1945
1993
|
recordId: mutationMode === 'update' ? subjectId : undefined,
|
|
1994
|
+
expectedRevision: mutationMode === 'update' ? loadedSubjectRevision : undefined,
|
|
1946
1995
|
onBack: onDismiss ? dismissDrawer : () => navigate(-1),
|
|
1947
1996
|
onSubmit: submit,
|
|
1948
1997
|
onAnswer: answer,
|
|
@@ -1971,7 +2020,7 @@ function StandardProcessSubmissionRenderer(props) {
|
|
|
1971
2020
|
}, new Map())].map(([section, fields]) => ({ section, fields }));
|
|
1972
2021
|
if (props.completion)
|
|
1973
2022
|
return _jsx(Result, { status: "success", title: "\u63D0\u4EA4\u6210\u529F", extra: _jsx(Button, { onClick: props.onBack, children: "\u8FD4\u56DE" }) });
|
|
1974
|
-
return _jsxs("div", { className: props.variant === 'mobile' ? 'oxa-mobile-page oxa-mobile-entry oxa-workflow-submission-mobile' : 'oxa-workflow-entry', children: [!props.embedded && _jsxs("header", { className: props.variant === 'mobile' ? 'oxa-mobile-header' : 'oxa-workflow-entry-header', children: [_jsx(Button, { type: "text", "aria-label": "\u8FD4\u56DE", icon: _jsx(ArrowLeftOutlined, {}), disabled: props.processing, onClick: props.onBack }), _jsx("h3", { children: props.title }), _jsx("span", {})] }), _jsx(ResourceFormContent, { variant: props.variant, mode: props.mutationMode === 'update' ? 'edit' : 'create', resourceCode: props.subjectDefinition.code, recordId: props.recordId, groups: groups, form: props.subjectForm, busy: props.loading || props.submitted, pending: props.loading || props.processing, submitDisabled: props.submitted, submitLabel: "\u63D0\u4EA4\u5BA1\u6279", canWriteField: () => true, renderers: props.fieldRenderers, feedback: _jsxs(_Fragment, { children: [props.launchControls, props.processing && _jsx(Alert, { type: "info", showIcon: true, title: "\u6B63\u5728\u63D0\u4EA4\u7533\u8BF7\uFF0C\u8BF7\u7A0D\u5019\u2026" })] }), onSubmit: values => void props.onSubmit(values) }), _jsx(ProcessCommandPanel, { error: props.processError, form: props.requirementForm, loading: props.loading, onAnswer: props.onAnswer, onRetry: props.onRetry, onRefresh: props.onRefresh, surface: props.processSurface })] });
|
|
2023
|
+
return _jsxs("div", { className: props.variant === 'mobile' ? 'oxa-mobile-page oxa-mobile-entry oxa-workflow-submission-mobile' : 'oxa-workflow-entry', children: [!props.embedded && _jsxs("header", { className: props.variant === 'mobile' ? 'oxa-mobile-header' : 'oxa-workflow-entry-header', children: [_jsx(Button, { type: "text", "aria-label": "\u8FD4\u56DE", icon: _jsx(ArrowLeftOutlined, {}), disabled: props.processing, onClick: props.onBack }), _jsx("h3", { children: props.title }), _jsx("span", {})] }), _jsx(ResourceFormContent, { variant: props.variant, mode: props.mutationMode === 'update' ? 'edit' : 'create', resourceCode: props.subjectDefinition.code, recordId: props.recordId, groups: groups, expectedRevision: props.expectedRevision, initialValues: props.mutationMode === 'update' ? undefined : Object.fromEntries(props.fields.filter(field => field.type === 'user.multiple').map(field => [field.key, []])), form: props.subjectForm, busy: props.loading || props.submitted, pending: props.loading || props.processing, submitDisabled: props.submitted || Boolean(props.formError), submitLabel: "\u63D0\u4EA4\u5BA1\u6279", canWriteField: () => true, renderers: props.fieldRenderers, feedback: _jsxs(_Fragment, { children: [props.formIntro, props.launchControls, props.formError && _jsx(Alert, { type: "error", showIcon: true, title: props.formError }), props.processing && _jsx(Alert, { type: "info", showIcon: true, title: "\u6B63\u5728\u63D0\u4EA4\u7533\u8BF7\uFF0C\u8BF7\u7A0D\u5019\u2026" })] }), onSubmit: values => void props.onSubmit(values) }), _jsx(ProcessCommandPanel, { error: props.processError, form: props.requirementForm, loading: props.loading, onAnswer: props.onAnswer, onRetry: props.onRetry, onRefresh: props.onRefresh, surface: props.processSurface })] });
|
|
1975
2024
|
}
|
|
1976
2025
|
function DesktopProcessSubmissionRenderer(props) { return _jsx(StandardProcessSubmissionRenderer, { ...props, variant: "desktop" }); }
|
|
1977
2026
|
function MobileProcessSubmissionRenderer(props) { return _jsx(StandardProcessSubmissionRenderer, { ...props, variant: "mobile" }); }
|