浏览代码

Merge remote-tracking branch 'origin/eta/1.8.4' into debug

# Conflicts:
#	controllers/data_manage/edb_info.go
Roc 11 月之前
父节点
当前提交
18d7c2284a

+ 28 - 6
controllers/data_manage/business_data.go

@@ -63,11 +63,19 @@ func (c *EdbBusinessController) List() {
 		c.Data["json"] = br
 		c.ServeJSON()
 	}()
-	pageSize, _ := c.GetInt("PageSize")
-	currentIndex, _ := c.GetInt("CurrentIndex")
-	keywords := c.GetString("Keywords")
-	frequency := c.GetString("Frequency")
-	source, _ := c.GetInt("Source") //分类
+
+	req := &request.BusinessDataListReq{}
+	if e := c.ParseForm(req); e != nil {
+		br.Msg = "获取失败"
+		br.ErrMsg = "参数解析失败, Err: " + e.Error()
+		return
+	}
+
+	pageSize := req.PageSize
+	currentIndex := req.CurrentIndex
+	keywords := req.Keywords
+	frequency := req.Frequency
+	source := req.Source
 
 	var startSize int
 	if pageSize <= 0 {
@@ -113,6 +121,20 @@ func (c *EdbBusinessController) List() {
 		pars = append(pars, source)
 	}
 
+	// 排序, 默认创建时间倒序
+	orderFields := map[int]string{
+		0: data_manage.BaseFromBusinessIndexCols.CreateTime, 1: data_manage.BaseFromBusinessIndexCols.StartDate,
+		2: data_manage.BaseFromBusinessIndexCols.EndDate,
+	}
+	orderType := map[int]string{0: "DESC", 1: "ASC", 2: "DESC"}
+	orderRule := ``
+
+	_, ok1 := orderFields[req.SortField]
+	_, ok2 := orderType[req.SortRule]
+	if ok1 && ok2 {
+		orderRule = fmt.Sprintf("%s %s", orderFields[req.SortField], orderType[req.SortRule])
+	}
+
 	obj := data_manage.BaseFromBusinessIndex{}
 
 	total, err := obj.GetListCount(condition, pars)
@@ -121,7 +143,7 @@ func (c *EdbBusinessController) List() {
 		br.ErrMsg = "获取失败,Err:" + err.Error()
 		return
 	}
-	list, err := obj.GetPageItemsByCondition(condition, pars, startSize, pageSize)
+	list, err := obj.GetPageItemsByCondition(condition, pars, orderRule, startSize, pageSize)
 	if err != nil {
 		br.Msg = "获取失败"
 		br.ErrMsg = "获取失败,Err:" + err.Error()

+ 32 - 0
controllers/data_manage/edb_info.go

@@ -9,6 +9,7 @@ import (
 	request2 "eta/eta_api/models/data_manage/excel/request"
 	"eta/eta_api/models/data_manage/request"
 	"eta/eta_api/models/data_manage/response"
+	"eta/eta_api/models/mgo"
 	"eta/eta_api/models/system"
 	"eta/eta_api/services/alarm_msg"
 	"eta/eta_api/services/data"
@@ -19,6 +20,8 @@ import (
 	etaTrialService "eta/eta_api/services/eta_trial"
 	"eta/eta_api/utils"
 	"fmt"
+	"github.com/rdlucklib/rdluck_tools/paging"
+	"go.mongodb.org/mongo-driver/bson"
 	"strconv"
 	"strings"
 	"sync"
@@ -1723,6 +1726,35 @@ func (this *EdbInfoController) EdbInfoSearch() {
 				searchItem.Unit = "%"
 				searchItem.EdbName = indexInfo.IndexName
 			}
+		} else if source == utils.DATA_SOURCE_BUSINESS { //外部数据
+			indexObj := data_manage.BaseFromBusinessIndex{}
+			indexInfo, err := indexObj.GetDetailByEdbCode(edbCode)
+			if err != nil && err.Error() != utils.ErrNoRow() {
+				br.Msg = "获取失败"
+				br.ErrMsg = "获取外部数据指标信息失败,Err:" + err.Error()
+				return
+			}
+
+			obj := mgo.BaseFromBusinessData{}
+			tmpDataList, err := obj.GetLimitDataList(bson.M{"index_code": edbCode}, utils.EDB_DATA_LIMIT, []string{"-data_time"})
+			if err != nil && err.Error() != utils.ErrNoRow() {
+				br.Msg = "获取失败"
+				br.ErrMsg = "获取外部数据已存在信息失败,Err:" + err.Error()
+				return
+			}
+			dataItems := make([]*data_manage.EdbInfoSearchData, 0)
+			for _, v := range tmpDataList {
+				dataItems = append(dataItems, &data_manage.EdbInfoSearchData{
+					DataTime: v.DataTime.Format(utils.FormatDate),
+					Value:    v.Value,
+				})
+			}
+			searchItem.DataList = dataItems
+			searchItem.StartDate = indexInfo.StartDate.Format(utils.FormatDate)
+			searchItem.EndDate = indexInfo.EndDate.Format(utils.FormatDate)
+			searchItem.Frequency = indexInfo.Frequency
+			searchItem.Unit = indexInfo.Unit
+			searchItem.EdbName = indexInfo.IndexName
 		} else {
 			// 代码中没有的来源那么从edb_source中找是否有对应的
 			sourceItem := data_manage.EdbSourceIdMap[source]

+ 13 - 0
go.mod

@@ -33,6 +33,7 @@ require (
 	github.com/mojocn/base64Captcha v1.3.6
 	github.com/nosixtools/solarlunar v0.0.0-20211112060703-1b6dea7b4a19
 	github.com/olivere/elastic/v7 v7.0.32
+	github.com/qiniu/qmgo v1.1.8
 	github.com/rdlucklib/rdluck_tools v1.0.3
 	github.com/shopspring/decimal v1.3.1
 	github.com/silenceper/wechat/v2 v2.1.6
@@ -42,6 +43,7 @@ require (
 	github.com/tencentcloud/tencentcloud-sdk-go/tencentcloud/ses v1.0.880
 	github.com/xuri/excelize/v2 v2.8.1
 	github.com/yidane/formula v0.0.0-20220322063702-c9da84ba3476
+	go.mongodb.org/mongo-driver v1.15.0
 	golang.org/x/net v0.21.0
 	gopkg.in/gomail.v2 v2.0.0-20160411212932-81ebce5c23df
 )
@@ -69,8 +71,12 @@ require (
 	github.com/dustin/go-humanize v1.0.1 // indirect
 	github.com/fatih/structs v1.1.0 // indirect
 	github.com/fsnotify/fsnotify v1.6.0 // indirect
+	github.com/go-playground/locales v0.13.0 // indirect
+	github.com/go-playground/universal-translator v0.17.0 // indirect
+	github.com/go-playground/validator/v10 v10.4.1 // indirect
 	github.com/golang/freetype v0.0.0-20170609003504-e2365dfdc4a0 // indirect
 	github.com/golang/protobuf v1.5.3 // indirect
+	github.com/golang/snappy v0.0.1 // indirect
 	github.com/gonum/blas v0.0.0-20181208220705-f22b278b28ac // indirect
 	github.com/gonum/floats v0.0.0-20181209220543-c233463c7e82 // indirect
 	github.com/gonum/integrate v0.0.0-20181209220457-a422b5c0fdf2 // indirect
@@ -85,6 +91,7 @@ require (
 	github.com/json-iterator/go v1.1.12 // indirect
 	github.com/klauspost/compress v1.17.6 // indirect
 	github.com/klauspost/cpuid/v2 v2.2.6 // indirect
+	github.com/leodido/go-urn v1.2.0 // indirect
 	github.com/mailru/easyjson v0.7.7 // indirect
 	github.com/matttproud/golang_protobuf_extensions v1.0.4 // indirect
 	github.com/minio/md5-simd v1.1.2 // indirect
@@ -93,6 +100,7 @@ require (
 	github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect
 	github.com/modern-go/reflect2 v1.0.2 // indirect
 	github.com/mohae/deepcopy v0.0.0-20170929034955-c48cc78d4826 // indirect
+	github.com/montanaflynn/stats v0.0.0-20171201202039-1bf9dbcd8cbe // indirect
 	github.com/opentracing/opentracing-go v1.2.1-0.20220228012449-10b1cf09e00b // indirect
 	github.com/pkg/errors v0.9.1 // indirect
 	github.com/prometheus/client_golang v1.16.0 // indirect
@@ -109,10 +117,15 @@ require (
 	github.com/tidwall/match v1.1.1 // indirect
 	github.com/tidwall/pretty v1.2.0 // indirect
 	github.com/tjfoc/gmsm v1.3.2 // indirect
+	github.com/xdg-go/pbkdf2 v1.0.0 // indirect
+	github.com/xdg-go/scram v1.1.2 // indirect
+	github.com/xdg-go/stringprep v1.0.4 // indirect
 	github.com/xuri/efp v0.0.0-20231025114914-d1ff6096ae53 // indirect
 	github.com/xuri/nfp v0.0.0-20230919160717-d98342af3f05 // indirect
+	github.com/youmark/pkcs8 v0.0.0-20181117223130-1be2e3e5546d // indirect
 	golang.org/x/crypto v0.19.0 // indirect
 	golang.org/x/image v0.15.0 // indirect
+	golang.org/x/sync v0.2.0 // indirect
 	golang.org/x/sys v0.17.0 // indirect
 	golang.org/x/text v0.14.0 // indirect
 	golang.org/x/time v0.0.0-20220609170525-579cf78fd858 // indirect

+ 38 - 0
go.sum

@@ -166,6 +166,14 @@ github.com/go-ldap/ldap v3.0.3+incompatible h1:HTeSZO8hWMS1Rgb2Ziku6b8a7qRIZZMHj
 github.com/go-ldap/ldap v3.0.3+incompatible/go.mod h1:qfd9rJvER9Q0/D/Sqn1DfHRoBp40uXYvFoEVrNEPqRc=
 github.com/go-logfmt/logfmt v0.3.0/go.mod h1:Qt1PoO58o5twSAckw1HlFXLmHsOX5/0LbT9GBnD5lWE=
 github.com/go-logfmt/logfmt v0.4.0/go.mod h1:3RMwSq7FuexP4Kalkev3ejPJsZTpXXBr9+V4qmtdjCk=
+github.com/go-playground/assert/v2 v2.0.1 h1:MsBgLAaY856+nPRTKrp3/OZK38U/wa0CcBYNjji3q3A=
+github.com/go-playground/assert/v2 v2.0.1/go.mod h1:VDjEfimB/XKnb+ZQfWdccd7VUvScMdVu0Titje2rxJ4=
+github.com/go-playground/locales v0.13.0 h1:HyWk6mgj5qFqCT5fjGBuRArbVDfE4hi8+e8ceBS/t7Q=
+github.com/go-playground/locales v0.13.0/go.mod h1:taPMhCMXrRLJO55olJkUXHZBHCxTMfnGwq/HNwmWNS8=
+github.com/go-playground/universal-translator v0.17.0 h1:icxd5fm+REJzpZx7ZfpaD876Lmtgy7VtROAbHHXk8no=
+github.com/go-playground/universal-translator v0.17.0/go.mod h1:UkSxE5sNxxRwHyU+Scu5vgOQjsIJAF8j9muTVoKLVtA=
+github.com/go-playground/validator/v10 v10.4.1 h1:pH2c5ADXtd66mxoE0Zm9SUhxE20r7aM3F26W0hOn+GE=
+github.com/go-playground/validator/v10 v10.4.1/go.mod h1:nlOn6nFhuKACm19sB/8EGNn9GlaMV7XkbRSipzJ0Ii4=
 github.com/go-redis/redis v6.14.2+incompatible/go.mod h1:NAIEuMOZ/fxfXJIrKDQDz8wamY7mA7PouImQ2Jvg6kA=
 github.com/go-redis/redis/v8 v8.11.5/go.mod h1:gREzHqY1hg6oD9ngVRbLStwAWKhA0FEgq8Jd4h5lpwo=
 github.com/go-redis/redis/v8 v8.11.6-0.20220405070650-99c79f7041fc h1:jZY+lpZB92nvBo2f31oPC/ivGll6NcsnEOORm8Fkr4M=
@@ -206,6 +214,8 @@ github.com/golang/protobuf v1.5.3 h1:KhyjKVUg7Usr/dYsdSqoFveMYd5ko72D+zANwlG1mmg
 github.com/golang/protobuf v1.5.3/go.mod h1:XVQd3VNwM+JqD3oG2Ue2ip4fOMUkwXdXDdiuN0vRsmY=
 github.com/golang/snappy v0.0.0-20170215233205-553a64147049/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q=
 github.com/golang/snappy v0.0.0-20180518054509-2e65f85255db/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q=
+github.com/golang/snappy v0.0.1 h1:Qgr9rKW7uDUkrbSmQeiDsGa8SjGyCOGtuasMWwvp2P4=
+github.com/golang/snappy v0.0.1/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q=
 github.com/gomodule/redigo v2.0.0+incompatible/go.mod h1:B4C85qUVwatsJoIUNIfCRsp7qO0iAmpGFZ4EELWSbC4=
 github.com/gonum/blas v0.0.0-20181208220705-f22b278b28ac h1:Q0Jsdxl5jbxouNs1TQYt0gxesYMU4VXRbsTlgDloZ50=
 github.com/gonum/blas v0.0.0-20181208220705-f22b278b28ac/go.mod h1:P32wAyui1PQ58Oce/KYkOqQv8cVw1zAapXOl+dRFGbc=
@@ -226,6 +236,7 @@ github.com/google/go-cmp v0.2.0/go.mod h1:oXzfMopK8JAjlY9xF4vHSVASa0yLyX7SntLO5a
 github.com/google/go-cmp v0.3.0/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU=
 github.com/google/go-cmp v0.3.1/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU=
 github.com/google/go-cmp v0.4.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
+github.com/google/go-cmp v0.5.2/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
 github.com/google/go-cmp v0.5.4/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
 github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
 github.com/google/go-cmp v0.5.9 h1:O2Tfq5qg4qc4AmwVlvv0oLiVAGB7enBSJ2x2DqQFi38=
@@ -278,6 +289,7 @@ github.com/jung-kurt/gofpdf v1.16.2/go.mod h1:1hl7y57EsiPAkLbOwzpzqgx1A30nQCk/Ym
 github.com/kgiannakakis/mp3duration v0.0.0-20191013070830-d834f8d5ed53 h1:+8X3HMX8A2QhvNg3dImiQTCiVUt6BQXz1mW+/DrWI+k=
 github.com/kgiannakakis/mp3duration v0.0.0-20191013070830-d834f8d5ed53/go.mod h1:E61jD6q4yJ6Cu9uDGRAfiENM1G5TVZhOog0Y3+GgTpQ=
 github.com/kisielk/gotool v1.0.0/go.mod h1:XhKaO+MFFWcvkIS/tQcRk01m1F5IRFswLeQ+oQHNcck=
+github.com/klauspost/compress v1.13.6/go.mod h1:/3/Vjq9QcHkK5uEr5lBEmyoZ1iFhe47etQ6QUkpK6sk=
 github.com/klauspost/compress v1.17.6 h1:60eq2E/jlfwQXtvZEeBUYADs+BwKBWURIY+Gj2eRGjI=
 github.com/klauspost/compress v1.17.6/go.mod h1:/dCuZOvVtNoHsyb+cuJD3itjs3NbnF6KH9zAO4BDxPM=
 github.com/klauspost/cpuid/v2 v2.0.1/go.mod h1:FInQzS24/EEf25PyTYn52gqo7WaD8xa0213Md/qVLRg=
@@ -293,6 +305,8 @@ github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI=
 github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY=
 github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE=
 github.com/ledisdb/ledisdb v0.0.0-20200510135210-d35789ec47e6/go.mod h1:n931TsDuKuq+uX4v1fulaMbA/7ZLLhjc85h7chZGBCQ=
+github.com/leodido/go-urn v1.2.0 h1:hpXL4XnriNwQ/ABnpepYM/1vCLWNDfUNts8dX3xTG6Y=
+github.com/leodido/go-urn v1.2.0/go.mod h1:+8+nEpDfqqsY+g338gtMEUOtuK+4dEMhiQEgxpxOKII=
 github.com/lib/pq v1.0.0/go.mod h1:5WUZQaWbwv1U+lTReE5YruASi9Al49XbQIvNi/34Woo=
 github.com/lib/pq v1.10.4/go.mod h1:AlVN5x4E4T544tWzH6hKfbfQvm3HdbOxrmggDNAPY9o=
 github.com/lib/pq v1.10.5 h1:J+gdV2cUmX7ZqL2B0lFcW0m+egaHC2V3lpO8nWxyYiQ=
@@ -327,6 +341,8 @@ github.com/mohae/deepcopy v0.0.0-20170929034955-c48cc78d4826 h1:RWengNIwukTxcDr9
 github.com/mohae/deepcopy v0.0.0-20170929034955-c48cc78d4826/go.mod h1:TaXosZuwdSHYgviHp1DAtfrULt5eUgsSMsZf+YrPgl8=
 github.com/mojocn/base64Captcha v1.3.6 h1:gZEKu1nsKpttuIAQgWHO+4Mhhls8cAKyiV2Ew03H+Tw=
 github.com/mojocn/base64Captcha v1.3.6/go.mod h1:i5CtHvm+oMbj1UzEPXaA8IH/xHFZ3DGY3Wh3dBpZ28E=
+github.com/montanaflynn/stats v0.0.0-20171201202039-1bf9dbcd8cbe h1:iruDEfMl2E6fbMZ9s0scYfZQ84/6SPL6zC8ACM2oIL0=
+github.com/montanaflynn/stats v0.0.0-20171201202039-1bf9dbcd8cbe/go.mod h1:wL8QJuTMNUDYhXwkmfOly8iTdp5TEcJFWZD2D7SIkUc=
 github.com/mwitkow/go-conntrack v0.0.0-20161129095857-cc309e4a2223/go.mod h1:qRWi+5nqEBWmkhHvq77mSJWrCKwh8bxhgT7d/eI7P4U=
 github.com/nbio/st v0.0.0-20140626010706-e9e8d9816f32/go.mod h1:9wM+0iRr9ahx58uYLpLIr5fm8diHn0JbqRycJi6w0Ms=
 github.com/niemeyer/pretty v0.0.0-20200227124842-a10e7caefd8e/go.mod h1:zD1mROLANZcx1PVRCS0qkT7pwLkGfwJo4zjcN/Tysno=
@@ -389,6 +405,8 @@ github.com/prometheus/procfs v0.0.2/go.mod h1:TjEm7ze935MbeOT/UhFTIMYKhuLP4wbCsT
 github.com/prometheus/procfs v0.1.3/go.mod h1:lV6e/gmhEcM9IjHGsFOCxxuZ+z1YqCvr4OA4YeYWdaU=
 github.com/prometheus/procfs v0.10.1 h1:kYK1Va/YMlutzCGazswoHKo//tZVlFpKYh+PymziUAg=
 github.com/prometheus/procfs v0.10.1/go.mod h1:nwNm2aOCAYw8uTR/9bWRREkZFxAUcWzPHWJq+XBB/FM=
+github.com/qiniu/qmgo v1.1.8 h1:E64M+P59aqQpXKI24ClVtluYkLaJLkkeD2hTVhrdMks=
+github.com/qiniu/qmgo v1.1.8/go.mod h1:QvZkzWNEv0buWPx0kdZsSs6URhESVubacxFPlITmvB8=
 github.com/rcrowley/go-metrics v0.0.0-20181016184325-3113b8401b8a/go.mod h1:bCqnVzQkZxMG4s8nGwiZ5l3QUCyqpo9Y+/ZMZ9VjZe4=
 github.com/rdlucklib/rdluck_tools v1.0.3 h1:iOtK2QPlPQ6CL6c1htCk5VnFCHzyG6DCfJtunrMswK0=
 github.com/rdlucklib/rdluck_tools v1.0.3/go.mod h1:9Onw9o4w19C8KE5lxb8GyxgRBbZweRVkQSc79v38EaA=
@@ -429,11 +447,13 @@ github.com/spf13/cast v1.5.0/go.mod h1:SpXXQ5YoyJw6s3/6cMTQuxvgRl3PCJiyaX9p6b155
 github.com/ssdb/gossdb v0.0.0-20180723034631-88f6b59b84ec/go.mod h1:QBvMkMya+gXctz3kmljlUCu/yB3GZ6oee+dUozsezQE=
 github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
 github.com/stretchr/objx v0.1.1/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
+github.com/stretchr/objx v0.2.0 h1:Hbg2NidpLE8veEBkEZTL3CvlkUIVzuU9jDplZO54c48=
 github.com/stretchr/objx v0.2.0/go.mod h1:qt09Ya8vawLte6SNmTgCsAVtYtaKzEcn8ATUoHMkEqE=
 github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs=
 github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI=
 github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4=
 github.com/stretchr/testify v1.5.1/go.mod h1:5W2xD1RspED5o8YsWQXVCued0rvSQ+mT+I5cxcmMvtA=
+github.com/stretchr/testify v1.6.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg=
 github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg=
 github.com/stretchr/testify v1.7.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg=
 github.com/stretchr/testify v1.8.4 h1:CcVxjf3Q8PM0mHUKJCdn+eZZtm5yQwehR5yeSVQQcUk=
@@ -452,6 +472,7 @@ github.com/tidwall/gjson v1.14.1 h1:iymTbGkQBhveq21bEvAQ81I0LEBork8BFe1CUZXdyuo=
 github.com/tidwall/gjson v1.14.1/go.mod h1:/wbyibRr2FHMks5tjHJ5F8dMZh3AcwJEMf5vlfC0lxk=
 github.com/tidwall/match v1.1.1 h1:+Ho715JplO36QYgwN9PGYNhgZvoUSc9X2c80KVTi+GA=
 github.com/tidwall/match v1.1.1/go.mod h1:eRSPERbgtNPcGhD8UCthc6PmLEQXEWd3PRB5JTxsfmM=
+github.com/tidwall/pretty v1.0.0/go.mod h1:XNkn88O1ChpSDQmQeStsy+sBenx6DDtFZJxhVysOjyk=
 github.com/tidwall/pretty v1.2.0 h1:RWIZEg2iJ8/g6fDDYzMpobmaoGh5OLl4AXtGUGPcqCs=
 github.com/tidwall/pretty v1.2.0/go.mod h1:ITEVvHYasfjBbM0u2Pg8T2nJnzm8xPwvNhhsoaGGjNU=
 github.com/tjfoc/gmsm v1.3.2 h1:7JVkAn5bvUJ7HtU08iW6UiD+UTmJTIToHCfeFzkcCxM=
@@ -462,6 +483,14 @@ github.com/uber/jaeger-lib v2.4.1+incompatible h1:td4jdvLcExb4cBISKIpHuGoVXh+dVK
 github.com/uber/jaeger-lib v2.4.1+incompatible/go.mod h1:ComeNDZlWwrWnDv8aPp0Ba6+uUTzImX/AauajbLI56U=
 github.com/ugorji/go v0.0.0-20171122102828-84cb69a8af83/go.mod h1:hnLbHMwcvSihnDhEfx2/BzKp2xb0Y+ErdfYcrs9tkJQ=
 github.com/wendal/errors v0.0.0-20130201093226-f66c77a7882b/go.mod h1:Q12BUT7DqIlHRmgv3RskH+UCM/4eqVMgI0EMmlSpAXc=
+github.com/xdg-go/pbkdf2 v1.0.0 h1:Su7DPu48wXMwC3bs7MCNG+z4FhcyEuz5dlvchbq0B0c=
+github.com/xdg-go/pbkdf2 v1.0.0/go.mod h1:jrpuAogTd400dnrH08LKmI/xc1MbPOebTwRqcT5RDeI=
+github.com/xdg-go/scram v1.1.1/go.mod h1:RaEWvsqvNKKvBPvcKeFjrG2cJqOkHTiyTpzz23ni57g=
+github.com/xdg-go/scram v1.1.2 h1:FHX5I5B4i4hKRVRBCFRxq1iQRej7WO3hhBuJf+UUySY=
+github.com/xdg-go/scram v1.1.2/go.mod h1:RT/sEzTbU5y00aCK8UOx6R7YryM0iF1N2MOmC3kKLN4=
+github.com/xdg-go/stringprep v1.0.3/go.mod h1:W3f5j4i+9rC0kuIEJL0ky1VpHXQU3ocBgklLGvcBnW8=
+github.com/xdg-go/stringprep v1.0.4 h1:XLI/Ng3O1Atzq0oBs3TWm+5ZVgkq2aqdlvP9JtoZ6c8=
+github.com/xdg-go/stringprep v1.0.4/go.mod h1:mPGuuIYwz7CmR2bT9j4GbQqutWS1zV24gijq1dTyGkM=
 github.com/xuri/efp v0.0.0-20231025114914-d1ff6096ae53 h1:Chd9DkqERQQuHpXjR/HSV1jLZA6uaoiwwH3vSuF3IW0=
 github.com/xuri/efp v0.0.0-20231025114914-d1ff6096ae53/go.mod h1:ybY/Jr0T0GTCnYjKqmdwxyxn2BQf2RcQIIvex5QldPI=
 github.com/xuri/excelize/v2 v2.8.1 h1:pZLMEwK8ep+CLIUWpWmvW8IWE/yxqG0I1xcN6cVMGuQ=
@@ -471,6 +500,8 @@ github.com/xuri/nfp v0.0.0-20230919160717-d98342af3f05/go.mod h1:WwHg+CVyzlv/TX9
 github.com/yidane/formula v0.0.0-20220322063702-c9da84ba3476 h1:66fLxv8xlhSr42ZhVAYjUY/sEF0olUUAESVlsxVduuw=
 github.com/yidane/formula v0.0.0-20220322063702-c9da84ba3476/go.mod h1:9/dQiKiN04yPMdgsuFmKGuI2Hdp6OmFV9gSWS1col6g=
 github.com/ylywyn/jpush-api-go-client v0.0.0-20190906031852-8c4466c6e369/go.mod h1:Nv7wKD2/bCdKUFNKcJRa99a+1+aSLlCRJFriFYdjz/I=
+github.com/youmark/pkcs8 v0.0.0-20181117223130-1be2e3e5546d h1:splanxYIlg+5LfHAM6xpdFEAYOk8iySO56hMFq6uLyA=
+github.com/youmark/pkcs8 v0.0.0-20181117223130-1be2e3e5546d/go.mod h1:rHwXgn7JulP+udvsHwJoVG1YGAP6VLg4y9I5dyZdqmA=
 github.com/yuin/goldmark v1.1.27/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74=
 github.com/yuin/goldmark v1.1.30/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74=
 github.com/yuin/goldmark v1.2.1/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74=
@@ -480,6 +511,9 @@ github.com/yuin/gopher-lua v0.0.0-20220504180219-658193537a64 h1:5mLPGnFdSsevFRF
 github.com/yuin/gopher-lua v0.0.0-20220504180219-658193537a64/go.mod h1:GBR0iDaNXjAgGg9zfCvksxSRnQx76gclCIb7kdAd1Pw=
 github.com/ziutek/mymysql v1.5.4 h1:GB0qdRGsTwQSBVYuVShFBKaXSnSnYYC2d9knnE1LHFs=
 github.com/ziutek/mymysql v1.5.4/go.mod h1:LMSpPZ6DbqWFxNCHW77HeMg9I646SAhApZ/wKdgO/C0=
+go.mongodb.org/mongo-driver v1.11.6/go.mod h1:G9TgswdsWjX4tmDA5zfs2+6AEPpYJwqblyjsfuh8oXY=
+go.mongodb.org/mongo-driver v1.15.0 h1:rJCKC8eEliewXjZGf0ddURtl7tTVy1TK3bfl0gkUSLc=
+go.mongodb.org/mongo-driver v1.15.0/go.mod h1:Vzb0Mk/pa7e6cWw85R4F/endUC3u0U9jGcNU603k65c=
 go.opencensus.io v0.20.1/go.mod h1:6WKK9ahsWS3RSO+PY9ZHZUfv2irvY6gN279GOPZjmmk=
 go.uber.org/atomic v1.9.0 h1:ECmE8Bn/WFTYwEW/bpKD3M8VtR/zQVbavAoalC1PYyE=
 go.uber.org/atomic v1.9.0/go.mod h1:fEN4uk6kAWBTFdckzkM89CLk9XfWZrxpCo0nPH17wJc=
@@ -558,8 +592,11 @@ golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJ
 golang.org/x/sync v0.0.0-20190911185100-cd5d95a43a6e/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
 golang.org/x/sync v0.0.0-20200317015054-43a5402ce75a/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
 golang.org/x/sync v0.0.0-20201020160332-67f06af15bc9/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
+golang.org/x/sync v0.0.0-20210220032951-036812b2e83c/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
 golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
 golang.org/x/sync v0.1.0/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
+golang.org/x/sync v0.2.0 h1:PUR+T4wwASmuSTYdKjYHI5TD22Wy5ogLU5qZCOLxBrI=
+golang.org/x/sync v0.2.0/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
 golang.org/x/sys v0.0.0-20180830151530-49385e6e1522/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
 golang.org/x/sys v0.0.0-20180905080454-ebe1bf3edb33/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
 golang.org/x/sys v0.0.0-20180909124046-d0be0721c37e/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
@@ -610,6 +647,7 @@ golang.org/x/text v0.3.2/go.mod h1:bEr9sfX3Q8Zfm5fL9x+3itogRgK3+ptLWKqgva+5dAk=
 golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
 golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
 golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ=
+golang.org/x/text v0.3.8/go.mod h1:E6s5w1FMmriuDzIBO73fBruAKo1PCIq6d2Q6DHfQ8WQ=
 golang.org/x/text v0.7.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8=
 golang.org/x/text v0.9.0/go.mod h1:e1OnstbJyHTd6l/uOt8jFFHp6TRDWZR/bV3emEE/zU8=
 golang.org/x/text v0.10.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE=

+ 46 - 2
models/data_manage/base_from_business_index.go

@@ -96,6 +96,15 @@ func (m *EdbBusinessSource) GetAllList() (items []*EdbBusinessSource, err error)
 	return
 }
 
+// GetListCount
+// @Description: 根据条件获取列表页的总数量
+// @author: Roc
+// @receiver m
+// @datetime 2024-05-06 17:15:28
+// @param condition string
+// @param pars []interface{}
+// @return count int
+// @return err error
 func (m *BaseFromBusinessIndex) GetListCount(condition string, pars []interface{}) (count int, err error) {
 	sql := ` select count(1) as count FROM base_from_business_index as a WHERE 1=1 `
 	if condition != "" {
@@ -106,6 +115,18 @@ func (m *BaseFromBusinessIndex) GetListCount(condition string, pars []interface{
 
 	return
 }
+
+// GetList
+// @Description: 根据条件获取列表页的数据
+// @author: Roc
+// @receiver m
+// @datetime 2024-05-06 17:15:42
+// @param condition string
+// @param pars []interface{}
+// @param startSize int
+// @param pageSize int
+// @return items []*BaseFromBusinessIndex
+// @return err error
 func (m *BaseFromBusinessIndex) GetList(condition string, pars []interface{}, startSize, pageSize int) (items []*BaseFromBusinessIndex, err error) {
 	sql := `select * FROM base_from_business_index AS a  WHERE 1=1 `
 	if condition != "" {
@@ -148,18 +169,33 @@ type BaseFromBusinessIndexItem struct {
 	EdbExist                int    `description:"指标库是否已添加:0-否;1-是"`
 }
 
-func (m *BaseFromBusinessIndex) GetPageItemsByCondition(condition string, pars []interface{}, startSize, pageSize int) (items []*BaseFromBusinessIndexItem, err error) {
+func (m *BaseFromBusinessIndex) GetPageItemsByCondition(condition string, pars []interface{}, orderRule string, startSize, pageSize int) (items []*BaseFromBusinessIndexItem, err error) {
 	sql := `select a.*,b.edb_info_id,b.unique_code as edb_unique_code,b.classify_id as edb_classify_id FROM base_from_business_index AS a LEFT JOIN edb_info b on a.index_code=b.edb_code AND b.source=? WHERE 1=1 `
 	if condition != "" {
 		sql += condition
 	}
-	sql += ` order by a.base_from_business_index_id desc limit ?,? `
+	if orderRule == `` {
+		sql += ` order by a.base_from_business_index_id desc`
+	} else {
+		sql += ` order by ` + orderRule
+	}
+	sql += ` limit ?,? `
 	o := orm.NewOrmUsingDB("data")
 	_, err = o.Raw(sql, utils.DATA_SOURCE_BUSINESS, pars, startSize, pageSize).QueryRows(&items)
 
 	return
 }
 
+// GeItemsByCondition
+// @Description: 根据条件获取指定数量的指标
+// @author: Roc
+// @receiver m
+// @datetime 2024-05-06 17:16:02
+// @param condition string
+// @param pars []interface{}
+// @param limitSize int
+// @return items []*BaseFromBusinessIndexItem
+// @return err error
 func (m *BaseFromBusinessIndex) GeItemsByCondition(condition string, pars []interface{}, limitSize int) (items []*BaseFromBusinessIndexItem, err error) {
 	sql := `select a.*,b.edb_info_id,b.unique_code as edb_unique_code,b.classify_id as edb_classify_id FROM base_from_business_index AS a LEFT JOIN edb_info b on a.index_code=b.edb_code AND b.source=? WHERE 1=1 `
 	if condition != "" {
@@ -175,3 +211,11 @@ func (m *BaseFromBusinessIndex) GeItemsByCondition(condition string, pars []inte
 
 	return
 }
+
+func (m *BaseFromBusinessIndex) GetDetailByEdbCode(edbCode string) (item *BaseFromBusinessIndex, err error) {
+	sql := `select *  FROM base_from_business_index  WHERE index_code = ? `
+	o := orm.NewOrmUsingDB("data")
+	err = o.Raw(sql, edbCode).QueryRow(&item)
+
+	return
+}

+ 2 - 0
models/data_manage/request/business_data.go

@@ -8,6 +8,8 @@ type BusinessDataListReq struct {
 	Source       int    `form:"Source" description:"来源id"`
 	Keywords     string `form:"Keywords" description:"指标ID/指标名称"`
 	ListAll      bool   `form:"ListAll" description:"列表全选"`
+	SortField    int    `form:"SortField" description:"排序字段: 0-默认; 1-开始时间; 2-最新时间; 3-更新时间"`
+	SortRule     int    `form:"SortRule" description:"排序方式: 0-默认; 1-正序; 2-倒序"`
 }
 
 // BusinessDataBatchAddCheckReq 外部(商家)指标批量添加校验

+ 288 - 0
models/mgo/base_from_business_data.go

@@ -0,0 +1,288 @@
+package mgo
+
+import (
+	"context"
+	"errors"
+	"eta/eta_api/utils"
+	"fmt"
+	"github.com/qiniu/qmgo"
+	"go.mongodb.org/mongo-driver/bson"
+	"go.mongodb.org/mongo-driver/bson/primitive"
+	"time"
+)
+
+// BaseFromBusinessData
+// @Description: 外部数据集合
+type BaseFromBusinessData struct {
+	ID primitive.ObjectID `json:"_id" bson:"_id,omitempty"` // 文档id
+	//ID string `json:"_id" bson:"_id" ` // 文档id
+	BaseFromBusinessIndexId int64     `json:"base_from_business_index_id" bson:"base_from_business_index_id"` // 指标id
+	IndexCode               string    `json:"index_code" bson:"index_code"`                                   // 指标编码
+	DataTime                time.Time `json:"data_time" bson:"data_time"`                                     // 数据日期
+	Value                   float64   `json:"value" bson:"value"`                                             // 数据值
+	CreateTime              time.Time `json:"create_time" bson:"create_time"`                                 // 创建时间
+	ModifyTime              time.Time `json:"modify_time" bson:"modify_time"`                                 // 修改时间
+}
+
+// CollectionName
+// @Description:  获取集合名称
+// @author: Roc
+// @receiver m
+// @datetime 2024-04-26 13:41:36
+// @return string
+func (m *BaseFromBusinessData) CollectionName() string {
+	return "base_from_business_data"
+}
+
+// DataBaseName
+// @Description: 获取数据库名称
+// @author: Roc
+// @receiver m
+// @datetime 2024-04-26 13:41:33
+// @return string
+func (m *BaseFromBusinessData) DataBaseName() string {
+	return utils.MgoDataDbName
+}
+
+// GetCollection
+// @Description: 获取mongodb集合的句柄
+// @author: Roc
+// @receiver m
+// @datetime 2024-04-26 13:41:33
+// @return string
+func (m *BaseFromBusinessData) GetCollection() *qmgo.Collection {
+	db := utils.MgoDataCli.Database(m.DataBaseName())
+	return db.Collection(m.CollectionName())
+}
+
+// GetAllDataList
+// @Description: 根据条件获取所有数据
+// @author: Roc
+// @receiver m
+// @datetime 2024-04-26 13:42:19
+// @param whereParams interface{}
+// @return result []BaseFromBusinessData
+// @return err error
+func (m *BaseFromBusinessData) GetAllDataList(whereParams interface{}) (result []*BaseFromBusinessData, err error) {
+	if utils.MgoDataCli == nil {
+		err = errors.New("mongodb连接失败")
+		return
+	}
+	db := utils.MgoDataCli.Database(m.DataBaseName())
+	coll := db.Collection(m.CollectionName())
+	ctx := context.TODO()
+	if err != nil {
+		fmt.Println("MgoGetColl Err:", err.Error())
+		return
+	}
+	err = coll.Find(ctx, whereParams).All(&result)
+	if err != nil {
+		return
+	}
+
+	for _, v := range result {
+		v.DataTime = v.DataTime.In(time.Local)
+		v.CreateTime = v.CreateTime.In(time.Local)
+		v.ModifyTime = v.ModifyTime.In(time.Local)
+	}
+
+	return
+}
+
+// GetLimitDataList
+// @Description: 根据条件获取指定数量数据列表
+// @author: Roc
+// @receiver m
+// @datetime 2024-05-06 17:08:32
+// @param whereParams interface{}
+// @param size int64
+// @return result []*BaseFromBusinessData
+// @return err error
+func (m *BaseFromBusinessData) GetLimitDataList(whereParams interface{}, size int64, sort []string) (result []*BaseFromBusinessData, err error) {
+	if utils.MgoDataCli == nil {
+		err = errors.New("mongodb连接失败")
+		return
+	}
+	db := utils.MgoDataCli.Database(m.DataBaseName())
+	coll := db.Collection(m.CollectionName())
+	ctx := context.TODO()
+	if err != nil {
+		fmt.Println("MgoGetColl Err:", err.Error())
+		return
+	}
+	err = coll.Find(ctx, whereParams).Sort(sort...).Limit(size).All(&result)
+	if err != nil {
+		return
+	}
+
+	for _, v := range result {
+		v.DataTime = v.DataTime.In(time.Local)
+		v.CreateTime = v.CreateTime.In(time.Local)
+		v.ModifyTime = v.ModifyTime.In(time.Local)
+	}
+
+	return
+}
+
+// BatchInsertData
+// @Description: 批量写入数据
+// @author: Roc
+// @receiver m
+// @datetime 2024-04-26 14:22:18
+// @param dataList interface{}
+// @return err error
+func (m *BaseFromBusinessData) BatchInsertData(dataList interface{}) (err error) {
+	db := utils.MgoDataCli.Database(m.DataBaseName())
+	coll := db.Collection(m.CollectionName())
+	ctx := context.TODO()
+	_, err = coll.InsertMany(ctx, dataList)
+	if err != nil {
+		fmt.Println("BatchInsertData:Err:" + err.Error())
+		return
+	}
+	return
+}
+
+// UpdateDataByColl
+// @Description: 单条数据修改
+// @author: Roc
+// @receiver m
+// @datetime 2024-04-26 15:01:51
+// @param whereParams interface{}
+// @param updateParams interface{}
+// @return err error
+func (m *BaseFromBusinessData) UpdateDataByColl(coll *qmgo.Collection, whereParams, updateParams interface{}) (err error) {
+	ctx := context.TODO()
+	err = coll.UpdateOne(ctx, whereParams, updateParams)
+	if err != nil {
+		fmt.Println("UpdateDataByColl:Err:" + err.Error())
+		return
+	}
+	return
+}
+
+// UpdateData
+// @Description: 单条数据修改
+// @author: Roc
+// @receiver m
+// @datetime 2024-04-26 15:01:51
+// @param whereParams interface{}
+// @param updateParams interface{}
+// @return err error
+func (m *BaseFromBusinessData) UpdateData(whereParams, updateParams interface{}) (err error) {
+	db := utils.MgoDataCli.Database(m.DataBaseName())
+	coll := db.Collection(m.CollectionName())
+	ctx := context.TODO()
+	err = coll.UpdateOne(ctx, whereParams, updateParams)
+	if err != nil {
+		fmt.Println("UpdateData:Err:" + err.Error())
+		return
+	}
+	return
+}
+
+// HandleData
+// @Description: 事务处理数据
+// @author: Roc
+// @receiver m
+// @datetime 2024-04-30 10:40:20
+// @param addDataList []BaseAddFromBusinessData
+// @param updateDataList []BaseFromBusinessData
+// @return result interface{}
+// @return err error
+func (m *BaseFromBusinessData) HandleData(addDataList, updateDataList []BaseFromBusinessData) (result interface{}, err error) {
+
+	ctx := context.TODO()
+
+	callback := func(sessCtx context.Context) (interface{}, error) {
+		// 重要:确保事务中的每一个操作,都使用传入的sessCtx参数
+
+		db := utils.MgoDataCli.Database(m.DataBaseName())
+		coll := db.Collection(m.CollectionName())
+
+		// 插入数据
+		if len(addDataList) > 0 {
+			_, err = coll.InsertMany(sessCtx, addDataList)
+			if err != nil {
+				return nil, err
+			}
+		}
+
+		// 修改
+
+		if len(updateDataList) > 0 {
+			for _, v := range updateDataList {
+				err = coll.UpdateOne(ctx, bson.M{"_id": v.ID}, bson.M{"$set": bson.M{"value": v.Value, "modify_time": v.ModifyTime}})
+				if err != nil {
+					fmt.Println("BatchInsertData:Err:" + err.Error())
+					return nil, err
+				}
+			}
+		}
+
+		return nil, nil
+	}
+	result, err = utils.MgoDataCli.DoTransaction(ctx, callback)
+
+	return
+}
+
+// GetEdbInfoMaxAndMinInfo
+// @Description: 获取当前指标的最大最小值
+// @author: Roc
+// @receiver m
+// @datetime 2024-04-30 17:15:39
+// @param whereParams interface{}
+// @return result EdbInfoMaxAndMinInfo
+// @return err error
+func (m *BaseFromBusinessData) GetEdbInfoMaxAndMinInfo(whereParams interface{}) (result EdbInfoMaxAndMinInfo, err error) {
+	if utils.MgoDataCli == nil {
+		err = errors.New("mongodb连接失败")
+		return
+	}
+	db := utils.MgoDataCli.Database(m.DataBaseName())
+	coll := db.Collection(m.CollectionName())
+	ctx := context.TODO()
+	if err != nil {
+		fmt.Println("MgoGetColl Err:", err.Error())
+		return
+	}
+	err = coll.Aggregate(ctx, whereParams).One(&result)
+	if err != nil {
+		return
+	}
+	result.MinDate = result.MinDate.In(time.Local)
+	result.MaxDate = result.MaxDate.In(time.Local)
+	result.LatestDate = result.LatestDate.In(time.Local)
+
+	return
+}
+
+// GetLatestValue
+// @Description: 获取当前指标的最新数据记录
+// @author: Roc
+// @receiver m
+// @datetime 2024-04-30 17:16:15
+// @param whereParams interface{}
+// @param selectParam interface{}
+// @return latestValue LatestValue
+// @return err error
+func (m *BaseFromBusinessData) GetLatestValue(whereParams, selectParam interface{}) (latestValue LatestValue, err error) {
+	if utils.MgoDataCli == nil {
+		err = errors.New("mongodb连接失败")
+		return
+	}
+	db := utils.MgoDataCli.Database(m.DataBaseName())
+	coll := db.Collection(m.CollectionName())
+	ctx := context.TODO()
+	if err != nil {
+		fmt.Println("MgoGetColl Err:", err.Error())
+		return
+	}
+
+	//var result interface{}
+	//err = coll.Find(ctx, whereParams).Select(selectParam).One(&result)
+	err = coll.Find(ctx, whereParams).Select(selectParam).One(&latestValue)
+
+	return
+}

+ 311 - 0
models/mgo/edb_data_business.go

@@ -0,0 +1,311 @@
+package mgo
+
+import (
+	"context"
+	"errors"
+	"eta/eta_api/utils"
+	"fmt"
+	"github.com/qiniu/qmgo"
+	"go.mongodb.org/mongo-driver/bson"
+	"go.mongodb.org/mongo-driver/bson/primitive"
+	"time"
+)
+
+// EdbDataBusiness
+// @Description: 外部数据集合(指标库)
+type EdbDataBusiness struct {
+	ID            primitive.ObjectID `json:"_id" bson:"_id,omitempty" `            // 文档id
+	EdbInfoId     int                `json:"edb_info_id" bson:"edb_info_id"`       // 指标编码
+	EdbCode       string             `json:"edb_code" bson:"edb_code"`             // 指标编码
+	DataTime      time.Time          `json:"data_time" bson:"data_time"`           // 数据日期
+	Value         float64            `json:"value" bson:"value"`                   // 数据值
+	CreateTime    time.Time          `json:"create_time" bson:"create_time"`       // 创建时间
+	ModifyTime    time.Time          `json:"modify_time" bson:"modify_time"`       // 修改时间
+	DataTimestamp int64              `json:"data_timestamp" bson:"data_timestamp"` // 数据日期时间戳
+}
+
+// CollectionName
+// @Description:  获取集合名称
+// @author: Roc
+// @receiver m
+// @datetime 2024-04-26 13:41:36
+// @return string
+func (m *EdbDataBusiness) CollectionName() string {
+	return "edb_data_business"
+}
+
+// DataBaseName
+// @Description: 获取数据库名称
+// @author: Roc
+// @receiver m
+// @datetime 2024-04-26 13:41:33
+// @return string
+func (m *EdbDataBusiness) DataBaseName() string {
+	return utils.MgoDataDbName
+}
+
+// GetCollection
+// @Description: 获取mongodb集合的句柄
+// @author: Roc
+// @receiver m
+// @datetime 2024-04-26 13:41:33
+// @return string
+func (m *EdbDataBusiness) GetCollection() *qmgo.Collection {
+	db := utils.MgoDataCli.Database(m.DataBaseName())
+	return db.Collection(m.CollectionName())
+}
+
+// GetAllDataList
+// @Description: 根据条件获取所有数据
+// @author: Roc
+// @receiver m
+// @datetime 2024-04-26 13:42:19
+// @param whereParams interface{}
+// @return result []EdbDataBusiness
+// @return err error
+func (m *EdbDataBusiness) GetAllDataList(whereParams interface{}) (result []*EdbDataBusiness, err error) {
+	if utils.MgoDataCli == nil {
+		err = errors.New("mongodb连接失败")
+		return
+	}
+	db := utils.MgoDataCli.Database(m.DataBaseName())
+	coll := db.Collection(m.CollectionName())
+	ctx := context.TODO()
+	if err != nil {
+		fmt.Println("MgoGetColl Err:", err.Error())
+		return
+	}
+	err = coll.Find(ctx, whereParams).All(&result)
+	if err != nil {
+		return
+	}
+
+	for _, v := range result {
+		v.DataTime = v.DataTime.In(time.Local)
+		v.CreateTime = v.CreateTime.In(time.Local)
+		v.ModifyTime = v.ModifyTime.In(time.Local)
+	}
+
+	return
+}
+
+// BatchInsertData
+// @Description: 批量写入数据
+// @author: Roc
+// @receiver m
+// @datetime 2024-04-26 14:22:18
+// @param dataList interface{}
+// @return err error
+func (m *EdbDataBusiness) BatchInsertData(dataList []EdbDataBusiness) (err error) {
+	db := utils.MgoDataCli.Database(m.DataBaseName())
+	coll := db.Collection(m.CollectionName())
+
+	return m.BatchInsertDataByColl(coll, dataList)
+}
+
+// BatchInsertDataByColl
+// @Description: 批量写入数据(外部传入集合)
+// @author: Roc
+// @receiver m
+// @datetime 2024-04-26 14:22:18
+// @param dataList interface{}
+// @return err error
+func (m *EdbDataBusiness) BatchInsertDataByColl(coll *qmgo.Collection, dataList []EdbDataBusiness) (err error) {
+	ctx := context.TODO()
+	_, err = coll.InsertMany(ctx, dataList)
+	if err != nil {
+		fmt.Println("BatchInsertData:Err:" + err.Error())
+		return
+	}
+
+	return
+}
+
+// UpdateData
+// @Description: 单条数据修改
+// @author: Roc
+// @receiver m
+// @datetime 2024-04-26 15:01:51
+// @param whereParams interface{}
+// @param updateParams interface{}
+// @return err error
+func (m *EdbDataBusiness) UpdateData(whereParams, updateParams interface{}) (err error) {
+	db := utils.MgoDataCli.Database(m.DataBaseName())
+	coll := db.Collection(m.CollectionName())
+
+	return m.UpdateDataByColl(coll, whereParams, updateParams)
+}
+
+// UpdateDataByColl
+// @Description: 单条数据修改(外部传入集合)
+// @author: Roc
+// @receiver m
+// @datetime 2024-04-26 15:01:51
+// @param whereParams interface{}
+// @param updateParams interface{}
+// @return err error
+func (m *EdbDataBusiness) UpdateDataByColl(coll *qmgo.Collection, whereParams, updateParams interface{}) (err error) {
+	ctx := context.TODO()
+	err = coll.UpdateOne(ctx, whereParams, updateParams)
+	if err != nil {
+		fmt.Println("UpdateDataByColl:Err:" + err.Error())
+		return
+	}
+
+	return
+}
+
+// RemoveMany
+// @Description: 根据条件删除多条数据
+// @author: Roc
+// @receiver m
+// @datetime 2024-04-30 13:17:02
+// @param whereParams interface{}
+// @return err error
+func (m *EdbDataBusiness) RemoveMany(whereParams interface{}) (err error) {
+	db := utils.MgoDataCli.Database(m.DataBaseName())
+	coll := db.Collection(m.CollectionName())
+
+	return m.RemoveManyByColl(coll, whereParams)
+}
+
+// RemoveManyByColl
+// @Description: 根据条件删除多条数据(外部传入集合)
+// @author: Roc
+// @receiver m
+// @datetime 2024-04-30 13:18:42
+// @param coll *qmgo.Collection
+// @param whereParams interface{}
+// @return err error
+func (m *EdbDataBusiness) RemoveManyByColl(coll *qmgo.Collection, whereParams interface{}) (err error) {
+	ctx := context.TODO()
+	_, err = coll.RemoveAll(ctx, whereParams)
+	if err != nil {
+		fmt.Println("RemoveManyByColl:Err:" + err.Error())
+		return
+	}
+
+	return
+}
+
+// HandleData
+// @Description: 事务处理数据
+// @author: Roc
+// @receiver m
+// @datetime 2024-04-30 10:39:01
+// @param addDataList []AddEdbDataBusiness
+// @param updateDataList []EdbDataBusiness
+// @return result interface{}
+// @return err error
+func (m *EdbDataBusiness) HandleData(addDataList, updateDataList []EdbDataBusiness) (result interface{}, err error) {
+
+	ctx := context.TODO()
+
+	callback := func(sessCtx context.Context) (interface{}, error) {
+		// 重要:确保事务中的每一个操作,都使用传入的sessCtx参数
+
+		db := utils.MgoDataCli.Database(m.DataBaseName())
+		coll := db.Collection(m.CollectionName())
+
+		// 插入数据
+		if len(addDataList) > 0 {
+			_, err = coll.InsertMany(sessCtx, addDataList)
+			if err != nil {
+				return nil, err
+			}
+		}
+
+		// 修改
+
+		if len(updateDataList) > 0 {
+			for _, v := range updateDataList {
+				err = coll.UpdateOne(ctx, bson.M{"_id": v.ID}, bson.M{"$set": bson.M{"value": v.Value, "modify_time": v.ModifyTime}})
+				if err != nil {
+					fmt.Println("BatchInsertData:Err:" + err.Error())
+					return nil, err
+				}
+			}
+		}
+
+		return nil, nil
+	}
+	result, err = utils.MgoDataCli.DoTransaction(ctx, callback)
+
+	return
+}
+
+// EdbInfoMaxAndMinInfo 指标最新数据记录结构体
+type EdbInfoMaxAndMinInfo struct {
+	MinDate     time.Time `description:"最小日期" bson:"min_date"`
+	MaxDate     time.Time `description:"最大日期" bson:"max_date"`
+	MinValue    float64   `description:"最小值" bson:"min_value"`
+	MaxValue    float64   `description:"最大值" bson:"max_value"`
+	LatestValue float64   `description:"最新值" bson:"latest_value"`
+	LatestDate  time.Time `description:"实际数据最新日期" bson:"latest_date"`
+	EndValue    float64   `description:"最新值" bson:"end_value"`
+}
+
+// GetEdbInfoMaxAndMinInfo
+// @Description: 获取当前指标的最大最小值
+// @author: Roc
+// @receiver m
+// @datetime 2024-04-30 17:15:39
+// @param whereParams interface{}
+// @return result EdbInfoMaxAndMinInfo
+// @return err error
+func (m *EdbDataBusiness) GetEdbInfoMaxAndMinInfo(whereParams interface{}) (result EdbInfoMaxAndMinInfo, err error) {
+	if utils.MgoDataCli == nil {
+		err = errors.New("mongodb连接失败")
+		return
+	}
+	db := utils.MgoDataCli.Database(m.DataBaseName())
+	coll := db.Collection(m.CollectionName())
+	ctx := context.TODO()
+	if err != nil {
+		fmt.Println("MgoGetColl Err:", err.Error())
+		return
+	}
+	err = coll.Aggregate(ctx, whereParams).One(&result)
+	if err != nil {
+		return
+	}
+	result.MinDate = result.MinDate.In(time.Local)
+	result.MaxDate = result.MaxDate.In(time.Local)
+	result.LatestDate = result.LatestDate.In(time.Local)
+
+	return
+}
+
+// LatestValue 指标最新数据记录结构体
+type LatestValue struct {
+	Value float64 `description:"值" bson:"value"`
+}
+
+// GetLatestValue
+// @Description: 获取当前指标的最新数据记录
+// @author: Roc
+// @receiver m
+// @datetime 2024-04-30 17:16:15
+// @param whereParams interface{}
+// @param selectParam interface{}
+// @return latestValue LatestValue
+// @return err error
+func (m *EdbDataBusiness) GetLatestValue(whereParams, selectParam interface{}) (latestValue LatestValue, err error) {
+	if utils.MgoDataCli == nil {
+		err = errors.New("mongodb连接失败")
+		return
+	}
+	db := utils.MgoDataCli.Database(m.DataBaseName())
+	coll := db.Collection(m.CollectionName())
+	ctx := context.TODO()
+	if err != nil {
+		fmt.Println("MgoGetColl Err:", err.Error())
+		return
+	}
+
+	//var result interface{}
+	//err = coll.Find(ctx, whereParams).Select(selectParam).One(&result)
+	err = coll.Find(ctx, whereParams).Select(selectParam).One(&latestValue)
+
+	return
+}

+ 274 - 0
models/mgo_base.go

@@ -0,0 +1,274 @@
+package models
+
+import (
+	"context"
+	"encoding/json"
+	"errors"
+	"eta/eta_api/utils"
+	"eta/eta_api/utils/mgodb"
+	"fmt"
+)
+
+func init() {
+	if utils.MgoUrlData != `` {
+		var mgoConfig mgodb.MgoConfig
+		if e := json.Unmarshal([]byte(utils.MgoUrlData), &mgoConfig); e != nil {
+			panic("mongodb链接失败,Err:" + e.Error())
+			return
+		}
+
+		mgoCli := mgodb.MgoNewClient(mgoConfig)
+		utils.MgoDataCli = mgoCli
+		utils.MgoDataDbName = mgoConfig.Database
+		//result, err := TestMgoFindOne("data_ths", bson.M{"edbcode": "s0033227", "datatime": "2015-12-04"})
+		//fmt.Println(time.Now())
+		//result, err := TestMgoFindOne("data_wind", bson.M{"edbcode": "s0033227", "datatime": "2007-12-29"})
+		//fmt.Println(time.Now())
+		//
+		//fmt.Println(err)
+		//fmt.Println(result)
+	}
+
+}
+
+// TestMgoFindOne
+// @Description: 获取单条数据
+// @author: Roc
+// @datetime 2024-04-25 15:44:07
+// @param colName string 集合名词:`data_ths`
+// @param whereParams interface{} bson.M{"edbcode": "s0033227", "datatime": "2015-12-04"}
+// @return result interface{}
+// @return err error
+func TestMgoFindOne(colName string, whereParams interface{}) (result interface{}, err error) {
+	if colName == "" {
+		err = errors.New("集合名称不可为空")
+		return
+	}
+	if utils.MgoDataCli == nil {
+		err = errors.New("mongodb连接失败")
+		return
+	}
+	db := utils.MgoDataCli.Database("hz_data")
+	coll := db.Collection("data_ths")
+	ctx := context.TODO()
+	if err != nil {
+		fmt.Println("MgoGetColl Err:", err.Error())
+		return
+	}
+	//err = coll.Find(ctx, whereParams).One(&result)
+	err = coll.Find(ctx, whereParams).All(&result)
+	return
+}
+
+// 创建集合
+//func MgoCreateCollection(collectionName string) (err error) {
+//	ctx := context.TODO()
+//
+//	mgoClient := mgodb.MgoNewClient()
+//
+//	defer func() {
+//		mgoClient.Close(ctx)
+//	}()
+//
+//	colName := collectionName
+//	err = mgoClient.Database("hz_data").CreateCollection(ctx, colName)
+//	return
+//}
+
+// 批量新增多条数据
+func MgoBatchInsertData(colName string, dataList interface{}) (err error) {
+	if colName == "" {
+		err = errors.New("集合名称不可为空")
+		return
+	}
+	ctx := context.TODO()
+	coll, err := mgodb.MgoGetColl(colName)
+	if err != nil {
+		fmt.Println("MgoGetColl Err:", err.Error())
+		return
+	}
+	defer func() {
+		coll.Close(ctx)
+	}()
+	_, err = coll.Collection.InsertMany(ctx, dataList)
+	if err != nil {
+		fmt.Println("InsertMany:Err:" + err.Error())
+		return
+	}
+	return
+}
+
+// 插入单条数据
+func MgoInsertData(colName string, dataItem interface{}) (insertedID interface{}, err error) {
+	if colName == "" {
+		err = errors.New("集合名称不可为空")
+		return
+	}
+	ctx := context.TODO()
+	coll, err := mgodb.MgoGetColl(colName)
+	if err != nil {
+		fmt.Println("MgoGetColl Err:", err.Error())
+		return
+	}
+	defer func() {
+		coll.Close(ctx)
+	}()
+	result, err := coll.Collection.InsertOne(ctx, dataItem)
+	if err != nil {
+		return
+	}
+	insertedID = result.InsertedID
+	return
+}
+
+/*
+删除数据
+colName := `data_gl`
+whereParams := bson.M{"edbcode": "s0033227"}
+err := MgoRemove(colName, whereParams)
+*/
+func MgoRemove(colName string, whereParams interface{}) (err error) {
+	if colName == "" {
+		err = errors.New("集合名称不可为空")
+		return
+	}
+	ctx := context.TODO()
+	coll, err := mgodb.MgoGetColl(colName)
+	if err != nil {
+		fmt.Println("MgoGetColl Err:", err.Error())
+		return
+	}
+	defer func() {
+		coll.Close(ctx)
+	}()
+	err = coll.Remove(ctx, whereParams)
+	return
+}
+
+/*
+删除多条数据
+colName := `data_gl`
+whereParams := bson.M{"edbcode": "s0033227"}
+err := MgoRemoveAll(colName, whereParams)
+*/
+func MgoRemoveAll(colName string, whereParams interface{}) (count int64, err error) {
+	if colName == "" {
+		err = errors.New("集合名称不可为空")
+		return
+	}
+	ctx := context.TODO()
+	coll, err := mgodb.MgoGetColl(colName)
+	if err != nil {
+		fmt.Println("MgoGetColl Err:", err.Error())
+		return
+	}
+	defer func() {
+		coll.Close(ctx)
+	}()
+	res, err := coll.RemoveAll(ctx, whereParams)
+	if err != nil {
+		fmt.Println("RemoveAll Err:", err.Error())
+		return
+	}
+	count = res.DeletedCount
+	return
+}
+
+/*
+修改单条数据
+colName := `data_ths`
+whereParams := bson.M{"edbcode": "s0033227", "datatime": "2015-12-04"}
+params := bson.M{"$set": bson.M{"value": "1000"}}
+*/
+func MgoUpdateData(colName string, params, whereParams interface{}) (err error) {
+	if colName == "" {
+		err = errors.New("集合名称不可为空")
+		return
+	}
+	ctx := context.TODO()
+	coll, err := mgodb.MgoGetColl(colName)
+	if err != nil {
+		fmt.Println("MgoGetColl Err:", err.Error())
+		return
+	}
+	defer func() {
+		coll.Close(ctx)
+	}()
+	err = coll.UpdateOne(ctx, whereParams, params)
+	return
+}
+
+/*
+获取单条数据
+colName := `data_ths`
+whereParams := bson.M{"edbcode": "s0033227", "datatime": "2015-12-04"}
+*/
+func MgoFindOne(colName string, whereParams interface{}) (result interface{}, err error) {
+	if colName == "" {
+		err = errors.New("集合名称不可为空")
+		return
+	}
+	ctx := context.TODO()
+	coll, err := mgodb.MgoGetColl(colName)
+	if err != nil {
+		fmt.Println("MgoGetColl Err:", err.Error())
+		return
+	}
+	defer func() {
+		coll.Close(ctx)
+	}()
+	err = coll.Find(ctx, whereParams).One(&result)
+	return
+}
+
+/*
+分页获取数据
+colName := `data_ths`
+whereParams := bson.M{"edbcode": "s0033227", "datatime": "2015-12-04"}
+
+sort:="-weight"
+skip:0
+limit:10
+*/
+func MgoBatchFind(colName, sort string, whereParams interface{}, skip, limit int64) (list []interface{}, err error) {
+	if colName == "" {
+		err = errors.New("集合名称不可为空")
+		return
+	}
+	ctx := context.TODO()
+	coll, err := mgodb.MgoGetColl(colName)
+	if err != nil {
+		fmt.Println("MgoGetColl Err:", err.Error())
+		return
+	}
+	defer func() {
+		coll.Close(ctx)
+	}()
+	err = coll.Find(ctx, whereParams).Sort(sort).Skip(skip).Limit(limit).All(&list)
+	return
+}
+
+/*
+MgoUpsertData
+更新插入数据-数据存在即更新, 否则新增
+colName := `data_ths`
+filter := bson.M{"edbcode": "s0033227", "datatime": "2015-12-04"}
+replacement := bson.M{"edb_info_id":0,"edb_code":m.EdbCode,"data_time":d.DataTime,"value":f,"create_time":now,"modify_time":now,"data_timestamp": stamp}
+*/
+func MgoUpsertData(colName string, filter, replacement interface{}) (err error) {
+	if colName == "" {
+		err = errors.New("集合名称不可为空")
+		return
+	}
+	ctx := context.TODO()
+	coll, err := mgodb.MgoGetColl(colName)
+	if err != nil {
+		fmt.Println("MgoGetColl Err:", err.Error())
+		return
+	}
+	defer func() {
+		_ = coll.Close(ctx)
+	}()
+	_, err = coll.Upsert(ctx, filter, replacement)
+	return
+}

+ 9 - 2
utils/config.go

@@ -4,6 +4,7 @@ import (
 	"fmt"
 	beeLogger "github.com/beego/bee/v2/logger"
 	"github.com/beego/beego/v2/server/web"
+	"github.com/qiniu/qmgo"
 	"strconv"
 )
 
@@ -17,11 +18,14 @@ var (
 	MYSQL_LOG_URL    string
 	MYSQL_WEEKLY_URL string //用户主库
 	MYSQL_AI_URL     string //ETA-AI 数据库
+	MgoUrlData       string // mongodb数据库连接配置
 
 	REDIS_CACHE string //缓存地址
 	//Rc          *cache.Cache //redis缓存
-	Re error       //redis错误
-	Rc RedisClient //redis缓存
+	Re            error        //redis错误
+	Rc            RedisClient  //redis缓存
+	MgoDataCli    *qmgo.Client // mongodb客户端连接
+	MgoDataDbName string       // mongodb指标数据的库名
 )
 
 // 基础配置
@@ -292,6 +296,9 @@ func init() {
 	//ETA-AI
 	MYSQL_AI_URL = config["mysql_url_ai"]
 
+	// mongodb数据库连接配置
+	MgoUrlData = config["mgo_url_data"]
+
 	REDIS_CACHE = config["beego_cache"]
 	if len(REDIS_CACHE) <= 0 {
 		panic(any("redis链接参数没有配置"))

+ 37 - 0
utils/logs.go

@@ -18,6 +18,7 @@ var FileLog *logs.BeeLogger
 var ApiLog *logs.BeeLogger
 var FileLogData *logs.BeeLogger
 var Binlog *logs.BeeLogger
+var MongoLog *logs.BeeLogger
 
 func init() {
 	if LogMaxDays == 0 {
@@ -46,6 +47,7 @@ func init() {
 	initBinlog()
 	initApiLog()
 	initFileLogData()
+	initMgoLog()
 }
 
 type logConfig struct {
@@ -128,6 +130,41 @@ func initFileLogData() {
 	FileLogData.EnableFuncCallDepth(true)
 }
 
+// initMgoLog
+// @Description: mongo日志
+// @author: Roc
+// @datetime 2024-05-06 16:42:47
+func initMgoLog() {
+	//mgo日志
+
+	var logPath string
+	{
+		binlogPath := BinLogPath
+		if binlogPath == "" {
+			binlogPath = DefaultBinlogPath
+		}
+		logPath = path.Dir(binlogPath)
+	}
+	if logPath == `` {
+		logPath = "./etalogs"
+	}
+
+	mongoLogPath := logPath + "/mongo"
+	mongoLogFile := "mongo.log"
+
+	os.MkdirAll(mongoLogPath, os.ModePerm)
+	logFileName := path.Join(mongoLogPath, mongoLogFile)
+	MongoLog = logs.NewLogger(1000000)
+	logConf := getDefaultLogConfig()
+
+	logConf.FileName = logFileName
+	//logConf.MaxLines = 10000000
+	//logConf.Rotate = true
+	b, _ := json.Marshal(logConf)
+	MongoLog.SetLogger(logs.AdapterFile, string(b))
+	MongoLog.EnableFuncCallDepth(true)
+}
+
 func getDefaultLogConfig() logConfig {
 	return logConfig{
 		FileName: "",

+ 127 - 0
utils/mgodb/mgo_config.go

@@ -0,0 +1,127 @@
+package mgodb
+
+import (
+	"context"
+	"eta/eta_api/utils"
+	"github.com/qiniu/qmgo"
+	"github.com/qiniu/qmgo/options"
+	"go.mongodb.org/mongo-driver/bson"
+	"go.mongodb.org/mongo-driver/event"
+	mgoptions "go.mongodb.org/mongo-driver/mongo/options"
+	"sync"
+)
+
+var (
+	ConnectTimeoutMS = int64(3000)
+	SocketTimeoutMS  = int64(500000)
+	MaxPoolSize      = uint64(50)
+	MinPoolSize      = uint64(0)
+)
+
+//func init() {
+//	fmt.Println("start MgoNewClient")
+//	MgoNewClient()
+//	fmt.Println("end MgoNewClient")
+//}
+
+type MgoConfig struct {
+	Host       string `json:"host"`
+	Port       string `json:"port"`
+	Username   string `json:"username"`
+	Password   string `json:"password"`
+	AuthSource string `json:"authSource"`
+	Database   string `json:"database"`
+}
+
+// MgoNewClient
+// @Description: 创建一个mongodb客户端链接
+// @author: Roc
+// @datetime 2024-04-25 14:01:14
+// @return *qmgo.Client
+func MgoNewClient(mgoConfig MgoConfig) *qmgo.Client {
+	// 创建cmdMonitor,用于打印SQL
+	//startedCommands := make(map[int64]bson.Raw)
+	startedCommands := sync.Map{} // map[int64]bson.Raw
+
+	cmdMonitor := &event.CommandMonitor{
+		Started: func(_ context.Context, evt *event.CommandStartedEvent) {
+			startedCommands.Store(evt.RequestID, evt.Command)
+			//startedCommands[evt.RequestID] = evt.Command
+		},
+		Succeeded: func(_ context.Context, evt *event.CommandSucceededEvent) {
+			//log.Printf("Command: %v Reply: %v\n",
+			//	startedCommands[evt.RequestID],
+			//	evt.Reply,
+			//)
+			var commands bson.Raw
+			v, ok := startedCommands.Load(evt.RequestID)
+			if ok {
+				commands = v.(bson.Raw)
+			}
+			utils.MongoLog.Info("\n【MongoDB】[%.3fms] [%v] %v \n", float64(evt.Duration)/1e6, commands, evt.Reply)
+		},
+		Failed: func(_ context.Context, evt *event.CommandFailedEvent) {
+			//log.Printf("Command: %v Failure: %v\n",
+			//	startedCommands[evt.RequestID],
+			//	evt.Failure,
+			//)
+			var commands bson.Raw
+			v, ok := startedCommands.Load(evt.RequestID)
+			if ok {
+				commands = v.(bson.Raw)
+			}
+			utils.MongoLog.Info("\n【MongoDB】[%.3fms] [%v] \n %v \n", float64(evt.Duration)/1e6, commands, evt.Failure)
+		},
+	}
+
+	// 创建options
+	ops := options.ClientOptions{ClientOptions: &mgoptions.ClientOptions{}}
+	ops.SetMonitor(cmdMonitor)
+
+	ctx := context.Background()
+
+	//mongodb+srv://myDatabaseUser:D1fficultP%40ssw0rd@mongodb0.example.com/?authSource=admin&replicaSet=myRepl
+
+	var mongoUrl string
+	if mgoConfig.Password != "" {
+		mongoUrl = "mongodb://" + mgoConfig.Username + ":" + mgoConfig.Password + "@" +
+			mgoConfig.Host + ":" + mgoConfig.Port
+
+		if mgoConfig.AuthSource != `` {
+			mongoUrl += mongoUrl + "?&authSource=" + mgoConfig.AuthSource
+		}
+	} else {
+		mongoUrl = "mongodb://" + mgoConfig.Host + ":" + mgoConfig.Port
+	}
+
+	// 创建一个数据库链接
+	client, err := qmgo.NewClient(ctx, &qmgo.Config{
+		Uri:              mongoUrl,
+		Database:         mgoConfig.Database,
+		ConnectTimeoutMS: &ConnectTimeoutMS,
+		SocketTimeoutMS:  &SocketTimeoutMS,
+		MaxPoolSize:      &MaxPoolSize,
+		MinPoolSize:      &MinPoolSize,
+	}, ops)
+
+	if err != nil {
+		panic("MongoDB连接异常:" + err.Error())
+	}
+
+	return client
+}
+
+func MgoGetColl(collName string) (cli *qmgo.QmgoClient, err error) {
+	ctx := context.Background()
+	config := &qmgo.Config{
+		//Uri:              MGO_URL,
+		//Database:         MGO_DB,
+		Coll:             collName,
+		ConnectTimeoutMS: &ConnectTimeoutMS,
+		SocketTimeoutMS:  &SocketTimeoutMS,
+		MaxPoolSize:      &MaxPoolSize,
+		MinPoolSize:      &MinPoolSize,
+	}
+	cli, err = qmgo.Open(ctx, config)
+	return
+}