diff --git a/web/pom.xml b/web/pom.xml index b956420..8c77649 100644 --- a/web/pom.xml +++ b/web/pom.xml @@ -18,6 +18,11 @@ + + org.dromara.easyai + easyAi + 1.3.2 + commons-net commons-net diff --git a/web/src/main/java/com/zhehekeji/web/config/EaseAiConfig.java b/web/src/main/java/com/zhehekeji/web/config/EaseAiConfig.java new file mode 100644 index 0000000..835b334 --- /dev/null +++ b/web/src/main/java/com/zhehekeji/web/config/EaseAiConfig.java @@ -0,0 +1,38 @@ +package com.zhehekeji.web.config; + +import lombok.Data; +import org.dromara.easyai.yolo.FastYolo; +import org.dromara.easyai.yolo.YoloConfig; +import org.springframework.boot.context.properties.ConfigurationProperties; +import org.springframework.context.annotation.Bean; +import org.springframework.stereotype.Component; + +import javax.annotation.Resource; + +@Component +@ConfigurationProperties +@Data +public class EaseAiConfig { + + + @Bean + public YoloConfig yoloConfig(){ + YoloConfig yoloConfig = new YoloConfig();//创建配置参数类 + yoloConfig.setWindowHeight(300); + yoloConfig.setWindowWidth(600); + yoloConfig.setTypeNub(5); + yoloConfig.setEnhance(40); + yoloConfig.setContainIouTh(0.1); + yoloConfig.setPth(0.7); + return yoloConfig; + } + + @Bean + public FastYolo fastYolo(YoloConfig yoloConfig){ + try { + return new FastYolo(yoloConfig); + } catch (Exception e) { + throw new RuntimeException(e); + } + } +} diff --git a/web/src/main/java/com/zhehekeji/web/controller/CameraIoController.java b/web/src/main/java/com/zhehekeji/web/controller/CameraIoController.java new file mode 100644 index 0000000..24a24dc --- /dev/null +++ b/web/src/main/java/com/zhehekeji/web/controller/CameraIoController.java @@ -0,0 +1,128 @@ +package com.zhehekeji.web.controller; + +import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper; +import com.github.pagehelper.PageInfo; +import com.zhehekeji.core.pojo.Result; +import com.zhehekeji.web.entity.*; +import com.zhehekeji.web.mapper.CameraIOMapper; +import com.zhehekeji.web.pojo.camera.CameraConfigSearchReq; +import com.zhehekeji.web.service.CameraService; +import io.swagger.annotations.Api; +import io.swagger.annotations.ApiOperation; +import lombok.extern.slf4j.Slf4j; +import org.apache.poi.ss.formula.functions.T; +import org.springframework.web.bind.annotation.*; + +import javax.annotation.Resource; +import java.io.BufferedWriter; +import java.io.IOException; +import java.nio.file.*; +import java.nio.file.attribute.BasicFileAttributes; +import java.time.LocalDateTime; +import java.util.ArrayList; +import java.util.List; +import java.util.Map; +import java.util.stream.Collectors; + +@Api(value = "cameraIo",tags = "球机预置点") +@RestController +@RequestMapping("/cameraIo") +@Slf4j +public class CameraIoController { + @Resource + private CameraIOMapper cameraIOMapper; + + @Resource + private CameraService cameraService; + @PostMapping("/config") + @ApiOperation(value = "球机IO配置新增 ") + public Result addConfig (@RequestBody CameraIO config) { + + cameraService.ptz(null, config.getCameraId(), config.getName(),0,config.getCode()); + return Result.success(); + } + + + @PostMapping("/realTimeCamera") + @ApiOperation(value = "球机IO配置分页列表") + public Result> configPage () { + List cameras = cameraService.allCameras(); + List cameraIOs = cameraIOMapper.selectList(new QueryWrapper()); + Map> map = cameraIOs.stream().collect(Collectors.groupingBy(CameraIO::getCameraId)); + for (Camera camera : cameras) { + camera.setStatus(cameraService.getPtzIdByCodeAndCameraId(camera.getRtsp(),camera.getId())!=null?"在线":"离线"); + camera.setCameraIOs(map.get(camera.getId())); + } + + return Result.success(cameras); + } + + + + @PostMapping("/config/page") + @ApiOperation(value = "球机IO配置分页列表") + public Result> configPage (@RequestBody CameraIO cameraIO) { + return Result.success(cameraIOMapper.selectList(new QueryWrapper().eq(cameraIO.getCameraId()!=null,"camera_id",cameraIO.getCameraId()))); + } + + @PutMapping("/config") + @ApiOperation(value = "球机IO配置修改 ") + public Result editConfig (@RequestBody CameraIO config) { + cameraIOMapper.updateById(config); + return Result.success(); + } + + @PostMapping("/getDeviceTree") + @ApiOperation(value = "获取设备树") + public Result> getDeviceTree () { + List deviceResps = cameraService.getDeviceTree(); + return Result.success(deviceResps); + } + + @DeleteMapping("/config") + @ApiOperation(value = "球机IO配置删除 ") + public Result delConfig (@RequestBody CameraIO config) { + cameraIOMapper.deleteById(config.getId()); + return Result.success(); + } + + public static void main(String[] args) { + Path sourceDirectory = Paths.get("E:\\玉溪\\mysql"); + Path targetFile = Paths.get("E:\\玉溪\\mysql1.txt"); + + try { + mergeFiles(sourceDirectory, targetFile); + System.out.println("文件合并完成!"); + } catch (IOException e) { + e.printStackTrace(); + } + } + + public static void mergeFiles(Path sourceDirectory, Path targetFile) throws IOException { + List files = new ArrayList<>(); + Files.walkFileTree(sourceDirectory, new SimpleFileVisitor() { + @Override + public FileVisitResult visitFile(Path file, BasicFileAttributes attrs) throws IOException { + if (Files.isRegularFile(file)) { + files.add(file); + } + return FileVisitResult.CONTINUE; + } + }); + + try (BufferedWriter writer = Files.newBufferedWriter(targetFile)) { + for (Path file : files) { + //writer.write("开始文件: " + file.getFileName() + "\n"); + Files.lines(file).forEach(line -> { + try { + writer.write(line); + writer.newLine(); + } catch (IOException e) { + e.printStackTrace(); + } + }); + // writer.write("结束文件: " + file.getFileName() + "\n\n"); + } + } + } +} diff --git a/web/src/main/java/com/zhehekeji/web/controller/EaseController.java b/web/src/main/java/com/zhehekeji/web/controller/EaseController.java new file mode 100644 index 0000000..5ed2f9c --- /dev/null +++ b/web/src/main/java/com/zhehekeji/web/controller/EaseController.java @@ -0,0 +1,119 @@ +package com.zhehekeji.web.controller; + +import com.alibaba.fastjson.JSON; +import com.github.pagehelper.PageInfo; +import com.zhehekeji.common.util.ValidatorUtil; +import com.zhehekeji.core.pojo.Result; +import com.zhehekeji.web.easeAi.TestPic; +import com.zhehekeji.web.entity.CheckLog; +import com.zhehekeji.web.pojo.stock.CheckLogSearch; +import com.zhehekeji.web.service.CheckLogService; +import io.swagger.annotations.Api; +import io.swagger.annotations.ApiOperation; +import org.dromara.easyai.entity.ThreeChannelMatrix; +import org.dromara.easyai.tools.ImageTools; +import org.dromara.easyai.tools.Picture; +import org.dromara.easyai.yolo.*; +import org.springframework.web.bind.annotation.PostMapping; +import org.springframework.web.bind.annotation.RequestBody; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RestController; + +import javax.annotation.Resource; +import java.util.ArrayList; +import java.util.List; +import java.util.UUID; + + +@Api(tags = "简单深度学习") +@RequestMapping("/EaseAiController") +@RestController +public class EaseController { + @Resource + private YoloConfig yoloConfig; + + @Resource + private FastYolo fastYolo; + + @Resource + private CheckLogService checkLogService; + @Resource + private ValidatorUtil validatorUtil; + + List yoloSamples = new ArrayList<>(); + + @ApiOperation("简单测试") + @PostMapping("") + public Result> list(@RequestBody YoloSample yoloSample){ + + + try { + +// YoloModel yoloModel = new YoloModel();//从训练的模型中JSON反序列化读取模型 +// +// yolo.insertModel(yoloModel); + + + yoloSample.setLocationURL("E:\\YXP/"+yoloSample.getLocationURL()); + yoloSamples.add(yoloSample); + + } catch (Exception e) { + throw new RuntimeException(e); + } + + +// 初始化过程 + return Result.success(); + } + + @ApiOperation("简单测试") + @PostMapping("2") + public Result> set(){ + try { + fastYolo.toStudy(yoloSamples);//开始训练,训练耗时较长 + } catch (Exception e) { + throw new RuntimeException(e); + } + + YoloModel yoloModel = null;//训练完毕获取模型 + try { + yoloModel = fastYolo.getModel(); + } catch (Exception e) { + throw new RuntimeException(e); + } + TestPic.writeModel(JSON.toJSONString(yoloModel), "D:\\lesson/yoloModel.json");//将模型序列化为JSON字符串,保存到磁盘文件 + return Result.success(); + } + + public static void main(String[] args) { + + } + + @ApiOperation("简单测试") + @PostMapping("11") + public Result> get(){ + + FastYolo yolo = null; //初始化图像识别类 + try { + yolo = new FastYolo(yoloConfig); +// YoloModel yoloModel = new YoloModel();//从训练的模型中JSON反序列化读取模型 +// +// yolo.insertModel(yoloModel); + + YoloModel yoloModel = TestPic.readModelParameter("D:\\lesson/yoloModel.json");//从训练的模型中JSON反序列化读取模型 + yolo.insertModel(yoloModel);//识别类注入模型 + //Picture picture = new Picture();//初始化图像解析类 + ThreeChannelMatrix th = Picture.getThreeMatrix("D:\\test\\11\\00J50359930.jpeg",false);//将图像解析为三通道矩阵 + List list = yolo.look(th, 100); + ImageTools imageTools = new ImageTools(); + ImageTools.drawBox("D:\\test\\11\\00J50359930.jpeg",list, "D:\\lesson\\yoloModel.jpeg",2); + //对该图像矩阵进行识别,并返回识别结果 + } catch (Exception e) { + throw new RuntimeException(e); + } + + return Result.success(); + } + + +} diff --git a/web/src/main/java/com/zhehekeji/web/controller/SseClientController.java b/web/src/main/java/com/zhehekeji/web/controller/SseClientController.java new file mode 100644 index 0000000..c5ee888 --- /dev/null +++ b/web/src/main/java/com/zhehekeji/web/controller/SseClientController.java @@ -0,0 +1,101 @@ +package com.zhehekeji.web.controller; + +import com.alibaba.fastjson.JSON; +import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper; +import com.zhehekeji.core.pojo.Result; +import com.zhehekeji.core.util.Assert; +import com.zhehekeji.web.entity.Camera; +import com.zhehekeji.web.entity.CameraIO; +import com.zhehekeji.web.entity.SseMsgEntity; +import com.zhehekeji.web.entity.Street; +import com.zhehekeji.web.lib.CameraControlModule; +import com.zhehekeji.web.mapper.CameraIOMapper; +import com.zhehekeji.web.service.CameraService; +import com.zhehekeji.web.service.StreetConn; +import com.zhehekeji.web.util.SseClient; +import io.swagger.annotations.Api; +import io.swagger.annotations.ApiOperation; +import lombok.extern.slf4j.Slf4j; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Controller; +import org.springframework.ui.ModelMap; +import org.springframework.web.bind.annotation.*; +import org.springframework.web.servlet.mvc.method.annotation.SseEmitter; + +import javax.annotation.Resource; +import java.util.ArrayList; +import java.util.List; +import java.util.UUID; + +@Api(value = "sseConfig",tags = "sse设置") +@RestController +@RequestMapping("/sse") +@Slf4j +public class SseClientController { + @Resource + private SseClient sseClient; + @Resource + private CameraIOMapper cameraIOMapper; + @Resource + private CameraService cameraService; + + @Resource + private CameraControlModule cameraControlModule; + @GetMapping("/index") + @ResponseBody + public Result index() { + String uid = UUID.randomUUID().toString(); + + return Result.success(uid); + } + + @GetMapping("/cameraIo/{type}") + @ApiOperation(value = "门禁警告上传") + public Result cameraIoType(@PathVariable String type){ + List cameraIOs = cameraIOMapper.selectList(new QueryWrapper().eq("code",type)); + for (CameraIO cameraIO: cameraIOs){ + try { + + cameraControlModule.toPtz(cameraIO.getPtzId(),cameraIO.getCameraId()); + }catch (Exception e){ + log.error("ptz失败",e); + } + Camera camera = cameraService.detail(cameraIO.getCameraId()); + camera.setCameraIOs(new ArrayList<>()); + camera.getCameraIOs().add(cameraIO); + SseMsgEntity sseMsgEntity = new SseMsgEntity(); + sseMsgEntity.setCameraId(camera.getId()); + sseMsgEntity.setDevice(camera.getType()); + sseMsgEntity.setCode(type); + sseMsgEntity.setCameraIO(cameraIO); + sseMsgEntity.setCamera(camera); + sseClient.sendAll(JSON.toJSONString(sseMsgEntity)); + } + return Result.success(); + } + @CrossOrigin + @GetMapping("/createSse/{uid}") + public SseEmitter createConnect(@PathVariable String uid) { + return sseClient.createSse(uid); + } + @CrossOrigin + @GetMapping("/sendMsg") + @ResponseBody + public String sseChat(@RequestBody SseMsgEntity sseMsgEntity) { + for (int i = 0; i < 10; i++) { + sseClient.sendMessage(sseMsgEntity.getUid(), "no"+i,sseMsgEntity.getMessage()); + } + return "ok"; + } + + /** + * 关闭连接 + */ + @CrossOrigin + @PostMapping("/closeSse") + public Result closeConnect(@RequestBody SseMsgEntity sseMsgEntity ){ + + sseClient.closeSse(sseMsgEntity.getUid()); + return Result.success(); + } +} diff --git a/web/src/main/java/com/zhehekeji/web/easeAi/Image.java b/web/src/main/java/com/zhehekeji/web/easeAi/Image.java new file mode 100644 index 0000000..a5f4910 --- /dev/null +++ b/web/src/main/java/com/zhehekeji/web/easeAi/Image.java @@ -0,0 +1,15 @@ +package com.zhehekeji.web.easeAi; + +import lombok.Data; + +@Data +public class Image { + private String url; + private int x; + private int y; + private int width; + private int height; + private String text; + private String type; + +} diff --git a/web/src/main/java/com/zhehekeji/web/easeAi/TestPic.java b/web/src/main/java/com/zhehekeji/web/easeAi/TestPic.java new file mode 100644 index 0000000..fbadefb --- /dev/null +++ b/web/src/main/java/com/zhehekeji/web/easeAi/TestPic.java @@ -0,0 +1,66 @@ +package com.zhehekeji.web.easeAi; + +import com.alibaba.fastjson.JSON; +import com.alibaba.fastjson.JSONObject; +import org.dromara.easyai.entity.ThreeChannelMatrix; +import org.dromara.easyai.yolo.*; + +import javax.annotation.Resource; +import java.io.BufferedWriter; +import java.io.FileReader; +import java.io.FileWriter; +import java.io.IOException; +import java.nio.file.Files; +import java.nio.file.Path; +import java.nio.file.Paths; +import java.util.ArrayList; +import java.util.List; + +public class TestPic { + @Resource + private YoloConfig yoloConfig; + public static void main(String[] args) { + + } + static public void writeModel(String json, String path) { + // 目标文件夹路径 + Path folderPath = Paths.get(path); + + try { + // 创建文件夹及所有上级文件夹 + Files.createDirectories(folderPath.getParent()); + System.out.println("文件夹已创建:" + folderPath); + } catch (IOException e) { + e.printStackTrace(); + System.out.println("创建文件夹失败!"); + } + try (BufferedWriter writer = new BufferedWriter(new FileWriter(path))) { + // 写入字符到文件 + writer.write(json); + writer.newLine(); // 写入换行符 + System.out.println("内容已成功写入文件。"); + } catch (IOException e) { + e.printStackTrace(); + } + } + + public static YoloModel readModelParameter(String s) { + YoloModel yoloModel = null; + try (FileReader reader = new FileReader(s)) { + // 读取JSON文件内容 + StringBuilder stringBuilder = new StringBuilder(); + int i; + while ((i = reader.read()) != -1) { + stringBuilder.append((char) i); + } + String jsonString = stringBuilder.toString(); + + // 将 JSON 字符串转换为 Person 对象 + yoloModel = JSON.parseObject(jsonString, YoloModel.class); + + } catch (IOException e) { + e.printStackTrace(); + } + return yoloModel; + } +} diff --git a/web/src/main/java/com/zhehekeji/web/entity/Camera.java b/web/src/main/java/com/zhehekeji/web/entity/Camera.java index e599dfc..1f2ef81 100644 --- a/web/src/main/java/com/zhehekeji/web/entity/Camera.java +++ b/web/src/main/java/com/zhehekeji/web/entity/Camera.java @@ -9,6 +9,7 @@ import io.swagger.annotations.ApiModelProperty; import lombok.Data; import java.time.LocalDateTime; +import java.util.List; @Data @TableName("`camera`") @@ -19,6 +20,8 @@ public class Camera { private String name; + private String type; + private String ip; private Integer port; @@ -35,10 +38,14 @@ public class Camera { private String status; private Integer rtcServerPort; + + private String channel; @ApiModelProperty(value = "预置点 增长值",hidden = true) private Integer ptzId; @JsonFormat(pattern="yyyy-MM-dd HH:mm:ss") private LocalDateTime updateTime; + @TableField(exist = false) + private List cameraIOs; } diff --git a/web/src/main/java/com/zhehekeji/web/entity/CameraIO.java b/web/src/main/java/com/zhehekeji/web/entity/CameraIO.java index 1d6ca73..89e3343 100644 --- a/web/src/main/java/com/zhehekeji/web/entity/CameraIO.java +++ b/web/src/main/java/com/zhehekeji/web/entity/CameraIO.java @@ -1,6 +1,7 @@ package com.zhehekeji.web.entity; import com.baomidou.mybatisplus.annotation.IdType; +import com.baomidou.mybatisplus.annotation.TableField; import com.baomidou.mybatisplus.annotation.TableId; import com.baomidou.mybatisplus.annotation.TableName; import com.fasterxml.jackson.annotation.JsonFormat; @@ -18,6 +19,7 @@ public class CameraIO { private Integer cameraId; + @TableField("code") private String code; private String name; diff --git a/web/src/main/java/com/zhehekeji/web/entity/CameraIOConfig.java b/web/src/main/java/com/zhehekeji/web/entity/CameraIOConfig.java index 231bc68..78356b3 100644 --- a/web/src/main/java/com/zhehekeji/web/entity/CameraIOConfig.java +++ b/web/src/main/java/com/zhehekeji/web/entity/CameraIOConfig.java @@ -14,6 +14,7 @@ public class CameraIOConfig { @TableId(type = IdType.AUTO) private Integer id; + private String name; private String code; diff --git a/web/src/main/java/com/zhehekeji/web/entity/DeviceResp.java b/web/src/main/java/com/zhehekeji/web/entity/DeviceResp.java new file mode 100644 index 0000000..ec24855 --- /dev/null +++ b/web/src/main/java/com/zhehekeji/web/entity/DeviceResp.java @@ -0,0 +1,17 @@ +package com.zhehekeji.web.entity; + +import lombok.Data; + +import java.util.List; + +@Data +public class DeviceResp { + private String title; + private String key; + private List children; + private Integer id; + private String name; + private Camera camera; + private CameraIO cameraIO; + +} diff --git a/web/src/main/java/com/zhehekeji/web/entity/SseMsgEntity.java b/web/src/main/java/com/zhehekeji/web/entity/SseMsgEntity.java new file mode 100644 index 0000000..23e19e1 --- /dev/null +++ b/web/src/main/java/com/zhehekeji/web/entity/SseMsgEntity.java @@ -0,0 +1,15 @@ +package com.zhehekeji.web.entity; + +import lombok.Data; + +@Data +public class SseMsgEntity { + private String messageId; + private String message; + private String uid; + private String device; + private Integer cameraId; + private CameraIO cameraIO; + private Camera camera; + private String code; +} diff --git a/web/src/main/java/com/zhehekeji/web/service/CameraService.java b/web/src/main/java/com/zhehekeji/web/service/CameraService.java index dfba0e5..abf76c5 100644 --- a/web/src/main/java/com/zhehekeji/web/service/CameraService.java +++ b/web/src/main/java/com/zhehekeji/web/service/CameraService.java @@ -1,6 +1,7 @@ package com.zhehekeji.web.service; import com.alibaba.excel.EasyExcel; +import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper; import com.github.pagehelper.PageHelper; import com.github.pagehelper.PageInfo; import com.zhehekeji.core.util.Assert; @@ -8,6 +9,7 @@ import com.zhehekeji.web.config.ConfigProperties; import com.zhehekeji.web.entity.Camera; import com.zhehekeji.web.entity.CameraIO; import com.zhehekeji.web.entity.CameraIOConfig; +import com.zhehekeji.web.entity.DeviceResp; import com.zhehekeji.web.lib.CameraConnMap; import com.zhehekeji.web.lib.CameraControlLoginModule; import com.zhehekeji.web.lib.CameraControlModule; @@ -23,6 +25,7 @@ import com.zhehekeji.web.pojo.camera.IOImport; import com.zhehekeji.web.pojo.street.StreetSearch; import io.swagger.models.auth.In; import lombok.extern.slf4j.Slf4j; +import org.apache.logging.log4j.util.Strings; import org.springframework.cache.annotation.CacheEvict; import org.springframework.cache.annotation.Cacheable; import org.springframework.dao.DuplicateKeyException; @@ -33,8 +36,10 @@ import org.springframework.web.multipart.MultipartFile; import javax.annotation.Resource; import java.io.IOException; import java.time.LocalDateTime; +import java.util.ArrayList; import java.util.HashMap; import java.util.List; +import java.util.Map; import java.util.concurrent.CountDownLatch; import java.util.stream.Collectors; @@ -125,6 +130,52 @@ public class CameraService { return new PageInfo<>(cameras); } + public List getDeviceTree() { + List cameras = cameraMapper.selectList(new QueryWrapper<>()); + List cameraIOS = ioMapper.selectList(new QueryWrapper<>()); + Map> mapCameraIo = cameraIOS.stream().collect(Collectors.groupingBy(CameraIO::getCameraId)); + Map> map = cameras.stream() + .peek(camera ->{ + camera.setCameraIOs(mapCameraIo.get(camera.getId())); + if(Strings.isBlank(camera.getType())){ + camera.setType("其他"); + } + } ) + .collect(Collectors.groupingBy(Camera::getType)); + List deviceResps = new ArrayList<>(); + //第一级 + map.forEach((key,value) -> { + DeviceResp deviceResp = new DeviceResp(); + deviceResp.setName(key); + deviceResp.setKey(key); + deviceResp.setTitle(key); + deviceResp.setChildren(new ArrayList<>()); + //第二级 + for (Camera camera: value){ + DeviceResp deviceResp2 = new DeviceResp(); + deviceResp2.setKey(key+"-"+camera.getId()); + deviceResp2.setTitle(camera.getName()); + deviceResp2.setId(camera.getId()); + deviceResp2.setCamera(camera); + deviceResp2.setChildren(new ArrayList<>()); + //第三级 + for (CameraIO cameraIO: mapCameraIo.get(camera.getId())){ + DeviceResp deviceResp3 = new DeviceResp(); + deviceResp3.setKey(key+"-"+camera.getId()+"-"+cameraIO.getId()); + + deviceResp3.setTitle(cameraIO.getName()); + deviceResp3.setId(cameraIO.getId()); + deviceResp3.setCamera(camera); + deviceResp3.setCameraIO(cameraIO); + deviceResp2.getChildren().add(deviceResp3); + } + deviceResp.getChildren().add(deviceResp2); + } + deviceResps.add(deviceResp); + }); + return deviceResps; + } + public class StatusThread extends Thread{ private Camera camera; private CountDownLatch latch; @@ -285,6 +336,7 @@ public class CameraService { cameraIO.setPtzId(ptzId); cameraIO.setCode(code); conver(cameraIO,0); + //ioMapper.insert(cameraIO); try { ioMapper.insert(cameraIO); }catch (DuplicateKeyException e){ diff --git a/web/src/main/java/com/zhehekeji/web/service/InitService.java b/web/src/main/java/com/zhehekeji/web/service/InitService.java index 5d88ad3..649aa6b 100644 --- a/web/src/main/java/com/zhehekeji/web/service/InitService.java +++ b/web/src/main/java/com/zhehekeji/web/service/InitService.java @@ -90,7 +90,7 @@ public class InitService implements ApplicationRunner { }); LPLicense.createLicKeyIfNotExist(); //plc连接 - if(configProperties.getServerMode() == 0){ + /*if(configProperties.getServerMode() == 0){ log.info("PLC TCP MODE"); //plc 连接状态初始化 List streets = streetMapper.selectByMap(new HashMap<>(0)); @@ -120,7 +120,7 @@ public class InitService implements ApplicationRunner { } } NettyServer nettyServer = new NettyServer(); - nettyServer.CreateNettyServer(9040); + nettyServer.CreateNettyServer(9040);*/ TaskDelayExecutor.runMp4DownloadExecutor(); GetPhotoDelayExecutor.runExecutor(streetMapper.selectList(new QueryWrapper<>()),plcService); } diff --git a/web/src/main/java/com/zhehekeji/web/util/SseClient.java b/web/src/main/java/com/zhehekeji/web/util/SseClient.java new file mode 100644 index 0000000..394a134 --- /dev/null +++ b/web/src/main/java/com/zhehekeji/web/util/SseClient.java @@ -0,0 +1,120 @@ +package com.zhehekeji.web.util; + +import lombok.extern.slf4j.Slf4j; +import org.apache.logging.log4j.util.Strings; +import org.springframework.stereotype.Component; +import org.springframework.web.servlet.mvc.method.annotation.SseEmitter; + +import java.io.IOException; +import java.util.Map; +import java.util.concurrent.ConcurrentHashMap; + +@Slf4j +@Component +public class SseClient { + private static final Map sseEmitterMap = new ConcurrentHashMap<>(); + /** + * 创建连接 + */ + public SseEmitter createSse(String uid) { + //默认30秒超时,设置为0L则永不超时 + SseEmitter sseEmitter = new SseEmitter(0l); + //完成后回调 + sseEmitter.onCompletion(() -> { + log.info("[{}]结束连接...................", uid); + sseEmitterMap.remove(uid); + }); + //超时回调 + sseEmitter.onTimeout(() -> { + log.info("[{}]连接超时...................", uid); + }); + //异常回调 + sseEmitter.onError( + throwable -> { + try { + log.info("[{}]连接异常,{}", uid, throwable.toString()); + sseEmitter.send(SseEmitter.event() + .id(uid) + .name("发生异常!") + .data("发生异常请重试!") + .reconnectTime(3000)); + sseEmitterMap.put(uid, sseEmitter); + } catch (IOException e) { + e.printStackTrace(); + } + } + ); + try { + sseEmitter.send(SseEmitter.event().reconnectTime(5000)); + } catch (IOException e) { + e.printStackTrace(); + } + sseEmitterMap.put(uid, sseEmitter); + log.info("[{}]创建sse连接成功!", uid); + return sseEmitter; + } + + /** + * 给指定用户发送消息 + * + */ + public boolean sendMessage(String uid,String messageId, String message) { + if (Strings.isBlank(message)) { + log.info("参数异常,msg为null", uid); + return false; + } + SseEmitter sseEmitter = sseEmitterMap.get(uid); + if (sseEmitter == null) { + log.info("消息推送失败uid:[{}],没有创建连接,请重试。", uid); + return false; + } + try { + sseEmitter.send(SseEmitter.event().id(messageId).reconnectTime(1*60*1000L).data(message)); + log.info("用户{},消息id:{},推送成功:{}", uid,messageId, message); + return true; + }catch (Exception e) { + sseEmitterMap.remove(uid); + log.info("用户{},消息id:{},推送异常:{}", uid,messageId, e.getMessage()); + sseEmitter.complete(); + return false; + } + } + public void sendAll(String message) { + if (Strings.isBlank(message)) { + log.info("参数异常,msg为null", message); + + } +// SseEmitter sseEmitter = sseEmitterMap.get(uid); + for (String sseEmitterStr :sseEmitterMap.keySet()){ + String messageId = "all"; + try { + sseEmitterMap.get(sseEmitterStr).send(SseEmitter.event().id(messageId).reconnectTime(1*60*1000L).data(message)); + log.info("用户{},消息id:{},推送成功:{}", sseEmitterMap.get(sseEmitterStr),messageId, message); + + }catch (Exception e) { + sseEmitterMap.remove( sseEmitterMap.get(sseEmitterStr)); + log.info("用户{},消息id:{},推送异常:{}", sseEmitterMap.get(sseEmitterStr),messageId, e.getMessage()); + sseEmitterMap.get(sseEmitterStr).complete(); + + } + } + + + } + + /** + * 断开 + * @param uid + */ + public void closeSse(String uid){ + if (sseEmitterMap.containsKey(uid)) { + SseEmitter sseEmitter = sseEmitterMap.get(uid); + sseEmitter.complete(); + sseEmitterMap.remove(uid); + }else { + log.info("用户{} 连接已关闭",uid); + } + + } + +} \ No newline at end of file