Browse Source

完成风格评测接口迁移

wangzaijun 1 năm trước cách đây
mục cha
commit
f2d904750d
38 tập tin đã thay đổi với 4448 bổ sung1 xóa
  1. 102 0
      src/main/java/com/smppw/analysis/application/service/style/StyleService.java
  2. 1136 0
      src/main/java/com/smppw/analysis/application/service/style/StyleServiceImpl.java
  3. 1 1
      src/main/java/com/smppw/analysis/client/FundPositionApi.java
  4. 135 0
      src/main/java/com/smppw/analysis/client/FundStyleApi.java
  5. 23 0
      src/main/java/com/smppw/analysis/domain/dto/performance/AnalyzeCovParams.java
  6. 11 0
      src/main/java/com/smppw/analysis/domain/dto/performance/HistoryRetTableSingleData.java
  7. 14 0
      src/main/java/com/smppw/analysis/domain/dto/performance/HistoryRetTableSingleResp.java
  8. 12 0
      src/main/java/com/smppw/analysis/domain/dto/performance/HistoryRetTableSingleRet.java
  9. 18 0
      src/main/java/com/smppw/analysis/domain/dto/performance/ImfTrendParams.java
  10. 18 0
      src/main/java/com/smppw/analysis/domain/dto/performance/RangIndicatorParams.java
  11. 19 0
      src/main/java/com/smppw/analysis/domain/dto/performance/RankParams.java
  12. 26 0
      src/main/java/com/smppw/analysis/domain/dto/performance/RevenueParams.java
  13. 18 0
      src/main/java/com/smppw/analysis/domain/dto/performance/RollIndicatorParams.java
  14. 18 0
      src/main/java/com/smppw/analysis/domain/dto/performance/WinParams.java
  15. 11 0
      src/main/java/com/smppw/analysis/domain/dto/style/BarraStyleParams.java
  16. 55 0
      src/main/java/com/smppw/analysis/domain/dto/style/BaseParams.java
  17. 9 0
      src/main/java/com/smppw/analysis/domain/dto/style/BondAttributionParams.java
  18. 28 0
      src/main/java/com/smppw/analysis/domain/dto/style/CustomRbsaParams.java
  19. 44 0
      src/main/java/com/smppw/analysis/domain/dto/style/CustomRbsaVO.java
  20. 44 0
      src/main/java/com/smppw/analysis/domain/dto/style/FundStyleVO.java
  21. 9 0
      src/main/java/com/smppw/analysis/domain/dto/style/FutureFactorParams.java
  22. 24 0
      src/main/java/com/smppw/analysis/domain/dto/style/GrowthValueParams.java
  23. 24 0
      src/main/java/com/smppw/analysis/domain/dto/style/IndustryValueParams.java
  24. 9 0
      src/main/java/com/smppw/analysis/domain/dto/style/RelativeAttributionParams.java
  25. 38 0
      src/main/java/com/smppw/analysis/domain/dto/style/RzStyleParams.java
  26. 22 0
      src/main/java/com/smppw/analysis/domain/dto/style/SelectionTimingParams.java
  27. 9 0
      src/main/java/com/smppw/analysis/domain/dto/style/StockAttributionParams.java
  28. 36 0
      src/main/java/com/smppw/analysis/domain/dto/style/py/PyReq.java
  29. 17 0
      src/main/java/com/smppw/analysis/domain/dto/style/py/PyReqBody.java
  30. 40 0
      src/main/java/com/smppw/analysis/domain/dto/style/py/PyReqParam.java
  31. 27 0
      src/main/java/com/smppw/analysis/domain/dto/style/py/PyResBody.java
  32. 1287 0
      src/main/java/com/smppw/analysis/domain/manager/performance/AbstractPerformanceService.java
  33. 145 0
      src/main/java/com/smppw/analysis/domain/manager/performance/PerformanceService.java
  34. 946 0
      src/main/java/com/smppw/analysis/domain/manager/performance/PerformanceServiceImpl.java
  35. 5 0
      src/main/java/com/smppw/analysis/domain/manager/performance/package-info.java
  36. 21 0
      src/main/java/com/smppw/analysis/infrastructure/consts/AssetStyleType.java
  37. 24 0
      src/main/java/com/smppw/analysis/infrastructure/consts/Constraint.java
  38. 23 0
      src/main/java/com/smppw/analysis/infrastructure/consts/WinRateBmk.java

+ 102 - 0
src/main/java/com/smppw/analysis/application/service/style/StyleService.java

@@ -0,0 +1,102 @@
+package com.smppw.analysis.application.service.style;
+
+
+import com.smppw.analysis.domain.dto.style.*;
+
+import java.util.Map;
+
+/**
+ * @author wangzaijun
+ * @date 2023/3/10 18:29
+ * @description 风格测评 业务接口 (全部现金项先保留,MVP版本发布后去掉)
+ */
+public interface StyleService {
+    /**
+     * 股票五因子-业绩归因
+     *
+     * @param params 请求参数
+     * @return /
+     */
+    Map<String, Object> stockAttribution(StockAttributionParams params);
+
+    /**
+     * 债券业绩归因
+     *
+     * @param params 请求参数
+     * @return /
+     */
+    Map<String, Object> bondAttribution(BondAttributionParams params);
+
+    /**
+     * 相对价值业绩归因
+     *
+     * @param params 请求参数
+     * @return /
+     */
+    Map<String, Object> relativeAttribution(RelativeAttributionParams params);
+
+    /**
+     * 成长价值风格
+     *
+     * @param params 请求参数
+     * @return /
+     */
+    FundStyleVO growthValue(GrowthValueParams params);
+
+    /**
+     * 行业配置风格
+     *
+     * @param params 请求参数
+     * @return /
+     */
+    FundStyleVO industryValue(IndustryValueParams params);
+
+    /**
+     * 期货风格
+     *
+     * @param params 请求参数
+     * @return /
+     */
+    Map<String, Object> futureFactor(FutureFactorParams params);
+
+    /**
+     * 自定义风格
+     *
+     * @param params 请求参数
+     * @return /
+     */
+    CustomRbsaVO customRbsa(CustomRbsaParams params);
+
+    /**
+     * barra概览
+     *
+     * @param params 请求参数
+     * @return /
+     */
+    Map<String, Object> barraOverview(BarraStyleParams params);
+
+    /**
+     * barra风格
+     *
+     * @param params 请求参数
+     * @return /
+     */
+    Map<String, Object> barraRiskProfit(BarraStyleParams params);
+
+    /**
+     * 选股择时能力
+     *
+     * @param params 请求参数
+     * @return /
+     */
+    Map<String, Object> selectionTiming(SelectionTimingParams params);
+
+    /**
+     * 融智 风格总览 (融智改排排网)
+     * todo 存储过程转换
+     *
+     * @param params 请求参数
+     * @return /
+     */
+    Map<String, Object> rzStyle(RzStyleParams params);
+}

Những thai đổi đã bị hủy bỏ vì nó quá lớn
+ 1136 - 0
src/main/java/com/smppw/analysis/application/service/style/StyleServiceImpl.java


+ 1 - 1
src/main/java/com/smppw/analysis/client/FundPositionApi.java

@@ -21,7 +21,7 @@ import java.util.Map;
  * @description 基金 持仓分析,包括公募、私募基金,区分综合、股票、债券和期货tab组件
  */
 @RestController
