机具领料导入

This commit is contained in:
hayu 2026-01-04 15:30:01 +08:00
parent 8fa6e994f0
commit f80d4148b9
6 changed files with 294 additions and 238 deletions

View File

@ -638,50 +638,58 @@ function backShowChenkStatus(){
/**
* 导入模板下载功能
*/
// function templateDownload() {
// // 1. 校验领料时间(与新增/删除逻辑保持一致,非今日不允许下载)
// if (applyDate !== today) {
// layer.alert('领料时间不是今天,不允许下载导入模板', {
// skin: 'layui-layer-molv',
// closeBtn: 0
// });
// return;
// }
//
// // 2. 构造下载请求携带必要参数taskId保证模板与当前任务关联
// var taskId = localStorage.getItem("taskId");
// var token = $("#token").val(); // 携带令牌,防止重复请求
// var downloadUrl = bonuspath + '/backstage/receiveDetails/downloadTemplate';
//
// // 3. 构造隐藏表单提交解决GET请求参数暴露/大小限制问题支持POST下载
// var $form = $("<form>").attr({
// "method": "POST",
// "action": downloadUrl,
// "target": "_blank" // 新窗口打开,不阻塞当前页面
// });
// // 添加请求参数
// $form.append($("<input>").attr({
// "type": "hidden",
// "name": "taskId",
// "value": taskId
// }));
// $form.append($("<input>").attr({
// "type": "hidden",
// "name": "token",
// "value": token
// }));
// // 插入页面并提交
// $("body").append($form);
// $form.submit();
// // 提交后移除表单
// $form.remove();
//
// // 4. 友好提示
// layer.msg('正在下载导入模板,请稍后...', {
// icon: 16,
// shade: 0.1,
// time: 1500
// });
// }
function templateDownload() {
// 1. 校验领料时间(与新增/删除逻辑保持一致,非今日不允许下载)
if (applyDate !== today) {
layer.alert('领料时间不是今天,不允许下载导入模板', {
skin: 'layui-layer-molv',
closeBtn: 0
});
return;
var params = {
}
// 2. 构造下载请求携带必要参数taskId保证模板与当前任务关联
var taskId = localStorage.getItem("taskId");
var token = $("#token").val(); // 携带令牌,防止重复请求
var downloadUrl = bonuspath + '/backstage/receiveDetails/downloadTemplate';
// 3. 构造隐藏表单提交解决GET请求参数暴露/大小限制问题支持POST下载
var $form = $("<form>").attr({
"method": "POST",
"action": downloadUrl,
"target": "_blank" // 新窗口打开,不阻塞当前页面
});
// 添加请求参数
$form.append($("<input>").attr({
"type": "hidden",
"name": "taskId",
"value": taskId
}));
$form.append($("<input>").attr({
"type": "hidden",
"name": "token",
"value": token
}));
// 插入页面并提交
$("body").append($form);
$form.submit();
// 提交后移除表单
$form.remove();
// 4. 友好提示
layer.msg('正在下载导入模板,请稍后...', {
icon: 16,
shade: 0.1,
time: 1500
});
var url = bonuspath + '/backstage/receiveDetails/downloadTemplate'
exportCommon(url,'POST', params,'机具类型表')
}

View File

@ -307,17 +307,18 @@
WHERE wtr.SUP_ID = #{taskId} and wir.MA_ID
</select>
<select id="getMaTypeByNameAndModel" resultType="com.bonus.lease.beans.ReceiveDetailsBean">
SELECT
mt.ID as maModelId,
SELECT mt.ID as maModelId,
mt.PARENT_ID as maTypeId,
mt2.`NAME`
FROM
mm_type mt
LEFT JOIN mm_type mt2 on mt2.ID=mt.PARENT_ID
WHERE
mt.`name`=#{maModel}
and mt.`level`='4'
and mt2.`NAME`=#{maType};
FROM mm_type mt
LEFT JOIN mm_type mt2 on mt2.ID = mt.PARENT_ID
LEFT JOIN mm_type mt3 on mt3.ID = mt2.PARENT_ID
LEFT JOIN mm_type mt4 on mt4.ID = mt3.PARENT_ID
WHERE mt.`name` = #{maModel}
and mt.`level` = '4'
and mt2.`NAME` = #{maType}
and mt3.`NAME` = #{secondName}
and mt4.`NAME` = #{firstName}
</select>
<select id="getUserByUserName" resultType="com.bonus.lease.beans.ReceiveDetailsBean">
SELECT id as customerSrepId,

View File

@ -863,7 +863,7 @@
'1'
and mat3.IS_ACTIVE
= '1' and mat4.IS_ACTIVE = '1'
<if test="keyWord != null || keyWord != '' || keyWord !=','">
<if test="keyWord != null and keyWord != '' and keyWord !=','">
and mat2.`NAME` like concat('%',#{keyWord},'%')
</if>
<!-- <if test="parentId != null || parentId != null "> and mat2.PARENT_ID

View File

@ -4,12 +4,7 @@ import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import org.apache.poi.hssf.usermodel.HSSFCell;
import org.apache.poi.hssf.usermodel.HSSFCellStyle;
import org.apache.poi.hssf.usermodel.HSSFFont;
import org.apache.poi.hssf.usermodel.HSSFRow;
import org.apache.poi.hssf.usermodel.HSSFSheet;
import org.apache.poi.hssf.usermodel.HSSFWorkbook;
import org.apache.poi.hssf.usermodel.*;
import org.apache.poi.hssf.util.CellRangeAddress;
import org.apache.poi.hssf.util.HSSFColor;
import org.apache.poi.ss.usermodel.CellStyle;
@ -156,4 +151,103 @@ public class POIOutputHelper {
return contentStyle;
}
public static HSSFWorkbook excelTwo(List<Map<String, Object>> result, List<String> list, String filename, String remark) {
// 获取工作簿对象
HSSFWorkbook workbook = new HSSFWorkbook();
HSSFSheet sheet = workbook.createSheet();
HSSFCellStyle tittleStyle = createTittleStyle(workbook);
HSSFCellStyle headerStyle = createHeaderStyle(workbook);
HSSFCellStyle contentStyle = createCellStyle(workbook);
// 完整sheet名称
String sheetName = filename + remark;
sheet.setDefaultColumnWidth(15);
HSSFRow row;
workbook.setSheetName(0, sheetName);
HSSFCell cell;
// 核心创建富文本标题实现局部红色
HSSFRichTextString richTitle = new HSSFRichTextString(sheetName);
// 创建红色字体单独设置不影响原有样式
HSSFFont redFont = workbook.createFont();
redFont.setFontHeightInPoints((short) 16); // 与标题字体大小一致
redFont.setBoldweight(HSSFFont.BOLDWEIGHT_BOLD); // 与标题字体加粗一致
redFont.setColor(HSSFColor.RED.index); // 设置字体为红色
// 给备注部分设置红色字体
// 起始索引基础文件名的长度结束索引完整标题的长度
int startIndex = filename.length();
int endIndex = sheetName.length();
richTitle.applyFont(startIndex, endIndex, redFont);
if (result != null && result.size() > 0) {
int nColumn = list.size();
row = sheet.createRow((short) 0);
row.setHeightInPoints(30);
sheet.addMergedRegion(new CellRangeAddress(0, 0, 0, (short) (nColumn - 1)));
cell = row.createCell(0);
cell.setCellStyle(tittleStyle);
// 设置富文本标题替代原普通字符串
cell.setCellValue(richTitle);
int ii = 1;
row = sheet.createRow((short) ii);
row.setHeightInPoints(20);
for (int j = 0; j < nColumn; j++) {
cell = row.createCell((short) j);
if (list.get(j) != null) {
cell.setCellStyle(headerStyle);
cell.setCellValue(list.get(j));
} else {
cell.setCellStyle(headerStyle);
cell.setCellValue("");
}
}
ii++;
for (int i = 0; i < result.size(); i++) {
Map<String, Object> resulttrow = result.get(i);
List<Object> rowdata = map2List(resulttrow);
row = sheet.createRow((short) ii);
row.setHeightInPoints(15);
for (int j = 0; j < nColumn; j++) {
cell = row.createCell((short) j);
if (rowdata.get(j) != null) {
cell.setCellStyle(contentStyle);
cell.setCellValue(rowdata.get(j).toString());
} else {
cell.setCellStyle(contentStyle);
cell.setCellValue("");
}
}
ii++;
}
} else {
int nColumn = list.size();
row = sheet.createRow((short) 0);
row.setHeightInPoints(30);
sheet.addMergedRegion(new CellRangeAddress(0, 0, 0, (short) (nColumn - 1)));
cell = row.createCell(0);
cell.setCellStyle(tittleStyle);
// 同样设置富文本标题
cell.setCellValue(richTitle);
int ii = 1;
row = sheet.createRow((short) ii);
row.setHeightInPoints(20);
for (int j = 0; j < nColumn; j++) {
cell = row.createCell((short) j);
if (list.get(j) != null) {
cell.setCellStyle(headerStyle);
cell.setCellValue(list.get(j));
} else {
cell.setCellStyle(contentStyle);
cell.setCellValue("");
}
}
}
return workbook;
}
}

View File

@ -4,6 +4,14 @@ import com.bonus.wf.beans.TaskRecordBean;
public class ReceiveDetailsBean extends TaskRecordBean {
/**
* 施工机具类型
*/
private String firstName;
/**
* 设备分类
*/
private String secondName;
private String maType;// 机具类型
private String maModel;// 机具规格
private String alreadyCollerNum;// 已领数量
@ -356,6 +364,22 @@ public class ReceiveDetailsBean extends TaskRecordBean {
this.maId = maId;
}
public String getFirstName() {
return firstName;
}
public void setFirstName(String firstName) {
this.firstName = firstName;
}
public String getSecondName() {
return secondName;
}
public void setSecondName(String secondName) {
this.secondName = secondName;
}
@Override
public String toString() {
return "ReceiveDetailsBean [maType=" + maType + ", maModel=" + maModel + ", alreadyCollerNum="

View File

@ -1,21 +1,18 @@
package com.bonus.lease.controller;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.*;
import java.math.BigDecimal;
import java.net.URLEncoder;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.*;
import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import com.bonus.exp.POIOutputHelper;
import com.bonus.ma.beans.MachineTypeBean;
import com.bonus.ma.service.MachineTypeService;
import com.bonus.sys.*;
import com.bonus.sys.beans.UserBean;
//导入POI核心类
@ -52,6 +49,9 @@ public class ReceiveDetailsController extends BaseController<ReceiveDetailsBean>
@Autowired
private ReceiveDetailsService service;
@Autowired
private MachineTypeService machineTypeService;
@RequestMapping("list")
public String index(Model model) {
return "/lease/receiveDetailslist";
@ -368,165 +368,81 @@ public class ReceiveDetailsController extends BaseController<ReceiveDetailsBean>
}
return ar;
}
//
// /**
// * 机具领料表导出
// *
// * @param request
// * @param response
// * @param page
// * @param o
// */
// @RequestMapping("expExcel")
// public void expExcel(HttpServletRequest request, HttpServletResponse response, ReceiveDetailsBean o) {
// try {
// String fileName = "机具领料详细";
// List<ReceiveDetailsBean> list = service.findMaReceiveMsg(o);
// String startTime = o.getStartTime();
// String endTime = o.getEndTime();
// String sb = "";
// if (startTime != null && startTime.equals(endTime)) {
// sb = startTime;
// } else {
// sb = startTime + "~" + endTime;
// }
// String keyWord = o.getKeyWord();
// if (StringHelper.isNotEmpty(keyWord)) {
// keyWord = "包含(" + keyWord + "";
// } else {
// keyWord = "";
// }
// expOutExcel(response, list, sb + fileName + keyWord);
// } catch (Exception e) {
// logger.error(e.toString(), e);
// }
// }
//
// private void expOutExcel(HttpServletResponse response, List<ReceiveDetailsBean> list, String filename)
// throws Exception {
// if (list != null) {
// List<Map<String, Object>> results = new ArrayList<Map<String, Object>>();
// int size = list.size();
// for (int i = 0; i < size; i++) {
// ReceiveDetailsBean bean = list.get(i);
// Map<String, Object> maps = outReceiveDetailsBeanToMap(i, bean);
// results.add(maps);
// }
// List<String> headers = receiveDetailsHeader();
// HSSFWorkbook workbook = POIOutputHelper.excel(results, headers, filename);
// OutputStream out = null;
// response.setContentType("application/vnd.ms-excel;charset=UTF-8");
// response.addHeader("Content-Disposition",
// "attachment;filename=" + URLEncoder.encode(filename, "UTF-8") + ".xls");
// response.setHeader("Pragma", "No-cache");
// out = response.getOutputStream();
// workbook.write(out);
// out.flush();
// out.close();
// }
// }
//
// private Map<String, Object> outReceiveDetailsBeanToMap(int i, ReceiveDetailsBean bean) {
// Map<String, Object> maps = new LinkedHashMap<String, Object>();
// maps.put("id", i + 1);
// maps.put("createTime", bean.getCreateTime());
// maps.put("applyMan", bean.getApplyMan());
// maps.put("leaseCompany", bean.getLeaseCompany());
// maps.put("projectName", bean.getProjectName());
// maps.put("agreementCode", bean.getAgreementCode());
// maps.put("applyNumber", bean.getApplyNumber());
// maps.put("leaseMan", bean.getLeaseMan());
// maps.put("phone", bean.getPhone());
// maps.put("remark", bean.getRemark());
// maps.put("machinesType", bean.getMachinesType());
// maps.put("machinesModel", bean.getMachinesModel());
// maps.put("machinesNum", bean.getMachinesNum());
// maps.put("actualNum", bean.getActualNum());
// maps.put("isSure", bean.getIsSure());
// return maps;
// }
//
// private List<String> receiveDetailsHeader() {
// ArrayList<String> list = new ArrayList<String>();
// list.add("序号");
// list.add("申请时间");
// list.add("申请人");
// list.add("租赁单位");
// list.add("工程名称");
// list.add("协议号");
// list.add("租赁申请单号");
// list.add("领料人");
// list.add("联系方式");
// list.add("备注");
// list.add("机具类型");
// list.add("机具型号");
// list.add("机具数量");
// list.add("已领数量");
// list.add("是否确认");
// return list;
// }
/**
* 下载物资导入模板
* @param taskId 任务ID
* @param token 令牌
* @param request HTTP请求对象显式声明参数Spring自动注入
* @param response 响应对象
* 导出导入模板机具类型
*/
@RequestMapping("/downloadTemplate")
// 注意文件下载接口建议移除@ResponseBody因为要直接写入响应流无需Spring序列化返回值
public void downloadTemplate(String taskId, String token,
HttpServletRequest request, // 关键添加request参数声明
HttpServletResponse response) {
// 1. 令牌校验此时request已正常获取可直接调用getSession()
HttpSession session = request.getSession();
String sessionToken = (String) session.getAttribute("TOKEN_IN_SESSION");
// if (token == null || !token.equals(sessionToken)) {
// // 令牌无效处理
// try {
// response.getWriter().write("令牌无效,请刷新页面重试");
// } catch (IOException e) {
// e.printStackTrace();
// }
// return;
// }
// 2. 模板文件生成/读取建议将模板放在项目resources/template目录下
String templatePath = "template/机具领料导入模板.xlsx";
File templateFile = null;
@RequestMapping("downloadTemplate")
public void downloadTemplate(HttpServletRequest request, HttpServletResponse response, MachineTypeBean o) {
try {
// 读取模板文件
Resource resource = new ClassPathResource(templatePath);
templateFile = resource.getFile();
// 3. 设置响应头实现文件下载
response.setContentType("application/vnd.openxmlformats-officedocument.spreadsheetml.sheet");
response.setHeader("Content-Disposition", "attachment; filename=" + URLEncoder.encode("物资导入模板.xlsx", "UTF-8"));
response.setContentLength((int) templateFile.length());
// 4. 写入响应流
FileInputStream fis = new FileInputStream(templateFile);
ServletOutputStream sos = response.getOutputStream();
byte[] buffer = new byte[1024];
int len;
while ((len = fis.read(buffer)) != -1) {
sos.write(buffer, 0, len);
}
sos.flush();
fis.close();
sos.close();
// // 5. 移除令牌可选防止重复下载
// session.removeAttribute("TOKEN_IN_SESSION");
List<MachineTypeBean> list = machineTypeService.findMaTypeMsg(o);
expOutExcel(response, list, "机具领料类型导入表");
} catch (Exception e) {
e.printStackTrace();
// 下载失败处理
try {
response.getWriter().write("模板下载失败,请联系管理员");
} catch (IOException ex) {
ex.printStackTrace();
logger.error(e.toString(), e);
}
}
private void expOutExcel(HttpServletResponse response, List<MachineTypeBean> list, String filename)
throws Exception {
if (list != null) {
List<Map<String, Object>> results = new ArrayList<Map<String, Object>>();
int size = list.size();
for (int i = 0; i < size; i++) {
MachineTypeBean bean = list.get(i);
Map<String, Object> maps = outMachineTypeBeanToMap(i, bean);
results.add(maps);
}
List<String> headers = machineTypeHeader();
//红字部分
String remark = "(填写需领设备的客服代表和领料数量)";
HSSFWorkbook workbook = POIOutputHelper.excelTwo(results, headers, filename, remark);
OutputStream out = null;
response.setContentType("application/vnd.ms-excel;charset=UTF-8");
response.addHeader("Content-Disposition",
"attachment;filename=" + URLEncoder.encode(filename, "UTF-8") + ".xls");
response.setHeader("Pragma", "No-cache");
out = response.getOutputStream();
workbook.write(out);
out.flush();
out.close();
}
}
private Map<String, Object> outMachineTypeBeanToMap(int i, MachineTypeBean bean) {
Map<String, Object> maps = new LinkedHashMap<String, Object>();
maps.put("id", i + 1);
maps.put("firstName", bean.getFirstName());
maps.put("secondName", bean.getSecondName());
maps.put("parentName", bean.getParentName());
maps.put("name", bean.getName());
maps.put("unit", bean.getUnit());
maps.put("nums", bean.getNums());
maps.put("buyPrice", bean.getBuyPrice());
maps.put("leasePrice", bean.getLeasePrice());
maps.put("payPrice", bean.getPayPrice());
maps.put("isTest", bean.getIsTest());
maps.put("customerSrep", "");
maps.put("machinesNum", "");
return maps;
}
private List<String> machineTypeHeader() {
ArrayList<String> list = new ArrayList<String>();
list.add("序号");
list.add("施工机具类型");
list.add("设备分类");
list.add("机具类型");
list.add("规格型号");
list.add("计量单位");
list.add("库存量");
list.add("原值(元)");
list.add("租赁价格(元)");
list.add("丢失赔偿价格(元)");
list.add("是否只计数");
list.add("客服代表");
list.add("领料数量");
return list;
}
@RequestMapping("/importData")
@ -606,34 +522,47 @@ public class ReceiveDetailsController extends BaseController<ReceiveDetailsBean>
StringBuilder rowErrorMsg = new StringBuilder();
// 低版本POI兼容手动判断单元格是否为null无MissingCellPolicy
Cell maTypeCell = row.getCell(0);
Cell firstNameCell = row.getCell(1);
String firstName = getCellStringValue(firstNameCell);
bean.setFirstName(firstName);
Cell secondNameCell = row.getCell(2);
String secondName = getCellStringValue(secondNameCell);
bean.setSecondName(secondName);
Cell maTypeCell = row.getCell(3);
String maType = getCellStringValue(maTypeCell);
bean.setMaType(maType);
Cell maModelCell = row.getCell(1);
Cell maModelCell = row.getCell(4);
String maModel = getCellStringValue(maModelCell);
bean.setMaModel(maModel);
Cell customerSrepCell = row.getCell(2);
Cell customerSrepCell = row.getCell(11);
String customerSrep = getCellStringValue(customerSrepCell);
bean.setCustomerSrep(customerSrep);
Cell machinesNumCell = row.getCell(3);
Cell machinesNumCell = row.getCell(12);
String machinesNum = getCellStringValue(machinesNumCell);
bean.setMachinesNum(machinesNum);
// 7. 原有校验逻辑完全不变
if (StringHelper.isEmpty(maType)) {
rowErrorMsg.append("物资名称为空;");
}
if (StringHelper.isEmpty(maModel)) {
rowErrorMsg.append("规格型号为空;");
}
if (StringHelper.isEmpty(customerSrep)) {
rowErrorMsg.append("客服代表为空;");
//如果施工机具类型设备分类物资名称规格型号客户代表领料数量中有一个为空则跳过该行数据
if (StringHelper.isEmpty(firstName) || StringHelper.isEmpty(secondName) || StringHelper.isEmpty(maType) || StringHelper.isEmpty(maModel) || StringHelper.isEmpty(customerSrep) || StringHelper.isEmpty(machinesNum)) {
continue;
}
// // 7. 原有校验逻辑完全不变
// if (StringHelper.isEmpty(maType)) {
// rowErrorMsg.append("物资名称为空;");
// }
// if (StringHelper.isEmpty(maModel)) {
// rowErrorMsg.append("规格型号为空;");
// }
// if (StringHelper.isEmpty(customerSrep)) {
// rowErrorMsg.append("客服代表为空;");
// }
if (StringHelper.isEmpty(machinesNum)) {
rowErrorMsg.append("机具数量为空;");
// rowErrorMsg.append("机具数量为空;");
} else {
try {
int machineNum = Integer.parseInt(machinesNum.trim());
@ -645,11 +574,11 @@ public class ReceiveDetailsController extends BaseController<ReceiveDetailsBean>
}
}
// 8. 物资名称+规格型号存在性校验不变
// 8. 施工机具类型+设备分类+物资名称+规格型号存在性校验
if (rowErrorMsg.length() == 0) {
ReceiveDetailsBean receiveDetailsBean = service.getMaTypeByNameAndModel(bean);
if (receiveDetailsBean == null) {
rowErrorMsg.append("物资名称或规格型号不存在");
rowErrorMsg.append("物资名称或规格型号不存在或不对应");
} else {
bean.setMaModelId(receiveDetailsBean.getMaModelId());
}