challenge.go 9.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326
  1. package dao
  2. import (
  3. "context"
  4. "database/sql"
  5. "encoding/json"
  6. "time"
  7. "go-common/app/admin/main/workflow/model"
  8. "github.com/jinzhu/gorm"
  9. "github.com/pkg/errors"
  10. )
  11. // Chall will retrive challenge by cid
  12. func (d *Dao) Chall(c context.Context, cid int64) (chall *model.Chall, err error) {
  13. chall = &model.Chall{}
  14. if db := d.ReadORM.Table("workflow_chall").Where("id=?", cid).First(chall); db.Error != nil {
  15. err = db.Error
  16. if db.RecordNotFound() {
  17. chall = nil
  18. err = nil
  19. } else {
  20. err = errors.Wrapf(err, "chall(%d)", cid)
  21. }
  22. }
  23. return
  24. }
  25. // Challs will select challenges by ids
  26. func (d *Dao) Challs(c context.Context, cids []int64) (challs map[int64]*model.Chall, err error) {
  27. challs = make(map[int64]*model.Chall, len(cids))
  28. if len(cids) <= 0 {
  29. return
  30. }
  31. chlist := make([]*model.Chall, 0)
  32. err = d.ReadORM.Table("workflow_chall").Where("id IN (?)", cids).Find(&chlist).Error
  33. if err != nil {
  34. err = errors.WithStack(err)
  35. return
  36. }
  37. for _, c := range chlist {
  38. challs[c.Cid] = c
  39. }
  40. return
  41. }
  42. // StateChalls will select a set of groups by challenge ids and state
  43. func (d *Dao) StateChalls(c context.Context, cids []int64, state int8) (challs map[int64]*model.Chall, err error) {
  44. challs = make(map[int64]*model.Chall, len(cids))
  45. challSlice := make([]*model.Chall, 0, len(cids))
  46. if len(cids) <= 0 {
  47. return
  48. }
  49. if err = d.ORM.Table("workflow_chall").Where("id IN (?)", cids).Find(&challSlice).Error; err != nil {
  50. err = errors.WithStack(err)
  51. return
  52. }
  53. for _, chall := range challSlice {
  54. chall.FromState()
  55. if chall.State != state {
  56. continue
  57. }
  58. challs[chall.Cid] = chall
  59. }
  60. return
  61. }
  62. // LastChallIDsByGids will select last chall ids by given gids
  63. func (d *Dao) LastChallIDsByGids(c context.Context, gids []int64) (cids []int64, err error) {
  64. if len(gids) <= 0 {
  65. return
  66. }
  67. var rows *sql.Rows
  68. if rows, err = d.ReadORM.Table("workflow_chall").Select("max(id)").Where("gid IN (?)", gids).Group("gid").Rows(); err != nil {
  69. return
  70. }
  71. defer rows.Close()
  72. for rows.Next() {
  73. var maxID int64
  74. if err = rows.Scan(&maxID); err != nil {
  75. return
  76. }
  77. cids = append(cids, maxID)
  78. }
  79. return
  80. }
  81. // TxUpChall will update state of a challenge
  82. // Deprecated
  83. func (d *Dao) TxUpChall(tx *gorm.DB, chall *model.Chall) (rows int64, err error) {
  84. // write old field
  85. chall.FromState()
  86. db := tx.Table("workflow_chall").Where("id=?", chall.Cid).
  87. Update("dispatch_state", chall.DispatchState)
  88. if db.Error != nil {
  89. err = errors.WithStack(db.Error)
  90. return
  91. }
  92. rows = db.RowsAffected
  93. return
  94. }
  95. // TxBatchUpChallByIDs will update state of challenges by cids
  96. func (d *Dao) TxBatchUpChallByIDs(tx *gorm.DB, cids []int64, state int8) (err error) {
  97. challSlice := make([]*model.Chall, 0, len(cids))
  98. if len(cids) <= 0 {
  99. return
  100. }
  101. if err = tx.Table("workflow_chall").Where("id IN (?)", cids).Find(&challSlice).Error; err != nil {
  102. err = errors.WithStack(err)
  103. return
  104. }
  105. for _, chall := range challSlice {
  106. chall.SetState(uint32(state), uint8(0))
  107. if err = tx.Table("workflow_chall").Where("id=?", chall.Cid).
  108. Update("dispatch_state", chall.DispatchState).Error; err != nil {
  109. err = errors.WithStack(err)
  110. return
  111. }
  112. }
  113. return
  114. }
  115. // AttPathsByCids will select a set of attachments paths by challenge ids
  116. func (d *Dao) AttPathsByCids(c context.Context, cids []int64) (paths map[int64][]string, err error) {
  117. var pathSlice []*struct {
  118. Cid int64
  119. Path string
  120. }
  121. paths = make(map[int64][]string, len(cids))
  122. if len(cids) <= 0 {
  123. return
  124. }
  125. if err = d.ReadORM.Table("workflow_attachment").Where("cid IN (?)", cids).Select("cid,path").Find(&pathSlice).Error; err != nil {
  126. return
  127. }
  128. for _, cp := range pathSlice {
  129. if _, ok := paths[cp.Cid]; !ok {
  130. paths[cp.Cid] = make([]string, 0, 1)
  131. }
  132. paths[cp.Cid] = append(paths[cp.Cid], cp.Path)
  133. }
  134. return
  135. }
  136. // AttPathsByCid will select a set of attachments paths by challenge id
  137. // Deprecated
  138. func (d *Dao) AttPathsByCid(c context.Context, cid int64) (paths []string, err error) {
  139. paths = make([]string, 0)
  140. rows, err := d.ReadORM.Table("workflow_attachment").Select("cid,path").Where("cid=?", cid).Rows()
  141. if err != nil {
  142. err = errors.Wrapf(err, "cid(%d)", cid)
  143. return
  144. }
  145. defer rows.Close()
  146. for rows.Next() {
  147. var cp struct {
  148. cid int32
  149. path string
  150. }
  151. if err = rows.Scan(&cp.cid, &cp.path); err != nil {
  152. err = errors.WithStack(err)
  153. return
  154. }
  155. paths = append(paths, cp.path)
  156. }
  157. return
  158. }
  159. // UpChallBusState will update specified business_state by conditions
  160. // Deprecated
  161. func (d *Dao) UpChallBusState(c context.Context, cid int64, busState int8, assigneeAdminid int64) (err error) {
  162. var chall *model.Chall
  163. if chall, err = d.Chall(c, cid); err != nil {
  164. return
  165. }
  166. if chall == nil {
  167. err = errors.Wrapf(err, "can not find challenge cid(%d)", cid)
  168. return
  169. }
  170. // double write to new field
  171. chall.SetState(uint32(busState), uint8(1))
  172. if err = d.ORM.Table("workflow_chall").Where("id=?", cid).
  173. Update("dispatch_state", chall.DispatchState).
  174. Update("assignee_adminid", assigneeAdminid).
  175. Error; err != nil {
  176. err = errors.WithStack(err)
  177. }
  178. return
  179. }
  180. // BatchUpChallBusState will update specified business_state by conditions
  181. func (d *Dao) BatchUpChallBusState(c context.Context, cids []int64, busState int8, assigneeAdminid int64) (err error) {
  182. var challs map[int64]*model.Chall
  183. challs, err = d.Challs(c, cids)
  184. if err != nil {
  185. return
  186. }
  187. for cid := range challs {
  188. challs[cid].SetState(uint32(busState), uint8(1))
  189. if err = d.ORM.Table("workflow_chall").Where("id=?", cid).
  190. Update("dispatch_state", challs[cid].DispatchState).
  191. Update("assignee_adminid", assigneeAdminid).Error; err != nil {
  192. err = errors.WithStack(err)
  193. return
  194. }
  195. }
  196. return
  197. }
  198. // TxChallsByBusStates select cids by business and oid
  199. func (d *Dao) TxChallsByBusStates(tx *gorm.DB, business int8, oid int64, busStates []int8) (cids []int64, err error) {
  200. cids = make([]int64, 0)
  201. rows, err := tx.Table("workflow_chall").Where("business=? AND oid=? ",
  202. business, oid).Select("id,dispatch_state").Rows()
  203. if err != nil {
  204. err = errors.WithStack(err)
  205. return
  206. }
  207. defer rows.Close()
  208. for rows.Next() {
  209. c := &model.Chall{}
  210. if err = rows.Scan(&c.Cid, &c.DispatchState); err != nil {
  211. return
  212. }
  213. for _, busState := range busStates {
  214. c.FromState()
  215. if c.BusinessState == busState {
  216. cids = append(cids, int64(c.Cid))
  217. }
  218. }
  219. }
  220. return
  221. }
  222. // TxUpChallsBusStateByIDs will update specified business_state by conditions
  223. func (d *Dao) TxUpChallsBusStateByIDs(tx *gorm.DB, cids []int64, busState int8, assigneeAdminid int64) (err error) {
  224. challSlice := make([]*model.Chall, 0)
  225. if err = tx.Table("workflow_chall").Where("id IN (?)", cids).
  226. Select("id,gid,mid,dispatch_state").Find(&challSlice).Error; err != nil {
  227. err = errors.WithStack(err)
  228. return
  229. }
  230. for _, chall := range challSlice {
  231. chall.SetState(uint32(busState), uint8(1))
  232. if err = tx.Table("workflow_chall").Where("id=?", chall.Cid).
  233. Update("dispatch_state", chall.DispatchState).Update("assignee_adminid", assigneeAdminid).Error; err != nil {
  234. err = errors.WithStack(err)
  235. return
  236. }
  237. }
  238. return
  239. }
  240. // TxUpChallExtraV2 will update Extra data by business oid
  241. func (d *Dao) TxUpChallExtraV2(tx *gorm.DB, business int8, oid, adminid int64, extra map[string]interface{}) (rows int64, err error) {
  242. exData, err := json.Marshal(extra)
  243. if err != nil {
  244. err = errors.Wrapf(err, "business(%d) oid(%d), extra(%s)", business, oid, extra)
  245. return
  246. }
  247. if err = tx.Table("workflow_business").Where("business=? AND oid=?", business, oid).Update("extra", exData).Error; err != nil {
  248. err = errors.Wrapf(err, "business(%d), oid(%d), extra(%s)", business, oid, exData)
  249. }
  250. return
  251. }
  252. // UpExtraV3 will update Extra data by gids
  253. func (d *Dao) UpExtraV3(gids []int64, adminid int64, extra string) error {
  254. return d.ORM.Table("workflow_business").Where("gid IN (?)", gids).Update("extra", extra).Error
  255. }
  256. // TxUpChallTag will update tid by cid
  257. func (d *Dao) TxUpChallTag(tx *gorm.DB, cid int64, tid int64) (err error) {
  258. if err = tx.Table("workflow_chall").Where("id=?", cid).Update("tid", tid).Error; err != nil {
  259. err = errors.Wrapf(err, "cid(%d), tid(%d)", cid, tid)
  260. }
  261. return
  262. }
  263. // BatchUpChallByIDs update dispatch_state field of cids
  264. func (d *Dao) BatchUpChallByIDs(cids []int64, dispatchState uint32, adminid int64) (err error) {
  265. if len(cids) <= 0 {
  266. return
  267. }
  268. if err = d.ORM.Table("workflow_chall").Where("id IN (?)", cids).
  269. Update("dispatch_state", dispatchState).Update("adminid", adminid).Error; err != nil {
  270. err = errors.WithStack(err)
  271. }
  272. return
  273. }
  274. // BatchResetAssigneeAdminID reset assignee_adminid by cids
  275. func (d *Dao) BatchResetAssigneeAdminID(cids []int64) (err error) {
  276. if len(cids) <= 0 {
  277. return
  278. }
  279. if err = d.ORM.Table("workflow_chall").Where("id IN (?)", cids).
  280. Update("assignee_adminid", 0).Error; err != nil {
  281. err = errors.WithStack(err)
  282. }
  283. return
  284. }
  285. // TxUpChallAssignee update assignee_adminid and dispatch_time when admin start a mission
  286. func (d *Dao) TxUpChallAssignee(tx *gorm.DB, cids []int64) error {
  287. return tx.Table("workflow_chall").Where("id IN (?)", cids).
  288. Update("dispatch_time", time.Now().Format("2006-01-02 15:04:05")).Error
  289. }