diff --git a/code/zcdev/zcgj-zcdev-zcdev-fs/src/main/java/zcgj/zcdev/zcdev/fs/plugin/form/SalaryPlugin.java b/code/zcdev/zcgj-zcdev-zcdev-fs/src/main/java/zcgj/zcdev/zcdev/fs/plugin/form/SalaryPlugin.java new file mode 100644 index 0000000..0edbe51 --- /dev/null +++ b/code/zcdev/zcgj-zcdev-zcdev-fs/src/main/java/zcgj/zcdev/zcdev/fs/plugin/form/SalaryPlugin.java @@ -0,0 +1,388 @@ +package zcgj.zcdev.zcdev.fs.plugin.form; + +import com.alibaba.fastjson.JSONArray; +import com.alibaba.fastjson.JSONObject; +import kd.bos.bill.AbstractBillPlugIn; +import kd.bos.bill.BillShowParameter; +import kd.bos.bill.OperationStatus; +import kd.bos.cache.CacheFactory; +import kd.bos.cache.tempfile.TempFileCacheDownloadable; +import kd.bos.dataentity.OperateOption; +import kd.bos.dataentity.entity.DynamicObject; +import kd.bos.dataentity.entity.DynamicObjectCollection; +import kd.bos.dataentity.utils.StringUtils; +import kd.bos.db.DB; +import kd.bos.db.DBRoute; +import kd.bos.db.ResultSetHandler; +import kd.bos.entity.datamodel.events.ChangeData; +import kd.bos.entity.datamodel.events.PropertyChangedArgs; +import kd.bos.entity.operate.result.OperationResult; +import kd.bos.fileservice.FileService; +import kd.bos.fileservice.FileServiceFactory; +import kd.bos.form.control.AttachmentPanel; +import kd.bos.form.control.Control; +import kd.bos.form.control.EntryGrid; +import kd.bos.form.control.Toolbar; +import kd.bos.form.control.events.ClickListener; +import kd.bos.form.control.events.UploadEvent; +import kd.bos.form.control.events.UploadListener; +import kd.bos.form.events.AfterDoOperationEventArgs; +import kd.bos.form.events.ClientCallBackEvent; +import kd.bos.id.ID; +import kd.bos.logging.Log; +import kd.bos.logging.LogFactory; +import kd.bos.servicehelper.AttachmentServiceHelper; +import kd.bos.servicehelper.operation.OperationServiceHelper; +import kd.bos.servicehelper.operation.SaveServiceHelper; +import kd.sdk.plugin.Plugin; +import org.apache.poi.ss.usermodel.*; + +import java.io.IOException; +import java.io.InputStream; +import java.math.BigDecimal; +import java.net.URL; +import java.nio.charset.StandardCharsets; +import java.security.MessageDigest; +import java.util.*; + +/** + * 人员工资附件excel读取,导入插件 + */ +public class SalaryPlugin extends AbstractBillPlugIn implements Plugin, UploadListener { + private static final Log log = LogFactory.getLog(SalaryPlugin.class); + + private static final String[] COLUMNKEYA = new String[]{"zcgj_name","zcgj_number","zcgj_personno","zcgj_persontype","zcgj_cbstype" ,"zcgj_yingfa" ,"zcgj_shebao" ,"zcgj_gongjijin" ,"zcgj_nianjin" ,"zcgj_geshui" ,"zcgj_shifa","zcgj_remark"}; + + private static final Set storSet = new HashSet(); + static { + storSet.add("zcgj_yingfa"); + storSet.add("zcgj_shebao"); + storSet.add("zcgj_gongjijin"); + storSet.add("zcgj_nianjin"); + storSet.add("zcgj_geshui"); + storSet.add("zcgj_shifa"); + } + + public void registerListener(EventObject e) { + super.registerListener(e); + AttachmentPanel toolbar = this.getControl("attachmentpanel"); + toolbar.addUploadListener(this); + } + + @Override + public void afterUpload(UploadEvent evt) { + UploadListener.super.afterUpload(evt); + OperateOption option= OperateOption.create(); + Object[] urls = evt.getUrls(); + String url = (String)((Map)urls[0]).get("url"); + OperationResult result = OperationServiceHelper.executeOperate("save", "zcgj_salary", new DynamicObject[]{ this.getModel().getDataEntity(true)}, option); + loadTextFileString(url); + sumData(); + this.getView().addClientCallBack("auto_save",0);//附件上传后自动保存 + } + + @Override + public void clientCallBack(ClientCallBackEvent e) { + super.clientCallBack(e); + if(e.getName().equals("auto_save")) { + AttachmentPanel attachmentPanel = getControl("attachmentpanel"); + List> data = attachmentPanel.getAttachmentData(); + if(data !=null && !data.isEmpty()) { + this.getView().invokeOperation("save"); + this.getView().invokeOperation("refresh"); + } + } + } + + @Override + public void afterRemove(UploadEvent evt) { + UploadListener.super.afterRemove(evt); + this.getView().invokeOperation("save"); + this.getExcelData(); + sumData(); + this.getView().invokeOperation("refresh"); + } + + /** + * 从临时文件缓存中获取文件,转为字符流导入 + */ + private void loadTextFileString(String fileUrl){ + + long billId = this.getModel().getDataEntity().getLong("id"); + + TempFileCacheDownloadable downLoad = (TempFileCacheDownloadable) CacheFactory.getCommonCacheFactory().getTempFileCache(); + + InputStream inStream = null; + try { + String[] queryParams = new URL(fileUrl).getQuery().split("&"); + Map downloadFileParams = new HashMap<>(); + for (String queryParam : queryParams) { + String[] p = queryParam.split("="); + downloadFileParams.put(p[0], p[1]); + } + TempFileCacheDownloadable.Content content = downLoad.get(downloadFileParams.get("configKey"), downloadFileParams.get("id")); + inStream = content.getInputStream(); + + //自动识别 XLS / XLSX,无需自己判断格式 + Workbook workbook = WorkbookFactory.create(inStream); + //getSheetJsonArray,请保持不变 + JSONArray sheetJsonArray = getSheetJsonArray( + stringArrayToMd5(COLUMNKEYA), + workbook, + 0 + ); + List params = new ArrayList<>(); + for (Object data : sheetJsonArray) { + System.out.println(); + List insertData = new ArrayList<>(); + long id = ID.genLongId(); + insertData.add(billId);//fid + insertData.add(id);//fentryid + for (int i=0;i<12;i++){ + String columnKey = ((JSONObject) ((JSONArray) data).get(i)).getString("columnKey"); + if (storSet.contains(columnKey)) { + insertData.add( ((JSONObject) ((JSONArray) data).get(i)).getBigDecimal("value")); + }else{ + insertData.add( ((JSONObject) ((JSONArray) data).get(i)).getString("value")); + } + } + params.add(insertData.toArray()); + } + DBRoute dbr = DBRoute.of("fi"); + if(!params.isEmpty()){ + String sql = "insert into tk_zcgj_salaryentry " + + "(fid,fentryid," + + "fk_zcgj_name,fk_zcgj_number,fk_zcgj_personno,fk_zcgj_persontype,fk_zcgj_cbstype,fk_zcgj_yingfa," + + "fk_zcgj_shebao,fk_zcgj_gongjijin,fk_zcgj_nianjin,fk_zcgj_geshui,fk_zcgj_shifa,fk_zcgj_remark) " + + "values(?,?,?,?,?,?,?,?,?,?,?,?,?,?)"; + DB.executeBatch(dbr,sql, params); + } + }catch(Exception e){ + log.info("SalaryPlugin:"+e.getMessage()); + }finally{ + try { + if (inStream != null){ + inStream.close(); + } + } catch (IOException e) { + log.info("SalaryPlugin:"+e.getMessage()); + } + } + } + + + /** + * 从附件面板中获取附件导入 + */ + public void getExcelData(){ + DBRoute dbr = DBRoute.of("fi"); + + BillShowParameter bsp=(BillShowParameter)this.getView().getFormShowParameter(); + long billId = this.getModel().getDataEntity().getLong("id"); + if(billId != 0){ + List paramsdel = new ArrayList<>(); + paramsdel.add(new Object[]{billId}); + String delsql = "delete from tk_zcgj_salaryentry where fid = ?"; + int[] ints = DB.executeBatch(dbr, delsql, paramsdel); + + String[] COLUMNKEYA = new String[]{"zcgj_name","zcgj_number","zcgj_personno","zcgj_persontype","zcgj_cbstype" ,"zcgj_yingfa" ,"zcgj_shebao" ,"zcgj_gongjijin" ,"zcgj_nianjin" ,"zcgj_geshui" ,"zcgj_shifa","zcgj_remark"}; + List> attachments = AttachmentServiceHelper.getAttachments("zcgj_salary",billId, "attachmentpanel"); + for (Map attachment : attachments) { + String url = (String)attachment.get("relativeUrl"); + // JSONArray objects = POIHelperFast.newInputExcel(url, POIHelperFast.stringArrayToHash(COLUMNKEYA)); + FileService service = FileServiceFactory.getAttachmentFileService(); + InputStream in = service.getInputStream(url); + try { + //自动识别 XLS / XLSX,无需自己判断格式 + Workbook workbook = WorkbookFactory.create(in); + //getSheetJsonArray,请保持不变 + JSONArray sheetJsonArray = getSheetJsonArray( + stringArrayToMd5(COLUMNKEYA), + workbook, + 0 + ); + List params = new ArrayList<>(); + for (Object data : sheetJsonArray) { + System.out.println(); + List insertData = new ArrayList<>(); + long id = ID.genLongId(); + insertData.add(billId);//fid + insertData.add(id);//fentryid + for (int i=0;i<12;i++){ + String columnKey = ((JSONObject) ((JSONArray) data).get(i)).getString("columnKey"); + if (storSet.contains(columnKey)) { + insertData.add( ((JSONObject) ((JSONArray) data).get(i)).getBigDecimal("value")); + }else{ + insertData.add( ((JSONObject) ((JSONArray) data).get(i)).getString("value")); + } + } + params.add(insertData.toArray()); + } + + if(!params.isEmpty()){ + String sql = "insert into tk_zcgj_salaryentry " + + "(fid,fentryid," + + "fk_zcgj_name,fk_zcgj_number,fk_zcgj_personno,fk_zcgj_persontype,fk_zcgj_cbstype,fk_zcgj_yingfa," + + "fk_zcgj_shebao,fk_zcgj_gongjijin,fk_zcgj_nianjin,fk_zcgj_geshui,fk_zcgj_shifa,fk_zcgj_remark) " + + "values(?,?,?,?,?,?,?,?,?,?,?,?,?,?)"; + DB.executeBatch(dbr,sql, params); + } + } catch (IOException ee) { + ee.printStackTrace(); + } + } + } + + } + + public void sumData(){ + DBRoute dbr = DBRoute.of("fi"); + long billId = this.getModel().getDataEntity().getLong("id"); + if(billId != 0){ + String sql = "select fk_zcgj_persontype persontype,fk_zcgj_cbstype cbstype,sum(fk_zcgj_yingfa) yingfa,"+ + " sum(fk_zcgj_shebao) shebao,sum(fk_zcgj_gongjijin) gongjijin,sum(fk_zcgj_nianjin) nianjin," + + "sum(fk_zcgj_geshui) geshui,sum(fk_zcgj_shifa) shifa" + + " from tk_zcgj_salaryentry"+ + " where fid = "+billId+ + " group by fk_zcgj_persontype,fk_zcgj_cbstype"; + List> resultData = DB.query(dbr, sql,resultSet -> { + List> rows = new ArrayList<>(); + while (resultSet.next()) { + Map row = new HashMap<>(); + row.put("persontype", resultSet.getString("persontype")); + row.put("cbstype", resultSet.getString("cbstype")); + row.put("yingfa", resultSet.getBigDecimal("yingfa")); + row.put("shebao", resultSet.getBigDecimal("shebao")); + row.put("gongjijin", resultSet.getBigDecimal("gongjijin")); + row.put("nianjin", resultSet.getBigDecimal("nianjin")); + row.put("geshui", resultSet.getBigDecimal("geshui")); + row.put("shifa", resultSet.getBigDecimal("shifa")); + rows.add(row); + } + + return rows; + }); + + DynamicObjectCollection dynamicObjectCollection = this.getModel().getDataEntity(true).getDynamicObjectCollection("zcgj_entryentity"); + dynamicObjectCollection.clear(); + if(resultData != null){ + for (Map resultDatum : resultData) { + DynamicObject dynamicObject = dynamicObjectCollection.addNew(); + dynamicObject.set("zcgj_persontype2", resultDatum.get("persontype")); + dynamicObject.set("zcgj_cbstype2", resultDatum.get("cbstype")); + dynamicObject.set("zcgj_yingfa2", resultDatum.get("yingfa")); + dynamicObject.set("zcgj_shebao2", resultDatum.get("shebao")); + dynamicObject.set("zcgj_gongjijin2", resultDatum.get("gongjijin")); + dynamicObject.set("zcgj_nianjin2", resultDatum.get("nianjin")); + dynamicObject.set("zcgj_geshui2", resultDatum.get("geshui")); + dynamicObject.set("zcgj_shifa2", resultDatum.get("shifa")); + } + } + this.getView().updateView("zcgj_entryentity"); + } + + + + } + + + private static JSONArray getSheetJsonArray(String columnHashCode, Workbook wb, int index) { + + JSONArray jsonArray = new JSONArray(); + Sheet sheet = wb.getSheetAt(index); + int rowNum = sheet.getLastRowNum(); + + Row columnKeyRow = sheet.getRow(1); + Row headerRow = sheet.getRow(2); + Row columnKeyHashRow = sheet.getRow(1); + + if (columnKeyHashRow != null && columnKeyHashRow.getCell(0) != null) { + + List excelData = new ArrayList(); + for (int i = 0; i < 12; i++) { + columnKeyHashRow.getCell(i).setCellType(CellType.STRING); + excelData.add(columnKeyHashRow.getCell(i).getStringCellValue()); + } + //columnKeyHashRow.getCell(0).setCellType(CellType.STRING); + String key = stringArrayToMd5(excelData.toArray(new String[0])); + //String columnKeyHashCellValue = columnKeyHashRow.getCell(0).getStringCellValue(); + if (!StringUtils.equals(key, columnHashCode)) { + return jsonArray; + } + + int columnNum = columnKeyRow.getLastCellNum(); + + // 计算真正的列数 + for (int i = 0; i < columnNum; ++i) { + Cell cell = headerRow.getCell(i); + if (cell == null) break; + cell.setCellType(CellType.STRING); + String value = cell.getStringCellValue(); + if (org.apache.commons.lang3.StringUtils.isEmpty(value)) { + columnNum = i; + break; + } + } + + // 解析数据行 + for (int j = 3; j <= rowNum; ++j) { + JSONArray jsonRow = new JSONArray(); + boolean isBlankRow = true; + + Row irow = sheet.getRow(j); + if (irow == null) break; + + for (int i = 0; i < columnNum; ++i) { + + JSONObject jsonObject = new JSONObject(); + + // columnKey + Cell keyCell = columnKeyRow.getCell(i); + keyCell.setCellType(CellType.STRING); + + // name + Cell nameCell = headerRow.getCell(i); + nameCell.setCellType(CellType.STRING); + + jsonObject.put("columnKey", keyCell.getStringCellValue()); + jsonObject.put("name", nameCell.getStringCellValue()); + + String value = ""; + Cell cell = irow.getCell(i); + if (cell != null) { + cell.setCellType(CellType.STRING); + value = cell.getStringCellValue(); + } + + jsonObject.put("value", value); + isBlankRow = isBlankRow && org.apache.commons.lang3.StringUtils.isEmpty(value); + + jsonRow.add(jsonObject); + } + + if (isBlankRow) break; + + jsonArray.add(jsonRow); + } + } + + return jsonArray; + } + + public static String stringArrayToMd5(String[] array) { + try { + MessageDigest md = MessageDigest.getInstance("MD5"); + md.update(String.join(",", array).getBytes(StandardCharsets.UTF_8)); + byte[] digest = md.digest(); + + StringBuilder sb = new StringBuilder(); + for (byte b : digest) { + sb.append(String.format("%02x", b)); + } + return sb.toString(); + } catch (Exception e) { + throw new RuntimeException(e); + } + } + +}