Sfoglia il codice sorgente

Merge branch 'release/v2.2.5' into 'master'

Release/v2.2.5

See merge request dcuc-tjdsj/app-service!94
黄资权 1 anno fa
parent
commit
54485ddf32
26 ha cambiato i file con 1182 aggiunte e 22 eliminazioni
  1. 9 0
      dcuc-app-api/src/main/java/com/dragoninfo/dcuc/app/facade/IResourceFacade.java
  2. 19 4
      dcuc-app-api/src/main/java/com/dragoninfo/dcuc/app/facade/sub/IAppDataItemInfoFacade.java
  3. 27 4
      dcuc-app-api/src/main/java/com/dragoninfo/dcuc/app/facade/sub/IAppDataResourceInfoFacade.java
  4. 24 0
      dcuc-app-model/src/main/java/com/dragoninfo/dcuc/app/dto/appindex/FhAppIndexRespDTO.java
  5. 115 0
      dcuc-app-model/src/main/java/com/dragoninfo/dcuc/app/dto/appindex/FhResourceRespDTO.java
  6. 34 0
      dcuc-app-model/src/main/java/com/dragoninfo/dcuc/app/dto/appindex/FhResponseParamRespDTO.java
  7. 56 0
      dcuc-app-model/src/main/java/com/dragoninfo/dcuc/app/vo/AppDataItemPageVo.java
  8. 65 0
      dcuc-app-model/src/main/java/com/dragoninfo/dcuc/app/vo/AppDataResourcePageVo.java
  9. 23 1
      dcuc-app-service/pom.xml
  10. 17 0
      dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/business/IFhAppSyncBusiness.java
  11. 255 0
      dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/business/impl/FhAppSyncBusinessImpl.java
  12. 18 0
      dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/config/FhAppSyncProperties.java
  13. 23 0
      dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/config/RestTemplateConfig.java
  14. 20 0
      dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/facade/ResourceFacade.java
  15. 14 0
      dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/facade/sub/AppDataItemInfoFacade.java
  16. 24 0
      dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/facade/sub/AppDataResourceInfoFacade.java
  17. 12 0
      dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/service/IApplyInfoService.java
  18. 32 3
      dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/service/impl/ApplyInfoServiceImpl.java
  19. 15 0
      dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/service/sub/IAppDataItemInfoService.java
  20. 30 0
      dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/service/sub/IAppDataResourceInfoService.java
  21. 37 0
      dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/service/sub/impl/AppDataItemInfoServiceImpl.java
  22. 101 2
      dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/service/sub/impl/AppDataResourceInfoServiceImpl.java
  23. 4 1
      dcuc-app-service/src/main/resources/application-app.yml
  24. 112 0
      dcuc-app-service/src/test/java/com/dragoninfo/dcuc/app/business/impl/FhAppSyncBusinessImplTerst.java
  25. 73 0
      dcuc-app-service/src/test/resources/fh/app.json
  26. 23 7
      pom.xml

+ 9 - 0
dcuc-app-api/src/main/java/com/dragoninfo/dcuc/app/facade/IResourceFacade.java

@@ -120,6 +120,14 @@ public interface IResourceFacade {
     @GetMapping(value = "subAppSync")
     ResponseStatus subAppSync();
 
+    /**
+     * 主客体授权-烽火应用数据同步
+     *
+     * @return
+     */
+    @GetMapping(value = "fhAppSync")
+    ResponseStatus fhAppSync();
+
     /**
      * 资源数量统计
      *
@@ -130,4 +138,5 @@ public interface IResourceFacade {
     @GetMapping("count")
     ResourceStatisticsDto count(@RequestParam(value = "startTime", required = false) Date startTime,
                                 @RequestParam(value = "endTime", required = false) Date endTime);
+
 }

+ 19 - 4
dcuc-app-api/src/main/java/com/dragoninfo/dcuc/app/facade/sub/IAppDataItemInfoFacade.java

@@ -1,12 +1,12 @@
 package com.dragoninfo.dcuc.app.facade.sub;
 
 import com.dragoninfo.dcuc.app.vo.AppDataItemInfoRespVO;
+import com.dragoninfo.dcuc.app.vo.AppDataItemPageVo;
+import com.dragonsoft.duceap.base.entity.http.ResponseStatus;
 import com.dragonsoft.duceap.base.entity.search.SearchDTO;
 import org.springframework.cloud.openfeign.FeignClient;
-import org.springframework.web.bind.annotation.GetMapping;
-import org.springframework.web.bind.annotation.PostMapping;
-import org.springframework.web.bind.annotation.RequestBody;
-import org.springframework.web.bind.annotation.RequestParam;
+import org.springframework.data.domain.Page;
+import org.springframework.web.bind.annotation.*;
 
 import java.util.List;
 
@@ -39,4 +39,19 @@ public interface IAppDataItemInfoFacade {
     @GetMapping("selectByTableId")
     List<AppDataItemInfoRespVO> selectByTableId(@RequestParam("tableId") String tableId);
 
+    /**
+     * 分页查询
+     * @param searchDTO
+     * @return
+     */
+    @PostMapping("pageSearch")
+    Page<AppDataItemPageVo> pageSearch(@RequestBody SearchDTO searchDTO);
+
+    /**
+     * 删除
+     * @param id
+     * @return
+     */
+    @DeleteMapping("deleteById/{id}")
+    ResponseStatus deleteById(@PathVariable("id") String id);
 }

+ 27 - 4
dcuc-app-api/src/main/java/com/dragoninfo/dcuc/app/facade/sub/IAppDataResourceInfoFacade.java

@@ -1,12 +1,12 @@
 package com.dragoninfo.dcuc.app.facade.sub;
 
 import com.dragoninfo.dcuc.app.vo.AppDataResourceInfoRespVO;
+import com.dragoninfo.dcuc.app.vo.AppDataResourcePageVo;
+import com.dragonsoft.duceap.base.entity.http.ResponseStatus;
 import com.dragonsoft.duceap.base.entity.search.SearchDTO;
 import org.springframework.cloud.openfeign.FeignClient;
-import org.springframework.web.bind.annotation.GetMapping;
-import org.springframework.web.bind.annotation.PostMapping;
-import org.springframework.web.bind.annotation.RequestBody;
-import org.springframework.web.bind.annotation.RequestParam;
+import org.springframework.data.domain.Page;
+import org.springframework.web.bind.annotation.*;
 
 import java.util.List;
 
@@ -38,4 +38,27 @@ public interface IAppDataResourceInfoFacade {
     @GetMapping("findByResourceCode")
     AppDataResourceInfoRespVO findByResourceCode(@RequestParam("resourceCode") String resourceCode);
 
+    /**
+     * 分页查询
+     * @param searchDTO
+     * @return
+     */
+    @PostMapping("pageSearch")
+    Page<AppDataResourcePageVo> pageSearch(@RequestBody SearchDTO searchDTO);
+
+    /**
+     * 查看详情
+     * @param id
+     * @return
+     */
+    @GetMapping("getById/{id}")
+    AppDataResourceInfoRespVO getById(@PathVariable("id") String id);
+
+    /**
+     * 删除
+     * @param id
+     * @return
+     */
+    @DeleteMapping("deleteById/{id}")
+    ResponseStatus deleteById(@PathVariable("id") String id);
 }

+ 24 - 0
dcuc-app-model/src/main/java/com/dragoninfo/dcuc/app/dto/appindex/FhAppIndexRespDTO.java

@@ -0,0 +1,24 @@
+
+package com.dragoninfo.dcuc.app.dto.appindex;
+
+import com.fasterxml.jackson.annotation.JsonProperty;
+import lombok.Data;
+
+/**
+ * 烽火应用资源目录返回
+ *
+ * @author huangzqa
+ */
+@Data
+public class FhAppIndexRespDTO {
+
+    @JsonProperty("MessageSequence")
+    private String messageSequence;
+    @JsonProperty("MessageStatus")
+    private String messageStatus;
+    @JsonProperty("Remark")
+    private String remark;
+    @JsonProperty("ResponseParam")
+    private FhResponseParamRespDTO responseParam;
+
+}

