From 7c6c6fe112e0718a954bfbe4cd258c7e08953f83 Mon Sep 17 00:00:00 2001 From: zhangminghua Date: Mon, 5 Dec 2022 14:59:02 +0800 Subject: [PATCH] =?UTF-8?q?(*)=E5=BC=80=E7=A5=A8=E6=98=8E=E7=BB=86?= =?UTF-8?q?=E5=AF=BC=E5=85=A5?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../src/sections/business/constants/index.js | 2 +- .../performanceReport/contractDetails.jsx | 2 +- .../importInvoicingDetailsModal.js | 84 +++++++++++++++++-- .../performanceReport/invoicingDetails.jsx | 5 +- 4 files changed, 83 insertions(+), 10 deletions(-) diff --git a/web/client/src/sections/business/constants/index.js b/web/client/src/sections/business/constants/index.js index c0fd58b..43e8e2c 100644 --- a/web/client/src/sections/business/constants/index.js +++ b/web/client/src/sections/business/constants/index.js @@ -47,7 +47,7 @@ export const contractDetailsColumnKeys = { industry: '行业', source: '信息来源', cusProvince: '客户省份', - cusArea: '项目所在地', + itemArea: '项目所在地', text: '备注', } diff --git a/web/client/src/sections/business/containers/performanceReport/contractDetails.jsx b/web/client/src/sections/business/containers/performanceReport/contractDetails.jsx index 3556a56..bb47784 100644 --- a/web/client/src/sections/business/containers/performanceReport/contractDetails.jsx +++ b/web/client/src/sections/business/containers/performanceReport/contractDetails.jsx @@ -35,7 +35,7 @@ const ContractDetails = (props) => { columns.push({ title: columnKeys[key], dataIndex: key, key: key, render: (text, record) => text === 0 ? text : text ? text : '-', - width: 32 + columnKeys[key].length * 32 + width: 60 + columnKeys[key].length * 16 }); break; } diff --git a/web/client/src/sections/business/containers/performanceReport/importInvoicingDetailsModal.js b/web/client/src/sections/business/containers/performanceReport/importInvoicingDetailsModal.js index cba870b..a571284 100644 --- a/web/client/src/sections/business/containers/performanceReport/importInvoicingDetailsModal.js +++ b/web/client/src/sections/business/containers/performanceReport/importInvoicingDetailsModal.js @@ -4,22 +4,35 @@ import { connect } from 'react-redux'; import { Modal, Form, Button, Notification } from '@douyinfe/semi-ui'; import { IconUpload } from '@douyinfe/semi-icons'; import XLSX from 'xlsx'; +import moment from 'moment'; import { invoicingDetailsColumnKeys } from '../../constants/index'; +const ColumnDateKey = ['invoiceDate']; +const ColumnDateName = ['开票日期']; //下载模板和上传文件读取 const ImportInvoicingDetailsModal = props => { const { dispatch, actions, onCancel } = props; - const { humanAffairs } = actions; + const { businessManagement } = actions; const [msg, setMsg] = useState(''); const [loading, setLoading] = useState(''); const [postData, setPostData] = useState([]); + const [uploadAble, setUploadAble] = useState(false); + const [allNumbers, setAllNumbers] = useState([]); //初始化 useEffect(() => { + //查询明细表已存在编号数据接口通用 + dispatch(businessManagement.getReceivedNumbers({ tableModel: 'InvoiceDetail' })).then(r => { + if (r.success) { + setUploadAble(true); + setAllNumbers(r.payload.data); + } + }) }, []); const confirm = () => { if (postData.length) { setLoading(true) - dispatch(humanAffairs.addSalesMemberBulk(postData)).then(res => { + //导入明细接口通用 + dispatch(businessManagement.importBackDetails(postData, { tableModel: 'InvoiceDetail' })).then(res => { if (res.success) { onCancel() } @@ -94,9 +107,29 @@ const ImportInvoicingDetailsModal = props => { }) } + const judgeNullTime = (v) => { + //注意的点:xlsx将excel中的时间内容解析后,会小一天 + //如2020/8/1,xlsx会解析成 Fri Jul 31 2020 23:59:17 GMT+0800 小了43秒 + let a = new Date(v); + a.setTime(a.getTime() + 43 * 1000); + return v ? a : null; + } - const judgeNull = (value) => { - return value ? String(value).trim().replace(/\s*/g, "") : null; + const judgeTimeValid = (time) => { + let valid = true; + if (!time) { + return valid;//可以不填 + } + const ymd = /^((19|20)[0-9]{2})[\/\-]((0[1-9])|(1[0-2]))[\/\-]((0[1-9])|((1|2)[0-9])|(3[0-1]))$/;//年月日 + if (time instanceof Date) { + let timeStr = moment(time).format('YYYY/MM/DD'); + if (!ymd.test(timeStr)) { + valid = false; + } + } else { + valid = false; + } + return valid; } return ( @@ -137,12 +170,51 @@ const ImportInvoicingDetailsModal = props => { return } let postData = []; + let yearPattern = /^(19|20)\d{2}$/;//1900-2099年 + let zzsPattern = /^[+]{0,1}(\d+)$/;//正整数 for (let i = 0; i < res.length; i++) { let d = res[i]; let obj = {}; Object.keys(invoicingDetailsColumnKeys).map(key => { - obj[key] = d[invoicingDetailsColumnKeys[key]] || ''; + //日期验证“开票日期” + if (ColumnDateKey.indexOf(key) != -1) {//两个时间 + obj[key] = judgeNullTime(d[invoicingDetailsColumnKeys[key]]); + } else { + obj[key] = d[invoicingDetailsColumnKeys[key]] || null; + } }) + //年度 序号 编号必填 + if (!obj.year || !obj.serialNo || !obj.number) { + error(`第${i + 2}行【年度】、【序号】、【编号】存在空值,请填写`) + return + } + //年度 + if (obj.year && !yearPattern.test(obj.year)) { + error(`第${i + 2}行【年度】填写错误`) + return + } + //序号 正整数 + if (obj.serialNo && !zzsPattern.test(obj.serialNo)) { + error(`第${i + 2}行【序号】填写错误,需要为非负整数`) + return + } + let exist = allNumbers.find(m => m.number == obj.number);//数据库中 已有该编号 + if (exist) { + error(`第${i + 2}行的【编号】在系统中已存在`) + return + } + if (postData.some(p => p.number == obj.number)) {//编号 唯一 + error(`第${i + 2}行【编号】重复,请更改后重新上传`) + return + } + + for (let k = 0; k < ColumnDateKey.length; k++) { + let cValid = judgeTimeValid(obj[ColumnDateKey[k]]); + if (!cValid) { + error(`第${i + 2}行【${ColumnDateName[k]}】错误,请填写yyyy/mm/dd格式`) + return + } + } postData.push(obj); } setPostData(postData) @@ -151,7 +223,7 @@ const ImportInvoicingDetailsModal = props => { onSuccess({ message: msg }) }) }}> - diff --git a/web/client/src/sections/business/containers/performanceReport/invoicingDetails.jsx b/web/client/src/sections/business/containers/performanceReport/invoicingDetails.jsx index 9a76a9b..717b0e6 100644 --- a/web/client/src/sections/business/containers/performanceReport/invoicingDetails.jsx +++ b/web/client/src/sections/business/containers/performanceReport/invoicingDetails.jsx @@ -34,8 +34,8 @@ const InvoicingDetails = (props) => { default: columns.push({ title: columnKeys[key], dataIndex: key, key: key, - render: (text, record) => text === 0 ? text : text ? text : '—', - width: 32 + columnKeys[key].length * 16 + render: (text, record) => text === 0 ? text : text ? text : '-', + width: 60 + columnKeys[key].length * 16 }); break; } @@ -216,6 +216,7 @@ const InvoicingDetails = (props) => { importModalV ? { setImportModalV(false); + getInvoicingDetailData(); }} /> : '' } {