diff --git a/apps/services/modules/pay/api.go b/apps/services/modules/pay/api.go index 18c67b1f..2fe1f57b 100644 --- a/apps/services/modules/pay/api.go +++ b/apps/services/modules/pay/api.go @@ -55,20 +55,24 @@ func grantOfAppGoods(g *comm.AppGoods) *goodsGrant { return &goodsGrant{Viptime: g.Viptime, Compute: c} } -// deliverResourceByOrder 按订单给用户发货:商品取自**业务库 goods 表**(历史口径, -// 微信/支付宝/Apple/Google 通知与 verifyorder 都走这条)。 -// 商品对不上时 grant 为 nil:不加资源,但仍走一遍更新与记账,与改造前行为一致。 +// deliverResourceByOrder 按订单给用户发货。商品先对管理后台 app_goods(与充值页同一份), +// 对不上再退回业务库 goods。微信/支付宝/Apple/Google 通知与 verifyorder 都走这条。 +// 两处都对不上时 grant 为 nil:不加资源,但仍走一遍更新与记账。 func (this *apiComp) deliverResourceByOrder(user *pb.DBUser, order *pb.DBPayOrder) (err error) { - var goodss []*pb.DBGoods - // 1. 检查订单状态 if order.Status != pb.PayOrderStatus_PAY_ORDER_PAID { err = fmt.Errorf("订单状态错误,无法下发资源: %v", order.Status) return } - goodss, err = this.module.model.goodss() + goods, err := this.module.model.appGoods(order.ProductId) if err != nil { - err = fmt.Errorf("查询商品信息失败: %v", err) - return + return fmt.Errorf("查询后台商品失败: %v", err) + } + if goods != nil { + return this.deliverGrant(user, order, grantOfAppGoods(goods)) + } + goodss, err := this.module.model.goodss() + if err != nil { + return fmt.Errorf("查询商品信息失败: %v", err) } var grant *goodsGrant for _, v := range goodss { diff --git a/apps/services/modules/pay/api_getgoodss.go b/apps/services/modules/pay/api_getgoodss.go index 58618795..65599ad2 100644 --- a/apps/services/modules/pay/api_getgoodss.go +++ b/apps/services/modules/pay/api_getgoodss.go @@ -7,7 +7,7 @@ import ( ) // @Summary 获取商品列表 -// @Description 获取商品列表 +// @Description 获取商品列表。后台已配置上架商品时返回应用商品配置,否则返回业务库旧商品。 // @Tags Pay // @Accept json // @Produce json @@ -16,29 +16,61 @@ import ( // @Success 200 {object} comm.HttpResult{data=pb.PayGetGoodssResp} "商品列表" // @Router /api/home/pay_getgoodss [post] func (this *apiComp) GetGoodss(session comm.IUserSession, req *pb.PayGetGoodssReq) (resp *pb.PayGetGoodssResp, errdata *pb.ErrorData) { - var ( - allgoodss []*pb.DBGoods - goodss []*pb.DBGoods - err error - ) - allgoodss, err = this.module.model.goodss() + appGoods, err := this.module.model.appGoodss() if err != nil { errdata = &pb.ErrorData{ Code: pb.ErrorCode_DBError, Message: err.Error(), } - this.module.Error("GetGoodss 失败!", log.Field{Key: "uid", Value: session.GetUserId()}, log.Field{Key: "err", Value: err.Error()}) + this.module.Error("GetGoodss 读后台商品失败!", + log.Field{Key: "uid", Value: session.GetUserId()}, + log.Field{Key: "err", Value: err.Error()}) return } - goodss = make([]*pb.DBGoods, 0, len(allgoodss)) - for _, v := range allgoodss { - if v.Enable { - goodss = append(goodss, v) + var legacy []*pb.DBGoods + if !hasEnabledAppGoods(appGoods) { + legacy, err = this.module.model.goodss() + if err != nil { + errdata = &pb.ErrorData{ + Code: pb.ErrorCode_DBError, + Message: err.Error(), + } + this.module.Error("GetGoodss 失败!", log.Field{Key: "uid", Value: session.GetUserId()}, log.Field{Key: "err", Value: err.Error()}) + return } } - resp = &pb.PayGetGoodssResp{ - Goodss: goodss, + Goodss: listedGoods(appGoods, legacy), } return } + +// listedGoods 是客户端充值页实际拿到的列表。 +// 后台「应用商品配置」有上架商品时只用那一份(与 pay_getgoodssv2 同源); +// 一条上架的都没有时,退回业务库 goods,避免还没迁商品的应用充值页被清空。 +func listedGoods(app []*comm.AppGoods, legacy []*pb.DBGoods) []*pb.DBGoods { + out := make([]*pb.DBGoods, 0) + for _, v := range app { + if v != nil && v.Enable { + out = append(out, dbGoodsOfAppGoods(v)) + } + } + if len(out) > 0 { + return out + } + for _, v := range legacy { + if v != nil && v.Enable { + out = append(out, v) + } + } + return out +} + +func hasEnabledAppGoods(app []*comm.AppGoods) bool { + for _, v := range app { + if v != nil && v.Enable { + return true + } + } + return false +} diff --git a/apps/services/modules/pay/api_getgoodss_test.go b/apps/services/modules/pay/api_getgoodss_test.go new file mode 100644 index 00000000..18454e09 --- /dev/null +++ b/apps/services/modules/pay/api_getgoodss_test.go @@ -0,0 +1,32 @@ +package pay + +import ( + "testing" + + "yunyan/comm" + "yunyan/pb" +) + +func TestListedGoodsPrefersEnabledAdminGoods(t *testing.T) { + got := listedGoods([]*comm.AppGoods{ + {GoodsId: "old", Enable: false, Name: "下架"}, + {GoodsId: "vip_month_1", Enable: true, Name: "月度", Price: 990, Usagetype: int32(pb.UsageType_VIP), Viptime: 30}, + }, []*pb.DBGoods{ + {Id: "legacy", Enable: true, Name: "旧商品"}, + }) + if len(got) != 1 || got[0].Id != "vip_month_1" || got[0].Viptime != 30 { + t.Fatalf("应只下发后台已上架商品,实际 %#v", got) + } +} + +func TestListedGoodsFallsBackWhenAdminHasNothingOnShelf(t *testing.T) { + got := listedGoods([]*comm.AppGoods{ + {GoodsId: "draft", Enable: false}, + }, []*pb.DBGoods{ + {Id: "legacy", Enable: true}, + {Id: "off", Enable: false}, + }) + if len(got) != 1 || got[0].Id != "legacy" { + t.Fatalf("后台没有上架商品时应退回业务库已上架商品,实际 %#v", got) + } +} diff --git a/apps/services/modules/pay/api_getgoodss_v2.go b/apps/services/modules/pay/api_getgoodss_v2.go index df37741e..9af02b8e 100644 --- a/apps/services/modules/pay/api_getgoodss_v2.go +++ b/apps/services/modules/pay/api_getgoodss_v2.go @@ -68,5 +68,6 @@ func dbGoodsOfAppGoods(g *comm.AppGoods) *pb.DBGoods { Meetnum: g.Meetnum, Tradenum: g.Tradenum, Viptime: g.Viptime, + Compute: g.Compute, } }