service-array.go 4.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189
  1. package api
  2. import (
  3. "fmt"
  4. "mesh/db/repo"
  5. "github.com/gin-gonic/gin"
  6. "go.mongodb.org/mongo-driver/bson"
  7. "go.mongodb.org/mongo-driver/bson/primitive"
  8. )
  9. type DetailHandler func(c *gin.Context, apictx *ApiSession, entity interface{}) (interface{}, error)
  10. type ArrayCRUDOption struct {
  11. Collection string
  12. ArrayFieldPath string
  13. NewModel CreateModel
  14. EmtyModel EmptyModel
  15. DocModel EmptyModel
  16. SearchProject []string
  17. Query repo.Map
  18. OnUpdate Update
  19. OnDetail DetailHandler
  20. NeedsUpdate bool
  21. NeedsRemove bool
  22. }
  23. func CreateArrayCRUD(router *GinRouter, prefix string, option *ArrayCRUDOption) {
  24. //创建
  25. creatpath := fmt.Sprintf("%s/create/:id", prefix)
  26. if option.NewModel != nil {
  27. router.POSTJWT(creatpath, func(c *gin.Context, apictx *ApiSession) (interface{}, error) {
  28. id := c.Param("id")
  29. if len(id) < 1 {
  30. return nil, NewError("参数id不能为空")
  31. }
  32. var entity interface{} = nil
  33. entity, _ = option.NewModel(c, apictx)
  34. if entity == nil {
  35. return nil, NewError("数据已存在!")
  36. }
  37. ret, _ := repo.RepoDocArrayAppend(apictx.CreateRepoCtx(), option.Collection, id, option.ArrayFieldPath, entity)
  38. if ret.ModifiedCount == 1 {
  39. return entity, nil
  40. }
  41. return nil, NewError("创建失败!")
  42. })
  43. }
  44. //更新
  45. if option.NeedsUpdate {
  46. updatePath := fmt.Sprintf("%s/update/:id", prefix)
  47. router.POSTJWT(updatePath, func(c *gin.Context, apictx *ApiSession) (interface{}, error) {
  48. docId := c.Param("id")
  49. if len(docId) < 1 {
  50. return nil, NewError("id不能为空!")
  51. }
  52. m := option.EmtyModel(c, apictx)
  53. err := c.ShouldBindJSON(m)
  54. if err != nil {
  55. fmt.Println(err)
  56. return nil, NewError("参数解析错误")
  57. }
  58. if option.OnUpdate != nil {
  59. option.OnUpdate(c, apictx, m)
  60. }
  61. updateQuery := repo.Map{}
  62. for k, v := range option.Query {
  63. p := fmt.Sprintf("%s.%s", option.ArrayFieldPath, k)
  64. updateQuery[p] = v
  65. }
  66. updateSet := repo.Map{}
  67. spath := fmt.Sprintf("%s.$", option.ArrayFieldPath)
  68. updateSet[spath] = m
  69. updateOption := &repo.ArrayOneUpdateOption{CollectName: option.Collection, Id: docId, Query: updateQuery, Set: updateSet}
  70. return repo.RepoDocArrayOneUpdate(apictx.CreateRepoCtx(), updateOption)
  71. })
  72. }
  73. //数组所有数据
  74. SearchPath := fmt.Sprintf("%s/list/:id", prefix)
  75. pageSearchFn := func(c *gin.Context, apictx *ApiSession) (interface{}, error) {
  76. docId := c.Param("id")
  77. if len(docId) < 1 {
  78. return nil, NewError("id不能为空!")
  79. }
  80. query := UtilQueryMap(c)
  81. query["_id"], _ = primitive.ObjectIDFromHex(docId)
  82. _, list := repo.RepoSeachDocsMap(apictx.CreateRepoCtx(), &repo.DocsSearchOptions{
  83. CollectName: option.Collection,
  84. Query: query,
  85. Project: option.SearchProject,
  86. })
  87. out := map[string]interface{}{"list": []string{}}
  88. if list != nil {
  89. out["list"] = list
  90. }
  91. return out, nil
  92. }
  93. router.GETJWT(SearchPath, pageSearchFn)
  94. //删除
  95. if option.NeedsRemove {
  96. removePath := fmt.Sprintf("%s/delete/:id", prefix)
  97. router.POSTJWT(removePath, func(c *gin.Context, apictx *ApiSession) (interface{}, error) {
  98. id := c.Param("id")
  99. if len(id) < 1 {
  100. return nil, NewError("参数不能为空")
  101. }
  102. body := map[string]interface{}{}
  103. c.ShouldBindJSON(&body)
  104. ArrayQuery := repo.Map{}
  105. if len(body) < 1 {
  106. return nil, NewError("body参数不能为空")
  107. }
  108. query := bson.M{}
  109. for k, v := range body {
  110. query[k] = v
  111. }
  112. ArrayQuery[option.ArrayFieldPath] = query
  113. options := &repo.ArrayOneRemoveOption{
  114. CollectName: option.Collection,
  115. Id: id,
  116. ArrayQuery: ArrayQuery,
  117. }
  118. ret, err := repo.RepoDocArrayOneRemove(apictx.CreateRepoCtx(), options)
  119. if ret.ModifiedCount < 1 {
  120. return nil, NewError("删除失败!")
  121. }
  122. return ret, err
  123. })
  124. }
  125. //详情
  126. if option.OnDetail != nil && option.DocModel != nil {
  127. DetailPath := fmt.Sprintf("%s/detail/:id", prefix)
  128. router.GETJWT(DetailPath, func(c *gin.Context, apictx *ApiSession) (interface{}, error) {
  129. docId := c.Param("id")
  130. if len(docId) < 1 {
  131. return nil, NewError("id不能为空!")
  132. }
  133. query := UtilQueryMap(c)
  134. filter := repo.Map{}
  135. if len(query) > 0 {
  136. filter[option.ArrayFieldPath] = query
  137. }
  138. m := option.DocModel(c, apictx)
  139. ok, ret := repo.RepoDocArraySearch(apictx.CreateRepoCtx(), &repo.ArrayOneSearchOption{
  140. CollectName: option.Collection,
  141. ArrayQuery: filter,
  142. Id: docId,
  143. Field: option.ArrayFieldPath,
  144. })
  145. if !ok {
  146. return nil, NewError("数据不存在!")
  147. }
  148. retOut, err := option.OnDetail(c, apictx, ret)
  149. if err != nil {
  150. return nil, err
  151. }
  152. if retOut != nil {
  153. return retOut, nil
  154. }
  155. return m, nil
  156. })
  157. }
  158. }