lyhzzz 2 ay önce
ebeveyn
işleme
b921e80f40
36 değiştirilmiş dosya ile 962 ekleme ve 101 silme
  1. 3 1
      src/main/java/com/fdkankan/fusion/common/ResultCode.java
  2. 0 4
      src/main/java/com/fdkankan/fusion/common/util/DateUtils.java
  3. 3 2
      src/main/java/com/fdkankan/fusion/common/util/ShellUtil.java
  4. 1 1
      src/main/java/com/fdkankan/fusion/config/FusionConfig.java
  5. 2 1
      src/main/java/com/fdkankan/fusion/config/SaTokenConfigure.java
  6. 10 0
      src/main/java/com/fdkankan/fusion/controller/CaseController.java
  7. 11 17
      src/main/java/com/fdkankan/fusion/controller/CaseFilesController.java
  8. 7 58
      src/main/java/com/fdkankan/fusion/controller/CaseFusionController.java
  9. 30 3
      src/main/java/com/fdkankan/fusion/controller/CaseOverviewController.java
  10. 4 2
      src/main/java/com/fdkankan/fusion/controller/CaseTabulationController.java
  11. 21 0
      src/main/java/com/fdkankan/fusion/controller/DictFileCaseController.java
  12. 36 0
      src/main/java/com/fdkankan/fusion/controller/DownOfflinePackageController.java
  13. 1 1
      src/main/java/com/fdkankan/fusion/down/CaseDownService.java
  14. 430 0
      src/main/java/com/fdkankan/fusion/down/FusionDownService.java
  15. 45 0
      src/main/java/com/fdkankan/fusion/entity/DictFileCase.java
  16. 2 2
      src/main/java/com/fdkankan/fusion/generate/AutoGenerate.java
  17. 26 0
      src/main/java/com/fdkankan/fusion/httpClient/HaixinInterceptor.java
  18. 33 0
      src/main/java/com/fdkankan/fusion/httpClient/HaixinService.java
  19. 20 0
      src/main/java/com/fdkankan/fusion/httpClient/address/HaixinAddressSource.java
  20. 22 0
      src/main/java/com/fdkankan/fusion/httpClient/client/HaixinClient.java
  21. 1 0
      src/main/java/com/fdkankan/fusion/httpClient/request/ManageSceneParam.java
  22. 22 0
      src/main/java/com/fdkankan/fusion/httpClient/response/HaixinCaseInfo.java
  23. 18 0
      src/main/java/com/fdkankan/fusion/mapper/IDictFileCaseMapper.java
  24. 8 0
      src/main/java/com/fdkankan/fusion/request/DownParam.java
  25. 2 0
      src/main/java/com/fdkankan/fusion/service/ICaseFusionService.java
  26. 4 0
      src/main/java/com/fdkankan/fusion/service/ICaseOverviewService.java
  27. 1 0
      src/main/java/com/fdkankan/fusion/service/ICaseTabulationService.java
  28. 17 0
      src/main/java/com/fdkankan/fusion/service/IDictFileCaseService.java
  29. 4 0
      src/main/java/com/fdkankan/fusion/service/IDictFileService.java
  30. 1 1
      src/main/java/com/fdkankan/fusion/service/IFusionGuideService.java
  31. 70 0
      src/main/java/com/fdkankan/fusion/service/impl/CaseFusionServiceImpl.java
  32. 37 7
      src/main/java/com/fdkankan/fusion/service/impl/CaseOverviewServiceImpl.java
  33. 8 0
      src/main/java/com/fdkankan/fusion/service/impl/CaseTabulationServiceImpl.java
  34. 48 0
      src/main/java/com/fdkankan/fusion/service/impl/DictFileCaseServiceImpl.java
  35. 9 1
      src/main/java/com/fdkankan/fusion/service/impl/DictFileServiceImpl.java
  36. 5 0
      src/main/resources/mapper/fusion/DictFileCaseMapper.xml

+ 3 - 1
src/main/java/com/fdkankan/fusion/common/ResultCode.java

