|
@@ -0,0 +1,359 @@
|
|
|
+package data
|
|
|
+
|
|
|
+import (
|
|
|
+ "encoding/json"
|
|
|
+ "errors"
|
|
|
+ "eta/eta_hub/models/data_manage"
|
|
|
+ "eta/eta_hub/utils"
|
|
|
+ "fmt"
|
|
|
+ "strings"
|
|
|
+ "time"
|
|
|
+)
|
|
|
+
|
|
|
+// TraceEdbInfoByEdbInfoId 指标追溯
|
|
|
+func TraceEdbInfoByEdbInfoId(edbInfoId int) (traceEdbInfo data_manage.TraceEdbInfoResp, err error) {
|
|
|
+ edbInfo, err := data_manage.GetEdbInfoById(edbInfoId)
|
|
|
+ if err != nil {
|
|
|
+ return
|
|
|
+ }
|
|
|
+ edbInfoRuleMap := make(map[int]string, 0)
|
|
|
+ edbMappingMap := make(map[int][]*data_manage.EdbInfoCalculateMappingInfo)
|
|
|
+ //edbInfoRuleMap[edbInfoId] = getEdbRuleTitle(edbInfo)
|
|
|
+ traceEdbInfo = data_manage.TraceEdbInfoResp{
|
|
|
+ //EdbInfoId: edbInfo.EdbInfoId,
|
|
|
+ EdbInfoId: edbInfoId,
|
|
|
+ EdbInfoType: edbInfo.EdbInfoType,
|
|
|
+ EdbName: edbInfo.EdbName,
|
|
|
+ EdbType: edbInfo.EdbType,
|
|
|
+ //Source: edbInfo.Source,
|
|
|
+ UniqueCode: edbInfo.UniqueCode,
|
|
|
+ ClassifyId: edbInfo.ClassifyId,
|
|
|
+ EdbInfo: edbInfo,
|
|
|
+ }
|
|
|
+ findIdMap := make(map[int]int)
|
|
|
+ findIdMap[edbInfoId] = edbInfoId
|
|
|
+ existMap := make(map[int]data_manage.TraceEdbInfoResp)
|
|
|
+ traceEdbInfo.Child, err = traceEdbInfoByEdbInfoId(edbInfoId, traceEdbInfo, edbInfoRuleMap, findIdMap, existMap, edbMappingMap)
|
|
|
+
|
|
|
+ edbInfoIdList := make([]int, 0)
|
|
|
+ for _, v := range findIdMap {
|
|
|
+ edbInfoIdList = append(edbInfoIdList, v)
|
|
|
+ }
|
|
|
+ edbInfoList, err := data_manage.GetEdbInfoByIdList(edbInfoIdList)
|
|
|
+ if err != nil {
|
|
|
+ return
|
|
|
+ }
|
|
|
+ edbInfoMap := make(map[int]*data_manage.EdbInfo)
|
|
|
+ for _, tmpEdbInfo := range edbInfoList {
|
|
|
+ edbInfoMap[tmpEdbInfo.EdbInfoId] = tmpEdbInfo
|
|
|
+ }
|
|
|
+ traceEdbInfo, err = handleTraceEdbInfo(traceEdbInfo, 0, edbInfoMap, edbMappingMap)
|
|
|
+ return
|
|
|
+}
|
|
|
+
|
|
|
+// traceEdbInfoByEdbInfoId 指标追溯
|
|
|
+func traceEdbInfoByEdbInfoId(edbInfoId int, traceEdbInfo data_manage.TraceEdbInfoResp, edbInfoRuleMap map[int]string, findIdMap map[int]int, existMap map[int]data_manage.TraceEdbInfoResp, edbMappingMap map[int][]*data_manage.EdbInfoCalculateMappingInfo) (child []data_manage.TraceEdbInfoResp, err error) {
|
|
|
+ traceEdbInfo, ok := existMap[edbInfoId]
|
|
|
+ if ok {
|
|
|
+ return
|
|
|
+ }
|
|
|
+ child = make([]data_manage.TraceEdbInfoResp, 0)
|
|
|
+
|
|
|
+ edbInfoMappingList, e := data_manage.GetEdbInfoCalculateMappingListByEdbInfoId(edbInfoId)
|
|
|
+ if e != nil {
|
|
|
+ err = fmt.Errorf("GetEdbInfoCalculateMappingListByEdbInfoId err: %s", e.Error())
|
|
|
+ return
|
|
|
+ }
|
|
|
+
|
|
|
+ // 指标信息map
|
|
|
+ edbInfoMap := make(map[int]*data_manage.EdbInfo)
|
|
|
+ if len(edbInfoMappingList) > 0 {
|
|
|
+ fromEdbInfoIdList := make([]int, 0)
|
|
|
+ for _, v := range edbInfoMappingList {
|
|
|
+ fromEdbInfoIdList = append(fromEdbInfoIdList, v.FromEdbInfoId)
|
|
|
+ }
|
|
|
+ edbInfoList, tmpErr := data_manage.GetEdbInfoByIdList(fromEdbInfoIdList)
|
|
|
+ if tmpErr != nil {
|
|
|
+ err = fmt.Errorf("traceEdbInfoByEdbInfoId GetEdbInfoByIdList err: %s", tmpErr.Error())
|
|
|
+ return
|
|
|
+ }
|
|
|
+ for _, v := range edbInfoList {
|
|
|
+ edbInfoMap[v.EdbInfoId] = v
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ edbMappingMap[edbInfoId] = edbInfoMappingList
|
|
|
+ for _, v := range edbInfoMappingList {
|
|
|
+ tmpEdbInfoId := v.FromEdbInfoId
|
|
|
+ tmpTraceEdbInfo := data_manage.TraceEdbInfoResp{
|
|
|
+ EdbInfoId: tmpEdbInfoId,
|
|
|
+ EdbInfoType: v.FromEdbInfoType,
|
|
|
+ EdbType: v.FromEdbType,
|
|
|
+ UniqueCode: v.FromUniqueCode,
|
|
|
+ ClassifyId: v.FromClassifyId,
|
|
|
+ EdbInfo: edbInfoMap[v.FromEdbInfoId],
|
|
|
+ }
|
|
|
+
|
|
|
+ // 计算指标/预测指标继续溯源
|
|
|
+ if v.FromEdbType == 2 || v.FromEdbInfoType == 1 {
|
|
|
+ // 查过了就不查了
|
|
|
+ if _, ok2 := findIdMap[tmpEdbInfoId]; !ok2 {
|
|
|
+ tmpTraceEdbInfo.Child, e = traceEdbInfoByEdbInfoId(tmpEdbInfoId, tmpTraceEdbInfo, edbInfoRuleMap, findIdMap, existMap, edbMappingMap)
|
|
|
+ if e != nil {
|
|
|
+ err = fmt.Errorf("traceEdbInfoByEdbInfoId err: %s", e.Error())
|
|
|
+ return
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ child = append(child, tmpTraceEdbInfo)
|
|
|
+ findIdMap[tmpEdbInfoId] = tmpEdbInfoId
|
|
|
+ }
|
|
|
+ existMap[edbInfoId] = traceEdbInfo
|
|
|
+ return
|
|
|
+}
|
|
|
+
|
|
|
+func handleTraceEdbInfo(traceEdbInfoResp data_manage.TraceEdbInfoResp, parentEdbInfoId int, edbInfoMap map[int]*data_manage.EdbInfo, edbMappingMap map[int][]*data_manage.EdbInfoCalculateMappingInfo) (newTraceEdbInfoResp data_manage.TraceEdbInfoResp, err error) {
|
|
|
+ edbInfo, ok := edbInfoMap[traceEdbInfoResp.EdbInfoId]
|
|
|
+ if !ok {
|
|
|
+ err = errors.New("指标异常")
|
|
|
+ return
|
|
|
+ }
|
|
|
+
|
|
|
+ var parentEdbInfo *data_manage.EdbInfo
|
|
|
+ if parentEdbInfoId > 0 {
|
|
|
+ parentEdbInfo, ok = edbInfoMap[parentEdbInfoId]
|
|
|
+ if !ok {
|
|
|
+ err = errors.New("指标异常")
|
|
|
+ return
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ //traceEdbInfoResp.EdbName = edbInfo.EdbName
|
|
|
+ traceEdbInfoResp.EdbName, traceEdbInfoResp.RuleTitle = getEdbRuleTitle(edbInfo, parentEdbInfo, traceEdbInfoResp.Child, edbInfoMap, edbMappingMap)
|
|
|
+
|
|
|
+ if traceEdbInfoResp.Child != nil && len(traceEdbInfoResp.Child) > 0 {
|
|
|
+ for k, v := range traceEdbInfoResp.Child {
|
|
|
+ traceEdbInfoResp.Child[k], err = handleTraceEdbInfo(v, traceEdbInfoResp.EdbInfoId, edbInfoMap, edbMappingMap)
|
|
|
+ if err != nil {
|
|
|
+ return
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ newTraceEdbInfoResp = traceEdbInfoResp
|
|
|
+
|
|
|
+ return
|
|
|
+}
|
|
|
+
|
|
|
+// getEdbRule 获取规则名称
|
|
|
+func getEdbRuleTitle(edbInfo, parentEdbInfo *data_manage.EdbInfo, childList []data_manage.TraceEdbInfoResp, edbInfoMap map[int]*data_manage.EdbInfo, edbMappingMap map[int][]*data_manage.EdbInfoCalculateMappingInfo) (edbName, ruleTitle string) {
|
|
|
+ edbName = edbInfo.EdbName
|
|
|
+ ruleTitle = `来源于` + edbInfo.SourceName
|
|
|
+
|
|
|
+ if parentEdbInfo != nil {
|
|
|
+ edbMappingList, ok := edbMappingMap[parentEdbInfo.EdbInfoId]
|
|
|
+ if !ok {
|
|
|
+ edbMappingList = []*data_manage.EdbInfoCalculateMappingInfo{}
|
|
|
+ }
|
|
|
+ // 指标名称
|
|
|
+ switch parentEdbInfo.Source {
|
|
|
+ case utils.DATA_SOURCE_CALCULATE, utils.DATA_SOURCE_PREDICT_CALCULATE:
|
|
|
+ for _, v := range edbMappingList {
|
|
|
+ if v.FromEdbInfoId == edbInfo.EdbInfoId {
|
|
|
+ edbName = fmt.Sprintf("%s(%s)", edbInfo.EdbName, v.FromTag)
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ case utils.DATA_SOURCE_CALCULATE_ZJPJ, utils.DATA_SOURCE_PREDICT_CALCULATE_ZJPJ, utils.DATA_SOURCE_CALCULATE_LJZTBPJ, utils.DATA_SOURCE_PREDICT_CALCULATE_LJZTBPJ: // 直接拼接 ,累计值同比拼接
|
|
|
+ for _, v := range edbMappingList {
|
|
|
+ if v.FromEdbInfoId == edbInfo.EdbInfoId {
|
|
|
+ tmpName := ``
|
|
|
+ if v.FromTag == `A` {
|
|
|
+ tmpName = `拼接日期前`
|
|
|
+ } else if v.FromTag == `B` {
|
|
|
+ tmpName = `拼接日期后`
|
|
|
+ }
|
|
|
+ edbName = fmt.Sprintf("%s(%s)", edbInfo.EdbName, tmpName)
|
|
|
+ }
|
|
|
+ }
|
|
|
+ case utils.DATA_SOURCE_CALCULATE_NHCC, utils.DATA_SOURCE_PREDICT_CALCULATE_NHCC: //计算指标(拟合残差)
|
|
|
+ for _, v := range edbMappingList {
|
|
|
+ //(需对上游指标+自变量,领先10天/因变量)
|
|
|
+ if v.FromEdbInfoId == edbInfo.EdbInfoId {
|
|
|
+ tmpName := ``
|
|
|
+ if v.FromTag == `A` {
|
|
|
+ tmpName = fmt.Sprintf(`自变量,领先%d天`, v.MoveValue)
|
|
|
+ } else if v.FromTag == `B` {
|
|
|
+ tmpName = `因变量`
|
|
|
+ }
|
|
|
+ edbName = fmt.Sprintf("%s(%s)", edbInfo.EdbName, tmpName)
|
|
|
+ }
|
|
|
+ }
|
|
|
+ case utils.DATA_SOURCE_CALCULATE_CORRELATION: // 滚动相关性
|
|
|
+ for _, v := range edbMappingList {
|
|
|
+ if v.FromEdbInfoId == edbInfo.EdbInfoId {
|
|
|
+ edbName = fmt.Sprintf("%s(%s)", edbInfo.EdbName, v.FromTag)
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if edbInfo.EdbType == 1 {
|
|
|
+ // 基础指标的话,直接返回来源名称
|
|
|
+ //ruleTitle = `来源于`+edbInfo.SourceName
|
|
|
+
|
|
|
+ return
|
|
|
+ }
|
|
|
+
|
|
|
+ // 规则
|
|
|
+ switch edbInfo.Source {
|
|
|
+ case utils.DATA_SOURCE_CALCULATE, utils.DATA_SOURCE_PREDICT_CALCULATE:
|
|
|
+ ruleTitle = "=" + edbInfo.CalculateFormula
|
|
|
+ case utils.DATA_SOURCE_CALCULATE_LJZZY, utils.DATA_SOURCE_PREDICT_CALCULATE_LJZZY:
|
|
|
+ ruleTitle = `累计转月值计算`
|
|
|
+ case utils.DATA_SOURCE_CALCULATE_TBZ, utils.DATA_SOURCE_PREDICT_CALCULATE_TBZ:
|
|
|
+ ruleTitle = `同比值计算`
|
|
|
+ case utils.DATA_SOURCE_CALCULATE_TCZ, utils.DATA_SOURCE_PREDICT_CALCULATE_TCZ:
|
|
|
+ ruleTitle = `同差值计算`
|
|
|
+ case utils.DATA_SOURCE_CALCULATE_NSZYDPJJS, utils.DATA_SOURCE_PREDICT_CALCULATE_NSZYDPJJS:
|
|
|
+ ruleTitle = fmt.Sprintf("N数值移动均值计算(N=%s)", edbInfo.CalculateFormula)
|
|
|
+ case utils.DATA_SOURCE_CALCULATE_HBZ, utils.DATA_SOURCE_PREDICT_CALCULATE_HBZ:
|
|
|
+ ruleTitle = fmt.Sprintf("N数值环比值计算(N=%s)", edbInfo.CalculateFormula)
|
|
|
+ case utils.DATA_SOURCE_CALCULATE_HCZ, utils.DATA_SOURCE_PREDICT_CALCULATE_HCZ:
|
|
|
+ ruleTitle = fmt.Sprintf("N数值环差值计算(N=%s)", edbInfo.CalculateFormula)
|
|
|
+ case utils.DATA_SOURCE_CALCULATE_TIME_SHIFT, utils.DATA_SOURCE_PREDICT_CALCULATE_TIME_SHIFT:
|
|
|
+ moveType := `领先`
|
|
|
+ if edbInfo.MoveType == 2 {
|
|
|
+ moveType = "滞后"
|
|
|
+ }
|
|
|
+ ruleTitle = fmt.Sprintf("时间移位计算(%s%s%s)", moveType, edbInfo.CalculateFormula, edbInfo.MoveFrequency)
|
|
|
+ case utils.DATA_SOURCE_CALCULATE_BP, utils.DATA_SOURCE_PREDICT_CALCULATE_BP: // 变频
|
|
|
+ childFrequency := ``
|
|
|
+ if len(childList) > 0 {
|
|
|
+ if childEdbInfo, ok := edbInfoMap[childList[0].EdbInfoId]; ok {
|
|
|
+ childFrequency = childEdbInfo.Frequency
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+ ruleTitle = fmt.Sprintf("升频计算(%s转%s)", childFrequency, edbInfo.Frequency)
|
|
|
+ case utils.DATA_SOURCE_CALCULATE_ZJPJ, utils.DATA_SOURCE_PREDICT_CALCULATE_ZJPJ: // 直接拼接
|
|
|
+ ruleTitle = fmt.Sprintf("直接拼接计算(%s)", edbInfo.CalculateFormula)
|
|
|
+ case utils.DATA_SOURCE_CALCULATE_LJZTBPJ, utils.DATA_SOURCE_PREDICT_CALCULATE_LJZTBPJ: // 累计值同比拼
|
|
|
+ ruleTitle = fmt.Sprintf("累计值同比值拼接计算(%s)", edbInfo.CalculateFormula)
|
|
|
+ case utils.DATA_SOURCE_PYTHON:
|
|
|
+ ruleTitle = `代码运算`
|
|
|
+ case utils.DATA_SOURCE_CALCULATE_CJJX, utils.DATA_SOURCE_PREDICT_CALCULATE_CJJX:
|
|
|
+ ruleTitle = fmt.Sprintf("超季节性计算(N=%s,%s)", edbInfo.CalculateFormula, edbInfo.Calendar)
|
|
|
+ case utils.DATA_SOURCE_CALCULATE_NHCC, utils.DATA_SOURCE_PREDICT_CALCULATE_NHCC: //计算指标(拟合残差)
|
|
|
+ var startDate, endDate string
|
|
|
+ dateList := strings.Split(edbInfo.CalculateFormula, ",")
|
|
|
+ if len(dateList) == 2 {
|
|
|
+ startDate = dateList[0]
|
|
|
+ endDate = dateList[1]
|
|
|
+ }
|
|
|
+ ruleTitle = fmt.Sprintf("拟合残差计算(%s至%s)", startDate, endDate)
|
|
|
+ case utils.DATA_SOURCE_CALCULATE_ADJUST:
|
|
|
+ ruleTitle = `数据调整`
|
|
|
+ case utils.DATA_SOURCE_CALCULATE_NH, utils.DATA_SOURCE_PREDICT_CALCULATE_NH:
|
|
|
+ ruleTitle = `年化计算`
|
|
|
+ case utils.DATA_SOURCE_CALCULATE_KSZS, utils.DATA_SOURCE_PREDICT_CALCULATE_KSZS: // 扩散指数->53
|
|
|
+ type KszsConfig struct {
|
|
|
+ DateType int `description:"扩散指标日期;1:全部指标日期并集;2:部分指标日期并集"`
|
|
|
+ CheckList []string `description:"选中的数据,A,B,C"`
|
|
|
+ }
|
|
|
+ var config KszsConfig
|
|
|
+ err := json.Unmarshal([]byte(edbInfo.CalculateFormula), &config)
|
|
|
+ if err != nil {
|
|
|
+ return
|
|
|
+ }
|
|
|
+ var startDate, endDate time.Time
|
|
|
+
|
|
|
+ childEdbInfoIdList := make([]int, 0)
|
|
|
+ if config.DateType == 1 {
|
|
|
+ for _, v := range childList {
|
|
|
+ childEdbInfoIdList = append(childEdbInfoIdList, v.EdbInfoId)
|
|
|
+ }
|
|
|
+
|
|
|
+ } else {
|
|
|
+ if parentEdbInfo != nil {
|
|
|
+ edbMappingList, ok := edbMappingMap[parentEdbInfo.EdbInfoId]
|
|
|
+ if !ok {
|
|
|
+ edbMappingList = []*data_manage.EdbInfoCalculateMappingInfo{}
|
|
|
+ }
|
|
|
+ tagMap := make(map[string]int)
|
|
|
+ for _, v := range edbMappingList {
|
|
|
+ tagMap[v.FromTag] = v.FromEdbInfoId
|
|
|
+ }
|
|
|
+ for _, v := range config.CheckList {
|
|
|
+ if tmpEdbInfoId, ok := tagMap[v]; ok {
|
|
|
+ childEdbInfoIdList = append(childEdbInfoIdList, tmpEdbInfoId)
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ for _, v := range childEdbInfoIdList {
|
|
|
+ if childEdbInfo, ok := edbInfoMap[v]; ok {
|
|
|
+ tmpStartDate, tmpErr := time.ParseInLocation(utils.FormatDate, childEdbInfo.StartDate, time.Local)
|
|
|
+ if tmpErr != nil {
|
|
|
+ return
|
|
|
+ }
|
|
|
+ if startDate.IsZero() || startDate.After(tmpStartDate) {
|
|
|
+ startDate = tmpStartDate
|
|
|
+ }
|
|
|
+
|
|
|
+ tmpEndDate, tmpErr := time.ParseInLocation(utils.FormatDate, childEdbInfo.EndDate, time.Local)
|
|
|
+ if tmpErr != nil {
|
|
|
+ return
|
|
|
+ }
|
|
|
+ if endDate.IsZero() || endDate.Before(tmpEndDate) {
|
|
|
+ endDate = tmpEndDate
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ ruleTitle = fmt.Sprintf("扩散指数计算(%s至%s)", startDate.Format(utils.FormatDate), endDate.Format(utils.FormatDate))
|
|
|
+ case utils.DATA_SOURCE_STOCK_PLANT:
|
|
|
+ ruleTitle = `来源于装置分析`
|
|
|
+ case utils.DATA_SOURCE_CALCULATE_CORRELATION:
|
|
|
+ type EdbCalculateFormula struct {
|
|
|
+ BaseCalculateValue int `description:"基础计算窗口"`
|
|
|
+ BaseCalculateUnit string `description:"基础计算频度"`
|
|
|
+ LeadValue int `description:"领先期数"`
|
|
|
+ LeadUnit string `description:"频度"`
|
|
|
+ CalculateValue int `description:"计算窗口"`
|
|
|
+ CalculateUnit string `description:"计算频度"`
|
|
|
+ }
|
|
|
+ var correlationConf EdbCalculateFormula
|
|
|
+ err := json.Unmarshal([]byte(edbInfo.CalculateFormula), &correlationConf)
|
|
|
+ if err != nil {
|
|
|
+ return
|
|
|
+ }
|
|
|
+ ruleTitle = fmt.Sprintf("滚动相关性(计算窗口%d%s,B领先A%d%s)", correlationConf.CalculateValue, correlationConf.CalculateUnit, correlationConf.LeadValue, correlationConf.LeadUnit)
|
|
|
+ case utils.DATA_SOURCE_CALCULATE_JP, utils.DATA_SOURCE_PREDICT_CALCULATE_JP:
|
|
|
+ childFrequency := ``
|
|
|
+ if len(childList) > 0 {
|
|
|
+ if childEdbInfo, ok := edbInfoMap[childList[0].EdbInfoId]; ok {
|
|
|
+ childFrequency = childEdbInfo.Frequency
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+ ruleTitle = fmt.Sprintf("降频计算(%s转%s,%s)", childFrequency, edbInfo.Frequency, edbInfo.CalculateFormula)
|
|
|
+ case utils.DATA_SOURCE_CALCULATE_STANDARD_DEVIATION:
|
|
|
+ ruleTitle = fmt.Sprintf("标准差(滚动%s期)", edbInfo.CalculateFormula)
|
|
|
+ case utils.DATA_SOURCE_CALCULATE_PERCENTILE, utils.DATA_SOURCE_PREDICT_CALCULATE_PERCENTILE:
|
|
|
+ type TempCalculate struct {
|
|
|
+ CalculateValue int `description:"计算窗口"`
|
|
|
+ CalculateUnit string `description:"计算频度"`
|
|
|
+ }
|
|
|
+ cf := TempCalculate{}
|
|
|
+ if e := json.Unmarshal([]byte(edbInfo.CalculateFormula), &cf); e != nil {
|
|
|
+ return
|
|
|
+ }
|
|
|
+ ruleTitle = fmt.Sprintf("百分位(时间长度%d%s)", cf.CalculateValue, cf.CalculateUnit)
|
|
|
+ case utils.DATA_SOURCE_CALCULATE_ZSXY, utils.DATA_SOURCE_PREDICT_CALCULATE_ZSXY:
|
|
|
+ ruleTitle = `指数修匀计算`
|
|
|
+ }
|
|
|
+
|
|
|
+ return
|
|
|
+}
|