service-asset.go 7.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290
  1. package api
  2. import (
  3. "errors"
  4. "fmt"
  5. "queencount/db/model"
  6. "queencount/db/repo"
  7. "time"
  8. "github.com/gin-gonic/gin"
  9. "go.mongodb.org/mongo-driver/bson"
  10. "go.mongodb.org/mongo-driver/bson/primitive"
  11. )
  12. func AssetCount(router *GinRouter) {
  13. // 统计总信息
  14. router.GET("/asset/info/types/:dbId", GetAssetCount)
  15. // 统计总图表
  16. router.GET("/asset/info", GetInfo)
  17. }
  18. type AssetDefCountInfo struct {
  19. Mesh []CountDefItem `json:"mesh"`
  20. Image []CountDefItem `json:"image"`
  21. Material []CountDefItem `json:"material"`
  22. Env3d []CountDefItem `json:"env3d"`
  23. }
  24. type CountDefItem struct {
  25. DefItemNum int `json:"defItemNum"`
  26. DefName string `json:"defName"`
  27. DefKey string `json:"defKey"`
  28. }
  29. func GetAssetCount(c *gin.Context, apictx *ApiSession) (interface{}, error) {
  30. // databases := []string{"mesh", "image", "material", "env3d"}
  31. // 定义模型数量
  32. dbId := c.Param("dbId")
  33. if dbId == "" {
  34. return nil, errors.New("dbId不能为空")
  35. }
  36. query := make(map[string]interface{})
  37. query["_id"], _ = primitive.ObjectIDFromHex(dbId)
  38. option := &repo.DocSearchOptions{
  39. CollectName: repo.CollectionDatabase,
  40. Query: query,
  41. Project: []string{"_id", "assets", "name"},
  42. }
  43. var datbaseDoc model.Database
  44. found, err := repo.RepoSeachDoc(apictx.CreateRepoCtx(), option, &datbaseDoc)
  45. if err != nil || !found {
  46. return nil, err
  47. }
  48. var countDefitem CountDefItem
  49. var assetDefCountInfo AssetDefCountInfo
  50. defMeshSet := make([]CountDefItem, 0)
  51. defImageSet := make([]CountDefItem, 0)
  52. defMaterialSet := make([]CountDefItem, 0)
  53. defEnv3dSet := make([]CountDefItem, 0)
  54. dbName := datbaseDoc.Name
  55. for _, v := range datbaseDoc.Assets {
  56. // 模型 mesh
  57. if v.Type == 10 {
  58. countDefitem.DefKey = v.Collection
  59. countDefitem.DefName = v.Label
  60. count, err := repo.RepoDbCountDoc(apictx.CreateRepoCtx(), dbName, v.Collection, repo.Map{})
  61. if err != nil {
  62. return nil, err
  63. }
  64. countDefitem.DefItemNum = int(count)
  65. defMeshSet = append(defMeshSet, countDefitem)
  66. assetDefCountInfo.Mesh = defMeshSet
  67. }
  68. if v.Type == 20 {
  69. countDefitem.DefKey = v.Collection
  70. countDefitem.DefName = v.Label
  71. count, err := repo.RepoDbCountDoc(apictx.CreateRepoCtx(), dbName, v.Collection, repo.Map{})
  72. if err != nil {
  73. return nil, err
  74. }
  75. countDefitem.DefItemNum = int(count)
  76. defImageSet = append(defImageSet, countDefitem)
  77. assetDefCountInfo.Image = defImageSet
  78. }
  79. if v.Type == 30 {
  80. countDefitem.DefKey = v.Collection
  81. countDefitem.DefName = v.Label
  82. count, err := repo.RepoDbCountDoc(apictx.CreateRepoCtx(), dbName, v.Collection, repo.Map{})
  83. if err != nil {
  84. return nil, err
  85. }
  86. countDefitem.DefItemNum = int(count)
  87. defMaterialSet = append(defMaterialSet, countDefitem)
  88. assetDefCountInfo.Material = defMaterialSet
  89. }
  90. if v.Type == 40 {
  91. countDefitem.DefKey = v.Collection
  92. countDefitem.DefName = v.Label
  93. count, err := repo.RepoDbCountDoc(apictx.CreateRepoCtx(), dbName, v.Collection, repo.Map{})
  94. if err != nil {
  95. return nil, err
  96. }
  97. countDefitem.DefItemNum = int(count)
  98. defEnv3dSet = append(defEnv3dSet, countDefitem)
  99. assetDefCountInfo.Env3d = defEnv3dSet
  100. }
  101. }
  102. return assetDefCountInfo, nil
  103. }
  104. type ReqAssetCount struct {
  105. DbId string `json:"dbId"`
  106. Step int `json:"step"`
  107. StartTime string `json:"startTime"`
  108. EndTime string `json:"endTime"`
  109. }
  110. const DateTimeLayout = "2006-01-02 15:04:05"
  111. func (req *ReqAssetCount) GetStartTime() (time.Time, error) {
  112. return time.Parse(DateTimeLayout, req.StartTime)
  113. }
  114. func (req *ReqAssetCount) GetEndTime() (time.Time, error) {
  115. return time.Parse(DateTimeLayout, req.EndTime)
  116. }
  117. type TypeCount struct {
  118. Time []*model.AssetCountV0 `json:"times"`
  119. DefName string `json:"defName"`
  120. DefType int `json:"defType"`
  121. DefId string `json:"defId"`
  122. }
  123. func GetStepIndex(t time.Time, endTime time.Time, step int) int64 {
  124. return int64(endTime.Sub(t).Seconds()) / int64(step)
  125. }
  126. // 获取统计信息图表需要的信息
  127. func GetInfo(c *gin.Context, apictx *ApiSession) (interface{}, error) {
  128. var form ReqAssetCount
  129. err := c.ShouldBindJSON(&form)
  130. if err != nil {
  131. return nil, errors.New("参数错误")
  132. }
  133. if form.Step == 0 {
  134. return nil, errors.New("时间步距不能为空")
  135. }
  136. if form.StartTime == "" {
  137. return nil, errors.New("开始时间不能为空")
  138. }
  139. if form.EndTime == "" {
  140. return nil, errors.New("结束时间不能为空")
  141. }
  142. if form.DbId == "" {
  143. return nil, errors.New("数据库id不为空")
  144. }
  145. startTime, err := form.GetStartTime()
  146. if err != nil {
  147. return nil, err
  148. }
  149. endTime, err := form.GetEndTime()
  150. if err != nil {
  151. return nil, err
  152. }
  153. ctx := apictx.CreateRepoCtx()
  154. dbId, _ := primitive.ObjectIDFromHex(form.DbId)
  155. // 根据id查询数据库名
  156. var databaseDoc model.Database
  157. dbParam := &repo.DocSearchOptions{
  158. CollectName: repo.CollectionDatabase,
  159. Query: map[string]interface{}{"_id": dbId},
  160. Project: []string{"_id", "name", "assets"},
  161. }
  162. is, err := repo.RepoSeachDoc(ctx, dbParam, &databaseDoc)
  163. if !is || err != nil {
  164. return nil, errors.New("资产数据为空")
  165. }
  166. searchTime := time.Now()
  167. listCounts := []*model.AssetCount{}
  168. err = repo.RepoDocsSearch(apictx.CreateRepoCtx(), &repo.PageSearchOptions{
  169. Db: databaseDoc.Name, // 对应资产数据库
  170. CollectName: repo.CollectionAssetCount, // 统计表
  171. Query: repo.Map{"$and": []bson.M{
  172. bson.M{"createTime": bson.M{"$lte": endTime}},
  173. bson.M{"createTime": bson.M{"$gte": startTime}},
  174. }},
  175. Project: []string{"defId", "createTime", "count"},
  176. // Sort: bson.M{"createTime": -1}, // 降序 小于等于createTime中取时间最近的 第一条
  177. }, &listCounts)
  178. if err != nil {
  179. return nil, err
  180. }
  181. defCountsMap := map[string]*TypeCount{}
  182. listCountIndex := len(listCounts)
  183. for {
  184. if listCountIndex == 0 {
  185. break
  186. }
  187. listCountIndex -= 1
  188. item := listCounts[listCountIndex]
  189. defId := item.DefId
  190. if defCountsMap[defId] == nil {
  191. defCountsMap[defId] = &TypeCount{Time: []*model.AssetCountV0{
  192. {
  193. DefId: item.DefId,
  194. CreateTime: item.CreateTime,
  195. Count: item.Count,
  196. StepIndex: int(GetStepIndex(item.CreateTime, endTime, form.Step)),
  197. },
  198. }}
  199. continue
  200. }
  201. typeList := defCountsMap[defId]
  202. lastType := typeList.Time[len(typeList.Time)-1]
  203. b, _ := time.ParseDuration(fmt.Sprintf("%ds", form.Step))
  204. if item.CreateTime.Unix() <= lastType.CreateTime.Add(b*-1).Unix() {
  205. typeList.Time = append(typeList.Time, &model.AssetCountV0{
  206. DefId: item.DefId,
  207. CreateTime: item.CreateTime,
  208. Count: item.Count,
  209. StepIndex: int(GetStepIndex(item.CreateTime, endTime, form.Step)),
  210. })
  211. }
  212. }
  213. out := []*TypeCount{}
  214. for defId, _ := range defCountsMap {
  215. for _, v := range databaseDoc.Assets {
  216. if v.Id == defId {
  217. defCountsMap[defId].DefType = v.Type
  218. defCountsMap[defId].DefName = v.Label
  219. defCountsMap[defId].DefId = v.Id
  220. break
  221. }
  222. }
  223. out = append(out, defCountsMap[defId])
  224. }
  225. return map[string]interface{}{
  226. "types": out,
  227. "time": time.Now().Sub(searchTime).Seconds(),
  228. }, nil
  229. }
  230. // 获取需要查询数据的时间点
  231. func GetCountTimeSet(form ReqAssetCount) (timeSet []time.Time) {
  232. // 计算有多少个时间段
  233. startTime, _ := time.Parse(DateTimeLayout, form.StartTime)
  234. endTime, _ := time.Parse(DateTimeLayout, form.EndTime)
  235. duration := endTime.Unix() - startTime.Unix()
  236. counts := int(duration / int64(form.Step)) // 取整
  237. for i := 0; i <= counts; i++ {
  238. b, _ := time.ParseDuration(fmt.Sprintf("%ds", i*form.Step))
  239. start := startTime.Add(b)
  240. // 第一个元素为开始时间
  241. timeSet = append(timeSet, start)
  242. }
  243. return
  244. }