+ 115 - 0
dcuc-app-model/src/main/java/com/dragoninfo/dcuc/app/dto/appindex/FhResourceRespDTO.java

@@ -0,0 +1,115 @@
+
+package com.dragoninfo.dcuc.app.dto.appindex;
+
+import com.fasterxml.jackson.annotation.JsonProperty;
+import lombok.Data;
+
+/**
+ * 烽火应用资源目录应用内容
+ *
+ * @author huangzqa
+ */
+@Data
+public class FhResourceRespDTO {
+
+    @JsonProperty("PTXTBH")
+    private Object ptxtbh;
+
+    /**
+     * 上线日期
+     */
+    @JsonProperty("SXRQ")
+    private String sxrq;
+
+    /**
+     * 系统架构类型
+     */
+    @JsonProperty("XTJGLX")
+    private String xtjglx;
+
+    /**
+     * 系统在用标识
+     */
+    @JsonProperty("XTZYBS")
+    private Long xtzybs;
+
+    /**
+     * 下线日期
+     */
+    @JsonProperty("XXRQ")
+    private Object xxrq;
+
+    /**
+     * 业务使用场景代码
+     */
+    @JsonProperty("YWSYCJDM")
+    private String ywsycjdm;
+
+    /**
+     *
+     */
+    @JsonProperty("YYLX")
+    private String yylx;
+
+    /**
+     * 应用系统编号
+     */
+    @JsonProperty("YYXTBH")
+    private String yyxtbh;
+
+    /**
+     * 应用系统承建单位代码
+     */
+    @JsonProperty("YYXTCJDWDM")
+    private String yyxtcjdwdm;
+
+    /**
+     * 应用系统分类代码
+     */
+    @JsonProperty("YYXTFLDM")
+    private String yyxtfldm;
+
+    /**
+     * 应用系统访问地址
+     */
+    @JsonProperty("YYXTFWDZ")
+    private String yyxtfwdz;
+
+    /**
+     * 应用系统管理单位代码
+     */
+    @JsonProperty("YYXTGLDWDM")
+    private String yyxtgldwdm;
+
+    /**
+     *应用系统名称
+     */
+    @JsonProperty("YYXTMC")
+    private String yyxtmc;
+
+    /**
+     *
+     */
+    @JsonProperty("YYXTRZJB")
+    private String yyxtrzjb;
+
+    /**
+     * 应用系统说明
+     */
+    @JsonProperty("YYXTSM")
+    private String yyxtsm;
+
+    /**
+     * 应用系统事权单位代码
+     */
+    @JsonProperty("YYXTSQDWDM")
+    private String yyxtsqdwdm;
+
+    /**
+     * 应用系统运维单位代码
+     */
+    @JsonProperty("YYXTYWDWDM")
+    private String yyxtywdwdm;
+
+
+}

+ 34 - 0
dcuc-app-model/src/main/java/com/dragoninfo/dcuc/app/dto/appindex/FhResponseParamRespDTO.java

@@ -0,0 +1,34 @@
+
+package com.dragoninfo.dcuc.app.dto.appindex;
+
+import com.fasterxml.jackson.annotation.JsonProperty;
+import lombok.Data;
+
+import java.util.List;
+
+/**
+ * 烽火应用资源目录参数
+ *
+ * @author huangzqa
+ */
+@Data
+public class FhResponseParamRespDTO {
+
+    @JsonProperty("Exception")
+    private List<Object> exception;
+    @JsonProperty("FileDigest")
+    private String fileDigest;
+    @JsonProperty("FileName")
+    private String fileName;
+    @JsonProperty("FileSize")
+    private String fileSize;
+    @JsonProperty("RegisterInfos")
+    private List<Object> registerInfos;
+    @JsonProperty("RelationId")
+    private Object relationId;
+    @JsonProperty("Resources")
+    private List<FhResourceRespDTO> resources;
+    @JsonProperty("TotalNum")
+    private Long totalNum;
+
+}

+ 56 - 0
dcuc-app-model/src/main/java/com/dragoninfo/dcuc/app/vo/AppDataItemPageVo.java

@@ -0,0 +1,56 @@
+package com.dragoninfo.dcuc.app.vo;
+
+import com.fasterxml.jackson.annotation.JsonFormat;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import org.springframework.format.annotation.DateTimeFormat;
+
+import java.util.Date;
+
+/**
+ * 数据集分页展示Vo
+ * @author mazq
+ * @date 2023/6/28
+ */
+@Data
+@ApiModel(value = "数据集分页展示Vo")
+public class AppDataItemPageVo {
+
+    @ApiModelProperty(value = "id")
+    private String id;
+
+    @ApiModelProperty(value = "数据集资源id")
+    private String resourceTableId;
+
+    @ApiModelProperty(value = "数据集资源名称")
+    private String appDataResourceName;
+
+    @ApiModelProperty(value = "字段分类名称")
+    private String columnClassifyName;
+
+    @ApiModelProperty(value = "字段英文名称")
+    private String columnCode;
+
+    @ApiModelProperty(value = "字段中文名称")
+    private String columnName;
+
+    @ApiModelProperty(value = "数据项编号")
+    private String dataItemNo;
+
+    @ApiModelProperty(value = "数据项标识符")
+    private String dataItemCode;
+
+    @ApiModelProperty(value = "是否失效,true/false")
+    private String invalidStatus;
+
+    @DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")
+    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GTM+8")
+    @ApiModelProperty(value = "创建时间")
+    private Date columnRegisterTime;
+
+    @DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")
+    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GTM+8")
+    @ApiModelProperty(value = "更新时间")
+    private Date columnUpdateTime;
+}

+ 65 - 0
dcuc-app-model/src/main/java/com/dragoninfo/dcuc/app/vo/AppDataResourcePageVo.java

@@ -0,0 +1,65 @@
+package com.dragoninfo.dcuc.app.vo;
+
+import com.fasterxml.jackson.annotation.JsonFormat;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import org.springframework.format.annotation.DateTimeFormat;
+
+import java.util.Date;
+
+/**
+ * 数据集分页展示Vo
+ * @author mazq
+ * @date 2023/6/28
+ */
+@Data
+@ApiModel(value = "数据集分页展示Vo")
+public class AppDataResourcePageVo {
+
+    @ApiModelProperty(value = "id")
+    private String id;
+
+    @ApiModelProperty(value = "数据资源名称")
+    private String resourceName;
+
+    @ApiModelProperty(value = "数据资源标识符")
+    private String resourceCode;
+
+    @ApiModelProperty(value = "应用系统编码称")
+    private String applicationCode;
+
+    @ApiModelProperty(value = "应用系统名称")
+    private String applicationCodeName;
+
+    @ApiModelProperty(value = "事权单位名称")
+    private String authorityDeptName;
+
+    @ApiModelProperty(value = "数据资源事权单位编号")
+    private String authorityDeptCode;
+
+    @ApiModelProperty(value = "管理单位名称")
+    private String manageDeptName;
+
+    @ApiModelProperty(value = "管理单位名称")
+    private String manageDeptCode;
+
+    @ApiModelProperty(value = "数据组织一级分类名称")
+    private String dataClassifyOneName;
+
+    @ApiModelProperty(value = "数据组织二级分类名称")
+    private String dataClassifyTwoName;
+
+    @ApiModelProperty(value = "标签名")
+    private String labelName;
+
+    @DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")
+    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GTM+8")
+    @ApiModelProperty(value = "创建时间")
+    private Date createTime;
+
+    @DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")
+    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GTM+8")
+    @ApiModelProperty(value = "更新时间")
+    private Date updateTime;
+}

+ 23 - 1
dcuc-app-service/pom.xml

@@ -86,7 +86,7 @@
         <dependency>
             <groupId>com.dragoninfo</groupId>
             <artifactId>dcuc-common</artifactId>
-            <version>2.0.0-SNAPSHOT</version>
+            <version>2.1.0-tjdsj-SNAPSHOT</version>
             <exclusions>
                 <exclusion>
                     <artifactId>hibernate-core</artifactId>
