sunpengfei
2025-06-11 1605af1ced748313e99f38e5eb6888768fbc7d54
fix:支付回调和供应商回调的并发问题
5个文件已修改
86 ■■■■■ 已修改文件
LifePayment/LifePayment.Application/LifePay/LifePayService.cs 9 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LifePayment/LifePayment.HttpApi/LifePay/ACOOLYNotifyController.cs 6 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LifePayment/LifePayment.HttpApi/LifePay/AliPayNotifyController.cs 10 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LifePayment/LifePayment.HttpApi/LifePay/WxPayNotifyController.cs 9 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LifePayment/LifePayment.Worker/Worker/CheckUnPayOrderWork.cs 52 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LifePayment/LifePayment.Application/LifePay/LifePayService.cs
@@ -18,6 +18,7 @@
using Volo.Abp;
using Volo.Abp.Application.Services;
using Volo.Abp.Data;
using Volo.Abp.DistributedLocking;
using Volo.Abp.Domain.Repositories;
using Volo.Abp.EventBus.Distributed;
using Z.EntityFramework.Plus;
@@ -44,6 +45,7 @@
    private readonly ILifePayOrderService _lifePayOrderService;
    private readonly IDataFilter dataFilter;
    private readonly IChannelFilter _channelFilter;
    private readonly IAbpDistributedLock distributedLock;
    private readonly IAliPayApi _aliPayApi;
    private readonly IAlipayInterfaceManager _alipayInterfaceManager;
    private readonly IWxPayApi _wxPayApi;
@@ -73,7 +75,8 @@
                          IRepository<LifePayChannles, Guid> lifePayChannlesRep,
                          IRepository<LifePayAccount, Guid> lifePayAccount,
                          IDataFilter dataFilter,
                          IChannelFilter channelFilter)
                          IChannelFilter channelFilter,
                          IAbpDistributedLock distributedLock)
    {
        _logger = logger;
        _aCOOLYManager = aCOOLYManager;
@@ -95,6 +98,7 @@
        _lifePayAccount = lifePayAccount;
        this.dataFilter = dataFilter;
        _channelFilter = channelFilter;
        this.distributedLock = distributedLock;
        _operateHistory = operateHistory;
    }
