package service import ( "fmt" "github.com/go-kratos/kratos/v2/log" "github.com/go-kratos/kratos/v2/transport/http" "io" http2 "net/http" "voucher/internal/biz" "voucher/internal/pkg/helper" ) type NotifyService struct { WechatBiz *biz.WechatBiz VoucherBiz *biz.VoucherBiz } func NewNotifyService(wechatBiz *biz.WechatBiz, VoucherBiz *biz.VoucherBiz) *NotifyService { return &NotifyService{WechatBiz: wechatBiz, VoucherBiz: VoucherBiz} } // Notify https://pay.weixin.qq.com/doc/v3/merchant/4012285250 func (srv *NotifyService) Notify(ctx http.Context) error { mchId := ctx.Vars().Get("mch_id") if mchId == "" { log.Errorf("微信回调通知,mchId参数不能为空") return ctx.JSON(http2.StatusNetworkAuthenticationRequired, map[string]string{ "code": "FAIL", "message": "微信回调通知,mchId参数不能为空", }) } headers := ctx.Request().Header if headers == nil { log.Errorf("微信回调通知[%s],headers参数不能为空", mchId) return ctx.JSON(http2.StatusNetworkAuthenticationRequired, map[string]string{ "code": "FAIL", "message": "微信回调通知,headers参数不能为空", }) } bodyBytes, err := io.ReadAll(ctx.Request().Body) if err != nil { log.Errorf("微信回调通知[%s],读取响应体失败: %v", mchId, err) return fmt.Errorf("读取响应体失败: %w", err) } if len(bodyBytes) == 0 { log.Errorf("微信回调通知[%s],响应体不能为空", mchId) return ctx.JSON(http2.StatusNetworkAuthenticationRequired, map[string]string{ "code": "FAIL", "message": "微信回调通知,响应体不能为空", }) } log.Warnf("微信回调通知[%s],数据,headers:%+v,body:%s", mchId, headers, string(bodyBytes)) response, err := srv.WechatBiz.CallBack(ctx, mchId, &headers, bodyBytes) if err != nil { return ctx.JSON(http2.StatusNetworkAuthenticationRequired, map[string]string{ "code": "FAIL", "message": err.Error(), }) } ip := helper.GetClientIP(ctx) if err = srv.VoucherBiz.WechatNotifyConsumer(ctx, ip, response); err != nil { log.Errorf("微信回调通知[%s],处理失败,headers:%+v,body:%s,err:%s", mchId, headers, string(bodyBytes), err.Error()) return ctx.JSON(http2.StatusBadRequest, map[string]string{ "code": "FAIL", "message": err.Error(), }) } return ctx.JSON(http2.StatusOK, nil) }