@@ -173,7 +173,29 @@
             <scope>compile</scope>
         </dependency>
         <!--配置 spring 结束-->
+        <dependency>
+            <groupId>com.github.dreamhead</groupId>
+            <artifactId>moco-core</artifactId>
+            <scope>test</scope>
+        </dependency>
+
+        <dependency>
+            <groupId>com.github.dreamhead</groupId>
+            <artifactId>moco-junit</artifactId>
+            <scope>test</scope>
+        </dependency>
 
+        <dependency>
+            <groupId>it.ozimov</groupId>
+            <artifactId>embedded-redis</artifactId>
+            <scope>test</scope>
+            <exclusions>
+                <exclusion>
+                    <artifactId>slf4j-simple</artifactId>
+                    <groupId>org.slf4j</groupId>
+                </exclusion>
+            </exclusions>
+        </dependency>
     </dependencies>
     <packaging>${project.packaging}</packaging>
 

+ 17 - 0
dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/business/IFhAppSyncBusiness.java

@@ -0,0 +1,17 @@
+package com.dragoninfo.dcuc.app.business;
+
+import com.dragonsoft.duceap.base.entity.http.ResponseStatus;
+
+/**
+ * @author mazq
+ * @date 2023/7/20
+ */
+public interface IFhAppSyncBusiness {
+
+    /**
+     * 同步应用信息
+     * @return
+     */
+    ResponseStatus syncAppInfo();
+
+}

+ 255 - 0
dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/business/impl/FhAppSyncBusinessImpl.java

@@ -0,0 +1,255 @@
+package com.dragoninfo.dcuc.app.business.impl;
+
+import cn.hutool.core.bean.BeanUtil;
+import com.dragoninfo.dcuc.app.business.IFhAppSyncBusiness;
+import com.dragoninfo.dcuc.app.config.FhAppSyncProperties;
+import com.dragoninfo.dcuc.app.dto.appindex.FhAppIndexRespDTO;
+import com.dragoninfo.dcuc.app.dto.appindex.FhResourceRespDTO;
+import com.dragoninfo.dcuc.app.dto.appindex.FhResponseParamRespDTO;
+import com.dragoninfo.dcuc.app.entity.ApplyInfo;
+import com.dragoninfo.dcuc.app.entity.ApplyOauth;
+import com.dragoninfo.dcuc.app.service.IApplyInfoService;
+import com.dragoninfo.dcuc.app.service.IApplyOauthService;
+import com.dragoninfo.dcuc.common.annotation.CacheLock;
+import com.dragoninfo.dcuc.common.utils.ResponseUtil;
+import com.dragoninfo.dcuc.user.entity.org.OrgInfo;
+import com.dragoninfo.dcuc.user.facade.org.IOrgInfoFacade;
+import com.dragonsoft.duceap.base.entity.http.ResponseDTO;
+import com.dragonsoft.duceap.base.entity.http.ResponseStatus;
+import com.dragonsoft.duceap.base.enums.BooleanEnum;
+import com.dragonsoft.duceap.commons.util.ObjectUtils;
+import com.dragonsoft.duceap.commons.util.collections.CollectionUtils;
+import com.dragonsoft.duceap.commons.util.json.JsonUtils;
+import com.dragonsoft.duceap.commons.util.string.StringUtils;
+import com.fasterxml.jackson.core.JsonProcessingException;
+import com.fasterxml.jackson.databind.ObjectMapper;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.http.HttpEntity;
+import org.springframework.http.HttpMethod;
+import org.springframework.http.ResponseEntity;
+import org.springframework.stereotype.Service;
+import org.springframework.web.client.RestTemplate;
+
+import java.text.SimpleDateFormat;
+import java.util.*;
+import java.util.stream.Collectors;
+
+/**
+ * @author mazq
+ * @date 2023/7/20
+ */
+@Slf4j
+@Service
+public class FhAppSyncBusinessImpl implements IFhAppSyncBusiness {
+
+    private final static String FH_SUCCESS_STATUS = "0200";
+
+    private RestTemplate restTemplate;
+
+    private FhAppSyncProperties fhAppSyncProperties;
+
+    private IApplyInfoService applyInfoService;
+
+    private IOrgInfoFacade orgInfoFacade;
+
+    private IApplyOauthService applyOauthService;
+
+    @Autowired
+    public void setApplyOauthService(IApplyOauthService applyOauthService) {
+        this.applyOauthService = applyOauthService;
+    }
+
+    @Autowired
+    public void setOrgInfoFacade(IOrgInfoFacade orgInfoFacade) {
+        this.orgInfoFacade = orgInfoFacade;
+    }
+
+    @Autowired
+    public void setRestTemplate(RestTemplate restTemplate) {
+        this.restTemplate = restTemplate;
+    }
+
+    @Autowired
+    public void setFhAppSyncProperties(FhAppSyncProperties fhAppSyncProperties) {
+        this.fhAppSyncProperties = fhAppSyncProperties;
+    }
+
+    @Autowired
+    public void setApplyInfoService(IApplyInfoService applyInfoService) {
+        this.applyInfoService = applyInfoService;
+    }
+
+    @CacheLock
+    @Override
+    public ResponseStatus syncAppInfo() {
+        ResponseDTO<FhAppIndexRespDTO> appResource = getAppResource();
+        if (ResponseUtil.isFail(appResource)) {
+            return appResource;
+        }
+        ResponseDTO<List<ApplyInfo>> resp = parseResp(ResponseUtil.getResult(appResource));
+        if (ResponseUtil.isFail(resp)) {
+            return resp;
+        }
+        saveAppInfos(ResponseUtil.getResult(resp));
+        return ResponseStatus.success();
+    }
+
+    private List<ApplyInfo> convertToAppInfo(List<FhResourceRespDTO> fhApps) {
+        if (CollectionUtils.isEmpty(fhApps)) {
+            return Collections.emptyList();
+        }
+        List<ApplyInfo> collect = fhApps.stream().map(this::getAppInfo).collect(Collectors.toList());
+
+        // 查询机构信息
+        Set<String> orgCodes = new HashSet<>();
+        collect.forEach(e -> {
+            orgCodes.add(e.getOrgCode());
+            orgCodes.add(e.getManagerOrgCode());
+        });
+        List<OrgInfo> orgInfos = orgInfoFacade.getOrgsByCodes(new ArrayList<>(orgCodes));
+        Map<String, String> orgNameMap = orgInfos.stream()
+                .collect(Collectors.toMap(OrgInfo::getCode, OrgInfo::getFullName));
+
+        // 设置机构信息和密钥信息
+        collect.forEach(e -> {
+            String orgName = orgNameMap.get(e.getOrgCode());
+            e.setOrgName(orgName);
+            String manageOrgName = orgNameMap.get(e.getManagerOrgCode());
+            e.setManagerOrgName(manageOrgName);
+            String apiKey = getApiKeys(e.getApplyCode());
+            String apiSecret = getApiKeys(e.getApplyCode());
+            e.setApiKey(apiKey);
+            e.setSecretKey(apiSecret);
+        });
+
+        return collect;
+    }
+
+    private String getApiKeys(String value) {
+        StringBuilder num = new StringBuilder();
+        for (int i = 0; i < 8; i++) {
+            int random = (int) (Math.random() * 10);
+            num.append(random);
+        }
+        return value + num;
+    }
+
+    private ApplyInfo getAppInfo(FhResourceRespDTO dto) {
+        ApplyInfo app = new ApplyInfo();
+        app.setApplyCode(dto.getYyxtbh());
+        app.setApplyName(dto.getYyxtmc());
+        //应用状态和我们自己的系统标识转换
+        Long xtzybs = dto.getXtzybs();
+        if (ObjectUtils.isNotEmpty(xtzybs)) {
+            if (Long.valueOf(1L).equals(xtzybs)) {
+                app.setApplyStatus(BooleanEnum.FALSE.value);
+            } else {
+                app.setApplyStatus(BooleanEnum.TRUE.value);
+            }
+        }
+        app.setAppOpsDepName(dto.getYyxtywdwdm());
+        app.setApplyUrl(dto.getYyxtfwdz());
+        app.setOrgCode(dto.getYyxtsqdwdm());
+        app.setManagerOrgCode(dto.getYyxtgldwdm());
+        app.setManagerDescribe(dto.getYyxtsm());
+        app.setDeleted(BooleanEnum.FALSE.value);
+        String sxrq = dto.getSxrq();
+        if (!StringUtils.isEmpty(sxrq)) {
+            app.setLineTime(sxrq);
+            SimpleDateFormat format = new SimpleDateFormat("yyyy-MM-dd");
+            try {
+                Date parse = format.parse(sxrq);
+                app.setRegistrationTime(parse);
+            } catch (Exception e) {
+                log.error("日期解析异常");
+            }
+        }
+        app.setApplyCategory(dto.getYyxtfldm());
+        return app;
+    }
+
+    protected ResponseDTO<List<ApplyInfo>> parseResp(FhAppIndexRespDTO appResource) {
+        if (null == appResource) {
+            log.error("响应结果为空");
+            return ResponseDTO.fail("同步失败", (Object) null);
+        }
+        String messageStatus = appResource.getMessageStatus();
+        String remark = appResource.getRemark();
+        log.info("调用应用同步接口接口返回 messageStatus:{}, remark:{}", messageStatus, remark);
+        if (!FH_SUCCESS_STATUS.equals(messageStatus)) {
+            return ResponseDTO.fail("同步失败", (Object) null);
+        }
+        FhResponseParamRespDTO responseParam = appResource.getResponseParam();
+        Long totalNum = responseParam.getTotalNum();
+        log.info("同步获取的应用资源数量:{}", totalNum);
+        List<FhResourceRespDTO> resources = responseParam.getResources();
+        List<ApplyInfo> applyInfos = convertToAppInfo(resources);
+        return ResponseDTO.success("", applyInfos);
+    }
+
+    protected ResponseDTO<FhAppIndexRespDTO> getAppResource() {
+        String address = fhAppSyncProperties.getAddress();
+        log.info("同步应用资源地址:{}", address);
+        HttpEntity<Map<String,String>> httpEntity = new HttpEntity<>(Collections.emptyMap());
+        ResponseEntity<String> exchange = restTemplate.exchange(address, HttpMethod.POST, httpEntity, String.class);
+        if (!exchange.getStatusCode().is2xxSuccessful()) {
+            log.error("调用同步接口响应异常. 响应结果:{}", JsonUtils.toJSONString(exchange));
+            return ResponseDTO.fail("同步失败", (Object) null);
+        }
+        String body = exchange.getBody();
+        // 解析响应结果
+        if (StringUtils.isBlank(body)) {
+            log.error("同步应用资源,响应内容为空");
+            return ResponseDTO.fail("同步失败", (Object) null);
+        }
+
+        ObjectMapper objectMapper = new ObjectMapper();
+        try {
+            FhAppIndexRespDTO fhAppIndexRespDTO = objectMapper.readValue(body, FhAppIndexRespDTO.class);
+            return ResponseDTO.success("", fhAppIndexRespDTO);
+        } catch (JsonProcessingException e) {
+            log.error("解析同步结果异常.", e);
+            return ResponseDTO.fail("同步失败", (Object) null);
+        }
+    }
+
+    private void saveAppInfos(List<ApplyInfo> applyInfoList) {
+        if (CollectionUtils.isEmpty(applyInfoList)) {
+            return;
+        }
+        // 查询已有的应用信息
+        List<ApplyInfo> all = applyInfoService.findAll();
+        Map<String, ApplyInfo> existMap = all.stream()
+                .collect(Collectors.toMap(ApplyInfo::getApplyCode, e -> e));
+        // 判断插入或是更新
+        Map<Boolean, List<ApplyInfo>> collect = applyInfoList.stream()
+                .collect(Collectors.partitioningBy(e -> existMap.containsKey(e.getApplyCode())));
+        List<ApplyInfo> saveApps = collect.get(Boolean.FALSE);
+        // 保存应用时同时保存密钥信息
+        if (CollectionUtils.isNotEmpty(saveApps)) {
+            applyInfoService.batchSave(saveApps);
+            List<ApplyOauth> oauthList = saveApps.stream()
+                    .map(e -> {
+                        ApplyOauth applyOauth = new ApplyOauth();
+                        applyOauth.setDeleted(BooleanEnum.FALSE.value);
+                        applyOauth.setApiKey(e.getApiKey());
+                        applyOauth.setSecretKey(e.getSecretKey());
+                        applyOauth.setApplyId(e.getId());
+                        return applyOauth;
+                    }).collect(Collectors.toList());
+            applyOauthService.saveAll(oauthList);
+        }
+        List<ApplyInfo> updateApps = collect.get(Boolean.TRUE);
+        // 更新时不能修改的字段
+        if (CollectionUtils.isNotEmpty(updateApps)) {
+            List<ApplyInfo> existUpdateApps = updateApps.stream()
+                    .map(e -> {
+                        ApplyInfo existApp = existMap.get(e.getApplyCode());
+                        BeanUtil.copyProperties(e, existApp, "id", "apiKey", "secretKey");
+                        return existApp;
+                    }).collect(Collectors.toList());
+            applyInfoService.batchUpdate(existUpdateApps);
+        }
+    }
+}