@@ -82,7 +82,9 @@ public enum ResultCode {
     FUSION_NOT_PERMISSION2(40111,"您没有权限,请联系管理员开通"),
     REMOVE_ERROR(60041, "至少保留一个实景三维/多元融合场景"),
 
-;
+    SCENE_BUILDING(60042, "场景计算中"),
+
+    ;
 
 
 

+ 0 - 4
src/main/java/com/fdkankan/fusion/common/util/DateUtils.java

@@ -89,10 +89,6 @@ public class DateUtils {
     }
 
 
-    public static void main(String[] args) {
-       // System.out.println(getMonthdateList(getYearAgo(),getMonthStr(new Date())));
-        System.out.println(getHoursTime(new Date()));
-    }
 
     public static String dateStr() {
         SimpleDateFormat df = new SimpleDateFormat("yyyyMMdd");

+ 3 - 2
src/main/java/com/fdkankan/fusion/common/util/ShellUtil.java

@@ -31,7 +31,8 @@ public class ShellUtil {
         try {
             // 执行命令, 返回一个子进程对象(命令在子进程中执行)
             log.info("执行cmd:{}",cmd);
-            process = Runtime.getRuntime().exec(cmd);
+            String[] cmds = new String[]{"/bin/sh", "-c", cmd};
+            process = Runtime.getRuntime().exec(cmds);
             // 获取命令执行结果, 有两个结果: 正常的输出 和 错误的输出(PS: 子进程的输出就是主进程的输入)
             //处理InputStream的线程
             threadRun(process);
@@ -119,7 +120,7 @@ public class ShellUtil {
 
     public static void zip(String zipPath, String dataPath) {
         log.info("打包zip开始");
-        String command = "zip -r -m " + zipPath + "  " ;
+        String command = "cd " + dataPath + " &&zip -r -m -p " + zipPath + " * " ;
         execCmd(command);
         log.info("打包zip完毕:" + command);
     }

+ 1 - 1
src/main/java/com/fdkankan/fusion/config/FusionConfig.java

@@ -19,7 +19,7 @@ public class FusionConfig {
     /**
      * 推送绘图平面图地址  http://1.119.159.10:58080/ecs/api/panoramicImageService/submitDrawing
      */
-    @Value("${fusion.push-draw.url}")
+    @Value("${haixin.basePath}")
     private String pushDrawUrl;
 
     @Value("${to-haixin.server-url}")

+ 2 - 1
src/main/java/com/fdkankan/fusion/config/SaTokenConfigure.java

@@ -75,7 +75,8 @@ public class SaTokenConfigure {
                                 "/**/upload/**",
                                 "/**/sceneListPost/**",
                                 "/**/mapConfig/**",
-                                "/**/notAuth/**"
+                                "/**/notAuth/**",
+                                "/**/offlinePackage/**"
                         );
                         match1.check(r ->checkCaseAuth(caseId,fusionId,pageType));
 

+ 10 - 0
src/main/java/com/fdkankan/fusion/controller/CaseController.java

@@ -55,6 +55,8 @@ public class CaseController extends BaseController{
     IJyUserService jyUserService;
     @Autowired
     FdService fdService;
+    @Autowired
+    ICaseOverviewService caseOverviewService;
 
     @PostMapping("/list")
     public ResultData list(@RequestBody CaseParam param ){
@@ -73,6 +75,14 @@ public class CaseController extends BaseController{
 
     @PostMapping("/sceneListPost")
     public ResultData sceneListPost(@RequestBody ManageSceneParam param ){
+        if(param.getOverviewId() != null){
+            CaseOverview caseOverview = caseOverviewService.getById(param.getOverviewId());
+            if(caseOverview!=null && StringUtils.isNotBlank(caseOverview.getNum())){
+                param.setNumList(Arrays.asList(caseOverview.getNum()));
+                Page<ScenePlus> page = scenePlusService.pageList(param);
+                return ResultData.ok(PageInfo.PageInfo(page));
+            }
+        }
         if(param.getCaseId() != null){
             List<CaseNumEntity> byCaseId = caseNumService.getByCaseId(param.getCaseId());
             List<String> numList = byCaseId.stream().map(CaseNumEntity::getNum).collect(Collectors.toList());

+ 11 - 17
src/main/java/com/fdkankan/fusion/controller/CaseFilesController.java

@@ -48,6 +48,8 @@ public class CaseFilesController extends BaseController{
     ICaseOverviewService caseOverviewService;
     @Autowired
     ICaseTabulationService caseTabulationService;
+    @Autowired
+    IDictFileCaseService dictFileCaseService;
 
     @Value("${spring.profiles.active}")
     private String environment;
@@ -69,13 +71,16 @@ public class CaseFilesController extends BaseController{
         if(param.getCaseId() == null || param.getUploadId() == null || param.getFilesTypeId() == null){
             throw new BusinessException(ResultCode.MISSING_REQUIRED_PARAMETERS);
         }
+        return ResultData.ok(addCaseFile(param));
+    }
+    private CaseFiles  addCaseFile(AddByMediaLibraryParam param){
         CommonUpload commonUpload = commonUploadService.getById(param.getUploadId());
         if(commonUpload == null || StringUtils.isBlank(commonUpload.getFileUrl())){
             throw new BusinessException(ResultCode.MEDIO_NOT_EXIT);
         }
         CaseFiles caseFiles = new CaseFiles();
         if(param.getFilesId() != null){
-             caseFiles = caseFilesService.getById(param.getFilesId());
+            caseFiles = caseFilesService.getById(param.getFilesId());
         }
         caseFiles.setCaseId(param.getCaseId());
         caseFiles.setFilesTypeId(param.getFilesTypeId());
@@ -87,7 +92,9 @@ public class CaseFilesController extends BaseController{
             caseFiles.setOgnFilesUrl(param.getOgnFileUrl());
         }
         caseFilesService.saveOrUpdate(caseFiles);
-        return ResultData.ok(caseFiles);
+
+        dictFileCaseService.add(param.getUploadId(),param.getCaseId());
+        return caseFiles;
     }
     @PostMapping("/addByMediaLibrarys")
     @PushJm(event_content = "关联媒体库文件")
@@ -97,21 +104,8 @@ public class CaseFilesController extends BaseController{
         }
         List<CaseFiles> caseFilesList = new ArrayList<>();
         for (Integer uploadId : param.getUploadIds()) {
-            CommonUpload commonUpload = commonUploadService.getById(uploadId);
-            if(commonUpload == null || StringUtils.isBlank(commonUpload.getFileUrl())){
-                throw new BusinessException(ResultCode.MEDIO_NOT_EXIT);
-            }
-            CaseFiles caseFiles = new CaseFiles();
-            if(param.getFilesId() != null){
-                caseFiles = caseFilesService.getById(param.getFilesId());
-            }
-            caseFiles.setCaseId(param.getCaseId());
-            caseFiles.setFilesTypeId(param.getFilesTypeId());
-            caseFiles.setFilesTitle(commonUpload.getFileName());
-            caseFiles.setFilesUrl(commonUpload.getFileUrl());
-            caseFiles.setContent(param.getContent());
-            caseFiles.setImgType(param.getImgType());
-            caseFilesList.add(caseFiles);
+            param.setUploadId(uploadId);
+            caseFilesList.add( addCaseFile(param));
         }
         if(!caseFilesList.isEmpty()){
             caseFilesService.saveOrUpdateBatch(caseFilesList);

+ 7 - 58
src/main/java/com/fdkankan/fusion/controller/CaseFusionController.java

@@ -8,12 +8,15 @@ import com.fdkankan.fusion.common.ResultCode;
 import com.fdkankan.fusion.common.ResultData;
 import com.fdkankan.fusion.common.util.CameraUtil;
 import com.fdkankan.fusion.common.util.FileWriterUtil;
+import com.fdkankan.fusion.down.FusionDownService;
 import com.fdkankan.fusion.entity.*;
 import com.fdkankan.fusion.entity.jsonEntity.Transform;
 import com.fdkankan.fusion.exception.BusinessException;
+import com.fdkankan.fusion.request.DownParam;
 import com.fdkankan.fusion.request.FusionParam;
 import com.fdkankan.fusion.request.SceneNumParam;
 import com.fdkankan.fusion.response.CaseFusionVo;
+import com.fdkankan.fusion.response.DownVo;
 import com.fdkankan.fusion.response.FusionNumVo;
 import com.fdkankan.fusion.response.SceneVo;
 import com.fdkankan.fusion.service.*;
@@ -57,9 +60,12 @@ public class CaseFusionController extends BaseController{
     IScenePlusExtService scenePlusExtService;
     @Autowired
     ICommonUploadService commonUploadService;
+    @Autowired
+    FusionDownService fusionDownService;
+
     @GetMapping("/list")
     public ResultData allList(@RequestParam(required = false) Integer fusionId){
-        return ResultData.ok(getSceneListVo(fusionId));
+        return ResultData.ok(caseFusionService.getSceneListVo(fusionId));
     }
 
 
@@ -148,62 +154,5 @@ public class CaseFusionController extends BaseController{
 
 
 
-
-    private List<FusionNumVo> getSceneListVo(Integer fusionId) {
-        List<FusionNumVo> sceneVos = new ArrayList<>();
-        List<FusionNum> fusionNumList = fusionNumService.getByFusionId(fusionId);
-
-        List<Integer> modelIds = fusionNumList.stream().map(FusionNum::getModelId).collect(Collectors.toList());
-        List<Model> listByModelIds = modelService.getListByModelIds(modelIds);
-        HashMap<Integer,Model> modelMap = new HashMap<>();
-        listByModelIds.stream().forEach(e -> modelMap.put(e.getModelId(),e));
-
-
-        List<String> numList = listByModelIds.stream().filter(e -> e.getNum() != null).map(Model::getNum).collect(Collectors.toList());
-        List<ScenePlus> scenePlusList = scenePlusService.getByNumList(numList);
-        HashMap<String,ScenePlus> map = new HashMap<>();
-        scenePlusList.stream().forEach(e -> map.put(e.getNum(),e));
-
-        List<Long> plusIds = scenePlusList.stream().map(ScenePlus::getId).collect(Collectors.toList());
-        List<ScenePlusExt> extList = scenePlusExtService.getByPlusIds(plusIds);
-        HashMap<Long,ScenePlusExt> mapext = new HashMap<>();
-        extList.stream().forEach(e -> mapext.put(e.getPlusId(),e));
-
-
-        for (FusionNum fusionNum : fusionNumList) {
-            Transform transform = JSONObject.parseObject(fusionNum.getTransform(),Transform.class);
-            FusionNumVo vo = new FusionNumVo();
-            vo.setTransform(transform);
-            BeanUtils.copyProperties(fusionNum,vo);
-            SceneVo sceneVo = new SceneVo();
-            Model model = modelMap.get(fusionNum.getModelId());
-            if(model != null){
-                BeanUtils.copyProperties(model,sceneVo);
-                if(model.getNum() != null ){
-                    ScenePlus scenePlus = map.get(model.getNum());
-                    if(scenePlus != null){
-                        BeanUtils.copyProperties(scenePlus,sceneVo);
-                        sceneVo.setStatus(scenePlus.getSceneStatus() == -2 ? 2:scenePlus.getSceneStatus());
-                        sceneVo.setName(scenePlus.getTitle());
-                        sceneVo.setSceneName(scenePlus.getTitle());
-                        sceneVo.setCreateTime(scenePlus.getCreateTime());
-                        ScenePlusExt scenePlusExt = mapext.get(scenePlus.getId());
-                        if(scenePlusExt != null){
-                            sceneVo.setRtkLocation(scenePlusExt.getRtkLocation());
-                            sceneVo.setOrientation(scenePlusExt.getOrientation());
-                        }
-                    }
-                }else {
-                    sceneVo.setStatus(2);
-                }
-                sceneVo.setSourceName(CameraUtil.getSourceName(model.getType()));
-            }
-            vo.setSceneData(sceneVo);
-            sceneVos.add(vo);
-        }
-
-        return sceneVos;
-    }
-
 }
 

+ 30 - 3
src/main/java/com/fdkankan/fusion/controller/CaseOverviewController.java

@@ -3,6 +3,7 @@ package com.fdkankan.fusion.controller;
 
 import cn.dev33.satoken.stp.StpUtil;
 import cn.hutool.core.date.DateUtil;
+import com.alibaba.fastjson.JSONObject;
 import com.fdkankan.fusion.aop.PushJm;
 import com.fdkankan.fusion.common.FilePath;
 import com.fdkankan.fusion.common.ResultCode;
@@ -16,10 +17,14 @@ import com.fdkankan.fusion.entity.CaseOverview;
 import com.fdkankan.fusion.entity.CaseTabulation;
 import com.fdkankan.fusion.entity.ScenePlus;
 import com.fdkankan.fusion.exception.BusinessException;
+import com.fdkankan.fusion.httpClient.HaixinService;
+import com.fdkankan.fusion.httpClient.client.HaixinClient;
 import com.fdkankan.fusion.httpClient.client.OtherClient;
+import com.fdkankan.fusion.httpClient.response.HaixinCaseInfo;
 import com.fdkankan.fusion.request.ExportOverviewParam;
 import com.fdkankan.fusion.service.*;
 import org.apache.commons.lang3.StringUtils;
+import org.apache.ibatis.annotations.Param;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.web.bind.annotation.*;
 
@@ -53,6 +58,8 @@ public class CaseOverviewController extends BaseController{
     UploadToOssUtil uploadToOssUtil;
     @Autowired
     IScenePlusService scenePlusService;
+    @Autowired
+    HaixinService haixinService;
 
 
     @GetMapping("/getByCaseId")
@@ -96,10 +103,20 @@ public class CaseOverviewController extends BaseController{
             if(scenePlus == null){
                 throw new BusinessException(ResultCode.SCENE_NOT_EXIST);
             }
-            CaseEntity caseEntity = caseService.getKnumber(scenePlus.getKNo());
-            if(caseEntity!=null){
-                caseOverview.setCaseId(caseEntity.getCaseId());
+            if(StringUtils.isNotBlank(scenePlus.getKNo())){
+                CaseEntity caseEntity = caseService.getKnumber(scenePlus.getKNo());
+                if(caseEntity!=null){
+                    caseOverview.setCaseId(caseEntity.getCaseId());
+
+                }
+                //“[发案时间]”+[发案地点]+[案件类别]+现场平面示意图
+                HaixinCaseInfo haixinCaseInfo = haixinService.queryScene(scenePlus.getKNo());
+                if(haixinCaseInfo != null && StringUtils.isNotBlank(haixinCaseInfo.getCrimeTimeBegin())){
+                    String date = DateUtil.format(new Date(Long.valueOf(haixinCaseInfo.getCrimeTimeBegin())),"yyyy.MM.dd");
+                    caseOverview.setTitle("“"+date+"”"+haixinCaseInfo.getCaseLocation()+haixinCaseInfo.getCaseTypeName()+"现场平面示意图");
+                }
             }
+
         }
         if(caseOverview.getId() ==null && StringUtils.isBlank(caseOverview.getTitle())){
             Long no = caseOverviewService.getNo(getSysUserId());
@@ -144,5 +161,15 @@ public class CaseOverviewController extends BaseController{
         caseOverviewService.export(param);
         return ResultData.ok();
     }
+
+
+
+    @GetMapping("/settingInfo")
+    public ResultData settingInfo (@RequestParam(required = false) String num){
+        if(StringUtils.isBlank(num)){
+            throw new BusinessException(ResultCode.MISSING_REQUIRED_PARAMETERS);
+        }
+        return ResultData.ok(caseOverviewService.settingInfo(num));
+    }
 }
 

+ 4 - 2
src/main/java/com/fdkankan/fusion/controller/CaseTabulationController.java

@@ -9,6 +9,7 @@ import com.fdkankan.fusion.common.util.MD5Checksum;
 import com.fdkankan.fusion.config.FusionConfig;
 import com.fdkankan.fusion.entity.*;
 import com.fdkankan.fusion.exception.BusinessException;
+import com.fdkankan.fusion.httpClient.client.HaixinClient;
 import com.fdkankan.fusion.httpClient.client.OtherClient;
 import com.fdkankan.fusion.request.ExportOverviewParam;
 import com.fdkankan.fusion.service.ICaseOverviewService;
@@ -40,7 +41,7 @@ public class CaseTabulationController extends BaseController{
     @Autowired
     ICaseTabulationService caseTabulationService;
     @Autowired
-    OtherClient otherClient;
+    HaixinClient haixinClient;
     @Autowired
     ICaseService caseService;
     @Autowired
@@ -115,7 +116,7 @@ public class CaseTabulationController extends BaseController{
                     map.put("fileUrl",caseTabulation.getListCover());
                     map.put("vendor","A0BF");// 供应商类型
                     map.put("serverUrl",fusionConfig.getServerUrl());// 供应商类型
-                    otherClient.postJson(fusionConfig.getPushDrawUrl(),map);
+                    haixinClient.submitDrawing(map);
                 }
             }
         }catch (Exception e){
@@ -132,5 +133,6 @@ public class CaseTabulationController extends BaseController{
         caseTabulationService.removeById(caseTabulation.getId());
         return ResultData.ok();
     }
+
 }
 

+ 21 - 0
src/main/java/com/fdkankan/fusion/controller/DictFileCaseController.java

@@ -0,0 +1,21 @@
+package com.fdkankan.fusion.controller;
+
+
+import org.springframework.web.bind.annotation.RequestMapping;
+
+import org.springframework.web.bind.annotation.RestController;
+
+/**
+ * <p>
+ *  前端控制器
+ * </p>
+ *
+ * @author 
+ * @since 2025-10-14
+ */
+@RestController
+@RequestMapping("/fusion/dictFileCase")
+public class DictFileCaseController {
+
+}
+

+ 36 - 0
src/main/java/com/fdkankan/fusion/controller/DownOfflinePackageController.java

@@ -1,12 +1,21 @@
 package com.fdkankan.fusion.controller;
 
 
+import com.fdkankan.fusion.common.ResultCode;
 import com.fdkankan.fusion.common.ResultData;
 import com.fdkankan.fusion.down.CaseDownService;
+import com.fdkankan.fusion.down.FusionDownService;
+import com.fdkankan.fusion.exception.BusinessException;
+import com.fdkankan.fusion.request.DownParam;
 import com.fdkankan.fusion.response.DownVo;
+import com.fdkankan.fusion.response.FusionNumVo;
+import com.fdkankan.fusion.response.SceneVo;
+import com.fdkankan.fusion.service.ICaseFusionService;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.web.bind.annotation.*;
 
+import java.util.List;
+
 
 /**
  * <p>
@@ -22,6 +31,10 @@ public class DownOfflinePackageController {
 
     @Autowired
     CaseDownService caseDownService;
+    @Autowired
+    FusionDownService fusionDownService;
+    @Autowired
+    ICaseFusionService caseFusionService;
 
     @GetMapping("/checkDown")
     public ResultData checkDown(@RequestParam(required = false) Integer caseId){
@@ -38,5 +51,28 @@ public class DownOfflinePackageController {
     public ResultData process(@RequestParam(required = false) Integer caseId){
         return ResultData.ok(caseDownService.process(caseId));
     }
+
+
+    @PostMapping("/downOfflineFusion")
+    public ResultData downOfflineFusion(@RequestBody DownParam param){
+        if(param.getFusionId() == null ){
+            throw new BusinessException(ResultCode.MISSING_REQUIRED_PARAMETERS);
+        }
+        List<FusionNumVo> fusionNumVos = caseFusionService.getSceneListVo(param.getFusionId());
+        for (FusionNumVo fusionNumVo : fusionNumVos) {
+            SceneVo sceneData = fusionNumVo.getSceneData();
+            if(sceneData.getType() !=3 && sceneData.getStatus() !=2){
+                throw new BusinessException(ResultCode.SCENE_BUILDING);
+            }
+        }
+        fusionDownService.downOffline(param.getFusionId());
+        DownVo downVo = new DownVo();
+        downVo.setDownloadStatus(1);
+        return ResultData.ok(downVo);
+    }
+    @GetMapping("/downFusionProcess")
+    public ResultData downFusionProcess(@RequestParam(required = false) Integer fusionId){
+        return ResultData.ok(fusionDownService.process(fusionId));
+    }
 }
 

+ 1 - 1
src/main/java/com/fdkankan/fusion/down/CaseDownService.java

@@ -181,7 +181,7 @@ public class CaseDownService {
             String path = "/mnt/fusion/offline";
             String name = "offline_"+ caseId;
             String zipName = path+File.separator+name+".zip";
-            ShellUtil.zipOffline(zipName,name);
+            ShellUtil.zip(zipName,name);
             setRedisProcess(caseId,70);
             //上传oss
             String ossUrl = zipName.replace("/mnt/", "");

+ 430 - 0
src/main/java/com/fdkankan/fusion/down/FusionDownService.java

@@ -0,0 +1,430 @@
+package com.fdkankan.fusion.down;
+
+import cn.hutool.core.io.FileUtil;
+import com.alibaba.fastjson.JSON;
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+import com.deepoove.poi.XWPFTemplate;
+import com.fdkankan.fusion.common.FilePath;
+import com.fdkankan.fusion.common.ResultData;
+import com.fdkankan.fusion.common.util.DateUtils;
+import com.fdkankan.fusion.common.util.ShellUtil;
+import com.fdkankan.fusion.common.util.UploadToOssUtil;
+import com.fdkankan.fusion.entity.*;
+import com.fdkankan.fusion.httpClient.LaserService;
+import com.fdkankan.fusion.httpClient.response.FdkkResponse;
+import com.fdkankan.fusion.request.CaseParam;
+import com.fdkankan.fusion.response.DownVo;
+import com.fdkankan.fusion.response.DownloadProcessVo;
+import com.fdkankan.fusion.response.FusionNumVo;
+import com.fdkankan.fusion.response.SceneVo;
+import com.fdkankan.fusion.service.*;
+import com.fdkankan.fusion.service.impl.DownService;
+import com.fdkankan.redis.util.RedisUtil;
+import lombok.extern.slf4j.Slf4j;
+import org.apache.commons.lang3.StringUtils;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.beans.factory.annotation.Value;
+import org.springframework.scheduling.annotation.Async;
+import org.springframework.stereotype.Service;
+
+import java.io.File;
+import java.io.FileOutputStream;
+import java.nio.charset.StandardCharsets;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.List;
+
+@Service
+@Slf4j
+public class FusionDownService {
+
+    @Value("${server.servlet.context-path}")
+    String basePath;
+
+    public static String jsonDataName = "data.json";
+    public static String caseFusionInfo =     "/caseFusion/info?fusionId=";
+    public static String caseFusionList=     "/caseFusion/list?fusionId=";
+    public static String mapConfig =     "/notAuth/getMapConfig";
+    public static String caseSettingsInfo =     "/caseSettings/info?fusionId=";
+    public static String hostIconTreeList =     "/edit/hotIcon/treeList?fusionId=";
+    public static String caseTag =      "/caseTag/allList?fusionId=";
+    public static String caseTagPoint =      "/caseTagPoint/allList?tagId=";
+    public static String fusionGuide =      "/fusionGuide/allList?fusionId=";
+    public static String fusionGuidePath =     "/fusionGuidePath/allList?guideId=";
+    public static String fusionMeter =      "/fusionMeter/allList?fusionId=";
+    public static String casePathInfoUrl =      "/casePath/info?fusionId=";
+    public static String caseAnimationUrl =      "/caseAnimation/list?fusionId=";
+    public static String laserData = "/laser/dataset/%s/getDataSet";
+    public static String laserDataSetAndControlPoint = "/laser/4dage/%s/getDataSetAndControlPoint";
+    public static String laserDataQuery = "/laser/filter/%s/query?datasetId=%s";
+
+
+    @Autowired
+    ICaseSettingsService caseSettingsService;
+    @Autowired
+    IFusionNumService fusionNumService;
+    @Autowired
+    ICaseViewService caseViewService;
+    @Autowired
+    ICaseVideoFolderService caseVideoFolderService;
+    @Autowired
+    ICaseVideoService caseVideoService;
+    @Autowired
+    ICaseFilesService caseFilesService;
+    @Autowired
+    ICaseFilesTypeService caseFilesTypeService;
+    @Autowired
+    IHotIconService hotIconService;
+    @Autowired
+    ICaseTagService caseTagService;
+    @Autowired
+    ICaseTagPointService caseTagPointService;
+    @Autowired
+    IFusionGuideService fusionGuideService;
+    @Autowired
+    IFusionGuidePathService fusionGuidePathService;
+    @Autowired
+    ICaseInquestService caseInquestService;
+    @Autowired
+    ICaseExtractDetailService caseExtractDetailService;
+    @Autowired
+    IFusionMeterService fusionMeterService;
+    @Autowired
+    IModelService modelService;
+    @Autowired
+    LaserService laserService;
+    @Autowired
+    ICaseOfflineService caseOfflineService;
+    @Autowired
+    ICaseImgService caseImgService;
+    @Autowired
+    ICaseInquestInfoService caseInquestInfoService;
+    @Autowired
+    ICasePathService casePathService;
+    @Autowired
+    ICaseFusionService caseFusionService;
+    @Autowired
+    ICaseAnimationService caseAnimationService;
+    @Autowired
+    IMapConfigService mapConfigService;
+
+    @Autowired
+    RedisUtil redisUtil;
+    public static String downProcessKey = "fusion:down:offline:process:fusionId:%s";
+
+    @Async
+    public void downOffline(Integer fusionId){
+        String caseOffPath = null;
+        String zipName = null;
+        try {
+            String redisKey = String.format(downProcessKey, fusionId);
+            if(redisUtil.hasKey(redisKey)){
+                String res = redisUtil.get(redisKey);
+                DownloadProcessVo downloadProcessVo = JSONObject.parseObject(res, DownloadProcessVo.class);
+                if(downloadProcessVo.getStatus() != 1003 && (downloadProcessVo.getPercent()== null || downloadProcessVo.getPercent() != 100)){
+                    return;
+                }
+            }
+
+            String timeKey = DateUtils.dateStr();
+            caseOffPath =FilePath.OFFLINE_PACKAGE_PATH+timeKey+fusionId ;
+
+            setRedisProcess(fusionId,0);
+            //复制前端资源
+            cpIndexHtml(fusionId,caseOffPath);
+            setRedisProcess(fusionId,10);
+            //创建data.json并下载资源
+            createDataJson(fusionId,caseOffPath+"/env/www");
+            //打包zip
+            zipName = caseOffPath+".zip";
+            ShellUtil.zip(zipName,caseOffPath);
+            setRedisProcess(fusionId,70);
+            //上传oss
+            String ossUrl = zipName.replace("/mnt/", "");
+            ShellUtil.yunUpload(zipName,ossUrl);
+            ossUrl = queryPath + ossUrl;
+            setRedisProcess(fusionId,100,ossUrl);
+        }catch (Exception e){
+            log.info("down-offline-error:{}",fusionId,e);
+            setRedisProcess(fusionId,0,null,1003);
+        }finally {
+            delFile(caseOffPath);
+            delFile(zipName);
+        }
+
+    }
+    private void delFile(String path){
+        if(StringUtils.isNotBlank(path)){
+            try {
+                FileUtil.del(path);
+            }catch (Exception e){
+                log.info("删除文件失败:{}",path);
+            }
+        }
+    }
+
+    public void setRedisProcess(Integer caseId,Integer num){
+        setRedisProcess(caseId,num,null,1000);
+    }
+
+    public void setRedisProcess(Integer caseId,Integer num,String url){
+       setRedisProcess(caseId,num,url,1000);
+    }
+
+    public void setRedisProcess(Integer caseId,Integer num,String url,Integer status){
+        String redisKey = String.format(downProcessKey, caseId);
+        log.info("down-offline-process:{},{},{}",caseId,num,url);
+        DownloadProcessVo processVo = new DownloadProcessVo();
+        processVo.setStatus(status);
+        processVo.setPercent(num);
+        processVo.setUrl( url);
+        redisUtil.set(redisKey,JSONObject.toJSONString(processVo));
+    }
+
+    public DownloadProcessVo process(Integer caseId) {
+        DownloadProcessVo downVo = new DownloadProcessVo();
+        String redisKey = String.format(downProcessKey, caseId);
+        if(redisUtil.hasKey(redisKey)){
+            return JSONObject.parseObject(redisUtil.get(redisKey),DownloadProcessVo.class);
+        }
+        return downVo;
+    }
+
+    public void createDataJson(Integer fusionId,String caseOffPath){
+        log.info("down-offline-createDataJson:{}",fusionId);
+        JSONObject jsonObject = new JSONObject();
+        CaseFusion caseFusion = caseFusionService.getById(fusionId);
+        jsonObject.put(basePath+caseFusionInfo+fusionId, ResultData.ok(caseFusion));
+
+        List<FusionNumVo> sceneListVo = caseFusionService.getSceneListVo(fusionId);
+        jsonObject.put(basePath+caseFusionList+fusionId, ResultData.ok(sceneListVo));
+
+        List<MapConfig> list = mapConfigService.list();
+        jsonObject.put(basePath+mapConfig, ResultData.ok(list));
+
+        List<CaseSettings> caseSettings = caseSettingsService.getByFusionId(fusionId);
+        jsonObject.put(basePath+caseSettingsInfo+fusionId, ResultData.ok(caseSettings));
+        for (CaseSettings caseSetting : caseSettings) {
+            downResource(caseSetting.getBack(),caseOffPath);
+            downResource(caseSetting.getCover(),caseOffPath);
+        }
+
+        jsonObject.put(basePath+fusionMeter+fusionId, ResultData.ok(fusionMeterService.getListByFusionId(fusionId,null)));
+
+        List<FusionNumVo> fusionNumVos = caseFusionService.getSceneListVo(fusionId);
+        for (FusionNumVo fusionNumVo : fusionNumVos) {
+            SceneVo sceneData = fusionNumVo.getSceneData();
+            //下载模型
+            sceneData.setCutModelPath(sceneData.getCutModelPath().replace("/oss/","/swkk/"+sceneData.getNum() +"/wwwroot/"));
+            sceneData.setSceneJsonPath(sceneData.getSceneJsonPath().replace("/oss/","/swkk/"+sceneData.getNum() +"/wwwroot/"));
+            sceneData.setSurveillancePath(sceneData.getSurveillancePath().replace("/oss/","/swkk/"+sceneData.getNum() +"/wwwroot/"));
+
+            if(StringUtils.isNotBlank(sceneData.getModelGlbUrl())){
+                downModel(sceneData.getModelGlbUrl(),caseOffPath);
+            }
+            if(sceneData.getType() != 3){
+                //下载场景离线包
+                downSwkk(caseOffPath,sceneData.getNum(),sceneData.getType());
+            }
+            if(sceneData.getType() == 2 || sceneData.getType() == 5){
+                FdkkResponse sceneInfo = laserService.getSceneInfo(sceneData.getNum());
+                HashSet<String> dataSetIds = new HashSet<>();
+                if(sceneInfo != null){
+                    JSONArray jsonArray = JSONArray.parseArray(JSONArray.toJSONString(sceneInfo.getData()));
+                    JSONArray newJsonArray = new JSONArray();
+                    for (Object object : jsonArray) {
+                        JSONObject sceneInfoObj = (JSONObject) object;
+                        String newPath = String.format(FilePath.OFFLINE_LASER_OSS_PATH, sceneData.getNum(), sceneData.getNum());
+                        String oldPath = sceneInfoObj.getString("webBin");
+                        sceneInfoObj.put("oldWebBin",oldPath);
+                        sceneInfoObj.put("webBin",newPath + oldPath);
+                        newJsonArray.add(sceneInfoObj);
+                        dataSetIds.add( sceneInfoObj.getString("id"));
+                    }
+                    sceneInfo.setData(newJsonArray);
+                    jsonObject.put(String.format(laserData,sceneData.getNum()),sceneInfo);
+                    if(!dataSetIds.isEmpty()){
+                        for (String dataSetId : dataSetIds) {
+                            FdkkResponse sceneInfo2 = laserService.getSceneInfoQuery(sceneData.getNum(),dataSetId);
+                            jsonObject.put(String.format(laserDataQuery,sceneData.getNum(),dataSetId),sceneInfo2);
+                        }
+                    }
+                }
+                FdkkResponse dataSetAndControlPoint = laserService.getDataSetAndControlPoint(sceneData.getNum());
+                if(dataSetAndControlPoint !=null){
+                    jsonObject.put(String.format(laserDataSetAndControlPoint,sceneData.getNum()),dataSetAndControlPoint);
+                }
+            }
+        }
+        jsonObject.put(basePath+caseFusionInfo+fusionId, ResultData.ok(fusionNumVos));
+
+        List<HotIcon> hotIconList = hotIconService.getListByFusionId(fusionId);
+        for (HotIcon hotIcon : hotIconList) {
+            downResource(hotIcon.getIconUrl(),caseOffPath);
+        }
+       // jsonObject.put(basePath+hostIcon+fusionId, ResultData.ok(hotIconList));
+        List<HotIcon> treeList = hotIconService.treeList(hotIconList);
+        jsonObject.put(basePath+hostIconTreeList+fusionId, ResultData.ok(treeList));
+
+        List<CaseTag> caseTagList = caseTagService.getListByFusionId(fusionId);
+        jsonObject.put(basePath+caseTag+fusionId, ResultData.ok(caseTagList));
+        for (CaseTag tag : caseTagList) {
+            jsonObject.put(basePath+caseTagPoint+tag.getTagId(), ResultData.ok(caseTagPointService.allList(tag.getTagId())));
+            downResources(tag.getTagImgUrl(),caseOffPath);
+            downResource(tag.getHotIconUrl(),caseOffPath);
+            downResource(tag.getAudio(),caseOffPath);
+        }
+
+        jsonObject.put(basePath+casePathInfoUrl+fusionId, ResultData.ok(casePathService.getByFusionId(fusionId)));
+        List<FusionGuide> fusionGuides = fusionGuideService.getByFusionId(fusionId);
+        jsonObject.put(basePath+fusionGuide+fusionId, ResultData.ok(fusionGuides));
+
+        for (FusionGuide guide : fusionGuides) {
+            downResource(guide.getCover(),caseOffPath);
+            List<FusionGuidePath> listByGuideId = fusionGuidePathService.getListByGuideId(guide.getFusionGuideId());
+            for (FusionGuidePath guidePath : listByGuideId) {
+                downResource(guidePath.getCover(),caseOffPath);
+            }
+            jsonObject.put(basePath+fusionGuidePath+guide.getFusionGuideId(), ResultData.ok(listByGuideId));
+        }
+
+        List<CaseAnimation> listByFusionId = caseAnimationService.getListByFusionId(fusionId);
+        jsonObject.put(basePath+caseAnimationUrl+fusionId, ResultData.ok(listByFusionId));
+
+
+        FileUtil.writeString(jsonObject.toJSONString(), caseOffPath+"/package/"+jsonDataName,"UTF-8");
+
+    }
+
+
+
+    //http://127.0.0.1:8080/offline.html?caseId=362&app=1&share=1#/show/summary
+
+    static String batName = "start-browser.bat";
+    static String batName2 = "信创环境启动(打开后选在终端运行).sh";
+   public void cpIndexHtml(Integer caseId,String caseOfflinePath){
+       log.info("down-offline-cpIndexHtml:{}",caseId);
+
+       FileUtil.copyContent(new File(FilePath.OFFLINE_TEMPLATE_PATH),new File(caseOfflinePath),true);
+
+       String s = FileUtil.readString(caseOfflinePath + File.separator + batName, StandardCharsets.UTF_8);
+       s = s.replaceAll("@caseId", String.valueOf(caseId));
+       FileUtil.writeString(s, caseOfflinePath + File.separator + batName,"UTF-8");
+
+       String s1 = FileUtil.readString(caseOfflinePath + File.separator + batName2, StandardCharsets.UTF_8);
+       s1 = s1.replaceAll("@caseId", String.valueOf(caseId));
+       FileUtil.writeString(s1, caseOfflinePath + File.separator + batName2,"UTF-8");
+
+   }
+
+
+   @Autowired
+    DownService downService;
+   @Autowired
+    UploadToOssUtil uploadToOssUtil;
+
+   public void downSwkk(String path,String num,Integer type){
+
+       String swkkPath = path + "/swkk/"+num;
+       String swkkZipPath = swkkPath +".zip";
+       String swssPath = path + "/swss/"+num;
+       String swssZipPath = swssPath +".zip";
+
+       Integer isObj = 0;
+       if(type == 4 || type == 6){
+           isObj =1;
+       }
+       try {
+
+           DownVo downVo = downService.checkDownLoad(num, isObj,"offline");
+           log.info("down:{}",downVo);
+           if(downVo.getDownloadStatus() == 3 && StringUtils.isNotBlank(downVo.getDownloadUrl())){
+               downZip(type,downVo.getDownloadUrl(),swkkZipPath,swkkPath,swssZipPath,swssPath);
+           }else {
+               DownVo down = downService.down(num, isObj,"offline");
+               if(down.getDownloadStatus() == 1){
+                   DownloadProcessVo downloadProcessVo = downService.downloadProcess(num, isObj);
+                   while (downloadProcessVo.getStatus() != 1002 ){
+                       downloadProcessVo =  downService.downloadProcess(num, isObj);
+                       Thread.sleep(2000L);
+                   }
+                   downZip(type,downloadProcessVo.getUrl(),swkkZipPath,swkkPath,swssZipPath,swssPath);
+               }
+           }
+       }catch (Exception e){
+           log.info("下载场景离线包失败:{}",num,e);
+       }
+
+   }
+    @Value("${upload.query-path}")
+    private String queryPath;
+   public void downZip(Integer type ,String uri,String kkzipPath,String kknumPath,String sszipPath,String ssNumPath){
+       try {
+           if(type != 2 && type != 5){ //深时点云
+               if(uri.contains("?")){
+                   uri = uri.split("[?]")[0];
+               }
+               ShellUtil.yunDownload(uri.replace(queryPath, ""), kkzipPath);
+
+               ShellUtil.unZip(kkzipPath,kknumPath);
+               FileUtil.del(kkzipPath);
+           }else {
+               ShellUtil.yunDownloadSs(uri.replace(queryPath, ""), sszipPath);
+               ShellUtil.unZip(sszipPath,ssNumPath);
+               FileUtil.del(sszipPath);
+           }
+       }catch (Exception e){
+            log.info("下载场景离线包失败:{}",uri,e);
+       }
+
+   }
+    public void downModel( String modelGlbUrl,String path) {
+
+        JSONArray jsonArray = JSONArray.parseArray(modelGlbUrl);
+        for (Object object : jsonArray) {
+            String res = (String) object;
+            log.info("下载模型:{}",res);
+            res = res.replace(queryPath, "");
+            if(res.contains(".json") ){
+                res = new File(res).getParentFile().getPath();
+            }
+            ShellUtil.yunDownload(res, path +queryPath + res);
+        }
+    }
+    public void downResources(String urls,String offPath) {
+        JSONArray jsonArray = JSONArray.parseArray(urls);
+        for (Object object : jsonArray) {
+            String res = (String) object;
+            downResource(res,offPath);
+        }
+    }
+
+    public void downResource(String url,String path) {
+        if(StringUtils.isBlank(url) ){
+            return;
+        }
+        url = url.replace(queryPath, "");
+        if( !uploadToOssUtil.existKey(url)){
+            log.info("downResource文件不存在:{},{}",url,path);
+            return;
+        }
+        ShellUtil.yunDownload(url,path+queryPath+url);
+    }
+
+    public void downWordByTemplate(Integer caseId,XWPFTemplate template,String name){
+        // 指定输出文件的路径
+        String outputPath = String.format(FilePath.OFFLINE_RESOURCE_PACKAGE_PATH,caseId) + name;
+        try {
+            FileOutputStream out = new FileOutputStream(outputPath);
+            template.write(out);
+            out.close();
+            log.info("文档已成功写入到: " + outputPath);
+        } catch (Exception e) {
+           log.info("写出文档失败:{},{}",caseId,name,e);
+        }
+    }
+
+
+
+}

+ 45 - 0
src/main/java/com/fdkankan/fusion/entity/DictFileCase.java

@@ -0,0 +1,45 @@
+package com.fdkankan.fusion.entity;
+
+import com.baomidou.mybatisplus.annotation.*;
+
+import java.io.Serializable;
+import java.util.Date;
+import lombok.Getter;
+import lombok.Setter;
+
+/**
+ * <p>
+ * 
+ * </p>
+ *
+ * @author 
+ * @since 2025-10-14
+ */
+@Getter
+@Setter
+@TableName("t_dict_file_case")
+public class DictFileCase implements Serializable {
+
+    private static final long serialVersionUID = 1L;
+
+    @TableId(value = "id", type = IdType.AUTO)
+    private Integer id;
+
+    @TableField("dict_file_id")
+    private Integer dictFileId;
+
+    @TableField("case_id")
+    private Integer caseId;
+
+    @TableField("rec_status")
+    @TableLogic(value = "A",delval = "I")
+    private String recStatus;
+
+    @TableField("create_time")
+    private Date createTime;
+
+    @TableField("update_time")
+    private Date updateTime;
+
+
+}

+ 2 - 2
src/main/java/com/fdkankan/fusion/generate/AutoGenerate.java

@@ -18,7 +18,7 @@ public class AutoGenerate {
         String path =System.getProperty("user.dir") ;
 
         generate(path,"fusion", getTables(new String[]{
-               "t_upload_file"
+               "t_dict_file_case"
         }));
 
 //        generate(path,"goods", getTables(new String[]{
@@ -48,7 +48,7 @@ public class AutoGenerate {
     public static void  generate(String path,String moduleName,  List<String> tables){
 //        FastAutoGenerator.create("jdbc:mysql://192.168.0.25:3306/fd_fusion_xj",
 //                "root","mysql123!ROOT.")
-        FastAutoGenerator.create("jdbc:mysql://192.168.0.125:13306/fd_fusion",
+        FastAutoGenerator.create("jdbc:mysql://192.168.0.125:13306/4dkankan_v4",
                 "root","4dkk2023cuikuan%")
                 .globalConfig(builder -> {
                     builder.author("")               //作者

+ 26 - 0
src/main/java/com/fdkankan/fusion/httpClient/HaixinInterceptor.java

@@ -0,0 +1,26 @@
+package com.fdkankan.fusion.httpClient;
+
+import com.alibaba.fastjson.JSONObject;
+import com.dtflys.forest.http.ForestRequest;
+import com.dtflys.forest.interceptor.Interceptor;
+import com.dtflys.forest.reflection.ForestMethod;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.beans.factory.annotation.Value;
+import org.springframework.stereotype.Component;
+
+/**
+ * @author Xiewj
+ * @date 2025/7/8
+ */
+@Component
+@Slf4j
+public class HaixinInterceptor implements Interceptor<JSONObject> {
+
+    @Value("${haixin.appkey}")
+    public String appkey;
+    @Override
+    public void onInvokeMethod(ForestRequest request, ForestMethod method, Object[] args) {
+        request.addHeader("appkey",appkey);
+
+    }
+}

+ 33 - 0
src/main/java/com/fdkankan/fusion/httpClient/HaixinService.java

@@ -0,0 +1,33 @@
+package com.fdkankan.fusion.httpClient;
+
+import cn.hutool.core.date.DateUtil;
+import com.alibaba.fastjson.JSONObject;
+import com.fdkankan.fusion.httpClient.client.HaixinClient;
+import com.fdkankan.fusion.httpClient.response.HaixinCaseInfo;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+
+import java.util.Date;
+import java.util.HashMap;
+
+@Service
+@Slf4j
+public class HaixinService {
+    @Autowired
+    HaixinClient haixinClient;
+
+    public HaixinCaseInfo queryScene(String kno){
+        try {
+            HashMap<String,Object> map = new HashMap<>();
+            map.put("investigationNo",kno);
+            JSONObject jsonObject = haixinClient.queryScene(map);
+            String data = jsonObject.getString("data");
+            HaixinCaseInfo haixinCaseInfo = JSONObject.parseObject(data,HaixinCaseInfo.class);
+            return haixinCaseInfo;
+        }catch (Exception e){
+            log.info("获取海鑫接口错误:{}",kno,e);
+        }
+        return null;
+    }
+}

+ 20 - 0
src/main/java/com/fdkankan/fusion/httpClient/address/HaixinAddressSource.java

@@ -0,0 +1,20 @@
+package com.fdkankan.fusion.httpClient.address;
+
+import com.dtflys.forest.callback.AddressSource;
+import com.dtflys.forest.http.ForestAddress;
+import com.dtflys.forest.http.ForestRequest;
+import org.springframework.beans.factory.annotation.Value;
+import org.springframework.stereotype.Component;
+
+@Component
+public class HaixinAddressSource implements AddressSource {
+
+    @Value("${haixin.basePath}")
+    private String basePath;
+
+
+    @Override
+    public ForestAddress getAddress(ForestRequest forestRequest) {
+        return new ForestAddress("","",null,basePath);
+    }
+}

+ 22 - 0
src/main/java/com/fdkankan/fusion/httpClient/client/HaixinClient.java

@@ -0,0 +1,22 @@
+package com.fdkankan.fusion.httpClient.client;
+
+import com.alibaba.fastjson.JSONObject;
+import com.dtflys.forest.annotation.*;
+import com.fdkankan.fusion.httpClient.HaixinInterceptor;
+import com.fdkankan.fusion.httpClient.address.HaixinAddressSource;
+
+import java.util.Map;
+
+
+/**
+ * 获取,调用4dkk服务
+ */
+@Address(source = HaixinAddressSource.class)
+public interface HaixinClient {
+
+    @Post("/ecs/api/panoramicImageService/submitDrawing")
+    String submitDrawing(@JSONBody Map<String,Object> param);
+
+    @Post(value = "/ecs/api/openapi/queryScene",interceptor = HaixinInterceptor.class)
+    JSONObject queryScene(@JSONBody Map<String,Object> param);
+}

+ 1 - 0
src/main/java/com/fdkankan/fusion/httpClient/request/ManageSceneParam.java

@@ -14,4 +14,5 @@ public class ManageSceneParam extends RequestBase {
     private Integer caseId;
     private List<String> numList;
     private Long userId;
+    private Integer overviewId;
 }

+ 22 - 0
src/main/java/com/fdkankan/fusion/httpClient/response/HaixinCaseInfo.java

@@ -0,0 +1,22 @@
+package com.fdkankan.fusion.httpClient.response;
+
+import lombok.Data;
+
+@Data
+public class HaixinCaseInfo {
+    /**
+     * 案发时间:crimeTimeBegin
+     * 案发地点:caseLocation
+     * 制图单位:orgName
+     * 制图人:investigatorName
+     * 案件类别:caseTypeName
+     */
+    private String orgName;
+    private String caseTypeName;
+    private String orgCode;
+    private String caseLocation;
+    private String crimeTimeBegin;
+    private String investigatorName;
+    private String investigationNo;
+    private String caseType;
+}

+ 18 - 0
src/main/java/com/fdkankan/fusion/mapper/IDictFileCaseMapper.java

@@ -0,0 +1,18 @@
+package com.fdkankan.fusion.mapper;
+
+import com.fdkankan.fusion.entity.DictFileCase;
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+import org.apache.ibatis.annotations.Mapper;
+
+/**
+ * <p>
+ *  Mapper 接口
+ * </p>
+ *
+ * @author 
+ * @since 2025-10-14
+ */
+@Mapper
+public interface IDictFileCaseMapper extends BaseMapper<DictFileCase> {
+
+}

+ 8 - 0
src/main/java/com/fdkankan/fusion/request/DownParam.java

@@ -0,0 +1,8 @@
+package com.fdkankan.fusion.request;
+
+import lombok.Data;
+
+@Data
+public class DownParam {
+    private Integer fusionId;
+}

+ 2 - 0
src/main/java/com/fdkankan/fusion/service/ICaseFusionService.java

@@ -2,6 +2,7 @@ package com.fdkankan.fusion.service;
 
 import com.fdkankan.fusion.entity.CaseFusion;
 import com.baomidou.mybatisplus.extension.service.IService;
+import com.fdkankan.fusion.response.FusionNumVo;
 
 import java.util.List;
 
@@ -19,4 +20,5 @@ public interface ICaseFusionService extends IService<CaseFusion> {
 
     void addFusionIds(List<Integer> fusionIds, Integer caseId);
 
+    List<FusionNumVo> getSceneListVo(Integer fusionId);
 }

+ 4 - 0
src/main/java/com/fdkankan/fusion/service/ICaseOverviewService.java

@@ -3,6 +3,7 @@ package com.fdkankan.fusion.service;
 import com.fdkankan.fusion.entity.CaseOverview;
 import com.baomidou.mybatisplus.extension.service.IService;
 import com.fdkankan.fusion.entity.CaseTabulation;
+import com.fdkankan.fusion.httpClient.response.HaixinCaseInfo;
 import com.fdkankan.fusion.request.ExportOverviewParam;
 
 import java.util.List;
@@ -34,4 +35,7 @@ public interface ICaseOverviewService extends IService<CaseOverview> {
     void updateCaseByIds(List<Integer> overviewIds, Integer caseId);
 
     void checkLoginUser(CaseOverview caseOverview, CaseTabulation caseTabulation,String pageType);
+
+
+    HaixinCaseInfo settingInfo(String num);
 }

+ 1 - 0
src/main/java/com/fdkankan/fusion/service/ICaseTabulationService.java

@@ -31,4 +31,5 @@ public interface ICaseTabulationService extends IService<CaseTabulation> {
     void updateCaseByIds(List<Integer> tabulationIds,  Integer caseId);
 
     CaseTabulation info(String tabulationId,String pageType);
+
 }

+ 17 - 0
src/main/java/com/fdkankan/fusion/service/IDictFileCaseService.java

@@ -0,0 +1,17 @@
+package com.fdkankan.fusion.service;
+
+import com.fdkankan.fusion.entity.DictFileCase;
+import com.baomidou.mybatisplus.extension.service.IService;
+
+/**
+ * <p>
+ *  服务类
+ * </p>
+ *
+ * @author 
+ * @since 2025-10-14
+ */
+public interface IDictFileCaseService extends IService<DictFileCase> {
+
+    void add(Integer uploadId, Integer caseId);
+}

+ 4 - 0
src/main/java/com/fdkankan/fusion/service/IDictFileService.java

@@ -4,6 +4,8 @@ import com.fdkankan.fusion.entity.CommonUpload;
 import com.fdkankan.fusion.entity.DictFile;
 import com.baomidou.mybatisplus.extension.service.IService;
 
+import java.util.List;
+
 /**
  * <p>
  *  服务类
@@ -15,4 +17,6 @@ import com.baomidou.mybatisplus.extension.service.IService;
 public interface IDictFileService extends IService<DictFile> {
 
     void addSystemFile(CommonUpload commonUpload);
+
+    List<DictFile> getByUploadId(Integer uploadId);
 }

+ 1 - 1
src/main/java/com/fdkankan/fusion/service/IFusionGuideService.java

@@ -21,5 +21,5 @@ public interface IFusionGuideService extends IService<FusionGuide> {
 
     Long getCountByCaseId(Integer caseId);
 
-    Object getByFusionId(Integer fusionId);
+    List<FusionGuide>  getByFusionId(Integer fusionId);
 }

+ 70 - 0
src/main/java/com/fdkankan/fusion/service/impl/CaseFusionServiceImpl.java

@@ -1,12 +1,16 @@
 package com.fdkankan.fusion.service.impl;
 
+import com.alibaba.fastjson.JSONObject;
 import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
 import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
 import com.fdkankan.fusion.common.ResultCode;
+import com.fdkankan.fusion.common.util.CameraUtil;
 import com.fdkankan.fusion.entity.*;
+import com.fdkankan.fusion.entity.jsonEntity.Transform;
 import com.fdkankan.fusion.exception.BusinessException;
 import com.fdkankan.fusion.mapper.ICaseFusionMapper;
 import com.fdkankan.fusion.response.CaseFusionVo;
+import com.fdkankan.fusion.response.FusionNumVo;
 import com.fdkankan.fusion.response.SceneVo;
 import com.fdkankan.fusion.service.*;
 import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
@@ -15,6 +19,7 @@ import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
 
 import java.util.ArrayList;
+import java.util.HashMap;
 import java.util.List;
 import java.util.stream.Collectors;
 
@@ -52,4 +57,69 @@ public class CaseFusionServiceImpl extends ServiceImpl<ICaseFusionMapper, CaseFu
         caseFusionRelationService.addFusionIds(fusionIds,caseId);
     }
 
+    @Autowired
+    IFusionNumService fusionNumService;
+    @Autowired
+    IModelService modelService;
+    @Autowired
+    IScenePlusService scenePlusService;
+    @Autowired
+    IScenePlusExtService scenePlusExtService;
+
+    @Override
+    public List<FusionNumVo> getSceneListVo(Integer fusionId) {
+        List<FusionNumVo> sceneVos = new ArrayList<>();
+        List<FusionNum> fusionNumList = fusionNumService.getByFusionId(fusionId);
+
+        List<Integer> modelIds = fusionNumList.stream().map(FusionNum::getModelId).collect(Collectors.toList());
+        List<Model> listByModelIds = modelService.getListByModelIds(modelIds);
+        HashMap<Integer,Model> modelMap = new HashMap<>();
+        listByModelIds.stream().forEach(e -> modelMap.put(e.getModelId(),e));
+
+
+        List<String> numList = listByModelIds.stream().filter(e -> e.getNum() != null).map(Model::getNum).collect(Collectors.toList());
+        List<ScenePlus> scenePlusList = scenePlusService.getByNumList(numList);
+        HashMap<String,ScenePlus> map = new HashMap<>();
+        scenePlusList.stream().forEach(e -> map.put(e.getNum(),e));
+
+        List<Long> plusIds = scenePlusList.stream().map(ScenePlus::getId).collect(Collectors.toList());
+        List<ScenePlusExt> extList = scenePlusExtService.getByPlusIds(plusIds);
+        HashMap<Long,ScenePlusExt> mapext = new HashMap<>();
+        extList.stream().forEach(e -> mapext.put(e.getPlusId(),e));
+
+
+        for (FusionNum fusionNum : fusionNumList) {
+            Transform transform = JSONObject.parseObject(fusionNum.getTransform(),Transform.class);
+            FusionNumVo vo = new FusionNumVo();
+            vo.setTransform(transform);
+            BeanUtils.copyProperties(fusionNum,vo);
+            SceneVo sceneVo = new SceneVo();
+            Model model = modelMap.get(fusionNum.getModelId());
+            if(model != null){
+                BeanUtils.copyProperties(model,sceneVo);
+                if(model.getNum() != null ){
+                    ScenePlus scenePlus = map.get(model.getNum());
+                    if(scenePlus != null){
+                        BeanUtils.copyProperties(scenePlus,sceneVo);
+                        sceneVo.setStatus(scenePlus.getSceneStatus() == -2 ? 2:scenePlus.getSceneStatus());
+                        sceneVo.setName(scenePlus.getTitle());
+                        sceneVo.setSceneName(scenePlus.getTitle());
+                        sceneVo.setCreateTime(scenePlus.getCreateTime());
+                        ScenePlusExt scenePlusExt = mapext.get(scenePlus.getId());
+                        if(scenePlusExt != null){
+                            sceneVo.setRtkLocation(scenePlusExt.getRtkLocation());
+                            sceneVo.setOrientation(scenePlusExt.getOrientation());
+                        }
+                    }
+                }else {
+                    sceneVo.setStatus(2);
+                }
+                sceneVo.setSourceName(CameraUtil.getSourceName(model.getType()));
+            }
+            vo.setSceneData(sceneVo);
+            sceneVos.add(vo);
+        }
+
+        return sceneVos;
+    }
 }

+ 37 - 7
src/main/java/com/fdkankan/fusion/service/impl/CaseOverviewServiceImpl.java

@@ -1,6 +1,7 @@
 package com.fdkankan.fusion.service.impl;
 
 import cn.dev33.satoken.stp.StpUtil;
+import cn.hutool.core.date.DateUtil;
 import cn.hutool.core.io.FileUtil;
 import com.alibaba.fastjson.JSONArray;
 import com.alibaba.fastjson.JSONObject;
@@ -11,18 +12,16 @@ import com.fdkankan.fusion.common.ResultCode;
 import com.fdkankan.fusion.common.util.MD5Checksum;
 import com.fdkankan.fusion.common.util.UploadToOssUtil;
 import com.fdkankan.fusion.config.SecurityUtil;
-import com.fdkankan.fusion.entity.CaseEntity;
-import com.fdkankan.fusion.entity.CaseFiles;
-import com.fdkankan.fusion.entity.CaseOverview;
-import com.fdkankan.fusion.entity.CaseTabulation;
+import com.fdkankan.fusion.entity.*;
 import com.fdkankan.fusion.exception.BusinessException;
 import com.fdkankan.fusion.httpClient.FdService;
+import com.fdkankan.fusion.httpClient.HaixinService;
+import com.fdkankan.fusion.httpClient.client.HaixinClient;
+import com.fdkankan.fusion.httpClient.response.HaixinCaseInfo;
 import com.fdkankan.fusion.mapper.ICaseOverviewMapper;
 import com.fdkankan.fusion.request.ExportOverviewParam;
-import com.fdkankan.fusion.service.ICaseFilesService;
-import com.fdkankan.fusion.service.ICaseOverviewService;
+import com.fdkankan.fusion.service.*;
 import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
-import com.fdkankan.fusion.service.ICaseTabulationService;
 import lombok.extern.slf4j.Slf4j;
 import org.apache.commons.lang3.StringUtils;
 import org.springframework.beans.factory.annotation.Autowired;
@@ -31,6 +30,7 @@ import org.springframework.stereotype.Service;
 import java.io.File;
 import java.nio.charset.StandardCharsets;
 import java.util.ArrayList;
+import java.util.Date;
 import java.util.HashMap;
 import java.util.List;
 import java.util.stream.Collectors;
@@ -154,6 +154,9 @@ public class CaseOverviewServiceImpl extends ServiceImpl<ICaseOverviewMapper, Ca
         try {
             uploadToOssUtil.copyFile(uploadToOssUtil.getOssPath(listCover),filePath + fileName);
 
+            if(uploadToOssUtil.existKey(jsonPath)){
+                jsonPathSource = jsonPath;
+            }
             String content = uploadToOssUtil.readFile(jsonPathSource);
             JSONObject jsonObject = JSONObject.parseObject(content);
             JSONArray jsonArray = jsonObject.getJSONArray("floors");
@@ -223,4 +226,31 @@ public class CaseOverviewServiceImpl extends ServiceImpl<ICaseOverviewMapper, Ca
         throw new BusinessException(ResultCode.NOT_PER);
 
     }
+
+
+    @Autowired
+    HaixinService haixinService;
+    @Autowired
+    ICaseService caseService;
+    @Autowired
+    IScenePlusService scenePlusService;
+    @Override
+    public HaixinCaseInfo settingInfo(String num) {
+        try {
+            ScenePlus scenePlus = scenePlusService.getByNum(num);
+            if(scenePlus != null && StringUtils.isNotBlank(scenePlus.getKNo())){
+                HaixinCaseInfo haixinCaseInfo = haixinService.queryScene(scenePlus.getKNo());
+                if(haixinCaseInfo != null && StringUtils.isNotBlank(haixinCaseInfo.getCrimeTimeBegin())){
+                    haixinCaseInfo.setCrimeTimeBegin(DateUtil.format(new Date(Long.valueOf(haixinCaseInfo.getCrimeTimeBegin())),"yyyy年MM月dd日HH时mm分"));
+                }
+                return haixinCaseInfo;
+            }
+        }catch (Exception e){
+            log.info("获取失败:{}",e);
+        }
+
+        return null;
+    }
+
+
 }

+ 8 - 0
src/main/java/com/fdkankan/fusion/service/impl/CaseTabulationServiceImpl.java

@@ -2,27 +2,34 @@ package com.fdkankan.fusion.service.impl;
 
 import cn.dev33.satoken.stp.StpUtil;
 import cn.hutool.core.date.DateUtil;
+import com.alibaba.fastjson.JSONObject;
 import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
 import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
 import com.fdkankan.fusion.common.ResultCode;
 import com.fdkankan.fusion.common.util.UploadToOssUtil;
+import com.fdkankan.fusion.entity.CaseEntity;
 import com.fdkankan.fusion.entity.CaseFiles;
 import com.fdkankan.fusion.entity.CaseOverview;
 import com.fdkankan.fusion.entity.CaseTabulation;
 import com.fdkankan.fusion.exception.BusinessException;
 import com.fdkankan.fusion.httpClient.client.FdKKClient;
+import com.fdkankan.fusion.httpClient.client.HaixinClient;
 import com.fdkankan.fusion.httpClient.request.AddMediaLibraryParam;
+import com.fdkankan.fusion.httpClient.response.HaixinCaseInfo;
 import com.fdkankan.fusion.mapper.ICaseTabulationMapper;
 import com.fdkankan.fusion.request.ExportOverviewParam;
 import com.fdkankan.fusion.service.ICaseFilesService;
 import com.fdkankan.fusion.service.ICaseOverviewService;
+import com.fdkankan.fusion.service.ICaseService;
 import com.fdkankan.fusion.service.ICaseTabulationService;
 import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
+import lombok.extern.slf4j.Slf4j;
 import org.apache.commons.lang3.StringUtils;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
 
 import java.util.Date;
+import java.util.HashMap;
 import java.util.List;
 
 /**
@@ -34,6 +41,7 @@ import java.util.List;
  * @since 2025-05-13
  */
 @Service
+@Slf4j
 public class CaseTabulationServiceImpl extends ServiceImpl<ICaseTabulationMapper, CaseTabulation> implements ICaseTabulationService {
 
     @Autowired

+ 48 - 0
src/main/java/com/fdkankan/fusion/service/impl/DictFileCaseServiceImpl.java

@@ -0,0 +1,48 @@
+package com.fdkankan.fusion.service.impl;
+
+import com.baomidou.dynamic.datasource.annotation.DS;
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.fdkankan.fusion.entity.DictFile;
+import com.fdkankan.fusion.entity.DictFileCase;
+import com.fdkankan.fusion.mapper.IDictFileCaseMapper;
+import com.fdkankan.fusion.service.IDictFileCaseService;
+import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
+import com.fdkankan.fusion.service.IDictFileService;
+import com.fdkankan.fusion.service.IDictService;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+
+import java.util.List;
+
+/**
+ * <p>
+ *  服务实现类
+ * </p>
+ *
+ * @author 
+ * @since 2025-10-14
+ */
+@Service
+@DS("db2")
+public class DictFileCaseServiceImpl extends ServiceImpl<IDictFileCaseMapper, DictFileCase> implements IDictFileCaseService {
+
+    @Autowired
+    IDictFileService dictFileService;
+
+    @Override
+    public void add(Integer uploadId, Integer caseId) {
+        List<DictFile> dictFiles = dictFileService.getByUploadId(uploadId);
+        for (DictFile dictFile : dictFiles) {
+            LambdaQueryWrapper<DictFileCase> wrapper = new LambdaQueryWrapper<>();
+            wrapper.eq(DictFileCase::getDictFileId,dictFile.getId());
+            wrapper.eq(DictFileCase::getCaseId,caseId);
+            List<DictFileCase> list = this.list(wrapper);
+            if(list.isEmpty()){
+                DictFileCase dictFileCase = new DictFileCase();
+                dictFileCase.setDictFileId(dictFile.getId());
+                dictFileCase.setCaseId(caseId);
+                this.save(dictFileCase);
+            }
+        }
+    }
+}

+ 9 - 1
src/main/java/com/fdkankan/fusion/service/impl/DictFileServiceImpl.java

@@ -1,6 +1,7 @@
 package com.fdkankan.fusion.service.impl;
 
 import com.baomidou.dynamic.datasource.annotation.DS;
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
 import com.fdkankan.fusion.entity.CommonUpload;
 import com.fdkankan.fusion.entity.Dict;
 import com.fdkankan.fusion.entity.DictFile;
@@ -11,6 +12,8 @@ import com.fdkankan.fusion.service.IDictService;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
 
+import java.util.List;
+
 /**
  * <p>
  *  服务实现类
@@ -40,5 +43,10 @@ public class DictFileServiceImpl extends ServiceImpl<IDictFileMapper, DictFile>
         this.save(dictFile);
     }
 
-
+    @Override
+    public List<DictFile> getByUploadId(Integer uploadId) {
+        LambdaQueryWrapper<DictFile> wrapper = new LambdaQueryWrapper<>();
+        wrapper.eq(DictFile::getUploadId,uploadId);
+        return this.list(wrapper);
+    }
 }

+ 5 - 0
src/main/resources/mapper/fusion/DictFileCaseMapper.xml

@@ -0,0 +1,5 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="com.fdkankan.fusion.mapper.IDictFileCaseMapper">
+
+</mapper>