package model import ( "errors" "fmt" "github.com/codinl/go-logger" "github.com/jinzhu/gorm" "math/rand" "qiniupkg.com/x/log.v7" "time" ) const ( OrderCardStatusUnPick = 1 // 待取货中 OrderCardStatusPlaying = 2 // 游玩中 OrderCardStatusReturning = 3 // 归还中 OrderCardStatusCompleted = 4 // 已完成 OrderCardStatusCancel = 5 // 已取消 OrderCardStatusRefund = 6 // 已退款 DeliveryTypeStorePick = 1 // 门店取货 DeliveryTypeExpress = 2 // 快递取货 ExpressFeeProvince = 10 * 100 // 省内 ExpressFeeOutsideProvince = 15 * 100 // 省外 PayStatusUnPay = 1 // 未支付 PayStatusPaid = 2 // 已支付 ) //go:generate goqueryset -in order.go // gen:qs type Order struct { Model Uid uint64 `json:"uid" gorm:"index"` GameCardId uint64 `json:"game_card_id" gorm:"index"` // 游戏id GameCardGoodsId uint64 `json:"game_card_goods_id" gorm:"index"` // 游戏卡id StoreId uint64 `json:"store_id"` // 门店id UserAddressId uint64 `json:"user_address_id"` // 地址id DeliveryType uint8 `json:"delivery_type"` // 取货类型 1-门店自取 2-快递 Count uint32 `json:"count"` // 数量 PickupCode string `json:"pickup_code"` // 取货码 CardStatus uint8 `json:"card_status"` // 1-待取货中 2-游玩中 3-归还中 4-已完成 5-已取消 DeliveryTime time.Time `json:"delivery_time"` // 发货时间 ReceiptTime time.Time `json:"receipt_time"` // 收货时间 PayTime time.Time `json:"pay_time"` // 支付时间 PayStatus uint8 `json:"pay_status"` // 支付状态 1-未支付 2-已支付 OrderSn string `json:"order_sn" gorm:"type:varchar(255);not null;COMMENT:'订单编号'"` // 订单编号 PayPrice uint32 `json:"pay_price"` // 实际付款金额(包含运费) Postage uint32 `json:"postage"` // 邮费 ExpressCompany string `json:"express_company"` // 物流公司 ExpressCompanyNo string `json:"express_company_no"` // 物流公司编号 ExpressNo string `json:"express_no"` // 物流单号 ExpressDuration uint64 `json:"express_duration"` // 物流时长 RevertStoreId uint64 `json:"revert_store_id"` // 归还门店id RevertTime time.Time `json:"revert_time"` // 归还时间 RevertExpressCompany string `json:"revert_express_company"` // 归还物流公司 RevertExpressCompanyNo string `json:"revert_express_company_no"` // 归还物流公司编号 RevertExpressNo string `json:"revert_express_no"` // 归还物流单号 RevertExpressDuration uint64 `json:"revert_express_duration"` // 归还物流时长 OutTradeNo string `json:"out_trade_no"` // 支付订单 Mchid string `json:"mchid"` // 商户 } type OrderCard struct { Model OrderId uint32 `json:"order_id" gorm:"index"` Uid uint32 `json:"uid" gorm:"index"` GameCardId uint32 `json:"game_card_id" gorm:"index"` // 游戏id GameCardGoodsId uint32 `json:"game_card_goods_id" gorm:"index"` // 游戏卡id StoreId uint32 `json:"store_id" gorm:"index"` // 门店id Status uint8 `json:"status" gorm:"index"` // 1-待领取 2-游玩中 3-已归还 4-未领取 } func (*Order) TableName() string { return "order" } func (m *Order) ToInfo(card *GameCard) OrderInfo { return OrderInfo{ Order: *m, GameName: card.Name, GamePrice: card.Price, GameCoverImg: card.CoverImg, } } type OrderInfo struct { Order GameName string `json:"name" gorm:"index"` // 名称 GamePrice uint32 `json:"price" gorm:"index"` // 价格 GameCoverImg string `json:"cover_img"` // 封面 } func GetOrderList(uid uint64, page, pageSize int) ([]OrderInfo, uint32, error) { var ( orders []Order totalPage uint32 orderInfos = make([]OrderInfo, 0, pageSize) ) page -= 1 if page < 0 { page = 0 } //oq := NewOrderQuerySet(DB).UidEq(uid).OrderDescByCreatedAt().PayStatusEq(PayStatusPaid) oq := NewOrderQuerySet(DB).UidEq(uid).OrderDescByCreatedAt() count, err := oq.Count() if err != nil { log.Error("NewGameCardQuerySet err:", err) return orderInfos, 0, err } err = oq.Offset(page * pageSize).Limit(pageSize).All(&orders) if err != nil && err != RecordNotFound { log.Error("err:", err) return orderInfos, 0, err } totalPage = uint32(count/pageSize + 1) var games []GameCard gameIds := make([]uint32, 0, len(orders)) for i, _ := range orders { gameIds = append(gameIds, uint32(orders[i].GameCardId)) } if len(gameIds) == 0 { log.Error("gameIds is null") return orderInfos, 0, err } err = NewGameCardQuerySet(DB).IDIn(gameIds...).All(&games) if err != nil && err != RecordNotFound { log.Error("err:", err) return orderInfos, 0, err } gamesMap := make(map[uint32]*GameCard) for i, _ := range games { gamesMap[games[i].ID] = &games[i] } for i, _ := range orders { card, ok := gamesMap[uint32(orders[i].GameCardId)] if !ok { continue } orderInfos = append(orderInfos, orders[i].ToInfo(card)) } return orderInfos, totalPage, nil } func (m *Order) Info() (*OrderInfo, error) { var ( order Order card GameCard ) err := NewOrderQuerySet(DB).IDEq(m.ID).One(&order) if err != nil { log.Error("err:", err) return nil, err } err = NewGameCardQuerySet(DB).IDEq(uint32(order.GameCardId)).One(&card) if err != nil && err != RecordNotFound { log.Error("err:", err) return nil, err } info := order.ToInfo(&card) return &info, nil } func (m *Order) Revert() (*OrderInfo, error) { var ( order Order card GameCard ) qs := NewOrderQuerySet(DB).IDEq(m.ID) err := qs.One(&order) if err != nil { logger.Errorf("err:%#v", err) return nil, err } if order.CardStatus == OrderCardStatusCompleted { logger.Error("order card status completed") return nil, errors.New("order card status completed") } err = qs.GetUpdater(). SetCardStatus(OrderCardStatusReturning). SetRevertTime(time.Now()). SetRevertStoreId(m.RevertStoreId). SetRevertExpressCompany(m.RevertExpressCompany). SetRevertExpressCompanyNo(m.RevertExpressCompanyNo). SetRevertExpressNo(m.RevertExpressNo).Update() if err != nil { log.Error("err:", err) return nil, err } order.CardStatus = OrderCardStatusReturning order.RevertTime = time.Now() order.RevertStoreId = m.RevertStoreId order.RevertExpressCompany = m.RevertExpressCompany order.RevertExpressCompanyNo = m.RevertExpressCompanyNo order.RevertExpressNo = m.RevertExpressNo //err = NewGameCardQuerySet(DB).IDEq(uint32(order.GameCardId)).One(&card) //if err != nil && err != RecordNotFound { // log.Error("err:", err) // return nil, err //} info := order.ToInfo(&card) return &info, nil } func (m *Order) RevertCancel() (*OrderInfo, error) { var ( order Order card GameCard ) qs := NewOrderQuerySet(DB).IDEq(m.ID) err := qs.One(&order) if err != nil { logger.Errorf("err:%#v", err) return nil, err } if order.CardStatus != OrderCardStatusReturning { logger.Error("order card status completed") return nil, errors.New("order card status completed") } err = qs.GetUpdater(). SetCardStatus(OrderCardStatusPlaying). SetRevertStoreId(0). SetRevertExpressCompany(""). SetRevertExpressCompanyNo(""). SetRevertExpressNo("").Update() if err != nil { log.Error("err:", err) return nil, err } order.CardStatus = OrderCardStatusPlaying //order.RevertTime = time.Now() order.RevertStoreId = m.RevertStoreId order.RevertExpressCompany = m.RevertExpressCompany order.RevertExpressCompanyNo = m.RevertExpressCompanyNo order.RevertExpressNo = m.RevertExpressNo info := order.ToInfo(&card) return &info, nil } func (m *Order) OrderCreate() error { err := m.Create(DB) if err != nil { log.Error("err:", err) return err } return nil } func (m *Order) Modify() (*OrderInfo, error) { if m.ID == 0 { return nil, errors.New("orderId is null") } fields := make([]OrderDBSchemaField, 0) if m.CardStatus != 0 { fields = append(fields, OrderDBSchema.CardStatus) } if len(fields) > 0 { err := m.Update(DB.Where(&Order{Model: Model{ID: m.ID}, Uid: m.Uid}), fields...) if err != nil { logger.Error("err:", err) return nil, err } } var card GameCard err := NewGameCardQuerySet(DB).IDEq(uint32(m.GameCardId)).One(&card) if err != nil && err != RecordNotFound { log.Error("err:", err) return nil, err } info := m.ToInfo(&card) return &info, nil } func IsHaveUnreturnedOrders(uid uint32) (bool, error) { fmt.Println("uid", uid) sql := fmt.Sprintf("SELECT COUNT(*) AS count FROM `order` WHERE uid = %d AND pay_status=2 AND card_status IN (1,2,3) ;", uid) //count, err := NewOrderQuerySet(DB).UidEq(uint64(uid)).PayStatusEq(PayStatusPaid).CardStatusIn(1, 2, 3).Count() //if err != nil { // logger.Error("err:", err) // return false, err //} unreturned := &struct { Count int `json:"count"` }{} DB.Raw(sql).Scan(unreturned) fmt.Println("订单数量count:", unreturned.Count) return unreturned.Count != 0, nil } func IsUserHaveUnreturnedOrder(uid uint32) (bool, error) { fmt.Println("uid", uid) sql := fmt.Sprintf("SELECT COUNT(*) AS count FROM `order` WHERE uid = %d AND pay_status IN (1,2) AND card_status IN (1,2,3) ;", uid) //count, err := NewOrderQuerySet(DB).UidEq(uint64(uid)).PayStatusEq(PayStatusPaid).CardStatusIn(1, 2, 3).Count() //if err != nil { // logger.Error("err:", err) // return false, err //} unreturned := &struct { Count int `json:"count"` }{} DB.Raw(sql).Scan(unreturned) fmt.Println("订单数量count:", unreturned.Count) return unreturned.Count != 0, nil } // gen:qs type ExpressCompany struct { Model CompanyName string `json:"company_name"` CompanyCode string `json:"company_code"` } func (*ExpressCompany) TableName() string { return "express_company" } func (*ExpressCompany) List() ([]ExpressCompany, error) { companys := make([]ExpressCompany, 0) err := NewExpressCompanyQuerySet(DB).OrderAscByID().All(&companys) if err != nil && err != RecordNotFound { logger.Error("err:", err) return companys, err } return companys, nil } func GetPickupCode() string { for { rand.Seed(time.Now().UnixNano()) code := fmt.Sprintf("%d", rand.Intn(1000000)+100000) count, err := NewOrderQuerySet(DB).PickupCodeEq(code).Count() if err != nil { logger.Error("err:", err) } if count == 0 { return code } } //将时间戳设置成种子数 } func (m *Order) Cancel() error { var userOrder Order err := NewOrderQuerySet(DB).IDEq(m.ID).One(&userOrder) if err != nil { log.Error("err:", err) return err } if userOrder.CardStatus != OrderCardStatusUnPick { log.Error("card status not unpick err: ") return errors.New("card status not unpick") } if userOrder.PayStatus == PayStatusUnPay && userOrder.CreatedAt.Add(30*time.Minute).Before(time.Now()) { //if userOrder.PayStatus == PayStatusUnPay && userOrder.CreatedAt.Add(3*time.Minute).Before(time.Now()) { log.Error("card status expire err: ") return errors.New("card status expire") } //fmt.Println("PayStatus",userOrder.PayStatus) //fmt.Println("DeliveryType",userOrder.DeliveryType) //fmt.Println("CreatedAt",userOrder.CreatedAt.Add(4*time.Minute)) //fmt.Println("Now",time.Now()) if userOrder.PayStatus == PayStatusPaid && userOrder.DeliveryType == DeliveryTypeStorePick && userOrder.CreatedAt.Add(24*time.Hour).Before(time.Now()) { //if userOrder.PayStatus == PayStatusPaid && userOrder.DeliveryType == DeliveryTypeStorePick && userOrder.CreatedAt.Add(4*time.Minute).Before(time.Now()) { log.Error("card status expire err: ") return errors.New("card status expire") } begin := DB.Begin() err = NewOrderQuerySet(begin).IDEq(m.ID).GetUpdater().SetCardStatus(OrderCardStatusCancel).Update() if err != nil { begin.Rollback() log.Error("err:", err) return err } sql := fmt.Sprintf("UPDATE game_card_goods_stock SET rent_stock= rent_stock+1 WHERE store_id=%d AND game_card_id=%d;", userOrder.StoreId, userOrder.GameCardId) fmt.Println("sql:", sql) err = begin.Exec(sql).Error if err != nil { begin.Rollback() logger.Errorf("err:%#v", err) return err } err = begin.Commit().Error if err != nil { begin.Rollback() logger.Errorf("err:%#v", err) return err } *m = userOrder return nil } func UnPayOrderSetCancel(uid uint32) { fmt.Println("uid:", uid) var order Order err := NewOrderQuerySet(DB.Debug()).UidEq(uint64(uid)).PayStatusEq(PayStatusUnPay).CardStatusEq(OrderCardStatusUnPick).One(&order) if err != nil { log.Error("err:", err) return } fmt.Println("Order:", order) begin := DB.Begin() _, err = NewOrderQuerySet(begin).IDEq(order.ID).GetUpdater(). SetCardStatus(OrderCardStatusCancel).UpdateNum() if err != nil { begin.Rollback() log.Error("err:", err) return } sql := fmt.Sprintf("UPDATE game_card_goods_stock SET rent_stock= rent_stock+1 WHERE store_id=%d AND game_card_id=%d;", order.StoreId, order.GameCardId) fmt.Println("sql:", sql) err = begin.Exec(sql).Error if err != nil { begin.Rollback() log.Error("err:", err) return } err = begin.Commit().Error if err != nil { begin.Rollback() log.Error("err:", err) } } func (m *Order) CreateByCardInfoList(cardInfos []CardInfo, gdb *gorm.DB) error { err := gdb.Create(m).Error if err != nil { log.Error("err:", err) return err } if m.ID == 0 { return errors.New("order id is 0") } for _, v := range cardInfos { for i := 0; i < int(v.Count); i++ { //OrderCard{ // OrderId: m.ID, // Uid: uint32(m.Uid), // GameCardId: v.GameCardId, // GameCardGoodsId: 0, // StoreId: uint32(m.StoreId), // Status: 0, //} } } return nil }