balance.go 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355
  1. package balance_model
  2. import (
  3. "fmt"
  4. "strings"
  5. "time"
  6. "github.com/astaxie/beego"
  7. "github.com/astaxie/beego/orm"
  8. "github.com/uuid"
  9. // "fohow.com/apps/shop"
  10. // "fohow.com/cache"
  11. // "fohow.com/apps/models/user_model"
  12. // "fohow.com/apps/models/vas_model"
  13. "fohow.com/cache"
  14. // "fohow.com/libs/wx_mp"
  15. )
  16. const (
  17. balances_tablename = "balances"
  18. // balance_hitories_tablename = "d5c_balance_hitories"
  19. balance_orders_tablename = "balance_orders"
  20. // BALANCE_SERVICE_CHARGE = 100 //手续费
  21. BALANCE_UPGRADE = int64(420000) //升级代金券
  22. BALANCE_PAIED = int64(300000) //升级支付金额
  23. BALANCE_BL = int64(8) //群主推荐比例
  24. RECHARGE_BALANCE_BL = int64(85) //群主优惠比例
  25. AWARD_UPGRADE = int64(50000) //升级群主奖励
  26. ORDER_ID_PREFIX_CZ = "CZ" //充值
  27. BALANCE_SOURCE_PLATFORM_EXCHANGE = "platform_exchange" //企业大使兑换拉比代金券
  28. BALANCE_SOURCE_PLATFORM_EXCHANGE_NAME = "企业大使兑换"
  29. BALANCE_SOURCE_RECHARGE = "recharge" //充值
  30. BALANCE_SOURCE_RECHARGE_NAME = "充值"
  31. BALANCE_SOURCE_EXCHANGE_PRODUCT = "exchange_product" //拉比代金券兑换商品
  32. BALANCE_SOURCE_EXCHANGE_PRODUCT_NAME = "兑换商品"
  33. BALANCE_SOURCE_ALL_REFUNDED = "all_refunded"
  34. BALANCE_SOURCE_ALL_REFUNDED_NAME = "全额退款"
  35. BALANCE_SOURCE_PART_REFUNDED = "part_refunded"
  36. BALANCE_SOURCE_PART_REFUNDED_NAME = "部分退款"
  37. SHOP_APPYCATION = "shop_applycation"
  38. SHOP_APPYCATION_NAME = "店铺申请"
  39. BALANCE_FREND_BUY = "frend_buy"
  40. BALANCE_FREND_BUY_NAME = "群员购物"
  41. BALANCE_SOURCE_DEDUCT = "deduct"
  42. BALANCE_SOURCE_DEDUCT_NAME = "扣除"
  43. PAY_WAY_TYPE_SERVICE_WXPAY = "service_wxpay"
  44. )
  45. type Balance struct {
  46. Id int64 `orm:"column(id);pk" json:"id"` // int(11)
  47. UserId int64 `orm:"column(user_id);null" json:"user_id"` // int(11)
  48. WxUserId int64 `orm:"column(wx_user_id);null" json:"wx_user_id"` // int(11)
  49. Count int64 `orm:"column(count);null" json:"count"` // int(11)
  50. Source string `orm:"column(source);null" json:"source"` // varchar(20)
  51. SourceName string `orm:"-" json:"source_name"` // varchar(20)
  52. RelateId string `orm:"column(relate_id);null" json:"relate_id"` // varchar(255)
  53. Remark string `orm:"column(remark);null" json:"remark"` // varchar(255)
  54. CreatedAt time.Time `orm:"column(created_at);auto_now_add;type(datetime)" json:"-"` // datetime
  55. CTime int64 `orm:"-" json:"ctime"` // datetime
  56. UpdatedAt time.Time `orm:"column(updated_at);auto_now;type(datetime)" json:"-"` // datetime
  57. }
  58. func (self *Balance) TableName() string {
  59. return balances_tablename
  60. }
  61. type BalanceOrder struct {
  62. Id int64 `orm:"column(id);pk" json:"id"` // int(11)
  63. OrderId string `orm:"column(order_id)" json:"order_id"` // varchar(64)
  64. UserId int64 `orm:"column(user_id)" json:"user_id"` // int(11)
  65. WxUserId int64 `orm:"column(wx_user_id);null" json:"wx_user_id"` // int(11)
  66. PayWay string `orm:"column(pay_way);null" json:"pay_way"` // varchar(20)
  67. TradeNo string `orm:"column(trade_no);null" json:"-"` // varchar(64)
  68. PaiedAt int64 `orm:"column(paied_at);null" json:"paied_at"` // datetime
  69. TotalPrice int64 `orm:"column(total_price);null" json:"total_price"` // int(11)
  70. PaiedPrice int64 `orm:"column(paied_price);null" json:"paied_price"` // int(11)
  71. State int64 `orm:"column(state);null" json:"state"` // tinyint(1)
  72. Remark string `orm:"column(remark);null" json:"remark"` // varchar(64)
  73. CreatedAt time.Time `orm:"column(created_at);auto_now_add;type(datetime)" json:"-"` // datetime
  74. UpdatedAt time.Time `orm:"column(updated_at);auto_now;type(datetime)" json:"-"` // datetime
  75. BalanceBankCardNo string `orm:"column(balance_bank_card_no);null" json:"balance_bank_card_no"`
  76. // 该字段是给连连支付认证支付时,卡前置存银行卡号用的
  77. BankCard string `orm:"-" json:"bank_card"` // datetime
  78. }
  79. func (self *BalanceOrder) TableName() string {
  80. return balance_orders_tablename
  81. }
  82. func (self *Balance) Create(wxUId, uId, c int64, s, rId, remark string) (item *Balance) {
  83. item = &Balance{
  84. Count: c,
  85. WxUserId: wxUId,
  86. UserId: uId,
  87. Source: s,
  88. RelateId: rId,
  89. Remark: remark,
  90. }
  91. id, err := orm.NewOrm().Insert(item)
  92. if err != nil {
  93. beego.BeeLogger.Error("Create Balance err=[%s]", err)
  94. return nil
  95. }
  96. item.Id = id
  97. return item
  98. }
  99. //返回source名称
  100. func (self *Balance) GetSourceName() string {
  101. sourceName := ""
  102. switch self.Source {
  103. case BALANCE_SOURCE_RECHARGE:
  104. sourceName = BALANCE_SOURCE_RECHARGE_NAME
  105. case BALANCE_SOURCE_PLATFORM_EXCHANGE:
  106. sourceName = BALANCE_SOURCE_PLATFORM_EXCHANGE_NAME
  107. case BALANCE_SOURCE_EXCHANGE_PRODUCT:
  108. sourceName = BALANCE_SOURCE_EXCHANGE_PRODUCT_NAME
  109. case BALANCE_SOURCE_ALL_REFUNDED:
  110. sourceName = BALANCE_SOURCE_ALL_REFUNDED_NAME
  111. case BALANCE_SOURCE_PART_REFUNDED:
  112. sourceName = BALANCE_SOURCE_PART_REFUNDED_NAME
  113. case BALANCE_SOURCE_DEDUCT:
  114. sourceName = BALANCE_SOURCE_DEDUCT_NAME
  115. case BALANCE_FREND_BUY:
  116. sourceName = BALANCE_FREND_BUY_NAME
  117. case SHOP_APPYCATION:
  118. sourceName = SHOP_APPYCATION_NAME
  119. }
  120. return sourceName
  121. }
  122. func GetBalanceById(id int64) *Balance {
  123. item := &Balance{}
  124. if err := orm.NewOrm().QueryTable(item).
  125. Filter("id", id).Limit(1).
  126. One(item); err != nil {
  127. beego.BeeLogger.Debug("GetBalanceById(%s), err=%s",
  128. id, err)
  129. return nil
  130. }
  131. return item
  132. }
  133. //获取某人的现金流列表
  134. func GetBalanceListByWxUId(wxUId, page, perPage int64, useCache bool) (list []*Balance) {
  135. k := fmt.Sprintf("balance_model.GetBalanceList.wxUId(%d).page(%d).perPage(%d)", wxUId, page, perPage)
  136. if useCache {
  137. if s, ok := cache.Cache.Get(k).([]*Balance); ok {
  138. return s
  139. }
  140. }
  141. balance := new(Balance)
  142. qs := orm.NewOrm().QueryTable(balance)
  143. qs = qs.Filter("wx_user_id", wxUId)
  144. if _, err := qs.OrderBy("-created_at", "-id").
  145. Limit(perPage, (page-1)*perPage).All(&list); err != nil {
  146. beego.BeeLogger.Debug("get balance with wxUId=%d, err=[%s]", wxUId, err)
  147. return nil
  148. }
  149. cache.Cache.Put(k, list, 10*time.Minute)
  150. return list
  151. }
  152. //获取某人的现金流列表总条数
  153. func GetBalanceCountByWxUId(wxUId int64) int64 {
  154. item := new(Balance)
  155. o := orm.NewOrm()
  156. count, _ := o.QueryTable(item).Filter("wx_user_id", wxUId).Count()
  157. return count
  158. }
  159. //获取某个用户的余额
  160. func GetUserTotalBalance(wxUId int64) int64 {
  161. type Ret struct {
  162. Count int64
  163. }
  164. ret := &Ret{}
  165. o := orm.NewOrm()
  166. tbn := new(Balance).TableName()
  167. sql := fmt.Sprintf("SELECT sum(`count`) as count FROM `%s` WHERE wx_user_id=?;", tbn)
  168. err := o.Raw(sql, wxUId).QueryRow(ret)
  169. if err != nil {
  170. beego.BeeLogger.Error("get user=[%d] total balance err=[%s]", wxUId, err)
  171. return 0
  172. }
  173. if ret.Count < 0 {
  174. return 0
  175. }
  176. return ret.Count
  177. }
  178. //获取某个source累计余额
  179. func GetBalanceCountBySource(wxUId int64, source string) int64 {
  180. type Ret struct {
  181. Count int64
  182. }
  183. ret := &Ret{}
  184. o := orm.NewOrm()
  185. tbn := new(Balance).TableName()
  186. sql := fmt.Sprintf("SELECT sum(`count`) as count FROM `%s` WHERE wx_user_id=? and source=?", tbn)
  187. err := o.Raw(sql, wxUId, source).QueryRow(ret)
  188. if err != nil {
  189. beego.BeeLogger.Error("get user=[%d] total balance err=[%s]", wxUId, err)
  190. return 0
  191. }
  192. if ret.Count < 0 {
  193. return 0
  194. }
  195. return ret.Count
  196. }
  197. func GetBalanceBySourceAndRId(source, rId string) *Balance {
  198. item := &Balance{}
  199. if err := orm.NewOrm().QueryTable(item).
  200. Filter("source", source).
  201. Filter("relate_id", rId).Limit(1).
  202. One(item); err != nil {
  203. beego.BeeLogger.Info("GetBalanceBySourceAndRId(%s,%s), err=%s",
  204. source, rId, err)
  205. return nil
  206. }
  207. return item
  208. }
  209. func GetBalanceByUIdAndRIdAndSource(uId int64, rId, source string) *Balance {
  210. item := &Balance{}
  211. if err := orm.NewOrm().QueryTable(item).
  212. Filter("user_id", uId).
  213. Filter("source", source).
  214. Filter("relate_id", rId).OrderBy("-created_at").Limit(1).
  215. One(item); err != nil {
  216. beego.BeeLogger.Info("GetBalanceByUIdAndRIdAndSource(%d,%s,%s), err=%s",
  217. uId, rId, source, err)
  218. return nil
  219. }
  220. return item
  221. }
  222. func GetBalanceOrderByOId(oId string, useCache bool) *BalanceOrder {
  223. k := fmt.Sprintf("balance_model.GetBalanceOrderByOId[%s]", oId)
  224. if useCache {
  225. if order, ok := cache.Cache.Get(k).(*BalanceOrder); ok {
  226. return order
  227. }
  228. }
  229. item := &BalanceOrder{}
  230. if err := orm.NewOrm().QueryTable(item).Filter("order_id", oId).Limit(1).
  231. One(item); err != nil {
  232. beego.BeeLogger.Info("GetBalanceOrderByOId(%s), err=%s", oId, err)
  233. return nil
  234. }
  235. cache.Cache.Put(k, item, 5*time.Minute)
  236. return item
  237. }
  238. func GetBuyBalanceByRelateId(rId string, useCache bool) *Balance {
  239. k := fmt.Sprintf("balance_model.GetBuyBalanceByRelateId[%s]", rId)
  240. if useCache {
  241. if order, ok := cache.Cache.Get(k).(*Balance); ok {
  242. return order
  243. }
  244. }
  245. //lt < 0
  246. item := &Balance{}
  247. if err := orm.NewOrm().QueryTable(item).Filter("relate_id", rId).Filter("count__lt", 0).Limit(1).
  248. One(item); err != nil {
  249. beego.BeeLogger.Info("GetBuyBalanceByRelateId(%s), err=%s", rId, err)
  250. return nil
  251. }
  252. cache.Cache.Put(k, item, 5*time.Minute)
  253. return item
  254. }
  255. func GetRefundBalanceByRelateId(rId string, useCache bool) *Balance {
  256. k := fmt.Sprintf("balance_model.GetRefundBalanceByRelateId[%s]", rId)
  257. if useCache {
  258. if order, ok := cache.Cache.Get(k).(*Balance); ok {
  259. return order
  260. }
  261. }
  262. //gt > 0
  263. item := &Balance{}
  264. if err := orm.NewOrm().QueryTable(item).Filter("relate_id", rId).Filter("count__gt", 0).Limit(1).
  265. One(item); err != nil {
  266. beego.BeeLogger.Info("GetRefundBalanceByRelateId(%s), err=%s", rId, err)
  267. return nil
  268. }
  269. cache.Cache.Put(k, item, 5*time.Minute)
  270. return item
  271. }
  272. // 获取订单号前缀
  273. func (self *BalanceOrder) GetOrderIdPrefix() string {
  274. s := strings.Split(self.OrderId, "")
  275. prefix := fmt.Sprintf("%s%s", s[0], s[1])
  276. return prefix
  277. }
  278. //生成订单ID
  279. func createOrderId(prefix string) string {
  280. if prefix == "" {
  281. return ""
  282. }
  283. n := time.Now().Format("20060102")
  284. u := uuid.NewV4().String()
  285. c := strings.Split(u, "-")
  286. oId := strings.ToUpper(fmt.Sprintf("%s%s%s", prefix, n, c[0]))
  287. return oId
  288. }
  289. func (self *BalanceOrder) Create(wxUId, uId, tp, paidPrice int64, payway string) (item *BalanceOrder) {
  290. oId := createOrderId(ORDER_ID_PREFIX_CZ)
  291. item = &BalanceOrder{
  292. OrderId: oId,
  293. WxUserId: wxUId,
  294. UserId: uId,
  295. PayWay: payway,
  296. TotalPrice: tp,
  297. PaiedPrice: paidPrice,
  298. Remark: "充值",
  299. }
  300. id, err := orm.NewOrm().Insert(item)
  301. if err != nil {
  302. beego.BeeLogger.Error("Create BalanceOrder err=[%s]", err)
  303. return nil
  304. }
  305. item.Id = id
  306. return item
  307. }
  308. func (self *Balance) Save() error {
  309. _, err := orm.NewOrm().Update(self)
  310. if err != nil {
  311. beego.BeeLogger.Error("Save Balance id=[%d] .err=[%s]", self.Id, err)
  312. }
  313. return err
  314. }
  315. func (self *BalanceOrder) Save() error {
  316. _, err := orm.NewOrm().Update(self)
  317. if err != nil {
  318. beego.BeeLogger.Error("Save BalanceOrder id=[%d] .err=[%s]", self.Id, err)
  319. }
  320. return err
  321. }