fusenapi/server/inventory/internal/logic/supplementlogic.go

184 lines
6.6 KiB
Go
Raw Normal View History

2023-06-28 09:05:31 +00:00
package logic
import (
"errors"
"fusenapi/constants"
"fusenapi/model/gmodel"
"fusenapi/utils/auth"
"fusenapi/utils/basic"
"fusenapi/utils/format"
"fusenapi/utils/id_generator"
"fusenapi/utils/step_price"
"gorm.io/gorm"
"math"
"strings"
"time"
"context"
"fusenapi/server/inventory/internal/svc"
"fusenapi/server/inventory/internal/types"
"github.com/zeromicro/go-zero/core/logx"
)
type SupplementLogic struct {
logx.Logger
ctx context.Context
svcCtx *svc.ServiceContext
}
func NewSupplementLogic(ctx context.Context, svcCtx *svc.ServiceContext) *SupplementLogic {
return &SupplementLogic{
Logger: logx.WithContext(ctx),
ctx: ctx,
svcCtx: svcCtx,
}
}
func (l *SupplementLogic) Supplement(req *types.SupplementReq, userinfo *auth.UserInfo) (resp *basic.Response) {
if userinfo.GetIdType() != auth.IDTYPE_User {
return resp.SetStatusWithMessage(basic.CodeServiceErr, "please login first")
}
if req.Id <= 0 {
return resp.SetStatusWithMessage(basic.CodeRequestParamsErr, "param id must greater than 0")
}
if req.Num <= 0 {
return resp.SetStatusWithMessage(basic.CodeRequestParamsErr, "param num must greater than 0")
}
//获取云仓数据
stockInfo, err := l.svcCtx.AllModels.FsUserStock.FindOne(l.ctx, req.Id, userinfo.UserId, true)
if err != nil {
if errors.Is(err, gorm.ErrRecordNotFound) {
return resp.SetStatusWithMessage(basic.CodeDbRecordNotFoundErr, "your stock info is not exists")
}
logx.Error(err)
return resp.SetStatusWithMessage(basic.CodeDbSqlErr, "failed to get stock info")
}
//获取订单详细模板数据
orderDetailTemplateInfo, err := l.svcCtx.AllModels.FsOrderDetailTemplate.FindOneBySn(l.ctx, *stockInfo.OrderDetailTemplateSn)
if err != nil {
if errors.Is(err, gorm.ErrRecordNotFound) {
return resp.SetStatusWithMessage(basic.CodeDbRecordNotFoundErr, "order detail template info is not exists")
}
logx.Error(err)
return resp.SetStatusWithMessage(basic.CodeDbSqlErr, "failed to get order detail template info")
}
//获取订单详细数据
orderDetailInfo, err := l.svcCtx.AllModels.FsOrderDetail.FindOneByOrderDetailTemplateId(l.ctx, orderDetailTemplateInfo.Id)
if err != nil {
if errors.Is(err, gorm.ErrRecordNotFound) {
return resp.SetStatusWithMessage(basic.CodeDbRecordNotFoundErr, "order detail info is not exists")
}
logx.Error(err)
return resp.SetStatusWithMessage(basic.CodeDbSqlErr, "failed to get order detail info")
}
//产品价格
productPriceByParamsReq := gmodel.FindOneProductPriceByParamsReq{
ProductId: orderDetailTemplateInfo.ProductId,
}
productPriceInfo, err := l.svcCtx.AllModels.FsProductPrice.FindOneProductPriceByParams(l.ctx, productPriceByParamsReq)
if err != nil {
if errors.Is(err, gorm.ErrRecordNotFound) {
return resp.SetStatusWithMessage(basic.CodeDbRecordNotFoundErr, "product price info is not exists")
}
logx.Error(err)
return resp.SetStatusWithMessage(basic.CodeDbSqlErr, "failed to get product price info")
}
//获取阶梯价格和阶梯数量
stepNum, err := format.StrSlicToIntSlice(strings.Split(*productPriceInfo.StepNum, ","))
if err != nil {
logx.Error(err)
return resp.SetStatusWithMessage(basic.CodeServiceErr, "invalid step num format: "+*productPriceInfo.StepNum)
}
stepPrice, err := format.StrSlicToIntSlice(strings.Split(*productPriceInfo.StepPrice, ","))
if err != nil {
logx.Error(err)
return resp.SetStatusWithMessage(basic.CodeServiceErr, "invalid step price format: "+*productPriceInfo.StepPrice)
}
//附件价格信息
optionalPrice := int64(0)
if *orderDetailInfo.OptionPrice > 0 {
optionalPrice = *orderDetailInfo.OptionPrice
}
//获取总价
minByNum := math.Ceil(float64(req.Num) / float64(*productPriceInfo.EachBoxNum))
amount := step_price.GetCentStepPrice(int(minByNum), stepNum, stepPrice) + optionalPrice
totalAmount := amount * req.Num
newOrderSn := id_generator.GenPickUpTrackNum()
now := time.Now().Unix()
deliveryMethod := int64(constants.DELIVERY_METHOD_CLOUD)
isSup := int64(1)
//生成雪花id
orderDetailTemplateSn, err := id_generator.GenSnowFlakeId()
if err != nil {
logx.Error(err)
return resp.SetStatusWithMessage(basic.CodeServiceErr, "gen order detail template sn err")
}
orderDetailSn, err := id_generator.GenSnowFlakeId()
if err != nil {
logx.Error(err)
return resp.SetStatusWithMessage(basic.CodeServiceErr, "gen order detail sn err")
}
2023-06-28 09:06:26 +00:00
//事务处理数据
2023-06-28 09:05:31 +00:00
err = l.svcCtx.MysqlConn.Transaction(func(tx *gorm.DB) error {
orderModel := gmodel.NewFsOrderModel(tx)
orderDetailModel := gmodel.NewFsOrderDetailModel(tx)
orderDetailTemplateModel := gmodel.NewFsOrderDetailTemplateModel(tx)
//订单创建数据
orderAddData := gmodel.FsOrder{
Sn: &newOrderSn,
UserId: &userinfo.UserId,
TotalAmount: &totalAmount,
Ctime: &now,
Utime: &now,
DeliveryMethod: &deliveryMethod,
IsSup: &isSup,
}
if err = orderModel.Create(l.ctx, &orderAddData); err != nil {
return err
}
//添加订单详情模板数据
orderDetailTemplateAddData := gmodel.FsOrderDetailTemplate{
Sn: &orderDetailTemplateSn,
ProductId: orderDetailTemplateInfo.ProductId,
ModelId: orderDetailTemplateInfo.ModelId,
TemplateId: orderDetailTemplateInfo.TemplateId,
MaterialId: orderDetailTemplateInfo.MaterialId,
SizeId: orderDetailTemplateInfo.SizeId,
EachBoxNum: orderDetailTemplateInfo.EachBoxNum,
EachBoxWeight: orderDetailTemplateInfo.EachBoxWeight,
DesignId: orderDetailTemplateInfo.DesignId,
Ctime: &now,
}
if err = orderDetailTemplateModel.Create(l.ctx, &orderDetailTemplateAddData); err != nil {
return err
}
//添加订单详细数据
factoryId := int64(1)
isCloud := int64(1)
orderDetailAddData := gmodel.FsOrderDetail{
Sn: &orderDetailSn,
OrderId: &orderAddData.Id,
UserId: &userinfo.UserId,
FactoryId: &factoryId,
OrderDetailTemplateId: &orderDetailTemplateAddData.Id,
ProductId: orderDetailTemplateInfo.ProductId,
BuyNum: &req.Num,
Amount: &amount,
Cover: orderDetailInfo.Cover,
Ctime: &now,
OptionalId: orderDetailInfo.OptionalId,
OptionalTitle: orderDetailInfo.OptionalTitle,
OptionPrice: orderDetailInfo.OptionPrice,
IsCloud: &isCloud,
}
return orderDetailModel.Create(l.ctx, &orderDetailAddData)
})
if err != nil {
logx.Error(err)
return resp.SetStatusWithMessage(basic.CodeDbSqlErr, "failed to supplement your stock")
}
return resp.SetStatus(basic.CodeOK)
}