payment_controller.go 5.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170
  1. package payment
  2. import (
  3. "errors"
  4. "eta/eta_mini_ht_api/common/exception"
  5. "eta/eta_mini_ht_api/common/utils/lock"
  6. payUtils "eta/eta_mini_ht_api/common/utils/payment"
  7. "eta/eta_mini_ht_api/common/utils/redis"
  8. "eta/eta_mini_ht_api/controllers"
  9. orderDomian "eta/eta_mini_ht_api/domian/order"
  10. userDomian "eta/eta_mini_ht_api/domian/user"
  11. "eta/eta_mini_ht_api/service/facade"
  12. "eta/eta_mini_ht_api/service/order"
  13. "gorm.io/gorm"
  14. )
  15. import "eta/eta_mini_ht_api/service/user"
  16. type PaymentController struct {
  17. controllers.BaseController
  18. }
  19. // 支付
  20. type PayRequest struct {
  21. ProductOrderNo string `json:"productOrderNo"`
  22. }
  23. type PayResponse struct {
  24. PaymentUrl string `json:"paymentUrl"`
  25. PaymentToken string `json:"paymentToken"`
  26. }
  27. // PayOrder 支付订单
  28. // @Summary 支付订单
  29. // @Description 支付订单
  30. // @Success 200 {object} controllers.BaseResponse
  31. // @router /payOrder [post]
  32. func (pc *PaymentController) PayOrder() {
  33. controllers.Wrap(&pc.BaseController, func() (result *controllers.WrapData, err error) {
  34. result = pc.InitWrapData("创建支付订单失败")
  35. payRequest := new(PayRequest)
  36. pc.GetPostParams(payRequest)
  37. if payRequest.ProductOrderNo == "" {
  38. pc.FailedResult("订单编号不能为空", result)
  39. err = exception.New(exception.IllegalOrderNo)
  40. return
  41. }
  42. userInfo := pc.Data["user"].(user.User)
  43. defer func() {
  44. lock.ReleaseLock(redis.GeneratePaymentKey(payRequest.ProductOrderNo), pc.Data["threadId"].(string))
  45. }()
  46. if lock.AcquireLock(redis.GeneratePaymentKey(payRequest.ProductOrderNo), 10, pc.Data["threadId"].(string)) {
  47. //校验商品订单状态
  48. var productOrder orderDomian.ProductOrderDTO
  49. productOrder, err = order.GetProductOrderByUser(userInfo.Id, payRequest.ProductOrderNo)
  50. if err != nil {
  51. if errors.Is(err, gorm.ErrRecordNotFound) {
  52. pc.FailedResult("支付失败,商品订单信息不存在", result)
  53. err = exception.New(exception.IllegalOrderNo)
  54. } else {
  55. pc.FailedResult("支付失败,查询商品订单失败", result)
  56. err = exception.New(exception.IllegalOrderNo)
  57. }
  58. return
  59. }
  60. if productOrder.Status != "pending" {
  61. if productOrder.Status == "closed" {
  62. pc.FailedResult("支付失败,商品订单已关闭", result)
  63. err = exception.New(exception.IllegalOrderStatus)
  64. } else {
  65. pc.FailedResult("支付失败,商品订单状态异常", result)
  66. err = exception.New(exception.IllegalOrderStatus)
  67. }
  68. return
  69. }
  70. //1、未发起支付,2、支付到一半退出了,3、支付中
  71. if productOrder.TradeNo != "" {
  72. tradeOrder, tradeErr := order.GetTradeOrderByNo(productOrder.TradeNo)
  73. if tradeErr != nil {
  74. err = exception.NewWithException(exception.PayTradeOrderFailed, tradeErr.Error())
  75. pc.FailedResult("支付失败,获取原支付订单信息失败", result)
  76. return
  77. }
  78. if tradeOrder.PaymentStatus != "failed" {
  79. err = exception.New(exception.PayTradeOrderFailed)
  80. pc.FailedResult("支付失败,商品订单支付中,请勿重复支付", result)
  81. return
  82. }
  83. }
  84. //检查商品状态
  85. err = order.CheckProductStatus(productOrder)
  86. if err != nil {
  87. pc.FailedResult("支付失败,商品状态异常", result)
  88. return
  89. }
  90. var officialUser userDomian.OfficialUserDTO
  91. officialUser, err = user.GetUserByTemplateUserId(userInfo.Id)
  92. if err != nil {
  93. pc.FailedResult("支付失败,正式用户信息不存在", result)
  94. }
  95. var payOrderDTO orderDomian.PayOrderDTO
  96. payOrderDTO, err = facade.PayOrder(officialUser.ID, userInfo.Id, productOrder)
  97. if err != nil {
  98. pc.FailedResult("支付订单创建失败", result)
  99. err = exception.NewWithException(exception.CreatePaymentOrderFailed, err.Error())
  100. return
  101. }
  102. //将参数填充为URL地址直接返回前端
  103. url, parseErr := orderDomian.CreatePaymentUrl(payOrderDTO)
  104. if parseErr != nil {
  105. pc.FailedResult("生成订单链接失败", result)
  106. err = exception.NewWithException(exception.CreatePaymentOrderFailed, err.Error())
  107. return
  108. }
  109. pc.SuccessResult("支付订单创建成功", PayResponse{
  110. PaymentToken: payOrderDTO.PaymentToken,
  111. PaymentUrl: url,
  112. }, result)
  113. return
  114. } else {
  115. pc.FailedResult("商品订单处理中,请稍后再试", result)
  116. err = exception.New(exception.PaymentProcessingError)
  117. return
  118. }
  119. })
  120. }
  121. // PayOrderStatus 获取微信订单状态
  122. // @Summary 获取微信订单状态
  123. // @Description 获取微信订单状态
  124. // @Success 200 {object} controllers.BaseResponse
  125. // @router /payOrderStatus [get]
  126. func (pc *PaymentController) PayOrderStatus(token string) {
  127. controllers.Wrap(&pc.BaseController, func() (result *controllers.WrapData, err error) {
  128. result = pc.InitWrapData("获取微信订单信息失败")
  129. if token == "" {
  130. pc.FailedResult("token", result)
  131. err = exception.New(exception.IllegalWechatToken)
  132. return
  133. }
  134. paymentParams, err := payUtils.GetPaymentParam(token)
  135. if err != nil {
  136. pc.FailedResult("微信订单信息不存在", result)
  137. err = exception.NewWithException(exception.GetPaymentTokenFailed, err.Error())
  138. return
  139. }
  140. if paymentParams.Status == payUtils.EXPIRED {
  141. pc.FailedResult("订单超时,请重新支付", result)
  142. err = exception.New(exception.GetPaymentTokenFailed)
  143. return
  144. }
  145. if paymentParams.Status == payUtils.USED {
  146. pc.FailedResult("请勿重复发起微信支付", result)
  147. err = exception.New(exception.GetPaymentTokenFailed)
  148. return
  149. }
  150. if paymentParams.Status == payUtils.PENDING {
  151. pc.FailedResult("微信支付发起中,请耐心等待", result)
  152. err = exception.New(exception.GetPaymentTokenFailed)
  153. return
  154. }
  155. if paymentParams.Status == payUtils.READY {
  156. //查询到就绪之后将token状态重置为已用
  157. pc.SuccessResult("支付订单创建成功", paymentParams, result)
  158. return
  159. }
  160. return
  161. })
  162. }
  163. //