@rytass/bpm-core-react 0.10.0 → 0.12.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (177) hide show
  1. package/CHANGELOG.md +55 -0
  2. package/dist/chunks/FormBuilderView-CLFlfDGe.cjs +3 -0
  3. package/dist/chunks/FormBuilderView-CLFlfDGe.cjs.map +1 -0
  4. package/dist/chunks/FormBuilderView-D4xIuPYB.js +1960 -0
  5. package/dist/chunks/FormBuilderView-D4xIuPYB.js.map +1 -0
  6. package/dist/chunks/FormRendererView-BxGT16z0.cjs +2 -0
  7. package/dist/chunks/FormRendererView-BxGT16z0.cjs.map +1 -0
  8. package/dist/chunks/FormRendererView-DUceSOXe.js +798 -0
  9. package/dist/chunks/FormRendererView-DUceSOXe.js.map +1 -0
  10. package/dist/chunks/admin-pickers-Btvij1at.cjs.map +1 -1
  11. package/dist/chunks/admin-pickers-DLlG_1du.js.map +1 -1
  12. package/dist/chunks/approval-instance-list-page-BjX2kaoF.js.map +1 -1
  13. package/dist/chunks/approval-instance-list-page-CWiQvnfE.cjs +2 -0
  14. package/dist/chunks/{approval-instance-list-page-C408vxE2.cjs.map → approval-instance-list-page-CWiQvnfE.cjs.map} +1 -1
  15. package/dist/chunks/auth-provider-4BeCw7cI.cjs.map +1 -1
  16. package/dist/chunks/auth-provider-B5oPmvk2.js.map +1 -1
  17. package/dist/chunks/bpm-form-field-Bc6k4ZEO.cjs.map +1 -1
  18. package/dist/chunks/categories-DGlxuC6X.js.map +1 -1
  19. package/dist/chunks/categories-Yid05WAX.cjs +2 -0
  20. package/dist/chunks/{categories-DUfldZ_9.cjs.map → categories-Yid05WAX.cjs.map} +1 -1
  21. package/dist/chunks/{compose-D-OS-Ngs.js → compose-Bb-REfoB.js} +4 -4
  22. package/dist/chunks/{compose-D-OS-Ngs.js.map → compose-Bb-REfoB.js.map} +1 -1
  23. package/dist/chunks/compose-DzRYZcqe.cjs +2 -0
  24. package/dist/chunks/{compose-CODnd9-2.cjs.map → compose-DzRYZcqe.cjs.map} +1 -1
  25. package/dist/chunks/dashboard-page-CH87L5nx.cjs +2 -0
  26. package/dist/chunks/{dashboard-page-DwHQY6Ki.cjs.map → dashboard-page-CH87L5nx.cjs.map} +1 -1
  27. package/dist/chunks/dashboard-page-DJ9vOPga.js.map +1 -1
  28. package/dist/chunks/{delegations-DLEEFBlH.js → delegations-0MbJ7CWj.js} +3 -2
  29. package/dist/chunks/{delegations-DLEEFBlH.js.map → delegations-0MbJ7CWj.js.map} +1 -1
  30. package/dist/chunks/delegations-Bc9psOZ3.cjs +2 -0
  31. package/dist/chunks/{delegations-CGj-tZNO.cjs.map → delegations-Bc9psOZ3.cjs.map} +1 -1
  32. package/dist/chunks/{delegations-DqMpI_Nk.js → delegations-DyMGIDpp.js} +3 -2
  33. package/dist/chunks/{delegations-DqMpI_Nk.js.map → delegations-DyMGIDpp.js.map} +1 -1
  34. package/dist/chunks/delegations-vpLtus9g.cjs +2 -0
  35. package/dist/chunks/{delegations-kbMOSEif.cjs.map → delegations-vpLtus9g.cjs.map} +1 -1
  36. package/dist/chunks/{designer-DDSxwtjV.js → designer-C6oIO9Kq.js} +39 -30
  37. package/dist/chunks/{designer-DDSxwtjV.js.map → designer-C6oIO9Kq.js.map} +1 -1
  38. package/dist/chunks/designer-gFUdImeZ.cjs +65 -0
  39. package/dist/chunks/{designer-Cdn10NNl.cjs.map → designer-gFUdImeZ.cjs.map} +1 -1
  40. package/dist/chunks/{detail-DAPz2qyn.js → detail-BgKgMvYx.js} +392 -391
  41. package/dist/chunks/{detail-DAPz2qyn.js.map → detail-BgKgMvYx.js.map} +1 -1
  42. package/dist/chunks/detail-Dnz5aaI-.cjs +2 -0
  43. package/dist/chunks/{detail-CtVu5NTi.cjs.map → detail-Dnz5aaI-.cjs.map} +1 -1
  44. package/dist/chunks/format-date-time-CB-LxzqT.js.map +1 -1
  45. package/dist/chunks/format-date-time-D-cx5M8z.cjs +2 -0
  46. package/dist/chunks/{format-date-time-XxBzF0F5.cjs.map → format-date-time-D-cx5M8z.cjs.map} +1 -1
  47. package/dist/chunks/login-9bCXyjbX.cjs.map +1 -1
  48. package/dist/chunks/login-BKxpLibd.js.map +1 -1
  49. package/dist/chunks/notifications-Bc4mgSds.cjs +2 -0
  50. package/dist/chunks/{notifications--hwl-DR0.cjs.map → notifications-Bc4mgSds.cjs.map} +1 -1
  51. package/dist/chunks/notifications-DJ5wzCye.js.map +1 -1
  52. package/dist/chunks/{orgs-DytLvZ_X.js → orgs-B930facb.js} +11 -10
  53. package/dist/chunks/{orgs-DytLvZ_X.js.map → orgs-B930facb.js.map} +1 -1
  54. package/dist/chunks/orgs-BefGgeyc.cjs +2 -0
  55. package/dist/chunks/{orgs-Ni22buHs.cjs.map → orgs-BefGgeyc.cjs.map} +1 -1
  56. package/dist/chunks/providers-BsEn3ikK.cjs +2 -0
  57. package/dist/chunks/{providers-D_zTbkQH.cjs.map → providers-BsEn3ikK.cjs.map} +1 -1
  58. package/dist/chunks/{providers-DEqcuXw9.js → providers-DjLh4oLY.js} +3 -3
  59. package/dist/chunks/{providers-DEqcuXw9.js.map → providers-DjLh4oLY.js.map} +1 -1
  60. package/dist/chunks/{chunk-CMqjfN_6.cjs → rolldown-runtime-BocRIvOZ.cjs} +1 -1
  61. package/dist/chunks/router-adapter--gYs13E8.cjs.map +1 -1
  62. package/dist/chunks/routes-config-fDVHmvXi.cjs.map +1 -1
  63. package/dist/chunks/users-C9LA-Rd7.cjs +2 -0
  64. package/dist/chunks/{users-0HqlM_VQ.cjs.map → users-C9LA-Rd7.cjs.map} +1 -1
  65. package/dist/chunks/users-FWrb3ehW.js.map +1 -1
  66. package/dist/index.cjs +1 -1
  67. package/dist/index.cjs.map +1 -1
  68. package/dist/index.js +1 -1
  69. package/dist/index.js.map +1 -1
  70. package/dist/next/index.cjs +1 -1
  71. package/dist/next/index.cjs.map +1 -1
  72. package/dist/next/index.js +9 -9
  73. package/dist/next/index.js.map +1 -1
  74. package/dist/next/workflow-chat-route.cjs +1 -1
  75. package/dist/next/workflow-chat-route.cjs.map +1 -1
  76. package/dist/next/workflow-chat-route.js +2 -1
  77. package/dist/next/workflow-chat-route.js.map +1 -1
  78. package/dist/pages/admin/delegations/index.cjs +1 -1
  79. package/dist/pages/admin/delegations/index.cjs.map +1 -1
  80. package/dist/pages/admin/delegations/index.js +1 -1
  81. package/dist/pages/admin/orgs/index.cjs +1 -1
  82. package/dist/pages/admin/orgs/index.cjs.map +1 -1
  83. package/dist/pages/admin/orgs/index.js +1 -1
  84. package/dist/pages/admin/users/index.cjs +1 -1
  85. package/dist/pages/admin/users/index.cjs.map +1 -1
  86. package/dist/pages/cc/index.cjs.map +1 -1
  87. package/dist/pages/dashboard/index.cjs.map +1 -1
  88. package/dist/pages/delegations/index.cjs +1 -1
  89. package/dist/pages/delegations/index.cjs.map +1 -1
  90. package/dist/pages/delegations/index.js +1 -1
  91. package/dist/pages/inbox/index.cjs.map +1 -1
  92. package/dist/pages/instances/detail/index.cjs +1 -1
  93. package/dist/pages/instances/detail/index.cjs.map +1 -1
  94. package/dist/pages/instances/detail/index.js +1 -1
  95. package/dist/pages/instances/new/index.cjs.map +1 -1
  96. package/dist/pages/login/index.cjs.map +1 -1
  97. package/dist/pages/root/index.cjs.map +1 -1
  98. package/dist/pages/search/index.cjs.map +1 -1
  99. package/dist/pages/sent/index.cjs.map +1 -1
  100. package/dist/pages/settings/notifications/index.cjs +1 -1
  101. package/dist/pages/settings/notifications/index.cjs.map +1 -1
  102. package/dist/pages/templates/categories/index.cjs +1 -1
  103. package/dist/pages/templates/categories/index.cjs.map +1 -1
  104. package/dist/pages/templates/compose/index.cjs +1 -1
  105. package/dist/pages/templates/compose/index.cjs.map +1 -1
  106. package/dist/pages/templates/compose/index.js +1 -1
  107. package/dist/pages/templates/designer/index.cjs +1 -1
  108. package/dist/pages/templates/designer/index.cjs.map +1 -1
  109. package/dist/pages/templates/designer/index.js +1 -1
  110. package/dist/pages/templates/index.cjs.map +1 -1
  111. package/dist/pages/templates/versions/index.cjs.map +1 -1
  112. package/dist/views/admin/delegations/index.cjs +1 -1
  113. package/dist/views/admin/delegations/index.js +1 -1
  114. package/dist/views/admin/index.cjs +1 -1
  115. package/dist/views/admin/index.js +2 -2
  116. package/dist/views/admin/orgs/index.cjs +1 -1
  117. package/dist/views/admin/orgs/index.js +1 -1
  118. package/dist/views/admin/users/index.cjs +1 -1
  119. package/dist/views/cc/index.cjs +1 -1
  120. package/dist/views/cc/index.cjs.map +1 -1
  121. package/dist/views/dashboard/index.cjs +1 -1
  122. package/dist/views/dashboard/index.cjs.map +1 -1
  123. package/dist/views/delegations/index.cjs +1 -1
  124. package/dist/views/delegations/index.js +1 -1
  125. package/dist/views/forms/builder/index.cjs +1 -1
  126. package/dist/views/forms/builder/index.js +1 -1
  127. package/dist/views/forms/renderer/form-data-source-field.d.ts +16 -0
  128. package/dist/views/forms/renderer/index.cjs +1 -1
  129. package/dist/views/forms/renderer/index.js +1 -1
  130. package/dist/views/inbox/index.cjs +1 -1
  131. package/dist/views/inbox/index.cjs.map +1 -1
  132. package/dist/views/inbox/index.js.map +1 -1
  133. package/dist/views/instances/detail/index.cjs +1 -1
  134. package/dist/views/instances/detail/index.js +1 -1
  135. package/dist/views/instances/new/index.cjs +1 -1
  136. package/dist/views/instances/new/index.cjs.map +1 -1
  137. package/dist/views/instances/new/index.js +48 -48
  138. package/dist/views/instances/new/index.js.map +1 -1
  139. package/dist/views/search/index.cjs +1 -1
  140. package/dist/views/search/index.cjs.map +1 -1
  141. package/dist/views/sent/index.cjs +1 -1
  142. package/dist/views/sent/index.cjs.map +1 -1
  143. package/dist/views/settings/index.cjs +1 -1
  144. package/dist/views/settings/notifications/index.cjs +1 -1
  145. package/dist/views/templates/categories/index.cjs +1 -1
  146. package/dist/views/templates/compose/index.cjs +1 -1
  147. package/dist/views/templates/compose/index.js +1 -1
  148. package/dist/views/templates/designer/index.cjs +1 -1
  149. package/dist/views/templates/designer/index.js +1 -1
  150. package/dist/views/templates/index.cjs +1 -1
  151. package/dist/views/templates/index.cjs.map +1 -1
  152. package/dist/views/templates/index.js.map +1 -1
  153. package/dist/views/templates/versions/index.cjs +1 -1
  154. package/dist/views/templates/versions/index.cjs.map +1 -1
  155. package/dist/views/templates/versions/index.js.map +1 -1
  156. package/package.json +3 -3
  157. package/dist/chunks/FormBuilderView-D6baVqBY.cjs +0 -3
  158. package/dist/chunks/FormBuilderView-D6baVqBY.cjs.map +0 -1
  159. package/dist/chunks/FormBuilderView-QtREqV4j.js +0 -1477
  160. package/dist/chunks/FormBuilderView-QtREqV4j.js.map +0 -1
  161. package/dist/chunks/FormRendererView-Cw9LiidV.cjs +0 -2
  162. package/dist/chunks/FormRendererView-Cw9LiidV.cjs.map +0 -1
  163. package/dist/chunks/FormRendererView-D8QHLvd0.js +0 -577
  164. package/dist/chunks/FormRendererView-D8QHLvd0.js.map +0 -1
  165. package/dist/chunks/approval-instance-list-page-C408vxE2.cjs +0 -2
  166. package/dist/chunks/categories-DUfldZ_9.cjs +0 -2
  167. package/dist/chunks/compose-CODnd9-2.cjs +0 -2
  168. package/dist/chunks/dashboard-page-DwHQY6Ki.cjs +0 -2
  169. package/dist/chunks/delegations-CGj-tZNO.cjs +0 -2
  170. package/dist/chunks/delegations-kbMOSEif.cjs +0 -2
  171. package/dist/chunks/designer-Cdn10NNl.cjs +0 -65
  172. package/dist/chunks/detail-CtVu5NTi.cjs +0 -2
  173. package/dist/chunks/format-date-time-XxBzF0F5.cjs +0 -2
  174. package/dist/chunks/notifications--hwl-DR0.cjs +0 -2
  175. package/dist/chunks/orgs-Ni22buHs.cjs +0 -2
  176. package/dist/chunks/providers-D_zTbkQH.cjs +0 -2
  177. package/dist/chunks/users-0HqlM_VQ.cjs +0 -2
