c# - Azure 服务总线重试选项不起作用

标签 c# .net-core azure-servicebus-queues

不幸的是,我尝试将 ServiceBusClient 配置为以 10 秒的固定延迟重试消息。我还尝试了指数重试配置。然而,代码总是在一两秒内重试消息并完全忽略配置。它甚至忽略 MaxRetries,只重试 10 次,这是在 Azure 门户中为队列配置的值。我做错了什么?

我正在使用Azure.Messaging.ServiceBus库,NuGet 包 7.0.0。

代码:

ServiceBusClient client = new ServiceBusClient(serviceBusConnectionString, new ServiceBusClientOptions()
            {
                RetryOptions = new ServiceBusRetryOptions()
                {
                    Mode = ServiceBusRetryMode.Fixed,
                    Delay = TimeSpan.FromSeconds(10),
                    MaxDelay = TimeSpan.FromMinutes(3),
                    MaxRetries = 30
                }
            });

ServiceBusProcessor processor = client.CreateProcessor(queueName, new ServiceBusProcessorOptions());

// throwing an exception in MyMessageHandlerAsync on purpose
// to test out the retries configuration
processor.ProcessMessageAsync += MyMessageHandlerAsync;

// The uncaught exception causes this method to execute. 
// Processing is attempted 10 times with
// virtually no delay between each attempt.
// After the 10th attempt, the message goes to deadletter,
// which is expected.
processor.ProcessErrorAsync += MyErrorHandler;

收到第一个回复后,我将对此问题添加更多内容:

目前,MyMessageHandlerAsync 是:

    private async Task MyMessageHandlerAsync(EventArgs eventArgs)
    {
        var args = (ProcessMessageEventArgs)eventArgs;

        var body = args.Message.Body.ToString();
        
        // ...
        // process body
        // ...

        await args.CompleteMessageAsync(args.Message);
    }

我应该如何更改方法的内容以重试非 transient ServiceBusException?请帮助提供以下 TODO 的代码:

    private async Task MyMessageHandlerAsync(EventArgs eventArgs)
    {
        var args = (ProcessMessageEventArgs)eventArgs;

        try
        {

            var body = args.Message.Body.ToString();
        
            // ...
            // process body
            // ...

            await args.CompleteMessageAsync(args.Message);
        }
        catch (ServiceBusException sbe)
        {
            if (sbe.IsTransiet)
            {
                // TODO: Is it correct that the exponential retry will work
                // here?  The one defined in the ServiceBusClient.
                // So, no code is needed here, just throw.
                throw;
            }
            else
            {
                // TODO: for non-transient, this is where the
                //       options in the ServiceBusClient don't apply.
                //       Is that correct?  How do I do an
                //       exponential retry here?
            }
        }
        catch (Exception e)
        {
            // TODO: same problem as else in first catch.
        }
    }

最佳答案

ServiceBusRetryOptions旨在由 ASB 客户端在存在未立即冒泡到您的代码的暂时性错误时使用,即客户端内置的内部重试机制,可在异常发生之前代表您执行重试提出。

使用重试策略向ASB客户端指定如何处理transient errors在放弃之前,不是消息处理程序抛出错误的次数:

enter image description here

关于c# - Azure 服务总线重试选项不起作用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/65945497/

相关文章:

c# - C++和C#中指针和函数参数的等价性

在 lambda 中捕获时 C# 结构实例行为发生变化

c# - 为调试目的获取 "critical"机器信息的库?

c# - dotnet core 3.1 windows 服务无法加载配置设置

azure - 完成 Azure 服务总线上死信队列中的消息

azure - 使用分区键从 Azure 服务总线队列检索消息

c# - NUnit 不等待异步任务完成

.net-core - ReSharper 2018.1.2 NUnit TestCaseSource (.NET Core/VS2017)

asp.net - 在 Linux 和 Visual Studio Code 中分析 dotnet core

Azure Functions 和 DocumentDB 触发器