-@RequestMapping("/v2/fund/position-analysis")
+@RequestMapping("/v1/api/position")
 public class FundPositionApi {
     //        private final BondPositionAnalysis bond;
     private final StockPositionAnalysis stock;

+ 135 - 0
src/main/java/com/smppw/analysis/client/FundStyleApi.java

@@ -0,0 +1,135 @@
+package com.smppw.analysis.client;
+
+import com.smppw.analysis.application.service.style.StyleService;
+import com.smppw.analysis.domain.dto.style.*;
+import com.smppw.common.pojo.ResultVo;
+import org.springframework.web.bind.annotation.GetMapping;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RestController;
+
+import java.util.Map;
+
+@RestController
+@RequestMapping("/v1/api/style")
+public class FundStyleApi {
+    private final StyleService service;
+
+    public FundStyleApi(StyleService service) {
+        this.service = service;
+    }
+
+    /**
+     * 股票业绩归因(五因子归因分析)-前端组件:风格评测-股票业绩归因组件
+     *
+     * @param params 请求参数
+     * @return /
+     */
+    @GetMapping("stock-attribution")
+    public ResultVo<Map<String, Object>> stockAttribution(StockAttributionParams params) {
+        return ResultVo.ok(this.service.stockAttribution(params));
+    }
+
+    /**
+     * 债券业绩归因-前端组件:风格评测-债券业绩归因
+     *
+     * @param params 请求参数
+     * @return /
+     */
+    @GetMapping("bond-attribution")
+    public ResultVo<Map<String, Object>> bondAttribution(BondAttributionParams params) {
+        return ResultVo.ok(this.service.bondAttribution(params));
+    }
+
+    /**
+     * 相对价值业绩归因-前端组件:风格评测-相对价值业绩归因
+     *
+     * @param params 请求参数
+     * @return /
+     */
+    @GetMapping("relative-attribution")
+    public ResultVo<Map<String, Object>> relativeAttribution(RelativeAttributionParams params) {
+        return ResultVo.ok(this.service.relativeAttribution(params));
+    }
+
+    /**
+     * 成长价值风格-前端组件:风格评测-成长价值风格
+     *
+     * @param params 请求参数
+     * @return /
+     */
+    @GetMapping("growth-value")
+    public ResultVo<FundStyleVO> growthValue(GrowthValueParams params) {
+        return ResultVo.ok(this.service.growthValue(params));
+    }
+
+    /**
+     * 行业配置-前端组件:风格评测-行业配置
+     *
+     * @param params 请求参数
+     * @return /
+     */
+    @GetMapping("industry-value")
+    public ResultVo<FundStyleVO> industryValue(IndustryValueParams params) {
+        return ResultVo.ok(this.service.industryValue(params));
+    }
+
+    /**
+     * 期货风格-前端组件:风格评测-期货风格
+     *
+     * @param params 请求参数
+     * @return /
+     */
+    @GetMapping("future-factor")
+    public ResultVo<Map<String, Object>> futureFactor(FutureFactorParams params) {
+        return ResultVo.ok(this.service.futureFactor(params));
+    }
+
+    /**
+     * 自定义风格-前端组件:风格评测-自定义风格
+     *
+     * @param params 请求参数
+     * @return /
+     */
+    @GetMapping("custom-rbsa")
+    public ResultVo<CustomRbsaVO> customRbsa(CustomRbsaParams params) {
+        return ResultVo.ok(this.service.customRbsa(params));
+    }
+
+    /**
+     * Barra风格概览
+     */
+    @GetMapping("/barra-factor-overview")
+    public ResultVo<Map<String, Object>> barraOverview(BarraStyleParams params) {
+        return ResultVo.ok(this.service.barraOverview(params));
+    }
+
+    /**
+     * Barra 风格归因
+     */
+    @GetMapping("/barra-factor-risk-profit")
+    public ResultVo<Map<String, Object>> barraRiskProfit(BarraStyleParams params) {
+        return ResultVo.ok((this.service.barraRiskProfit(params)));
+    }
+
+    /**
+     * 选股择时能力-前端组件:风格评测-选股择时能力
+     *
+     * @param params 请求参数
+     * @return /
+     */
+    @GetMapping("selection-timing")
+    public ResultVo<Map<String, Object>> selectionTiming(SelectionTimingParams params) {
+        return ResultVo.ok(this.service.selectionTiming(params));
+    }
+
+    /**
+     * 融智 风格总览-前端组件:风格评测-融智 风格总览
+     *
+     * @param params 请求参数
+     * @return /
+     */
+    @GetMapping("ppw")
+    public ResultVo<Map<String, Object>> rzStyle(RzStyleParams params) {
+        return ResultVo.ok(this.service.rzStyle(params));
+    }
+}

+ 23 - 0
src/main/java/com/smppw/analysis/domain/dto/performance/AnalyzeCovParams.java

@@ -0,0 +1,23 @@
+package com.smppw.analysis.domain.dto.performance;
+
+import com.smppw.constants.Consts;
+import lombok.Getter;
+import lombok.Setter;
+
+import java.io.Serial;
+
+/**
+ * @author wangzaijun
+ * @date 2023/3/3 19:24
+ * @description 相关性分析接口请求参数
+ */
+@Setter
+@Getter
+public class AnalyzeCovParams extends BaseParams {
+    @Serial
+    private static final long serialVersionUID = Consts.DEFAULT_SERIAL_VERSION_UID;
+    // 滚动窗口
+    private Integer rollingWindow;
+    // 步长
+    private Integer step;
+}

+ 11 - 0
src/main/java/com/smppw/analysis/domain/dto/performance/HistoryRetTableSingleData.java

@@ -0,0 +1,11 @@
+package com.smppw.analysis.domain.dto.performance;
+
+import lombok.Data;
+
+import java.util.List;
+
+@Data
+public class HistoryRetTableSingleData {
+    private String year;
+    private List<HistoryRetTableSingleRet> rets;
+}

+ 14 - 0
src/main/java/com/smppw/analysis/domain/dto/performance/HistoryRetTableSingleResp.java

@@ -0,0 +1,14 @@
+package com.smppw.analysis.domain.dto.performance;
+
+import lombok.Data;
+
+import java.util.List;
+
+@Data
+public class HistoryRetTableSingleResp {
+    private List<Integer> datetime;
+    private List<HistoryRetTableSingleData> data;
+    private String endDate;
+    private String startDate;
+    private String indicatorName;
+}

+ 12 - 0
src/main/java/com/smppw/analysis/domain/dto/performance/HistoryRetTableSingleRet.java

@@ -0,0 +1,12 @@
+package com.smppw.analysis.domain.dto.performance;
+
+import lombok.Data;
+
+import java.util.List;
+
+@Data
+public class HistoryRetTableSingleRet {
+    private String id;
+    private String type;
+    private List<String> ret;
+}

+ 18 - 0
src/main/java/com/smppw/analysis/domain/dto/performance/ImfTrendParams.java

@@ -0,0 +1,18 @@
+package com.smppw.analysis.domain.dto.performance;
+
+import lombok.Getter;
+import lombok.Setter;
+
+/**
+ * @author wangzaijun
+ * @date 2023/3/6 8:38
+ * @description 公募货币基金业绩走势接口请求参数
+ */
+@Setter
+@Getter
+public class ImfTrendParams extends BaseParams {
+    /**
+     * 货币面值类型,百份/万份/百万份收益
+     */
+    private String parValue;
+}

+ 18 - 0
src/main/java/com/smppw/analysis/domain/dto/performance/RangIndicatorParams.java

@@ -0,0 +1,18 @@
+package com.smppw.analysis.domain.dto.performance;
+
+import com.smppw.common.pojo.enums.Indicator;
+import lombok.Getter;
+import lombok.Setter;
+
+/**
+ * @author wangzaijun
+ * @date 2023/3/6 11:10
+ * @description 区间指标缝隙接口请求参数
+ */
+@Setter
+@Getter
+public class RangIndicatorParams extends BaseParams {
+    private Indicator indicator;
+
+    private Boolean excess = false;
+}

+ 19 - 0
src/main/java/com/smppw/analysis/domain/dto/performance/RankParams.java

@@ -0,0 +1,19 @@
+package com.smppw.analysis.domain.dto.performance;
+
+import com.smppw.common.pojo.enums.Indicator;
+import lombok.Getter;
+import lombok.Setter;
+
+/**
+ * @author wangzaijun
+ * @date 2023/3/3 19:25
+ * @description 业绩排名接口请求参数
+ */
+@Setter
+@Getter
+public class RankParams extends BaseParams {
+    /**
+     * 选择的指标
+     */
+    private Indicator indicator;
+}

+ 26 - 0
src/main/java/com/smppw/analysis/domain/dto/performance/RevenueParams.java

@@ -0,0 +1,26 @@
+package com.smppw.analysis.domain.dto.performance;
+
+import com.smppw.common.pojo.enums.Frequency;
+import lombok.Getter;
+import lombok.Setter;
+
+/**
+ * @author wangzaijun
+ * @date 2023/3/6 11:25
+ * @description 收益统计接口请求参数
+ */
+@Setter
+@Getter
+public class RevenueParams extends BaseParams {
+    // 1-收益统计,2-收益分布
+    private String revenuType;
+
+    // 是否计算超额
+    private Boolean ifExcessReturn = false;
+
+    // 滚动频率,周、月、季度和年度
+    private Frequency rollingFrequency;
+
+    // 组距,收益分布图表支持用户自定义,收益分布必传参数,可以提供默认值为6
+    private String space;
+}

+ 18 - 0
src/main/java/com/smppw/analysis/domain/dto/performance/RollIndicatorParams.java

@@ -0,0 +1,18 @@
+package com.smppw.analysis.domain.dto.performance;
+
+import com.smppw.common.pojo.enums.Frequency;
+import com.smppw.common.pojo.enums.Indicator;
+import lombok.Getter;
+import lombok.Setter;
+
+/**
+ * @author wangzaijun
+ * @date 2023/3/6 11:20
+ * @description 滚动指标分析接口请求参数
+ */
+@Setter
+@Getter
+public class RollIndicatorParams extends BaseParams {
+    private Indicator indicator;
+    private Frequency rollingFrequency;
+}

+ 18 - 0
src/main/java/com/smppw/analysis/domain/dto/performance/WinParams.java

@@ -0,0 +1,18 @@
+package com.smppw.analysis.domain.dto.performance;
+
+import com.smppw.analysis.infrastructure.consts.WinRateBmk;
+import lombok.Getter;
+import lombok.Setter;
+
+/**
+ * @author wangzaijun
+ * @date 2023/3/6 16:32
+ * @description 胜率分析接口请求参数
+ */
+@Setter
+@Getter
+public class WinParams extends BaseParams {
+    private WinRateBmk winRateBmk;
+    private String lower;
+    private String upper;
+}

+ 11 - 0
src/main/java/com/smppw/analysis/domain/dto/style/BarraStyleParams.java

@@ -0,0 +1,11 @@
+package com.smppw.analysis.domain.dto.style;
+
+import lombok.Getter;
+import lombok.Setter;
+
+@Setter
+@Getter
+public class BarraStyleParams extends BaseParams {
+    private Integer excess;
+    private String benchmarkId;
+}

+ 55 - 0
src/main/java/com/smppw/analysis/domain/dto/style/BaseParams.java

@@ -0,0 +1,55 @@
+package com.smppw.analysis.domain.dto.style;
+
+import com.smppw.common.pojo.enums.Frequency;
+import com.smppw.common.pojo.enums.RaiseType;
+import com.smppw.constants.Consts;
+import lombok.Getter;
+import lombok.Setter;
+
+import java.io.Serial;
+import java.io.Serializable;
+
+/**
+ * @author wangzaijun
+ * @date 2023/3/13 20:28
+ * @description 风格评测 公共参数
+ */
+@Setter
+@Getter
+public abstract class BaseParams implements Serializable {
+    @Serial
+    private static final long serialVersionUID = Consts.DEFAULT_SERIAL_VERSION_UID;
+
+    /**
+     * 标的id,包括基金、机构行业经理
+     */
+    private String secId;
+    /**
+     * 开始日期
+     */
+    private String startDate;
+    /**
+     * 结束日期
+     */
+    private String endDate;
+    /**
+     * 滚动期数,默认24期
+     */
+    private String winlen;
+    /**
+     * 滚动步长,默认1
+     */
+    private String step;
+    /**
+     * 净值频率
+     */
+    private Frequency frequency;
+
+    private RaiseType raiseType;
+
+    private String strategy;
+
+    public Frequency getFrequency() {
+        return frequency == Frequency.Default ? Frequency.Daily : this.frequency;
+    }
+}

+ 9 - 0
src/main/java/com/smppw/analysis/domain/dto/style/BondAttributionParams.java

@@ -0,0 +1,9 @@
+package com.smppw.analysis.domain.dto.style;
+
+import lombok.Getter;
+import lombok.Setter;
+
+@Setter
+@Getter
+public class BondAttributionParams extends BaseParams {
+}

+ 28 - 0
src/main/java/com/smppw/analysis/domain/dto/style/CustomRbsaParams.java

@@ -0,0 +1,28 @@
+package com.smppw.analysis.domain.dto.style;
+
+import com.smppw.analysis.infrastructure.consts.Constraint;
+import lombok.Getter;
+import lombok.Setter;
+
+import java.util.List;
+
+@Setter
+@Getter
+public class CustomRbsaParams extends BaseParams {
+    /**
+     * 约束,LongPosition-多头,ShortPosition-多空
+     */
+    private Constraint constraint = Constraint.LongPosition;
+    /**
+     * 自选基准
+     */
+    private List<String> indexIds;
+    /**
+     * 系数和是否为1
+     */
+    private Integer constraintType;
+    /**
+     * 是否计算超额,1-是,0-否,默认0
+     */
+    private Integer excess;
+}

+ 44 - 0
src/main/java/com/smppw/analysis/domain/dto/style/CustomRbsaVO.java

@@ -0,0 +1,44 @@
+package com.smppw.analysis.domain.dto.style;
+
+import com.fasterxml.jackson.annotation.JsonProperty;
+import lombok.Builder;
+import lombok.Getter;
+import lombok.Setter;
+
+import java.util.List;
+import java.util.Map;
+
+@Setter
+@Getter
+@Builder
+public class CustomRbsaVO {
+    private Chart1 chart1;
+    private Chart2 chart2;
+
+    @Getter
+    @Builder
+    public static class Chart1 {
+        private final List<Map<String, Object>> dataset;
+        private final Map<String, String> chartProductNameMapping;
+    }
+
+    @Getter
+    @Builder
+    public static class Chart2 {
+        private final DataSet dataset;
+        private final Map<String, String> chartProductNameMapping;
+        @JsonProperty("R-squared")
+        private final String r2;
+    }
+
+    @Getter
+    public static class DataSet {
+        private final Map<String, Object> risk;
+        private final Map<String, Object> profit;
+
+        public DataSet(Map<String, Object> risk, Map<String, Object> profit) {
+            this.risk = risk;
+            this.profit = profit;
+        }
+    }
+}

+ 44 - 0
src/main/java/com/smppw/analysis/domain/dto/style/FundStyleVO.java

@@ -0,0 +1,44 @@
+package com.smppw.analysis.domain.dto.style;
+
+import com.fasterxml.jackson.annotation.JsonProperty;
+import lombok.Builder;
+import lombok.Getter;
+import lombok.Setter;
+
+import java.util.List;
+import java.util.Map;
+
+@Setter
+@Getter
+@Builder
+public class FundStyleVO {
+    private Chart1 chart1;
+    private Chart2 chart2;
+
+    @Getter
+    @Builder
+    public static class Chart1 {
+        private final List<Map<String, Object>> dataset;
+        private final Map<String, String> chartProductNameMapping;
+    }
+
+    @Getter
+    @Builder
+    public static class Chart2 {
+        private final DataSet dataset;
+        private final Map<String, String> chartProductNameMapping;
+        @JsonProperty("R-squared")
+        private final String r2;
+    }
+
+    @Getter
+    public static class DataSet {
+        private final Map<String, Object> risk;
+        private final Map<String, Object> profit;
+
+        public DataSet(Map<String, Object> risk, Map<String, Object> profit) {
+            this.risk = risk;
+            this.profit = profit;
+        }
+    }
+}

+ 9 - 0
src/main/java/com/smppw/analysis/domain/dto/style/FutureFactorParams.java

@@ -0,0 +1,9 @@
+package com.smppw.analysis.domain.dto.style;
+
+import lombok.Getter;
+import lombok.Setter;
+
+@Setter
+@Getter
+public class FutureFactorParams extends BaseParams {
+}

+ 24 - 0
src/main/java/com/smppw/analysis/domain/dto/style/GrowthValueParams.java

@@ -0,0 +1,24 @@
+package com.smppw.analysis.domain.dto.style;
+
+import com.smppw.analysis.infrastructure.consts.Constraint;
+import com.smppw.analysis.infrastructure.consts.ValueGrowthType;
+import lombok.Getter;
+import lombok.Setter;
+
+/**
+ * @author wangzaijun
+ * @date 2023/3/14 9:23
+ * @description 成长价值风格 请求参数
+ */
+@Setter
+@Getter
+public class GrowthValueParams extends BaseParams {
+    /**
+     * 风格指数, 国证风格、国证策略、巨潮风格
+     */
+    private ValueGrowthType allocationIndex;
+    /**
+     * 约束,LongPosition-多头,ShortPosition-多空
+     */
+    private Constraint constraint = Constraint.LongPosition;
+}

+ 24 - 0
src/main/java/com/smppw/analysis/domain/dto/style/IndustryValueParams.java

@@ -0,0 +1,24 @@
+package com.smppw.analysis.domain.dto.style;
+
+import com.smppw.analysis.infrastructure.consts.Constraint;
+import com.smppw.analysis.infrastructure.consts.IndustryType;
+import lombok.Getter;
+import lombok.Setter;
+
+/**
+ * @author wangzaijun
+ * @date 2023/3/14 9:23
+ * @description 行业配置风格 请求参数
+ */
+@Setter
+@Getter
+public class IndustryValueParams extends BaseParams {
+    /**
+     * 风格指数, 国证风格、国证策略、巨潮风格
+     */
+    private IndustryType industryIndex;
+    /**
+     * 约束,LongPosition-多头,ShortPosition-多空
+     */
+    private Constraint constraint = Constraint.LongPosition;
+}

+ 9 - 0
src/main/java/com/smppw/analysis/domain/dto/style/RelativeAttributionParams.java

@@ -0,0 +1,9 @@
+package com.smppw.analysis.domain.dto.style;
+
+import lombok.Getter;
+import lombok.Setter;
+
+@Setter
+@Getter
+public class RelativeAttributionParams extends BaseParams {
+}

+ 38 - 0
src/main/java/com/smppw/analysis/domain/dto/style/RzStyleParams.java

@@ -0,0 +1,38 @@
+package com.smppw.analysis.domain.dto.style;
+
+import com.smppw.common.pojo.enums.RaiseType;
+import com.smppw.constants.Consts;
+import lombok.Getter;
+import lombok.Setter;
+
+/**
+ * @author wangzaijun
+ * @date 2023/3/17 14:18
+ * @description 风格总览 接口请求参数
+ */
+@Setter
+@Getter
+public class RzStyleParams {
+    /**
+     * 标的id
+     */
+    private String secId;
+    /**
+     * 开始日期
+     */
+    private String startDate = Consts.START_DATE;
+    /**
+     * 结束日期
+     */
+    private String endDate;
+    /**
+     * 标的类型
+     */
+    private RaiseType raiseType;
+    /**
+     * 基准id
+     */
+    private String benchmarkId;
+
+    private Integer userId;
+}

+ 22 - 0
src/main/java/com/smppw/analysis/domain/dto/style/SelectionTimingParams.java

@@ -0,0 +1,22 @@
+package com.smppw.analysis.domain.dto.style;
+
+public class SelectionTimingParams extends BaseParams {
+    private String benchmarkId;
+    private Integer model;
+
+    public String getBenchmarkId() {
+        return benchmarkId;
+    }
+
+    public void setBenchmarkId(String benchmarkId) {
+        this.benchmarkId = benchmarkId;
+    }
+
+    public Integer getModel() {
+        return model;
+    }
+
+    public void setModel(Integer model) {
+        this.model = model;
+    }
+}

+ 9 - 0
src/main/java/com/smppw/analysis/domain/dto/style/StockAttributionParams.java

@@ -0,0 +1,9 @@
+package com.smppw.analysis.domain.dto.style;
+
+import lombok.Getter;
+import lombok.Setter;
+
+@Setter
+@Getter
+public class StockAttributionParams extends BaseParams {
+}

+ 36 - 0
src/main/java/com/smppw/analysis/domain/dto/style/py/PyReq.java

@@ -0,0 +1,36 @@
+package com.smppw.analysis.domain.dto.style.py;
+
+import cn.hutool.core.map.MapUtil;
+import cn.hutool.core.util.StrUtil;
+import lombok.Builder;
+
+import java.util.Map;
+
+@Builder
+public class PyReq {
+    private final String taskId;
+    private final String api;
+    private final String method;
+    private final Boolean json;
+    private final Map<String, Object> params;
+
+    public String getTaskId() {
+        return taskId;
+    }
+
+    public String getApi() {
+        return api;
+    }
+
+    public String getMethod() {
+        return StrUtil.isBlank(this.method) ? "post" : this.method;
+    }
+
+    public boolean getJson() {
+        return json == null || json == Boolean.TRUE;
+    }
+
+    public Map<String, Object> getParams() {
+        return params == null ? MapUtil.newHashMap() : params;
+    }
+}

+ 17 - 0
src/main/java/com/smppw/analysis/domain/dto/style/py/PyReqBody.java

@@ -0,0 +1,17 @@
+package com.smppw.analysis.domain.dto.style.py;
+
+import lombok.Builder;
+import lombok.Getter;
+import lombok.Setter;
+
+@Setter
+@Getter
+@Builder
+public class PyReqBody {
+    private String fundIds;
+    private String startDate;
+    private String endDate;
+    private String freq;
+    private String winLen;
+    private String step;
+}

+ 40 - 0
src/main/java/com/smppw/analysis/domain/dto/style/py/PyReqParam.java

@@ -0,0 +1,40 @@
+package com.smppw.analysis.domain.dto.style.py;
+
+import cn.hutool.core.map.MapUtil;
+import lombok.Builder;
+
+import java.util.Map;
+
+@Builder
+public class PyReqParam {
+    private final String api;
+    private final String method;
+    private final Boolean json;
+    private final String taskId;
+    private final Integer control;
+    private final Map<String, Object> ext;
+
+    public String getApi() {
+        return api;
+    }
+
+    public String getMethod() {
+        return method;
+    }
+
+    public Boolean getJson() {
+        return json;
+    }
+
+    public String getTaskId() {
+        return taskId;
+    }
+
+    public Integer getControl() {
+        return control;
+    }
+
+    public Map<String, Object> getExt() {
+        return ext == null ? MapUtil.newHashMap() : ext;
+    }
+}

+ 27 - 0
src/main/java/com/smppw/analysis/domain/dto/style/py/PyResBody.java

@@ -0,0 +1,27 @@
+package com.smppw.analysis.domain.dto.style.py;
+
+import cn.hutool.core.collection.ListUtil;
+import cn.hutool.core.map.MapUtil;
+import lombok.Setter;
+
+import java.util.List;
+import java.util.Map;
+
+@Setter
+public class PyResBody {
+    private Map<String, Object> holistic;
+    private List<Map<String, Object>> sequential;
+    private Map<String, List<Map<String, Object>>> extBody;
+
+    public Map<String, Object> getHolistic() {
+        return holistic == null ? MapUtil.newHashMap() : holistic;
+    }
+
+    public List<Map<String, Object>> getSequential() {
+        return sequential == null ? ListUtil.list(false) : sequential;
+    }
+
+    public Map<String, List<Map<String, Object>>> getExtBody() {
+        return extBody == null ? MapUtil.newHashMap() : extBody;
+    }
+}

Những thai đổi đã bị hủy bỏ vì nó quá lớn
+ 1287 - 0
src/main/java/com/smppw/analysis/domain/manager/performance/AbstractPerformanceService.java


+ 145 - 0
src/main/java/com/smppw/analysis/domain/manager/performance/PerformanceService.java

@@ -0,0 +1,145 @@
+//package com.smppw.analysis.domain.manager.performance;
+//
+//import cn.hutool.core.collection.ListUtil;
+//import com.smppw.analysis.domain.dto.performance.*;
+//import com.smppw.common.pojo.enums.Indicator;
+//import com.smppw.common.pojo.enums.TimeRange;
+//import com.smppw.common.pojo.enums.TrendType;
+//
+//import java.util.List;
+//import java.util.Map;
+//
+///**
+// * @author wangzaijun
+// * @date 2023/3/10 17:51
+// * @description 业绩表现接口,包括基金、机构和基金经理
+// */
+//public interface PerformanceService {
+//    /**
+//     * 计算收益风险指标,包括部分几何指标
+//     *
+//     * @param params /
+//     * @return /
+//     */
+//    default Map<String, Object> rateRiskIndicators(IndicatorParams params) {
+//        return this.rateRiskIndicators(params, ListUtil.toList(Indicator.INDICATOR_TYPE_ARRAY), ListUtil.toList(Indicator.RISK_TABLE_EXCESS_INDICATOR_ARRAY));
+//    }
+//
+//    Map<String, Object> rateRiskIndicators(IndicatorParams params, List<Indicator> indicators, List<Indicator> geoIndicators);
+//
+//    /**
+//     * 动态回撤 接口业务,返回回撤、超额回撤、最大回撤和最大超额回撤
+//     *
+//     * @param params /
+//     * @return /
+//     */
+//    default Map<String, Object> dynamicDown(TrendParams params) {
+//        return this.dynamicDown(params, null);
+//    }
+//
+//    /**
+//     * 动态回撤 接口业务,返回回撤、超额回撤、最大回撤和最大超额回撤
+//     *
+//     * @param params /
+//     * @return /
+//     */
+//    Map<String, Object> dynamicDown(TrendParams params, String masterId);
+//
+//    /**
+//     * 业绩走势接口业务处理
+//     *
+//     * @param params 请求参数
+//     * @return /
+//     */
+//    default Map<String, Object> trend(TrendParams params) {
+//        List<TrendType> trendTypes = ListUtil.toList(TrendType.Ret, TrendType.Nav, TrendType.ExtraNav, TrendType.OrigNav, TrendType.ExtraRetAri, TrendType.NetValueChange, TrendType.ExtraRetGeo, TrendType.DrawdownTrend);
+//        List<TrendType> indexTrendTypes = ListUtil.toList(TrendType.Ret, TrendType.OrigNav);
+//        return this.trend(params, trendTypes, indexTrendTypes);
+//    }
+//
+//    /**
+//     * 业绩走势接口业务处理
+//     *
+//     * @param params          请求参数
+//     * @param trendTypes      标的走势图类型列表
+//     * @param indexTrendTypes 指数走势图类型列表
+//     * @return /
+//     */
+//    Map<String, Object> trend(TrendParams params, List<TrendType> trendTypes, List<TrendType> indexTrendTypes);
+//
+//    /**
+//     * 货币基金业绩走势
+//     *
+//     * @param params /
+//     * @return /
+//     */
+//    Map<String, Object> imfTrend(ImfTrendParams params);
+//
+//    /**
+//     * 业绩排名 接口请求业务处理
+//     *
+//     * @param params 请求参数
+//     * @return /
+//     */
+//    Map<String, Object> rank(RankParams params);
+//
+//    /**
+//     * 区间指标分析 接口请求业务处理
+//     *
+//     * @param params 请求参数
+//     * @return /
+//     */
+//    default Map<String, Object> rangIndicator(RangIndicatorParams params) {
+//        return this.rangIndicator(params, null);
+//    }
+//
+//
+//    /**
+//     * 区间指标分析 接口请求业务处理
+//     *
+//     * @param params   请求参数
+//     * @param rangeMap 返回结果映射函数
+//     * @return /
+//     */
+//    Map<String, Object> rangIndicator(RangIndicatorParams params, Map<TimeRange, String> rangeMap);
+//
+//    /**
+//     * 滚动指标分析 接口请求业务处理,不支持多标的
+//     *
+//     * @param params 请求参数
+//     * @return /
+//     */
+//    Map<String, Object> rollIndicator(RollIndicatorParams params);
+//
+//    /**
+//     * 收益统计/收益分布 接口请求业务处理
+//     *
+//     * @param params 请求参数
+//     * @return /
+//     */
+//    Map<String, Object> revenue(RevenueParams params);
+//
+//    /**
+//     * 胜率分析,只支持单标的 业务处理
+//     *
+//     * @param params /
+//     * @return /
+//     */
+//    Map<String, Object> win(WinParams params);
+//
+//    /**
+//     * 指标分析
+//     *
+//     * @param params
+//     * @return
+//     */
+//    Map<String, Object> analyzeIndicatorNew(RangIndicatorParams params);
+//
+//    /**
+//     * 相关性
+//     *
+//     * @param params
+//     * @return
+//     */
+//    Map<String, Object> analyzeCovNew(AnalyzeCovParams params);
+//}

+ 946 - 0
src/main/java/com/smppw/analysis/domain/manager/performance/PerformanceServiceImpl.java

@@ -0,0 +1,946 @@
+//package com.smppw.analysis.domain.manager.performance;
+//
+//import cn.hutool.core.collection.CollUtil;
+//import cn.hutool.core.collection.CollectionUtil;
+//import cn.hutool.core.collection.ListUtil;
+//import cn.hutool.core.date.DateUtil;
+//import cn.hutool.core.map.MapUtil;
+//import cn.hutool.core.text.CharSequenceUtil;
+//import cn.hutool.core.util.NumberUtil;
+//import cn.hutool.core.util.StrUtil;
+//
+//import com.smppw.analysis.domain.dto.performance.*;
+//import com.smppw.analysis.infrastructure.consts.WinRateBmk;
+//import com.smppw.analysis.infrastructure.exception.APIException;
+//import com.smppw.common.pojo.IStrategy;
+//import com.smppw.common.pojo.dto.CompoundRet;
+//import com.smppw.common.pojo.dto.DateRange;
+//import com.smppw.common.pojo.dto.calc.*;
+//import com.smppw.common.pojo.dto.indicator.CalcMultipleSecMultipleTimeRangeIndicatorReq;
+//import com.smppw.common.pojo.dto.indicator.DateIntervalDto;
+//import com.smppw.common.pojo.enums.*;
+//import com.smppw.common.pojo.enums.strategy.Strategy;
+//import com.smppw.common.rollrange.RollingSpliter;
+//import com.smppw.constants.Consts;
+//import com.smppw.utils.CalcUtils;
+//import com.smppw.utils.CommonUtil;
+//import com.smppw.utils.NavUtil;
+//import com.smppw.utils.StrategyHandleUtils;
+//import lombok.extern.slf4j.Slf4j;
+//import org.apache.commons.lang3.StringUtils;
+//import org.springframework.beans.factory.annotation.Autowired;
+//import org.springframework.beans.factory.annotation.Qualifier;
+//import org.springframework.jdbc.core.JdbcTemplate;
+//import org.springframework.stereotype.Service;
+//
+//import java.io.IOException;
+//import java.math.BigDecimal;
+//import java.util.*;
+//import java.util.function.Function;
+//import java.util.stream.Collectors;
+//
+//
+///**
+// * @author wangzaijun
+// * @date 2023/3/3 17:22
+// * @description 业绩表现页面的所有接口服务,包含基金、机构和经理
+// */
+//@Service
+//@Slf4j
+//public class PerformanceServiceImpl extends AbstractPerformanceService {
+//    /**
+//     * 指数成分类型: 1-表示融智策略指数;2-表示融智获奖指数;
+//     */
+//    public static final int COMPONENT_TYPE_STRATEGY = 1;
+//
+//    private static final String ONE = "1";
+//    private static final String TWO = "2";
+//
+//    private static final List<String> TYPE_LIST = ListUtil.of(ONE, TWO);
+//
+//    @Autowired
+//    @Qualifier("jdbcTemplateReportBuilder")
+//    private JdbcTemplate jdbcTemplate;
+//    @Autowired
+//    private RankRatService rankRatService;
+//    @Autowired
+//    private IndexPerformanceBaseService indexPerformanceBaseService;
+//    @Autowired
+//    private FundHeadInfoBaseService fundHeadInfoBaseService;
+//    @Autowired
+//    private ManagerHeadInfoBaseService managerHeadInfoBaseService;
+//    @Autowired
+//    private CompanyHeadInfoBaseService companyHeadInfoBaseService;
+//    @Autowired
+//    private ManagerInfoImpl managerInfo;
+//    @Autowired
+//    private MonetaryFundProfitBaseService monetaryFundProfitBaseService;
+//
+//    @Autowired
+//    private CmPublicCompanyStatisHistoryDAO cmPublicCompanyStatisHistoryDAO;
+//    private UserPermissionService userPermissionService;
+//
+//    @Autowired
+//    private FundManagerMappingDOMapper fundManagerMappingDOMapper;
+//
+//    @Autowired
+//    private MfAdvisorScaleRankMapper mfAdvisorScaleRankMapper;
+//
+//    public PerformanceServiceImpl(NavService navService, InfoService infoService, SecId2NameService secId2NameService,
+//                                  BaseIndicatorServiceV2 baseIndicatorServiceV2, UserPermissionService userPermissionService) {
+//        super(navService, infoService, secId2NameService, baseIndicatorServiceV2);
+//        this.userPermissionService = userPermissionService;
+//    }
+//
+//    /**
+//     * 计算收益风险指标,包括部分几何指标
+//     *
+//     * @param params /
+//     * @return /
+//     */
+//    public Map<String, Object> rateRiskIndicators(IndicatorParams params, List<Indicator> indicators, List<Indicator> geoIndicators) {
+//        try {
+//            // 1.参数处理
+//            this.checkParams(params);
+//            List<String> refIds = params.getFundId();
+//            List<String> secIds = this.getSecIdsByParams(params);
+//            // 差集求指数id集合,包括基�
+//            List<String> indexIds = CollectionUtil.subtractToList(secIds, refIds);
+//            String riskOfFreeId = params.getRiskOfFreeId();
+//            Double riskOfFreeValue = params.getRiskOfFreeValue();
+//            if (StrUtil.isBlank(riskOfFreeId)) {
+//                riskOfFreeId = Consts.RISK_OF_FREE;
+//            } else if (NumberUtil.isNumber(riskOfFreeId)) {
+//                riskOfFreeValue = Double.parseDouble(riskOfFreeId);
+//                riskOfFreeId = null;
+//            }
+//            CalcMultipleSecMultipleTimeRangeIndicatorReq req = this.buildCalcReq(params, indicators, geoIndicators, DateIntervalType.CustomInterval, null);
+//            req.setRiskOfFreeId(riskOfFreeId);
+//            req.setRiskOfFreeValue(riskOfFreeValue);
+//            req.setIfExtract(params.getIsExtract() != null && params.getIsExtract());
+//
+//            // 2.指标计算
+//            Map<String, List<IndicatorCalcPropertyDto>> indicator = this.baseIndicatorServiceV2.calcMultipleSecMultipleTimeRangeIndicator(req);
+//
+//            // 3.返回结果处理
+//            Map<String, Object> valuesMap = MapUtil.newHashMap(true);
+//            Map<String, Object> indexValuesMap = MapUtil.newHashMap(true);
+//            for (String refId : refIds) {
+//                IndicatorCalcPropertyDto dto = Optional.ofNullable(indicator.get(refId)).filter(e -> !e.isEmpty()).map(e -> e.get(0)).orElse(null);
+//                // 标的指标
+//                Map<String, String> indicatorValues = Optional.ofNullable(dto).map(IndicatorCalcPropertyDto::getSecData).map(IndicatorCalcSecDataDto::getIndicatorValueMap).orElse(MapUtil.empty());
+//                // 标的几何指标
+//                Map<String, String> geoIndicatorValues = Optional.ofNullable(dto).map(IndicatorCalcPropertyDto::getSecData).map(IndicatorCalcSecDataDto::getExtraGeoIndicatorValueMap).orElse(MapUtil.empty());
+//                // 指数指标,包括基�
+//                Map<String, Map<String, String>> indexIndicatorValuesMap = Optional.ofNullable(dto).map(IndicatorCalcPropertyDto::getIndexData).map(IndicatorCalcIndexDataDto::getIndexIndicatorValueMap).orElse(MapUtil.empty());
+//                // 指数几何指标
+//                Map<String, Map<String, String>> indexGeoIndicatorValuesMap = Optional.ofNullable(dto).map(IndicatorCalcPropertyDto::getIndexData).map(IndicatorCalcIndexDataDto::getIndexGeoExtraIndicatorValueMap).orElse(MapUtil.empty());
+//                // 标的和指数分别处理最大回撤指标,并合并指标结果到一个map�
+//                Map<String, String> values = this.handleMaxDrawdown(indicatorValues, refId, null, false);
+//                Map<String, String> geoValues = this.handleMaxDrawdown(geoIndicatorValues, refId, null, true);
+//                Map<String, String> unionValues = MapUtil.<String, String>builder().putAll(values).putAll(geoValues).build();
+//                valuesMap.put(refId, unionValues);
+//                for (String indexId : indexIds) {
+//                    if (indexValuesMap.containsKey(indexId)) {
+//                        continue;
+//                    }
+//                    Map<String, String> indexValues = this.handleMaxDrawdown(indexIndicatorValuesMap.get(indexId), indexId, null, false);
+//                    Map<String, String> indexGeoValues = this.handleMaxDrawdown(indexGeoIndicatorValuesMap.get(indexId), indexId, params.getBenchmarkId(), true);
+//                    Map<String, String> unionIndexValues = MapUtil.<String, String>builder().putAll(indexValues).putAll(indexGeoValues).build();
+//                    indexValuesMap.put(indexId, unionIndexValues);
+//                }
+//            }
+//
+//            // 返回结果对象构建
+//            Map<String, Object> dataset = MapUtil.builder(valuesMap).putAll(indexValuesMap).build();
+//            Map<String, Object> extInfos = MapUtil.<String, Object>builder("endDate", params.getStartDate() + "~" + params.getEndDate()).build();
+//            Map<String, String> productNameMapping = this.secId2NameService.query(secIds);
+//            CommonData<Map<String, Object>> data = CommonData.<Map<String, Object>>builder().dataset(dataset).productNameMapping(productNameMapping).extInfos(extInfos).build();
+//            return CommonUtil.covertToMap(data, "endDate");
+//        } catch (Exception e) {
+//            logger.error(String.format("基金收益风险指标计算错误:%s", e.getMessage()));
+//        }
+//        return MapUtil.newHashMap();
+//    }
+//
+//    /**
+//     * 动态回撤接口业务,返回回撤、超额回撤、最大回撤和最大超额回撤
+//     *
+//     * @param params /
+//     * @return /
+//     */
+//    public Map<String, Object> dynamicDown(TrendParams params, String masterId) {
+//        try {
+//            List<TrendType> trendTypes = ListUtil.toList(TrendType.DrawdownTrend, TrendType.ExtraDrawdownTrend);
+//            List<TrendType> indexTrendTypes = ListUtil.toList(TrendType.DrawdownTrend);
+//            CommonData<Map<String, List<Map<String, Object>>>> data = this.handleTrends(params, trendTypes, indexTrendTypes, masterId);
+//            return CommonUtil.covertToMap(data, "maxDown", "maxExtraDown", "startDate", "endDate");
+//        } catch (Exception e) {
+//            logger.error(String.format("动态回撤错误:%s", e.getMessage()), e);
+//        }
+//        return MapUtil.newHashMap();
+//    }
+//
+//    /**
+//     * 业绩排名 接口请求业务处理
+//     *
+//     * @param params 请求参数
+//     * @return /
+//     */
+//    public Map<String, Object> rank(RankParams params) {
+//        try {
+//            // 1.参数处理
+//            this.checkParams(params);
+//            String refId = params.getFundId().get(0);
+//            List<String> secIds = this.getSecIdsByParams(params);
+//            List<String> indexIds = CollectionUtil.subtractToList(secIds, params.getFundId());
+//            String rankDate = Optional.ofNullable(rankRatService.getLatestRankRat()).map(CmRankRatControlDo::getEndDate).orElse(null);
+//            IStrategy strategy = StrategyHandleUtils.getStrategy(params.getStrategy());
+//            List<Map<String, Object>> tempList = ListUtil.list(false);
+//            String rankFiled = null;
+//            CmBigDataFundRetDO cmBigDataFundRetDO = fundHeadInfoBaseService.selectFundRetByFundId(refId);
+//            String endDate = Optional.ofNullable(cmBigDataFundRetDO).map(CmBigDataFundRetDO::getEndDate).orElse(null);
+//            if (StringUtils.isNotEmpty(endDate) && StringUtils.isNotEmpty(rankDate)) {
+//                rankDate = endDate.compareTo(rankDate) > 0 ? rankDate : endDate;
+//            } else {
+//                if (StringUtils.isEmpty(endDate)) {
+//                    rankDate = endDate;
+//                }
+//            }
+//            rankFiled = "fund_rank";
+//            Integer isInvestAdvisor = Optional.ofNullable(UserUtils.getLoginUser()).map(SysUserDto::getIsInvestAdvisor).orElse(null);
+//            if (params.getIsExtract() != null && params.getIsExtract()) {
+//                tempList = null;
+//            } else {
+//                tempList = new FundRankProDao(this.jdbcTemplate, rankDate, refId, indexIds, params.getIndicator(), isInvestAdvisor).query();
+//            }
+//            Map<String, String> mapper = this.secId2NameService.query(secIds);
+//            Map<String, String> productMapper = MapUtil.<String, String>builder(MapUtil.newHashMap(true)).putAll(mapper)
+//                    .put("rank", "同策略排名")
+//                    .put("strategy_avg", "同策略平均")
+//                    .put("strategy_avg_99", "同策略平均(1%-99%)")
+//                    .put("strategy_best", "同策略最好")
+//                    .put("strategy_worst", "同策略最差")
+//                    .put("percent5", "5%分位数")
+//                    .put("percent25", "25%分位数")
+//                    .put("percent50", "50%分位数")
+//                    .put("percent75", "75%分位数")
+//                    .put("percent95", "95%分位数").build();
+//            Map<String, Object> extInfos = MapUtil.<String, Object>builder("strategy", strategy.getStrategyNameDesc()).build();
+//            List<Map<String, Object>> dataset = this.getRankDataset(tempList, rankFiled);
+//            if (CollUtil.isEmpty(dataset)) {
+//                CommonData<List<Map<String, Object>>> data = CommonData.<List<Map<String, Object>>>builder()
+//                        .dataset(dataset).productNameMapping(productMapper).extInfos(extInfos).build();
+//                return CommonUtil.covertToMap(data);
+//            }
+//            CommonData<List<Map<String, Object>>> data = CommonData.<List<Map<String, Object>>>builder()
+//                    .dataset(dataset).productNameMapping(productMapper).extInfos(extInfos).build();
+//            return CommonUtil.covertToMap(data);
+//        } catch (Exception e) {
+//            logger.error(String.format("业绩排名错误:%s", e.getMessage()), e);
+//        }
+//        return MapUtil.newHashMap();
+//    }
+//
+//    private List<Map<String, Object>> getRankDataset(List<Map<String, Object>> tempList, String rankFiled) {
+//        Map<String, Map<String, Object>> resMap = new LinkedHashMap<>();
+//        if (CollUtil.isEmpty(tempList)) {
+//            return CollUtil.newArrayList();
+//        }
+//        for (Map<String, Object> unit : tempList) {
+//            String classification = MapUtil.getStr(unit, "classification");
+//            String name = MapUtil.getStr(unit, "name");
+//            if (name == null && classification == null) {
+//                continue;
+//            }
+//            List<String> keys = new ArrayList<>(unit.keySet());
+//            keys.remove("name");
+//            keys.remove("classification");
+//            for (String key : keys) {
+//                if (!resMap.containsKey(key)) {
+//                    resMap.put(key, MapUtil.newHashMap(false));
+//                }
+//                if (classification.startsWith("strategy") || classification.startsWith("percen") || classification.equals(rankFiled)) {
+//                    name = classification;
+//                }
+//                resMap.get(key).put(name, unit.get(key));
+//            }
+//        }
+//        List<Map<String, Object>> dataset = ListUtil.list(false);
+//        resMap.forEach((k, v) -> dataset.add(MapUtil.<String, Object>builder("date", k).putAll(v).build()));
+//        dataset.forEach(e -> {
+//            String rank = MapUtil.getStr(e, rankFiled);
+//            String rankCnt = MapUtil.getStr(e, "strategy_rank_cnt");
+//            String strRank = null;
+//            if (CharSequenceUtil.isAllNotBlank(rank, rankCnt)) {
+//                strRank = StrUtil.subBefore(rank, ".", false) + "/"
+//                        + StrUtil.subBefore(rankCnt, ".", false);
+//            }
+//            e.put("rank", strRank);
+//            e.remove(rankFiled);
+//            e.remove("strategy_rank_cnt");
+//        });
+//        dataset.sort((o1, o2) -> MapUtil.getStr(o2, "date").compareTo(MapUtil.getStr(o1, "date")));
+//        return dataset;
+//    }
+//
+//    /**
+//     * 业绩走势接口业务处理
+//     *
+//     * @param params 请求参数
+//     * @return /
+//     */
+//    public Map<String, Object> trend(TrendParams params, List<TrendType> trendTypes, List<TrendType> indexTrendTypes) {
+//        try {
+//            // 1.参数处理
+//            List<String> refIds = params.getFundId();
+//            CommonData<Map<String, List<Map<String, Object>>>> data = this.handleTrends(params, trendTypes, indexTrendTypes, null);
+//            List<Map<String, String>> warnings = this.infoService.getWarningInfo(refIds, params.getStartDate(), params.getEndDate());
+//            data.getExtInfos().put("warning", warnings);
+//            return CommonUtil.covertToMap(data, "endDate", "startDate", "warning", "annualBenchmark", "annual");
+//        } catch (Exception e) {
+//            logger.error(String.format("业绩走势接口业务错误:%s", e.getMessage()), e);
+//
+//        }
+//        return MapUtil.newHashMap();
+//    }
+//
+//    @Override
+//    public Map<String, Object> imfTrend(ImfTrendParams params) {
+//        String fundId = params.getFundId().get(0);
+//        List<TrendType> trendTypes = ListUtil.toList(TrendType.Ret, TrendType.Nav, TrendType.ExtraNav, TrendType.OrigNav, TrendType.NetValueChange, TrendType.ExtraRetGeo);
+//        List<TrendType> indexTrendTypes = ListUtil.toList(TrendType.Ret, TrendType.OrigNav);
+//        CommonData<Map<String, List<Map<String, Object>>>> data = this.handleTrends(params, trendTypes, indexTrendTypes, null);
+//        Map<String, List<Map<String, Object>>> dataset = data.getDataset();
+//        List<MonetaryFundProfitDO> doList = this.monetaryFundProfitBaseService.queryByFundId(fundId);
+//        dataset.forEach((k, v) -> {
+//            if (fundId.equals(k)) {
+//                for (Map<String, Object> map : v) {
+//                    String date = MapUtil.getStr(map, "date");
+//                    MonetaryFundProfitDO aDo = doList.stream().filter(e -> date.equals(DateUtil.formatDate(e.getPriceDate()))).findFirst().orElse(null);
+//                    map.put("profit", Optional.ofNullable(aDo).map(MonetaryFundProfitDO::getProfitPerMillion).orElse(null));
+//                    map.put("serven", Optional.ofNullable(aDo).map(MonetaryFundProfitDO::getProfitServenDayAnnual).orElse(null));
+//                }
+//            }
+//        });
+//        data.setDataset(dataset);
+//        return CommonUtil.covertToMap(data, "endDate", "startDate", "annualBenchmark", "annual");
+//    }
+//
+//    /**
+//     * 区间指标分析 接口请求业务处理
+//     *
+//     * @param params 请求参数
+//     * @return /
+//     */
+//    public Map<String, Object> rangIndicator(RangIndicatorParams params, Map<TimeRange, String> rangeMap) {
+//        try {
+//            if (params.getIndicator() == null) {
+//                throw new APIException("分析的指标不能为空");
+//            }
+//            Function<IndicatorCalcTimeRangeDto, String> function = e -> e.getTimeRange().name();
+//            if (rangeMap != null && !rangeMap.isEmpty()) {
+//                function = e -> rangeMap.get(e.getTimeRange());
+//            }
+//            boolean excess = params.getExcess() == Boolean.TRUE || Indicator.INDICATOR_EXCESS_RETURN_TYPE_ARRAY.contains(params.getIndicator());
+//            CommonData<Map<String, Object>> data = this.analyzeMultiIndicator(params, params.getIndicator(), excess, params.getFrequency(), function);
+//            return CommonUtil.covertToMap(data);
+//        } catch (Exception e) {
+//            logger.error(String.format("区间指标分析接口业务错误:%s", e.getMessage()), e);
+//        }
+//        return MapUtil.newHashMap();
+//    }
+//
+//    /**
+//     * 滚动指标分析 接口请求业务处理
+//     *
+//     * @param params 请求参数
+//     * @return /
+//     */
+//    public Map<String, Object> rollIndicator(RollIndicatorParams params) {
+//        try {
+//            if (params.getIndicator() == null) {
+//                throw new APIException("分析的指标不能为空");
+//            }
+//            List<Frequency> frequencies = ListUtil.toList(Frequency.Monthly, Frequency.Quarterly, Frequency.Annually);
+//            if (params.getRollingFrequency() == null || !frequencies.contains(params.getRollingFrequency())) {
+//                logger.warn(String.format("当前滚动频率为:%s,设置为默认滚动频率:%s", params.getRollingFrequency(), Frequency.Monthly));
+//                params.setRollingFrequency(Frequency.Monthly);
+//            }
+//            CommonData<Map<String, Object>> data = this.analyzeIndicator(params, params.getIndicator(), DateIntervalType.DefaultRolling,
+//                    Indicator.INDICATOR_EXCESS_RETURN_TYPE_ARRAY.contains(params.getIndicator()), params.getRollingFrequency(), IndicatorCalcTimeRangeDto::getEndDate);
+//            return CommonUtil.covertToMap(data);
+//        } catch (Exception e) {
+//            logger.error(String.format("滚动指标分析接口业务错误:%s", e.getMessage()), e);
+//
+//        }
+//        return MapUtil.newHashMap();
+//    }
+//
+//    private <P extends BaseParams> CommonData<Map<String, Object>> analyzeMultiIndicator(P params, Indicator indicator, boolean excess,
+//                                                                                         Frequency rollingFrequency, Function<IndicatorCalcTimeRangeDto, String> function) {
+//        // 1.参数处理
+//        this.checkParams(params);
+//        List<String> refIds = params.getFundId();
+//        List<String> secIds = this.getSecIdsByParams(params);
+//        List<String> indexIds = CollectionUtil.subtractToList(secIds, refIds);
+//        List<Indicator> indicators = ListUtil.toList(Indicator.MaxDrawdown);
+//        List<Indicator> geoIndicators = ListUtil.list(false);
+//        if (excess) {
+//            geoIndicators.add(indicator);
+//        } else {
+//            indicators.add(indicator);
+//        }
+//        CalcMultipleSecMultipleTimeRangeIndicatorReq req;
+//
+//        req = this.buildMultiCalcReq(params, indicators, geoIndicators, rollingFrequency);
+//
+//        req.setRiskOfFreeId(RetConst.RISK_OF_FREE_1Y);
+//
+//        // 2、指标计�
+//        Map<String, List<IndicatorCalcPropertyDto>> indicatorMap = this.baseIndicatorServiceV2.calcMultipleSecMultipleTimeRangeIndicator(req);
+//
+//        // 3、结果处�
+//        Map<TimeRange, Boolean> timeRangeFlag = MapUtil.newHashMap();
+//        Map<String, Object> valuesMap = MapUtil.newHashMap(true);
+//        Map<String, Object> indexValuesMap = MapUtil.newHashMap(true);
+//        for (String refId : refIds) {
+//            List<IndicatorCalcPropertyDto> dtos = Optional.ofNullable(indicatorMap.get(refId)).filter(e -> !e.isEmpty()).orElse(ListUtil.empty());
+//            // 当前基金的数据处�
+//            List<Map<String, Object>> fundIndicatorList = ListUtil.list(true);
+//            for (IndicatorCalcPropertyDto dto : dtos) {
+//                String date = Optional.ofNullable(dto.getIndicatorCalcReq()).map(IndicatorCalcReqPropertyDto::getIndicatorCalcTimeRangeDto).map(function).orElse(null);
+//                String id = Optional.ofNullable(dto.getIndicatorCalcReq()).map(IndicatorCalcReqPropertyDto::getIndicatorCalcTimeRangeDto).map(IndicatorCalcTimeRangeDto::getId).orElse(null);
+//                TimeRange timeRange = Optional.ofNullable(dto.getIndicatorCalcReq()).map(IndicatorCalcReqPropertyDto::getIndicatorCalcTimeRangeDto).map(IndicatorCalcTimeRangeDto::getTimeRange).orElse(null);
+//                if (timeRange == null || (id != null && YEAR_MONTH_ROLL_LIST.contains(id)) || timeRange == TimeRange.FromSetup) {
+//                    continue;
+//                }
+//                String start = Optional.ofNullable(dto.getIndicatorCalcReq()).map(IndicatorCalcReqPropertyDto::getIndicatorCalcTimeRangeDto).map(IndicatorCalcTimeRangeDto::getStartDate).orElse(null);
+//                if (params.getStartDate() != null && start != null && params.getStartDate().compareTo(start) > 0) {
+//                    timeRangeFlag.put(timeRange, true);
+//                    continue;
+//                }
+//                // 如果是月�需要过滤掉近一�
+//                if (Frequency.Monthly == params.getFrequency()) {
+//                    if (timeRange == TimeRange.Last1Week) {
+//                        timeRangeFlag.put(TimeRange.Last1Week, true);
+//                        continue;
+//                    }
+//
+//                }
+//
+//                String value = Optional.ofNullable(dto.getSecData()).map(e -> excess ? e.getExtraGeoIndicatorValueMap() : e.getIndicatorValueMap()).map(e -> e.get(indicator.name())).orElse(null);
+//                fundIndicatorList.add(MapUtil.<String, Object>builder("date", date).put("value", value).build());
+//            }
+//            valuesMap.put(refId, fundIndicatorList);
+//            // 指数的数据处�
+//            if (excess) {
+//                continue;
+//            }
+//            for (String indexId : indexIds) {
+//                if (indexValuesMap.containsKey(indexId)) {
+//                    continue;
+//                }
+//                List<Map<String, Object>> indexIndicatorList = ListUtil.list(true);
+//                for (IndicatorCalcPropertyDto dto : dtos) {
+//                    String id = Optional.ofNullable(dto.getIndicatorCalcReq()).map(IndicatorCalcReqPropertyDto::getIndicatorCalcTimeRangeDto).map(IndicatorCalcTimeRangeDto::getId).orElse(null);
+//                    String date = Optional.ofNullable(dto.getIndicatorCalcReq()).map(IndicatorCalcReqPropertyDto::getIndicatorCalcTimeRangeDto).map(function).orElse(null);
+//                    TimeRange timeRange = Optional.ofNullable(dto.getIndicatorCalcReq()).map(IndicatorCalcReqPropertyDto::getIndicatorCalcTimeRangeDto).map(IndicatorCalcTimeRangeDto::getTimeRange).orElse(null);
+//                    if (timeRange == null || date == null || timeRangeFlag.getOrDefault(timeRange, false) || (id != null && YEAR_MONTH_ROLL_LIST.contains(id))) {
+//                        continue;
+//                    }
+//                    String value = Optional.ofNullable(dto.getIndexData()).map(IndicatorCalcIndexDataDto::getIndexIndicatorValueMap).map(e -> e.get(indexId)).map(e -> e.get(indicator.name())).orElse(null);
+//                    indexIndicatorList.add(MapUtil.<String, Object>builder("date", date).put("value", value).build());
+//                }
+//                indexValuesMap.put(indexId, indexIndicatorList);
+//            }
+//        }
+//        Map<String, Object> dataset = MapUtil.<String, Object>builder().putAll(valuesMap).putAll(indexValuesMap).build();
+//
+//        Map<String, String> productNameMapping = this.secId2NameService.query(secIds);
+//        if (excess) {
+//            for (String indexId : indexIds) {
+//                productNameMapping.remove(indexId);
+//            }
+//        }
+//        Map<String, Object> extInfos = MapUtil.<String, Object>builder("endDate", params.getEndDate()).put("startDate", params.getStartDate()).build();
+//        return CommonData.<Map<String, Object>>builder().dataset(dataset).productNameMapping(productNameMapping).extInfos(extInfos).build();
+//    }
+//
+//    protected CalcMultipleSecMultipleTimeRangeIndicatorReq buildMultiCalcReq(BaseParams params, List<Indicator> indicatorList,
+//                                                                             List<Indicator> geoIndicatorList,
+//                                                                             Frequency frequency) {
+//        List<String> refIds = params.getFundId();
+//        List<DateIntervalDto> dateIntervalDtoList = new ArrayList<>();
+//        DateIntervalDto defaultIntervalDto = new DateIntervalDto();
+//        defaultIntervalDto.setEndDate(params.getEndDate());
+//        defaultIntervalDto.setFrequency(frequency);
+//        defaultIntervalDto.setDateIntervalType(DateIntervalType.DefaultInterval);
+//        dateIntervalDtoList.add(defaultIntervalDto);
+//
+//        DateIntervalDto customIntervalDto = new DateIntervalDto();
+//        customIntervalDto.setStartDate(params.getStartDate());
+//        customIntervalDto.setEndDate(params.getEndDate());
+//        customIntervalDto.setTimeRange(TimeRange.Custom);
+//        customIntervalDto.setFrequency(frequency);
+//        customIntervalDto.setDateIntervalType(DateIntervalType.CustomInterval);
+//        dateIntervalDtoList.add(customIntervalDto);
+//
+//        Map<String, List<DateIntervalDto>> dateIntervalMap = MapUtil.newHashMap(true);
+//        for (String refId : refIds) {
+//            dateIntervalMap.put(refId, dateIntervalDtoList);
+//        }
+//
+//        List<String> secIds = this.getSecIdsByParams(params);
+//        // 差集求指数id集合,包括基�
+//        List<String> indexIds = CollectionUtil.subtractToList(secIds, refIds);
+//        Map<String, String> benchmarkIdMap = MapUtil.newHashMap(true);
+//        for (String refId : refIds) {
+//            if (StrUtil.isBlank(params.getBenchmarkId())) {
+//                continue;
+//            }
+//            benchmarkIdMap.put(refId, params.getBenchmarkId());
+//        }
+//        return CalcMultipleSecMultipleTimeRangeIndicatorReq.builder()
+//                .mainSecIdList(refIds) // 标的id集合
+//                .secBenchmarkIdMap(benchmarkIdMap) // 标的对应基准
+//                .indexIdList(indexIds) // 指数id集合,包括基�
+//                .raiseType(params.getRaiseType()) // 标的类型
+//                .strategy(this.getOriginStrategy(params)) // 二级策略
+//                .visibility(Visibility.Both)
+//                .dataFrequency(params.getFrequency()) // 净值频�
+//                .navType(params.getNavType()) // 净值类�
+//                .secDateIntervalDtoListMap(dateIntervalMap) // 日期区间
+//                .indicatorList(indicatorList) // 要计算的指标
+//                .geoExtraindicatorList(geoIndicatorList) // 要计算的几何指标
+//                .ifAnnualize(true) // 要年�
+//                .needExtraRet(true)
+//                .needRet(true)
+//                .calcIndexRetIndicatorValue(true) //
+//                .ifConvertPerformanceConsistencyWord(true).build();
+//    }
+//
+//    /**
+//     * 收益统计/收益分布 接口请求业务处理
+//     *
+//     * @param params 请求参数
+//     * @return /
+//     */
+//    public Map<String, Object> revenue(RevenueParams params) {
+//        try {
+//            // 1.参数处理
+//            this.checkParams(params);
+//            if (StrUtil.isBlank(params.getRevenuType()) || !TYPE_LIST.contains(params.getRevenuType())) {
+//                params.setRevenuType(ONE);
+//            }
+//            List<Frequency> frequencies = ListUtil.toList(Frequency.Weekly, Frequency.Monthly, Frequency.Quarterly, Frequency.Annually);
+//            if (params.getRollingFrequency() == null || !frequencies.contains(params.getRollingFrequency())) {
+//                logger.warn(String.format("当前滚动频率为:%s,设置为默认滚动频率:%s", params.getRollingFrequency(), Frequency.Monthly));
+//                params.setRollingFrequency(Frequency.Monthly);
+//            }
+//            //支持调整组距�-20%�
+//            if (TWO.equals(params.getRevenuType())) {
+//                if (!NumberUtil.isNumber(params.getSpace()) || !NumberUtil.isIn(NumberUtil.toBigDecimal(params.getSpace()), NumberUtil.toBigDecimal("1"), NumberUtil.toBigDecimal("20"))) {
+//                    throw new APIException("组距必须是大于1小于20的数");
+//                }
+//            }
+//            boolean ifExcessReturn = params.getIfExcessReturn() != null && params.getIfExcessReturn();
+//            List<String> refIds = params.getFundId();
+//            List<String> secIds = this.getSecIdsByParams(params);
+//            List<String> indexIds = CollectionUtil.subtractToList(secIds, refIds);
+//            List<Indicator> indicators = ListUtil.toList(Indicator.IntervalReturn);
+//            CalcMultipleSecMultipleTimeRangeIndicatorReq req = this.buildCalcReq(params, indicators, indicators, params.getRollingFrequency());
+//            req.setRiskOfFreeId(Consts.RISK_OF_FREE);
+//
+//            // 2、指标计�
+//            Map<String, List<IndicatorCalcPropertyDto>> secRangIndicatorMap = this.baseIndicatorServiceV2.calcMultipleSecMultipleTimeRangeIndicator(req);
+//
+//            // 3、结果处�
+//            Map<String, Object> dataset = MapUtil.newHashMap();
+//            if (ONE.equals(params.getRevenuType())) {
+//                dataset = this.getRevenueDataset(refIds, indexIds, params.getRollingFrequency(), secRangIndicatorMap, ifExcessReturn);
+//            } else if (TWO.equals(params.getRevenuType())) {
+//                dataset = this.loadDistributionData(refIds, indexIds, secRangIndicatorMap, Double.parseDouble(params.getSpace()), ifExcessReturn);
+//            }
+//            Map<String, String> productNameMapping = this.secId2NameService.query(secIds);
+//            Map<String, Object> extInfos = MapUtil.<String, Object>builder("endDate", params.getEndDate()).put("startDate", params.getStartDate()).build();
+//            if (ONE.equals(params.getRevenuType())) {
+//                // table
+//                HistoryRetTableSingleResp resp = getHistoryRetTableSingleResp(refIds, indexIds, secRangIndicatorMap, Indicator.IntervalReturn, ifExcessReturn, params.getRollingFrequency());
+//                extInfos.put("table", this.buildTableData(productNameMapping, resp, ifExcessReturn, false));
+//            }
+//            CommonData<Map<String, Object>> data = CommonData.<Map<String, Object>>builder().dataset(dataset).productNameMapping(productNameMapping).extInfos(extInfos).build();
+//            return CommonUtil.covertToMap(data);
+//        } catch (Exception e) {
+//            logger.error(String.format("收益统计/收益分布接口业务错误:%s", e.getMessage()), e);
+//            return MapUtil.newHashMap();
+//        }
+//    }
+//
+//    private Map<String, Object> getRevenueDataset(List<String> refIds, List<String> indexIds, Frequency frequency, Map<String, List<IndicatorCalcPropertyDto>> secRangIndicatorMap, boolean ifExcessReturn) {
+//        Map<String, Object> dataset = MapUtil.newHashMap();
+//        Map<String, List<Map<String, Object>>> valuesMap = MapUtil.newHashMap(true);
+//        Map<String, List<Map<String, Object>>> indexValuesMap = MapUtil.newHashMap(true);
+//        List<String> dateList = ListUtil.list(false);
+//        for (String refId : refIds) {
+//            List<IndicatorCalcPropertyDto> dtos = Optional.ofNullable(secRangIndicatorMap.get(refId)).filter(e -> !e.isEmpty()).orElse(ListUtil.empty());
+//            // 当前基金的数据处�
+//            List<Map<String, Object>> fundIndicatorList = ListUtil.list(true);
+//            for (IndicatorCalcPropertyDto dto : dtos) {
+//                String id = Optional.ofNullable(dto.getIndicatorCalcReq()).map(IndicatorCalcReqPropertyDto::getIndicatorCalcTimeRangeDto).map(IndicatorCalcTimeRangeDto::getId).orElse(null);
+//                String date = Optional.ofNullable(dto.getIndicatorCalcReq()).map(IndicatorCalcReqPropertyDto::getIndicatorCalcTimeRangeDto).map(IndicatorCalcTimeRangeDto::getEndDate).orElse(null);
+//                if (id == null || YEAR_MONTH_ROLL_LIST.contains(id)) {
+//                    continue;
+//                }
+//                date = this.handleStrDate(date, frequency);
+//                if (!dateList.contains(date)) {
+//                    dateList.add(date);
+//                }
+//                String value = Optional.ofNullable(dto.getSecData()).map(IndicatorCalcSecDataDto::getIndicatorValueMap).map(e -> e.get(Indicator.IntervalReturn.name())).orElse(null);
+//                String extraValue = Optional.ofNullable(dto.getSecData()).map(IndicatorCalcSecDataDto::getExtraGeoIndicatorValueMap).map(e -> e.get(Indicator.IntervalReturn.name())).orElse(null);
+//                Map<String, Object> build = MapUtil.<String, Object>builder("date", date).put("d", date).put("extraValue", extraValue).put("value", value).build();
+//                fundIndicatorList.add(build);
+//            }
+//            valuesMap.put(refId, fundIndicatorList);
+//            // 指数的数据处�
+//            for (String indexId : indexIds) {
+//                if (indexValuesMap.containsKey(indexId)) {
+//                    continue;
+//                }
+//                List<Map<String, Object>> indexIndicatorList = ListUtil.list(true);
+//                for (IndicatorCalcPropertyDto dto : dtos) {
+//                    String id = Optional.ofNullable(dto.getIndicatorCalcReq()).map(IndicatorCalcReqPropertyDto::getIndicatorCalcTimeRangeDto).map(IndicatorCalcTimeRangeDto::getId).orElse(null);
+//                    if (id == null || YEAR_MONTH_ROLL_LIST.contains(id)) {
+//                        continue;
+//                    }
+//                    String date = Optional.ofNullable(dto.getIndicatorCalcReq()).map(IndicatorCalcReqPropertyDto::getIndicatorCalcTimeRangeDto).map(IndicatorCalcTimeRangeDto::getEndDate).orElse(null);
+//                    date = this.handleStrDate(date, frequency);
+//                    String value = Optional.ofNullable(dto.getIndexData()).map(IndicatorCalcIndexDataDto::getIndexIndicatorValueMap).map(e -> e.get(indexId)).map(e -> e.get(Indicator.IntervalReturn.name())).orElse(null);
+//                    indexIndicatorList.add(MapUtil.<String, Object>builder("date", date).put("value", value).build());
+//                }
+//                indexValuesMap.put(indexId, indexIndicatorList);
+//            }
+//        }
+//        dateList.sort(Comparator.naturalOrder());
+//        for (String refId : refIds) {
+//            List<Map<String, Object>> data = ListUtil.list(true);
+//            for (String date : dateList) {
+//                String value = valuesMap.get(refId).stream().filter(e -> date.equals(MapUtil.getStr(e, "date")))
+//                        .findFirst().map(e -> MapUtil.getStr(e, "value")).orElse(null);
+//                Map<String, Object> build = MapUtil.<String, Object>builder().put("date", date).put("value", value).build();
+//                if (ifExcessReturn) {
+//                    String extraValue = valuesMap.get(refId).stream().filter(e -> date.equals(MapUtil.getStr(e, "date")))
+//                            .findFirst().map(e -> MapUtil.getStr(e, "extraValue")).orElse(null);
+//                    build.put("extraValue", extraValue);
+//                }
+//                data.add(build);
+//            }
+//            dataset.put(refId, data);
+//        }
+//        for (String refId : indexIds) {
+//            List<Map<String, Object>> data = ListUtil.list(true);
+//            for (String date : dateList) {
+//                String value = indexValuesMap.get(refId).stream().filter(e -> date.equals(MapUtil.getStr(e, "date")))
+//                        .findFirst().map(e -> MapUtil.getStr(e, "value")).orElse(null);
+//                data.add(MapUtil.<String, Object>builder().put("date", date).put("value", value).build());
+//            }
+//            dataset.put(refId, data);
+//        }
+//        return dataset;
+//    }
+//
+//    /**
+//     * 胜率分析 业务处理
+//     *
+//     * @param params /
+//     * @return /
+//     */
+//    public Map<String, Object> win(WinParams params) {
+//        try {
+//            // 1.参数处理
+//            this.checkParams(params);
+//            List<String> refIds = params.getFundId();
+//            if (refIds.size() > 1) {
+//                logger.warn("多标的不支持胜率分析!");
+//            }
+//            String fundId = refIds.get(0);
+//            Indicator indicator = Indicator.WinRate;
+//            boolean winZero = params.getWinRateBmk() == WinRateBmk.Zero;
+//            List<Indicator> indicators = ListUtil.toList(Indicator.IntervalReturn, indicator);
+//
+//            CalcMultipleSecMultipleTimeRangeIndicatorReq req = this.buildCalcReq(params, indicators, ListUtil.list(false), DateIntervalType.CustomInterval, null);
+//            req.setRiskOfFreeId(Consts.RISK_OF_FREE);
+//            req.setIndexIdList(ListUtil.empty());
+//            req.setNeedRet(true);
+//            req.setNeedExtraRet(true);
+//            if (!winZero) {
+//                req.setGeoExtraindicatorList(ListUtil.toList(indicator));
+//            }
+//
+//            // 2、指标计�
+//            Map<String, List<IndicatorCalcPropertyDto>> secIndicatorMap = this.baseIndicatorServiceV2.calcMultipleSecMultipleTimeRangeIndicator(req);
+//
+//            // 3、结果处�
+//            IndicatorCalcSecDataDto secData = Optional.ofNullable(secIndicatorMap.get(fundId)).filter(e -> !e.isEmpty()).map(e -> e.get(0))
+//                    .map(IndicatorCalcPropertyDto::getSecData).orElseThrow(() -> new APIException("计算错误"));
+//            String winRate = winZero ? secData.getIndicatorValueMap().get(indicator.name()) : secData.getExtraGeoIndicatorValueMap().get(indicator.name());
+//            List<CompoundRet> retList = secData.getRetList();
+//            // 返回结果对象构建
+//            Map<String, String> winData = this.prepareWinRateData("allTime", winRate, retList, winZero);
+//            Double lower = Optional.ofNullable(params.getLower()).map(Double::parseDouble).map(e -> e / 100).orElse(-0.03d);
+//            Double upper = Optional.ofNullable(params.getUpper()).map(Double::parseDouble).map(e -> e / 100).orElse(0.03d);
+//            List<CompoundRet> riseRetList = retList.stream().filter(e -> e.getRetOfBmk() != null && e.getRetOfBmk() >= upper).collect(Collectors.toList());
+//            List<CompoundRet> fallRetList = retList.stream().filter(e -> e.getRetOfBmk() != null && e.getRetOfBmk() <= lower).collect(Collectors.toList());
+//            List<CompoundRet> shockRetList = retList.stream().filter(e -> e.getRetOfBmk() != null && e.getRetOfBmk() <= upper && e.getRetOfBmk() >= lower).collect(Collectors.toList());
+//            List<Map<String, String>> marketWinData = ListUtil.list(true);
+//            Map<String, List<CompoundRet>> timeMap = MapUtil.<String, List<CompoundRet>>builder(MapUtil.newHashMap(true))
+//                    .put("allTime", retList).put("riseTime", riseRetList).put("shockTime", shockRetList).put("fallTime", fallRetList).build();
+//            if (winZero) {
+//                timeMap.remove("shockTime");
+//            }
+//            timeMap.forEach((k, v) -> marketWinData.add(this.prepareWinRateData(k, winRate, v, winZero)));
+//
+//            Map<String, Object> dataset = MapUtil.<String, Object>builder("win", winData).put("marketWin", marketWinData).build();
+//            CommonData<Map<String, Object>> data = CommonData.<Map<String, Object>>builder().dataset(dataset).build();
+//            return CommonUtil.covertToMap(data);
+//        } catch (Exception e) {
+//            logger.error(String.format("胜率计算错误:%s", e.getMessage()), e);
+//            return MapUtil.newHashMap();
+//        }
+//    }
+//
+//    @Override
+//    public Map<String, Object> analyzeIndicatorNew(RangIndicatorParams params) {
+//        // 1.参数处理
+//        this.checkParams(params);
+//        List<String> refIds = params.getFundId();
+//        List<String> secIds = this.getSecIdsByParams(params);
+//        List<String> indexIds = CollectionUtil.subtractToList(secIds, refIds);
+//        Indicator indicator = params.getIndicator();
+//        List<Indicator> indicators = ListUtil.toList(Indicator.MaxDrawdown);
+//        List<Indicator> geoIndicators = ListUtil.list(false);
+//        boolean excess = params.getExcess() != null && params.getExcess() || Indicator.INDICATOR_EXCESS_RETURN_TYPE_ARRAY.contains(params.getIndicator());
+//        if (excess) {
+//            geoIndicators.add(indicator);
+//        } else {
+//            indicators.add(indicator);
+//        }
+//
+//        CalcMultipleSecMultipleTimeRangeIndicatorReq req = this.buildCalcReq(params, indicators, geoIndicators, DateIntervalType.DefaultInterval, null);
+//        req.setRiskOfFreeId(Consts.RISK_OF_FREE);
+//
+//        // 2、指标计�
+//        Map<String, List<IndicatorCalcPropertyDto>> indicatorMap = this.baseIndicatorServiceV2.calcMultipleSecMultipleTimeRangeIndicator(req);
+//
+//        // 3、结果处�
+//        Map<TimeRange, Boolean> timeRangeFlag = MapUtil.newHashMap();
+//        Map<String, Object> valuesMap = MapUtil.newHashMap(true);
+//        Map<String, Object> indexValuesMap = MapUtil.newHashMap(true);
+//        for (String refId : refIds) {
+//            List<IndicatorCalcPropertyDto> dtos = Optional.ofNullable(indicatorMap.get(refId)).filter(e -> !e.isEmpty()).orElse(ListUtil.empty());
+//            // 当前基金的数据处�
+//            List<Map<String, Object>> fundIndicatorList = ListUtil.list(true);
+//            for (IndicatorCalcPropertyDto dto : dtos) {
+//                TimeRange timeRange = Optional.ofNullable(dto.getIndicatorCalcReq()).map(IndicatorCalcReqPropertyDto::getIndicatorCalcTimeRangeDto)
+//                        .map(IndicatorCalcTimeRangeDto::getTimeRange).orElse(null);
+//                if (timeRange == null) {
+//                    continue;
+//                }
+//                if (params.getTimeRange() != null) {
+//                    String start = Optional.ofNullable(dto.getIndicatorCalcReq()).map(IndicatorCalcReqPropertyDto::getIndicatorCalcTimeRangeDto).map(IndicatorCalcTimeRangeDto::getStartDate).orElse(null);
+//                    boolean isFrom = timeRange != TimeRange.FromSetup && timeRange != TimeRange.FromThisYear;
+//                    boolean isDate = CharSequenceUtil.compare(params.getStartDate(), start, true) > 0;
+//                    if (isFrom && isDate) {
+//                        timeRangeFlag.put(timeRange, true);
+//                        continue;
+//                    }
+//                }
+//                String value = Optional.ofNullable(dto.getSecData()).map(e -> excess ? e.getExtraGeoIndicatorValueMap() : e.getIndicatorValueMap())
+//                        .map(e -> e.get(indicator.name())).orElse(null);
+//                fundIndicatorList.add(MapUtil.<String, Object>builder("date", this.handleStrDate(timeRange.name(), null)).put("value", value).build());
+//            }
+//            valuesMap.put(refId, fundIndicatorList);
+//            // 指数的数据处�
+//            for (String indexId : indexIds) {
+//                boolean excessBench = (excess && indexId.equals(params.getBenchmarkId()));
+//                if (indexValuesMap.containsKey(indexId) || excessBench) {
+//                    continue;
+//                }
+//                List<Map<String, Object>> indexIndicatorList = ListUtil.list(true);
+//                for (IndicatorCalcPropertyDto dto : dtos) {
+//                    TimeRange timeRange = Optional.ofNullable(dto.getIndicatorCalcReq()).map(IndicatorCalcReqPropertyDto::getIndicatorCalcTimeRangeDto)
+//                            .map(IndicatorCalcTimeRangeDto::getTimeRange).orElse(null);
+//                    if (timeRange == null || timeRangeFlag.getOrDefault(timeRange, false)) {
+//                        continue;
+//                    }
+//                    String value = Optional.ofNullable(dto.getIndexData()).map(IndicatorCalcIndexDataDto::getIndexIndicatorValueMap).map(e -> e.get(indexId)).map(e -> e.get(indicator.name())).orElse(null);
+//                    indexIndicatorList.add(MapUtil.<String, Object>builder("date", this.handleStrDate(timeRange.name(), null)).put("value", value).build());
+//                }
+//                indexValuesMap.put(indexId, indexIndicatorList);
+//            }
+//        }
+//        Map<String, Object> dataset = MapUtil.<String, Object>builder().putAll(valuesMap).putAll(indexValuesMap).build();
+//
+//        Map<String, String> productNameMapping = this.secId2NameService.query(secIds);
+//        if (excess) {
+//            for (String indexId : indexIds) {
+//                productNameMapping.remove(indexId);
+//            }
+//        }
+//        Map<String, Object> extInfos = MapUtil.<String, Object>builder("endDate", params.getEndDate()).put("startDate", params.getStartDate()).build();
+//        CommonData<Map<String, Object>> data = CommonData.<Map<String, Object>>builder().dataset(dataset).productNameMapping(productNameMapping).extInfos(extInfos).build();
+//        return CommonUtil.covertToMap(data);
+//    }
+//
+//    @Override
+//    public Map<String, Object> analyzeCovNew(AnalyzeCovParams params) {
+//        try {
+//            // 1.参数处理
+//            this.checkParams(params);
+//            String startDate = params.getStartDate();
+//            String endDate = params.getEndDate();
+//            List<String> refIds = params.getFundId();
+//            String fundId = refIds.get(0);
+//            List<Map<String, String>> secTimeRanges = this.baseIndicatorServiceV2.getSecTimeRanges(fundId, params.getRaiseType(), Strategy.All, Visibility.Both);
+//            List<String> secIds = this.getSecIdsByParams(params);
+//            List<String> indexIds = CollectionUtil.subtractToList(secIds, refIds);
+//            List<DateRange> dateRangeList = new RollingSpliter(startDate, endDate, params.getRollingWindow(), params.getRollingWindow(), false, Frequency.Monthly).split();
+//            if (dateRangeList.isEmpty()) {
+//                throw new APIException("净值数量小于窗口期,请尝试调整取值区间");
+//            }
+//            Map<String, List<Double>> corrData = MapUtil.newHashMap();
+//            List<String> dates = ListUtil.list(true);
+//            List<Map<String, Object>> corRetList = ListUtil.list(false);
+//            List<List<Map<String, Object>>> matrixList = this.getMatrixList(params, dateRangeList, dates, corrData, corRetList);
+//            List<Map<String, Object>> dataList = ListUtil.list(true);
+//            for (int i = 0; i < dates.size(); i++) {
+//                Object values = matrixList.get(i).get(0).get("values");
+//                dataList.add(MapUtil.<String, Object>builder("date", dates.get(i))
+//                        .put("matrix", values).build());
+//            }
+//            Map<String, Object> dataset = MapUtil.<String, Object>builder(fundId, dataList).build();
+//            for (String indexId : indexIds) {
+//                List<Map<String, Object>> indexDataList = ListUtil.list(true);
+//                for (int i = 0; i < dates.size(); i++) {
+//                    Object values = matrixList.get(i).stream().filter(e -> Objects.equals(indexId, e.get("id"))).findFirst()
+//                            .map(e -> e.get("values")).orElse(null);
+//                    indexDataList.add(MapUtil.<String, Object>builder("date", dates.get(i))
+//                            .put("value", corrData.get(indexId).get(i))
+//                            .put("matrix", values).build());
+//                }
+//                dataset.put(indexId, indexDataList);
+//            }
+//            String endDate1 = null;
+//            Map<String, String> timeRangeMap = MapUtil.newHashMap();
+//            for (Map<String, String> timeRange : secTimeRanges) {
+//                if (StrUtil.isBlank(endDate1)) {
+//                    endDate1 = timeRange.get("endDate");
+//                }
+//                timeRangeMap.put(timeRange.get("name"), timeRange.get("startDate"));
+//            }
+//            List<Map<String, Object>> resultList = ListUtil.list(true);
+//            Map<TimeRange, String> yearOptions = TimeRange.COR_DATES;
+//            yearOptions.forEach((k, v) -> {
+//                Map<String, Object> result = MapUtil.newHashMap();
+//                result.put("id", v);
+//                result.put("range", k);
+//                result.put("startDate", timeRangeMap.get(k.name()) == null ? null : timeRangeMap.get(k.name()));
+//                resultList.add(result);
+//            });
+//            List<Map<String, Object>> dataset2 = getDataset(params, refIds, indexIds, corRetList, endDate1, resultList);
+//
+//            // 直接把原数据转换一�
+//            Map<String, String> productNameMapping = this.secId2NameService.query(secIds);
+//            Map<String, Object> extInfos = MapUtil.<String, Object>builder().put("table", dataset2).build();
+//            CommonData<Map<String, Object>> data = CommonData.<Map<String, Object>>builder()
+//                    .dataset(dataset).productNameMapping(productNameMapping).extInfos(extInfos).build();
+//            return CommonUtil.covertToMap(data);
+//        } catch (Exception e) {
+//            logger.error(String.format("相关性分析错误:%s", e.getMessage()), e);
+//            return MapUtil.newHashMap();
+//        }
+//    }
+//
+//    private List<List<Map<String, Object>>> getMatrixList(AnalyzeCovParams params, List<DateRange> dateRangeList, List<String> dates, Map<String,
+//            List<Double>> corrData, List<Map<String, Object>> corRetList) {
+//        List<List<Map<String, Object>>> matrixList = ListUtil.list(false);
+//        List<String> refIds = params.getFundId();
+//        String fundId = refIds.get(0);
+//        List<String> secIds = this.getSecIdsByParams(params);
+//        List<String> indexIds = CollectionUtil.subtractToList(secIds, refIds);
+//        IStrategy strategy = StrategyHandleUtils.getStrategy(params.getStrategy());
+//        List<Map<String, String>> secTimeRanges = this.baseIndicatorServiceV2.getSecTimeRanges(fundId, params.getRaiseType(), strategy, Visibility.Both);
+//        String incepStart = null;
+//        String incepEnd = null;
+//        if (CollUtil.isNotEmpty(secTimeRanges)) {
+//            for (Map<String, String> secTimeRange : secTimeRanges) {
+//                if (secTimeRange.get("name").equals(TimeRange.FromSetup.name())) {
+//                    incepStart = secTimeRange.get("startDate");
+//                    incepEnd = secTimeRange.get("endDate");
+//                }
+//            }
+//        }
+//        Frequency frequency = params.getFrequency();
+//        if (frequency == null || frequency == Frequency.Default) {
+//            frequency = Frequency.Daily;
+//        }
+//        Map<String, List<IndicatorCalcPropertyDto>> multiSecRetListNew = this.baseIndicatorServiceV2.getMultiSecRetListNew(
+//                secIds, ListUtil.empty(), frequency, Frequency.Daily, incepStart, incepEnd, false, params.getBenchmarkId(),
+//                params.getRaiseType(), strategy, Visibility.Visible, params.getNavType(), isExtract, params.getUserId());
+//        if (CollectionUtil.isEmpty(indexIds)) {
+//            throw new APIException("指数不能为空");
+//        }
+//        List<Map<String, Object>> mapList = NavUtil.handleNextStepNew(secIds, indexIds, multiSecRetListNew, false);
+//        corRetList.addAll(mapList);
+//        for (DateRange dr : dateRangeList) {
+//            String start = dr.getStartDate();
+//            String end = dr.getEndDate();
+//            dates.add(end);
+//            Map<String, Map<String, Double>> retMap = findRetData(corRetList, start, end);
+//            Double[][] correlationMatrix = CalcUtils.getCorrelationMatrix(retMap, refIds, indexIds);
+//            Double[] values = correlationMatrix[0];
+//            for (int i = 0; i < values.length; i++) {
+//                String idx = indexIds.get(i);
+//                List<Double> cList = corrData.getOrDefault(idx, new ArrayList<>());
+//                cList.add(values[i]);
+//                corrData.put(idx, cList);
+//            }
+//            // 相关性矩�
+//            Double[][] matrix = CalcUtils.getCorrelationMatrix(retMap, secIds, secIds);
+//            List<Map<String, Object>> rowList = new ArrayList<>(matrix.length);
+//            for (int i = 0; i < matrix.length; i++) {
+//                rowList.add(MapUtil.<String, Object>builder("id", secIds.get(i)).put("values", matrix[i]).build());
+//            }
+//            matrixList.add(rowList);
+//        }
+//        return matrixList;
+//    }
+//
+//    private List<Map<String, Object>> getDataset(AnalyzeCovParams params, List<String> refIds, List<String> indexIds, List<Map<String, Object>> corRetList,
+//                                                 String endDate1, List<Map<String, Object>> resultList) {
+//        // 除了成立以来  今年以来 其他都需要加上过滤条�只要开始日期大于等�前端传参的开始日�
+//        List<Map<String, Object>> dataset2 = ListUtil.list(true);
+//        for (Map<String, Object> timeRange : resultList) {
+//            Map<String, Object> temp = MapUtil.newHashMap();
+//            String start = MapUtil.getStr(timeRange, "startDate");
+//            if (StrUtil.isBlank(start)) {
+//                continue;
+//            }
+//            TimeRange range = (TimeRange) timeRange.get("range");
+//            boolean isTime = range != TimeRange.FromSetup && range != TimeRange.FromThisYear;
+//            if (isTime && params.getStartDate().compareTo(start) > 0) {
+//                continue;
+//            }
+//
+//            Map<String, Map<String, Double>> retMap = findRetData(corRetList, start, endDate1);
+//            Double[][] correlationMatrix = CalcUtils.getCorrelationMatrix(retMap, refIds, indexIds);
+//            Double[] values = correlationMatrix[0];
+//            temp.put("timeRange", timeRange.get("id"));
+//            for (int i = 0; i < indexIds.size(); i++) {
+//                temp.put(indexIds.get(i), values[i]);
+//            }
+//            dataset2.add(temp);
+//        }
+//        return dataset2;
+//    }
+//}

+ 5 - 0
src/main/java/com/smppw/analysis/domain/manager/performance/package-info.java

@@ -0,0 +1,5 @@
+package com.smppw.analysis.domain.manager.performance;
+
+/*
+   这里重新实现业绩表现的接口
+ */

+ 21 - 0
src/main/java/com/smppw/analysis/infrastructure/consts/AssetStyleType.java

@@ -0,0 +1,21 @@
+package com.smppw.analysis.infrastructure.consts;
+
+import java.util.stream.Stream;
+
+public enum AssetStyleType {
+	MultiAsset(2),
+	SegmentationAsset(10),
+	RongZhiStrategy(7);
+	
+	private int id;
+	private AssetStyleType(int id) {
+		this.id = id;
+	}
+	public int getId() {
+		return id;
+	}
+	
+	public static AssetStyleType getIndex(int id) {
+		return Stream.of(AssetStyleType.values()).filter(e -> e.id == id).findFirst().orElse(null);
+	}
+}

+ 24 - 0
src/main/java/com/smppw/analysis/infrastructure/consts/Constraint.java

@@ -0,0 +1,24 @@
+package com.smppw.analysis.infrastructure.consts;
+
+import java.util.stream.Stream;
+
+/**
+ * @author zhengsongliang
+ * @datetime 2017年8月7日 下午4:41:43
+ */
+public enum Constraint {
+	LongPosition(1), ShortPosition(2);
+	private int id;
+
+	public int getId() {
+		return id;
+	}
+
+	private Constraint(int id) {
+		this.id = id;
+	}
+
+	public static Constraint getConstraint(int id) {
+		return Stream.of(Constraint.values()).filter(e -> e.id == id).findFirst().orElse(null);
+	}
+}

+ 23 - 0
src/main/java/com/smppw/analysis/infrastructure/consts/WinRateBmk.java

@@ -0,0 +1,23 @@
+package com.smppw.analysis.infrastructure.consts;
+
+import java.util.stream.Stream;
+
+/**
+ * @author zhengsongliang
+ */
+public enum WinRateBmk {
+	Benchmark(1), Zero(2),AssetModel(3);
+	private final int id;
+
+	WinRateBmk(int id) {
+		this.id = id;
+	}
+
+	public int getId() {
+		return id;
+	}
+
+	public static WinRateBmk getWinningRateBmk(int id) {
+		return Stream.of(WinRateBmk.values()).filter(e -> e.id == id).findFirst().orElse(null);
+	}
+}