@@ -1 +0,0 @@
1
- {"version":3,"file":"FormRendererView-D8QHLvd0.js","names":[],"sources":["../../src/views/forms/renderer/form-data-source-field.ts","../../src/views/forms/renderer/FormRendererView.tsx"],"sourcesContent":["'use client';\n\nimport { useCallback, useEffect, useMemo, useRef, useState } from 'react';\nimport {\n FormDataSourceValueSnapshots,\n FormDefinitionSchema,\n FormFieldDefinition,\n FormFieldOption,\n FormFieldValue,\n FormUiSchema,\n isFormDataSourceFieldDefinition,\n} from '@rytass/bpm-core-shared/form';\nimport {\n FormDataSourceErrorCode,\n FormDataSourceFieldStatus,\n FormRendererValues,\n mergeFormDataSourceOptions,\n previewResolveFormFieldOptions,\n readFormDataSourceErrorCode,\n readFormDataSourceErrorMessage,\n readMissingFormDataSourceDependencies,\n readMissingFormDataSourceOptionValues,\n previewFormFieldOptions,\n readFormDataSourceSelectedValues,\n readFormDataSourceValueSignature,\n readSelectedFormDataSourceOptions,\n readFormFieldOptions,\n resolveFormFieldOptions,\n} from '@rytass/bpm-core-client/form';\n\nexport type FormRendererDataSourceContext =\n | { readonly kind: 'preview' }\n | {\n readonly instanceId?: string | null;\n readonly kind: 'runtime';\n readonly templateId?: string | null;\n };\n\nexport interface FormDataSourceFieldState {\n /**\n * False when nothing can be re-requested — a read-only or context-less field\n * has no query to retry, so the view must not offer a dead retry action.\n */\n readonly canRetry: boolean;\n readonly error: string | null;\n readonly hasValue: boolean;\n readonly hasNextPage: boolean;\n readonly invalidValues: readonly string[];\n readonly onReachBottom: () => void;\n readonly onSearch: (searchText: string) => void;\n readonly options: readonly FormFieldOption[];\n readonly retry: () => void;\n readonly status: FormDataSourceFieldStatus;\n}\n\nexport interface UseFormDataSourceFieldInput {\n readonly context?: FormRendererDataSourceContext;\n readonly field: FormFieldDefinition;\n readonly formData: FormRendererValues;\n readonly initialFormData?: FormRendererValues;\n readonly initialValue?: FormFieldValue | undefined;\n readonly optionSnapshots?: FormDataSourceValueSnapshots;\n readonly readonly: boolean;\n readonly schema: FormDefinitionSchema;\n readonly uiSchema: FormUiSchema;\n}\n\ninterface FormDataSourceResolution {\n readonly signature: string;\n readonly unresolvedValues: readonly string[];\n}\n\nconst EMPTY_FIELD_STATE: FormDataSourceFieldState = {\n canRetry: false,\n error: null,\n hasValue: false,\n hasNextPage: false,\n invalidValues: [],\n onReachBottom: (): void => undefined,\n onSearch: (): void => undefined,\n options: [],\n retry: (): void => undefined,\n status: 'IDLE',\n};\n\nconst NO_INVALID_VALUES: readonly string[] = [];\n\n/**\n * A dropdown only fires `onReachBottom` once its content overflows. A source\n * whose first page is smaller than the menu is therefore unreachable past page\n * one — `demo.cost-centers` serves 3 at a time, which fits exactly, so nothing\n * ever scrolls and the remaining options cannot be selected at all. Keep\n * pulling pages until there are enough rows to scroll, or the source runs out.\n */\nconst MIN_SCROLLABLE_OPTION_COUNT = 10;\n\n/**\n * Failures the filler can clear on their own by typing differently. They are\n * reported as an inline hint and never turn the field unavailable, because a\n * short search string says nothing about the validity of an existing value.\n */\nconst RECOVERABLE_ERROR_CODES: readonly FormDataSourceErrorCode[] = [\n 'FORM_DATA_SOURCE_SEARCH_NOT_SUPPORTED',\n 'FORM_DATA_SOURCE_SEARCH_TOO_SHORT',\n];\n\nexport function useFormDataSourceField(\n input: UseFormDataSourceFieldInput,\n): FormDataSourceFieldState {\n const dynamicField = isFormDataSourceFieldDefinition(input.field)\n ? input.field\n : null;\n const snapshot = dynamicField\n ? input.optionSnapshots?.[dynamicField.fieldKey]\n : undefined;\n // The field object is rebuilt on every parent render, so depending on its\n // identity re-ran the load effect three extra times per change — each request\n // aborting the last. Depend on what actually decides the query instead.\n const dynamicFieldSignature = dynamicField\n ? JSON.stringify({\n dataSource: dynamicField.dataSource,\n fieldKey: dynamicField.fieldKey,\n type: dynamicField.type,\n })\n : '';\n const snapshotSignature = JSON.stringify(snapshot ?? null);\n const snapshotOptions = useMemo(\n (): readonly FormFieldOption[] => snapshot?.options ?? [],\n [snapshotSignature],\n );\n const formDataSignature = JSON.stringify(input.formData);\n const initialFormDataSignature = JSON.stringify(input.initialFormData ?? {});\n const schemaSignature = JSON.stringify(input.schema);\n const uiSchemaSignature = JSON.stringify(input.uiSchema);\n const contextKind = input.context?.kind;\n const contextInstanceId =\n input.context?.kind === 'runtime' ? input.context.instanceId : undefined;\n const contextTemplateId =\n input.context?.kind === 'runtime' ? input.context.templateId : undefined;\n const currentValue = dynamicField\n ? input.formData[dynamicField.fieldKey]\n : undefined;\n const currentValueSignature = readFormDataSourceValueSignature(currentValue);\n const selectedValues = useMemo(\n (): readonly string[] => readFormDataSourceSelectedValues(currentValue),\n [currentValueSignature],\n );\n const hasValue = selectedValues.length > 0;\n const dataSourceRefreshSignature = dynamicField\n ? JSON.stringify({\n bindings: dynamicField.dataSource.bindings.map((binding) =>\n binding.from.kind === 'FIELD'\n ? {\n fieldKey: binding.from.fieldKey,\n value: input.formData[binding.from.fieldKey],\n }\n : { value: binding.from.value },\n ),\n value:\n typeof input.initialFormData !== 'undefined' ||\n typeof input.initialValue !== 'undefined'\n ? input.formData[dynamicField.fieldKey]\n : undefined,\n })\n : '';\n const effectiveContext = useMemo(\n (): FormRendererDataSourceContext | undefined => {\n if (contextKind === 'preview') {\n return { kind: 'preview' };\n }\n\n if (contextKind === 'runtime' && !input.readonly) {\n return {\n instanceId: contextInstanceId,\n kind: 'runtime',\n templateId: contextTemplateId,\n };\n }\n\n return undefined;\n },\n [\n contextInstanceId,\n contextKind,\n contextTemplateId,\n input.readonly,\n ],\n );\n const valueChanged = dynamicField\n ? (typeof input.initialFormData !== 'undefined' ||\n typeof input.initialValue !== 'undefined') &&\n readFormDataSourceValueSignature(input.initialValue) !==\n currentValueSignature\n : false;\n const bindingsChanged = dynamicField\n ? typeof input.initialFormData !== 'undefined' &&\n dynamicField.dataSource.bindings.some((binding) => {\n if (binding.from.kind !== 'FIELD') {\n return false;\n }\n\n return (\n readFormDataSourceValueSignature(\n input.initialFormData?.[binding.from.fieldKey],\n ) !==\n readFormDataSourceValueSignature(input.formData[binding.from.fieldKey])\n );\n })\n : false;\n const isStale = Boolean(\n (snapshot || hasValue) && (valueChanged || bindingsChanged),\n );\n // A stale field with a value is only trustworthy once the host has resolved\n // it: display options may still carry the value through the snapshot merge.\n const needsResolve = Boolean(dynamicField && effectiveContext && isStale && hasValue);\n const quiescentStatus = readQuiescentFormDataSourceStatus({\n hasSnapshot: Boolean(snapshot),\n hasValue,\n isStale,\n readonly: input.readonly,\n });\n // AutoComplete only queries on search, so every other control is the one that\n // loads by itself as soon as it has a context.\n const autoQueries = Boolean(\n dynamicField && effectiveContext && dynamicField.type !== 'autocomplete',\n );\n // Optimistic, and only until the first answer arrives: a binding pointing at\n // an empty field is usually blocking, and showing the control as usable for\n // one round trip would flash an enabled, empty list. AutoComplete is excluded\n // because nothing would ever correct the guess — it cannot be searched while\n // disabled, so an optional binding would lock it for good.\n const waitsForDependencies =\n autoQueries &&\n dynamicField !== null &&\n readMissingFormDataSourceDependencies(dynamicField, input.formData).length >\n 0;\n const pendingQueryStatus = readPendingQueryStatus(isStale, waitsForDependencies);\n const [remoteOptions, setRemoteOptions] = useState<readonly FormFieldOption[]>(\n [],\n );\n const [searchText, setSearchText] = useState('');\n const [nextCursor, setNextCursor] = useState<string | null>(null);\n const [resolution, setResolution] = useState<FormDataSourceResolution | null>(\n null,\n );\n const [status, setStatus] = useState<FormDataSourceFieldStatus>(\n (): FormDataSourceFieldStatus => {\n if (!dynamicField) {\n return 'IDLE';\n }\n\n // The very first paint already reflects the query the effect is about to\n // fire, so the control never appears usable before its options exist.\n return autoQueries ? pendingQueryStatus : quiescentStatus;\n },\n );\n const [error, setError] = useState<string | null>(null);\n const loadedOptionCount = useRef(0);\n const requestSequence = useRef(0);\n const resolveSequence = useRef(0);\n const optionsAbort = useRef<AbortController | null>(null);\n const resolveAbort = useRef<AbortController | null>(null);\n const lastRequest = useRef<{ readonly cursor: string | null; readonly searchText: string }>({\n cursor: null,\n searchText: '',\n });\n\n const queryFormData = useMemo(\n (): Readonly<Record<string, FormFieldValue>> =>\n Object.entries(input.formData).reduce<\n Readonly<Record<string, FormFieldValue>>\n >((values, [key, value]) => {\n if (typeof value === 'undefined') {\n return values;\n }\n\n return { ...values, [key]: value };\n }, {}),\n [formDataSignature],\n );\n const mergedOptions = useMemo(\n (): readonly FormFieldOption[] =>\n mergeFormDataSourceOptions(snapshotOptions, remoteOptions),\n [remoteOptions, snapshotOptions],\n );\n const currentResolution =\n resolution && resolution.signature === dataSourceRefreshSignature\n ? resolution\n : null;\n const resolvePending = needsResolve && !currentResolution;\n const invalidValues = readInvalidFormDataSourceValues({\n options: mergedOptions,\n resolution: currentResolution,\n resolvePending,\n value: currentValue,\n });\n\n const loadOptions = useCallback(\n (nextSearchTextToLoad: string, cursor: string | null): void => {\n if (!dynamicField || !effectiveContext) {\n return;\n }\n\n const requestId = requestSequence.current + 1;\n requestSequence.current = requestId;\n lastRequest.current = {\n cursor,\n searchText: nextSearchTextToLoad,\n };\n optionsAbort.current?.abort();\n const controller = new AbortController();\n optionsAbort.current = controller;\n setStatus(pendingQueryStatus);\n setError(null);\n\n const request =\n effectiveContext.kind === 'preview'\n ? previewFormFieldOptions({\n cursor,\n fieldKey: dynamicField.fieldKey,\n formData: queryFormData,\n schema: input.schema,\n searchText: nextSearchTextToLoad,\n signal: controller.signal,\n uiSchema: input.uiSchema,\n })\n : readFormFieldOptions({\n cursor,\n fieldKey: dynamicField.fieldKey,\n formData: queryFormData,\n instanceId: effectiveContext.instanceId ?? null,\n searchText: nextSearchTextToLoad,\n signal: controller.signal,\n templateId: effectiveContext.templateId ?? null,\n });\n\n void request\n .then((result): void => {\n if (isSupersededRequest(controller, requestSequence, requestId)) {\n return;\n }\n\n setRemoteOptions((currentOptions) => {\n const selectedOptions = readSelectedFormDataSourceOptions(\n dynamicField ? input.formData[dynamicField.fieldKey] : undefined,\n currentOptions,\n );\n\n return mergeFormDataSourceOptions(\n selectedOptions,\n cursor ? currentOptions : [],\n result.options,\n );\n });\n setNextCursor(result.nextCursor);\n setError(null);\n loadedOptionCount.current = cursor\n ? loadedOptionCount.current + result.options.length\n : result.options.length;\n\n // An empty page that still hands back a cursor would loop forever.\n if (\n result.nextCursor &&\n result.options.length > 0 &&\n loadedOptionCount.current < MIN_SCROLLABLE_OPTION_COUNT\n ) {\n loadOptionsRef.current(nextSearchTextToLoad, result.nextCursor);\n }\n\n // Only the host knows which bound parameters are required, so a\n // control is disabled on its answer instead of on a browser guess.\n setStatus(\n result.waitingForFieldKeys.length\n ? 'WAITING_FOR_DEPENDENCIES'\n : 'VALID',\n );\n })\n .catch((requestError: unknown): void => {\n if (isSupersededRequest(controller, requestSequence, requestId)) {\n return;\n }\n\n // Anything that is not a DataSource code — a transport failure, or a\n // server-side error the host deliberately reduced to a generic\n // message — must not be rendered verbatim; it is English technical\n // copy the filler cannot act on.\n const message =\n readFormDataSourceErrorMessage(requestError) ??\n '選項來源暫時無法使用。';\n const code = readFormDataSourceErrorCode(requestError);\n\n setError(message);\n setStatus(\n readFailedQueryStatus(\n Boolean(code && RECOVERABLE_ERROR_CODES.includes(code)),\n hasValue,\n ),\n );\n });\n },\n [\n dynamicFieldSignature,\n effectiveContext,\n hasValue,\n pendingQueryStatus,\n queryFormData,\n schemaSignature,\n uiSchemaSignature,\n ],\n );\n const loadOptionsRef = useRef(loadOptions);\n loadOptionsRef.current = loadOptions;\n\n const runResolve = useCallback((): void => {\n if (!dynamicField || !effectiveContext || selectedValues.length === 0) {\n return;\n }\n\n const signature = dataSourceRefreshSignature;\n const requestId = resolveSequence.current + 1;\n resolveSequence.current = requestId;\n resolveAbort.current?.abort();\n const controller = new AbortController();\n resolveAbort.current = controller;\n setError(null);\n\n const request =\n effectiveContext.kind === 'preview'\n ? previewResolveFormFieldOptions({\n fieldKey: dynamicField.fieldKey,\n formData: queryFormData,\n schema: input.schema,\n signal: controller.signal,\n uiSchema: input.uiSchema,\n values: selectedValues,\n })\n : resolveFormFieldOptions({\n fieldKey: dynamicField.fieldKey,\n formData: queryFormData,\n instanceId: effectiveContext.instanceId ?? null,\n signal: controller.signal,\n templateId: effectiveContext.templateId ?? null,\n values: selectedValues,\n });\n\n void request\n .then((result): void => {\n if (isSupersededRequest(controller, resolveSequence, requestId)) {\n return;\n }\n\n if (result.waitingForFieldKeys.length) {\n // The host could not consult the provider, so this is no answer about\n // the value: leave the field waiting rather than call it resolved.\n setStatus('WAITING_FOR_DEPENDENCIES');\n\n return;\n }\n\n // Authoritative labels for the values that survived, merged so the old\n // snapshot label of an unresolved value stays visible for recognition.\n setRemoteOptions((currentOptions) =>\n mergeFormDataSourceOptions(currentOptions, result.options),\n );\n setResolution({\n signature,\n unresolvedValues: result.unresolvedValues,\n });\n // `invalidValues` turns this into `INVALID` when anything went missing.\n setStatus('VALID');\n })\n .catch((requestError: unknown): void => {\n if (isSupersededRequest(controller, resolveSequence, requestId)) {\n return;\n }\n\n setStatus('UNAVAILABLE');\n setError(\n readFormDataSourceErrorMessage(requestError) ??\n '選項來源暫時無法使用。',\n );\n });\n }, [\n dataSourceRefreshSignature,\n dynamicFieldSignature,\n effectiveContext,\n queryFormData,\n schemaSignature,\n selectedValues,\n uiSchemaSignature,\n ]);\n const runResolveRef = useRef(runResolve);\n runResolveRef.current = runResolve;\n\n useEffect((): void => {\n requestSequence.current += 1;\n optionsAbort.current?.abort();\n setRemoteOptions((currentOptions) =>\n readSelectedFormDataSourceOptions(currentValue, currentOptions),\n );\n setNextCursor((currentCursor) =>\n currentCursor === null ? currentCursor : null,\n );\n setSearchText((currentSearchText) =>\n currentSearchText ? '' : currentSearchText,\n );\n setError((currentError) => (currentError ? null : currentError));\n\n if (!dynamicField) {\n setStatus('IDLE');\n\n return;\n }\n\n if (!autoQueries) {\n // AutoComplete queries on search only, so it stays quiescent until the\n // filler types; a context-less field has nothing to query at all.\n setStatus(quiescentStatus);\n\n return;\n }\n\n loadOptionsRef.current('', null);\n }, [\n autoQueries,\n dynamicFieldSignature,\n effectiveContext,\n dataSourceRefreshSignature,\n initialFormDataSignature,\n input.readonly,\n pendingQueryStatus,\n quiescentStatus,\n snapshotSignature,\n ]);\n\n useEffect((): void => {\n if (!needsResolve) {\n return;\n }\n\n runResolveRef.current();\n }, [dataSourceRefreshSignature, effectiveContext, needsResolve]);\n\n useEffect((): (() => void) => {\n return (): void => {\n optionsAbort.current?.abort();\n resolveAbort.current?.abort();\n };\n }, []);\n\n const onSearch = useCallback(\n (nextSearchTextToLoad: string): void => {\n setSearchText(nextSearchTextToLoad);\n setRemoteOptions((currentOptions) =>\n readSelectedFormDataSourceOptions(currentValue, currentOptions),\n );\n setNextCursor(null);\n loadOptions(nextSearchTextToLoad, null);\n },\n [loadOptions],\n );\n const onReachBottom = useCallback((): void => {\n if (nextCursor) {\n loadOptions(searchText, nextCursor);\n }\n }, [loadOptions, nextCursor, searchText]);\n const retry = useCallback((): void => {\n if (!effectiveContext) {\n return;\n }\n\n loadOptions(lastRequest.current.searchText, lastRequest.current.cursor);\n\n if (needsResolve) {\n runResolveRef.current();\n }\n }, [effectiveContext, loadOptions, needsResolve]);\n\n if (!dynamicField) {\n return EMPTY_FIELD_STATE;\n }\n\n return {\n canRetry: Boolean(effectiveContext),\n error,\n hasValue,\n hasNextPage: Boolean(nextCursor),\n invalidValues,\n onReachBottom,\n onSearch,\n options: mergedOptions,\n retry,\n status: readFormDataSourceExposedStatus({\n invalidValues,\n resolvePending,\n status,\n }),\n };\n}\n\nexport function readFormDataSourceFieldStatusMessage(\n state: FormDataSourceFieldState,\n): string | null {\n switch (state.status) {\n case 'WAITING_FOR_DEPENDENCIES':\n return '請先填寫相依欄位。';\n case 'STALE':\n return '選項需要重新載入或驗證。';\n case 'INVALID':\n return state.invalidValues.length\n ? `無法辨識選項:${state.invalidValues.join('、')}`\n : '目前選項已失效,請重新選擇。';\n case 'UNAVAILABLE':\n return state.error ?? '選項來源暫時無法使用。';\n case 'VALID':\n // A recoverable search hint outranks the empty-result copy: it is what\n // tells the filler how to get results at all.\n return state.error ?? (state.options.length ? null : '目前沒有可用選項。');\n default:\n return state.error;\n }\n}\n\nexport function isFormDataSourceFieldSubmissionBlocked(\n state: Pick<FormDataSourceFieldState, 'hasValue' | 'status'>,\n): boolean {\n return state.hasValue && state.status !== 'VALID';\n}\n\n/**\n * The copy to show when a submission is refused because of dynamic options.\n * `LOADING` and `STALE` clear on their own once the pending query answers, so\n * saying \"finish validating\" reads as a dead end for what is really a \"wait a\n * moment\"; the caller would otherwise show the same permanent-sounding line for\n * both cases.\n *\n * Returns `null` when nothing blocks the submission.\n */\nexport function readFormDataSourceSubmissionBlockMessage(\n states: readonly Pick<FormDataSourceFieldState, 'hasValue' | 'status'>[],\n): string | null {\n const blocked = states.filter(isFormDataSourceFieldSubmissionBlocked);\n\n if (blocked.length === 0) {\n return null;\n }\n\n return blocked.every(\n (state) => state.status === 'LOADING' || state.status === 'STALE',\n )\n ? '選項驗證中,請稍候再送出。'\n : '請先完成動態選項驗證。';\n}\n\n/**\n * The values the field holds that no option accounts for.\n *\n * A completed resolve is the authority — the loaded pages are not, because the\n * option snapshot is merged into them for display and would vouch for a value\n * the source has already dropped.\n */\nfunction readInvalidFormDataSourceValues(input: {\n readonly options: readonly FormFieldOption[];\n readonly resolution: FormDataSourceResolution | null;\n readonly resolvePending: boolean;\n readonly value: FormFieldValue | undefined;\n}): readonly string[] {\n if (input.resolution) {\n return input.resolution.unresolvedValues;\n }\n\n // While the host is being asked, its answer is the only one worth showing.\n if (input.resolvePending) {\n return NO_INVALID_VALUES;\n }\n\n return readMissingFormDataSourceOptionValues(input.value, input.options);\n}\n\n/**\n * Status of a field nobody is querying — read-only history, a Designer preview\n * before the first search, or a control the host gave no context for.\n */\nfunction readQuiescentFormDataSourceStatus(input: {\n readonly hasSnapshot: boolean;\n readonly hasValue: boolean;\n readonly isStale: boolean;\n readonly readonly: boolean;\n}): FormDataSourceFieldStatus {\n if (input.isStale) {\n return 'STALE';\n }\n\n if (input.hasSnapshot) {\n return 'VALID';\n }\n\n // A read-only value with no snapshot cannot be labelled from anywhere, which\n // is worth saying. An empty read-only field is simply blank — warning about a\n // source nobody is going to query would be noise.\n return input.readonly && input.hasValue ? 'UNAVAILABLE' : 'IDLE';\n}\n\n/**\n * Status held while a query is in flight.\n *\n * `waiting` is the browser's optimistic guess and only survives until the host\n * answers: `waitingForFieldKeys` from the response replaces it either way, so an\n * optional binding left empty clears within one round trip instead of locking\n * the control.\n */\nfunction readPendingQueryStatus(\n isStale: boolean,\n waiting: boolean,\n): FormDataSourceFieldStatus {\n if (waiting) {\n return 'WAITING_FOR_DEPENDENCIES';\n }\n\n return isStale ? 'STALE' : 'LOADING';\n}\n\n/**\n * Status after a rejected query. A recoverable failure leaves the field as\n * usable as it was — only a broken source makes it unavailable.\n */\nfunction readFailedQueryStatus(\n recoverable: boolean,\n hasValue: boolean,\n): FormDataSourceFieldStatus {\n if (!recoverable) {\n return 'UNAVAILABLE';\n }\n\n return hasValue ? 'VALID' : 'IDLE';\n}\n\nfunction readFormDataSourceExposedStatus(input: {\n readonly invalidValues: readonly string[];\n readonly resolvePending: boolean;\n readonly status: FormDataSourceFieldStatus;\n}): FormDataSourceFieldStatus {\n if (\n input.status === 'LOADING' ||\n input.status === 'UNAVAILABLE' ||\n input.status === 'WAITING_FOR_DEPENDENCIES'\n ) {\n return input.status;\n }\n\n if (input.invalidValues.length) {\n return 'INVALID';\n }\n\n return input.resolvePending ? 'STALE' : input.status;\n}\n\n/**\n * True when a response no longer belongs to the field: its request was aborted\n * by a newer one, or a newer one started before it settled. Such a response\n * must not touch state — an aborted request is not a failure to report.\n */\nfunction isSupersededRequest(\n controller: AbortController,\n sequence: { readonly current: number },\n requestId: number,\n): boolean {\n return controller.signal.aborted || sequence.current !== requestId;\n}\n","'use client';\n\nimport {\n ChangeEvent,\n CSSProperties,\n ReactElement,\n useEffect,\n useMemo,\n useRef,\n useState,\n} from 'react';\nimport {\n AutoComplete,\n Button,\n CheckboxGroup,\n DatePicker,\n DateTimePicker,\n Input,\n RadioGroup,\n Select,\n Textarea,\n Toggle,\n Typography,\n Upload,\n} from '@mezzanine-ui/react';\nimport type { UploadFile } from '@mezzanine-ui/react/Upload';\nimport {\n FormDataSourceOptionFieldDefinition,\n FormDataSourceValueSnapshots,\n FormDefinitionSchema,\n FormFieldDefinition,\n FormFieldValue,\n FormUiSchema,\n isFormDataSourceFieldDefinition,\n isFormStaticOptionFieldDefinition,\n readFormFieldSelectionMode,\n} from '@rytass/bpm-core-shared/form';\nimport {\n buildFormRendererValues,\n clampOptionalNumber,\n formatDatePickerValue,\n formatDateTimePickerValue,\n FormRendererValues,\n isFormRendererFieldReadonly,\n isFormRendererFieldRequired,\n parseOptionalNumberInput,\n readDatePickerValue,\n readFieldOptionAsSelectOption,\n readSelectedFormDataSourceOptions,\n readSelectOption,\n readVisibleFormRendererFields,\n} from '@rytass/bpm-core-client/form';\nimport { BPMFormField } from '../../../components/bpm-form-field';\nimport {\n FormDataSourceFieldState,\n FormRendererDataSourceContext,\n readFormDataSourceFieldStatusMessage,\n useFormDataSourceField,\n} from './form-data-source-field';\n\nexport interface FormRendererProps {\n readonly dataSourceContext?: FormRendererDataSourceContext;\n readonly dataSourceInitialValues?: FormRendererValues;\n readonly emptyText?: string;\n readonly errors?: Readonly<Record<string, string>>;\n readonly maxWidth?: CSSProperties['maxWidth'];\n readonly onChange?: (values: FormRendererValues) => void;\n readonly onDataSourceStateChange?: (\n fieldKey: string,\n state: Pick<\n FormDataSourceFieldState,\n 'hasValue' | 'invalidValues' | 'status'\n >,\n ) => void;\n readonly onUploadAttachment?: (\n field: FormFieldDefinition,\n file: File,\n ) => Promise<{ readonly id: string }>;\n readonly optionSnapshots?: FormDataSourceValueSnapshots;\n readonly readonly?: boolean;\n readonly schema: FormDefinitionSchema;\n readonly singleColumn?: boolean;\n readonly uiSchema: FormUiSchema;\n readonly value?: FormRendererValues;\n}\n\nconst FORM_RENDERER_GRID_STYLE: CSSProperties = {\n alignItems: 'start',\n display: 'grid',\n gap: 12,\n gridTemplateColumns: 'repeat(12, minmax(0, 1fr))',\n};\n\nconst FORM_RENDERER_EMPTY_STYLE: CSSProperties = {\n gridColumn: '1 / -1',\n};\n\nconst FORM_RENDERER_FIELD_STYLE: CSSProperties = {\n alignItems: 'start',\n display: 'grid',\n gap: 8,\n minWidth: 0,\n};\n\nconst TEXTAREA_STYLE: CSSProperties = {\n minWidth: '100%',\n width: '100%',\n};\n\nfunction applyFullWidthTextareaHost(element: HTMLDivElement | null): void {\n if (!element) {\n return;\n }\n\n element.style.width = '100%';\n}\n\nexport function FormRenderer({\n dataSourceContext,\n dataSourceInitialValues,\n emptyText = '尚未建立欄位。',\n errors = {},\n maxWidth,\n onChange,\n onDataSourceStateChange,\n onUploadAttachment,\n optionSnapshots,\n readonly = false,\n schema,\n singleColumn = false,\n uiSchema,\n value,\n}: FormRendererProps): ReactElement {\n const [internalValues, setInternalValues] = useState<FormRendererValues>(() =>\n buildFormRendererValues(schema.fields, value ?? {}),\n );\n const values = useMemo(\n (): FormRendererValues =>\n buildFormRendererValues(schema.fields, value ?? internalValues),\n [internalValues, schema.fields, value],\n );\n const valuesRef = useRef<FormRendererValues>(values);\n const visibleFields = useMemo(\n (): readonly FormFieldDefinition[] =>\n readVisibleFormRendererFields(schema, uiSchema, values),\n [schema, uiSchema, values],\n );\n\n useEffect((): void => {\n valuesRef.current = values;\n }, [values]);\n\n useEffect((): void => {\n setInternalValues((currentValues) =>\n buildFormRendererValues(schema.fields, value ?? currentValues),\n );\n }, [schema.fields, value]);\n\n function updateValue(\n fieldKey: string,\n nextValue: FormFieldValue | undefined,\n ): void {\n const nextValues = {\n ...valuesRef.current,\n [fieldKey]: nextValue,\n };\n valuesRef.current = nextValues;\n\n if (!value) {\n setInternalValues(nextValues);\n }\n\n onChange?.(nextValues);\n }\n\n if (!visibleFields.length) {\n return (\n <div style={FORM_RENDERER_GRID_STYLE}>\n <Typography\n color=\"text-neutral\"\n style={FORM_RENDERER_EMPTY_STYLE}\n variant=\"body\"\n >\n {schema.fields.length > 0 ? '目前條件下沒有可填寫欄位。' : emptyText}\n </Typography>\n </div>\n );\n }\n\n return (\n <div\n style={{\n ...FORM_RENDERER_GRID_STYLE,\n ...(singleColumn ? { maxWidth, width: '100%' } : {}),\n }}\n >\n {visibleFields.map((field) => (\n <FormRendererField\n dataSourceContext={dataSourceContext}\n dataSourceInitialValues={dataSourceInitialValues}\n field={field}\n error={errors[field.fieldKey] ?? null}\n fields={schema.fields}\n key={field.fieldKey}\n onChange={updateValue}\n onDataSourceStateChange={onDataSourceStateChange}\n onUploadAttachment={onUploadAttachment}\n optionSnapshots={optionSnapshots}\n readonly={readonly}\n schema={schema}\n style={{\n ...FORM_RENDERER_FIELD_STYLE,\n gridColumn: `span ${\n singleColumn ? 12 : readFieldColumnSpan(field, uiSchema)\n }`,\n }}\n value={values[field.fieldKey]}\n values={values}\n uiSchema={uiSchema}\n />\n ))}\n </div>\n );\n}\n\nfunction FormRendererField({\n dataSourceContext,\n dataSourceInitialValues,\n error,\n field,\n fields,\n onChange,\n onDataSourceStateChange,\n onUploadAttachment,\n optionSnapshots,\n readonly,\n schema,\n style,\n value,\n values,\n uiSchema,\n}: {\n readonly dataSourceContext?: FormRendererDataSourceContext;\n readonly dataSourceInitialValues?: FormRendererValues;\n readonly error: string | null;\n readonly field: FormFieldDefinition;\n readonly fields: readonly FormFieldDefinition[];\n readonly onChange: (\n fieldKey: string,\n value: FormFieldValue | undefined,\n ) => void;\n readonly onDataSourceStateChange?: (\n fieldKey: string,\n state: Pick<\n FormDataSourceFieldState,\n 'hasValue' | 'invalidValues' | 'status'\n >,\n ) => void;\n readonly onUploadAttachment?:\n | ((\n field: FormFieldDefinition,\n file: File,\n ) => Promise<{ readonly id: string }>)\n | undefined;\n readonly optionSnapshots?: FormDataSourceValueSnapshots;\n readonly readonly: boolean;\n readonly schema: FormDefinitionSchema;\n readonly style: CSSProperties;\n readonly uiSchema: FormUiSchema;\n readonly value: FormFieldValue | undefined;\n readonly values: FormRendererValues;\n}): ReactElement {\n const required = isFormRendererFieldRequired(field, fields, values);\n const fieldReadonly =\n readonly || isFormRendererFieldReadonly(field, fields, values);\n const dataSourceState = useFormDataSourceField({\n context: dataSourceContext,\n field,\n formData: values,\n initialFormData: dataSourceInitialValues,\n initialValue: dataSourceInitialValues?.[field.fieldKey],\n optionSnapshots,\n readonly: fieldReadonly,\n schema,\n uiSchema,\n });\n const dataSourceStatusMessage = readFormDataSourceFieldStatusMessage(\n dataSourceState,\n );\n const dataSourceStateSignature = JSON.stringify({\n hasValue: dataSourceState.hasValue,\n invalidValues: dataSourceState.invalidValues,\n status: dataSourceState.status,\n });\n\n useEffect((): void => {\n if (!isFormDataSourceFieldDefinition(field)) {\n return;\n }\n\n onDataSourceStateChange?.(field.fieldKey, {\n hasValue: dataSourceState.hasValue,\n invalidValues: dataSourceState.invalidValues,\n status: dataSourceState.status,\n });\n }, [\n dataSourceStateSignature,\n field.fieldKey,\n onDataSourceStateChange,\n ]);\n\n return (\n <div data-form-field-key={field.fieldKey} style={style}>\n <BPMFormField\n label={field.label}\n name={field.fieldKey}\n required={required}\n >\n {renderControl(\n field,\n value,\n fieldReadonly,\n onChange,\n onUploadAttachment,\n dataSourceContext,\n dataSourceState,\n )}\n </BPMFormField>\n {error ? (\n <Typography color=\"text-error\" variant=\"caption\">\n {error}\n </Typography>\n ) : null}\n {dataSourceStatusMessage ? (\n <div style={DATA_SOURCE_FEEDBACK_STYLE}>\n <Typography\n color={\n dataSourceState.status === 'INVALID' ||\n dataSourceState.status === 'UNAVAILABLE'\n ? 'text-error'\n : 'text-neutral'\n }\n variant=\"caption\"\n >\n {dataSourceStatusMessage}\n </Typography>\n {dataSourceState.status === 'UNAVAILABLE' && dataSourceState.canRetry ? (\n <Button\n onClick={dataSourceState.retry}\n size=\"sub\"\n type=\"button\"\n variant=\"base-ghost\"\n >\n 重試\n </Button>\n ) : null}\n </div>\n ) : null}\n </div>\n );\n}\n\nconst DATA_SOURCE_FEEDBACK_STYLE: CSSProperties = {\n alignItems: 'center',\n display: 'flex',\n gap: 8,\n};\n\nfunction renderControl(\n field: FormFieldDefinition,\n value: FormFieldValue | undefined,\n readonly: boolean,\n onChange: (fieldKey: string, value: FormFieldValue | undefined) => void,\n onUploadAttachment:\n | ((\n field: FormFieldDefinition,\n file: File,\n ) => Promise<{ readonly id: string }>)\n | undefined,\n dataSourceContext: FormRendererDataSourceContext | undefined,\n dataSourceState: FormDataSourceFieldState,\n): ReactElement {\n if (field.type === 'textarea') {\n return (\n <Textarea\n onChange={(event: ChangeEvent<HTMLTextAreaElement>): void =>\n onChange(field.fieldKey, event.target.value)\n }\n placeholder={field.placeholder ?? '請輸入多行文字'}\n readOnly={readonly}\n ref={applyFullWidthTextareaHost}\n rows={3}\n style={TEXTAREA_STYLE}\n value={readStringValue(value)}\n />\n );\n }\n\n if (field.type === 'boolean') {\n return (\n <Toggle\n checked={value === true}\n disabled={readonly}\n label=\"啟用\"\n onChange={(event: ChangeEvent<HTMLInputElement>): void =>\n onChange(field.fieldKey, event.target.checked)\n }\n />\n );\n }\n\n if (isFormDataSourceFieldDefinition(field)) {\n return renderDynamicOptionControl(\n field,\n value,\n readonly,\n onChange,\n dataSourceContext,\n dataSourceState,\n );\n }\n\n if (isFormStaticOptionFieldDefinition(field) && field.type === 'checkbox') {\n const options = field.options.map(readFieldOptionAsSelectOption);\n\n return (\n <Select\n mode=\"multiple\"\n onChange={(options): void =>\n onChange(\n field.fieldKey,\n options?.length\n ? options.map((option) => option.id)\n : undefined,\n )\n }\n options={options}\n placeholder={field.placeholder ?? '請選擇一或多個選項'}\n readOnly={readonly}\n value={options.filter((option) =>\n readStringArrayValue(value).includes(option.id),\n )}\n />\n );\n }\n\n if (isFormStaticOptionFieldDefinition(field)) {\n const options = field.options.map(readFieldOptionAsSelectOption);\n\n return (\n <Select\n onChange={(option): void =>\n onChange(field.fieldKey, option?.id ?? undefined)\n }\n options={options}\n placeholder={field.placeholder ?? '請選擇'}\n readOnly={readonly}\n value={readSelectOption(options, readStringValue(value))}\n />\n );\n }\n\n if (field.type === 'file_upload') {\n return (\n <Upload\n accept={field.acceptedMimeTypes?.join(',')}\n disabled={readonly}\n maxFiles={field.maxFiles}\n mode=\"button-list\"\n {...((field.maxFiles ?? 1) > 1 ? { multiple: true } : {})}\n onChange={(files): void =>\n onChange(\n field.fieldKey,\n files.length ? files.map((file) => file.id) : undefined,\n )\n }\n onUpload={async (files): Promise<UploadFile[]> =>\n Promise.all(\n files.map(async (file): Promise<UploadFile> => {\n const uploadedFile = onUploadAttachment\n ? await onUploadAttachment(field, file)\n : { id: `${file.name}-${file.lastModified}` };\n\n return {\n file,\n id: uploadedFile.id,\n progress: 100,\n status: 'done',\n };\n }),\n )\n }\n size=\"sub\"\n />\n );\n }\n\n if (field.type === 'date') {\n return (\n <DatePicker\n format=\"YYYY-MM-DD\"\n fullWidth\n onChange={(nextValue): void =>\n onChange(field.fieldKey, formatDatePickerValue(nextValue))\n }\n placeholder={field.placeholder ?? readInputPlaceholder(field.type)}\n readOnly={readonly}\n value={readDatePickerValue(value)}\n />\n );\n }\n\n if (field.type === 'datetime') {\n return (\n <DateTimePicker\n formatDate=\"YYYY-MM-DD\"\n formatTime=\"HH:mm\"\n fullWidth\n hideSecond\n onChange={(nextValue): void =>\n onChange(field.fieldKey, formatDateTimePickerValue(nextValue))\n }\n placeholderLeft=\"選擇日期\"\n placeholderRight=\"選擇時間\"\n readOnly={readonly}\n value={readDatePickerValue(value)}\n />\n );\n }\n\n if (field.type === 'number' || field.type === 'money') {\n return (\n <Input\n fullWidth\n max={field.maximum}\n min={field.minimum}\n onChange={(event: ChangeEvent<HTMLInputElement>): void =>\n onChange(\n field.fieldKey,\n clampOptionalNumber(parseOptionalNumberInput(event.target.value), {\n max: field.maximum,\n min: field.minimum,\n }),\n )\n }\n placeholder={field.placeholder ?? readInputPlaceholder(field.type)}\n {...(readonly ? { readonly: true as const } : {})}\n showSpinner\n value={readNumberInputValue(value)}\n variant=\"measure\"\n />\n );\n }\n\n return (\n <Input\n fullWidth\n onChange={(event: ChangeEvent<HTMLInputElement>): void =>\n onChange(field.fieldKey, event.target.value)\n }\n placeholder={field.placeholder ?? readInputPlaceholder(field.type)}\n {...(readonly ? { readonly: true as const } : {})}\n value={readStringValue(value)}\n variant=\"base\"\n />\n );\n}\n\nfunction renderDynamicOptionControl(\n field: FormDataSourceOptionFieldDefinition,\n value: FormFieldValue | undefined,\n readonly: boolean,\n onChange: (fieldKey: string, value: FormFieldValue | undefined) => void,\n dataSourceContext: FormRendererDataSourceContext | undefined,\n dataSourceState: FormDataSourceFieldState,\n): ReactElement {\n const options = dataSourceState.options.map(readFieldOptionAsSelectOption);\n const selectedOptions = readSelectedFormDataSourceOptions(\n value,\n dataSourceState.options,\n ).map(readFieldOptionAsSelectOption);\n const loading = dataSourceState.status === 'LOADING';\n const waitingForDependencies =\n dataSourceState.status === 'WAITING_FOR_DEPENDENCIES';\n const interactiveSearch = Boolean(dataSourceContext) && !readonly;\n const optionControlDisabled = readonly || waitingForDependencies;\n // AutoComplete alone has no pre-query gate — it only learns a dependency is\n // missing from the answer to a search the filler already typed. Disabling it\n // at that point strands that text in a locked input with no way to clear it,\n // so it stays editable and reports the wait through the status line instead.\n const autoCompleteDisabled = readonly;\n\n if (field.type === 'autocomplete') {\n if (readFormFieldSelectionMode(field) === 'multiple') {\n return (\n <AutoComplete\n asyncData={interactiveSearch}\n clearSearchText\n disabled={autoCompleteDisabled}\n disabledOptionsFilter={interactiveSearch}\n globalPortal\n loading={loading}\n mode=\"multiple\"\n onChange={(nextOptions): void =>\n onChange(\n field.fieldKey,\n nextOptions.length\n ? nextOptions.map((option) => option.id)\n : undefined,\n )\n }\n onReachBottom={\n dataSourceState.hasNextPage\n ? dataSourceState.onReachBottom\n : undefined\n }\n onSearch={interactiveSearch ? dataSourceState.onSearch : undefined}\n options={options}\n placeholder={field.placeholder ?? '請輸入或選擇'}\n readOnly={readonly}\n searchDebounceTime={300}\n value={selectedOptions}\n />\n );\n }\n\n return (\n <AutoComplete\n asyncData={interactiveSearch}\n clearSearchText\n disabled={autoCompleteDisabled}\n disabledOptionsFilter={interactiveSearch}\n globalPortal\n loading={loading}\n mode=\"single\"\n onChange={(nextOption): void =>\n onChange(field.fieldKey, nextOption?.id ?? undefined)\n }\n onReachBottom={\n dataSourceState.hasNextPage\n ? dataSourceState.onReachBottom\n : undefined\n }\n onSearch={interactiveSearch ? dataSourceState.onSearch : undefined}\n options={options}\n placeholder={field.placeholder ?? '請輸入或選擇'}\n readOnly={readonly}\n searchDebounceTime={300}\n value={selectedOptions[0] ?? null}\n />\n );\n }\n\n if (field.type === 'radio') {\n return (\n <RadioGroup\n disabled={optionControlDisabled}\n name={field.fieldKey}\n onChange={(event): void =>\n onChange(field.fieldKey, event.target.value || undefined)\n }\n options={options}\n value={readStringValue(value)}\n />\n );\n }\n\n if (field.type === 'checkbox') {\n return (\n <CheckboxGroup\n disabled={optionControlDisabled}\n name={field.fieldKey}\n onChange={(event): void =>\n onChange(\n field.fieldKey,\n event.target.values.length ? event.target.values : undefined,\n )\n }\n options={options.map((option) => ({\n label: option.name,\n value: option.id,\n }))}\n value={[...readStringArrayValue(value)]}\n />\n );\n }\n\n if (readFormFieldSelectionMode(field) === 'multiple') {\n return (\n <Select\n disabled={optionControlDisabled}\n loading={loading}\n mode=\"multiple\"\n onChange={(nextOptions): void =>\n onChange(\n field.fieldKey,\n nextOptions.length\n ? nextOptions.map((option) => option.id)\n : undefined,\n )\n }\n onReachBottom={\n dataSourceState.hasNextPage\n ? dataSourceState.onReachBottom\n : undefined\n }\n options={options}\n placeholder={field.placeholder ?? '請選擇一或多個選項'}\n readOnly={readonly}\n value={selectedOptions}\n />\n );\n }\n\n return (\n <Select\n disabled={optionControlDisabled}\n loading={loading}\n onChange={(nextOption): void =>\n onChange(field.fieldKey, nextOption?.id ?? undefined)\n }\n onReachBottom={\n dataSourceState.hasNextPage\n ? dataSourceState.onReachBottom\n : undefined\n }\n options={options}\n placeholder={field.placeholder ?? '請選擇'}\n readOnly={readonly}\n value={selectedOptions[0] ?? null}\n />\n );\n}\n\nfunction readFieldColumnSpan(\n field: FormFieldDefinition,\n uiSchema: FormUiSchema,\n): number {\n const width =\n uiSchema.layout.find((item) => item.fieldKey === field.fieldKey)?.width ??\n 'FULL';\n const spans: Readonly<Record<typeof width, number>> = {\n FULL: 12,\n HALF: 6,\n THIRD: 4,\n };\n\n return spans[width];\n}\n\nfunction readStringValue(value: FormFieldValue | undefined): string {\n return typeof value === 'string' ? value : '';\n}\n\nfunction readStringArrayValue(\n value: FormFieldValue | undefined,\n): readonly string[] {\n return Array.isArray(value) ? value : [];\n}\n\nfunction readNumberInputValue(value: FormFieldValue | undefined): string {\n return typeof value === 'number' ? String(value) : '';\n}\n\nfunction readInputPlaceholder(type: FormFieldDefinition['type']): string {\n const placeholders: Readonly<Record<FormFieldDefinition['type'], string>> = {\n boolean: '',\n autocomplete: '請輸入或選擇',\n checkbox: '請選擇一或多個選項',\n date: '請選擇日期',\n datetime: '請選擇日期與時間',\n file_upload: '請上傳附件',\n money: '請輸入金額',\n number: '請輸入數字',\n radio: '請選擇一個選項',\n select: '請選擇一個選項',\n text: '請輸入文字',\n textarea: '請輸入多行文字',\n };\n\n return placeholders[type];\n}\n\nexport { FormRenderer as FormRendererView };\n"],"mappings":"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"}
@@ -1,2 +0,0 @@
1
- "use client";require('../approval-instance-list-page.css');const e=require("./chunk-CMqjfN_6.cjs"),t=require("./router-adapter--gYs13E8.cjs"),n=require("./format-date-time-XxBzF0F5.cjs"),r=require("./routes-config-fDVHmvXi.cjs");let i=require("react"),a=require("@mezzanine-ui/react"),o=require("@rytass/bpm-core-client"),s=require("react/jsx-runtime"),c=require("@rytass/bpm-core-client/workflow"),l=require("@mezzanine-ui/core/form"),u=require("@mezzanine-ui/react/ContentHeader");u=e.t(u,1);var d={instanceFilterArea:`bpm_instanceFilterArea_qpvJq`},f=[10,20,50],p=[{id:`ALL`,name:`全部狀態`,state:null},{id:`RUNNING`,name:`進行中`,state:`RUNNING`},{id:`APPROVED`,name:`已通過`,state:`APPROVED`},{id:`REJECTED`,name:`已拒絕`,state:`REJECTED`},{id:`RETURNED`,name:`已退回`,state:`RETURNED`},{id:`CANCELLED`,name:`已取消`,state:`CANCELLED`},{id:`EXPIRED`,name:`已逾期`,state:`EXPIRED`},{id:`DRAFT`,name:`草稿`,state:`DRAFT`}];function m({defaultState:e,description:m,emptyMessage:y,searchPlaceholder:b,title:w,view:T}){let E=t.r(),D=r.r(),[O,k]=(0,i.useState)(null),[A,j]=(0,i.useState)(new Map),[M,N]=(0,i.useState)(1),[P,F]=(0,i.useState)(10),[I,L]=(0,i.useState)(0),[R,z]=(0,i.useState)(!0),[B,V]=(0,i.useState)([]),[H,U]=(0,i.useState)(``),[W,G]=(0,i.useState)(_(e)),K=(0,i.useRef)(0),q=(0,i.useCallback)(async()=>{let e=K.current+1;K.current=e,z(!0),k(null);try{let t=await(0,c.listApprovalInstancesPage)({page:M,pageSize:P,searchText:H,state:W.state,templateId:null,view:T});if(e!==K.current)return;V(t.instances.map(h)),L(t.totalCount)}catch(t){e===K.current&&k(C(t))}finally{e===K.current&&z(!1)}},[M,P,H,W,T]);(0,i.useEffect)(()=>{q()},[q]),(0,i.useEffect)(()=>{let e=Array.from(new Set(B.map(e=>e.initiatorMemberId).filter(Boolean)));if(e.length===0){j(new Map);return}let t=!1;return(async()=>{try{let n=await(0,o.resolveMembers)(e);if(t)return;j(new Map(n.map(e=>[e.memberId,e])))}catch{if(t)return;j(new Map)}})(),()=>{t=!0}},[B]);let J=(0,i.useMemo)(()=>[{dataIndex:`caseTitle`,key:`caseTitle`,title:`案件`,width:300},{key:`state`,render:e=>(0,s.jsx)(a.Typography,{color:x(e.state),component:`span`,variant:`body`,children:e.stateLabel}),title:`狀態`,width:120},{key:`initiatorMemberId`,render:e=>(0,s.jsx)(a.Typography,{component:`span`,variant:`body`,children:S(e.initiatorMemberId,A)}),title:`發起人`,width:180},{key:`startedAt`,render:e=>(0,s.jsx)(a.Typography,{component:`span`,variant:`body`,children:n.t(e.startedAt)}),title:`發起時間`,width:220},{key:`completedAt`,render:e=>(0,s.jsx)(a.Typography,{component:`span`,variant:`body`,children:n.t(e.completedAt)}),title:`完成時間`,width:220}],[A]),Y=(0,i.useMemo)(()=>({render:e=>[{name:`查看`,onClick:()=>E.push(D.caseDetail(e.id))}],variant:`base-secondary`,width:88}),[E]);return(0,s.jsxs)(s.Fragment,{children:[(0,s.jsx)(a.PageHeader,{children:(0,s.jsx)(u.default,{description:m,title:w})}),(0,s.jsx)(a.SectionGroup,{children:(0,s.jsxs)(a.Section,{filterArea:(0,s.jsx)(a.FilterArea,{className:d.instanceFilterArea,size:`sub`,children:(0,s.jsxs)(a.FilterLine,{children:[(0,s.jsx)(a.Filter,{span:3,children:(0,s.jsx)(a.FormField,{fullWidth:!0,layout:l.FormFieldLayout.VERTICAL,name:`instanceSearchText`,children:(0,s.jsx)(a.Input,{fullWidth:!0,onChange:e=>{U(e.target.value),N(1)},placeholder:b,size:`sub`,value:H,variant:`base`})})}),(0,s.jsx)(a.Filter,{span:2,children:(0,s.jsx)(a.FormField,{fullWidth:!0,layout:l.FormFieldLayout.VERTICAL,name:`instanceState`,children:(0,s.jsx)(a.Select,{clearable:!1,fullWidth:!0,onChange:e=>{G(g(e)),N(1)},options:[...p],placeholder:`狀態`,renderValue:e=>`狀態:${v(e)}`,size:`sub`,value:W})})})]})}),children:[O?(0,s.jsx)(a.Typography,{color:`text-error`,variant:`body`,children:O}):null,!O&&!R&&B.length===0?(0,s.jsx)(a.Typography,{color:`text-neutral`,variant:`body`,children:y}):null,(0,s.jsx)(a.Table,{actions:Y,columns:J,dataSource:[...B],fullWidth:!0,loading:R,pagination:{current:M,onChange:e=>{N(e)},onChangePageSize:e=>{N(1),F(e)},pageSize:P,pageSizeLabel:`每頁筆數`,pageSizeOptions:f,renderResultSummary:(e,t,n)=>`顯示 ${e}-${t} 筆,共 ${n} 筆`,showPageSizeOptions:!0,total:I}})]})})]})}function h(e){return{...e,caseTitle:(0,c.readApprovalInstanceCaseTitle)(e),key:e.id,stateLabel:b(e.state)}}function g(e){return y(e)?_(e.state):p[0]}function _(e){return p.find(t=>t.state===e)??p[0]}function v(e){return y(e)?e.name:p[0].name}function y(e){return typeof e==`object`&&!!e&&`id`in e&&`name`in e&&`state`in e}function b(e){return e===`RUNNING`?`進行中`:e===`APPROVED`?`已通過`:e===`REJECTED`?`已拒絕`:e===`RETURNED`?`已退回`:e===`CANCELLED`?`已取消`:e===`EXPIRED`?`已逾期`:`草稿`}function x(e){return e===`APPROVED`?`text-success`:e===`REJECTED`||e===`CANCELLED`||e===`EXPIRED`?`text-error`:`text-neutral`}function S(e,t){let n=(e??``).trim();return n?t.get(n)?.name??n:`未知發起人`}function C(e){return e instanceof Error?e.message:`讀取簽核案件失敗。`}Object.defineProperty(exports,"t",{enumerable:!0,get:function(){return m}});
2
- //# sourceMappingURL=approval-instance-list-page-C408vxE2.cjs.map
@@ -1,2 +0,0 @@
1
- "use client";require('../categories.css');const e=require("./chunk-CMqjfN_6.cjs"),t=require("./format-date-time-XxBzF0F5.cjs"),n=require("./bpm-form-field-Bc6k4ZEO.cjs");let r=require("react"),i=require("@mezzanine-ui/react"),a=require("react/jsx-runtime"),o=require("@mezzanine-ui/core/form"),s=require("@mezzanine-ui/react/ContentHeader");s=e.t(s,1);let c=require("@mezzanine-ui/icons"),l=require("@rytass/bpm-core-client/template");var u={templateFilterArea:`bpm_templateFilterArea_nUL-R`,templateModalFields:`bpm_templateModalFields_hUxWp`},d=[10,20,50],f=[{key:`ALL`,label:`全部`},{key:`ACTIVE`,label:`啟用`},{key:`INACTIVE`,label:`停用`}];function p(){let[e,n]=(0,r.useState)([]),[p,y]=(0,r.useState)(1),[b,x]=(0,r.useState)(10),[S,C]=(0,r.useState)(`ALL`),[w,T]=(0,r.useState)(0),[E,D]=(0,r.useState)(null),[O,k]=(0,r.useState)(null),[A,j]=(0,r.useState)(!0),[M,N]=(0,r.useState)(null),[P,F]=(0,r.useState)(!1),[I,L]=(0,r.useState)(``),R=(0,r.useCallback)(async()=>{j(!0),k(null);try{let e=await(0,l.listApprovalTemplateCategoriesPage)({page:p,pageSize:b,searchText:I,status:_(S)});n(e.categories),T(e.totalCount)}catch(e){k(v(e))}finally{j(!1)}},[p,b,S,I]);(0,r.useEffect)(()=>{R()},[R]);let z=(0,r.useMemo)(()=>e.map(e=>({...e,key:e.id,updatedAtLabel:t.t(e.updatedAt)})),[e]),B=(0,r.useMemo)(()=>[{dataIndex:`name`,key:`name`,title:`分類名稱`,width:180},{key:`status`,render:e=>(0,a.jsx)(h,{isActive:e.isActive}),title:`狀態`,width:120},{dataIndex:`sortOrder`,key:`sortOrder`,title:`排序`,width:100},{key:`description`,render:e=>(0,a.jsx)(i.Typography,{component:`span`,variant:`body`,children:e.description||`無`}),title:`說明`,width:260},{dataIndex:`updatedAtLabel`,key:`updatedAtLabel`,title:`更新時間`,width:220}],[]);async function V(e){F(!0),k(null);try{M?.type===`EDIT`&&M.record?await(0,l.updateApprovalTemplateCategory)({...e,id:M.record.id}):await(0,l.createApprovalTemplateCategory)(e),N(null),await R()}catch(e){throw k(v(e)),e}finally{F(!1)}}async function H(e){F(!0),k(null);try{await(0,l.updateApprovalTemplateCategory)({description:e.description,id:e.id,isActive:!e.isActive,name:e.name,sortOrder:e.sortOrder}),await R()}catch(e){k(v(e))}finally{F(!1)}}async function U(){if(E){F(!0),k(null);try{await(0,l.deleteApprovalTemplateCategory)(E.id),D(null),await R()}catch(e){k(v(e))}finally{F(!1)}}}let W=(0,r.useMemo)(()=>({render:e=>[{name:`編輯`,onClick:()=>N({record:e,type:`EDIT`})},{name:e.isActive?`停用`:`啟用`,onClick:()=>void H(e),variant:e.isActive?`destructive-secondary`:`base-secondary`},{name:`刪除`,onClick:()=>D({id:e.id,name:e.name}),variant:`destructive-secondary`}],variant:`base-secondary`,width:192}),[R]);return(0,a.jsxs)(a.Fragment,{children:[(0,a.jsxs)(a.Fragment,{children:[(0,a.jsx)(i.PageHeader,{children:(0,a.jsx)(s.default,{description:`維護簽核模板分類,供模板建立、篩選與列表標示使用。`,title:`簽核模板分類`,children:(0,a.jsx)(i.Button,{icon:c.PlusIcon,iconType:`leading`,onClick:()=>N({record:null,type:`CREATE`}),variant:`base-primary`,children:`建立分類`})})}),(0,a.jsx)(i.SectionGroup,{children:(0,a.jsxs)(i.Section,{filterArea:(0,a.jsx)(i.FilterArea,{className:u.templateFilterArea,size:`sub`,children:(0,a.jsx)(i.FilterLine,{children:(0,a.jsx)(i.Filter,{span:3,children:(0,a.jsx)(i.FormField,{fullWidth:!0,layout:o.FormFieldLayout.VERTICAL,name:`categorySearchText`,children:(0,a.jsx)(i.Input,{fullWidth:!0,onChange:e=>{L(e.target.value),y(1)},placeholder:`關鍵字:搜尋分類名稱或說明`,size:`sub`,value:I,variant:`base`})})})})}),tab:(0,a.jsx)(i.Tab,{activeKey:S,onChange:e=>{C(g(e)),y(1)},children:f.map(e=>(0,a.jsx)(i.TabItem,{children:e.label},e.key))}),children:[O?(0,a.jsx)(i.Typography,{color:`text-error`,variant:`body`,children:O}):null,(0,a.jsx)(i.Table,{actions:W,columns:B,dataSource:z,fullWidth:!0,loading:A||P,pagination:{current:p,onChange:e=>{y(e)},onChangePageSize:e=>{y(1),x(e)},pageSize:b,pageSizeLabel:`每頁筆數`,pageSizeOptions:d,renderResultSummary:(e,t,n)=>`顯示 ${e}-${t} 筆,共 ${n} 筆`,showPageSizeOptions:!0,total:w}})]})})]}),(0,a.jsx)(m,{loading:P,modal:M,onClose:()=>N(null),onSubmit:V}),(0,a.jsx)(i.Modal,{cancelText:`取消`,confirmButtonProps:{variant:`destructive-primary`},confirmText:`刪除`,loading:P,modalStatusType:`error`,modalType:`standard`,onCancel:()=>D(null),onClose:()=>D(null),onConfirm:()=>void U(),open:!!E,showModalFooter:!0,showModalHeader:!0,size:`regular`,supportingText:`若分類已被模板使用,系統會改為停用分類並保留既有模板關聯。`,title:`刪除分類`,children:(0,a.jsxs)(i.Typography,{color:`text-neutral`,variant:`body`,children:[`確定要刪除「`,E?.name??``,`」嗎?`]})})]})}function m({loading:e,modal:t,onClose:o,onSubmit:s}){let[c,l]=(0,r.useState)(``),[d,f]=(0,r.useState)(null),[p,m]=(0,r.useState)(``),[h,g]=(0,r.useState)(`0`);(0,r.useEffect)(()=>{t&&(l(t.record?.description??``),f(null),m(t.record?.name??``),g(String(t.record?.sortOrder??0)))},[t]);async function _(){let e=p.trim(),n=Number(h);if(!e){f(`請輸入分類名稱`);return}if(!Number.isInteger(n)){f(`排序必須是整數`);return}try{await s({description:c.trim()||null,isActive:t?.record?.isActive??!0,name:e,sortOrder:n})}catch(e){f(v(e))}}return(0,a.jsxs)(i.Modal,{cancelText:`取消`,confirmButtonProps:{disabled:!p.trim()},confirmText:t?.type===`EDIT`?`儲存`:`建立`,loading:e,modalType:`standard`,onCancel:o,onClose:o,onConfirm:()=>void _(),open:!!t,showModalFooter:!0,showModalHeader:!0,size:`regular`,title:t?.type===`EDIT`?`編輯分類`:`建立分類`,children:[(0,a.jsxs)(`div`,{className:u.templateModalFields,children:[(0,a.jsx)(n.t,{label:`分類名稱`,name:`categoryName`,required:!0,children:(0,a.jsx)(i.Input,{autoFocus:!0,fullWidth:!0,onChange:e=>{m(e.target.value),f(null)},placeholder:`例如:行政管理`,value:p,variant:`base`})}),(0,a.jsx)(n.t,{label:`排序`,name:`categorySortOrder`,children:(0,a.jsx)(i.Input,{fullWidth:!0,onChange:e=>{g(e.target.value),f(null)},placeholder:`0`,value:h,variant:`base`})}),(0,a.jsx)(n.t,{label:`說明`,name:`categoryDescription`,children:(0,a.jsx)(i.Textarea,{onChange:e=>{l(e.target.value),f(null)},placeholder:`補充分類用途`,value:c})})]}),d?(0,a.jsx)(i.Typography,{color:`text-error`,variant:`body`,children:d}):null]})}function h({isActive:e}){return e?(0,a.jsx)(i.Badge,{size:`sub`,text:`啟用`,variant:`dot-success`}):(0,a.jsx)(i.Badge,{size:`sub`,text:`停用`,variant:`dot-inactive`})}function g(e){return e===`ACTIVE`||e===`INACTIVE`?e:`ALL`}function _(e){return e}function v(e){return e instanceof Error?e.message:`發生未知錯誤`}Object.defineProperty(exports,"n",{enumerable:!0,get:function(){return u}}),Object.defineProperty(exports,"t",{enumerable:!0,get:function(){return p}});
2
- //# sourceMappingURL=categories-DUfldZ_9.cjs.map
@@ -1,2 +0,0 @@
1
- "use client";const e=require("./chunk-CMqjfN_6.cjs"),t=require("./router-adapter--gYs13E8.cjs"),n=require("./routes-config-fDVHmvXi.cjs"),r=require("./FormRendererView-Cw9LiidV.cjs"),i=require("./FormBuilderView-D6baVqBY.cjs"),a=require("./designer-Cdn10NNl.cjs");let o=require("react"),s=require("@mezzanine-ui/react"),c=require("react/jsx-runtime"),l=require("@mezzanine-ui/core/form"),u=require("@mezzanine-ui/react/ContentHeader");u=e.t(u,1);let d=require("@rytass/bpm-core-client/form"),f=require("@rytass/bpm-core-client/template");var p={id:`UNCATEGORIZED`,name:`未分類`},m=100;function h({categoryId:e,formSchema:t,formUiSchema:n,name:r,onCategoryIdChange:a,onFormChange:u,onNameChange:d}){let[h,_]=(0,o.useState)([]);(0,o.useEffect)(()=>{let e=!0;return(async()=>{try{let t=await(0,f.listApprovalTemplateCategoriesPage)({page:1,pageSize:m,searchText:``,status:`ACTIVE`});e&&_(t.categories)}catch{e&&_([])}})(),()=>{e=!1}},[]);let v=[p,...h.map(e=>({id:e.id,name:e.name}))],y=v.find(t=>t.id===e)??p;return(0,c.jsxs)(c.Fragment,{children:[(0,c.jsxs)(`div`,{style:g,children:[(0,c.jsx)(s.FormField,{label:`名稱`,layout:l.FormFieldLayout.VERTICAL,name:`composeName`,children:(0,c.jsx)(s.Input,{fullWidth:!0,onChange:e=>d(e.target.value),placeholder:`例如:請款簽核`,value:r})}),(0,c.jsx)(s.FormField,{label:`分類(選填)`,layout:l.FormFieldLayout.VERTICAL,name:`composeCategory`,children:(0,c.jsx)(s.Select,{clearable:!1,fullWidth:!0,onChange:e=>a(e&&e.id!==p.id?e.id:null),options:v,placeholder:`未分類`,value:y})})]}),(0,c.jsx)(s.Typography,{color:`text-neutral`,variant:`caption`,children:`先設計表單欄位,下一步的流程條件分流即可直接引用這些欄位。`}),(0,c.jsx)(i.t,{onChange:u,value:{schema:t,uiSchema:n}})]})}var g={display:`grid`,gap:16,gridTemplateColumns:`repeat(auto-fit, minmax(220px, 1fr))`};function _({formSchema:e,formUiSchema:t,initiatorPolicyCel:n,name:i,publishError:a,workflowDefinition:o}){let l=o?.nodes??[],u=o?.edges??[],d=e.fields.length,f=new Map(l.map(e=>[e.id,e.data.label])),p=l.map(e=>({detail:x(e)??`—`,key:e.id,label:e.data.label,typeLabel:b(e)})),m=u.filter(e=>!!e.data.condition).map(e=>({condition:e.data.condition??``,key:e.id,source:f.get(e.source)??e.source,target:f.get(e.target)??e.target}));return(0,c.jsxs)(`div`,{style:S,children:[(0,c.jsx)(s.Typography,{component:`h2`,style:C,variant:`h2`,children:i||`(未命名)`}),(0,c.jsxs)(`div`,{style:S,children:[(0,c.jsx)(s.Typography,{variant:`h3`,children:`表單預覽`}),d>0?(0,c.jsx)(r.t,{dataSourceContext:{kind:`preview`},readonly:!0,schema:e,uiSchema:t}):(0,c.jsx)(s.Empty,{title:`尚未設計表單欄位`})]}),(0,c.jsxs)(`div`,{style:S,children:[(0,c.jsx)(s.Typography,{variant:`h3`,children:`流程概覽`}),l.length>0?(0,c.jsx)(s.Table,{columns:v,dataSource:p,fullWidth:!0}):(0,c.jsx)(s.Empty,{title:`尚未設計流程節點`}),m.length>0?(0,c.jsxs)(c.Fragment,{children:[(0,c.jsx)(s.Typography,{color:`text-neutral`,variant:`caption`,children:`條件分流`}),(0,c.jsx)(s.Table,{columns:y,dataSource:m,fullWidth:!0})]}):null,n?(0,c.jsxs)(s.Typography,{color:`text-neutral`,variant:`caption`,children:[`發起權限:`,n]}):null]}),a?(0,c.jsx)(s.Typography,{color:`text-error`,variant:`body`,children:a}):null]})}var v=[{key:`type`,render:e=>(0,c.jsx)(s.Tag,{label:e.typeLabel,size:`sub`,type:`static`}),title:`類型`,width:130},{dataIndex:`label`,key:`label`,title:`節點`},{dataIndex:`detail`,key:`detail`,title:`簽核方式`,width:160}],y=[{dataIndex:`source`,key:`source`,title:`來源`,width:180},{dataIndex:`target`,key:`target`,title:`目標`,width:180},{dataIndex:`condition`,key:`condition`,title:`條件`}];function b(e){switch(e.type){case`startEvent`:return`開始`;case`endEvent`:return e.data.endState===`REJECTED`?`結束(駁回)`:`結束(核准)`;case`userTask`:return`簽核`;case`serviceTask`:return`服務`;case`exclusiveGateway`:return`條件閘道`;case`parallelGateway`:return`平行閘道`;default:return`節點`}}function x(e){if(e.type!==`userTask`)return null;switch(e.data.approverResolver.type){case`DIRECT`:return`指定成員`;case`POSITION`:return`指定職位`;case`ORG_UNIT_MEMBER`:return`單位成員`;case`ORG_UNIT_POSITION`:return`單位職位`;case`ORG_MANAGER`:return`主管`;case`ORG_UNIT_MANAGER`:return`單位主管`;case`DYNAMIC_FORM`:return`表單動態指派`;case`EXPRESSION`:return`運算式`;default:return`簽核人`}}var S={display:`grid`,gap:12},C={marginTop:`var(--mzn-spacing-padding-vertical-spacious)`};function w({aiAssistantAvailable:e=!1,formSchema:t,initiatorPolicyCel:n,onInitiatorPolicyChange:r,onWorkflowChange:i,showAiAssistant:o=!1,workflowDefinition:l}){return(0,c.jsxs)(c.Fragment,{children:[(0,c.jsx)(s.Typography,{color:`text-neutral`,variant:`caption`,children:`設計簽核節點與條件分流;條件可直接引用上一步設計的表單欄位。`}),(0,c.jsx)(a.t,{aiAssistantAvailable:e,embedded:!0,formSchemaOverride:t,initialInitiatorPolicyCel:n,initialWorkflowDefinition:l??void 0,onInitiatorPolicyChange:r,onWorkflowChange:i,showAiAssistant:o})]})}var T={fields:[],schemaVersion:1},E={layout:[],schemaVersion:1};function D(){let[e,t]=(0,o.useState)(0),[n,r]=(0,o.useState)(``),[i,a]=(0,o.useState)(null),[s,c]=(0,o.useState)(T),[l,u]=(0,o.useState)(E),[d,p]=(0,o.useState)(null),[m,h]=(0,o.useState)(null),[g,_]=(0,o.useState)(`idle`),[v,y]=(0,o.useState)(null),b=n.trim().length>0&&s.fields.length>0,x=(0,o.useCallback)(e=>{t(e)},[]),S=(0,o.useCallback)(()=>{t(e=>e<2?e+1:e)},[]),C=(0,o.useCallback)(()=>{t(e=>e>0?e-1:e)},[]),w=(0,o.useCallback)(e=>{c(e.schema),u(e.uiSchema)},[]),D=(0,o.useCallback)(e=>{p(e)},[]),A=(0,o.useCallback)(e=>{h(e)},[]);return{canLeaveBasics:b,categoryId:i,currentStep:e,formSchema:s,formUiSchema:l,goBack:C,goNext:S,goToStep:x,initiatorPolicyCel:m,name:n,publish:(0,o.useCallback)(async()=>{_(`submitting`),y(null);try{let e=await(0,f.composeApprovalTemplateWithForm)({category:null,categoryId:i,formDefinitionId:null,formDescription:null,formName:n,initiatorPolicyCel:m,notificationConfig:null,publish:!0,schema:s,slaDefaults:null,templateDescription:null,templateId:null,templateName:n,uiSchema:l,workflowDefinition:d??O});return _(`success`),e}catch(e){return y(k(e)),_(`error`),null}},[i,s,l,m,n,d]),publishError:v,publishPhase:g,setCategoryId:a,setFormValue:w,setInitiatorPolicyCel:A,setName:r,setWorkflowDefinition:D,workflowDefinition:d}}var O={edges:[],meta:{schemaVersion:1},nodes:[{data:{label:`開始`},id:`start`,position:{x:80,y:160},type:`startEvent`},{data:{endState:`APPROVED`,label:`完成`,triggerMode:`AND`},id:`end`,position:{x:560,y:160},type:`endEvent`}]};function k(e){return e instanceof Error?(0,d.readFormSchemaLintMessage)(e.message):`發生未知錯誤`}function A({aiAssistantAvailable:e=!1,showAiAssistant:r=!1}={}){let i=t.r(),a=n.r(),o=D(),l=o.publishPhase===`submitting`;async function d(){let e=await o.publish();e&&i.push(a.templateDesigner(e.templateId))}return(0,c.jsxs)(c.Fragment,{children:[(0,c.jsx)(s.PageHeader,{children:(0,c.jsx)(u.default,{description:`一次完成表單與流程設計,發佈後即可直接發起。`,title:`建立模板(表單 + 流程)`,children:(0,c.jsx)(s.Button,{disabled:l,onClick:()=>i.push(a.templates()),variant:`base-secondary`,children:`返回模板列表`})})}),(0,c.jsx)(s.SectionGroup,{children:(0,c.jsxs)(s.Section,{children:[(0,c.jsxs)(s.Stepper,{currentStep:o.currentStep,children:[(0,c.jsx)(s.Step,{description:`設計欄位與版面`,title:`表單設計`}),(0,c.jsx)(s.Step,{description:`設計簽核節點與條件`,title:`流程設計`}),(0,c.jsx)(s.Step,{description:`確認後發佈`,title:`檢視並發佈`})]}),o.currentStep===0?(0,c.jsx)(h,{categoryId:o.categoryId,formSchema:o.formSchema,formUiSchema:o.formUiSchema,name:o.name,onCategoryIdChange:o.setCategoryId,onFormChange:o.setFormValue,onNameChange:o.setName}):null,o.currentStep===1?(0,c.jsx)(w,{aiAssistantAvailable:e,formSchema:o.formSchema,initiatorPolicyCel:o.initiatorPolicyCel,onInitiatorPolicyChange:o.setInitiatorPolicyCel,onWorkflowChange:o.setWorkflowDefinition,showAiAssistant:r,workflowDefinition:o.workflowDefinition}):null,o.currentStep===2?(0,c.jsx)(_,{formSchema:o.formSchema,formUiSchema:o.formUiSchema,initiatorPolicyCel:o.initiatorPolicyCel,name:o.name,publishError:o.publishError,workflowDefinition:o.workflowDefinition}):null,(0,c.jsxs)(`div`,{style:j,children:[o.currentStep===0&&!o.canLeaveBasics?(0,c.jsx)(s.Typography,{color:`text-neutral`,variant:`caption`,children:`請填寫模板名稱、表單名稱,並至少新增一個表單欄位。`}):(0,c.jsx)(`span`,{}),(0,c.jsxs)(`div`,{style:M,children:[(0,c.jsx)(s.Button,{disabled:o.currentStep===0||l,onClick:o.goBack,variant:`base-secondary`,children:`上一步`}),o.currentStep<2?(0,c.jsx)(s.Button,{disabled:o.currentStep===0&&!o.canLeaveBasics,onClick:o.goNext,variant:`base-primary`,children:`下一步`}):(0,c.jsx)(s.Button,{disabled:l,loading:l,onClick:()=>{d()},variant:`base-primary`,children:`發佈`})]})]})]})})]})}var j={alignItems:`center`,display:`flex`,marginTop:`var(--mzn-spacing-padding-vertical-spacious)`,justifyContent:`space-between`,gap:16},M={display:`flex`,gap:8};Object.defineProperty(exports,"i",{enumerable:!0,get:function(){return D}}),Object.defineProperty(exports,"n",{enumerable:!0,get:function(){return T}}),Object.defineProperty(exports,"r",{enumerable:!0,get:function(){return E}}),Object.defineProperty(exports,"t",{enumerable:!0,get:function(){return A}});
2
- //# sourceMappingURL=compose-CODnd9-2.cjs.map
@@ -1,2 +0,0 @@
1
- "use client";require('../dashboard-page.css');const e=require("./chunk-CMqjfN_6.cjs"),t=require("./router-adapter--gYs13E8.cjs"),n=require("./auth-provider-4BeCw7cI.cjs"),r=require("./routes-config-fDVHmvXi.cjs");let i=require("react"),a=require("@mezzanine-ui/react"),o=require("react/jsx-runtime"),s=require("@rytass/bpm-core-client/workflow"),c=require("@mezzanine-ui/react/ContentHeader");c=e.t(c,1);let l=require("@mezzanine-ui/icons");var u={metricCard:`bpm_metricCard_vp2qC`},d={activeInstanceCount:0,completedInstanceCount:0,overdueTaskCount:0,pendingTaskCount:0,rejectedInstanceCount:0,totalInstanceCount:0,unreadNotificationCount:0};function f(){let e=t.r(),f=r.r(),{member:h}=n.n(),g=h?.memberId??null,[_,v]=(0,i.useState)(null),[y,b]=(0,i.useState)(!0),[x,S]=(0,i.useState)(d),C=(0,i.useCallback)(async()=>{if(!g){b(!1);return}b(!0),v(null);try{S(await(0,s.readWorkflowDashboardSummary)({currentMemberId:g,from:null,to:null}))}catch(e){v(m(e))}finally{b(!1)}},[g]);(0,i.useEffect)(()=>{C()},[C]);let w=(0,i.useMemo)(()=>[{caption:`目前需要你處理的任務`,href:f.inbox(),label:`待處理簽核`,value:p(x.pendingTaskCount,y)},{caption:`尚未讀取的站內通知`,href:f.inbox(),label:`未讀通知`,value:p(x.unreadNotificationCount,y)},{caption:`目前仍在流程中的案件`,href:f.search(),label:`進行中案件`,value:p(x.activeInstanceCount,y)},{caption:`已超過 SLA 的待處理任務`,href:f.inbox(),label:`逾時任務`,value:p(x.overdueTaskCount,y)},{caption:`你有權限查看的全部案件`,href:f.search(),label:`案件總數`,value:p(x.totalInstanceCount,y)}],[y,f,x]);return(0,o.jsxs)(o.Fragment,{children:[(0,o.jsx)(a.PageHeader,{children:(0,o.jsx)(c.default,{description:`查看待處理簽核、近期通知與你發起的案件進度。`,title:`工作台`,children:(0,o.jsx)(a.Button,{icon:l.PlusIcon,iconType:`leading`,onClick:()=>e.push(f.caseNew()),variant:`base-primary`,children:`發起簽核`})})}),(0,o.jsx)(a.SectionGroup,{children:(0,o.jsxs)(a.Section,{children:[_?(0,o.jsx)(a.Typography,{color:`text-error`,variant:`body`,children:_}):null,(0,o.jsx)(a.CardGroup,{children:w.map(t=>(0,o.jsx)(a.BaseCard,{"aria-label":`前往${t.label}`,className:u.metricCard,description:t.value,onClick:()=>e.push(t.href),onKeyDown:n=>{(n.key===`Enter`||n.key===` `)&&(n.preventDefault(),e.push(t.href))},role:`link`,tabIndex:0,title:t.label,children:(0,o.jsx)(a.Typography,{color:`text-neutral`,variant:`caption`,children:t.caption})},t.label))})]})})]})}function p(e,t){return t?`-`:String(e)}function m(e){return e instanceof Error?e.message:`讀取工作台摘要失敗。`}Object.defineProperty(exports,"t",{enumerable:!0,get:function(){return f}});
2
- //# sourceMappingURL=dashboard-page-DwHQY6Ki.cjs.map
@@ -1,2 +0,0 @@
1
- "use client";require('../delegations.css');const e=require("./chunk-CMqjfN_6.cjs"),t=require("./auth-provider-4BeCw7cI.cjs"),n=require("./format-date-time-XxBzF0F5.cjs"),r=require("./bpm-form-field-Bc6k4ZEO.cjs");let i=require("react"),a=require("@mezzanine-ui/react"),o=require("react/jsx-runtime"),s=require("@rytass/bpm-core-client/workflow"),c=require("@mezzanine-ui/core/form"),l=require("@mezzanine-ui/react/ContentHeader");l=e.t(l,1);let u=require("@mezzanine-ui/icons"),d=require("@rytass/bpm-core-client/template");var f={delegationModalFields:`bpm_delegationModalFields_gUlCQ`,delegationFilterArea:`bpm_delegationFilterArea_QDZkw`,memberNameWithTooltip:`bpm_memberNameWithTooltip_RggTW`},p=c.FormFieldLayout.HORIZONTAL,m=[10,20,50],h=[{key:`ALL`,label:`全部`},{key:`ACTIVE`,label:`啟用中`},{key:`REVOKED`,label:`已撤銷`},{key:`EXPIRED`,label:`已過期`}],g=[{id:`ALL`,name:`全部簽核`},{id:`TEMPLATE_LIST`,name:`指定模板`}],_=[{id:`ALL_SCOPES`,name:`全部範圍`,scopeType:null},{id:`ALL`,name:`全部簽核`,scopeType:`ALL`},{id:`TEMPLATE_LIST`,name:`指定模板`,scopeType:`TEMPLATE_LIST`}];function v(){let{member:e}=t.n(),p=e?.memberId??null,[v,x]=(0,i.useState)(null),[C,w]=(0,i.useState)(``),[E,D]=(0,i.useState)(null),[O,A]=(0,i.useState)(!0),[j,M]=(0,i.useState)(!1),[N,P]=(0,i.useState)([]),[F,de]=(0,i.useState)(null),[I,fe]=(0,i.useState)(null),[pe,L]=(0,i.useState)(!1),[R,z]=(0,i.useState)(null),[B,me]=(0,i.useState)(`100`),[V,H]=(0,i.useState)(1),[U,he]=(0,i.useState)(10),[W,ge]=(0,i.useState)(`ALL`),[_e,ve]=(0,i.useState)(0),[ye,be]=(0,i.useState)([]),[xe,Se]=(0,i.useState)(!1),[G,Ce]=(0,i.useState)([]),[K,we]=(0,i.useState)(_[0]),[Te,Ee]=(0,i.useState)(g[0]),[q,De]=(0,i.useState)(``),[Oe,ke]=(0,i.useState)(!1),[Ae,J]=(0,i.useState)([]),Y=(0,i.useCallback)(async()=>{A(!0),D(null);try{let[e,t]=await Promise.all([(0,s.listDelegationRulesPage)({agentMemberId:I?.id??null,includeInactive:!0,page:V,pageSize:U,principalMemberId:F?.id??null,scopeType:K.scopeType,status:W===`ALL`?null:W}),(0,s.searchMembers)(``)]);be(e.rules),ve(e.totalCount),P(t.map(b))}catch(e){D(k(e))}finally{A(!1)}},[I,F,V,U,W,K]);(0,i.useEffect)(()=>{Y()},[Y]);let X=(0,i.useMemo)(()=>new Map(N.map(e=>[e.id,e])),[N]),je=(0,i.useMemo)(()=>ye.map(e=>({...e,agentEmail:X.get(e.agentMemberId)?.email??null,agentName:X.get(e.agentMemberId)?.displayName??e.agentMemberId,key:e.id,principalEmail:X.get(e.principalMemberId)?.email??null,principalName:X.get(e.principalMemberId)?.displayName??e.principalMemberId,scopeLabel:oe(e)})),[X,ye]),Z=g.find(e=>e.id===Te.id)??g[0],Me=(0,i.useMemo)(()=>[{key:`principal`,render:e=>(0,o.jsx)(S,{email:e.principalEmail,name:e.principalName}),title:`原簽核人`,width:220},{key:`agent`,render:e=>(0,o.jsx)(S,{email:e.agentEmail,name:e.agentName}),title:`代理人`,width:220},{dataIndex:`scopeLabel`,key:`scope`,title:`代理範圍`,width:220},{key:`status`,render:e=>(0,o.jsx)(se,{status:e.status}),title:`狀態`,width:120},{dataIndex:`priority`,key:`priority`,title:`優先序`,width:100},{key:`startAt`,render:e=>(0,o.jsx)(a.Typography,{component:`span`,variant:`body`,children:n.t(e.startAt)}),title:`開始時間`,width:220},{key:`endAt`,render:e=>(0,o.jsx)(a.Typography,{component:`span`,variant:`body`,children:e.endAt?n.t(e.endAt):`-`}),title:`結束時間`,width:220}],[]),Ne=(0,i.useCallback)(async e=>{if(p){D(null);try{await(0,s.revokeDelegationRule)({id:e,revokedByMemberId:p}),await Y()}catch(e){D(k(e))}}},[p,Y]),Pe=(0,i.useMemo)(()=>({render:e=>e.status===`ACTIVE`?[{name:`撤銷`,onClick:()=>void Ne(e.id)}]:[],variant:`destructive-secondary`,width:88}),[Ne]);async function Q(e){M(!0);try{P((await(0,s.searchMembers)(e)).map(b))}catch(e){D(k(e))}finally{M(!1)}}async function $(e,t=G){ke(!0);try{J(re(t,ne((await(0,d.listApprovalTemplates)()).map(ee),e)))}catch(e){D(k(e))}finally{ke(!1)}}function Fe(){x(null),w(``),z(null),me(`100`),Ce([]),Ee(g[0]),De(``),J([]),$(``,[]),L(!0)}function Ie(){xe||L(!1)}async function Le(){if(p){if(!R||!v){D(`請選擇原簽核人與代理人`);return}if(Z.id===`TEMPLATE_LIST`&&G.length<1){D(`請選擇至少一個簽核模板`);return}if(ue(q,C)){D(`結束時間必須晚於起始時間`);return}Se(!0),D(null);try{await(0,s.createDelegationRule)({agentMemberId:v.id,createdByMemberId:p,endAt:C||null,principalMemberId:R.id,priority:Number(B)||100,requiresConfirmation:!1,scopeConditionCel:null,scopeTemplateIds:Z.id===`TEMPLATE_LIST`?G.map(e=>e.id):[],scopeType:Z.id,startAt:q||null}),L(!1),V===1?await Y():H(1)}catch(e){D(k(e))}finally{Se(!1)}}}return(0,o.jsxs)(o.Fragment,{children:[(0,o.jsx)(a.PageHeader,{children:(0,o.jsx)(l.default,{description:`設定簽核代理規則,讓符合範圍的待簽任務自動改派給代理人。`,title:`代理設定`,children:(0,o.jsx)(a.Button,{icon:u.PlusIcon,iconType:`leading`,onClick:Fe,variant:`base-primary`,children:`建立代理`})})}),(0,o.jsx)(a.SectionGroup,{children:(0,o.jsxs)(a.Section,{filterArea:(0,o.jsx)(a.FilterArea,{className:f.delegationFilterArea,children:(0,o.jsxs)(a.FilterLine,{children:[(0,o.jsx)(a.Filter,{span:2,children:(0,o.jsx)(y,{hideLabel:!0,label:`原簽核人`,loading:j,name:`principalFilterMemberId`,onChange:e=>{de(e),H(1)},onSearch:Q,options:N,required:!1,layout:c.FormFieldLayout.VERTICAL,size:`sub`,value:F})}),(0,o.jsx)(a.Filter,{span:2,children:(0,o.jsx)(y,{hideLabel:!0,label:`代理人`,loading:j,name:`agentFilterMemberId`,onChange:e=>{fe(e),H(1)},onSearch:Q,options:N,required:!1,layout:c.FormFieldLayout.VERTICAL,size:`sub`,value:I})}),(0,o.jsx)(a.Filter,{span:2,children:(0,o.jsx)(a.FormField,{fullWidth:!0,layout:c.FormFieldLayout.VERTICAL,name:`scopeFilterType`,children:(0,o.jsx)(a.Select,{clearable:!1,fullWidth:!0,onChange:e=>{we(ae(e)),H(1)},options:[..._],placeholder:`代理範圍`,size:`sub`,value:K})})})]})}),tab:(0,o.jsx)(a.Tab,{activeKey:W,onChange:e=>{ge(ce(e)),H(1)},children:h.map(e=>(0,o.jsx)(a.TabItem,{children:e.label},e.key))}),children:[E?(0,o.jsx)(a.Typography,{color:`text-error`,variant:`body`,children:E}):null,(0,o.jsx)(a.Table,{actions:Pe,columns:Me,dataSource:je,fullWidth:!0,loading:O,pagination:{current:V,onChange:e=>{H(e)},onChangePageSize:e=>{H(1),he(e)},pageSize:U,pageSizeLabel:`每頁筆數`,pageSizeOptions:m,renderResultSummary:(e,t,n)=>`顯示 ${e}-${t} 筆,共 ${n} 筆`,showPageSizeOptions:!0,total:_e}})]})}),(0,o.jsx)(a.Modal,{cancelText:`取消`,confirmButtonProps:{disabled:!R||!v},confirmText:`建立代理`,loading:xe,modalType:`standard`,onCancel:Ie,onClose:Ie,onConfirm:()=>void Le(),open:pe,showModalFooter:!0,showModalHeader:!0,size:`regular`,supportingText:`代理生效後,後續建立的待簽任務會依範圍自動指派。`,title:`建立代理`,children:(0,o.jsxs)(`div`,{className:f.delegationModalFields,children:[(0,o.jsx)(y,{label:`原簽核人`,loading:j,name:`principalMemberId`,onChange:z,onSearch:Q,options:N,value:R}),(0,o.jsx)(y,{label:`代理人`,loading:j,name:`agentMemberId`,onChange:x,onSearch:Q,options:N,value:v}),(0,o.jsx)(r.t,{label:`代理範圍`,name:`scopeType`,required:!0,children:(0,o.jsx)(a.Select,{clearable:!1,fullWidth:!0,onChange:e=>Ee(ie(e)),options:[...g],value:Z})}),Z.id===`TEMPLATE_LIST`?(0,o.jsx)(r.t,{label:`簽核模板`,name:`scopeTemplateIds`,required:!0,children:(0,o.jsx)(a.AutoComplete,{asyncData:!0,disabledOptionsFilter:!0,emptyText:`沒有符合的模板`,inputProps:{autoCapitalize:`none`,autoCorrect:`off`,name:`scopeTemplateIds`,spellCheck:!1},loading:Oe,loadingText:`搜尋模板中...`,mode:`multiple`,onChange:e=>{let t=te(e);Ce(t),J(e=>re(t,e))},onSearch:$,onVisibilityChange:e=>{e&&$(``)},options:[...Ae],overflowStrategy:`wrap`,placeholder:`搜尋並選取簽核模板`,searchDebounceTime:300,value:[...G]})}):null,(0,o.jsx)(r.t,{label:`優先序`,name:`priority`,children:(0,o.jsx)(a.Input,{fullWidth:!0,onChange:e=>me(e.target.value),value:B,variant:`base`})}),(0,o.jsx)(r.t,{label:`起始時間`,name:`startAt`,children:(0,o.jsx)(a.DateTimePicker,{formatDate:`YYYY-MM-DD`,formatTime:`HH:mm`,fullWidth:!0,hideSecond:!0,onChange:e=>De(T(e)),placeholderLeft:`留空立即生效`,placeholderRight:`選擇時間`,value:le(q)})}),(0,o.jsx)(r.t,{label:`結束時間`,name:`endAt`,children:(0,o.jsx)(a.DateTimePicker,{formatDate:`YYYY-MM-DD`,formatTime:`HH:mm`,fullWidth:!0,hideSecond:!0,onChange:e=>w(T(e)),placeholderLeft:`可留空`,placeholderRight:`選擇時間`,value:le(C)})})]})})]})}function y({hideLabel:e=!1,label:t,layout:n=p,loading:i,name:s,onChange:c,onSearch:l,options:u,required:d=!0,size:f,value:m}){let h=(0,o.jsx)(a.AutoComplete,{asyncData:!0,disabledOptionsFilter:!0,emptyText:`沒有符合的成員`,inputProps:{autoCapitalize:`none`,autoCorrect:`off`,name:s,spellCheck:!1},loading:i,loadingText:`搜尋成員中...`,mode:`single`,onChange:e=>c(x(e)),onSearch:l,onSearchTextChange:e=>c(C(e,u)),onVisibilityChange:e=>{e&&l(``)},options:[...u],placeholder:e?t:`搜尋姓名或信箱`,searchDebounceTime:300,size:f,value:m});return e?(0,o.jsx)(a.FormField,{fullWidth:!0,layout:n,name:s,children:h}):(0,o.jsx)(r.t,{label:t,layout:n,name:s,required:d,children:h})}function b(e){return{displayName:e.name,email:e.email,id:e.memberId,name:`${e.name} · ${e.email}`}}function x(e){if(!A(e))return null;let t=e.id,n=e.name,r=e.email,i=e.displayName;return typeof t==`string`&&typeof n==`string`?{displayName:typeof i==`string`?i:n,email:typeof r==`string`?r:null,id:t,name:n}:null}function S({email:e,name:t}){return e?(0,o.jsx)(a.Tooltip,{title:e,children:({onMouseEnter:e,onMouseLeave:n,ref:r})=>(0,o.jsx)(`span`,{className:f.memberNameWithTooltip,onMouseEnter:e,onMouseLeave:n,ref:r,children:t})}):(0,o.jsx)(`span`,{children:t})}function C(e,t){let n=e.trim().toLocaleLowerCase();if(!n)return null;let r=t.filter(e=>[e.id,e.name,e.email??``].some(e=>e.toLocaleLowerCase().includes(n)));return r.length===1?r[0]??null:null}function ee(e){return{id:e.id,name:e.name}}function te(e){return e.flatMap(e=>{if(!A(e))return[];let t=e.id,n=e.name;return typeof t==`string`&&typeof n==`string`?[{id:t,name:n}]:[]})}function ne(e,t){let n=t.trim().toLocaleLowerCase();return n?e.filter(e=>[e.id,e.name].some(e=>e.toLocaleLowerCase().includes(n))):e}function re(e,t){return[...e,...t].reduce((e,t)=>e.some(e=>e.id===t.id)?e:[...e,t],[])}function ie(e){return!A(e)||!w(e.id)?g[0]:g.find(t=>t.id===e.id)??g[0]}function ae(e){if(!A(e))return _[0];let t=e.id;return _.find(e=>e.id===t)??_[0]}function w(e){return e===`ALL`||e===`TEMPLATE_LIST`}function oe(e){return e.scopeType===`ALL`?`全部簽核`:e.scopeType===`TEMPLATE_LIST`?`指定模板:${e.scopeTemplateIds.length}`:e.scopeConditionCel?`條件:${e.scopeConditionCel}`:`條件式`}function se({status:e}){return e===`ACTIVE`?(0,o.jsx)(a.Badge,{size:`sub`,text:`啟用中`,variant:`dot-success`}):e===`REVOKED`?(0,o.jsx)(a.Badge,{size:`sub`,text:`已撤銷`,variant:`dot-inactive`}):e===`EXPIRED`?(0,o.jsx)(a.Badge,{size:`sub`,text:`已過期`,variant:`dot-warning`}):(0,o.jsx)(a.Badge,{size:`sub`,text:e,variant:`dot-info`})}function ce(e){return e===`ACTIVE`||e===`REVOKED`||e===`EXPIRED`?e:`ALL`}function le(e){let t=e?E(e):null;return t?`${D(t)}T${O(t.getHours())}:${O(t.getMinutes())}`:void 0}function T(e){let t=e?E(e):null;return t?t.toISOString():``}function ue(e,t){if(!e||!t)return!1;let n=E(e),r=E(t);return!!n&&!!r&&r.getTime()<=n.getTime()}function E(e){if(e.endsWith(`Z`)||/[+-]\d{2}:\d{2}$/.test(e)){let t=new Date(e);return Number.isNaN(t.getTime())?null:t}let[t=``,n=`00:00`]=e.split(`T`),[r=0,i=1,a=1]=t.split(`-`).map(Number),[o=0,s=0]=n.split(`:`).map(Number),c=new Date(r,i-1,a,o,s);return Number.isNaN(c.getTime())?null:c}function D(e){return`${e.getFullYear()}-${O(e.getMonth()+1)}-${O(e.getDate())}`}function O(e){return String(e).padStart(2,`0`)}function k(e){return e instanceof Error?e.message:`發生未知錯誤`}function A(e){return typeof e==`object`&&!!e}Object.defineProperty(exports,"t",{enumerable:!0,get:function(){return v}});
2
- //# sourceMappingURL=delegations-CGj-tZNO.cjs.map
@@ -1,2 +0,0 @@
1
- "use client";require('../delegations2.css');const e=require("./chunk-CMqjfN_6.cjs"),t=require("./auth-provider-4BeCw7cI.cjs"),n=require("./format-date-time-XxBzF0F5.cjs"),r=require("./bpm-form-field-Bc6k4ZEO.cjs");let i=require("react"),a=require("@mezzanine-ui/react"),o=require("react/jsx-runtime"),s=require("@rytass/bpm-core-client/workflow"),c=require("@mezzanine-ui/core/form"),l=require("@mezzanine-ui/react/ContentHeader");l=e.t(l,1);let ee=require("@mezzanine-ui/icons"),te=require("@rytass/bpm-core-client/template");var u={delegationFilterArea:`bpm_delegationFilterArea_hAA4C`,delegationModalFields:`bpm_delegationModalFields_1aOVW`,memberNameWithTooltip:`bpm_memberNameWithTooltip_6Mojc`},d=c.FormFieldLayout.HORIZONTAL,ne=[10,20,50],re=[{key:`ALL`,label:`全部`},{key:`ACTIVE`,label:`啟用中`},{key:`REVOKED`,label:`已撤銷`},{key:`EXPIRED`,label:`已過期`}],f=[{id:`ALL_SCOPES`,name:`全部範圍`,scopeType:null},{id:`ALL`,name:`全部簽核`,scopeType:`ALL`},{id:`TEMPLATE_LIST`,name:`指定模板`,scopeType:`TEMPLATE_LIST`}],p=[{id:`ALL`,name:`全部簽核`},{id:`TEMPLATE_LIST`,name:`指定模板`}];function m(){let{member:e}=t.n(),d=e?.memberId??null,[m,g]=(0,i.useState)(null),[_,y]=(0,i.useState)(``),[S,C]=(0,i.useState)(null),[w,E]=(0,i.useState)(!0),[he,D]=(0,i.useState)(!1),[O,k]=(0,i.useState)([]),[ge,A]=(0,i.useState)(!1),[j,M]=(0,i.useState)(1),[N,_e]=(0,i.useState)(10),[P,ve]=(0,i.useState)(`ALL`),[ye,be]=(0,i.useState)(0),[F,xe]=(0,i.useState)([]),[I,L]=(0,i.useState)(!1),[R,Se]=(0,i.useState)(f[0]),[z,B]=(0,i.useState)([]),[Ce,V]=(0,i.useState)(p[0]),[H,U]=(0,i.useState)(``),[we,W]=(0,i.useState)(!1),[Te,G]=(0,i.useState)([]),K=(0,i.useRef)(0),q=(0,i.useCallback)(async()=>{let e=K.current+1;if(K.current=e,!d){E(!1);return}E(!0),C(null);try{let[t,n]=await Promise.all([(0,s.listDelegationRulesPage)({includeInactive:!0,page:j,pageSize:N,principalMemberId:d,scopeType:R.scopeType,status:P===`ALL`?null:P}),(0,s.searchMembers)(``)]);e===K.current&&(xe(t.rules),be(t.totalCount),k(n.map(h)))}catch(t){e===K.current&&C(T(t))}finally{e===K.current&&E(!1)}},[d,j,N,P,R]);(0,i.useEffect)(()=>{q()},[q]);let J=(0,i.useMemo)(()=>new Map(O.map(e=>[e.id,e])),[O]),Ee=(0,i.useMemo)(()=>F.map(e=>({...e,agentEmail:J.get(e.agentMemberId)?.email??null,agentName:J.get(e.agentMemberId)?.displayName??e.agentMemberId,key:e.id,scopeLabel:ue(e)})),[J,F]),Y=p.find(e=>e.id===Ce.id)??p[0],X=(0,i.useMemo)(()=>[{key:`agent`,render:e=>(0,o.jsx)(ae,{email:e.agentEmail,name:e.agentName}),title:`代理人`,width:220},{dataIndex:`scopeLabel`,key:`scope`,title:`代理範圍`,width:220},{key:`status`,render:e=>(0,o.jsx)(fe,{status:e.status}),title:`狀態`,width:120},{key:`startAt`,render:e=>(0,o.jsx)(a.Typography,{component:`span`,variant:`body`,children:n.t(e.startAt)}),title:`開始時間`,width:220},{key:`endAt`,render:e=>(0,o.jsx)(a.Typography,{component:`span`,variant:`body`,children:e.endAt?n.t(e.endAt):`-`}),title:`結束時間`,width:220}],[]),Z=(0,i.useCallback)(async e=>{if(d){C(null);try{await(0,s.revokeDelegationRule)({id:e,revokedByMemberId:d}),await q()}catch(e){C(T(e))}}},[d,q]),De=(0,i.useMemo)(()=>({render:e=>e.status===`ACTIVE`?[{name:`撤銷`,onClick:()=>void Z(e.id)}]:[],variant:`destructive-secondary`,width:88}),[Z]);async function Oe(e){D(!0);try{k((await(0,s.searchMembers)(e)).map(h))}catch(e){C(T(e))}finally{D(!1)}}async function Q(e,t=z){W(!0);try{G(v(t,ce((await(0,te.listApprovalTemplates)()).map(oe),e)))}catch(e){C(T(e))}finally{W(!1)}}function ke(){g(null),y(``),B([]),V(p[0]),U(``),G([]),Q(``,[]),A(!0)}function $(){I||A(!1)}async function Ae(){if(d){if(!m){C(`請選擇代理人`);return}if(m.id===d){C(`代理人不可設定為自己`);return}if(Y.id===`TEMPLATE_LIST`&&z.length<1){C(`請選擇至少一個簽核模板`);return}if(me(H,_)){C(`結束時間必須晚於起始時間`);return}L(!0),C(null);try{await(0,s.createDelegationRule)({agentMemberId:m.id,createdByMemberId:d,endAt:_||null,principalMemberId:d,priority:100,requiresConfirmation:!1,scopeConditionCel:null,scopeTemplateIds:Y.id===`TEMPLATE_LIST`?z.map(e=>e.id):[],scopeType:Y.id,startAt:H||null}),A(!1),j===1?await q():M(1)}catch(e){C(T(e))}finally{L(!1)}}}return(0,o.jsxs)(o.Fragment,{children:[(0,o.jsx)(a.PageHeader,{children:(0,o.jsx)(l.default,{description:`設定自己的簽核代理,讓指定期間內的新待簽任務自動交由代理人處理。`,title:`我的代理`,children:(0,o.jsx)(a.Button,{icon:ee.PlusIcon,iconType:`leading`,onClick:ke,variant:`base-primary`,children:`建立代理`})})}),(0,o.jsx)(a.SectionGroup,{children:(0,o.jsxs)(a.Section,{filterArea:(0,o.jsx)(a.FilterArea,{className:u.delegationFilterArea,size:`sub`,children:(0,o.jsx)(a.FilterLine,{children:(0,o.jsx)(a.Filter,{span:2,children:(0,o.jsx)(a.FormField,{fullWidth:!0,layout:c.FormFieldLayout.VERTICAL,name:`scopeFilterType`,children:(0,o.jsx)(a.Select,{clearable:!1,fullWidth:!0,onChange:e=>{Se(le(e)),M(1)},options:[...f],placeholder:`代理範圍`,size:`sub`,value:R})})})})}),tab:(0,o.jsx)(a.Tab,{activeKey:P,onChange:e=>{ve(pe(e)),M(1)},children:re.map(e=>(0,o.jsx)(a.TabItem,{children:e.label},e.key))}),children:[S?(0,o.jsx)(a.Typography,{color:`text-error`,variant:`body`,children:S}):null,(0,o.jsx)(a.Table,{actions:De,columns:X,dataSource:Ee,fullWidth:!0,loading:w,pagination:{current:j,onChange:e=>{M(e)},onChangePageSize:e=>{M(1),_e(e)},pageSize:N,pageSizeLabel:`每頁筆數`,pageSizeOptions:ne,renderResultSummary:(e,t,n)=>`顯示 ${e}-${t} 筆,共 ${n} 筆`,showPageSizeOptions:!0,total:ye}})]})}),(0,o.jsx)(a.Modal,{cancelText:`取消`,confirmButtonProps:{disabled:!m},confirmText:`建立代理`,loading:I,modalType:`standard`,onCancel:$,onClose:$,onConfirm:()=>void Ae(),open:ge,showModalFooter:!0,showModalHeader:!0,size:`regular`,supportingText:`代理生效後,後續建立的待簽任務會依範圍自動指派給代理人。`,title:`建立個人代理`,children:(0,o.jsxs)(`div`,{className:u.delegationModalFields,children:[(0,o.jsx)(ie,{label:`代理人`,loading:he,name:`agentMemberId`,onChange:g,onSearch:Oe,options:O,value:m}),(0,o.jsx)(r.t,{label:`代理範圍`,name:`scopeType`,required:!0,children:(0,o.jsx)(a.Select,{clearable:!1,fullWidth:!0,onChange:e=>V(de(e)),options:[...p],placeholder:`選擇代理範圍`,value:Y})}),Y.id===`TEMPLATE_LIST`?(0,o.jsx)(r.t,{label:`簽核模板`,name:`scopeTemplateIds`,required:!0,children:(0,o.jsx)(a.AutoComplete,{asyncData:!0,disabledOptionsFilter:!0,emptyText:`沒有符合的模板`,inputProps:{autoCapitalize:`none`,autoCorrect:`off`,name:`scopeTemplateIds`,spellCheck:!1},loading:we,loadingText:`搜尋模板中...`,mode:`multiple`,onChange:e=>{let t=se(e);B(t),G(e=>v(t,e))},onSearch:Q,onVisibilityChange:e=>{e&&Q(``)},options:[...Te],overflowStrategy:`wrap`,placeholder:`搜尋並選取簽核模板`,searchDebounceTime:300,value:[...z]})}):null,(0,o.jsx)(r.t,{label:`起始時間`,name:`startAt`,children:(0,o.jsx)(a.DateTimePicker,{formatDate:`YYYY-MM-DD`,formatTime:`HH:mm`,fullWidth:!0,hideSecond:!0,onChange:e=>U(x(e)),placeholderLeft:`留空立即生效`,placeholderRight:`選擇時間`,value:b(H)})}),(0,o.jsx)(r.t,{label:`結束時間`,name:`endAt`,children:(0,o.jsx)(a.DateTimePicker,{formatDate:`YYYY-MM-DD`,formatTime:`HH:mm`,fullWidth:!0,hideSecond:!0,onChange:e=>y(x(e)),placeholderLeft:`可留空`,placeholderRight:`選擇時間`,value:b(_)})})]})})]})}function ie({label:e,loading:t,name:n,onChange:i,onSearch:s,options:c,value:l}){return(0,o.jsx)(r.t,{label:e,layout:d,name:n,required:!0,children:(0,o.jsx)(a.AutoComplete,{asyncData:!0,disabledOptionsFilter:!0,emptyText:`沒有符合的成員`,inputProps:{autoCapitalize:`none`,autoCorrect:`off`,name:n,spellCheck:!1},loading:t,loadingText:`搜尋成員中...`,mode:`single`,onChange:e=>i(g(e)),onSearch:s,onSearchTextChange:e=>i(_(e,c)),onVisibilityChange:e=>{e&&s(``)},options:[...c],placeholder:`搜尋姓名或信箱`,searchDebounceTime:300,value:l})})}function ae({email:e,name:t}){return e?(0,o.jsx)(a.Tooltip,{title:e,children:({onMouseEnter:e,onMouseLeave:n,ref:r})=>(0,o.jsx)(`span`,{className:u.memberNameWithTooltip,onMouseEnter:e,onMouseLeave:n,ref:r,children:t})}):(0,o.jsx)(`span`,{children:t})}function h(e){return{displayName:e.name,email:e.email,id:e.memberId,name:`${e.name} (${e.email})`}}function g(e){if(!E(e))return null;let t=e.displayName,n=e.email,r=e.id,i=e.name;return typeof r==`string`&&typeof i==`string`?{displayName:typeof t==`string`?t:i,email:typeof n==`string`?n:null,id:r,name:i}:null}function _(e,t){let n=e.trim().toLocaleLowerCase();if(!n)return null;let r=t.filter(e=>[e.id,e.name,e.email??``].some(e=>e.toLocaleLowerCase().includes(n)));return r.length===1?r[0]??null:null}function oe(e){return{id:e.id,name:e.name}}function se(e){return e.flatMap(e=>{if(!E(e))return[];let t=e.id,n=e.name;return typeof t==`string`&&typeof n==`string`?[{id:t,name:n}]:[]})}function ce(e,t){let n=t.trim().toLocaleLowerCase();return n?e.filter(e=>[e.id,e.name].some(e=>e.toLocaleLowerCase().includes(n))):e}function v(e,t){return[...e,...t].reduce((e,t)=>e.some(e=>e.id===t.id)?e:[...e,t],[])}function le(e){if(!E(e))return f[0];let t=e.id;return f.find(e=>e.id===t)??f[0]}function ue(e){return e.scopeType===`ALL`?`全部簽核`:e.scopeType===`TEMPLATE_LIST`?`指定模板:${e.scopeTemplateIds.length}`:e.scopeConditionCel?`條件:${e.scopeConditionCel}`:`條件式`}function de(e){return!E(e)||!y(e.id)?p[0]:p.find(t=>t.id===e.id)??p[0]}function y(e){return e===`ALL`||e===`TEMPLATE_LIST`}function fe({status:e}){return e===`ACTIVE`?(0,o.jsx)(a.Badge,{size:`sub`,text:`啟用中`,variant:`dot-success`}):e===`REVOKED`?(0,o.jsx)(a.Badge,{size:`sub`,text:`已撤銷`,variant:`dot-inactive`}):e===`EXPIRED`?(0,o.jsx)(a.Badge,{size:`sub`,text:`已過期`,variant:`dot-warning`}):(0,o.jsx)(a.Badge,{size:`sub`,text:e,variant:`dot-info`})}function pe(e){return e===`ACTIVE`||e===`REVOKED`||e===`EXPIRED`?e:`ALL`}function b(e){let t=e?S(e):null;return t?`${C(t)}T${w(t.getHours())}:${w(t.getMinutes())}`:void 0}function x(e){let t=e?S(e):null;return t?t.toISOString():``}function me(e,t){if(!e||!t)return!1;let n=S(e),r=S(t);return!!n&&!!r&&r.getTime()<=n.getTime()}function S(e){if(e.endsWith(`Z`)||/[+-]\d{2}:\d{2}$/.test(e)){let t=new Date(e);return Number.isNaN(t.getTime())?null:t}let[t=``,n=`00:00`]=e.split(`T`),[r=0,i=1,a=1]=t.split(`-`).map(Number),[o=0,s=0]=n.split(`:`).map(Number),c=new Date(r,i-1,a,o,s);return Number.isNaN(c.getTime())?null:c}function C(e){return`${e.getFullYear()}-${w(e.getMonth()+1)}-${w(e.getDate())}`}function w(e){return String(e).padStart(2,`0`)}function T(e){return e instanceof Error?e.message:`發生未知錯誤`}function E(e){return typeof e==`object`&&!!e}Object.defineProperty(exports,"t",{enumerable:!0,get:function(){return m}});
2
- //# sourceMappingURL=delegations-kbMOSEif.cjs.map
@@ -1,65 +0,0 @@
1
- "use client";require('../style.css');const e=require("./chunk-CMqjfN_6.cjs"),t=require("./router-adapter--gYs13E8.cjs"),n=require("./routes-config-fDVHmvXi.cjs"),r=require("./bpm-form-field-Bc6k4ZEO.cjs"),i=require("./admin-pickers-Btvij1at.cjs");;/* empty css */const a=require("./FormBuilderView-D6baVqBY.cjs");let o=require("react"),s=require("@mezzanine-ui/react"),c=require("react/jsx-runtime"),l=require("@mezzanine-ui/react/Drawer");l=e.t(l,1);let u=require("@mezzanine-ui/react/ContentHeader");u=e.t(u,1);let d=require("@mezzanine-ui/icons"),f=require("ai"),p=require("@rytass/bpm-core-shared"),m=require("@rytass/bpm-core-client/form"),h=require("@rytass/bpm-core-shared/form"),g=require("@rytass/bpm-core-client/organization"),_=require("@xyflow/react"),v=require("dagre");v=e.t(v,1);let y=require("@rytass/bpm-core-client/template"),ee=require("@ai-sdk/react"),b=require("@rytass/bpm-core-shared/workflow-graph");function x({directory:e,initialState:t,layout:n,onLayout:r}){let[i,a]=(0,o.useState)(t),s=(0,o.useRef)(t),c=(0,o.useRef)(e);c.current=e;let l=(0,o.useCallback)(e=>{if(!e.changed&&!e.error)return e;let t=e.effects.layout?n(e.state.definition):e.state.definition,i={...e.state,definition:t};return s.current=i,a(i),e.effects.layout&&r?.(t),{...e,state:i}},[n,r]),u=(0,o.useCallback)(e=>l((0,p.applyWorkflowCommand)(s.current,e)),[l]),d=(0,o.useCallback)(e=>l((0,p.applyWorkflowMacroCommand)(s.current,e)),[l]),f=(0,o.useCallback)(async(e,t)=>{let n=await(0,p.executeWorkflowTool)(s.current,e,t,{directory:c.current});if(n.ok&&(n.kind===`mutation`||n.kind===`macro`)){let e=l(n.result);return{...n,result:e,snapshot:(0,p.readWorkflowSnapshot)(e.state)}}return n},[l]),m=(0,o.useCallback)(e=>{let t=typeof e==`function`?e(s.current):e;s.current=t,a(t)},[]),h=(0,o.useCallback)(()=>s.current,[]),g=(0,o.useMemo)(()=>(0,p.readWorkflowSnapshot)(i),[i]);return(0,o.useMemo)(()=>({dispatch:u,dispatchMacro:d,executeTool:f,getState:h,replaceState:m,snapshot:g,state:i,tools:p.WORKFLOW_TOOLSET}),[u,d,f,h,m,g,i])}function te({controller:e,api:t=`/api/chat`}){let n=(0,ee.useChat)({transport:(0,o.useMemo)(()=>new f.DefaultChatTransport({api:t}),[t]),sendAutomaticallyWhen:f.lastAssistantMessageIsCompleteWithToolCalls,async onToolCall({toolCall:t}){let r=await e.executeTool(t.toolName,t.input);if(r.ok){n.addToolOutput({output:r.kind===`query`?r.data:r.snapshot,tool:t.toolName,toolCallId:t.toolCallId});return}n.addToolOutput({errorText:r.error,state:`output-error`,tool:t.toolName,toolCallId:t.toolCallId})}});return n}var ne=12;function re(){let e=globalThis.LanguageModel;return e&&typeof e==`object`?e:null}var ie={additionalProperties:!1,properties:{action:{enum:[`tool`,`message`],type:`string`},input:{type:`object`},text:{type:`string`},tool:{type:`string`}},required:[`action`],type:`object`};function ae(){return`你是「簽核流程設計器」頁面的離線 AI 助理。只能透過下列工具操作這個流程畫布,其他請求一律婉拒並引導回流程設計。
2
-
3
- 每一步只輸出一個 JSON 決策物件:
4
- - 呼叫工具:{"action":"tool","tool":"<工具名>","input":{...}}
5
- - 回覆使用者(完成或詢問):{"action":"message","text":"<繁體中文訊息>"}
6
-
7
- 規則:先用 get_workflow_snapshot 了解現況再規劃;完成後用 validate_workflow 檢查並以 message 說明做了什麼。
8
-
9
- 可用工具:
10
- ${p.WORKFLOW_TOOLSET.map(e=>`- ${e.name}(${JSON.stringify(e.inputSchema.properties??{})}): ${e.description}`).join(`
11
- `)}`}function oe({controller:e}){let[t,n]=(0,o.useState)(!1),[r,i]=(0,o.useState)([]),[a,s]=(0,o.useState)(`ready`),c=(0,o.useRef)(0);(0,o.useEffect)(()=>{let e=re();e&&e.availability().then(e=>{n(e!==`unavailable`)}).catch(()=>n(!1))},[]);let l=(0,o.useCallback)((e,t)=>{c.current+=1,i(n=>[...n,{id:`chrome-${c.current}`,parts:[{text:t,type:`text`}],role:e}])},[]);return{available:t,messages:r,send:(0,o.useCallback)(t=>{let n=re();!n||a!==`ready`||(l(`user`,t),s(`submitted`),S({appendMessage:l,controller:e,model:n,userText:t}).then(()=>s(`ready`)).catch(e=>{l(`assistant`,C(e)),s(`error`)}))},[l,e,a]),status:a}}async function S({appendMessage:e,controller:t,model:n,userText:r}){let i=await n.create({initialPrompts:[{content:ae(),role:`system`}]});try{let n=`使用者需求:${r}\n目前流程:${JSON.stringify(t.snapshot)}`;for(let r=0;r<ne;r+=1){let r=se(await i.prompt(n,{responseConstraint:ie}));if(!r||r.action===`message`){e(`assistant`,r?.text??`我已完成可處理的部分。`);return}if(!r.tool){e(`assistant`,`我已完成可處理的部分。`);return}let a=await t.executeTool(r.tool,r.input??{});if(a.ok){let t=a.kind===`query`?a.data:a.snapshot;e(`assistant`,`⚙ ${r.tool}`),n=`工具 ${r.tool} 已執行。最新流程:${JSON.stringify(t)}\n請決定下一步。`}else n=`工具 ${r.tool} 失敗:${a.error}\n請改用其他方式或回覆使用者。`}e(`assistant`,`已達到單次操作步數上限,請告訴我下一步。`)}finally{i.destroy()}}function se(e){try{let t=JSON.parse(e);return typeof t==`object`&&t&&t.action!==void 0?t:null}catch{return null}}function C(e){return e instanceof Error?`離線模式發生錯誤:${e.message}`:`離線模式發生未知錯誤。`}var ce={display:`flex`,flexDirection:`column`,gap:12,height:`100%`},le={display:`flex`,flex:1,flexDirection:`column`,gap:12,minHeight:0,overflowY:`auto`},ue={display:`flex`,gap:8,paddingBottom:4},de={borderTop:`1px solid var(--mzn-color-border-neutral, #e5e7eb)`,display:`flex`,flexDirection:`column`,gap:8,paddingTop:12},fe={display:`flex`,justifyContent:`flex-end`},pe={width:`100%`},me=`workflow-chat-input-field`,he=`
12
- .${me}.mzn-text-field {
13
- width: 100%;
14
- }
15
- `,ge={color:`var(--mzn-color-text-secondary, #6b7280)`,fontSize:12,padding:`2px 0`},_e={"input-available":`執行中…`,"input-streaming":`準備中…`,"output-available":`完成`,"output-error":`失敗`};function ve(e){let t=e===`user`;return{alignSelf:t?`flex-end`:`flex-start`,background:t?`var(--mzn-color-primary, #2563eb)`:`var(--mzn-color-surface, #f3f4f6)`,borderRadius:10,color:t?`#fff`:`var(--mzn-color-text-primary, #111827)`,maxWidth:`85%`,padding:`8px 12px`,whiteSpace:`pre-wrap`,wordBreak:`break-word`}}function ye({api:e,controller:t,onClose:n,open:r}){let i=te({api:e,controller:t}),a=oe({controller:t}),[u,d]=(0,o.useState)(`online`),[f,p]=(0,o.useState)(``),m=u===`offline`?{messages:a.messages,send:a.send,status:a.status}:{messages:i.messages,send:e=>{i.sendMessage({text:e})},status:i.status},{messages:h,send:g}=m,_=m.status===`submitted`||m.status===`streaming`,v=(0,o.useCallback)(()=>{let e=f.trim();!e||_||(p(``),g(e))},[_,f,g]),y=(0,o.useCallback)(e=>{e.nativeEvent.isComposing||e.key===`Enter`&&!e.shiftKey&&(e.preventDefault(),v())},[v]);return(0,c.jsxs)(l.default,{headerTitle:`AI 流程助理`,isHeaderDisplay:!0,onClose:n,open:r,size:`medium`,children:[(0,c.jsx)(`style`,{children:he}),(0,c.jsxs)(`div`,{style:ce,children:[a.available?(0,c.jsxs)(`div`,{style:ue,children:[(0,c.jsx)(s.Button,{onClick:()=>d(`online`),variant:u===`online`?`base-primary`:`base-tertiary`,children:`線上`}),(0,c.jsx)(s.Button,{onClick:()=>d(`offline`),variant:u===`offline`?`base-primary`:`base-tertiary`,children:`離線(裝置內,實驗)`})]}):null,(0,c.jsxs)(`div`,{role:`log`,style:le,children:[h.length===0?(0,c.jsx)(s.Typography,{color:`text-neutral`,variant:`body`,children:`用一句話描述你想要的流程,例如:「建立三關簽核:部門主管 → 經理 → 財務,金額大於十萬走財務複核」。我會直接在畫布上幫你繪製。`}):null,h.map(e=>(0,c.jsx)(o.Fragment,{children:be(e)},e.id)),_?(0,c.jsx)(s.Typography,{color:`text-neutral`,variant:`body`,children:`思考中…`}):null]}),(0,c.jsxs)(`div`,{style:de,children:[(0,c.jsx)(s.Textarea,{className:me,disabled:_,maxLength:2e3,onChange:e=>p(e.target.value),onKeyDown:y,placeholder:`描述你想要的流程…(Enter 送出,Shift + Enter 換行)`,rows:3,style:pe,value:f}),(0,c.jsx)(`div`,{style:fe,children:(0,c.jsx)(s.Button,{disabled:_||f.trim().length===0,loading:_,onClick:v,type:`button`,variant:`base-primary`,children:`送出`})})]})]})]})}function be(e){return e.parts.map((t,n)=>t.type===`text`?(0,c.jsx)(`div`,{style:ve(e.role),children:t.text},`${e.id}-${n}`):t.type===`dynamic-tool`||(0,f.isToolUIPart)(t)?(0,c.jsx)(`div`,{style:ge,children:`⚙ ${(0,f.getToolName)(t)} · ${_e[t.state]??t.state}`},`${e.id}-${n}`):null)}var xe={display:`grid`,gap:16},Se={alignItems:`start`,display:`grid`,gap:16,gridTemplateColumns:`minmax(0, 1fr) 420px`},Ce={border:`1px solid var(--mzn-color-border-neutral)`,borderRadius:6,height:620,minWidth:0,overflow:`hidden`},we={alignItems:`center`,boxSizing:`border-box`,color:`var(--mzn-color-text-error)`,display:`flex`,height:26,justifyContent:`center`,lineHeight:0,padding:0,width:26},Te={alignItems:`center`,display:`flex`,height:`100%`,justifyContent:`center`,width:`100%`},Ee=`workflow-designer-side-panel`,w=96,De=`
16
- .${Ee} .mzn-form-field--stretch .mzn-form-field__label-area,
17
- .${Ee} .mzn-form-field--horizontal .mzn-form-field__label-area {
18
- flex: 0 0 ${w}px;
19
- width: ${w}px;
20
- }
21
-
22
- .${Ee} .mzn-form-field--stretch .mzn-form-field__data-entry,
23
- .${Ee} .mzn-form-field--horizontal .mzn-form-field__data-entry {
24
- min-width: 0;
25
- }
26
- `,T=`#2563eb`,E=`#64748b`,Oe=`var(--mzn-color-text-error, #dc2626)`,D=`drop-shadow(0 0 3px rgba(0, 87, 255, 0.85)) drop-shadow(0 0 9px rgba(0, 87, 255, 0.36))`,ke=`
27
- .workflow-selection-delete-control.react-flow__controls-button {
28
- align-items: center !important;
29
- display: flex !important;
30
- height: 26px !important;
31
- justify-content: center !important;
32
- padding: 0 !important;
33
- width: 26px !important;
34
- }
35
-
36
- .workflow-selection-delete-control .mzn-icon {
37
- align-items: center;
38
- display: flex;
39
- justify-content: center;
40
- }
41
-
42
- .workflow-selection-delete-control .mzn-icon svg {
43
- height: 16px !important;
44
- max-height: none !important;
45
- max-width: none !important;
46
- width: 16px !important;
47
- }
48
-
49
- .workflow-edge--selected .react-flow__edge-path,
50
- .react-flow__edge-path.workflow-edge--selected {
51
- filter: ${D};
52
- opacity: 1 !important;
53
- stroke: ${E} !important;
54
- stroke-opacity: 1 !important;
55
- stroke-width: 1.5px !important;
56
- }
57
-
58
- .workflow-edge--selected {
59
- --xy-edge-stroke: ${E};
60
- --xy-edge-stroke-selected: ${E};
61
- --xy-edge-stroke-width: 1.5px;
62
- }
63
-
64
- `,Ae={display:`grid`,gap:12},O={display:`grid`,gap:12},je={border:`1px solid var(--mzn-color-border-neutral)`,borderRadius:6,display:`grid`,gap:8,maxHeight:360,overflow:`auto`,padding:12},Me={borderBottom:`1px solid var(--mzn-color-border-neutral)`,display:`grid`,gap:4,padding:`0 0 8px`},Ne={display:`flex`,flexWrap:`wrap`,gap:8},Pe={alignItems:`center`,display:`flex`,gap:8},Fe={flex:`1 1 auto`,minWidth:0},Ie={flex:`0 0 auto`},Le={display:`grid`,gap:8},k={alignContent:`center`,background:`var(--mzn-color-bg-surface)`,border:`1px solid var(--mzn-color-border-neutral)`,borderRadius:6,boxShadow:`0 8px 20px rgba(15, 23, 42, 0.08)`,boxSizing:`border-box`,display:`grid`,gap:4,height:`100%`,minWidth:132,overflow:`visible`,padding:`10px 12px`,textAlign:`center`,width:`100%`},A=`0 8px 20px rgba(15, 23, 42, 0.08), 0 0 0 1px var(--mzn-color-primary, #0057ff), 0 0 10px rgba(0, 87, 255, 0.3)`,Re=64,ze=160,Be=20,Ve=64,He=180,j={...k,display:`grid`,gap:8,padding:`10px 12px`},Ue={...j,background:`#eff6ff`,border:`1px solid #2563eb`},We={...j,background:`#f0fdfa`,border:`1px solid #0f766e`},M={...k,background:`#ffffff`},Ge={...k,background:`#ecfdf3`,border:`1px solid #2f855a`},N={...k,background:`#fff4ed`,border:`1px solid #c2410c`},Ke={display:`block`,maxWidth:`100%`,minWidth:0},qe={display:`grid`,gap:2,minWidth:0},P=`input`,F=`output`,Je={endEvent:`結束`,exclusiveGateway:`條件分流`,parallelGateway:`並行處理`,serviceTask:`系統`,startEvent:`開始`,userTask:`簽核`},Ye=[{icon:d.UserIcon,label:`簽核節點`,type:`userTask`},{icon:d.MailIcon,label:`知會節點`,type:`serviceTask`}],Xe=[{icon:d.FilterIcon,label:`條件分流`,type:`exclusiveGateway`}],Ze=[{id:`AND`,name:`全部前置完成`},{id:`OR`,name:`任一前置完成`}],Qe=[{id:`RESTART`,name:`重新送出後從開始重跑`},{id:`FROM_RETURN_POINT`,name:`重新送出後回到退回節點`}],$e=[{id:`NONE`,name:`不提醒`,value:null},{id:`0.5`,name:`過半時提醒`,value:.5},{id:`0.75`,name:`剩四分之一時提醒`,value:.75},{id:`0.9`,name:`剩十分之一時提醒`,value:.9}],et=[{id:`DIRECT`,name:`指定會員`},{id:`ORG_MANAGER`,name:`發起人主管`},{id:`ORG_UNIT_MANAGER`,name:`指定組織主管`},{id:`ORG_UNIT_MEMBER`,name:`組織任一人`},{id:`ORG_UNIT_POSITION`,name:`組織特定職位`},{id:`POSITION`,name:`指定職位`}],tt=[{id:`SINGLE`,name:`單人簽核`},{id:`PARALLEL_ANY`,name:`任一人同意`},{id:`PARALLEL_ALL`,name:`全部同意`},{id:`QUORUM`,name:`達到指定門檻`}],nt=[{id:`COUNT`,name:`人數`},{id:`PERCENTAGE`,name:`百分比`}],I=[{id:`1`,name:`直屬主管`,value:1},{id:`2`,name:`第二層主管`,value:2},{id:`3`,name:`第三層主管`,value:3}],rt=[{id:`NONE`,name:`停止流程並提示`},{id:`DIRECT`,name:`固定改派`}],it=[{id:`EQUALS`,name:`等於`},{id:`NOT_EQUALS`,name:`不等於`},{id:`GREATER_THAN`,name:`大於`},{id:`GREATER_THAN_OR_EQUALS`,name:`大於等於`},{id:`LESS_THAN`,name:`小於`},{id:`LESS_THAN_OR_EQUALS`,name:`小於等於`},{id:`IS_FILLED`,name:`已填寫`},{id:`IS_EMPTY`,name:`未填寫`}],at=[`EQUALS`,`GREATER_THAN`,`GREATER_THAN_OR_EQUALS`,`LESS_THAN`,`LESS_THAN_OR_EQUALS`,`NOT_EQUALS`],ot=[{id:`NONE`,name:`未設定`},{id:`ALL`,name:`所有人`},{id:`ORG_UNIT`,name:`指定組織`},{id:`ORG_UNIT_POSITION`,name:`指定組織職位`}],st={id:`CUSTOM`,name:`既有自訂規則`},ct=`member-001`,lt={display:`flex`,flexDirection:`column`,height:`100%`},ut={flex:1,minHeight:0,overflowY:`auto`},dt={borderTop:`1px solid var(--mzn-color-border-neutral)`,display:`flex`,gap:8,paddingTop:12},ft={fields:[],schemaVersion:1},pt={layout:[],schemaVersion:1},mt={endEvent:R,exclusiveGateway:R,parallelGateway:R,serviceTask:R,startEvent:R,userTask:R};function L(e,t){return typeof e==`function`?e(t):e}function ht({aiAssistantAvailable:e=!0,embedded:f=!1,formSchemaOverride:p,initialInitiatorPolicyCel:h,initialWorkflowDefinition:v,onInitiatorPolicyChange:ee,onWorkflowChange:te,showAiAssistant:ne=!1,showDryRun:re=!0,templateId:ie}){let ae=t.r(),oe=n.r(),[S,se]=(0,o.useState)(null),[C,ce]=(0,o.useState)(null),[le,ue]=(0,o.useState)(``),[de,fe]=(0,o.useState)(null),[pe,me]=(0,o.useState)(null),he=(0,o.useRef)(null),[ge,_e]=(0,o.useState)(void 0),ve=(0,o.useRef)([]),be=(0,o.useRef)([]),w=x({directory:(0,o.useMemo)(()=>({listOrgUnits:async()=>ve.current.map(e=>({id:e.id,name:e.name})),listPositions:async()=>be.current.map(e=>({id:e.id,name:e.name})),searchMembers:async e=>wn(await(0,y.searchMemberOptions)(e)).map(e=>({email:e.email,id:e.memberId,name:e.name}))}),[]),initialState:{definition:f&&v!=null?Et(v):kt(),editingEdgeId:null,formDefinitionVersionId:null,formSchema:null,initiatorPolicyCel:f&&h!==void 0?h:null,selectedEdgeIds:[],selectedNodeId:f&&v!=null?v.nodes[0]?.id??`start`:`start`},layout:jt,onLayout:e=>{let t=Un(e,he.current);t&&_e(t)}}),T=w.state.definition,E=w.state.formDefinitionVersionId,D=w.state.initiatorPolicyCel,k=w.state.selectedNodeId,A=w.state.selectedEdgeIds,Re=w.state.editingEdgeId,ze=e=>w.replaceState(t=>({...t,definition:L(e,t.definition)})),Be=e=>w.replaceState(t=>({...t,formDefinitionVersionId:L(e,t.formDefinitionVersionId)})),Ve=e=>w.replaceState(t=>({...t,initiatorPolicyCel:L(e,t.initiatorPolicyCel)})),He=e=>w.replaceState(t=>({...t,selectedNodeId:L(e,t.selectedNodeId)})),j=e=>w.replaceState(t=>({...t,selectedEdgeIds:L(e,t.selectedEdgeIds)})),Ue=e=>w.replaceState(t=>({...t,editingEdgeId:L(e,t.editingEdgeId)})),[We,M]=(0,o.useState)(null),[Ge,N]=(0,o.useState)(null);(0,o.useEffect)(()=>{N(null)},[k]);let[Ke,qe]=(0,o.useState)(!0),[P,F]=(0,o.useState)(!1),[it,at]=(0,o.useState)(!1),[ht,R]=(0,o.useState)([]),_t=(0,o.useMemo)(()=>JSON.stringify({formDefinitionVersionId:E,initiatorPolicyCel:D,workflowDefinition:T}),[E,D,T]),z=!!le&&_t!==le,[vt,yt]=(0,o.useState)(!1),[B,xt]=(0,o.useState)([]),[St,Ct]=(0,o.useState)([]),Tt=(0,o.useRef)(0),[V,Dt]=(0,o.useState)([]),[H,Ot]=(0,o.useState)([]),[Jt,nn]=(0,o.useState)([]);ve.current=V,be.current=H;let[on,cn]=(0,o.useState)(!1),[pn,mn]=(0,o.useState)(!1),[hn,yn]=(0,o.useState)(`{}`),[W,G]=(0,o.useState)(null),[kn,jn]=(0,o.useState)(null),[Mn,Nn]=(0,o.useState)(!1),[Pn,K]=(0,o.useState)(!1),[q,Rn]=(0,o.useState)(null),[zn,Bn]=(0,o.useState)(!1),[Vn,Hn]=(0,o.useState)(!1),Gn=z||zn?`保存並發布`:C?`發布草稿`:`已發布`;(0,o.useEffect)(()=>{f?_r():vr()},[f,ie]),(0,o.useEffect)(()=>{function e(e){z&&(e.preventDefault(),e.returnValue=``)}return window.addEventListener(`beforeunload`,e),()=>{window.removeEventListener(`beforeunload`,e)}},[z]),(0,o.useEffect)(()=>{xr(T)},[T,B]),(0,o.useEffect)(()=>{ze(e=>Et(e))},[T.edges,T.nodes]);function Zn(){z&&!window.confirm(`目前有尚未儲存的流程草稿,確定要離開嗎?`)||ae.push(oe.templates())}let J=(0,o.useMemo)(()=>T.nodes.find(e=>e.id===k)??null,[k,T.nodes]),nr=J?fn(J):!1,ir=A.length>0||nr,ar=(0,o.useCallback)(()=>{w.getState().selectedEdgeIds.forEach(e=>w.dispatch({edgeId:e,type:`deleteEdge`})),J&&fn(J)&&w.dispatch({nodeId:J.id,type:`deleteNode`})},[w,J]);(0,o.useEffect)(()=>{if(!ir)return;function e(e){e.key!==`Delete`&&e.key!==`Backspace`||gn(e.target)||(e.preventDefault(),ar())}return window.addEventListener(`keydown`,e),()=>{window.removeEventListener(`keydown`,e)}},[ir,ar]);let or=(0,o.useMemo)(()=>T.edges.find(e=>e.id===Re)??null,[Re,T.edges]),sr=(0,o.useMemo)(()=>A.length===1?T.edges.find(e=>e.id===A[0])??null:null,[A,T.edges]),cr=(0,o.useMemo)(()=>A.map(e=>T.edges.find(t=>t.id===e)??null).filter(e=>!!e),[A,T.edges]),X=(0,o.useMemo)(()=>pe??rn(D,de),[D,pe,de]),lr=(0,o.useMemo)(()=>T.nodes.map(e=>bt(e,B,V,H,e.id===k,X)),[X,B,V,H,k,T.nodes]),ur=(0,o.useMemo)(()=>T.edges.map(e=>wt(e,T.nodes,A.includes(e.id))),[A,T.edges,T.nodes]),Z=(0,o.useMemo)(()=>U(ht,E)??U(_n(S?.formVersions??[]),E),[E,ht,S?.formVersions]),dr=(0,o.useMemo)(()=>Cn(ht,Z),[ht,Z]),fr=Z?.schema??null,pr=f?p??null:fr;(0,o.useEffect)(()=>{w.getState().formSchema!==pr&&w.replaceState(e=>({...e,formSchema:pr}))},[w,pr]);let mr=(0,o.useMemo)(()=>Wn(T),[T]),hr=(0,o.useMemo)(()=>Kn(T),[T]),gr=(0,o.useMemo)(()=>an(X),[X]);(0,o.useEffect)(()=>{f&&te?.(T)},[f,T]),(0,o.useEffect)(()=>{f&&ee?.(D)},[f,D]);async function _r(){qe(!0),M(null);try{let e=await(0,g.readOrganizationDashboard)();Dt(e.orgUnits),Ot(e.positions),nn(e.memberships)}catch(e){M(Y(e))}finally{qe(!1)}}async function vr(){qe(!0),M(null),N(null);try{let[e,t]=await Promise.all([(0,y.readTemplateDesigner)(ie),(0,g.readOrganizationDashboard)()]),n=e.versions.find(e=>e.status===`DRAFT`)??null,r=n??e.versions[0]??null;se(e),ce(n),Dt(t.orgUnits),Ot(t.positions),nn(t.memberships),R(_n(e.formVersions));let i=Et(r?.workflowDefinition??kt()),a=r?.formDefinitionVersionId??e.formVersions[0]?.id??null,o=r?.initiatorPolicyCel??null;ze(i),Be(a),Ve(o),ue(JSON.stringify({formDefinitionVersionId:a,initiatorPolicyCel:o,workflowDefinition:i})),fe(r&&!e.template.currentVersionId&&!r.initiatorPolicyCel&&At(r.workflowDefinition)?`NONE`:null),me(null),He(r?.workflowDefinition.nodes[0]?.id??`start`),j([]),Ue(null),Rn(null),Bn(!1)}catch(e){M(Y(e))}finally{qe(!1)}}async function yr(e){at(!0),M(null);try{R(Cn(_n(await(0,y.searchPublishedFormVersionOptions)(e)),Z))}catch(e){M(Y(e))}finally{at(!1)}}async function br(e){yt(!0),M(null);let t=++Tt.current;try{let n=wn(await(0,y.searchMemberOptions)(e));xt(e=>In(e,n)),t===Tt.current&&Ct(n)}catch(e){t===Tt.current&&M(Y(e))}finally{t===Tt.current&&yt(!1)}}async function xr(e){let t=Ln(e).filter(e=>!B.some(t=>t.memberId===e&&!t.unresolved));if(t.length!==0)try{let e=await(0,y.resolveMemberOptions)(t);xt(t=>In(t,wn(e)))}catch{xt(e=>In(e,t.map(Tn)))}}async function Sr(e){F(!0),M(null);try{let t=Wn(T),n=an(X);if(t||n){let e=t??n??`流程設定未完成`;throw M(e),Error(e)}if(zn&&q!==null)await(0,y.composeApprovalTemplateWithForm)({category:S?.template.category??null,categoryId:S?.template.categoryId??null,formDefinitionId:Z?.formDefinitionId??null,formDescription:null,formName:Z?.formName??S?.template.name??`表單`,initiatorPolicyCel:D,notificationConfig:null,publish:e,schema:q.schema,slaDefaults:null,templateDescription:null,templateId:ie??null,templateName:S?.template.name??`模板`,uiSchema:q.uiSchema,workflowDefinition:T}),Bn(!1),Rn(null),await vr();else{let t=await(0,y.updateApprovalTemplateDraft)({formDefinitionVersionId:E,initiatorPolicyCel:D,versionId:(C??await(0,y.forkApprovalTemplate)(ie)).id,workflowDefinition:T});ce(t),e&&await(0,y.publishApprovalTemplateVersion)(t.id),await vr()}}catch(e){throw M(Y(e)),e}finally{F(!1)}}async function Cr(){await Sr(!1)}async function wr(){await Sr(!0)}function Tr(){yn(JSON.stringify(vn(Z),null,2)),G(null),jn(null),cn(!0)}function Er(){pn||cn(!1)}async function Dr(){mn(!0),jn(null),G(null);try{G(await(0,y.dryRunApprovalWorkflow)({formData:bn(hn),initiatorMemberId:ct,initiatorMetadataSnapshot:An(ct,Jt),workflowDefinition:T}))}catch(e){jn(Y(e))}finally{mn(!1)}}async function Or(){if(K(!0),q!==null)return;let e=Z?.formDefinitionId??null;if(!e){Rn({schema:ft,uiSchema:pt});return}Hn(!0);try{let t=await(0,m.readFormBuilder)(e),n=t.versions.find(e=>e.status===`DRAFT`)??t.versions.find(e=>e.id===t.definition.currentVersionId)??t.versions[0]??null;Rn({schema:n?.schema??ft,uiSchema:n?.uiSchema??pt})}catch(e){M(Y(e))}finally{Hn(!1)}}function kr(e){let t=(0,_.applyNodeChanges)(e,lr);ze(e=>({...e,nodes:e.nodes.map(e=>{let n=t.find(t=>t.id===e.id);return n?{...e,position:n.position}:e})}))}function Ar(e){!un(e,T.nodes)||!e.source||!e.target||w.dispatch({source:e.source,target:e.target,type:`connectEdge`})}function jr(e,t){e.stopPropagation(),j(n=>e.shiftKey||e.metaKey||e.ctrlKey?dn(n,t.id):[t.id]),He(null)}function Mr(){Ue(null)}function Nr(e){w.dispatch({nodeType:e,type:`addNode`})}function Pr(e){J&&w.dispatch({label:e,nodeId:J.id,type:`renameNode`})}function Q(e){if(!J||J.type!==`userTask`)return;let t=J.id,n=J.data.decisionPolicy;w.dispatch({approverResolver:e,nodeId:t,type:`setUserTaskApprover`}),N(null),(0,b.isDecisionPolicyUnsatisfiable)(n,e)&&N({message:`簽核者已變更為 ${(0,b.readDesignTimeApproverCount)(e)} 位,不足原本設定的 ${n?.type===`QUORUM`?n.threshold:0} 位門檻,簽核政策已重設為單人簽核,請重新設定。`,nodeId:t})}function Fr(e){!J||J.type!==`userTask`||w.dispatch({nodeId:J.id,resubmitStrategy:e,type:`setUserTaskReturnResubmitStrategy`})}function Ir(e){!J||J.type!==`userTask`||w.dispatch({nodeId:J.id,requireComment:e,type:`setUserTaskReturnRequireComment`})}function $(e){!J||J.type!==`userTask`||w.dispatch({nodeId:J.id,sla:e,type:`setUserTaskSla`})}function Lr(e){if(!J||J.type!==`userTask`)return;N(null);let t=e.type===`QUORUM`?{...e,threshold:(0,b.composeQuorumThreshold)(e.threshold,e.thresholdType)}:e;w.dispatch({decisionPolicy:t,nodeId:J.id,type:`setUserTaskDecisionPolicy`})}function Rr(e){!J||J.type!==`userTask`||w.dispatch({...e,nodeId:J.id,type:`setUserTaskOptions`})}function zr(e){!J||J.type!==`serviceTask`||w.dispatch({action:e,nodeId:J.id,type:`setServiceAction`})}function Br(e){me(e.mode===`ALL`||e.mode===`CUSTOM`?null:e),fe(e.mode===`ALL`||e.mode===`CUSTOM`?null:e.mode),Ve(sn(e,V))}function Vr(e){!J||J.type===`startEvent`||w.dispatch({nodeId:J.id,triggerMode:e,type:`setNodeTriggerMode`})}function Hr(e,t){w.dispatch({edgeId:e,isDefault:t,type:`setEdgeDefault`})}function Ur({edgeId:e,fieldKey:t,operator:n,value:r}){w.dispatch({edgeId:e,fieldKey:t,operator:n,type:`setEdgeCondition`,value:r})}function Wr(){w.dispatch({type:`autoLayout`})}return(0,c.jsxs)(c.Fragment,{children:[(0,c.jsx)(`style`,{children:De}),f?null:(0,c.jsx)(s.PageHeader,{children:(0,c.jsxs)(u.default,{description:`${C?`草稿 v${C.version}`:`尚未建立草稿`} ·${S?.template.currentVersionId?` 已發布版本`:` 尚未發布`}`,onBackClick:Zn,title:S?.template.name??`流程設計器`,children:[ne?(0,c.jsx)(s.Button,{disabled:!e,onClick:()=>Nn(e=>!e),variant:Mn?`base-primary`:`base-secondary`,children:e?`AI 助理`:`AI 助理(未設定)`}):null,(0,c.jsx)(s.Button,{"aria-label":`儲存草稿`,disabled:P||!!mr||!!gr,icon:d.SaveIcon,iconType:`icon-only`,onClick:()=>void Cr(),variant:`base-secondary`,children:`儲存草稿`}),re?(0,c.jsx)(s.Button,{disabled:Ke||!!mr||!!gr,icon:d.EyeIcon,iconType:`leading`,onClick:Tr,variant:`base-secondary`,children:`試跑流程`}):null,(0,c.jsx)(s.Button,{disabled:P||!C&&!z&&!zn||!!mr||!!gr,icon:d.CheckedIcon,iconType:`leading`,onClick:()=>void wr(),variant:`base-primary`,children:Gn})]})}),(0,c.jsx)(s.SectionGroup,{children:(0,c.jsx)(s.Section,{children:(0,c.jsxs)(`div`,{style:xe,children:[We?(0,c.jsx)(s.Typography,{color:`text-error`,variant:`body`,children:We}):null,Ge&&Ge.nodeId===J?.id&&J.type===`userTask`&&(J.data.decisionPolicy?.type??`SINGLE`)===`SINGLE`?(0,c.jsx)(s.Typography,{color:`text-warning`,variant:`body`,children:Ge.message}):null,mr?(0,c.jsx)(s.Typography,{color:`text-error`,variant:`body`,children:mr}):null,gr?(0,c.jsx)(s.Typography,{color:`text-error`,variant:`body`,children:gr}):null,f?null:(0,c.jsx)(`div`,{style:O,children:(0,c.jsx)(r.t,{hintText:hr?`已設定條件分流條件。請先移除所有條件,才能更換綁定表單版本。`:void 0,label:`綁定表單版本`,name:`formDefinitionVersionId`,required:!0,children:(0,c.jsxs)(`div`,{style:Pe,children:[(0,c.jsx)(`div`,{style:Fe,children:(0,c.jsx)(s.AutoComplete,{asyncData:!0,disabled:Ke||hr,disabledOptionsFilter:!0,emptyText:`沒有符合的已發布表單版本`,isForceClearable:!!E&&!hr,loading:it,loadingText:`搜尋表單版本中...`,mode:`single`,onChange:e=>{hr||Be(e?.id??null)},onClear:()=>{hr||Be(null)},onSearch:yr,onVisibilityChange:e=>{e&&!hr&&yr(``)},options:[...dr],placeholder:`選擇已發布表單版本`,searchDebounceTime:300,value:Z})}),(0,c.jsx)(s.Button,{disabled:Ke,onClick:()=>{Or()},style:Ie,variant:`base-secondary`,children:`編輯表單`})]})})}),(0,c.jsxs)(`div`,{style:Se,children:[(0,c.jsx)(`div`,{ref:he,style:Ce,children:(0,c.jsxs)(_.ReactFlow,{connectionMode:_.ConnectionMode.Strict,edges:ur,fitView:!0,isValidConnection:e=>un(e,T.nodes),nodeTypes:mt,nodes:lr,deleteKeyCode:null,multiSelectionKeyCode:[`Shift`,`Meta`,`Control`],onConnect:Ar,onEdgeClick:jr,onNodeClick:(e,t)=>{He(t.id),j([])},onNodesChange:kr,onPaneClick:()=>{He(null),j([])},onViewportChange:_e,viewport:ge,children:[(0,c.jsx)(_.Background,{}),(0,c.jsx)(`style`,{children:ke}),(0,c.jsx)(_.Controls,{children:ir?(0,c.jsx)(_.ControlButton,{"aria-label":`刪除選取項目`,className:`workflow-selection-delete-control`,onClick:ar,style:we,title:`刪除選取項目`,children:(0,c.jsx)(`span`,{style:Te,children:(0,c.jsx)(s.Icon,{color:`error`,icon:d.TrashIcon,size:16})})}):null}),(0,c.jsx)(gt,{onApplyAutoLayout:Wr}),(0,c.jsx)(_.MiniMap,{})]})}),(0,c.jsxs)(`div`,{className:Ee,style:Ae,children:[(0,c.jsx)(s.Typography,{component:`h2`,variant:`h3`,children:`流程工具`}),f&&ne?(0,c.jsxs)(`div`,{style:Le,children:[(0,c.jsx)(s.Typography,{color:`text-neutral`,variant:`caption`,children:`AI 協助`}),(0,c.jsx)(`div`,{style:Ne,children:(0,c.jsx)(s.Button,{disabled:!e,onClick:()=>Nn(e=>!e),size:`sub`,variant:Mn?`base-primary`:`base-secondary`,children:e?`AI 助理`:`AI 助理(未設定)`})})]}):null,(0,c.jsxs)(`div`,{style:Le,children:[(0,c.jsx)(s.Typography,{color:`text-neutral`,variant:`caption`,children:`動作節點`}),(0,c.jsx)(`div`,{style:Ne,children:Ye.map(e=>(0,c.jsx)(s.Button,{icon:e.icon,iconType:`leading`,onClick:()=>Nr(e.type),size:`sub`,variant:`base-secondary`,children:e.label},e.type))})]}),(0,c.jsxs)(`div`,{style:Le,children:[(0,c.jsx)(s.Typography,{color:`text-neutral`,variant:`caption`,children:`流程控制`}),(0,c.jsx)(`div`,{style:Ne,children:Xe.map(e=>(0,c.jsx)(s.Button,{icon:e.icon,iconType:`leading`,onClick:()=>Nr(e.type),size:`sub`,variant:`base-secondary`,children:e.label},e.type))})]}),cr.length>1?Zr(cr):null,cr.length===1&&sr?Qr(sr):null,cr.length===0&&J?Kr(J):null]})]})]})})}),$r(or),!f&&re?Gr():null,ne&&e?(0,c.jsx)(ye,{controller:w,onClose:()=>Nn(!1),open:Mn}):null,f?null:(0,c.jsx)(l.default,{headerTitle:`編輯表單`,isHeaderDisplay:!0,onClose:()=>K(!1),open:Pn,size:`wide`,children:(0,c.jsxs)(`div`,{style:lt,children:[(0,c.jsx)(`div`,{style:ut,children:Vn?(0,c.jsx)(s.Typography,{color:`text-neutral`,variant:`body`,children:`載入中…`}):(0,c.jsx)(a.t,{onChange:e=>{Rn(e)},value:q??{schema:ft,uiSchema:pt}})}),(0,c.jsxs)(`div`,{style:dt,children:[(0,c.jsx)(s.Button,{disabled:Vn,onClick:()=>{q!==null&&(Bn(!0),w.replaceState(e=>({...e,formSchema:q.schema}))),K(!1)},variant:`base-primary`,children:`套用`}),(0,c.jsx)(s.Button,{onClick:()=>K(!1),variant:`base-secondary`,children:`取消`})]})]})})]});function Gr(){return(0,c.jsx)(s.Modal,{cancelText:`關閉`,confirmText:`執行試跑`,loading:pn,modalType:`standard`,onCancel:Er,onClose:Er,onConfirm:()=>void Dr(),open:on,showModalFooter:!0,showModalHeader:!0,size:`wide`,supportingText:`使用 ${ct} 與範例表單資料模擬目前畫布流程,不會建立案件。`,title:`試跑流程`,children:(0,c.jsxs)(`div`,{style:O,children:[(0,c.jsx)(r.t,{label:`表單資料 JSON`,name:`dryRunFormDataJson`,required:!0,children:(0,c.jsx)(s.Textarea,{onChange:e=>yn(e.target.value),resize:`vertical`,rows:8,value:hn})}),kn?(0,c.jsx)(s.Typography,{color:`text-error`,variant:`body`,children:kn}):null,W?(0,c.jsxs)(`div`,{style:je,children:[(0,c.jsx)(s.Typography,{color:W.valid?`text-success`:`text-error`,variant:`label-primary-highlight`,children:W.valid?`試跑通過`:`試跑失敗`}),W.errors.map(e=>(0,c.jsx)(s.Typography,{color:`text-error`,variant:`body`,children:e},e)),W.steps.map(e=>(0,c.jsxs)(`div`,{style:Me,children:[(0,c.jsxs)(s.Typography,{variant:`label-primary-highlight`,children:[e.nodeLabel,` · `,xn(e.status)]}),(0,c.jsxs)(s.Typography,{color:`text-neutral`,variant:`caption`,children:[Sn(e.nodeType),e.assigneeMemberId?` · 處理者:${e.assigneeMemberId}`:``,e.edgeLabel?` · 來源線段:${e.edgeLabel}`:``]}),e.edgeReason?(0,c.jsx)(s.Typography,{color:`text-neutral`,variant:`caption`,children:e.edgeReason}):null,e.entryCondition?(0,c.jsxs)(s.Typography,{color:`text-neutral`,variant:`caption`,children:[`進入條件:`,e.entryConditionMatched?`符合`:`不符合`,` ·`,` `,e.entryCondition]}):null,(0,c.jsx)(s.Typography,{color:`text-neutral`,variant:`body`,children:e.message})]},e.id))]}):null]})})}function Kr(e){return(0,c.jsxs)(`div`,{style:O,children:[(0,c.jsx)(s.Typography,{component:`h2`,variant:`h3`,children:`節點屬性`}),(0,c.jsxs)(s.Typography,{color:`text-neutral`,variant:`body`,children:[Je[e.type],` · `,e.id]}),(0,c.jsx)(r.t,{label:`顯示名稱`,name:`nodeLabel`,required:!0,children:(0,c.jsx)(s.Input,{onChange:e=>Pr(e.target.value),value:e.data.label,variant:`base`})}),e.type===`startEvent`?qr():null,e.type===`startEvent`?null:Jr(e),e.type===`userTask`?Yr(e):null,e.type===`serviceTask`?Xr(e):null]})}function qr(){let e=X.mode===`CUSTOM`?[...ot,st]:[...ot],t=X.mode===`ORG_UNIT`||X.mode===`ORG_UNIT_POSITION`?Dn(V,X.orgUnitId??``):null,n=X.mode===`ORG_UNIT_POSITION`?On(H,X.positionId??``):null,a=X.mode===`ORG_UNIT_POSITION`?Fn({includeDescendants:!!X.includeDescendants,memberships:Jt,orgUnitId:X.orgUnitId??``,orgUnits:V,positions:H}):[];return(0,c.jsxs)(c.Fragment,{children:[(0,c.jsx)(r.t,{hintText:X.mode===`CUSTOM`?`這是舊版表達式規則;切換成標準選項後會改由 UI 管理。`:void 0,label:`發起權限`,name:`initiatorPolicyMode`,required:!0,children:(0,c.jsx)(s.Select,{clearable:!1,onChange:e=>{if(e?.id===`CUSTOM`){fe(null),me(null);return}let t=tn(e?.id??null),n=ln(t);fe(t===`ALL`?null:t),me(t===`ALL`?null:n),Ve(sn(n,V))},options:e,placeholder:`選擇誰可以發起`,value:U(e,X.mode)})}),X.mode===`ORG_UNIT`||X.mode===`ORG_UNIT_POSITION`?(0,c.jsx)(r.t,{label:`組織`,name:`initiatorOrgUnitId`,required:!0,children:(0,c.jsx)(i.n,{name:`initiatorOrgUnitId`,onChange:e=>Br({...X,orgUnitId:e?.id??``,positionId:``,value:e?.id??``}),orgUnits:V,placeholder:`選擇組織`,value:t})}):null,X.mode===`ORG_UNIT`||X.mode===`ORG_UNIT_POSITION`?(0,c.jsx)(r.t,{label:`包含下層`,name:`initiatorIncludeDescendants`,children:(0,c.jsx)(s.Toggle,{checked:!!X.includeDescendants,onChange:e=>Br({...X,includeDescendants:e.target.checked,...X.mode===`ORG_UNIT_POSITION`?{positionId:``}:{}})})}):null,X.mode===`ORG_UNIT_POSITION`?(0,c.jsx)(r.t,{label:`職位`,name:`initiatorPositionId`,required:!0,children:(0,c.jsx)(i.r,{disabled:!X.orgUnitId?.trim(),name:`initiatorPositionId`,onChange:e=>Br({...X,positionId:e?.id??``}),placeholder:X.orgUnitId?.trim()?`選擇職位`:`請先選擇組織`,positions:a,value:n})}):null]})}function Jr(e){let t=T.edges.filter(t=>t.target===e.id).length,n=t<2,i=n?`AND`:e.data.triggerMode??`AND`;return(0,c.jsx)(r.t,{hintText:n?`需要至少兩條前置連線,才可切換為任一前置完成。`:t>1?`${t} 條前置連線會依此規則觸發。`:`只有一條前置連線時,兩種設定效果相同。`,label:`前置條件`,name:`triggerMode`,required:!0,children:(0,c.jsx)(s.Select,{clearable:!1,onChange:e=>n?void 0:Vr(Mt(e?.id??null)),options:[...Ze],readOnly:n,value:U(Ze,i)})})}function Yr(e){let t=e.data.approverResolver,n=Yt(t.type),a=t.type===`DIRECT`?t.memberIds.map(e=>En(B,e)):[],o=t.type===`ORG_UNIT_MANAGER`||t.type===`ORG_UNIT_MEMBER`||t.type===`ORG_UNIT_POSITION`?Dn(V,t.orgUnitId):null,l=t.type===`POSITION`||t.type===`ORG_UNIT_POSITION`?On(H,t.positionId):null,u=t.type===`ORG_UNIT_POSITION`?Fn({includeDescendants:!!t.includeDescendants,memberships:Jt,orgUnitId:t.orgUnitId,orgUnits:V,positions:H}):[],d=t.type===`ORG_MANAGER`?$t(t.levelsUp):I[0],f=t.type===`ORG_MANAGER`||t.type===`ORG_UNIT_MANAGER`?t.fallback??{type:`NONE`}:{type:`NONE`},p=f.type===`DIRECT`&&f.memberId?En(B,f.memberId):null,m=e.data.returnBehavior.resubmitStrategy??`RESTART`,h=e.data.sla??null,g=h?(0,b.readSlaDurationParts)(h.duration):null,_=g?.unit??`DAY`,v=Ut(h?.warningAt??null),y=$t(h?.escalateLevelsUp??1),ee=Ft(e.data.decisionPolicy),x=Rt(e.data.decisionPolicy);return(0,c.jsxs)(c.Fragment,{children:[(0,c.jsx)(r.t,{label:`簽核來源`,name:`approverResolverType`,required:!0,children:(0,c.jsx)(s.Select,{clearable:!1,onChange:e=>Q(Xt(e?.id??null)),options:[...et],value:U(et,n)})}),t.type===`DIRECT`?(0,c.jsx)(r.t,{hintText:Pt(e.data.decisionPolicy),label:`簽核者`,name:`memberId`,required:!0,children:(0,c.jsx)(s.AutoComplete,{asyncData:!0,disabledOptionsFilter:!0,emptyText:`沒有符合的成員`,inputProps:{autoCapitalize:`none`,autoCorrect:`off`,name:`workflow-approver-search`,spellCheck:!1},loading:vt,loadingText:`搜尋成員中...`,mode:`multiple`,onChange:e=>Q({memberIds:e.map(e=>e.id),type:`DIRECT`}),onSearch:br,onVisibilityChange:e=>{e&&(Ct([]),br(``))},options:[...In(a,St)],placeholder:`搜尋姓名或信箱`,searchDebounceTime:300,value:a})}):null,t.type===`ORG_MANAGER`?(0,c.jsx)(r.t,{hintText:`依發起人的有效會員歸屬與主管解析規則決定簽核人。`,label:`主管層級`,name:`managerLevelsUp`,required:!0,children:(0,c.jsx)(s.Select,{clearable:!1,onChange:e=>Q({baseFromInitiator:!0,levelsUp:en(e?.id??null).value,type:`ORG_MANAGER`}),options:[...I],value:d})}):null,t.type===`ORG_UNIT_MANAGER`||t.type===`ORG_UNIT_MEMBER`||t.type===`ORG_UNIT_POSITION`?(0,c.jsx)(r.t,{hintText:t.type===`ORG_UNIT_MANAGER`?`依指定組織或其上層的主管解析規則決定簽核人。`:`依指定組織目前有效會員歸屬建立候選簽核人。`,label:`組織`,name:`orgUnitId`,required:!0,children:(0,c.jsx)(i.n,{name:`orgUnitId`,onChange:e=>Q(t.type===`ORG_UNIT_MEMBER`?{includeDescendants:t.includeDescendants,orgUnitId:e?.id??``,type:`ORG_UNIT_MEMBER`}:t.type===`ORG_UNIT_POSITION`?{includeDescendants:t.includeDescendants,orgUnitId:e?.id??``,positionId:``,type:`ORG_UNIT_POSITION`}:{fallback:t.fallback,orgUnitId:e?.id??``,type:`ORG_UNIT_MANAGER`}),orgUnits:V,placeholder:`選擇組織`,value:o})}):null,t.type===`ORG_MANAGER`||t.type===`ORG_UNIT_MANAGER`?(0,c.jsxs)(c.Fragment,{children:[(0,c.jsx)(r.t,{hintText:`開啟後只取離該員最近一層的主管規則;掛在上層單位、涵蓋範圍較大的規則不會再一併加入簽核人。`,label:`只取最近一層主管`,name:`preferClosestOrgUnit`,children:(0,c.jsx)(s.Toggle,{checked:!!t.preferClosestOrgUnit,inputProps:{id:`preferClosestOrgUnit`,name:`preferClosestOrgUnit`},onChange:e=>Q({...t,preferClosestOrgUnit:e.target.checked})})}),(0,c.jsx)(r.t,{hintText:`預設會停止流程並提示;若設定固定人,找不到主管時會改派給該會員。`,label:`無主管時`,name:`approverFallbackMode`,required:!0,children:(0,c.jsx)(s.Select,{clearable:!1,onChange:e=>Q(Qt(t,Zt(e?.id??null)===`DIRECT`?{memberId:``,type:`DIRECT`}:{type:`NONE`})),options:[...rt],value:U(rt,f.type)})}),f.type===`DIRECT`?(0,c.jsxs)(c.Fragment,{children:[(0,c.jsx)(r.t,{label:`改派人員`,name:`approverFallbackMemberId`,required:!0,children:(0,c.jsx)(s.AutoComplete,{asyncData:!0,disabledOptionsFilter:!0,emptyText:`沒有符合的成員`,inputProps:{autoCapitalize:`none`,autoCorrect:`off`,name:`workflow-approver-fallback-search`,spellCheck:!1},loading:vt,loadingText:`搜尋成員中...`,mode:`single`,onChange:e=>Q(Qt(t,{allowInitiatorSelfApproval:f.allowInitiatorSelfApproval,memberId:e?.id??``,type:`DIRECT`})),onSearch:br,onVisibilityChange:e=>{e&&(Ct([]),br(``))},options:[...In(St,p?[p]:[])],placeholder:`搜尋姓名或信箱`,searchDebounceTime:300,value:p})}),(0,c.jsx)(r.t,{hintText:`預設禁止申請人簽自己的案件;只有此流程允許自簽時才開啟。`,label:`允許自簽`,name:`allowInitiatorSelfApproval`,children:(0,c.jsx)(s.Toggle,{checked:!!f.allowInitiatorSelfApproval,inputProps:{id:`allowInitiatorSelfApproval`,name:`allowInitiatorSelfApproval`},onChange:e=>Q(Qt(t,{allowInitiatorSelfApproval:e.target.checked,memberId:f.memberId,type:`DIRECT`}))})})]}):null]}):null,t.type===`ORG_UNIT_MEMBER`||t.type===`ORG_UNIT_POSITION`?(0,c.jsx)(r.t,{label:`包含下層`,name:`includeDescendants`,children:(0,c.jsx)(s.Toggle,{checked:!!t.includeDescendants,inputProps:{id:`includeDescendants`,name:`includeDescendants`},onChange:e=>Q({...t,includeDescendants:e.target.checked,...t.type===`ORG_UNIT_POSITION`?{positionId:``}:{}})})}):null,t.type===`POSITION`?(0,c.jsx)(r.t,{hintText:`指派給目前有效歸屬中擁有此職位的會員;主要歸屬優先。`,label:`職位`,name:`positionId`,required:!0,children:(0,c.jsx)(i.r,{name:`positionId`,onChange:e=>Q({positionId:e?.id??``,type:`POSITION`}),placeholder:`選擇職位`,positions:H,value:l})}):null,t.type===`ORG_UNIT_POSITION`?(0,c.jsx)(r.t,{hintText:`只納入指定組織範圍內擁有此職位的有效會員。`,label:`職位`,name:`orgUnitPositionId`,required:!0,children:(0,c.jsx)(i.r,{disabled:!t.orgUnitId.trim(),name:`orgUnitPositionId`,onChange:e=>Q({includeDescendants:t.includeDescendants,orgUnitId:t.orgUnitId,positionId:e?.id??``,type:`ORG_UNIT_POSITION`}),placeholder:t.orgUnitId.trim()?`選擇職位`:`請先選擇組織`,positions:u,value:l})}):null,(0,c.jsx)(r.t,{hintText:`決定這一關要幾位簽核者同意才會通過;單人簽核與任一人同意的效果完全相同,皆為其中一人同意即通過。`,label:`決策方式`,name:`decisionPolicy`,required:!0,children:(0,c.jsx)(s.Select,{clearable:!1,onChange:t=>Lr(Lt(t?.id??null,e.data.decisionPolicy)),options:[...tt],value:It(ee)})}),ee===`QUORUM`?(0,c.jsxs)(c.Fragment,{children:[(0,c.jsx)(r.t,{label:`門檻計算方式`,name:`quorumThresholdType`,required:!0,children:(0,c.jsx)(s.Select,{clearable:!1,onChange:e=>Lr({threshold:x.threshold,thresholdType:zt(e?.id??null),type:`QUORUM`}),options:[...nt],value:U(nt,x.thresholdType)})}),(0,c.jsx)(r.t,{hintText:x.thresholdType===`PERCENTAGE`?`達到簽核者總數的這個百分比即通過,換算人數時無條件進位;超過 100 的輸入會自動夾至 100。`:`達到這個同意人數即通過;門檻超過實際簽核者人數時,這一關將永遠無法通過,請勿設定超過實際簽核者人數。`,label:x.thresholdType===`PERCENTAGE`?`門檻百分比`:`門檻人數`,name:`quorumThreshold`,required:!0,children:(0,c.jsx)(s.Input,{id:`quorumThreshold`,inputProps:x.thresholdType===`PERCENTAGE`?{max:100,min:1}:{min:1},inputType:`number`,name:`quorumThreshold`,onChange:e=>Lr({threshold:(0,b.composeQuorumThreshold)(Number(e.target.value),x.thresholdType),thresholdType:x.thresholdType,type:`QUORUM`}),value:String(x.threshold),variant:`base`})})]}):null,e.data.returnBehavior.allowReturn?(0,c.jsx)(r.t,{hintText:`退回發起人後,重新送出時要從流程開始重跑,或直接回到退回的簽核節點。`,label:`重送策略`,name:`returnResubmitStrategy`,required:!0,children:(0,c.jsx)(s.Select,{clearable:!1,onChange:e=>Fr(Nt(e?.id??null)),options:[...Qe],value:U(Qe,m)})}):null,e.data.returnBehavior.allowReturn?(0,c.jsx)(r.t,{hintText:`開啟後,簽核者按下退回時必須填寫意見,未填寫會被擋下。`,label:`退回時意見必填`,name:`returnRequireComment`,children:(0,c.jsx)(s.Toggle,{checked:e.data.returnBehavior.requireComment===!0,inputProps:{id:`returnRequireComment`,name:`returnRequireComment`},onChange:e=>Ir(e.target.checked)})}):null,(0,c.jsx)(r.t,{hintText:`開啟後可設定簽核期限,逾時將依下方設定處理。`,label:`啟用時效`,name:`slaEnabled`,children:(0,c.jsx)(s.Toggle,{checked:!!h,inputProps:{id:`slaEnabled`,name:`slaEnabled`},onChange:e=>$(e.target.checked?b.DEFAULT_SLA_CONFIG:null)})}),h&&!g?(0,c.jsx)(r.t,{hintText:`此期限混用了日與時,無法在表單中編輯。請改以單一單位設定,或透過 API 維護。`,label:`時效期限`,name:`slaDurationRaw`,children:(0,c.jsx)(s.Input,{disabled:!0,value:h.duration,variant:`base`})}):null,h&&g?(0,c.jsxs)(c.Fragment,{children:[(0,c.jsx)(r.t,{label:`時效期限`,name:`slaDurationValue`,required:!0,children:(0,c.jsx)(s.Input,{id:`slaDurationValue`,inputProps:{min:1},inputType:`number`,name:`slaDurationValue`,onChange:e=>$(Gt(h,{unit:_,value:Number(e.target.value)})),value:String(g.value),variant:`base`})}),(0,c.jsx)(r.t,{label:`期限單位`,name:`slaDurationUnit`,required:!0,children:(0,c.jsx)(s.Select,{clearable:!1,onChange:e=>$(Gt(h,{unit:Bt(e?.id??null),value:g.value})),options:[...b.SLA_DURATION_UNIT_OPTIONS],value:U(b.SLA_DURATION_UNIT_OPTIONS,_)})})]}):null,h&&_===`DAY`?(0,c.jsx)(r.t,{hintText:`工作日會跳過週末與行事曆上的假日,補班日仍計為工作日;行事曆由系統管理者設定。`,label:`計算方式`,name:`slaCalendar`,required:!0,children:(0,c.jsx)(s.Select,{clearable:!1,onChange:e=>$({...h,calendar:Vt(e?.id??null)}),options:[...b.SLA_CALENDAR_MODE_OPTIONS],value:U(b.SLA_CALENDAR_MODE_OPTIONS,h.calendar??`CALENDAR`)})}):null,h?(0,c.jsx)(r.t,{label:`逾時處理`,name:`slaOnTimeout`,required:!0,children:(0,c.jsx)(s.Select,{clearable:!1,onChange:e=>$(Kt(h,Ht(e?.id??null))),options:[...b.SLA_TIMEOUT_ACTION_OPTIONS],value:U(b.SLA_TIMEOUT_ACTION_OPTIONS,h.onTimeout)})}):null,h?.onTimeout===`ESCALATE`?(0,c.jsx)(r.t,{hintText:`逾時後改派給簽核者的上層主管,只會升級一次。`,label:`升級層級`,name:`slaEscalateLevelsUp`,required:!0,children:(0,c.jsx)(s.Select,{clearable:!1,onChange:e=>$({...h,escalateLevelsUp:en(e?.id??null).value}),options:[...I],value:y})}):null,h?(0,c.jsx)(r.t,{hintText:`在期限到達前先送出一次提醒。`,label:`預警提醒`,name:`slaWarningAt`,children:(0,c.jsx)(s.Select,{clearable:!1,onChange:e=>$(qt(h,Wt(e?.id??null).value)),options:[...$e],value:v})}):null,(0,c.jsx)(r.t,{hintText:`關閉後,簽核者在此關卡看不到「拒絕」按鈕。`,label:`允許拒絕`,name:`allowReject`,children:(0,c.jsx)(s.Toggle,{checked:e.data.allowReject,inputProps:{id:`allowReject`,name:`allowReject`},onChange:e=>Rr({allowReject:e.target.checked})})}),(0,c.jsx)(r.t,{hintText:`關閉後,簽核者無法把此關卡的任務轉派給其他人。`,label:`允許轉派`,name:`allowTransfer`,children:(0,c.jsx)(s.Toggle,{checked:e.data.allowTransfer,inputProps:{id:`allowTransfer`,name:`allowTransfer`},onChange:e=>Rr({allowTransfer:e.target.checked})})}),(0,c.jsx)(r.t,{hintText:`開啟後,簽核者可在此關卡臨時加入其他簽核人;會簽為平行處理,加簽則需等加入者簽完才往下。`,label:`允許加簽`,name:`allowAddSigner`,children:(0,c.jsx)(s.Toggle,{checked:e.data.allowAddSigner,inputProps:{id:`allowAddSigner`,name:`allowAddSigner`},onChange:e=>Rr({allowAddSigner:e.target.checked})})})]})}function Xr(e){let t=rr(e.data.action).map(e=>En(B,e));return(0,c.jsx)(r.t,{label:`知會對象`,name:`notifyMemberIds`,required:!0,children:(0,c.jsx)(s.AutoComplete,{asyncData:!0,disabledOptionsFilter:!0,emptyText:`沒有符合的成員`,loading:vt,loadingText:`搜尋成員中...`,mode:`multiple`,onChange:e=>zr({channels:[`IN_APP`],recipients:{memberIds:e.map(e=>e.id),type:`DIRECT`},type:`NOTIFY`}),onSearch:br,onVisibilityChange:e=>{e&&(Ct([]),br(``))},options:[...In(t,St)],overflowStrategy:`wrap`,placeholder:`搜尋姓名或信箱`,searchDebounceTime:300,value:[...t]})})}function Zr(e){return(0,c.jsxs)(`div`,{style:O,children:[(0,c.jsx)(s.Typography,{component:`h2`,variant:`h3`,children:`已選取線段`}),(0,c.jsxs)(s.Typography,{color:`text-neutral`,variant:`body`,children:[`已選取 `,e.length,` 條線段,可使用 Delete 或控制面板刪除。`]})]})}function Qr(e){let t=tr(e,T.nodes);return(0,c.jsxs)(`div`,{style:O,children:[(0,c.jsx)(s.Typography,{component:`h2`,variant:`h3`,children:t?`條件設定`:`線段屬性`}),(0,c.jsxs)(s.Typography,{color:`text-neutral`,variant:`body`,children:[e.source,` → `,e.target]}),t?ei(e):(0,c.jsx)(s.Typography,{color:`text-neutral`,variant:`body`,children:`這條線會直接把流程送到下一個節點。`})]})}function $r(e){return!e||!tr(e,T.nodes)?null:(0,c.jsx)(s.Modal,{cancelText:`取消`,confirmButtonProps:{disabled:!e.data.isDefault&&!e.data.condition},confirmText:`完成`,modalType:`standard`,onCancel:Mr,onClose:Mr,onConfirm:Mr,open:!!Re,showModalFooter:!0,showModalHeader:!0,size:`regular`,supportingText:`條件分流的輸出連線需要指定條件,條件會直接顯示在線上。`,title:`條件設定`,children:ei(e)})}function ei(e){let t=er(e,T.nodes),n=qn(Z?.schema??null),i=Jn(Z?.schema??null,e.data.conditionFieldKey??null),a=Yn(i),o=Qn(i),l=U(a,e.data.conditionOperator??null);return(0,c.jsxs)(`div`,{style:O,children:[(0,c.jsxs)(s.Typography,{color:`text-neutral`,variant:`body`,children:[`畫布上的這條線目前會顯示「`,(0,c.jsx)(`span`,{style:{color:!e.data.isDefault&&!e.data.condition?Oe:void 0},children:t??`請設定條件`}),`」。`]}),(0,c.jsx)(s.Toggle,{checked:!!e.data.isDefault,label:`其他情況走這條`,onChange:t=>Hr(e.id,t.target.checked)}),e.data.isDefault?(0,c.jsx)(s.Typography,{color:`text-neutral`,variant:`body`,children:`其他條件都不符合時,流程會走這條線。`}):(0,c.jsxs)(c.Fragment,{children:[Z?null:(0,c.jsx)(s.Typography,{color:`text-neutral`,variant:`body`,children:`請先綁定表單版本,才能選擇條件欄位。`}),(0,c.jsx)(r.t,{label:`條件欄位`,name:`edgeConditionField`,required:!0,children:(0,c.jsx)(s.Select,{clearable:!1,onChange:t=>Ur({edgeId:e.id,fieldKey:t?.id??null,operator:null,value:null}),options:[...n],placeholder:`選擇條件欄位`,value:U(n,e.data.conditionFieldKey??null)})}),(0,c.jsx)(r.t,{label:`條件判斷`,name:`edgeConditionOperator`,required:!0,children:(0,c.jsx)(s.Select,{clearable:!1,onChange:t=>Ur({edgeId:e.id,operator:Xn(t?.id??null),value:null}),options:[...a],placeholder:`選擇判斷方式`,value:l})}),l&&$n(l.id)?(0,c.jsx)(r.t,{label:`條件值`,name:`edgeConditionValue`,required:!0,children:o.length>0?(0,c.jsx)(s.Select,{clearable:!1,onChange:t=>Ur({edgeId:e.id,value:t?.id??null}),options:[...o],placeholder:`選擇條件值`,value:U(o,e.data.conditionValue??null)}):(0,c.jsx)(s.Input,{onChange:t=>Ur({edgeId:e.id,value:t.target.value}),placeholder:`輸入要比對的值`,value:e.data.conditionValue??``,variant:`base`})}):null]})]})}}function gt({onApplyAutoLayout:e}){function t(){e()}return(0,c.jsx)(_.Panel,{position:`top-right`,children:(0,c.jsx)(s.Button,{icon:d.DotGridIcon,iconType:`leading`,onClick:t,size:`sub`,variant:`base-secondary`,children:`自動排版`})})}function R({data:e,selected:t,type:n}){let r=e.approverLines??[e.approverSummary??e.label],i=_t(e);return(0,c.jsxs)(`div`,{style:z(n,t),children:[yt(e),(0,c.jsx)(`div`,{style:qe,children:r.map((e,t)=>(0,c.jsx)(s.Typography,{component:`span`,ellipsis:!0,style:Ke,title:e,variant:`label-primary`,children:e},`${e}_${t}`))}),(0,c.jsx)(s.Typography,{color:`text-neutral`,component:`span`,ellipsis:!0,style:Ke,title:i,variant:`caption`,children:i})]})}function _t(e){return e.nodeKind===`startEvent`?e.initiatorPolicySummary??`所有人`:e.approverSummary||e.approverLines?e.label:e.nodeKind===`exclusiveGateway`?`條件在線上`:e.nodeKind===`parallelGateway`?`多條路徑同時進行`:Je[e.nodeKind]}function z(e,t){let n=vt(e);return t?{...n,border:`1px solid var(--mzn-color-primary, #0057ff)`,boxShadow:A}:n}function vt(e){return e===`exclusiveGateway`?Ue:e===`parallelGateway`?We:e===`startEvent`?Ge:e===`endEvent`?N:e===`userTask`?M:k}function yt(e){return!e.hasInput&&e.hasOutput?(0,c.jsx)(_.Handle,{id:F,position:_.Position.Right,type:`source`}):e.hasInput&&!e.hasOutput?(0,c.jsx)(_.Handle,{id:P,position:_.Position.Left,type:`target`}):!e.hasInput&&!e.hasOutput?null:[(0,c.jsx)(_.Handle,{id:P,position:_.Position.Left,type:`target`},`target`),(0,c.jsx)(_.Handle,{id:F,position:_.Position.Right,type:`source`},`source`)]}function bt(e,t,n,r,i,a){let o=B(e);return{data:{approverLines:Bn(e,t),approverSummary:Rn(e,t,n,r),hasInput:pn(e),hasOutput:mn(e),initiatorPolicySummary:e.type===`startEvent`?cn(a,n,r):null,label:e.data.label,nodeKind:e.type},height:o.height,handles:xt(e),id:e.id,initialHeight:o.height,initialWidth:o.width,position:e.position,selected:i,sourcePosition:_.Position.Right,targetPosition:_.Position.Left,type:e.type,width:o.width}}function B(e){return e.type===`exclusiveGateway`||e.type===`parallelGateway`?{height:Ve,width:He}:e.type===`serviceTask`?{height:Re+(Math.max(1,rr(e.data.action).length)-1)*Be,width:ze}:{height:Re,width:ze}}function xt(e){let t=B(e);return[...pn(e)?[St(t)]:[],...mn(e)?[Ct(t)]:[]]}function St({height:e}){let t=e/2-9/2;return{height:9,id:P,position:_.Position.Left,type:`target`,width:9,x:-9/2,y:t}}function Ct({height:e,width:t}){let n=e/2-9/2;return{height:9,id:F,position:_.Position.Right,type:`source`,width:9,x:t-9/2,y:n}}function wt(e,t,n){let r=er(e,t),i=tr(e,t),a=i&&!e.data.isDefault&&!e.data.condition,o=a?Oe:i?T:`#475569`,s=a?`#fef2f2`:i?`#eff6ff`:`#ffffff`,c=a?Oe:i?T:E;return{className:n?`workflow-edge--selected`:void 0,data:e.data,id:e.id,label:r,labelBgBorderRadius:6,labelBgPadding:[8,4],labelBgStyle:{fill:s,stroke:c,strokeWidth:1},labelShowBg:!!r,labelStyle:{fill:o,fontSize:12,fontWeight:600},selected:n,source:e.source,sourceHandle:e.sourceHandle,style:{filter:n?D:void 0,opacity:1,stroke:E,strokeOpacity:1,strokeWidth:1.5},target:e.target,targetHandle:e.targetHandle,type:e.type??`smoothstep`}}function Tt(e,t){return e.type===`startEvent`?e:(e.type===`endEvent`||e.type===`userTask`||e.type===`serviceTask`||e.type,{...e,data:{...e.data,triggerMode:t}})}function Et(e){return Ot(Dt(H(V(e))))}function V(e){let t=e.edges.map(e=>{let t=e.data??{};return e.data===t?e:{...e,data:t}});return t.some((t,n)=>t!==e.edges[n])?{...e,edges:t}:e}function Dt(e){let t=e.nodes.map(e=>{if(e.type!==`userTask`)return e;let t=e.data.allowAddSigner??!1,n=e.data.allowReject??!0,r=e.data.allowTransfer??!0,i=!e.data.decisionPolicy;return e.data.allowAddSigner===t&&e.data.allowReject===n&&e.data.allowTransfer===r&&!i?e:{...e,data:{...e.data,allowAddSigner:t,allowReject:n,allowTransfer:r,decisionPolicy:e.data.decisionPolicy??{type:`SINGLE`}}}});return t.some((t,n)=>t!==e.nodes[n])?{...e,nodes:t}:e}function H(e){let t=new Set(e.nodes.filter(e=>hn(e)).map(e=>e.id)),n=e.edges.filter(e=>!t.has(e.source));return n.length===e.edges.length?e:{...e,edges:n}}function Ot(e){let t=e.edges.reduce((e,t)=>({...e,[t.target]:(e[t.target]??0)+1}),{}),n=e.nodes.map(e=>e.type===`startEvent`?e:(t[e.id]??0)<2&&e.data.triggerMode!==`AND`?Tt(e,`AND`):e);return n.some((t,n)=>t!==e.nodes[n])?{...e,nodes:n}:e}function kt(){return{edges:[],meta:{schemaVersion:1},nodes:[{data:{label:`開始`},id:`start`,position:{x:80,y:160},type:`startEvent`},{data:{endState:`APPROVED`,label:`完成`,triggerMode:`AND`},id:`end`,position:{x:560,y:160},type:`endEvent`}]}}function At(e){return e.edges.length===0&&e.nodes.length===2&&e.nodes.some(e=>e.type===`startEvent`)&&e.nodes.some(e=>e.type===`endEvent`)}function jt(e){let t=new v.graphlib.Graph;return t.setDefaultEdgeLabel(()=>({})),t.setGraph({rankdir:`LR`,ranksep:120}),e.nodes.forEach(e=>{t.setNode(e.id,B(e))}),e.edges.forEach(e=>{t.setEdge(e.source,e.target)}),v.layout(t),{...e,nodes:e.nodes.map(e=>{let n=t.node(e.id);return n?{...e,position:{x:n.x-B(e).width/2,y:n.y-B(e).height/2}}:e})}}function U(e,t){return t?e.find(e=>e.id===t)??null:null}function Mt(e){return e===`OR`?`OR`:`AND`}function Nt(e){return e===`FROM_RETURN_POINT`?`FROM_RETURN_POINT`:`RESTART`}function Pt(e){if(!e||e.type===`SINGLE`||e.type===`PARALLEL_ANY`)return`可指定多位;多位時所有人都會收到待辦,任一人同意即可通過。`;if(e.type===`PARALLEL_ALL`)return`可指定多位;多位時所有人都會收到待辦,全部同意後才會通過。`;if(e.type===`SEQUENTIAL`)return`可指定多位;所有人會同時收到待辦,需全部同意後才會通過。`;let t=e.thresholdType===`PERCENTAGE`?`%`:` 位簽核者`;return`可指定多位;需達到 ${e.threshold}${t} 才會通過。`}function Ft(e){return e?.type??`SINGLE`}function It(e){return tt.find(t=>t.id===e)||(e===`SEQUENTIAL`?{id:e,name:`全部同意(既有設定)`}:{id:e,name:`未知決策方式(${e})`})}function Lt(e,t){return e===`QUORUM`?t?.type===`QUORUM`?t:{threshold:b.DEFAULT_QUORUM_THRESHOLD,thresholdType:`COUNT`,type:`QUORUM`}:e===`PARALLEL_ALL`||e===`PARALLEL_ANY`||e===`SEQUENTIAL`?{type:e}:{type:`SINGLE`}}function Rt(e){return e?.type===`QUORUM`?{threshold:Number.isFinite(e.threshold)?e.threshold:b.DEFAULT_QUORUM_THRESHOLD,thresholdType:zt(e.thresholdType??null)}:{threshold:b.DEFAULT_QUORUM_THRESHOLD,thresholdType:`COUNT`}}function zt(e){return e===`PERCENTAGE`?`PERCENTAGE`:`COUNT`}function Bt(e){return e===`HOUR`?`HOUR`:`DAY`}function Vt(e){return e===`BUSINESS_DAY`?`BUSINESS_DAY`:`CALENDAR`}function Ht(e){return b.SLA_TIMEOUT_ACTION_OPTIONS.find(t=>t.id===e)?.id??`REMIND`}function Ut(e){return $e.find(t=>t.value===e)??$e[0]}function Wt(e){return $e.find(t=>t.id===e)??$e[0]}function Gt(e,t){let n=Number.isFinite(t.value)?Math.trunc(t.value):1,r=(0,b.composeSlaDuration)({unit:t.unit,value:n});return{...e,calendar:t.unit===`DAY`?e.calendar??`CALENDAR`:`CALENDAR`,duration:r}}function Kt(e,t){return t===`ESCALATE`?{...e,escalateLevelsUp:e.escalateLevelsUp??1,onTimeout:t}:{...Jt(e,`escalateLevelsUp`),onTimeout:t}}function qt(e,t){return t===null?Jt(e,`warningAt`):{...e,warningAt:t}}function Jt(e,t){return Object.fromEntries(Object.entries(e).filter(([e])=>e!==t))}function Yt(e){return e===`ORG_MANAGER`||e===`ORG_UNIT_MANAGER`||e===`ORG_UNIT_MEMBER`||e===`ORG_UNIT_POSITION`||e===`POSITION`?e:`DIRECT`}function Xt(e){let t=Yt(e??`DIRECT`);return t===`ORG_MANAGER`?{baseFromInitiator:!0,levelsUp:1,type:`ORG_MANAGER`}:t===`ORG_UNIT_MANAGER`?{orgUnitId:``,type:`ORG_UNIT_MANAGER`}:t===`ORG_UNIT_MEMBER`?{includeDescendants:!1,orgUnitId:``,type:`ORG_UNIT_MEMBER`}:t===`ORG_UNIT_POSITION`?{includeDescendants:!1,orgUnitId:``,positionId:``,type:`ORG_UNIT_POSITION`}:t===`POSITION`?{positionId:``,type:`POSITION`}:{memberIds:[],type:`DIRECT`}}function Zt(e){return e===`DIRECT`?`DIRECT`:`NONE`}function Qt(e,t){return e.type===`ORG_MANAGER`||e.type===`ORG_UNIT_MANAGER`?{...e,fallback:t}:e}function $t(e){return I.find(t=>t.value===e)??I[0]}function en(e){return I.find(t=>t.id===e)??I[0]}function tn(e){return e===`ORG_UNIT`||e===`ORG_UNIT_POSITION`||e===`NONE`?e:`ALL`}function nn(e){let t=e?.trim();if(!t)return{mode:`ALL`,value:``};let n=on(t,/"([^"]+)" in subject\.orgUnitIds/gu),r=on(t,/"([^"]+)" in subject\.positionIds/gu);return n.length>0&&r.length>0?{includeDescendants:n.length>1,mode:`ORG_UNIT_POSITION`,orgUnitId:n[0],positionId:r[0],value:n[0]??``}:n.length>0?{includeDescendants:n.length>1,mode:`ORG_UNIT`,orgUnitId:n[0],value:n[0]??``}:{mode:`CUSTOM`,value:t}}function rn(e,t){let n=nn(e);return!t||t===`ALL`||t===`NONE`?t===`ALL`||t===`NONE`?{mode:t,value:``}:n:n.mode===t?n:ln(t)}function an(e){return e.mode===`NONE`?`發起權限需要選擇誰可以發起。`:(e.mode===`ORG_UNIT`||e.mode===`ORG_UNIT_POSITION`)&&!e.orgUnitId?.trim()?`指定組織發起時,需要選擇組織。`:e.mode===`ORG_UNIT_POSITION`&&!e.positionId?.trim()?`指定組織職位發起時,需要選擇職位。`:null}function on(e,t){return[...e.matchAll(t)].map(e=>e[1]).filter(e=>!!e)}function sn(e,t){if(e.mode===`ALL`||e.mode===`NONE`)return null;let n=e.orgUnitId?.trim()??``;if(!n)return null;let r=K(t,n,!!e.includeDescendants).map(e=>`${JSON.stringify(e)} in subject.orgUnitIds`).join(` || `);if(e.mode===`ORG_UNIT`)return r?`(${r})`:null;let i=e.positionId?.trim()??``;return i&&r?`(${r}) && ${JSON.stringify(i)} in subject.positionIds`:null}function cn(e,t,n){return e.mode===`NONE`?`未設定`:e.mode===`ORG_UNIT`?e.orgUnitId?`組織:${G(t,e.orgUnitId)}`:`指定組織`:e.mode===`ORG_UNIT_POSITION`?e.orgUnitId&&e.positionId?`組織職位:${G(t,e.orgUnitId)} / ${kn(n,e.positionId)}`:`指定組織職位`:e.mode===`CUSTOM`?`既有自訂規則`:`所有人`}function ln(e){return{includeDescendants:!0,mode:e,orgUnitId:``,positionId:``,value:``}}function un(e,t){let n=e.source?t.find(t=>t.id===e.source)??null:null,r=e.target?t.find(t=>t.id===e.target)??null:null;return!!n&&!!r&&e.source!==e.target&&e.sourceHandle===F&&e.targetHandle===P&&!!(n&&mn(n))&&!!(r&&pn(r))}function dn(e,t){return e.includes(t)?e.filter(e=>e!==t):[...e,t]}function fn(e){return e.type!==`startEvent`&&e.type!==`endEvent`}function pn(e){return e.type!==`startEvent`}function mn(e){return e.type!==`endEvent`&&!hn(e)}function hn(e){return e.type===`serviceTask`&&e.data.action.type===`NOTIFY`}function gn(e){return e instanceof HTMLElement?e.isContentEditable||e.tagName===`INPUT`||e.tagName===`TEXTAREA`||e.tagName===`SELECT`||!!e.closest(`[contenteditable="true"]`):!1}function _n(e){return e.map(e=>({formDefinitionId:e.formDefinitionId,formName:e.formName,id:e.id,name:`${e.formName} | v${e.version}`,schema:e.schema}))}function vn(e){return(e?.schema.fields??[]).reduce((e,t)=>({...e,[t.fieldKey]:yn(t)}),{})}function yn(e){return e.type===`number`?1e3:e.type===`boolean`?!0:(0,h.isFormStaticOptionFieldDefinition)(e)?e.type===`checkbox`?e.options[0]?[e.options[0].value]:[]:e.options[0]?.value??``:e.type===`date`?`2026-05-08`:e.type===`datetime`?`2026-05-08T09:00:00+08:00`:e.placeholder??e.label}function bn(e){let t=JSON.parse(e);if(!W(t))throw Error(`表單資料 JSON 必須是物件。`);return t}function W(e){return typeof e==`object`&&!!e&&!Array.isArray(e)}function xn(e){return e===`COMPLETED`?`完成`:e===`PASSED`?`通過`:e===`SKIPPED`?`略過`:e===`STOPPED`?`已停止`:e===`WAITING`?`將等待簽核`:e}function Sn(e){return e in Je?Je[e]:e}function Cn(e,t){return t&&!e.some(e=>e.id===t.id)?[t,...e]:e}function wn(e){return e.map(e=>({displayName:e.name,email:e.email,id:e.memberId,memberId:e.memberId,name:Hn(e.name,e.email)}))}function Tn(e){return{displayName:`未知會員`,email:``,id:e,memberId:e,name:`未知會員`,unresolved:!0}}function En(e,t){return e.find(e=>e.memberId===t)??Tn(t)}function Dn(e,t){let n=e.find(e=>e.id===t);return n?i.a(n):null}function On(e,t){let n=e.find(e=>e.id===t);return n?i.o(n):null}function G(e,t){return Dn(e,t)?.name??`未指定組織`}function kn(e,t){return On(e,t)?.name??`未指定職位`}function An(e,t){let n=jn(),r=t.filter(t=>t.memberId===e&&Mn(t,n)),i=r.reduce((e,t)=>e&&Nn(e,t)<=0?e:t,null);return{customFields:{},managerMemberId:`member-002`,memberId:e,orgCode:`HQ`,orgUnitIds:Pn(r.map(e=>e.orgUnitId)),positionId:i?.positionId??null,positionIds:Pn(r.map(e=>e.positionId)),primaryOrgUnitId:i?.orgUnitId??null,roles:[`manager`]}}function jn(){return new Date().toISOString().slice(0,10)}function Mn(e,t){return e.effectiveFrom<=t&&(!e.effectiveTo||e.effectiveTo>=t)}function Nn(e,t){return e.isPrimary===t.isPrimary?t.effectiveFrom.localeCompare(e.effectiveFrom):e.isPrimary?-1:1}function Pn(e){return e.reduce((e,t)=>t&&!e.includes(t)?[...e,t]:e,[])}function Fn({includeDescendants:e,memberships:t,orgUnitId:n,orgUnits:r,positions:i}){let a=new Set(K(r,n,e)),o=new Set(t.filter(e=>a.has(e.orgUnitId)).map(e=>e.positionId).filter(e=>!!e));return i.filter(e=>o.has(e.id))}function K(e,t,n){let r=e.find(e=>e.id===t);return r?n?e.filter(e=>e.id===r.id||e.path.startsWith(`${r.path}.`)).map(e=>e.id):[r.id]:t.trim()?[t]:[]}function In(e,t){let n=new Map(t.filter(e=>!e.unresolved).map(e=>[e.memberId,e])),r=new Set(e.map(e=>e.memberId)),i=t.filter(e=>!r.has(e.memberId)),a=e.map(e=>(e.unresolved?n.get(e.memberId):null)??e);return i.length>0||a.some((t,n)=>t!==e[n])?[...a,...i]:e}function q(e){return e.type===`DIRECT`?e.memberIds:(e.type===`ORG_MANAGER`||e.type===`ORG_UNIT_MANAGER`)&&e.fallback?.type===`DIRECT`&&e.fallback.memberId?[e.fallback.memberId]:[]}function Ln(e){return[...new Set(e.nodes.flatMap(e=>e.type===`userTask`?q(e.data.approverResolver):e.type===`serviceTask`?rr(e.data.action):[]))]}function Rn(e,t,n,r){return e.type===`userTask`?zn(e.data.approverResolver,t,n,r):null}function zn(e,t,n,r){return e.type===`DIRECT`?Vn(e.memberIds,t,`未指定簽核者`):e.type===`ORG_MANAGER`?$t(e.levelsUp).name:e.type===`ORG_UNIT_MANAGER`?`組織主管:${G(n,e.orgUnitId)}`:e.type===`ORG_UNIT_MEMBER`?`組織任一人:${G(n,e.orgUnitId)}`:e.type===`ORG_UNIT_POSITION`?`組織職位:${G(n,e.orgUnitId)} / ${kn(r,e.positionId)}`:e.type===`POSITION`?`職位:${kn(r,e.positionId)}`:e.type===`DYNAMIC_FORM`?`表單欄位:${e.formPath||`未設定`}`:`自訂表達式`}function Bn(e,t){if(e.type!==`serviceTask`)return null;let n=rr(e.data.action);return n.length===0?[`未指定知會對象`]:n.map(e=>En(t,e).name)}function Vn(e,t,n){let r=e.map(e=>En(t,e).name);return r.length===0?n:r.length<=2?r.join(`、`):`${r.slice(0,2).join(`、`)} 等 ${r.length} 人`}function Hn(e,t){return`${e} (${t})`}function Un(e,t){let n=t?.getBoundingClientRect();if(!n||e.nodes.length===0)return null;let r=e.nodes.reduce((e,t)=>{let n=B(t);return{maxX:Math.max(e.maxX,t.position.x+n.width),maxY:Math.max(e.maxY,t.position.y+n.height),minX:Math.min(e.minX,t.position.x),minY:Math.min(e.minY,t.position.y)}},{maxX:-1/0,maxY:-1/0,minX:1/0,minY:1/0});return(0,_.getViewportForBounds)({height:r.maxY-r.minY,width:r.maxX-r.minX,x:r.minX,y:r.minY},n.width,n.height,.1,1,.2)}function Wn(e){let t=e.nodes.find(e=>e.type===`userTask`&&!!Gn(e.data.approverResolver)),n=e.nodes.find(e=>e.type===`serviceTask`&&e.data.action.type===`NOTIFY`&&rr(e.data.action).length===0),r=e.edges.find(t=>tr(t,e.nodes)&&!t.data.isDefault&&!t.data.condition);return t&&t.type===`userTask`?Gn(t.data.approverResolver):n?`知會節點需要至少一位知會對象。`:r?`條件分流的每條輸出連線都需要先設定條件。`:null}function Gn(e){return e.type===`DIRECT`&&e.memberIds.length===0?`簽核節點需要指定簽核會員。`:e.type===`ORG_MANAGER`&&e.levelsUp<1?`簽核節點需要指定有效的主管層級。`:e.type===`ORG_UNIT_MANAGER`&&!e.orgUnitId.trim()||e.type===`ORG_UNIT_MEMBER`&&!e.orgUnitId.trim()?`簽核節點需要指定組織。`:e.type===`ORG_UNIT_POSITION`&&(!e.orgUnitId.trim()||!e.positionId.trim())?`簽核節點需要指定組織與職位。`:(e.type===`ORG_MANAGER`||e.type===`ORG_UNIT_MANAGER`)&&e.fallback?.type===`DIRECT`&&!e.fallback.memberId.trim()?`簽核節點需要指定改派固定人。`:e.type===`POSITION`&&!e.positionId.trim()?`簽核節點需要指定職位。`:null}function Kn(e){return e.edges.some(t=>tr(t,e.nodes)&&!!(t.data.condition||t.data.conditionFieldKey||t.data.conditionOperator||t.data.conditionValue))}function qn(e){return e?.fields.map(e=>({fieldType:e.type,id:e.fieldKey,name:`${e.label} (${e.fieldKey})`}))??[]}function Jn(e,t){return t?e?.fields.find(e=>e.fieldKey===t)??null:null}function Yn(e){if(!e)return[];let t=Zn(e);return it.filter(e=>t.includes(e.id))}function Xn(e){return it.some(t=>t.id===e)?e:null}function Zn(e){return e.type===`file_upload`?[`IS_FILLED`,`IS_EMPTY`]:e.type===`boolean`?[`EQUALS`,`NOT_EQUALS`,`IS_FILLED`,`IS_EMPTY`]:e.type===`date`||e.type===`datetime`||e.type===`money`||e.type===`number`?[`EQUALS`,`NOT_EQUALS`,`GREATER_THAN`,`GREATER_THAN_OR_EQUALS`,`LESS_THAN`,`LESS_THAN_OR_EQUALS`,`IS_FILLED`,`IS_EMPTY`]:[`EQUALS`,`NOT_EQUALS`,`IS_FILLED`,`IS_EMPTY`]}function Qn(e){return e?e.type===`boolean`?[{id:`true`,name:`是`},{id:`false`,name:`否`}]:(0,h.isFormStaticOptionFieldDefinition)(e)?e.options.map(e=>({id:e.value,name:e.label})):[]:[]}function $n(e){return at.includes(e)}function er(e,t){if(e.data.label)return e.data.label;if(tr(e,t))return J(e);if(nr(e,t))return`同時進行`}function J(e){return e.data.isDefault?`其他情況`:`請設定條件`}function tr(e,t){return t.some(t=>t.id===e.source&&t.type===`exclusiveGateway`)}function nr(e,t){return t.some(t=>t.id===e.source&&t.type===`parallelGateway`)}function rr(e){return e.type===`NOTIFY`&&e.recipients.type===`DIRECT`?e.recipients.memberIds:[]}function Y(e){return e instanceof Error?(0,m.readFormSchemaLintMessage)(e.message):`發生未知錯誤`}Object.defineProperty(exports,"t",{enumerable:!0,get:function(){return ht}});
65
- //# sourceMappingURL=designer-Cdn10NNl.cjs.map