+ 18 - 0
dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/config/FhAppSyncProperties.java

@@ -0,0 +1,18 @@
+package com.dragoninfo.dcuc.app.config;
+
+import lombok.Data;
+import org.springframework.boot.context.properties.ConfigurationProperties;
+import org.springframework.context.annotation.Configuration;
+
+/**
+ * @author mazq
+ * @date 2023/7/20
+ */
+@Data
+@Configuration
+@ConfigurationProperties(prefix = "dcuc.app.fh.app-sync")
+public class FhAppSyncProperties {
+
+    private String address;
+
+}

+ 23 - 0
dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/config/RestTemplateConfig.java

@@ -0,0 +1,23 @@
+package com.dragoninfo.dcuc.app.config;
+
+import com.dragoninfo.dcuc.common.http.SkipSslVerificationHttpRequestFactory;
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.Configuration;
+import org.springframework.web.client.RestTemplate;
+
+/**
+ * @author mazq
+ * @date 2023/2/23
+ */
+@Configuration
+public class RestTemplateConfig {
+
+    @Bean
+    public RestTemplate restTemplate() {
+        SkipSslVerificationHttpRequestFactory skipSslVerificationHttpRequestFactory
+                = new SkipSslVerificationHttpRequestFactory();
+
+        return new RestTemplate(skipSslVerificationHttpRequestFactory);
+    }
+
+}

+ 20 - 0
dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/facade/ResourceFacade.java

@@ -1,5 +1,6 @@
 package com.dragoninfo.dcuc.app.facade;
 
+import com.dragoninfo.dcuc.app.business.IFhAppSyncBusiness;
 import com.dragoninfo.dcuc.app.business.IResourceBusiness;
 import com.dragoninfo.dcuc.app.dto.*;
 import com.dragoninfo.dcuc.app.dto.statistics.ResourceStatisticsDto;
