蛋蛋星球-客户端
選択できるのは25トピックまでです。 トピックは、先頭が英数字で、英数字とダッシュ('-')を使用した35文字以内のものにしてください。

svc_im.go 13 KiB

1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366
  1. package svc
  2. import (
  3. "applet/app/cfg"
  4. "applet/app/db"
  5. model2 "applet/app/db/im/model"
  6. "applet/app/md"
  7. "applet/app/pkg/pb"
  8. "applet/app/utils"
  9. "applet/app/utils/cache"
  10. "code.fnuoos.com/EggPlanet/egg_models.git/src/implement"
  11. "code.fnuoos.com/EggPlanet/egg_models.git/src/model"
  12. rule2 "code.fnuoos.com/EggPlanet/egg_system_rules.git"
  13. md2 "code.fnuoos.com/EggPlanet/egg_system_rules.git/md"
  14. "code.fnuoos.com/EggPlanet/egg_system_rules.git/rule"
  15. "code.fnuoos.com/EggPlanet/egg_system_rules.git/svc"
  16. "errors"
  17. "github.com/google/uuid"
  18. "github.com/shopspring/decimal"
  19. "google.golang.org/protobuf/proto"
  20. "strings"
  21. "time"
  22. )
  23. func DelGrabRedPackage(req *md.GrabRedPackageReq, user *model.User) (resp []byte, grabAmount string, err error) {
  24. var redPacketBalanceAmount, redPacketReceivedUserIds, redPacketReceivedImUserIds, redPackageReceivedUserAmount string
  25. //1、查找红包
  26. redPackageOrdDb := implement.NewImSendRedPackageOrdDb(db.Db)
  27. imSendRedPackageOrd, err := redPackageOrdDb.ImSendRedPackageOrdGetOneByParams(map[string]interface{}{
  28. "key": "id",
  29. "value": req.RedPackageId,
  30. })
  31. if err != nil {
  32. return nil, grabAmount, err
  33. }
  34. if imSendRedPackageOrd == nil {
  35. return nil, grabAmount, errors.New("未查询到对应的红包记录")
  36. }
  37. if imSendRedPackageOrd.RedPacketBalanceNums == 0 || imSendRedPackageOrd.State == int(pb.RedPacketStatusType_RPS_EXPIRE) {
  38. return nil, "-1", nil
  39. }
  40. //2、判断用户是否已领取
  41. receivedUserIds := strings.Split(imSendRedPackageOrd.ReceivedUserIds, ",")
  42. for k, receivedUserId := range receivedUserIds {
  43. if receivedUserId == utils.Int64ToStr(user.Id) {
  44. redPackageReceivedUserAmounts := strings.Split(imSendRedPackageOrd.ReceivedUserAmount, ",")
  45. grabAmount = redPackageReceivedUserAmounts[k]
  46. return nil, grabAmount, err
  47. }
  48. }
  49. //3、判断红包类型
  50. if imSendRedPackageOrd.RedPacketType == int(pb.RedPacketType_RPT_FRIEND) {
  51. //好友红包
  52. grabAmount = imSendRedPackageOrd.Amount
  53. redPacketBalanceAmount = "0"
  54. redPacketReceivedImUserIds = req.UserId
  55. redPacketReceivedUserIds = utils.Int64ToStr(user.Id)
  56. redPackageReceivedUserAmount = imSendRedPackageOrd.Amount
  57. } else {
  58. var receivedImUserIds, receivedUserIds, waitDrawImUserIds, redPackageReceivedUserAmounts []string
  59. if imSendRedPackageOrd.ReceivedImUserIds != "" {
  60. receivedImUserIds = strings.Split(imSendRedPackageOrd.ReceivedImUserIds, ",")
  61. }
  62. if imSendRedPackageOrd.ReceivedUserIds != "" {
  63. receivedUserIds = strings.Split(imSendRedPackageOrd.ReceivedUserIds, ",")
  64. }
  65. if imSendRedPackageOrd.WaitDrawImUserIds != "" {
  66. waitDrawImUserIds = strings.Split(imSendRedPackageOrd.WaitDrawImUserIds, ",")
  67. }
  68. if imSendRedPackageOrd.ReceivedUserAmount != "" {
  69. redPackageReceivedUserAmounts = strings.Split(imSendRedPackageOrd.ReceivedUserAmount, ",")
  70. }
  71. //群组红包
  72. switch imSendRedPackageOrd.RedPacketType {
  73. case int(pb.RedPacketType_RPT_GROUP_NORMAL):
  74. amount, _ := decimal.NewFromString(imSendRedPackageOrd.Amount)
  75. tmpGrabAmount := amount.Div(decimal.NewFromInt(int64(imSendRedPackageOrd.RedPacketNums)))
  76. grabAmount = tmpGrabAmount.String()
  77. tempRedPacketBalanceAmount, _ := decimal.NewFromString(imSendRedPackageOrd.RedPacketBalanceAmount)
  78. redPacketBalanceAmount = tempRedPacketBalanceAmount.Sub(tmpGrabAmount).String()
  79. break
  80. case int(pb.RedPacketType_RPT_GROUP_LUCK):
  81. balanceAmount, err := decimal.NewFromString(imSendRedPackageOrd.RedPacketBalanceAmount)
  82. if err != nil {
  83. return nil, grabAmount, err
  84. }
  85. balanceAmountValue, _ := balanceAmount.Float64()
  86. tmpGrabAmount := float64(utils.DoubleAverage(int64(imSendRedPackageOrd.RedPacketBalanceNums), utils.FloatToInt64(balanceAmountValue*100))) / 100
  87. grabAmount = utils.AnyToString(tmpGrabAmount)
  88. redPacketBalanceAmount = balanceAmount.Sub(decimal.NewFromFloat(tmpGrabAmount)).String()
  89. break
  90. case int(pb.RedPacketType_RPT_GROUP_SPECIALLY):
  91. if !utils.ContainerStr(waitDrawImUserIds, req.UserId) {
  92. return nil, grabAmount, errors.New("非专属用户不能领取")
  93. }
  94. grabAmount = imSendRedPackageOrd.Amount
  95. redPacketBalanceAmount = "0"
  96. redPacketReceivedImUserIds = req.UserId
  97. break
  98. case int(pb.RedPacketType_RPT_SYSTEM_FOR):
  99. if !utils.ContainerStr(waitDrawImUserIds, req.UserId) {
  100. return nil, grabAmount, errors.New("非专属用户不能领取")
  101. }
  102. grabAmount = imSendRedPackageOrd.Amount
  103. redPacketBalanceAmount = "0"
  104. redPacketReceivedImUserIds = req.UserId
  105. break
  106. }
  107. receivedImUserIds = append(receivedImUserIds, req.UserId)
  108. redPacketReceivedImUserIds = strings.Join(receivedImUserIds, ",")
  109. receivedUserIds = append(receivedUserIds, utils.AnyToString(user.Id))
  110. redPacketReceivedUserIds = strings.Join(receivedUserIds, ",")
  111. redPackageReceivedUserAmounts = append(redPackageReceivedUserAmounts, grabAmount)
  112. redPackageReceivedUserAmount = strings.Join(redPackageReceivedUserAmounts, ",")
  113. }
  114. session := db.Db.NewSession()
  115. defer session.Close()
  116. //2、改变红包记录状态
  117. if imSendRedPackageOrd.ReceivedTimes != "" {
  118. receivedTimes := strings.Split(imSendRedPackageOrd.ReceivedTimes, ",")
  119. receivedTimes = append(receivedTimes, time.Now().Format("2006-01-02 15:04:05"))
  120. imSendRedPackageOrd.ReceivedTimes = strings.Join(receivedTimes, ",")
  121. } else {
  122. imSendRedPackageOrd.ReceivedTimes = time.Now().Format("2006-01-02 15:04:05")
  123. }
  124. imSendRedPackageOrd.RedPacketBalanceNums = imSendRedPackageOrd.RedPacketBalanceNums - 1
  125. if imSendRedPackageOrd.RedPacketBalanceNums > 0 {
  126. imSendRedPackageOrd.State = int(pb.RedPacketStatusType_RPS_DRAWING)
  127. } else {
  128. imSendRedPackageOrd.State = int(pb.RedPacketStatusType_RPS_DRAW_OVER)
  129. }
  130. imSendRedPackageOrd.ReceivedUserAmount = redPackageReceivedUserAmount
  131. imSendRedPackageOrd.RedPacketBalanceAmount = redPacketBalanceAmount
  132. imSendRedPackageOrd.ReceivedUserIds = redPacketReceivedUserIds
  133. imSendRedPackageOrd.ReceivedImUserIds = redPacketReceivedImUserIds
  134. _, err = redPackageOrdDb.ImSendRedPackageOrdUpdateBySession(session, imSendRedPackageOrd.Id, imSendRedPackageOrd, "red_packet_balance_nums", "state", "received_user_ids", "received_im_user_ids", "received_times",
  135. "received_user_amount", "create_time", "update_time", "red_packet_balance_amount")
  136. if err != nil {
  137. session.Rollback()
  138. return nil, grabAmount, err
  139. }
  140. //3、加上给用户加上余额
  141. dealUserWalletReq := md2.DealUserWalletReq{
  142. Direction: "add",
  143. Kind: 5,
  144. Title: "领取红包收益",
  145. Uid: user.Id,
  146. Amount: utils.StrToFloat64(grabAmount),
  147. }
  148. err = rule.DealUserWallet(session, dealUserWalletReq)
  149. if err != nil {
  150. session.Rollback()
  151. return nil, grabAmount, err
  152. }
  153. //4、组装消息参数
  154. msg := &pb.RED_PACKAGE{
  155. RedMessageType: pb.RedPacketMessageType_RMT_GRAB,
  156. RedPacketType: pb.RedPacketType(imSendRedPackageOrd.RedPacketType),
  157. RedPacketContent: "",
  158. //RedPacketAmount: float32(utils.AnyToFloat64(req.Amount)),
  159. //RedPacketNums: int32(req.RedPacketNums),
  160. RedPacketBalanceAmount: float32(utils.AnyToFloat64(imSendRedPackageOrd.RedPacketBalanceAmount)),
  161. ReceivedUserId: utils.StrToInt64(req.UserId),
  162. ReceivedUserAmount: utils.StrToFloat32(grabAmount),
  163. ReceivedUserNickname: user.Nickname,
  164. RedPacketStatusType: pb.RedPacketStatusType(imSendRedPackageOrd.State),
  165. RedPacketId: imSendRedPackageOrd.Id,
  166. SendRedPacketUid: int64(imSendRedPackageOrd.ImUid),
  167. SendRedPacketNickname: req.SendRedPackageUserNikeName,
  168. SendRedPacketAvatarUrl: req.SendRedPacketAvatarUrl,
  169. //RedPacketSmallContent: req.RedPacketSmallContent,
  170. RedPacketCover: req.RedPackageCover,
  171. }
  172. utils.FilePutContents("DelGrabRedPackage", utils.SerializeStr(map[string]interface{}{
  173. "args": req,
  174. "msg": msg,
  175. "ord": imSendRedPackageOrd,
  176. }))
  177. resp, err = proto.Marshal(msg)
  178. if err != nil {
  179. return nil, grabAmount, err
  180. }
  181. return resp, grabAmount, nil
  182. }
  183. func DetailGrabRedPackage(redPackageId string) (resp []md.RedPackageDetailUserNode, imSendRedPackageOrd *model.ImSendRedPackageOrd, err error) {
  184. //1、查找红包
  185. redPackageOrdDb := implement.NewImSendRedPackageOrdDb(db.Db)
  186. imSendRedPackageOrd, err = redPackageOrdDb.ImSendRedPackageOrdGetOneByParams(map[string]interface{}{
  187. "key": "id",
  188. "value": redPackageId,
  189. })
  190. if err != nil {
  191. return nil, nil, err
  192. }
  193. if imSendRedPackageOrd == nil {
  194. return resp, imSendRedPackageOrd, errors.New("未查询到对应的红包记录")
  195. }
  196. receivedUserIds := strings.Split(imSendRedPackageOrd.ReceivedUserIds, ",")
  197. userDb := implement.NewUserDb(db.Db)
  198. users, err := userDb.UserFindByParams(map[string]interface{}{
  199. "key": "id",
  200. "value": receivedUserIds,
  201. })
  202. if err != nil {
  203. return resp, imSendRedPackageOrd, err
  204. }
  205. var usersMap = map[string]model.User{}
  206. for _, v := range users {
  207. usersMap[utils.AnyToString(v.Id)] = v
  208. }
  209. receivedImUserIds := strings.Split(imSendRedPackageOrd.ReceivedImUserIds, ",")
  210. receivedTimes := strings.Split(imSendRedPackageOrd.ReceivedTimes, ",")
  211. receivedUserAmount := strings.Split(imSendRedPackageOrd.ReceivedUserAmount, ",")
  212. redisConn := cache.GetPool().Get()
  213. scheme, domain := svc.ImageBucket(db.Db, redisConn)
  214. for k, v := range receivedUserIds {
  215. resp = append(resp, md.RedPackageDetailUserNode{
  216. ImUserId: receivedImUserIds[k],
  217. UserNickName: usersMap[v].Nickname,
  218. UserAvatarUrl: svc.ImageFormatWithBucket(scheme, domain, usersMap[v].Avatar),
  219. Amount: receivedUserAmount[k],
  220. ReceiveAt: receivedTimes[k],
  221. })
  222. }
  223. return resp, imSendRedPackageOrd, nil
  224. }
  225. // BalancePayForRedPackage 红包余额支付
  226. func BalancePayForRedPackage(user *model.User, money string, req md.SendRedPackageReq) (resp []byte, redPackageId int64, err error) {
  227. session := db.Db.NewSession()
  228. defer session.Close()
  229. //扣除用户余额
  230. dealUserWalletReq := md2.DealUserWalletReq{
  231. Direction: "sub",
  232. Kind: 6,
  233. Title: "领取红包收益",
  234. Uid: user.Id,
  235. Amount: utils.StrToFloat64(money),
  236. }
  237. rule2.Init(cfg.RedisAddr)
  238. err = rule.DealUserWallet(session, dealUserWalletReq)
  239. if err != nil {
  240. session.Rollback()
  241. return nil, 0, err
  242. }
  243. // 新增红包记录
  244. var imUid int
  245. if req.UserId != "" {
  246. imUid = utils.StrToInt(req.UserId)
  247. } else {
  248. //TODO::请求rpc接口,同步用户数据
  249. resp, err := utils.GetBusinessExtClient(cfg.ImBusinessRpc.URL, cfg.ImBusinessRpc.PORT).GetUser(utils.GetCtx("", "", ""), &pb.GetUserReq{
  250. UserId: 0,
  251. Phone: user.Phone,
  252. })
  253. if err != nil {
  254. return nil, redPackageId, err
  255. }
  256. imUid = int(resp.User.UserId)
  257. }
  258. now := time.Now()
  259. ordNo := uuid.New().String()
  260. var waitDrawUserIds string
  261. var waitDrawImUserIds string
  262. if req.RedPacketType == int(pb.RedPacketType_RPT_GROUP_SPECIALLY) {
  263. var toUserIds []string
  264. for _, v := range req.ToUserIds {
  265. toUserIds = append(toUserIds, utils.AnyToString(v))
  266. }
  267. waitDrawUserIds = strings.Join(toUserIds, ",")
  268. userDb := implement.NewUserDb(db.Db)
  269. waitDrawUsers, err1 := userDb.UserFindByParams(map[string]interface{}{
  270. "key": "id",
  271. "value": toUserIds,
  272. })
  273. if err1 != nil {
  274. return nil, 0, err1
  275. }
  276. var waitDrawUserPhones []string
  277. for _, v := range waitDrawUsers {
  278. waitDrawUserPhones = append(waitDrawUserPhones, v.Phone)
  279. }
  280. var waitDrawImUsers []model2.User
  281. err = db.DbIm.Table("user").In("phone_number", waitDrawUserPhones).Find(&waitDrawUsers)
  282. if err != nil {
  283. return nil, 0, err
  284. }
  285. var toUserIMIDs []string
  286. for _, v := range waitDrawImUsers {
  287. toUserIMIDs = append(toUserIMIDs, utils.AnyToString(v.Id))
  288. }
  289. waitDrawImUserIds = strings.Join(toUserIMIDs, ",")
  290. }
  291. ordDb := implement.NewImSendRedPackageOrdDb(db.Db)
  292. m := model.ImSendRedPackageOrd{
  293. OrdNo: ordNo,
  294. Uid: int(user.Id),
  295. ImUid: imUid,
  296. Amount: req.Amount,
  297. RedPacketBalanceAmount: req.Amount,
  298. RedPacketType: req.RedPacketType,
  299. RedPacketNums: req.RedPacketNums,
  300. RedPacketBalanceNums: req.RedPacketNums,
  301. State: 0,
  302. WaitDrawUserIds: waitDrawUserIds,
  303. WaitDrawImUserIds: waitDrawImUserIds,
  304. ReceivedUserIds: "",
  305. ReceivedImUserIds: "",
  306. ReceivedUserAmount: "",
  307. CreateTime: now.Format("2006-01-02 15:04:05"),
  308. UpdateTime: now.Format("2006-01-02 15:04:05"),
  309. }
  310. redPackageOrdId, err := ordDb.ImSendRedPackageOrdInsertBySession(session, &m)
  311. if err != nil {
  312. session.Rollback()
  313. return nil, redPackageId, err
  314. }
  315. err = session.Commit()
  316. if err != nil {
  317. return nil, redPackageOrdId, err
  318. }
  319. redisConn := cache.GetPool().Get()
  320. scheme, domain := svc.ImageBucket(db.Db, redisConn)
  321. msg := &pb.RED_PACKAGE{
  322. RedMessageType: pb.RedPacketMessageType_RMT_SEND,
  323. RedPacketType: pb.RedPacketType(req.RedPacketType),
  324. RedPacketContent: req.RedPacketContent,
  325. RedPacketAmount: float32(utils.AnyToFloat64(req.Amount)),
  326. RedPacketNums: int32(req.RedPacketNums),
  327. RedPacketBalanceAmount: float32(utils.AnyToFloat64(req.Amount)),
  328. ReceivedUserId: utils.StrToInt64(waitDrawUserIds),
  329. ReceivedUserAmount: 0,
  330. ReceivedUserNickname: "",
  331. RedPacketStatusType: 0,
  332. RedPacketId: redPackageOrdId,
  333. SendRedPacketUid: utils.StrToInt64(req.UserId),
  334. SendRedPacketNickname: user.Nickname,
  335. SendRedPacketAvatarUrl: svc.ImageFormatWithBucket(scheme, domain, user.Avatar),
  336. RedPacketSmallContent: req.RedPacketSmallContent,
  337. }
  338. resp, err = proto.Marshal(msg)
  339. if err != nil {
  340. return nil, redPackageId, err
  341. }
  342. redPackageId = redPackageOrdId
  343. return resp, redPackageId, nil
  344. }