123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285 |
- package dao
- import (
- "context"
- "fmt"
- "github.com/jinzhu/gorm"
- "go-common/app/admin/main/growup/dao/shell"
- "go-common/app/admin/main/growup/model/offlineactivity"
- "go-common/app/admin/main/up/util"
- "go-common/library/log"
- "strconv"
- "strings"
- )
- func generateDelimiter(delimiter string) func(r rune) bool {
- return func(r rune) bool {
- for _, v := range delimiter {
- if v == r {
- return true
- }
- }
- return false
- }
- }
- const (
- trimSet = "\r\n "
- )
- func strlistToInt64List(list []string, trimSet string) (result []int64) {
- for _, v := range list {
- mid, e := strconv.ParseInt(strings.Trim(v, trimSet), 10, 64)
- if e != nil {
- continue
- }
- result = append(result, mid)
- }
- return
- }
- func trimString(strlist []string, trimset string) (result []string) {
- for _, v := range strlist {
- var trimed = strings.Trim(v, trimSet)
- if trimed == "" {
- continue
- }
- result = append(result, trimed)
- }
- return
- }
- //ParseMidsFromString parse []int64 from string
- func ParseMidsFromString(str string) (result []int64) {
- var midstrlist = trimString(strings.FieldsFunc(str, generateDelimiter(",\r\n")), trimSet)
- result = util.Unique(strlistToInt64List(midstrlist, trimSet))
- return
- }
- //OfflineActivityAddActivity add acitvity
- func (d *Dao) OfflineActivityAddActivity(ctx context.Context, arg *offlineactivity.AddActivityArg) (err error) {
- var activityInfo = offlineactivity.OfflineActivityInfo{
- Title: arg.Title,
- Link: arg.Link,
- BonusType: arg.BonusType,
- Memo: arg.Memo,
- State: int8(offlineactivity.ActivityStateInit),
- Creator: arg.Creator,
- }
- var bonusList = arg.BonusList
- var hasBonus = false
- for _, bonus := range bonusList {
- if bonus.TotalMoney <= 0 {
- err = fmt.Errorf("bonus money < 0, money=%f", bonus.TotalMoney)
- log.Error(err.Error())
- return
- }
- bonus.MidList = ParseMidsFromString(bonus.Mids)
- bonus.MemberCount = int64(len(bonus.MidList))
- if bonus.MemberCount == 0 {
- log.Warn("no mid for this bonus, bonus:money=%.2f", bonus.TotalMoney)
- continue
- }
- hasBonus = true
- log.Info("bonus info:money=%.2f, membercount=%d", bonus.TotalMoney/1000, bonus.MemberCount)
- }
- // 如果一个bonus都没有,则什么也不做
- if !hasBonus {
- log.Error("no bonus")
- err = fmt.Errorf("no bonus info")
- return
- }
- if err = d.db.Create(&activityInfo).Error; err != nil {
- log.Error("err insert offline activity, err=%s", err)
- return
- }
- var tx = d.db.Begin()
- defer func() {
- if r := recover(); r != nil || err != nil {
- tx.Rollback()
- activityInfo.State = int8(offlineactivity.ActivityStateCreateFail)
- if err = d.db.Select("state").Save(&activityInfo).Error; err != nil {
- log.Error("err update offline activity, err=%s", err)
- return
- }
- }
- }()
- // create
- for _, bonus := range bonusList {
- if bonus.MemberCount <= 0 {
- continue
- }
- // 插入OfflineActivityBonus
- //if activityInfo.BonusType == offlineactivity.BonusTypeMoney {
- bonusMoney := offlineactivity.GetMoneyForDb(bonus.TotalMoney)
- //}
- var bonusInfo = offlineactivity.OfflineActivityBonus{
- TotalMoney: bonusMoney,
- MemberCount: uint32(bonus.MemberCount),
- State: int8(offlineactivity.BonusStateInit),
- ActivityID: activityInfo.ID,
- }
- if err = tx.Create(&bonusInfo).Error; err != nil {
- log.Error("err insert offline activity bonus, err=%s", err)
- return
- }
- // 插入OfflineActivityResult
- var insertSchema []string
- var vals []interface{}
- var dbmoney = bonusInfo.TotalMoney / int64(bonusInfo.MemberCount)
- for _, mid := range bonus.MidList {
- insertSchema = append(insertSchema, "(?,?,?,?,?)")
- vals = append(vals, activityInfo.ID, bonusInfo.ID, activityInfo.BonusType, mid, dbmoney)
- }
- var insertPre = "insert into offline_activity_result (activity_id, bonus_id, bonus_type, mid, bonus_money) values "
- var insertSQL = insertPre + strings.Join(insertSchema, ",")
- if err = tx.Table(offlineactivity.TableOfflineActivityResult).Exec(insertSQL, vals...).Error; err != nil {
- log.Error("err insert offline activity result, err=%s", err)
- return
- }
- }
- activityInfo.State = int8(offlineactivity.ActivityStateSending)
- if arg.BonusType == int8(offlineactivity.BonusTypeThing) {
- activityInfo.State = int8(offlineactivity.ActivityStateSucess)
- }
- if err = tx.Select("state").Save(&activityInfo).Error; err != nil {
- log.Error("err update offline activity, err=%s", err)
- return
- }
- return tx.Commit().Error
- }
- //ShellCallbackUpdate shell callback
- func (d *Dao) ShellCallbackUpdate(ctx context.Context, result *shell.OrderCallbackJSON, msgid string) (orderInfo offlineactivity.OfflineActivityShellOrder, err error) {
- // 找到order info, 写入结果
- var stateResult = offlineactivity.ActivityStateWaitResult
- if result.IsSuccess() {
- stateResult = offlineactivity.ActivityStateSucess
- } else if result.IsFail() {
- stateResult = offlineactivity.ActivityStateFail
- }
- if err = d.db.Where("order_id=?", result.ThirdOrderNo).Find(&orderInfo).Error; err != nil {
- log.Error("order id=%s, find order id fail, err=%s", result.ThirdOrderNo, err)
- return
- }
- var tx = d.db.Begin()
- defer func() {
- if r := recover(); r != nil || err != nil {
- tx.Rollback()
- }
- }()
- if err = tx.Table(offlineactivity.TableOfflineActivityShellOrder).
- Where("id=?", orderInfo.ID).
- Update("order_status", result.Status).
- Error; err != nil {
- log.Error("order id=%s, update order fail, err=%s", result.ThirdOrderNo, err)
- return
- }
- if err = tx.Table(offlineactivity.TableOfflineActivityResult).
- Where("id=?", orderInfo.ResultID).
- Update("state", stateResult).
- Error; err != nil {
- log.Error("order id=%s, update result fail, err=%s", result.ThirdOrderNo, err)
- return
- }
- log.Info("order id=%s, shell callback, success, mid=%s, status=%s", result.ThirdOrderNo, result.Mid, result.Status)
- err = tx.Commit().Error
- return
- }
- //OfflineActivityGetUpBonusResult Up主所有Activity一起统计
- func (d *Dao) OfflineActivityGetUpBonusResult(ctx context.Context, needCount bool, limit, offset int, query string, args ...interface{}) (upResult []*offlineactivity.OfflineActivityResult, totalCount int, err error) {
- // 查询所有的 result for mid
- // 区分已结算、未结算
- // 已结算= 成功, 未结算= 初始、发送、等待
- if needCount {
- if err = d.db.Table(offlineactivity.TableOfflineActivityResult).Where(query, args...).Count(&totalCount).Error; err != nil {
- log.Error("fail to get from db, err=%s", err)
- return
- }
- }
- if err = d.db.Where(query, args...).Limit(limit).Offset(offset).Find(&upResult).Error; err != nil {
- log.Error("fail to get from db, err=%s", err)
- return
- }
- return
- }
- //OfflineActivityGetUpBonusResultSelect select by selection
- func (d *Dao) OfflineActivityGetUpBonusResultSelect(ctx context.Context, selectQuery string, query string, args ...interface{}) (upResult []*offlineactivity.OfflineActivityResult, err error) {
- if err = d.db.Where(query, args...).Select(selectQuery).Find(&upResult).Error; err != nil {
- log.Error("fail to get from db, err=%s", err)
- return
- }
- return
- }
- //OfflineActivityGetUpBonusByActivityResult 根据Activity来分别统计
- func (d *Dao) OfflineActivityGetUpBonusByActivityResult(ctx context.Context, limit, offset int, mid int64) (upResult []*offlineactivity.OfflineActivityResult, totalCount int, err error) {
- // 查询所有的 result for mid
- // 区分已结算、未结算
- // 已结算= 成功, 未结算= 初始、发送、等待
- var actividyIds []struct {
- ActivityID int64 `gorm:"column:activity_id"`
- }
- if err = d.db.Table(offlineactivity.TableOfflineActivityResult).Select("count(distinct(activity_id))").Where("mid=?", mid).Count(&totalCount).Error; err != nil {
- log.Error("fail to get from db, err=%s", err)
- return
- }
- if err = d.db.Table(offlineactivity.TableOfflineActivityResult).Select("distinct(activity_id)").Where("mid=?", mid).Offset(offset).Limit(limit).Find(&actividyIds).Error; err != nil {
- log.Error("fail to get from db, err=%s", err)
- return
- }
- //totalCount = len(actividyIds)
- var ids []int64
- for i := 0; i < len(actividyIds); i++ {
- ids = append(ids, actividyIds[i].ActivityID)
- }
- if err = d.db.Where("mid=? and activity_id in(?)", mid, ids).Find(&upResult).Error; err != nil {
- log.Error("fail to get from db, err=%s", err)
- return
- }
- return
- }
- //OfflineActivityGetDB get gorm db
- func (d *Dao) OfflineActivityGetDB() *gorm.DB {
- return d.db
- }
- //UpdateActivityState 更新Activity的状态,根据每一个付款记录的状态
- func (d *Dao) UpdateActivityState(ctx context.Context, activityID int64) (affectedRow int64, err error) {
- // 找到所有result中,state最小的一个
- // 更新到activity的状态
- var record offlineactivity.OfflineActivityResult
- if err = d.db.Model(&record).Select("min(state) as state").Where("activity_id=?", activityID).Find(&record).Error; err != nil {
- log.Error("fail to get from db, err=%s", err)
- return
- }
- var db = d.db.Table(offlineactivity.TableOfflineActivityInfo).
- Where("id=? and state<10 and state<?", activityID, record.State).
- Update("state", record.State)
- if err = db.Error; err != nil {
- log.Error("fail to get from db, err=%s", err)
- return
- }
- affectedRow = db.RowsAffected
- if affectedRow > 0 {
- log.Info("update activity state, id=%d, newstate=%d", activityID, record.State)
- } else {
- log.Info("no need to update activity, id=%d, newstate=%d", activityID, record.State)
- }
- return
- }
|