二维码功能开发
This commit is contained in:
@@ -94,7 +94,7 @@
|
||||
<dependency>
|
||||
<groupId>org.docx4j</groupId>
|
||||
<artifactId>docx4j</artifactId>
|
||||
<version>3.3.4</version>
|
||||
<version>6.1.0</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>com.fasterxml.jackson.core</groupId>
|
||||
@@ -112,6 +112,18 @@
|
||||
<version>2.12.0</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.njcn</groupId>
|
||||
<artifactId>RestTemplate-plugin</artifactId>
|
||||
<version>1.0.0</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>commons-net</groupId>
|
||||
<artifactId>commons-net</artifactId>
|
||||
<version>3.10.0</version>
|
||||
</dependency>
|
||||
|
||||
</dependencies>
|
||||
|
||||
|
||||
|
||||
@@ -13,6 +13,9 @@ public interface DetectionCommunicateConstant {
|
||||
|
||||
String DEVICE_CHANNEL_NAME = "AUTO_DETECTION_DEV";
|
||||
|
||||
String DEV = "_Dev";
|
||||
|
||||
String SOURCE = "_Source";
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -94,6 +94,11 @@ public enum SourceOperateCodeEnum {
|
||||
small_comp_end("small_comp_end","小电压校准结束"),
|
||||
|
||||
|
||||
/**
|
||||
* ftp文件传送指令
|
||||
*/
|
||||
FTP_SEND_01("FTP_SEND$01", "发送文件")
|
||||
|
||||
|
||||
;
|
||||
|
||||
|
||||
@@ -191,7 +191,7 @@ public class PreDetectionServiceImpl implements PreDetectionService {
|
||||
xuMsg.setOperateCode(SourceOperateCodeEnum.OPER_GATHER.getValue());
|
||||
xuMsg.setData(JSON.toJSONString(sourceIssues));
|
||||
xuMsg.setRequestId(SourceOperateCodeEnum.FORMAL_REAL.getValue() + "&&" + sourceIssues.getType());
|
||||
SocketManager.sendMsg(DetectionCommunicateConstant.SOURCE_CHANNEL_NAME, JSON.toJSONString(xuMsg));
|
||||
SocketManager.sendMsg(param.getUserPageId() + DetectionCommunicateConstant.SOURCE, JSON.toJSONString(xuMsg));
|
||||
} else {
|
||||
//TODO 是否最终检测完成需要推送给用户
|
||||
PqScriptCheckDataParam checkDataParam = new PqScriptCheckDataParam();
|
||||
@@ -219,7 +219,7 @@ public class PreDetectionServiceImpl implements PreDetectionService {
|
||||
|
||||
@Override
|
||||
public void sendScript(SimulateDetectionParam param) {
|
||||
Channel channel = SocketManager.getChannelByUserId(DetectionCommunicateConstant.SOURCE_CHANNEL_NAME);
|
||||
Channel channel = SocketManager.getChannelByUserId(param.getUserPageId() + DetectionCommunicateConstant.SOURCE);
|
||||
if (Objects.isNull(channel) || !channel.isActive()) {
|
||||
// 进行源通信连接
|
||||
PreDetectionParam preDetectionParam = new PreDetectionParam();
|
||||
@@ -253,7 +253,7 @@ public class PreDetectionServiceImpl implements PreDetectionService {
|
||||
|
||||
@Override
|
||||
public void closeTestSimulate(SimulateDetectionParam param) {
|
||||
Channel channel = SocketManager.getChannelByUserId(DetectionCommunicateConstant.SOURCE_CHANNEL_NAME);
|
||||
Channel channel = SocketManager.getChannelByUserId(param.getUserPageId() + DetectionCommunicateConstant.SOURCE);
|
||||
if (Objects.isNull(channel) || !channel.isActive()) {
|
||||
throw new BusinessException(DetectionResponseEnum.SOURCE_NOT_CONNECT);
|
||||
}
|
||||
|
||||
@@ -10,7 +10,6 @@ import lombok.extern.slf4j.Slf4j;
|
||||
import java.util.Objects;
|
||||
|
||||
/**
|
||||
*
|
||||
* 检测通讯工具类
|
||||
*
|
||||
* @author hongawen
|
||||
@@ -26,8 +25,9 @@ public class DetectionCommunicateUtil {
|
||||
* 有则强行关闭
|
||||
*/
|
||||
public static void checkCommunicateChannel(PreDetectionParam param) {
|
||||
Channel channelSource = SocketManager.getChannelByUserId(DetectionCommunicateConstant.SOURCE_CHANNEL_NAME);
|
||||
Channel channelDev = SocketManager.getChannelByUserId(DetectionCommunicateConstant.DEVICE_CHANNEL_NAME);
|
||||
Channel channelSource = SocketManager.getChannelByUserId(param.getUserPageId() + DetectionCommunicateConstant.SOURCE);
|
||||
Channel channelDev = SocketManager.getChannelByUserId(param.getUserPageId() + DetectionCommunicateConstant.DEV);
|
||||
|
||||
if (Objects.nonNull(channelSource) && channelSource.isActive()) {
|
||||
System.out.println("发送关闭源指令。。。。。。。。");
|
||||
CnSocketUtil.quitSendSource(param);
|
||||
@@ -43,8 +43,8 @@ public class DetectionCommunicateUtil {
|
||||
log.error(e.getMessage());
|
||||
}
|
||||
|
||||
SocketManager.removeUser(DetectionCommunicateConstant.SOURCE_CHANNEL_NAME);
|
||||
SocketManager.removeUser(DetectionCommunicateConstant.DEVICE_CHANNEL_NAME);
|
||||
SocketManager.removeUser(param.getUserPageId() + DetectionCommunicateConstant.SOURCE);
|
||||
SocketManager.removeUser(param.getUserPageId() + DetectionCommunicateConstant.DEV);
|
||||
|
||||
try {
|
||||
Thread.sleep(2000);
|
||||
@@ -54,5 +54,4 @@ public class DetectionCommunicateUtil {
|
||||
}
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
||||
@@ -64,8 +64,10 @@ public interface IPqReportService extends IService<PqReport> {
|
||||
|
||||
void generateReport(DevReportParam devReportParam);
|
||||
|
||||
|
||||
void downloadReport(DevReportParam devReportParam, HttpServletResponse response);
|
||||
|
||||
|
||||
/**
|
||||
* 设备归档操作
|
||||
*
|
||||
@@ -73,4 +75,7 @@ public interface IPqReportService extends IService<PqReport> {
|
||||
* @return 归档成功返回true,否则返回false
|
||||
*/
|
||||
boolean documented(List<String> id);
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
||||
@@ -8,7 +8,12 @@ import cn.hutool.core.text.StrPool;
|
||||
import cn.hutool.core.util.ArrayUtil;
|
||||
import cn.hutool.core.util.ObjectUtil;
|
||||
import cn.hutool.core.util.StrUtil;
|
||||
import cn.hutool.extra.ftp.Ftp;
|
||||
import cn.hutool.extra.qrcode.QrCodeUtil;
|
||||
import cn.hutool.extra.qrcode.QrConfig;
|
||||
import cn.hutool.json.JSONObject;
|
||||
import cn.hutool.json.JSONUtil;
|
||||
import com.alibaba.fastjson.JSON;
|
||||
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
||||
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
|
||||
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
|
||||
@@ -17,8 +22,18 @@ import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
|
||||
import com.njcn.common.pojo.constant.PatternRegex;
|
||||
import com.njcn.common.pojo.enums.common.DataStateEnum;
|
||||
import com.njcn.common.pojo.exception.BusinessException;
|
||||
import com.njcn.common.utils.BinaryDataConverter;
|
||||
import com.njcn.common.utils.images.ImageConverter;
|
||||
import com.njcn.gather.detection.handler.SocketDevResponseService;
|
||||
import com.njcn.gather.detection.pojo.constant.DetectionCommunicateConstant;
|
||||
import com.njcn.gather.detection.pojo.enums.DetectionCodeEnum;
|
||||
import com.njcn.gather.detection.pojo.enums.SourceOperateCodeEnum;
|
||||
import com.njcn.gather.detection.pojo.param.PreDetectionParam;
|
||||
import com.njcn.gather.detection.pojo.vo.DetectionData;
|
||||
import com.njcn.gather.detection.pojo.vo.SocketMsg;
|
||||
import com.njcn.gather.detection.util.socket.SocketManager;
|
||||
import com.njcn.gather.detection.util.socket.cilent.NettyClient;
|
||||
import com.njcn.gather.detection.util.socket.cilent.NettyDevClientHandler;
|
||||
import com.njcn.gather.device.mapper.PqDevMapper;
|
||||
import com.njcn.gather.device.pojo.enums.CheckStateEnum;
|
||||
import com.njcn.gather.device.pojo.enums.DevReportStateEnum;
|
||||
@@ -35,7 +50,6 @@ import com.njcn.gather.report.pojo.constant.PowerConstant;
|
||||
import com.njcn.gather.report.pojo.constant.ReportConstant;
|
||||
import com.njcn.gather.report.pojo.enums.*;
|
||||
import com.njcn.gather.report.pojo.param.ReportParam;
|
||||
import com.njcn.gather.report.pojo.po.CellEntity;
|
||||
import com.njcn.gather.report.pojo.po.PqReport;
|
||||
import com.njcn.gather.report.pojo.result.SingleTestResult;
|
||||
import com.njcn.gather.report.pojo.vo.PqReportVO;
|
||||
@@ -57,7 +71,10 @@ import com.njcn.gather.system.dictionary.pojo.po.DictData;
|
||||
import com.njcn.gather.system.dictionary.service.IDictDataService;
|
||||
import com.njcn.gather.type.pojo.po.DevType;
|
||||
import com.njcn.gather.type.service.IDevTypeService;
|
||||
import com.njcn.http.util.RestTemplateUtil;
|
||||
import com.njcn.web.factory.PageFactory;
|
||||
import com.njcn.web.utils.HttpServletUtil;
|
||||
import io.netty.channel.Channel;
|
||||
import lombok.RequiredArgsConstructor;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.apache.poi.xwpf.usermodel.*;
|
||||
@@ -65,24 +82,34 @@ import org.docx4j.jaxb.Context;
|
||||
import org.docx4j.openpackaging.packages.WordprocessingMLPackage;
|
||||
import org.docx4j.openpackaging.parts.WordprocessingML.MainDocumentPart;
|
||||
import org.docx4j.wml.*;
|
||||
import org.openxmlformats.schemas.wordprocessingml.x2006.main.*;
|
||||
import org.springframework.beans.BeanUtils;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.beans.factory.annotation.Value;
|
||||
import org.springframework.core.io.ClassPathResource;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.stereotype.Service;
|
||||
import org.springframework.transaction.annotation.Transactional;
|
||||
import org.springframework.web.multipart.MultipartFile;
|
||||
|
||||
import javax.imageio.ImageIO;
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
import javax.xml.bind.JAXBElement;
|
||||
import java.awt.*;
|
||||
import java.awt.Color;
|
||||
import java.awt.image.BufferedImage;
|
||||
import java.awt.image.DataBufferUShort;
|
||||
import java.io.*;
|
||||
import java.math.BigDecimal;
|
||||
import java.math.BigInteger;
|
||||
import java.math.RoundingMode;
|
||||
import java.nio.ByteBuffer;
|
||||
import java.nio.ByteOrder;
|
||||
import java.nio.file.Files;
|
||||
import java.nio.file.Path;
|
||||
import java.nio.file.Paths;
|
||||
import java.util.*;
|
||||
import java.util.List;
|
||||
import java.util.concurrent.*;
|
||||
import java.util.regex.Pattern;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
@@ -120,6 +147,16 @@ public class PqReportServiceImpl extends ServiceImpl<PqReportMapper, PqReport> i
|
||||
|
||||
private final ISysTestConfigService sysTestConfigService;
|
||||
|
||||
@Autowired
|
||||
private RestTemplateUtil restTemplateUtil;
|
||||
|
||||
private final ThreadPoolExecutor executor = new ThreadPoolExecutor(
|
||||
4, 8, 30, TimeUnit.SECONDS,
|
||||
new LinkedBlockingQueue<>(100),
|
||||
// 队列满时由主线程执行
|
||||
new ThreadPoolExecutor.CallerRunsPolicy()
|
||||
);
|
||||
|
||||
private final long FILE_SIZE_LIMIT = 5 * 1024 * 1024;
|
||||
|
||||
@Override
|
||||
@@ -496,6 +533,7 @@ public class PqReportServiceImpl extends ServiceImpl<PqReportMapper, PqReport> i
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* 根据设备类型生成报告
|
||||
* 注:该方法目前仅支持楼下出厂检测场景,属于模板占位符替换方式,后期可能会有调整
|
||||
@@ -537,7 +575,8 @@ public class PqReportServiceImpl extends ServiceImpl<PqReportMapper, PqReport> i
|
||||
String dirPath = reportPath;
|
||||
// 确保目录存在
|
||||
ensureDirectoryExists(dirPath);
|
||||
FileOutputStream out = new FileOutputStream(dirPath.concat(File.separator).concat(pqDevVO.getCreateId()).concat(".docx"));
|
||||
String reportFullPath = dirPath.concat(File.separator).concat(pqDevVO.getCreateId()).concat(".docx");
|
||||
FileOutputStream out = new FileOutputStream(reportFullPath);
|
||||
// 4. 保存新的Word文档
|
||||
try {
|
||||
baseModelDocument.write(out);
|
||||
@@ -546,7 +585,16 @@ public class PqReportServiceImpl extends ServiceImpl<PqReportMapper, PqReport> i
|
||||
}
|
||||
out.close();
|
||||
|
||||
this.updateDevAndPlanState(devReportParam.getDevId(), devReportParam.getPlanId());
|
||||
Future<?> future = executor.submit(() -> {
|
||||
this.updateDevAndPlanState(devReportParam.getDevId(), pqDevVO.getCreateId() + ".docx");
|
||||
});
|
||||
|
||||
try {
|
||||
future.get();
|
||||
} catch (Exception e) {
|
||||
log.error("检测报告上云异常,异常为:"+e.getMessage());
|
||||
}
|
||||
sendReportToCloud(pqDevVO.getIp(), reportFullPath, pqDevVO.getCreateId() + ".docx");
|
||||
} catch (IOException e) {
|
||||
log.error(ReportResponseEnum.GENERATE_REPORT_ERROR.getMessage(), e);
|
||||
throw new BusinessException(ReportResponseEnum.GENERATE_REPORT_ERROR);
|
||||
@@ -554,6 +602,86 @@ public class PqReportServiceImpl extends ServiceImpl<PqReportMapper, PqReport> i
|
||||
});
|
||||
}
|
||||
|
||||
@Value("${socket.device.ip}")
|
||||
private String ip;
|
||||
|
||||
@Value("${socket.device.port}")
|
||||
private Integer port;
|
||||
|
||||
private final SocketDevResponseService socketDevResponseService;
|
||||
|
||||
/**
|
||||
* 处理检测报告上传云服务器并生成二维码下装到装置
|
||||
* 做成异步执行
|
||||
*
|
||||
* @param devIp 设备IP
|
||||
* @param reportFullPath 检测报告本地全路径
|
||||
* @param reportName 检测报告名称
|
||||
*/
|
||||
public void sendReportToCloud(String devIp, String reportFullPath, String reportName) {
|
||||
// String url = "http://pqmcc.com:8060/api/file";
|
||||
String url = "http://127.0.0.1:18082/api/file";
|
||||
devIp = "192.168.1.239";
|
||||
// 将文件上传至目标服务器
|
||||
File file = new File(reportFullPath);
|
||||
try {
|
||||
ResponseEntity<String> responseEntity = restTemplateUtil.uploadFile(url + "/upload", file);
|
||||
if (responseEntity.getStatusCode().is2xxSuccessful()) {
|
||||
// 上传没问题后,拼接url生成二维码,并将二维码转为bin格式文件传递给设备通讯模块
|
||||
String qrUrl = url + "/download/" + reportName;
|
||||
BufferedImage bufferedImage = QrCodeUtil.generate(qrUrl, 148, 148);
|
||||
// 将 BufferedImage 转换为单色图像
|
||||
BufferedImage monoImage = new BufferedImage(148, 148, BufferedImage.TYPE_BYTE_BINARY);
|
||||
Graphics2D g2d = monoImage.createGraphics();
|
||||
g2d.drawImage(bufferedImage, 0, 0, null);
|
||||
g2d.dispose();
|
||||
// 3. 【关键修正】创建一个新的1-bit单色图像,并将原始图像绘制上去,以强制转换为单色位图
|
||||
BufferedImage monochromeImage = new BufferedImage(bufferedImage.getWidth(), bufferedImage.getHeight(), BufferedImage.TYPE_BYTE_BINARY);
|
||||
monochromeImage.getGraphics().drawImage(bufferedImage, 0, 0, null);
|
||||
// 4. 将单色图像在内存中编码为完整的BMP文件流
|
||||
byte[] finalBinData = ImageConverter.convertToBinFormat(bufferedImage);
|
||||
|
||||
String base64String = Base64.getEncoder().encodeToString(finalBinData);
|
||||
System.out.println("二维码base64数据为:" + base64String);
|
||||
|
||||
// 组装设备通讯模块的参数
|
||||
SocketMsg<String> sendFileMsg = new SocketMsg<>();
|
||||
sendFileMsg.setOperateCode(SourceOperateCodeEnum.FTP_SEND_01.getValue());
|
||||
sendFileMsg.setRequestId(SourceOperateCodeEnum.FTP_SEND_01.getValue());
|
||||
// 组装业务数据
|
||||
JSONObject data = new JSONObject();
|
||||
data.set("name", "njcn");
|
||||
data.set("password", "Pqs@12345678");
|
||||
data.set("port", "21");
|
||||
data.set("path", "ftp://" + devIp + "/etc/temp.bin");
|
||||
data.set("binData", base64String);
|
||||
|
||||
|
||||
|
||||
sendFileMsg.setData(data.toString());
|
||||
String msg = JSON.toJSONString(sendFileMsg);
|
||||
Channel channel = SocketManager.getChannelByUserId("cdf" + DetectionCommunicateConstant.DEV);
|
||||
if (Objects.isNull(channel) || !channel.isActive()) {
|
||||
// 进行源通信连接
|
||||
PreDetectionParam preDetectionParam = new PreDetectionParam();
|
||||
preDetectionParam.setUserPageId("cdf");
|
||||
preDetectionParam.setSendWebMsg(false);
|
||||
|
||||
NettyClient.socketClient(ip, port, preDetectionParam, msg, new NettyDevClientHandler(preDetectionParam, socketDevResponseService));
|
||||
} else {
|
||||
channel.writeAndFlush(msg + "\n");
|
||||
}
|
||||
|
||||
}
|
||||
} catch (Exception e) {
|
||||
// 进行日志记录入口
|
||||
System.out.println("异常为:" + e.getMessage());
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* 根据计划绑定的报告模板生成报告
|
||||
* 注:该方法目前属于同用信息占位符替换,数据页为面向对象动态填充拼凑方式
|
||||
|
||||
@@ -77,8 +77,8 @@ Dip:
|
||||
|
||||
|
||||
Flicker:
|
||||
waveFluType: SQU
|
||||
waveType: CPM
|
||||
waveFluType: CPM
|
||||
waveType: SQU
|
||||
fDutyCycle: 50f
|
||||
|
||||
log:
|
||||
|
||||
@@ -3,13 +3,18 @@ package com.njcn;
|
||||
import com.njcn.gather.EntranceApplication;
|
||||
import com.njcn.gather.report.pojo.DevReportParam;
|
||||
import com.njcn.gather.report.service.IPqReportService;
|
||||
import com.njcn.http.util.RestTemplateUtil;
|
||||
import org.junit.Test;
|
||||
import org.junit.runner.RunWith;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.boot.test.context.SpringBootTest;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.test.context.junit4.SpringRunner;
|
||||
import org.springframework.test.context.web.WebAppConfiguration;
|
||||
|
||||
import java.io.File;
|
||||
import java.util.HashMap;
|
||||
|
||||
|
||||
/**
|
||||
* @author hongawen
|
||||
@@ -24,14 +29,18 @@ public class BaseJunitTest {
|
||||
@Autowired
|
||||
private IPqReportService pqReportService;
|
||||
|
||||
@Autowired
|
||||
private RestTemplateUtil restTemplateUtil;
|
||||
|
||||
@Test
|
||||
public void test() {
|
||||
DevReportParam devReportParam = new DevReportParam();
|
||||
devReportParam.setPlanId("ad3df9e4a90b4c3c8ce7d21a84ce6f59");
|
||||
devReportParam.setPlanCode("31");
|
||||
devReportParam.setScriptId("810e4050e1d445e3542c998a077a263a");
|
||||
devReportParam.setDevId("a46349a3b3cf4789a6b82690a6076afd");
|
||||
pqReportService.generateReport(devReportParam);
|
||||
File file = new File("D:\\report\\PQS_882B4\\5555.docx");
|
||||
|
||||
try{
|
||||
ResponseEntity<String> stringResponseEntity = restTemplateUtil.uploadFile("http://localhost:18082/api/file/upload",file);
|
||||
}catch (Exception runtimeException){
|
||||
System.out.println(runtimeException.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user