@@ -1528,8 +1532,11 @@
    public async Task ACOOLYOrderNotifyHandler(string orderNo, string acoolyOrderNo, LifePayOrderStatusEnum status, ACOOLYStatusEnum acoolyStatus, decimal payAmount, string refundApplyRemark, decimal? parValue = 0, decimal? actualParValue = 0)
    {
        var order = await _lifePayOrderRepository.Where(x => x.OrderNo == orderNo).FirstOrDefaultAsync();
        CheckExtensions.IfTrueThrowUserFriendlyException(order == null, "订单不存在");
        await using var orderLock = await distributedLock.TryAcquireAsync($"LockKey:UpdateOrder:{orderNo}", TimeSpan.FromSeconds(60));
        if (order.ACOOLYStatus.HasValue && (int)order.ACOOLYStatus > (int)acoolyStatus)
        {
            _logger.LogInformation($"订单({orderNo})由{order.ACOOLYStatus}至{acoolyStatus}失败,不可回滚状态");
LifePayment/LifePayment.HttpApi/LifePay/ACOOLYNotifyController.cs
@@ -10,6 +10,7 @@
using System.Threading.Tasks;
using Volo.Abp;
using Volo.Abp.AspNetCore.Mvc;
using Volo.Abp.DistributedLocking;
using Volo.Abp.Uow;
namespace LifePayment.HttpApi
@@ -20,14 +21,17 @@
    public class ACOOLYNotifyController : AbpController
    {
        private readonly ILifePayService _lifePayService;
        private readonly IAbpDistributedLock distributedLock;
        private readonly ILogger<ACOOLYNotifyController> _logger;
        public ACOOLYNotifyController(
               ILogger<ACOOLYNotifyController> logger,
               ILifePayService lifePayService)
               ILifePayService lifePayService,
               IAbpDistributedLock distributedLock)
        {
            _logger = logger;
            _lifePayService = lifePayService;
            this.distributedLock = distributedLock;
        }
        /// <summary>
LifePayment/LifePayment.HttpApi/LifePay/AliPayNotifyController.cs
@@ -2,6 +2,7 @@
using Castle.Core.Internal;
using LifePayment.Application.Contracts;
using LifePayment.Domain.Shared;
using Medallion.Threading;
using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Logging;
@@ -11,6 +12,7 @@
using System.Text.RegularExpressions;
using System.Threading.Tasks;
using Volo.Abp.AspNetCore.Mvc;
using Volo.Abp.DistributedLocking;
using Volo.Abp.Uow;
using ZeroD.Util;
@@ -27,15 +29,17 @@
        private readonly ILifePayOrderService _lifePayOrderService;
        private readonly ILogger<AliPayNotifyController> _logger;
        private readonly IAbpDistributedLock distributedLock;
        public AliPayNotifyController(
               ILogger<AliPayNotifyController> logger,
               IAbpDistributedLock distributedLock,
               ILifePayService lifePayService,
               ILifePayOrderService lifePayOrderService)
        {
            _logger = logger;
            this.distributedLock = distributedLock;
            _lifePayService = lifePayService;
            _lifePayOrderService = lifePayOrderService;
        }
@@ -61,6 +65,8 @@
            {
                if (input.TradeStatus == LifePaymentConstant.AliPayStatus.支付成功 && input.OutBizNo.IsNullOrEmpty())
                {
                    await using var orderLock = await distributedLock.TryAcquireAsync($"LockKey:UpdateOrder:{input.OutTradeNo}", TimeSpan.FromSeconds(60));
                    await _lifePayService.LifePaySuccessHandler(input.OutTradeNo, input.TradeNo);
                    // 插入收支流水
                    await _lifePayOrderService.AddLifePayExpensesReceipts(new AddLifePayExpensesReceiptsInput()
@@ -75,6 +81,8 @@
                    && input.OutBizNo.IsNotNullOrEmpty()
                    && (input.RefundFee.HasValue && input.RefundFee > 0)))
                {
                    await using var orderLock = await distributedLock.TryAcquireAsync($"LockKey:UpdateOrder:{input.OutTradeNo}", TimeSpan.FromSeconds(60));
                    await _lifePayService.LifePayRefundsHandler(input.OutTradeNo, LifePayRefundStatusEnum.已退款);
                    // 插入收支流水
                    await _lifePayOrderService.AddLifePayExpensesReceipts(new AddLifePayExpensesReceiptsInput()
LifePayment/LifePayment.HttpApi/LifePay/WxPayNotifyController.cs
@@ -1,6 +1,7 @@
using LifePayment.Application.Contracts;
using LifePayment.Domain;
using LifePayment.Domain.Shared;
using Medallion.Threading;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Caching.Distributed;
using Microsoft.Extensions.Logging;
@@ -10,6 +11,7 @@
using System.Threading.Tasks;
using Volo.Abp.AspNetCore.Mvc;
using Volo.Abp.Caching;
using Volo.Abp.DistributedLocking;
using Volo.Abp.Uow;
using ZeroD.Util;
@@ -26,6 +28,7 @@
        private readonly ILifePayService _lifePayService;
        private readonly ILifePayOrderService _lifePayOrderService;
        private readonly IDistributedCache<string> distributedCache;
        private readonly IAbpDistributedLock distributedLock;
        private readonly ILogger<WxPayNotifyController> _logger;
        public WxPayNotifyController(
@@ -33,13 +36,15 @@
               ILogger<WxPayNotifyController> logger,
               ILifePayService lifePayService,
               ILifePayOrderService lifePayOrderService,
               IDistributedCache<string> distributedCache)
               IDistributedCache<string> distributedCache,
               IAbpDistributedLock distributedLock)
        {
            _wxPayApi = wxPayApi;
            _logger = logger;
            _lifePayService = lifePayService;
            _lifePayOrderService = lifePayOrderService;
            this.distributedCache = distributedCache;
            this.distributedLock = distributedLock;
        }
        /// <summary>
@@ -63,6 +68,8 @@
                {
                    if (wxPayNotice.TradeState == LifePaymentConstant.WxPayStatus.支付成功)
                    {
                        await using var orderLock = await distributedLock.TryAcquireAsync($"LockKey:UpdateOrder:{wxPayNotice.OutTradeNo}", TimeSpan.FromSeconds(60));
                        var key = $"WxRechargeNotify_{wxPayNotice.OutTradeNo}";
                        if (string.IsNullOrWhiteSpace(distributedCache.Get(key)))
                        {
LifePayment/LifePayment.Worker/Worker/CheckUnPayOrderWork.cs
@@ -6,16 +6,19 @@
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Logging;
using Nest;
using StackExchange.Redis;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Volo.Abp.BackgroundWorkers;
using Volo.Abp.DistributedLocking;
using Volo.Abp.Domain.Repositories;
using Volo.Abp.Threading;
using Volo.Abp.Uow;
using ZeroD.Util;
using ZeroD.Util.Fadd;
namespace LifePayment.Worker.Worker
{
@@ -25,6 +28,7 @@
        private readonly int _doWorkMinute = 1;
        private readonly ILifePayOrderService lifePayOrderService;
        private readonly ILifePayService lifePayService;
        private readonly IAbpDistributedLock distributedLock;
        private readonly IRepository<LifePayOrder, Guid> lifePayOrderRepository;
        public CheckUnPayOrderWork(
@@ -32,11 +36,13 @@
            IServiceScopeFactory serviceScopeFactory,
            ILifePayOrderService lifePayOrderService,
            ILifePayService lifePayService,
            IAbpDistributedLock distributedLock,
            IRepository<LifePayOrder, Guid> lifePayOrderRepository) : base(timer, serviceScopeFactory)
        {
            timer.Period = (int)TimeSpan.FromMinutes(10).TotalMilliseconds;
            timer.Period = (int)TimeSpan.FromSeconds(5).TotalMilliseconds;
            this.lifePayOrderService = lifePayOrderService;
            this.lifePayService = lifePayService;
            this.distributedLock = distributedLock;
            this.lifePayOrderRepository = lifePayOrderRepository;
        }
@@ -51,30 +57,32 @@
                var orders = lifePayOrderRepository.Where(it => it.PayStatus == LifePayStatusEnum.未支付 && it.CreationTime >= start && it.CreationTime <= end).ToList();
                foreach (var order in orders)
                {
                    await using var orderLock = await distributedLock.TryAcquireAsync($"LockKey:UpdateOrder:{order.OrderNo}", TimeSpan.FromSeconds(60));
                    Logger.LogInformation($"订单:{order.OrderNo}-{order.ToJson()}");
                    //var wxPayNotice = await lifePayService.WxPayTradeQuery(order.OrderNo);
                    //var json = wxPayNotice.ToJson();
                    //Logger.LogInformation($"订单({wxPayNotice.OutTradeNo})信息: {json}");
                    //if (wxPayNotice.OutTradeNo.Contains("JF") && wxPayNotice.TradeState == LifePaymentConstant.WxPayStatus.支付成功)
                    //{
                    //    await lifePayService.LifePaySuccessHandler(wxPayNotice.OutTradeNo, wxPayNotice.TransactionId);
                    var wxPayNotice = await lifePayService.WxPayTradeQuery(order.OrderNo);
                    var json = wxPayNotice.ToJson();
                    Logger.LogInformation($"订单({wxPayNotice.OutTradeNo})信息: {json}");
                    if (wxPayNotice.OutTradeNo.Contains("JF") && wxPayNotice.TradeState == LifePaymentConstant.WxPayStatus.支付成功)
                    {
                        await lifePayService.LifePaySuccessHandler(wxPayNotice.OutTradeNo, wxPayNotice.TransactionId);
                    //    // 插入收支流水
                    //    await lifePayOrderService.AddLifePayExpensesReceipts(new AddLifePayExpensesReceiptsInput()
                    //    {
                    //        OrderNo = wxPayNotice.OutTradeNo,
                    //        OutOrderNo = wxPayNotice.TransactionId,
                    //        LifePayType = LifePayTypeEnum.WxPay,
                    //        ExpensesReceiptsType = ExpensesReceiptsTypeEnum.Expenses,
                    //        Amount = wxPayNotice.Amount.Total
                    //    });
                        // 插入收支流水
                        await lifePayOrderService.AddLifePayExpensesReceipts(new AddLifePayExpensesReceiptsInput()
                        {
                            OrderNo = wxPayNotice.OutTradeNo,
                            OutOrderNo = wxPayNotice.TransactionId,
                            LifePayType = LifePayTypeEnum.WxPay,
                            ExpensesReceiptsType = ExpensesReceiptsTypeEnum.Expenses,
                            Amount = wxPayNotice.Amount.Total
                        });
                    //    Logger.LogInformation("已改为支付成功");
                    //}
                    //else
                    //{
                    //    Logger.LogInformation("未更新");
                    //}
                        Logger.LogInformation("已改为支付成功");
                    }
                    else
                    {
                        Logger.LogInformation("未更新");
                    }
                }
            }
            catch (Exception ex)