@@ -44,6 +45,9 @@ public class ResourceFacade implements IResourceFacade {
     @Autowired
     IResourceBusiness iResourceBusiness;
 
+    @Autowired
+    IFhAppSyncBusiness fhAppSyncBusiness;
+
     @Override
     public ResourceSyncDTO insertResourceSync(ResourceSyncDTO dto) {
         ResourceSync resourceSync = syncService.insertRemoteResourceSync(dto);
@@ -109,6 +113,22 @@ public class ResourceFacade implements IResourceFacade {
         return ResponseStatus.success();
     }
 
+    @Override
+    public ResponseStatus fhAppSync() {
+        RequestAttributes requestAttributes = RequestContextHolder.getRequestAttributes();
+        Runnable r = ()->{
+            RequestContextHolder.setRequestAttributes(requestAttributes);
+            try {
+                fhAppSyncBusiness.syncAppInfo();
+            } finally {
+                RequestContextHolder.resetRequestAttributes();
+            }
+        };
+        Thread t = new Thread(r);
+        t.start();
+        return ResponseStatus.success();
+    }
+
     @Override
     public ResourceStatisticsDto count(Date startTime, Date endTime) {
         return iResourceBusiness.count(startTime, endTime);

+ 14 - 0
dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/facade/sub/AppDataItemInfoFacade.java

@@ -5,10 +5,13 @@ import com.dragoninfo.dcuc.app.entity.sub.AppDataItemInfo;
 import com.dragoninfo.dcuc.app.entity.sub.AppDataResourceInfo;
 import com.dragoninfo.dcuc.app.service.sub.IAppDataItemInfoService;
 import com.dragoninfo.dcuc.app.vo.AppDataItemInfoRespVO;
+import com.dragoninfo.dcuc.app.vo.AppDataItemPageVo;
 import com.dragoninfo.dcuc.app.vo.AppDataResourceInfoRespVO;
+import com.dragonsoft.duceap.base.entity.http.ResponseStatus;
 import com.dragonsoft.duceap.base.entity.search.SearchDTO;
 import com.dragonsoft.duceap.core.search.Searchable;
 import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.data.domain.Page;
 import org.springframework.web.bind.annotation.RequestMapping;
 import org.springframework.web.bind.annotation.RestController;
 
@@ -42,6 +45,17 @@ public class AppDataItemInfoFacade implements IAppDataItemInfoFacade {
         return toRespVOList(dataItemInfoList);
     }
 
+    @Override
+    public Page<AppDataItemPageVo> pageSearch(SearchDTO searchDTO) {
+        return appDataItemInfoService.pageSearch(searchDTO);
+    }
+
+    @Override
+    public ResponseStatus deleteById(String id) {
+        appDataItemInfoService.deleteById(id);
+        return ResponseStatus.success();
+    }
+
     private List<AppDataItemInfoRespVO> toRespVOList(List<AppDataItemInfo> dataItemInfoList) {
         List<AppDataItemInfoRespVO> respVOList = new ArrayList<>(dataItemInfoList.size());
         for (AppDataItemInfo appDataItemInfo : dataItemInfoList) {

+ 24 - 0
dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/facade/sub/AppDataResourceInfoFacade.java

@@ -4,14 +4,19 @@ import cn.hutool.core.bean.BeanUtil;
 import com.dragoninfo.dcuc.app.entity.sub.AppDataResourceInfo;
 import com.dragoninfo.dcuc.app.service.sub.IAppDataResourceInfoService;
 import com.dragoninfo.dcuc.app.vo.AppDataResourceInfoRespVO;
+import com.dragoninfo.dcuc.app.vo.AppDataResourcePageVo;
+import com.dragoninfo.dcuc.common.utils.DcucBeanUtil;
+import com.dragonsoft.duceap.base.entity.http.ResponseStatus;
 import com.dragonsoft.duceap.base.entity.search.SearchDTO;
 import com.dragonsoft.duceap.core.search.Searchable;
 import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.data.domain.Page;
 import org.springframework.web.bind.annotation.RequestMapping;
 import org.springframework.web.bind.annotation.RestController;
 
 import java.util.ArrayList;
 import java.util.List;
+import java.util.Optional;
 
 /**
  * <p>
@@ -50,4 +55,23 @@ public class AppDataResourceInfoFacade implements IAppDataResourceInfoFacade {
         BeanUtil.copyProperties(appDataResourceInfo, appDataResourceInfoRespVO);
         return appDataResourceInfoRespVO;
     }
+
+    @Override
+    public Page<AppDataResourcePageVo> pageSearch(SearchDTO searchDTO) {
+        return appDataResourceInfoService.pageSearch(searchDTO);
+    }
+
+    @Override
+    public AppDataResourceInfoRespVO getById(String id) {
+        AppDataResourceInfo resourceInfo = appDataResourceInfoService.getById(id);
+        return Optional.ofNullable(resourceInfo)
+                .map(e-> DcucBeanUtil.createCopyToObject(e, AppDataResourceInfoRespVO.class))
+                .orElse(null);
+    }
+
+    @Override
+    public ResponseStatus deleteById(String id) {
+        appDataResourceInfoService.deleteById(id);
+        return ResponseStatus.success();
+    }
 }

+ 12 - 0
dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/service/IApplyInfoService.java

@@ -270,4 +270,16 @@ public interface IApplyInfoService {
      * @return
      */
     Long count(Date startTime, Date endTime);
+
+    /**
+     * 批量保存
+     * @param saveApps
+     */
+    void batchSave(List<ApplyInfo> saveApps);
+
+    /**
+     * 批量更新
+     * @param existUpdateApps
+     */
+    void batchUpdate(List<ApplyInfo> existUpdateApps);
 }

+ 32 - 3
dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/service/impl/ApplyInfoServiceImpl.java

@@ -5,6 +5,7 @@ import cn.hutool.core.util.StrUtil;
 import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
 import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
 import com.baomidou.mybatisplus.core.toolkit.Wrappers;
+import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
 import com.dragoninfo.dcuc.app.dto.ApplyInfoDTO;
 import com.dragoninfo.dcuc.app.entity.ApplyInfo;
 import com.dragoninfo.dcuc.app.entity.ManufacturerInfo;
@@ -27,6 +28,7 @@ import com.dragonsoft.duceap.base.enums.BooleanEnum;
 import com.dragonsoft.duceap.core.search.Searchable;
 import org.apache.commons.collections4.CollectionUtils;
 import org.apache.commons.lang3.StringUtils;
+import org.apache.ibatis.session.SqlSession;
 import org.apache.poi.hssf.usermodel.HSSFWorkbook;
 import org.apache.poi.ss.usermodel.Cell;
 import org.apache.poi.ss.usermodel.Row;
@@ -57,7 +59,7 @@ import java.util.stream.Collectors;
  */
 @CacheConfig(cacheNames = "DCUC-APP-APP")
 @Service
-public class ApplyInfoServiceImpl implements IApplyInfoService {
+public class ApplyInfoServiceImpl extends ServiceImpl<ApplyInfoMapper, ApplyInfo> implements IApplyInfoService {
 
     @Autowired
     private ApplyInfoMapper applyInfoMapper;
@@ -91,8 +93,8 @@ public class ApplyInfoServiceImpl implements IApplyInfoService {
     public Page<ApplyInfo> applyInfoPage(SearchDTO searchDTO) {
 
         Searchable searchable = Searchable.toSearchable(searchDTO);
-        searchable.addSort(Sort.Direction.DESC, "SORT");
         searchable.addSort(Sort.Direction.DESC, "REGISTRATION_TIME");
+        searchable.addSort(Sort.Direction.DESC, "SORT");
         return applyInfoMapper.pagingBySearchable(searchable);
     }
 
@@ -272,7 +274,7 @@ public class ApplyInfoServiceImpl implements IApplyInfoService {
     @Cacheable(key = "targetClass + methodName+#p0")
     @Override
     public List<ApplyInfo> getAppById(List<String> ids) {
-        if(CollectionUtils.isEmpty(ids)) {
+        if (CollectionUtils.isEmpty(ids)) {
             return Collections.emptyList();
         }
         return applyInfoMapper.selectBatchIds(ids);
@@ -486,6 +488,30 @@ public class ApplyInfoServiceImpl implements IApplyInfoService {
         return Long.valueOf(applyInfoMapper.selectCount(query));
     }
 
+    @Transactional(rollbackFor = Exception.class)
+    @Override
+    public void batchSave(List<ApplyInfo> saveApps) {
+        if (CollectionUtils.isEmpty(saveApps)) {
+            return;
+        }
+        super.saveBatch(saveApps);
+    }
+
+    @Transactional(rollbackFor = Exception.class)
+    @Override
+    public void batchUpdate(List<ApplyInfo> existUpdateApps) {
+        if (CollectionUtils.isEmpty(existUpdateApps)) {
+            return;
+        }
+        try (SqlSession sqlSession = sqlSessionBatch()) {
+            ApplyInfoMapper mapper = sqlSession.getMapper(ApplyInfoMapper.class);
+            for (ApplyInfo existUpdateApp : existUpdateApps) {
+                mapper.updateById(existUpdateApp);
+            }
+            sqlSession.flushStatements();
+        }
+    }
+
     @Override
     public List<ApplyInfo> findList(String applyStatus) {
         LambdaQueryWrapper<ApplyInfo> queryWrapper = new LambdaQueryWrapper<>();
@@ -701,6 +727,9 @@ public class ApplyInfoServiceImpl implements IApplyInfoService {
 
     @Override
     public List<ApplyInfo> getListByCodes(List<String> appCodes) {
+        if (CollectionUtils.isEmpty(appCodes)) {
+            return Collections.emptyList();
+        }
         LambdaQueryWrapper<ApplyInfo> queryWrapper = new LambdaQueryWrapper<>();
         LambdaQueryWrapper<ApplyInfo> wrapper = queryWrapper.select().in(ApplyInfo::getApplyCode, appCodes);
         return applyInfoMapper.selectList(wrapper);

+ 15 - 0
dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/service/sub/IAppDataItemInfoService.java

@@ -2,8 +2,10 @@ package com.dragoninfo.dcuc.app.service.sub;
 
 import com.dragoninfo.dcuc.app.entity.sub.AppDataItemInfo;
 import com.dragoninfo.dcuc.app.vo.AppDataItemInfoRespVO;
+import com.dragoninfo.dcuc.app.vo.AppDataItemPageVo;
 import com.dragonsoft.duceap.base.entity.search.SearchDTO;
 import com.dragonsoft.duceap.core.search.Searchable;
+import org.springframework.data.domain.Page;
 import org.springframework.web.bind.annotation.GetMapping;
 import org.springframework.web.bind.annotation.PostMapping;
 import org.springframework.web.bind.annotation.RequestBody;
@@ -79,4 +81,17 @@ public interface IAppDataItemInfoService {
      * @return
      */
     Long count(Date startTime, Date endTime);
+
+    /**
+     * 分页查询
+     * @param searchDTO
+     * @return
+     */
+    Page<AppDataItemPageVo> pageSearch(SearchDTO searchDTO);
+
+    /**
+     * 根据id删除
+     * @param id
+     */
+    void deleteById(String id);
 }

+ 30 - 0
dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/service/sub/IAppDataResourceInfoService.java

@@ -1,7 +1,10 @@
 package com.dragoninfo.dcuc.app.service.sub;
 
 import com.dragoninfo.dcuc.app.entity.sub.AppDataResourceInfo;
+import com.dragoninfo.dcuc.app.vo.AppDataResourcePageVo;
+import com.dragonsoft.duceap.base.entity.search.SearchDTO;
 import com.dragonsoft.duceap.core.search.Searchable;
+import org.springframework.data.domain.Page;
 
 import java.util.List;
 
@@ -63,4 +66,31 @@ public interface IAppDataResourceInfoService {
      * @return 数据资源
      */
     AppDataResourceInfo findByResourceCode(String resourceCode);
+
+    /**
+     * 根据id查询
+     * @param ids
+     * @return
+     */
+    List<AppDataResourceInfo> getByIds(List<String> ids);
+
+    /**
+     * 分页查询
+     * @param searchDTO
+     * @return
+     */
+    Page<AppDataResourcePageVo> pageSearch(SearchDTO searchDTO);
+
+    /**
+     * 查询详情
+     * @param id
+     * @return
+     */
+    AppDataResourceInfo getById(String id);
+
+    /**
+     * 删除
+     * @param id
+     */
+    void deleteById(String id);
 }

+ 37 - 0
dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/service/sub/impl/AppDataItemInfoServiceImpl.java

@@ -4,16 +4,23 @@ import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
 import com.baomidou.mybatisplus.core.toolkit.Wrappers;
 import com.dragoninfo.dcuc.app.entity.ServiceResource;
 import com.dragoninfo.dcuc.app.entity.sub.AppDataItemInfo;
+import com.dragoninfo.dcuc.app.entity.sub.AppDataResourceInfo;
 import com.dragoninfo.dcuc.app.mapper.sub.AppDataItemInfoMapper;
 import com.dragoninfo.dcuc.app.service.sub.IAppDataItemInfoService;
+import com.dragoninfo.dcuc.app.service.sub.IAppDataResourceInfoService;
+import com.dragoninfo.dcuc.app.vo.AppDataItemPageVo;
+import com.dragoninfo.dcuc.common.utils.DcucBeanUtil;
+import com.dragonsoft.duceap.base.entity.search.SearchDTO;
 import com.dragonsoft.duceap.commons.util.string.StringUtils;
 import com.dragonsoft.duceap.core.search.Searchable;
 import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.data.domain.Page;
 import org.springframework.stereotype.Service;
 import org.springframework.transaction.annotation.Transactional;
 
 import java.util.Date;
 import java.util.List;
+import java.util.Map;
 import java.util.stream.Collectors;
 
 /**
@@ -30,6 +37,9 @@ public class AppDataItemInfoServiceImpl implements IAppDataItemInfoService {
     @Autowired
     private AppDataItemInfoMapper appDataItemInfoMapper;
 
+    @Autowired
+    private IAppDataResourceInfoService appDataResourceInfoService;
+
     @Transactional(rollbackFor = Throwable.class)
     @Override
     public void saveAll(List<AppDataItemInfo> appDataItemInfoList) {
@@ -85,6 +95,33 @@ public class AppDataItemInfoServiceImpl implements IAppDataItemInfoService {
         return Long.valueOf(appDataItemInfoMapper.selectCount(query));
     }
 
+    @Override
+    public Page<AppDataItemPageVo> pageSearch(SearchDTO searchDTO) {
+        Searchable searchable = Searchable.toSearchable(searchDTO);
+        Page<AppDataItemInfo> appDataItemInfos = appDataItemInfoMapper.pagingBySearchable(searchable);
+        Page<AppDataItemPageVo> page = DcucBeanUtil.createCopyToObjectPage(appDataItemInfos, AppDataItemPageVo.class);
+        // 查询数据集资源
+        List<String> tableIds = page.getContent()
+                .stream()
+                .map(AppDataItemPageVo::getResourceTableId).distinct()
+                .collect(Collectors.toList());
+        List<AppDataResourceInfo> tableInfos = appDataResourceInfoService.getByIds(tableIds);
+        Map<String, String> tableNameMap = tableInfos.stream()
+                .collect(Collectors.toMap(AppDataResourceInfo::getId, AppDataResourceInfo::getResourceName));
+        page.getContent().forEach(e -> {
+            String resourceTableId = e.getResourceTableId();
+            e.setAppDataResourceName(tableNameMap.get(resourceTableId));
+        });
+
+        return page;
+    }
+
+    @Transactional(rollbackFor = Throwable.class)
+    @Override
+    public void deleteById(String id) {
+        appDataItemInfoMapper.deleteById(id);
+    }
+
     @Override
     public List<AppDataItemInfo> getHasClassifyColInfos() {
         LambdaQueryWrapper<AppDataItemInfo> query = Wrappers.lambdaQuery();

+ 101 - 2
dcuc-app-service/src/main/java/com/dragoninfo/dcuc/app/service/sub/impl/AppDataResourceInfoServiceImpl.java

@@ -1,19 +1,29 @@
 package com.dragoninfo.dcuc.app.service.sub.impl;
 
+import cn.hutool.core.util.StrUtil;
 import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
 import com.baomidou.mybatisplus.core.toolkit.Wrappers;
+import com.dragoninfo.dcuc.app.entity.ApplyInfo;
 import com.dragoninfo.dcuc.app.entity.sub.AppDataResourceInfo;
 import com.dragoninfo.dcuc.app.mapper.sub.AppDataResourceInfoMapper;
+import com.dragoninfo.dcuc.app.service.IApplyInfoService;
 import com.dragoninfo.dcuc.app.service.sub.IAppDataResourceInfoService;
-import com.dragonsoft.duceap.commons.util.string.StringUtils;
+import com.dragoninfo.dcuc.app.vo.AppDataResourcePageVo;
+import com.dragoninfo.dcuc.common.utils.DcucBeanUtil;
+import com.dragoninfo.dcuc.user.entity.org.OrgInfo;
+import com.dragoninfo.dcuc.user.facade.org.IOrgInfoFacade;
 import com.dragonsoft.duceap.base.entity.search.SearchDTO;
+import com.dragonsoft.duceap.commons.util.string.StringUtils;
 import com.dragonsoft.duceap.core.search.Searchable;
+import org.apache.commons.collections4.CollectionUtils;
 import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.data.domain.Page;
 import org.springframework.stereotype.Service;
 import org.springframework.transaction.annotation.Transactional;
 
-import java.util.List;
+import java.util.*;
 import java.util.stream.Collectors;
+import java.util.stream.Stream;
 
 /**
  * <p>
@@ -29,6 +39,12 @@ public class AppDataResourceInfoServiceImpl implements IAppDataResourceInfoServi
     @Autowired
     private AppDataResourceInfoMapper appDataResourceInfoMapper;
 
+    @Autowired
+    private IApplyInfoService applyInfoService;
+
+    @Autowired
+    private IOrgInfoFacade orgInfoFacade;
+
     @Transactional(rollbackFor = Throwable.class)
     @Override
     public void saveAll(List<AppDataResourceInfo> resourceInfoList) {
@@ -92,4 +108,87 @@ public class AppDataResourceInfoServiceImpl implements IAppDataResourceInfoServi
         queryWrapper.eq(AppDataResourceInfo::getResourceCode, resourceCode);
         return appDataResourceInfoMapper.selectOne(queryWrapper);
     }
+
+    @Override
+    public List<AppDataResourceInfo> getByIds(List<String> ids) {
+        if (CollectionUtils.isEmpty(ids)) {
+            return Collections.emptyList();
+        }
+        LambdaQueryWrapper<AppDataResourceInfo> query = Wrappers.lambdaQuery();
+        query.in(AppDataResourceInfo::getId, ids);
+        return appDataResourceInfoMapper.selectList(query);
+    }
+
+    @Override
+    public Page<AppDataResourcePageVo> pageSearch(SearchDTO searchDTO) {
+        Searchable searchable = Searchable.toSearchable(searchDTO);
+        Page<AppDataResourceInfo> page = appDataResourceInfoMapper.pagingBySearchable(searchable);
+        Page<AppDataResourcePageVo> pageVos = DcucBeanUtil.createCopyToObjectPage(page, AppDataResourcePageVo.class, (s, t) -> {
+            String labelName = Stream.of(s.getDataLabelOneName(), s.getDataLabelTwoName(),
+                            s.getDataLabelThreeName(), s.getDataLabelFourName(),
+                            s.getDataLabelFiveName()).filter(StringUtils::isNotBlank)
+                    .collect(Collectors.joining(StrUtil.COMMA));
+            t.setLabelName(labelName);
+            return t;
+        });
+
+        // 查询应用名和机构名
+        List<String> appCodes = pageVos.stream()
+                .map(AppDataResourcePageVo::getApplicationCode)
+                .distinct()
+                .collect(Collectors.toList());
+        List<ApplyInfo> appInfos = applyInfoService.getListByCodes(appCodes);
+
+        Map<String, ApplyInfo> appInfoMap = appInfos.stream()
+                .collect(Collectors.toMap(ApplyInfo::getApplyCode, e -> e));
+
+        // 查询机构名称
+        Set<String> orgCodeSet = new HashSet<>();
+        pageVos.stream().forEach(e -> {
+            orgCodeSet.add(e.getManageDeptCode());
+            orgCodeSet.add(e.getAuthorityDeptCode());
+        });
+
+        List<OrgInfo> orgInfos = orgInfoFacade.getOrgsByCodes(new ArrayList<>(orgCodeSet));
+        Map<String, OrgInfo> orgInMap = orgInfos.stream()
+                .collect(Collectors.toMap(OrgInfo::getCode, e -> e));
+
+        // 设置Vo字段名称
+        pageVos.stream().forEach(e -> {
+            String appName = Optional.ofNullable(appInfoMap.get(e.getApplicationCode()))
+                    .map(ApplyInfo::getApplyName)
+                    .orElse(null);
+            e.setApplicationCodeName(appName);
+
+            String authorityDeptCode = e.getAuthorityDeptCode();
+            String authorityDeptName = Optional.ofNullable(orgInMap.get(authorityDeptCode))
+                    .map(OrgInfo::getFullName)
+                    .orElse(null);
+            e.setAuthorityDeptName(authorityDeptName);
+
+            String manageDeptCode = e.getManageDeptCode();
+            String manageDeptName = Optional.ofNullable(orgInMap.get(manageDeptCode))
+                    .map(OrgInfo::getFullName)
+                    .orElse(null);
+            e.setManageDeptName(manageDeptName);
+        });
+
+        return pageVos;
+    }
+
+    @Override
+    public AppDataResourceInfo getById(String id) {
+        if (StringUtils.isBlank(id)) {
+            return null;
+        }
+        return appDataResourceInfoMapper.selectById(id);
+    }
+
+    @Override
+    public void deleteById(String id) {
+        if (StringUtils.isBlank(id)) {
+            return;
+        }
+        appDataResourceInfoMapper.deleteById(id);
+    }
 }

+ 4 - 1
dcuc-app-service/src/main/resources/application-app.yml

@@ -39,4 +39,7 @@ dcuc:
       data-resource:
         data-catalog-url: http://10.201.8.40:9977
       resource-url: http://10.201.7.31:8585/bus/send
-      bu-service-url: http://10.11.0.41:8081/ddos/v1/ministryResources/searchMinistryResources
+      bu-service-url: http://10.11.0.41:8081/ddos/v1/ministryResources/searchMinistryResources
+      fh:
+        app-sync:
+          address: http://130.0.56.174:9988/metadata/app/resource/QueryDataResource

+ 112 - 0
dcuc-app-service/src/test/java/com/dragoninfo/dcuc/app/business/impl/FhAppSyncBusinessImplTerst.java

@@ -0,0 +1,112 @@
+package com.dragoninfo.dcuc.app.business.impl;
+
+import com.dragoninfo.dcuc.app.business.impl.FhAppSyncBusinessImpl;
+import com.dragoninfo.dcuc.app.config.FhAppSyncProperties;
+import com.dragoninfo.dcuc.app.dto.appindex.FhAppIndexRespDTO;
+import com.dragoninfo.dcuc.app.dto.appindex.FhResourceRespDTO;
+import com.dragoninfo.dcuc.app.entity.ApplyInfo;
+import com.dragoninfo.dcuc.common.http.SkipSslVerificationHttpRequestFactory;
+import com.dragoninfo.dcuc.common.utils.ResponseUtil;
+import com.dragoninfo.dcuc.user.entity.org.OrgInfo;
+import com.dragoninfo.dcuc.user.facade.org.IOrgInfoFacade;
+import com.dragonsoft.duceap.base.entity.http.ResponseDTO;
+import com.dragonsoft.duceap.commons.util.ObjectUtils;
+import com.github.dreamhead.moco.HttpServer;
+import com.github.dreamhead.moco.Runner;
+import org.junit.*;
+import org.junit.platform.commons.util.StringUtils;
+import org.mockito.Mock;
+import org.mockito.Mockito;
+import org.springframework.web.client.RestTemplate;
+
+import java.util.ArrayList;
+import java.util.Date;
+import java.util.List;
+
+import static com.github.dreamhead.moco.Moco.*;
+
+/**
+ * @author mazq
+ * @date 2023/7/20
+ */
+public class FhAppSyncBusinessImplTerst {
+
+    public static FhAppSyncBusinessImpl fhAppSyncBusiness;
+
+    public static Runner runner;
+
+    public static String address = "/metadata/app/resource/QueryDataResource";
+
+    @BeforeClass
+    public static void before() {
+
+        // 远程调用服务
+        HttpServer httpServer = httpServer(19988, log());
+        httpServer.request(by(uri(address)))
+                .response(pathResource("fh/app.json"));
+        runner = Runner.runner(httpServer);
+        runner.start();
+
+        fhAppSyncBusiness = new FhAppSyncBusinessImpl();
+        FhAppSyncProperties fhAppSyncProperties = new FhAppSyncProperties();
+        // 配置文件
+        fhAppSyncProperties.setAddress("http://127.0.0.1:19988" + address);
+        fhAppSyncBusiness.setFhAppSyncProperties(fhAppSyncProperties);
+        // 机构查询
+        IOrgInfoFacade orgInfoFacade = Mockito.spy(IOrgInfoFacade.class);
+        List<OrgInfo> orgInfos = new ArrayList<>();
+        OrgInfo orgInfo = new OrgInfo();
+        orgInfo.setCode("120000000000");
+        orgInfo.setFullName("天津市GAJ");
+        orgInfos.add(orgInfo);
+        Mockito.when(orgInfoFacade.getOrgsByCodes(Mockito.anyList()))
+                .thenReturn(orgInfos);
+        fhAppSyncBusiness.setOrgInfoFacade(orgInfoFacade);
+
+        // restTemplate
+        SkipSslVerificationHttpRequestFactory skipSslVerificationHttpRequestFactory
+                = new SkipSslVerificationHttpRequestFactory();
+        skipSslVerificationHttpRequestFactory.setReadTimeout(5000);
+        skipSslVerificationHttpRequestFactory.setConnectTimeout(5000);
+        RestTemplate restTemplate = new RestTemplate(skipSslVerificationHttpRequestFactory);
+        fhAppSyncBusiness.setRestTemplate(restTemplate);
+    }
+
+    @AfterClass
+    public static void after() {
+        runner.stop();
+    }
+
+    @Test
+    public void appSyncTest() {
+        ResponseDTO<FhAppIndexRespDTO> appResource = fhAppSyncBusiness.getAppResource();
+        FhAppIndexRespDTO result = ResponseUtil.getResult(appResource);
+        ResponseDTO<List<ApplyInfo>> appInfoResp = fhAppSyncBusiness.parseResp(result);
+        List<ApplyInfo> applyInfos = ResponseUtil.getResult(appInfoResp);
+        applyInfos.forEach(e -> {
+            String orgCode = e.getOrgCode();
+            String orgName = e.getOrgName();
+            String managerOrgCode = e.getManagerOrgCode();
+            String managerOrgName = e.getManagerOrgName();
+            String applyCode = e.getApplyCode();
+            String applyStatus = e.getApplyStatus();
+            String applyName = e.getApplyName();
+            String lineTime = e.getLineTime();
+            Date registrationTime = e.getRegistrationTime();
+            String apiKey = e.getApiKey();
+            String secretKey = e.getSecretKey();
+            Assert.assertEquals("120000000000", orgCode);
+            Assert.assertEquals("120000000000", managerOrgCode);
+            Assert.assertEquals("天津市GAJ", orgName);
+            Assert.assertEquals("天津市GAJ", managerOrgName);
+            Assert.assertEquals("0", applyStatus);
+            Assert.assertTrue(StringUtils.isNotBlank(applyCode));
+            Assert.assertTrue(StringUtils.isNotBlank(applyName));
+            Assert.assertTrue(StringUtils.isNotBlank(lineTime));
+            Assert.assertTrue(ObjectUtils.isNotEmpty(registrationTime));
+            Assert.assertTrue(StringUtils.isNotBlank(apiKey));
+            Assert.assertTrue(StringUtils.isNotBlank(secretKey));
+        });
+    }
+
+}

+ 73 - 0
dcuc-app-service/src/test/resources/fh/app.json

@@ -0,0 +1,73 @@
+{
+  "MessageStatus": "0200",
+  "MessageSequence": "2023-07-19 18:07:24",
+  "Remark": "正常",
+  "ResponseParam": {
+    "RegisterInfos": [],
+    "TotalNum": 3,
+    "Resources": [
+      {
+        "YYXTBH": "A-120000000000-3508",
+        "YYXTMC": "公安大数据治理平台",
+        "YYXTSM": "公安大数据治理平台",
+        "YYXTSQDWDM": "120000000000",
+        "YYXTGLDWDM": "120000000000",
+        "YYXTCJDWDM": "烽火",
+        "YYXTYWDWDM": "烽火",
+        "SXRQ": "2021-06-19",
+        "XXRQ": null,
+        "YYXTFLDM": "04",
+        "YYXTRZJB": "01",
+        "XTZYBS": 1,
+        "XTJGLX": "1",
+        "YYXTFWDZ": "http://130.0.46.34:11018",
+        "YWSYCJDM": "04",
+        "PTXTBH": null,
+        "YYLX": "1"
+      },
+      {
+        "YYXTBH": "A-120000000000-0001",
+        "YYXTMC": "公安大数据治理平台",
+        "YYXTSM": "进行公安大数据治理及管理工作",
+        "YYXTSQDWDM": "120000000000",
+        "YYXTGLDWDM": "120000000000",
+        "YYXTCJDWDM": "",
+        "YYXTYWDWDM": "",
+        "SXRQ": "2021-04-15",
+        "XXRQ": "",
+        "YYXTFLDM": "04",
+        "YYXTRZJB": "01",
+        "XTZYBS": 1,
+        "XTJGLX": "1",
+        "YYXTFWDZ": "",
+        "YWSYCJDM": "03",
+        "PTXTBH": null,
+        "YYLX": "1"
+      },
+      {
+        "YYXTBH": "A-120000000000-5517",
+        "YYXTMC": "智能助理",
+        "YYXTSM": "移动端快捷查询系统",
+        "YYXTSQDWDM": "120000000000",
+        "YYXTGLDWDM": "120000000000",
+        "YYXTCJDWDM": "",
+        "YYXTYWDWDM": "",
+        "SXRQ": "2023-01-05",
+        "XXRQ": "",
+        "YYXTFLDM": "01",
+        "YYXTRZJB": "01",
+        "XTZYBS": 1,
+        "XTJGLX": "2",
+        "YYXTFWDZ": "http://130.0.46.114:18080/?code=admin&state=1&policeNo=888888&policeInfoCode=000&policeCaseCode=000#/siri",
+        "YWSYCJDM": "01",
+        "PTXTBH": null,
+        "YYLX": "1"
+      }
+    ],
+    "FileName": "",
+    "FileDigest": "",
+    "FileSize": "",
+    "RelationId": null,
+    "Exception": []
+  }
+}

+ 23 - 7
pom.xml

@@ -23,6 +23,8 @@
         <oracle.version>11.2.0.1.0</oracle.version>
         <mysql.version>5.1.49</mysql.version>
         <lombok.version>1.18.8</lombok.version>
+        <moco.version>0.12.0</moco.version>
+        <embedded.redis.version>0.7.3</embedded.redis.version>
     </properties>
 
     <dependencyManagement>
@@ -66,13 +68,27 @@
                 <artifactId>nosql-elasticsearch-api</artifactId>
                 <version>1.0.0-SNAPSHOT</version>
             </dependency>
-            <!--接入配置中心使用依赖-->
-            <!--<dependency>
-               <groupId>com.dragonsoft.dyy</groupId>
-               <artifactId>nosql-plugins-springconfig</artifactId>
-               <version>1.0.0-SNAPSHOT</version>
-           </dependency>-->
-            <!--框架组Es组件结束-->
+
+            <dependency>
+                <groupId>it.ozimov</groupId>
+                <artifactId>embedded-redis</artifactId>
+                <version>${embedded.redis.version}</version>
+                <scope>test</scope>
+            </dependency>
+
+            <dependency>
+                <groupId>com.github.dreamhead</groupId>
+                <artifactId>moco-core</artifactId>
+                <version>${moco.version}</version>
+                <scope>test</scope>
+            </dependency>
+
+            <dependency>
+                <groupId>com.github.dreamhead</groupId>
+                <artifactId>moco-junit</artifactId>
+                <version>${moco.version}</version>
+                <scope>test</scope>
+            </dependency>
         </dependencies>
 
     </dependencyManagement>