@gct-paas/excel 0.1.28-beta.13 → 0.1.28-beta.15

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 (140) hide show
  1. package/dist/{BaseComponent-yoXj5Q9c.js → BaseComponent-xTm5lvAr.js} +1 -1
  2. package/dist/{VueVideoPlayer-PNmROB21.js → VueVideoPlayer-VqMD-VzE.js} +2 -2
  3. package/dist/{agg-design-CIzPSLQK.js → agg-design-CDGxy74G.js} +1 -1
  4. package/dist/{agg-props-BtExSoDy.js → agg-props-I0uVWtew.js} +1 -1
  5. package/dist/{agg-style-BpM01gwW.js → agg-style-BOgtQhbI.js} +1 -1
  6. package/dist/{align-editor-BFJLBBrG.js → align-editor-BlSGHkKV.js} +1 -1
  7. package/dist/{attach-fields-editor-DESDkODo.js → attach-fields-editor-BD9EqEpy.js} +2 -2
  8. package/dist/{barcode-design-E0XlG9we.js → barcode-design-DX7HKncP.js} +2 -2
  9. package/dist/base/index.es.js +38 -25
  10. package/dist/{base-font-editor-DKfvfFLW.js → base-font-editor-J0236vKt.js} +2 -2
  11. package/dist/{boolean-design-C2Ge6IJa.js → boolean-design-C4IL71hn.js} +2 -2
  12. package/dist/{boolean-props-BC9qPn3v.js → boolean-props-DPnQjPn4.js} +3 -3
  13. package/dist/{boolean-style-SCwjwD08.js → boolean-style-DcPK-sHx.js} +4 -4
  14. package/dist/{cell-upload-BwgoWoQu.js → cell-upload-Cl_q0TFe.js} +2 -2
  15. package/dist/{date-range-editor-QmZ_SH1T.js → date-range-editor-dw8bGEDk.js} +2 -2
  16. package/dist/{date-time-design-CkX96TXi.js → date-time-design-CddPutOC.js} +2 -2
  17. package/dist/{date-time-props-1NtodWBx.js → date-time-props-8WiF6kij.js} +3 -3
  18. package/dist/{date-time-style-C2TiyGPc.js → date-time-style-rpjmesdl.js} +1 -1
  19. package/dist/{decimal-design-Bm3X3dXb.js → decimal-design-BxjCOMQo.js} +1 -1
  20. package/dist/{decimal-display-mode-CtCHuV5o.js → decimal-display-mode-DUtCChqm.js} +2 -2
  21. package/dist/{decimal-props-EyBLuOaV.js → decimal-props-E8kDPi62.js} +4 -4
  22. package/dist/{decimal-style-BjE-jGFo.js → decimal-style-spHhzPje.js} +1 -1
  23. package/dist/{default-value-editor.vue_vue_type_script_setup_true_name_default-value-editor_lang-CLX0rk6o.js → default-value-editor.vue_vue_type_script_setup_true_name_default-value-editor_lang-CC6lhMFx.js} +2 -2
  24. package/dist/{diagonal-design-D6Fc3gj9.js → diagonal-design-o2_Ln07d.js} +2 -2
  25. package/dist/{double-design-DEj7ZOUS.js → double-design-ClNDFQeg.js} +1 -1
  26. package/dist/{double-props-fwy17Nm3.js → double-props-Cx1TFszr.js} +4 -4
  27. package/dist/{double-style-dq6tMEc1.js → double-style-Cd2X6Gaj.js} +1 -1
  28. package/dist/{dynamic-table-action-CIpRxnGv.js → dynamic-table-action-B1t4gegC.js} +153 -54
  29. package/dist/{dynamic-table-action.vue_vue_type_style_index_0_scoped_53d7e66c_lang-CJWFZ-MC.js → dynamic-table-action.vue_vue_type_style_index_0_scoped_53d7e66c_lang-pfvEPOi4.js} +27 -8
  30. package/dist/{edit.utils-CXmmCnxE-1A0siaIV.js → edit.utils-CXmmCnxE-B4bsziH1.js} +1 -1
  31. package/dist/{enum-design-DDnWoH67.js → enum-design-CyA0j-zz.js} +2 -2
  32. package/dist/{enum-props-BD8bagB0.js → enum-props-A-KWiAWF.js} +3 -3
  33. package/dist/{enum-style-BEq7-HmM.js → enum-style-V2Z6YO2q.js} +3 -3
  34. package/dist/excel.css +49 -49
  35. package/dist/{exceljs.min-BtL4ssJW.js → exceljs.min-Ba22AEEJ.js} +2 -2
  36. package/dist/{expression-design-BclTTB2d.js → expression-design-DjepSTdq.js} +1 -1
  37. package/dist/{expression-props-BPWTmoRN.js → expression-props-Bp788TOc.js} +1 -1
  38. package/dist/{expression-style-KN43Asr8.js → expression-style-DePg4hbS.js} +1 -1
  39. package/dist/{file-design-B4R2a1EF.js → file-design-BZFrxxck.js} +1 -1
  40. package/dist/{file-props-B_iOIHQc.js → file-props-B3f2SUnQ.js} +2 -2
  41. package/dist/{file-style-DRihncjw.js → file-style-Cp8I50eh.js} +1 -1
  42. package/dist/{font-editor-DILLEpBf.js → font-editor-1MVL3eZf.js} +3 -3
  43. package/dist/{image-design-Cdue-t-P.js → image-design-C2IB09BL.js} +2 -2
  44. package/dist/{image-design-BWH4KEb5.js → image-design-yw08zkfR.js} +1 -1
  45. package/dist/{image-props-CRcWdDsz.js → image-props-C-RpjQZo.js} +1 -1
  46. package/dist/{image-style-CaHLG6Kv.js → image-style-BFRLtn4j.js} +1 -1
  47. package/dist/{index-FB6-4yO4.js → index-B0TYMwSH.js} +2 -2
  48. package/dist/{index-DF7AaeZr.js → index-B9_evTl8.js} +2 -2
  49. package/dist/{index-PWz8qpGY.js → index-BIx_FKsP.js} +1 -1
  50. package/dist/{index--9YrGUGP.js → index-BN77Db6w.js} +1 -1
  51. package/dist/{index-DVu7ZqxY.js → index-BPKQSGBa.js} +3 -3
  52. package/dist/{index-DBInAbL5.js → index-BUVIxRH1.js} +2 -2
  53. package/dist/{index-BwAWrUBy.js → index-BXxZaXM0.js} +1 -1
  54. package/dist/{index-CyziZcCV.js → index-BYiHlyNO.js} +1 -1
  55. package/dist/{index-CzTlLy5h.js → index-B_C2TV0O.js} +2 -2
  56. package/dist/{index-BznCWqjU.js → index-BcjXXndd.js} +2 -2
  57. package/dist/{index-CC598O9j.js → index-Bn9lfGTg.js} +2 -2
  58. package/dist/{index-lKAhsmrc.js → index-BrbLkQ85.js} +1 -1
  59. package/dist/{index-D8X_W_pp.js → index-BzKmBFgF.js} +2 -2
  60. package/dist/{index-D-yvhtrU.js → index-C19mNa-C.js} +2 -2
  61. package/dist/{index-ClLKpkX-.js → index-C3MntK5E.js} +2 -2
  62. package/dist/{index-ByzIMvBq.js → index-C9EPhy9Y.js} +2 -2
  63. package/dist/{index-B-79lVcx.js → index-CGDCyk1j.js} +2 -2
  64. package/dist/{index-OIVcO8s_.js → index-CISPYl9d.js} +1 -1
  65. package/dist/{index-Cipk_7qc.js → index-CKZaoE4M.js} +2 -2
  66. package/dist/{index-BYhpHZAo.js → index-CTvP2ZsP.js} +2 -2
  67. package/dist/{index-B5_bwjeV.js → index-Ccy6EfNX.js} +1 -1
  68. package/dist/{index-D8Nx2OJG.js → index-CduVjl_-.js} +2 -2
  69. package/dist/{index-coGNwri5.js → index-CeHE4Lud.js} +1 -1
  70. package/dist/{index-BhhGzubm.js → index-Cf71IqK7.js} +1 -1
  71. package/dist/{index-C3qZBL6L.js → index-CfuGtMMK.js} +3 -3
  72. package/dist/{index-BZRsVrR9.js → index-D8LRwKFp.js} +1 -1
  73. package/dist/{index-Zc6LSiHo.js → index-DC0feGcK.js} +2 -2
  74. package/dist/{index-CyW-4owh.js → index-DDfokD0Z.js} +2 -2
  75. package/dist/{index-CfStY_Cz.js → index-DWkm7pZL.js} +2 -2
  76. package/dist/{index-BFgZXsNC.js → index-DaXFWKRj.js} +3 -3
  77. package/dist/{index-DOqfBBNa.js → index-Dpb0uLo3.js} +3 -3
  78. package/dist/{index-YKd9P21f.js → index-NwgCso5Y.js} +246 -74
  79. package/dist/{index-C9j0OIvN.js → index-f4u_4-Vz.js} +2 -2
  80. package/dist/index.es.js +2 -2
  81. package/dist/{integer-design-Cc-fwu5M.js → integer-design-CP4_pQ4s.js} +1 -1
  82. package/dist/{integer-props-NqSyDTdp.js → integer-props-DNzb4tKt.js} +4 -4
  83. package/dist/{integer-style-D6RV1Wrt.js → integer-style-CcVyRSf9.js} +1 -1
  84. package/dist/{mb-render-CTK4W79-.js → mb-render-B2yKo5OJ.js} +1 -1
  85. package/dist/{number-input-ex-FzDH4jte.js → number-input-ex-BpheHcmW.js} +1 -1
  86. package/dist/{org-props-Du18mwlt.js → org-props-CmYJh6tl.js} +2 -2
  87. package/dist/{org-style-vVR0PIRF.js → org-style-C1b4OsQu.js} +1 -1
  88. package/dist/{pagination-design-CbMPd2rJ.js → pagination-design-_vsK4b0a.js} +2 -2
  89. package/dist/paper-widget-design-DTWrlciw.js +4 -0
  90. package/dist/{qrcode-design-1l-v3cJO.js → qrcode-design-CgA3sbDN.js} +1 -1
  91. package/dist/{quick-search.util-_1ukDLe3.js → quick-search.util-D28vFuWm.js} +1 -1
  92. package/dist/{ref-autofill-editor-pz2xOPV9.js → ref-autofill-editor-CxspMCr8.js} +3 -3
  93. package/dist/{ref-props-DDE-Cqab.js → ref-props-DG5uZ73Q.js} +4 -4
  94. package/dist/{ref-style-CIGZXNUI.js → ref-style-DurdweBv.js} +1 -1
  95. package/dist/{regex-editor-CZIkZwo2.js → regex-editor-BJqtyjrd.js} +2 -2
  96. package/dist/{revo-grid.entry-DaQhq21b.js → revo-grid.entry-CdGl1o68.js} +1 -1
  97. package/dist/{revogr-attribution_7.entry-8lq6FIyD.js → revogr-attribution_7.entry-DTBowB-3.js} +3 -3
  98. package/dist/{revogr-clipboard_3.entry-JKz3q4Hr.js → revogr-clipboard_3.entry-CHaJF7Fr.js} +2 -2
  99. package/dist/{revogr-data_4.entry-dKqISKJJ.js → revogr-data_4.entry-BOlY6RhY.js} +2 -2
  100. package/dist/{revogr-filter-panel.entry-N7r1TehE.js → revogr-filter-panel.entry-DJFcQ4PR.js} +1 -1
  101. package/dist/{select-render-type-editor.vue_vue_type_script_setup_true_lang-BmK6eR2q.js → select-render-type-editor.vue_vue_type_script_setup_true_lang-BO5Cziz6.js} +2 -2
  102. package/dist/{serialnumber-design-oNoAPQYE.js → serialnumber-design-CwWMrxPl.js} +1 -1
  103. package/dist/shared/index.es.js +2 -2
  104. package/dist/{signature-design-BKVUj3dz.js → signature-design-MvfT6Ckd.js} +1 -1
  105. package/dist/{signature-props-VS7FQ4WT.js → signature-props-BLgkvcaW.js} +3 -3
  106. package/dist/{signature-style-D45JHPQ9.js → signature-style-dZXB9Fqk.js} +1 -1
  107. package/dist/{single-field-drop-CHr4xlT7.js → single-field-drop-CQSHoCNn.js} +2 -2
  108. package/dist/{size-editor-FCeiT5v-.js → size-editor-DLvvzfaB.js} +1 -1
  109. package/dist/src/nocode-base/src/hooks/material-consume/bom-validator.d.ts +15 -4
  110. package/dist/src/nocode-base/src/hooks/material-consume/material-consume-table-controller.d.ts +16 -7
  111. package/dist/src/nocode-base/src/hooks/material-consume/tmpl-bom-controller.d.ts +1 -4
  112. package/dist/src/nocode-base/src/hooks/useRenderPageFactory.d.ts +6 -0
  113. package/dist/src/nocode-base/src/types/common/base.d.ts +4 -0
  114. package/dist/{text-design-k2YJTgHF.js → text-design-CLGyFj36.js} +2 -2
  115. package/dist/{text-design-6crpgsvL.js → text-design-CLO0d-ma.js} +2 -2
  116. package/dist/{text-props-BdkFSEYb.js → text-props-Dip3NOUi.js} +4 -4
  117. package/dist/{text-style-G_QJbeqV.js → text-style-CDQKakb6.js} +1 -1
  118. package/dist/{throttle-Cpk1LoGk-Chwxknn8.js → throttle-Cpk1LoGk-UC-FZa3V.js} +1 -1
  119. package/dist/{timediff-design-nFxf6PDJ.js → timediff-design-BhbElBy_.js} +1 -1
  120. package/dist/{trace-design-CypNF3jg.js → trace-design-CNvlAWJq.js} +2 -2
  121. package/dist/{trace-props-Dbu6m3sG.js → trace-props-CKhHYXvo.js} +14 -7
  122. package/dist/{trace-style-ivwTK2Ip.js → trace-style-DGT2hz9I.js} +1 -1
  123. package/dist/{user-props-Cy7pdSkn.js → user-props-Cr0-wazJ.js} +2 -2
  124. package/dist/{user-style-BGf-anIc.js → user-style-DFDrCaD8.js} +1 -1
  125. package/dist/{value-editor.vue_vue_type_style_index_0_lang-BNs_Pti3.js → value-editor.vue_vue_type_style_index_0_lang-CuzD81ts.js} +2 -2
  126. package/dist/{version-select-X8WcI5Eg.js → version-select-Bm0da2Lh.js} +1 -1
  127. package/dist/web-render/index.es.js +3 -3
  128. package/dist/{widget-barcode-BUrn0yvZ.js → widget-barcode-CtPYoT2X.js} +4 -4
  129. package/dist/{widget-diagonal-BSD8oWxq.js → widget-diagonal-3gBCUJJ-.js} +3 -3
  130. package/dist/{widget-image-BBmNrtJm.js → widget-image-CHrI6UUR.js} +5 -5
  131. package/dist/{widget-line-Dd_FE9s8.js → widget-line-Hdg3sTBz.js} +2 -2
  132. package/dist/{widget-pagination-C8YFddnq.js → widget-pagination-VrbdYDf9.js} +5 -5
  133. package/dist/{widget-power-eUE8GyiB.js → widget-power-6Om7To49.js} +3 -3
  134. package/dist/{widget-qrcode-dK_cxHdu.js → widget-qrcode-TrDSd0Za.js} +3 -3
  135. package/dist/{widget-rangelimit-Bkvpg74s.js → widget-rangelimit-BFuZoeqJ.js} +3 -3
  136. package/dist/{widget-serialnumber-Cg-YHSe9.js → widget-serialnumber-Tm49o2Xy.js} +1 -1
  137. package/dist/{widget-text-BdO-7z8L.js → widget-text-C-o-Tq83.js} +5 -5
  138. package/dist/{widget-timediff-D4jaO4t-.js → widget-timediff-CcA_6dU9.js} +2 -2
  139. package/package.json +2 -2
  140. package/dist/paper-widget-design-CyrB9ozG.js +0 -4
