transfer_yl/cmd/api/internal/logic/yl/ylAsyncLogic.go

279 lines
7.3 KiB
Go
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

package yl
import (
"context"
"database/sql"
"encoding/json"
"errors"
"fmt"
"github.com/bytedance/sonic"
"rs/genModel"
"rs/untils/sign"
"rs/cmd/api/internal/logic/vo"
"rs/rpc/transfer"
"rs/untils/httpclient"
"strconv"
"strings"
"time"
"rs/cmd/api/internal/svc"
"rs/cmd/api/internal/types"
"github.com/zeromicro/go-zero/core/logx"
)
type YlAsyncLogic struct {
logx.Logger
ctx context.Context
svcCtx *svc.ServiceContext
}
// 卡密异步发放接口
func NewYlAsyncLogic(ctx context.Context, svcCtx *svc.ServiceContext) *YlAsyncLogic {
return &YlAsyncLogic{
Logger: logx.WithContext(ctx),
ctx: ctx,
svcCtx: svcCtx,
}
}
func (l *YlAsyncLogic) YlAsync(req *types.AsyncReq) (resp *types.AsyncResp, err error) {
var (
reqData transfer.MarketKeySendReq
VoucherId string
supplierOrderNo = req.DeliverOrderNo
result *transfer.MarketKeySendRes
)
defer func() {
var status int64
var msg string
if err != nil {
status = 2
msg = err.Error()
} else {
status = 1
}
// 记录订单
l.saveOrder(req, result, supplierOrderNo, VoucherId, msg, status)
}()
if v, ok := l.svcCtx.Config.MarketConfig.SupplierSkuId[strconv.Itoa(int(req.SupplierSkuId))]; ok {
VoucherId = v
} else {
return nil, fmt.Errorf("供货商sku 未配置")
}
reqData = transfer.MarketKeySendReq{
AppId: l.svcCtx.Config.MarketConfig.AppId,
ReqCode: "voucher.create",
MemId: fmt.Sprintf("%d", req.SupplierId),
ReqSerialNo: req.DeliverOrderNo,
Timestamp: time.Unix(req.CreateTime, 0).Format("20060102150405"),
PosId: l.svcCtx.Config.MarketConfig.PosId,
VoucherId: VoucherId,
VoucherNum: 1,
//MobileNo: extendParam.MobileNo,
//SendMsg: extendParam.SendMsg,
}
if reqData.SendMsg == "" {
reqData.SendMsg = "2"
}
reqData.Sign = l.svcCtx.Config.Sys.PrimaryKey
result, err = l.svcCtx.TransferRpc.MarketKeySend(l.ctx, &reqData)
if err != nil {
return nil, fmt.Errorf("rpc请求失败:%v", err.Error())
}
if result.ErrCode != vo.RES_SUCCESS {
return nil, fmt.Errorf("请求失败:%v", result.Msg)
}
if result.Data == nil {
return nil, fmt.Errorf("请求失败:%v", result.Msg)
}
if result.Data.VoucherCode == "" {
return nil, fmt.Errorf("请求失败未取到数据:%v", result.Msg)
}
// 异步通知
go func() {
time.Sleep(2 * time.Second)
l.asyncSendMarket(supplierOrderNo, req, result.Data)
}()
return &types.AsyncResp{
Msg: "",
Status: 0,
SupplierOrderNo: supplierOrderNo,
}, nil
}
func (l *YlAsyncLogic) getExchangeCode(voucherCode string) string {
if !strings.Contains(voucherCode, "http") {
return voucherCode
}
temp := strings.Split(voucherCode, "/")
return temp[len(temp)-1]
}
// 返回数据,通知下游系统
func (l *YlAsyncLogic) asyncSendMarket(supplierOrderNo string, asyncReq *types.AsyncReq, data *transfer.MarketKeySendRes_Data) {
startTime, err := time.Parse("20060102", data.VoucherSdate)
if err != nil {
startTime = time.Now()
}
endTime, err := time.Parse("20060102", data.VoucherEdate)
if err != nil {
endTime = startTime.AddDate(0, 0, 30).Add(23*time.Hour + 59*time.Minute + 59*time.Second)
}
var (
reqDataMap map[string]interface{}
header = map[string]string{"Content-Type": "application/json;charset=UTF-8"}
targetUrl = l.svcCtx.Config.YouleHost + "/supplier/order/sendResultNotify"
req = &types.NotifyReq{
DeliverOrderNo: asyncReq.DeliverOrderNo,
SupplierOrderNo: supplierOrderNo,
SupplierSkuId: asyncReq.SupplierSkuId,
RequestTime: time.Now().Unix(),
Account: asyncReq.Account,
Status: 1,
Msg: "",
Price: asyncReq.Price,
SupplierId: asyncReq.SupplierId,
CardNo: "",
CardKey: l.getCode(data.VoucherCode),
CardExpireTime: endTime.Add(23*time.Hour + 59*time.Minute + 59*time.Second).Format(time.DateTime),
CardExchangeUrl: data.ShortUrl,
Sign: "",
}
)
b, _ := json.Marshal(req)
err = json.Unmarshal(b, &reqDataMap)
if err != nil {
return
}
req.Sign, err = sign.GetSign(reqDataMap, l.svcCtx.Config.Sys.Key)
if err != nil {
l.Logger.Errorf("签名失败:%v", err.Error())
return
}
body, err := sonic.Marshal(req)
if err != nil {
l.Logger.Errorf("解析json失败:%v", err.Error())
return
}
resp, err := httpclient.FastHttpPost(targetUrl, header, body, 0)
if err != nil {
l.Logger.Errorf("请求失败:%v", err.Error())
return
}
l.Logger.Infof("发货通知完成url=%s,请求数据:%v 请求返回数据:%v", targetUrl, string(body), string(resp))
return
}
// 写入数据
func (l *YlAsyncLogic) saveOrder(req *types.AsyncReq, rsp *transfer.MarketKeySendRes, supplierOrderNo, VoucherId, msg string, status int64) {
// 查询订单
order, err := l.svcCtx.BaseServiceContext.YlOrdersMarketRepo.FindOneByDeliverOrderNoSupplierOrderNo(l.ctx, req.DeliverOrderNo, supplierOrderNo)
if err != nil {
if !errors.Is(err, genModel.ErrNotFound) {
l.Logger.Errorf("supplierOrderNo = %s 查询订单失败:%v", supplierOrderNo, err.Error())
}
}
b, _ := json.Marshal(req)
rp, _ := json.Marshal(rsp)
if order != nil {
// 订单存在,更新
if order.Status != status {
order.Status = status
}
if order.Resp.String != string(rp) {
order.Resp.String = string(rp)
order.Resp.Valid = true
}
if order.Request != string(b) {
order.Request = string(b)
}
if msg != "" {
order.ErrMsg.String += msg
order.ErrMsg.Valid = true
}
if VoucherId != order.VoucherId {
order.VoucherId = VoucherId
}
err = l.svcCtx.BaseServiceContext.YlOrdersMarketRepo.Update(l.ctx, order)
if err != nil {
l.Logger.Errorf("DeliverOrderNo = %s 更新订单失败:%v", order.DeliverOrderNo, err.Error())
}
} else {
// 订单不存在,插入
data := &genModel.YlOrdersMarket{
DeliverOrderNo: req.DeliverOrderNo,
SupplierOrderNo: supplierOrderNo,
Request: string(b),
Resp: sql.NullString{
String: string(rp),
Valid: true,
},
ErrMsg: sql.NullString{
String: msg,
Valid: true,
},
Status: status,
VoucherId: VoucherId,
}
_, err = l.svcCtx.BaseServiceContext.YlOrdersMarketRepo.Insert(l.ctx, data)
if err != nil {
l.Logger.Errorf("data = %s 插入订单失败:%v", data, err.Error())
}
}
}
// 更新状态和响应数据
func (l *YlAsyncLogic) updateOrder(req *types.AsyncReq, rsp *transfer.MarketKeySendRes, supplierOrderNo string, status int64) {
order, err := l.svcCtx.BaseServiceContext.YlOrdersMarketRepo.FindOneByDeliverOrderNoSupplierOrderNo(l.ctx, req.DeliverOrderNo, supplierOrderNo)
if err != nil {
if !errors.Is(err, genModel.ErrNotFound) {
l.Logger.Errorf("data = %s 查询订单失败:%v", order, err.Error())
}
}
if order != nil {
l.Logger.Errorf("DeliverOrderNo = %s 订单已存在", order.DeliverOrderNo)
return
}
r, _ := json.Marshal(rsp)
order.Status = status
order.Resp = sql.NullString{
String: string(r),
Valid: true,
}
err = l.svcCtx.BaseServiceContext.YlOrdersMarketRepo.Update(l.ctx, order)
if err != nil {
l.Logger.Errorf("order = %s 插入订单失败:%v", order, err.Error())
}
}
func (l *YlAsyncLogic) getCode(voucherCode string) string {
if strings.Contains(voucherCode, "http") {
temp := strings.Split(strings.TrimSpace(voucherCode), "/")
return temp[len(temp)-1]
}
return voucherCode
}