@@ -1,10 +1,10 @@
1
1
  import { computed, watch, toRaw, onUnmounted, markRaw, ref, inject, unref, provide, reactive, defineComponent, openBlock, createElementBlock, mergeProps, createElementVNode, normalizeClass, renderSlot, createCommentVNode, createVNode, toDisplayString, toRef, isVNode, h, onBeforeMount, resolveComponent, createBlock, withCtx, Fragment, renderList, createTextVNode, onMounted } from "vue";
2
2
  import { isNil, cloneDeep, merge, pickBy, mergeWith, omit, last, pick } from "lodash-es";
3
- import { ax as useWidgetStaticAttrs, Q as PlatformEnum, m as ComponentTypeEnum, cE as assembleRules, cF as deleteFormRule, cG as setFormRule, bx as requestDisplayValidation, cH as isReferenceOptionActive, cI as validateAllFields, cJ as runValidation, cK as ensureFrontRowKey, cL as FRONT_ROW_KEY, bK as getRowId, aL as getParseRuleInfo, br as transformUtils, aO as materialCheck, aP as getLotLockedReason, aU as FormulaRuleFieldKeyEnum, aF as NCB_PROVIDE, F as FIELD_TYPE, w as api, d as SubTableType, aM as getParseRuleValue, bE as uuid2, ap as DeviceLink, _ as _export_sfc, c3 as buildFormChangeDisplayRows, cA as resolveRowFormChangeMark, cz as resolveFormChangeRowUi, cl as isAnnLocationSelected, cB as setSelectMobileTdId, cm as isFormChangeGhostRow, t as CellType, az as setSelectAnnotationId, cu as recordSubtableRowDelete, c5 as deleteSubtableRow, cv as relocateDeletedRowsToEnd, ck as insertSubtableRows, ct as recordSubtableRowAdd, aN as useCurrentPageFormState, aC as renderUtils, y as useModal, cM as q, cN as groupFixedTableRows, cO as QUICK_FILL_ALLOWED_FIELDS, cP as processQuickFillRows, cQ as getIsGroupEmpty, aS as RenderModeEnum, cf as getSubTableQuickFillInfo } from "./dynamic-table-action.vue_vue_type_style_index_0_scoped_53d7e66c_lang-CJWFZ-MC.js";
3
+ import { ax as useWidgetStaticAttrs, Q as PlatformEnum, m as ComponentTypeEnum, cE as assembleRules, cF as deleteFormRule, cG as setFormRule, bx as requestDisplayValidation, cH as isReferenceOptionActive, cI as validateAllFields, cJ as runValidation, cK as ensureFrontRowKey, cL as FRONT_ROW_KEY, bK as getRowId, aL as getParseRuleInfo, br as transformUtils, aO as materialCheck, aP as getLotLockedReason, aU as FormulaRuleFieldKeyEnum, aF as NCB_PROVIDE, F as FIELD_TYPE, w as api, d as SubTableType, aM as getParseRuleValue, bE as uuid2, ap as DeviceLink, _ as _export_sfc, c3 as buildFormChangeDisplayRows, cA as resolveRowFormChangeMark, cz as resolveFormChangeRowUi, cl as isAnnLocationSelected, cB as setSelectMobileTdId, cm as isFormChangeGhostRow, t as CellType, az as setSelectAnnotationId, cu as recordSubtableRowDelete, c5 as deleteSubtableRow, cv as relocateDeletedRowsToEnd, ck as insertSubtableRows, ct as recordSubtableRowAdd, aN as useCurrentPageFormState, aC as renderUtils, y as useModal, cM as q, cN as groupFixedTableRows, cO as QUICK_FILL_ALLOWED_FIELDS, cP as processQuickFillRows, cQ as getIsGroupEmpty, aS as RenderModeEnum, cf as getSubTableQuickFillInfo } from "./dynamic-table-action.vue_vue_type_style_index_0_scoped_53d7e66c_lang-pfvEPOi4.js";
4
4
  import dayjs from "dayjs";
5
5
  import { u as useNamespace } from "./use-namespace-BxkK4ofX.js";
6
6
  import { Modal, message } from "ant-design-vue";
7
- import { u as useFormModel } from "./mb-render-CTK4W79-.js";
7
+ import { u as useFormModel } from "./mb-render-B2yKo5OJ.js";
8
8
  const InstanceStatusValues = {
9
9
  /** 作废状态 */
10
10
  ABANDON: "ABANDON",
@@ -327,6 +327,16 @@ const validate = async (formData, paper, uniqueId) => {
327
327
  uiApplied: false
328
328
  };
329
329
  };
330
+ class McRowValidateError extends Error {
331
+ constructor(message2, targetFieldId, row) {
332
+ super(message2);
333
+ this.targetFieldId = targetFieldId;
334
+ this.row = row;
335
+ this.name = "McRowValidateError";
336
+ }
337
+ targetFieldId;
338
+ row;
339
+ }
330
340
  class BomEntryValidator {
331
341
  constructor(bomEntry, enableSequenceLoading, getMaterialNoNum, historyData, mainMaterialNo, noBomMode) {
332
342
  this.bomEntry = bomEntry;
@@ -499,7 +509,7 @@ class BomEntryValidator {
499
509
  }
500
510
  const allowed = (this.bomEntry.specified_material_entries_ ?? []).map((e) => e.name_).filter(Boolean);
501
511
  if (!allowed.includes(lot)) {
502
- throw new Error(`${lot},不在指定物料批次范围内`);
512
+ throw new McRowValidateError(`${lot},不在指定物料批次范围内`, "material_no_", row);
503
513
  }
504
514
  }
505
515
  /** 整组指定批次校验:组内每一行有批次值的都检查 */
@@ -878,15 +888,9 @@ class BomEntriesValidator {
878
888
  if (!rows.length) throw new Error($t("sys.edhr.mcTable.materialEmptyError"));
879
889
  rows.forEach((row) => {
880
890
  this.validateDataCompleted(row);
881
- if (row.expiration_date_ && dayjs(row.expiration_date_).endOf("day").isBefore(dayjs())) {
882
- throw new Error(
883
- $t("sys.expirationDateError", { product: row.product_id__lb_, lot: row.material_no_ })
884
- );
885
- }
886
891
  });
887
892
  util.validateSubstitute(arr);
888
893
  util.validateLotMixing(arr);
889
- util.validateSpecifiedMaterialNoForGroup(arr);
890
894
  const orderIndex = this.resolveGroupOrderIndexByUtil(util, arr);
891
895
  const groupNo = orderIndex >= 0 ? orderIndex + 1 : void 0;
892
896
  await util.validateGroupQty(arr, this.enableSequenceLoading, groupNo);
@@ -898,46 +902,98 @@ class BomEntriesValidator {
898
902
  await this.validateGroup(arr, current);
899
903
  }
900
904
  /**
901
- * 校验物料是否在bom里被使用
902
- * @param row 单行的数据
905
+ * 行级错误(提交收集全部打标;切组/扫码抛第一条)
903
906
  */
904
- validateInBom(row) {
907
+ getRowFieldErrors(row) {
905
908
  if (this.noBomMode) {
906
- return;
909
+ return [];
907
910
  }
911
+ const errors = [];
908
912
  if (!row.product_id_) {
909
- throw new Error($t("sys.edhr.mcTable.materialEmptyError"));
913
+ errors.push(
914
+ new McRowValidateError($t("sys.edhr.mcTable.materialEmptyError"), "product_id_", row)
915
+ );
916
+ return errors;
910
917
  }
911
918
  const util = this.findUtilByProductId(row.product_id_);
912
919
  if (!util) {
913
- throw new Error($t("匹配不到对应物料,请按规则上料或新增物料"));
920
+ errors.push(
921
+ new McRowValidateError($t("匹配不到对应物料,请按规则上料或新增物料"), "product_id_", row)
922
+ );
923
+ return errors;
914
924
  }
915
- }
916
- /**
917
- * 检查数据是否完整
918
- * @param arr
919
- */
920
- validateDataCompleted(row) {
921
- this.validateInBom(row);
922
- const util = this.findUtilByProductId(row.product_id_);
923
925
  const { type_ } = util.bomEntry;
924
926
  if (type_ === "view") {
925
- return;
927
+ return errors;
926
928
  }
927
929
  if (type_ === "by_lot" && !row.material_no_) {
928
- throw new Error(
929
- $t("sys.edhr.mcTable.materialNoEmptyError", {
930
- product: this.translateProductCode(row.product_id_)
931
- })
930
+ errors.push(
931
+ new McRowValidateError(
932
+ $t("sys.edhr.mcTable.materialNoEmptyError", {
933
+ product: this.translateProductCode(row.product_id_)
934
+ }),
935
+ "material_no_",
936
+ row
937
+ )
932
938
  );
933
939
  }
934
940
  if (!row.qty_) {
935
- throw new Error(
936
- $t("sys.edhr.mcTable.materialNumEmptyError", {
937
- product: this.translateProductCode(row.product_id_)
938
- })
941
+ errors.push(
942
+ new McRowValidateError(
943
+ $t("sys.edhr.mcTable.materialNumEmptyError", {
944
+ product: this.translateProductCode(row.product_id_)
945
+ }),
946
+ "qty_",
947
+ row
948
+ )
949
+ );
950
+ }
951
+ if (row.expiration_date_ && dayjs(row.expiration_date_).endOf("day").isBefore(dayjs())) {
952
+ errors.push(
953
+ new McRowValidateError(
954
+ $t("sys.expirationDateError", {
955
+ product: row.product_id__lb_,
956
+ lot: row.material_no_
957
+ }),
958
+ "expiration_date_",
959
+ row
960
+ )
939
961
  );
940
962
  }
963
+ try {
964
+ util.validateSpecifiedMaterialNo(row);
965
+ } catch (e) {
966
+ if (e instanceof McRowValidateError) {
967
+ errors.push(e);
968
+ } else if (e?.message) {
969
+ errors.push(new McRowValidateError(e.message, "material_no_", row));
970
+ }
971
+ }
972
+ return errors;
973
+ }
974
+ /**
975
+ * 校验物料是否在bom里被使用
976
+ * @param row 单行的数据
977
+ */
978
+ validateInBom(row) {
979
+ const first = this.getRowFieldErrors(row).find((e) => e.targetFieldId === "product_id_");
980
+ if (first) throw first;
981
+ }
982
+ /**
983
+ * 检查数据是否完整(切组/扫码:遇错即抛)
984
+ */
985
+ validateDataCompleted(row) {
986
+ const first = this.getRowFieldErrors(row)[0];
987
+ if (first) throw first;
988
+ }
989
+ /** 提交:收集全表行级错误,不中断。无物料且无组归属的占位行跳过 */
990
+ collectRowErrors(arr) {
991
+ const errors = [];
992
+ arr.forEach((row) => {
993
+ if (row.deleted_ || !row.product_id_ && !row.bom_entry_id_) return;
994
+ errors.push(...this.getRowFieldErrors(row));
995
+ });
996
+ return errors;
941
997
  }
942
998
  /**
943
999
  * 检查扫描数据是否可以插入,通过后返回填充计划(记录模式无 plan)
@@ -971,9 +1027,9 @@ class BomEntriesValidator {
971
1027
  }
972
1028
  }
973
1029
  /**
974
- * 提交整表校验:必须上料组须存在;顺序上料校验组序;表中存在的组走整组校验(不含库存)
1030
+ * 提交组级校验:必须上料 / 顺序 / 替代料 / 混批 / 组数量。遇错即抛,不含行级必填。
975
1031
  */
976
- async validateAllRows(arr) {
1032
+ async assertGroupRules(arr) {
977
1033
  if (this.noBomMode) {
978
1034
  return;
979
1035
  }
@@ -986,9 +1042,16 @@ class BomEntriesValidator {
986
1042
  this.assertSubmitSequenceOrder(arr);
987
1043
  }
988
1044
  for (const util of this.bomEntryValidators) {
989
- if (this.groupExistsInTable(arr, util)) {
990
- await this.validateGroup(arr, util);
991
- }
1045
+ if (!this.groupExistsInTable(arr, util)) continue;
1046
+ const rows = arr.filter(
1047
+ (r) => !r.deleted_ && r.product_id_ && (util.productIds.includes(r.product_id_) || r.bom_entry_id_ === util.bomEntry.id_)
1048
+ );
1049
+ if (!rows.length) continue;
1050
+ util.validateSubstitute(arr);
1051
+ util.validateLotMixing(arr);
1052
+ const orderIndex = this.resolveGroupOrderIndexByUtil(util, arr);
1053
+ const groupNo = orderIndex >= 0 ? orderIndex + 1 : void 0;
1054
+ await util.validateGroupQty(arr, this.enableSequenceLoading, groupNo);
992
1055
  }
993
1056
  }
994
1057
  /**
@@ -1891,23 +1954,42 @@ class MaterialConsumeTableController {
1891
1954
  // }
1892
1955
  // }
1893
1956
  /**
1894
- * 生成校验清单格式的报错
1895
- * @param message
1896
- * @return {*}
1957
+ * 生成校验清单格式的报错(仅行级,挂对应单元格)
1897
1958
  */
1898
- calcErrorObj(message2) {
1959
+ calcErrorObj(err) {
1960
+ const targetFieldId = err.targetFieldId;
1961
+ const rowIndex = Math.max(this.actualTableData.indexOf(err.row), 0);
1962
+ const modelKey = this.widget.props.modelKey;
1963
+ const showFieldName = this.formModelController?.findField(modelKey, targetFieldId)?.name || targetFieldId;
1899
1964
  return {
1900
- field: this.widget.props.field + "_0_product_id_",
1965
+ field: `${this.widget.props.field}_${rowIndex}_${targetFieldId}`,
1901
1966
  message: JSON.stringify({
1902
- message: message2,
1903
- showFieldName: $t("sys.model.product"),
1904
- showModelKey: this.widget.props.modelKey,
1967
+ message: err.message,
1968
+ showFieldName,
1969
+ showModelKey: modelKey,
1905
1970
  showModelName: this.widget.props.tableTitle,
1906
1971
  subFieldKey: this.widget.props.field,
1907
- targetFieldId: "product_id_"
1972
+ targetFieldId
1908
1973
  })
1909
1974
  };
1910
1975
  }
1976
+ /**
1977
+ * 当前行 BOM 行级批注:待删除的 key + 重算后的错误
1978
+ * 改物料/批次会清批次数量有效期,四个字段一起替换;改数量/有效期只动自身
1979
+ */
1980
+ getRowCommentPatch(row, field) {
1981
+ const rowIndex = Math.max(this.actualTableData.indexOf(row), 0);
1982
+ const fieldKeys = field === "qty_" || field === "expiration_date_" ? [field] : ["product_id_", "material_no_", "qty_", "expiration_date_"];
1983
+ const keys = fieldKeys.map((f) => `${this.widget.props.field}_${rowIndex}_${f}`);
1984
+ const keySet = new Set(keys);
1985
+ const add = {};
1986
+ this.bomEntriesValidator.getRowFieldErrors(row).forEach((e) => {
1987
+ const obj = this.calcErrorObj(e);
1988
+ if (!keySet.has(obj.field)) return;
1989
+ (add[obj.field] ??= []).push(obj);
1990
+ });
1991
+ return { keys, add };
1992
+ }
1911
1993
  /**
1912
1994
  * 是否是单独一行空数据
1913
1995
  */
@@ -1921,23 +2003,33 @@ class MaterialConsumeTableController {
1921
2003
  return false;
1922
2004
  }
1923
2005
  /**
1924
- * 提交的时候的校验
2006
+ * 提交校验:先行级打标,全部通过后再组级 fail-fast toast
1925
2007
  */
1926
2008
  async submitValidate() {
1927
2009
  if (this.isOnlyEmptyRow()) {
1928
- return;
2010
+ return { isValid: true };
2011
+ }
2012
+ if (this.mcPattern === MaterialConsumptionPatternEnum.RECORD && !this.tmplBom.personal_bom_enabled_) {
2013
+ return { isValid: true };
2014
+ }
2015
+ const rowErrors = this.bomEntriesValidator.collectRowErrors(this.actualTableData);
2016
+ if (rowErrors.length) {
2017
+ const fields = {};
2018
+ rowErrors.forEach((e) => {
2019
+ const obj = this.calcErrorObj(e);
2020
+ (fields[obj.field] ??= []).push(obj);
2021
+ });
2022
+ return { isValid: false, fields };
1929
2023
  }
1930
- let errorObj;
1931
2024
  try {
1932
- if (this.mcPattern !== MaterialConsumptionPatternEnum.RECORD && !this.tmplBom.personal_bom_enabled_) {
1933
- await this.bomEntriesValidator.validateAllRows(this.actualTableData);
1934
- }
2025
+ await this.bomEntriesValidator.assertGroupRules(this.actualTableData);
1935
2026
  } catch (e) {
1936
2027
  if (e?.message) {
1937
- errorObj = this.calcErrorObj(e.message);
2028
+ this.error(e.message);
1938
2029
  }
2030
+ return { isValid: false };
1939
2031
  }
1940
- return errorObj;
2032
+ return { isValid: true };
1941
2033
  }
1942
2034
  /**
1943
2035
  * 是否有正在编辑的行
@@ -4104,6 +4196,11 @@ const MaterialConsumeTable = /* @__PURE__ */ defineComponent({
4104
4196
  row.tempDeleted = true;
4105
4197
  }
4106
4198
  };
4199
+ const clearMcValidatorComments = () => {
4200
+ if (!dataRelationShip) return;
4201
+ dataRelationShip.mcValidatorMessageMap = {};
4202
+ dataRelationShip.mcValidatorLocationList = [];
4203
+ };
4107
4204
  const deleteRowAt = (row, index) => {
4108
4205
  recordSubtableRowDelete(dataRelationShip, field, row);
4109
4206
  deleteSubtableRow(field, index);
@@ -4123,6 +4220,7 @@ const MaterialConsumeTable = /* @__PURE__ */ defineComponent({
4123
4220
  deleteRowAt(rowData, realIndex);
4124
4221
  }
4125
4222
  modelValue.value = relocateDeletedRowsToEnd(modelValue.value.filter((d) => !d.tempDeleted));
4223
+ clearMcValidatorComments();
4126
4224
  };
4127
4225
  const createDefaultRows = (rowNum, quickFillDatas, patch) => {
4128
4226
  return Array.from({
@@ -4147,6 +4245,7 @@ const MaterialConsumeTable = /* @__PURE__ */ defineComponent({
4147
4245
  modelValue.value = relocateDeletedRowsToEnd(modelValue.value);
4148
4246
  recordSubtableRowAdd(dataRelationShip, field, rows);
4149
4247
  updateCalcCallback?.(dataRelationShip?.uniqueId);
4248
+ clearMcValidatorComments();
4150
4249
  };
4151
4250
  const resolveRealIndex = (index) => dataInfo.value.visibleToRealIndexMap[props.start + index];
4152
4251
  const handleAddRowForGroup = ({
@@ -60793,7 +60793,10 @@ function setSelectValidatorId(event, basicInfoItem) {
60793
60793
  Array.from(scope.querySelectorAll(".validator-icon")).map((el2) => el2.dataset.ann).filter((id) => !!id)
60794
60794
  )
60795
60795
  ];
60796
- const validateList = ids.map((id) => basicInfoItem.validatorMessageMap?.[id]).filter(Boolean);
60796
+ const validateList = ids.map((id) => [
60797
+ ...basicInfoItem.validatorMessageMap?.[id] ?? [],
60798
+ ...basicInfoItem.mcValidatorMessageMap?.[id] ?? []
60799
+ ]).filter((list) => list.length);
60797
60800
  const flattenedErrors = validateList.flatMap(
60798
60801
  (validates) => validates.map(({ field: _field, message: message2 }) => JSON.parse(message2))
60799
60802
  );
@@ -65566,13 +65569,28 @@ function useNocodeFormWidget(props, emit) {
65566
65569
  }
65567
65570
  async function handleEvent(eventType, callback, valueData, optionDetail) {
65568
65571
  await nextTick$1();
65572
+ const patchMcRowComments = (field2) => {
65573
+ if (!MCTableC || !dataRelationShip?.mcValidatorLocationList?.length || !["product_id_", "material_no_", "qty_", "expiration_date_"].includes(field2)) {
65574
+ return;
65575
+ }
65576
+ const { keys: keys2, add } = MCTableC.getRowCommentPatch(props.formData, field2);
65577
+ const next = { ...dataRelationShip.mcValidatorMessageMap ?? {} };
65578
+ keys2.forEach((k) => delete next[k]);
65579
+ Object.assign(next, add);
65580
+ dataRelationShip.mcValidatorMessageMap = next;
65581
+ dataRelationShip.mcValidatorLocationList = Object.keys(next);
65582
+ };
65569
65583
  if (MCTableC && eventType === "onChange") {
65570
- MCTableC.handleChange({
65584
+ await MCTableC.handleChange({
65571
65585
  field: targetFieldId,
65572
65586
  row: props.formData,
65573
65587
  value: value.value,
65574
65588
  option: valueData
65575
65589
  });
65590
+ patchMcRowComments(targetFieldId);
65591
+ }
65592
+ if (MCTableC && eventType === "onBlur") {
65593
+ patchMcRowComments(targetFieldId);
65576
65594
  }
65577
65595
  if (subTableCore && eventType === "onChange") {
65578
65596
  subTableCore.handleChange({
@@ -65647,6 +65665,7 @@ function useNocodeFormWidget(props, emit) {
65647
65665
  }
65648
65666
  const annList = dataRelationShip?.annCellLocationList;
65649
65667
  const validatorList = dataRelationShip?.validatorLocationList;
65668
+ const mcValidatorList = dataRelationShip?.mcValidatorLocationList;
65650
65669
  const colIdx = resolveSubtableColIdx();
65651
65670
  const matchedAnnLoc = props.subtableFieldId ? resolveAnnotationFieldLocation({
65652
65671
  annList,
@@ -65657,7 +65676,7 @@ function useNocodeFormWidget(props, emit) {
65657
65676
  }) : dataRelationShip?.annSwitchStatus && Array.isArray(annList) && fieldId && annList.includes(fieldId) ? fieldId : void 0;
65658
65677
  const annIncluded = !!dataRelationShip?.annSwitchStatus && !!matchedAnnLoc;
65659
65678
  const isSelected = isAnnLocationSelected(dataRelationShip?.annSelectId, matchedAnnLoc);
65660
- const isInvalid = dataRelationShip?.platformType !== PlatformEnum.INTEGRATION_PAAS_DP && !dataRelationShip?.annSwitchStatus && Array.isArray(validatorList) && !!fieldId && validatorList.includes(fieldId);
65679
+ const isInvalid = dataRelationShip?.platformType !== PlatformEnum.INTEGRATION_PAAS_DP && !dataRelationShip?.annSwitchStatus && !!fieldId && (Array.isArray(validatorList) && validatorList.includes(fieldId) || Array.isArray(mcValidatorList) && mcValidatorList.includes(fieldId));
65661
65680
  const annClassList = [];
65662
65681
  if (annIncluded && matchedAnnLoc) {
65663
65682
  annClassList.push(matchedAnnLoc, "annotation-mark");
@@ -66338,27 +66357,27 @@ var loadModule = (cmpMeta, hostRef, hmrVersionId) => {
66338
66357
  case "revo-grid":
66339
66358
  return import(
66340
66359
  /* webpackMode: "lazy" */
66341
- "./revo-grid.entry-DaQhq21b.js"
66360
+ "./revo-grid.entry-CdGl1o68.js"
66342
66361
  ).then(processMod, consoleError);
66343
66362
  case "revogr-filter-panel":
66344
66363
  return import(
66345
66364
  /* webpackMode: "lazy" */
66346
- "./revogr-filter-panel.entry-N7r1TehE.js"
66365
+ "./revogr-filter-panel.entry-DJFcQ4PR.js"
66347
66366
  ).then(processMod, consoleError);
66348
66367
  case "revogr-attribution_7":
66349
66368
  return import(
66350
66369
  /* webpackMode: "lazy" */
66351
- "./revogr-attribution_7.entry-8lq6FIyD.js"
66370
+ "./revogr-attribution_7.entry-DTBowB-3.js"
66352
66371
  ).then(processMod, consoleError);
66353
66372
  case "revogr-clipboard_3":
66354
66373
  return import(
66355
66374
  /* webpackMode: "lazy" */
66356
- "./revogr-clipboard_3.entry-JKz3q4Hr.js"
66375
+ "./revogr-clipboard_3.entry-CHaJF7Fr.js"
66357
66376
  ).then(processMod, consoleError);
66358
66377
  case "revogr-data_4":
66359
66378
  return import(
66360
66379
  /* webpackMode: "lazy" */
66361
- "./revogr-data_4.entry-dKqISKJJ.js"
66380
+ "./revogr-data_4.entry-BOlY6RhY.js"
66362
66381
  ).then(processMod, consoleError);
66363
66382
  }
66364
66383
  }
@@ -1,4 +1,4 @@
1
- import { e6 as EDIT_INPUT_WR, e7 as keyValues, d_ as codesLetter } from "./dynamic-table-action.vue_vue_type_style_index_0_scoped_53d7e66c_lang-CJWFZ-MC.js";
1
+ import { e6 as EDIT_INPUT_WR, e7 as keyValues, d_ as codesLetter } from "./dynamic-table-action.vue_vue_type_style_index_0_scoped_53d7e66c_lang-pfvEPOi4.js";
2
2
  function isClear(code) {
3
3
  return codesLetter.BACKSPACE === code || codesLetter.DELETE === code;
4
4
  }
@@ -1,6 +1,6 @@
1
1
  import { defineComponent, computed, openBlock, createElementBlock, normalizeClass, toDisplayString, createCommentVNode, createVNode, unref, normalizeStyle, withCtx, Fragment, renderList, createBlock } from "vue";
2
- import { C as CellWidgetRenderComp, S as SelectEx, a as CellWidgetDesign } from "./index-YKd9P21f.js";
3
- import { F as FIELD_TYPE, _ as _export_sfc } from "./dynamic-table-action.vue_vue_type_style_index_0_scoped_53d7e66c_lang-CJWFZ-MC.js";
2
+ import { C as CellWidgetRenderComp, S as SelectEx, a as CellWidgetDesign } from "./index-NwgCso5Y.js";
3
+ import { F as FIELD_TYPE, _ as _export_sfc } from "./dynamic-table-action.vue_vue_type_style_index_0_scoped_53d7e66c_lang-pfvEPOi4.js";
4
4
  import { isNil } from "lodash-es";
5
5
  const _hoisted_1 = {
6
6
  key: 0,
@@ -1,9 +1,9 @@
1
1
  import { defineComponent, reactive, ref, onMounted, resolveComponent, openBlock, createElementBlock, createVNode, withCtx, createElementVNode, createTextVNode, toDisplayString, Fragment, createBlock, createCommentVNode, computed, toRaw, normalizeClass, unref } from "vue";
2
- import { i as useSpreadSheet, I as Icon, b as FormItem, k as draggableComponent } from "./index-YKd9P21f.js";
3
- import { $ as buildUUID, _ as _export_sfc, F as FIELD_TYPE } from "./dynamic-table-action.vue_vue_type_style_index_0_scoped_53d7e66c_lang-CJWFZ-MC.js";
2
+ import { i as useSpreadSheet, I as Icon, b as FormItem, k as draggableComponent } from "./index-NwgCso5Y.js";
3
+ import { $ as buildUUID, _ as _export_sfc, F as FIELD_TYPE } from "./dynamic-table-action.vue_vue_type_style_index_0_scoped_53d7e66c_lang-pfvEPOi4.js";
4
4
  import { clone, cloneDeep, differenceBy } from "lodash-es";
5
5
  import { useModal } from "@gct-paas/core";
6
- import { A as AttachFieldEditor } from "./attach-fields-editor-DESDkODo.js";
6
+ import { A as AttachFieldEditor } from "./attach-fields-editor-BD9EqEpy.js";
7
7
  import { u as useNamespace } from "./use-namespace-BxkK4ofX.js";
8
8
  const _hoisted_1$3 = { class: "enum-option-modal" };
9
9
  const _hoisted_2$3 = { class: "enum-option-modal__footer" };
@@ -1,7 +1,7 @@
1
1
  import { defineComponent, computed, openBlock, createElementBlock, Fragment, createVNode, createBlock, createCommentVNode } from "vue";
2
- import { B as BaseFontEditor } from "./base-font-editor-DKfvfFLW.js";
3
- import { _ as _sfc_main$1, a as _sfc_main$2 } from "./select-render-type-editor.vue_vue_type_script_setup_true_lang-BmK6eR2q.js";
4
- import { C as CellWidgetRenderComp } from "./index-YKd9P21f.js";
2
+ import { B as BaseFontEditor } from "./base-font-editor-J0236vKt.js";
3
+ import { _ as _sfc_main$1, a as _sfc_main$2 } from "./select-render-type-editor.vue_vue_type_script_setup_true_lang-BO5Cziz6.js";
4
+ import { C as CellWidgetRenderComp } from "./index-NwgCso5Y.js";
5
5
  const DEFAULT_LETTER_SPACE = 8;
6
6
  const DEFAULT_OPTION_GAP = 12;
7
7
  const _sfc_main = /* @__PURE__ */ defineComponent({