.NET 幫助

Polly 重試(開發人員如何運作)

發佈 2024年6月6日
分享:

處理瞬態故障、超時和異常是構建穩健和有韌性的應用程式的關鍵。Polly 是一個流行的 .NET 函式庫,提供了彈性和瞬態故障處理功能。在其眾多功能中,「重試」是最廣泛使用的策略之一。

在本文中,我們將深入探討 Polly 的重試策略在 C#,探索其使用和配置選項,並提供實用的代碼示例。另外,我們將使用 IronPDF 使用Polly重試嘗試生成表單請求結果的PDF。

什麼是 Polly Retry?

Polly Retry 是由 Polly 庫提供的一個策略,使開發人員可以自動重試由於錯誤或暫時性故障而失敗的操作。暫時性故障是由於網絡毛刺、服務不可用或其他暫時性問題而發生的臨時錯誤。

使用 Polly 的重試策略,您可以定義重試操作的規則,包括最大重試次數、多次重試之間的延遲,以及重試失敗請求的條件。這有助於構建能夠從臨時失敗中恢復的具有彈性的應用程式,而不會崩潰或對終端用戶造成干擾。

開始使用 Polly 重試

在深入了解程式碼範例之前,讓我們先建立一個有關如何在 C# 專案中安裝和配置 Polly 的基本認識。

安裝 Polly

您可以使用以下指令透過 NuGet 套件管理器主控台安裝 Polly:

Install-Package Polly
Install-Package Polly
'INSTANT VB TODO TASK: The following line uses invalid syntax:
'Install-Package Polly
VB   C#

或者通過 .NET CLI:

dotnet add package Polly
dotnet add package Polly
'INSTANT VB TODO TASK: The following line uses invalid syntax:
'dotnet add package Polly
VB   C#

加入 Polly 使用語句

在你的 C# 文件中,包含 Polly 命名空間:

using Polly;
using Polly;
Imports Polly
VB   C#

基本重试策略示例

讓我們從一個簡單的示例開始,我們將重试一个模拟从远程服务获取数据的操作。 我们将设置一個最多重试3次的重试策略,并且在每次重试之间设置固定的2秒超时延迟。

using System;
using System.Net.Http;
using Polly;
namespace PollyRetryExample
{
    public class Program
    {
        public static void Main(string[] args)
        {
           var retryPolicy = Policy
                .Handle<HttpRequestException>()
                .WaitAndRetry(
                    3,
                    retryAttempt => TimeSpan.FromSeconds(2),
                    (exception, timeSpan, retryCount, context) =>
                    {
                        Console.WriteLine("Retry {0} due to {1}", retryCount, exception.Message);
                    });
            try
            {
                retryPolicy.Execute(() =>
                {
                    FetchDataFromRemoteService();
                });
            }
            catch (Exception ex)
            {
                Console.WriteLine("Failed after 3 retries: {0}", ex.Message);
            }
        }
        public static void FetchDataFromRemoteService()
        {
            throw new HttpRequestException("Failed to fetch data from remote service");
        }
    }
}
using System;
using System.Net.Http;
using Polly;
namespace PollyRetryExample
{
    public class Program
    {
        public static void Main(string[] args)
        {
           var retryPolicy = Policy
                .Handle<HttpRequestException>()
                .WaitAndRetry(
                    3,
                    retryAttempt => TimeSpan.FromSeconds(2),
                    (exception, timeSpan, retryCount, context) =>
                    {
                        Console.WriteLine("Retry {0} due to {1}", retryCount, exception.Message);
                    });
            try
            {
                retryPolicy.Execute(() =>
                {
                    FetchDataFromRemoteService();
                });
            }
            catch (Exception ex)
            {
                Console.WriteLine("Failed after 3 retries: {0}", ex.Message);
            }
        }
        public static void FetchDataFromRemoteService()
        {
            throw new HttpRequestException("Failed to fetch data from remote service");
        }
    }
}
Imports System
Imports System.Net.Http
Imports Polly
Namespace PollyRetryExample
	Public Class Program
		Public Shared Sub Main(ByVal args() As String)
		   Dim retryPolicy = Policy.Handle(Of HttpRequestException)().WaitAndRetry(3, Function(retryAttempt) TimeSpan.FromSeconds(2), Sub(exception, timeSpan, retryCount, context)
			   Console.WriteLine("Retry {0} due to {1}", retryCount, exception.Message)
		   End Sub)
			Try
				retryPolicy.Execute(Sub()
					FetchDataFromRemoteService()
				End Sub)
			Catch ex As Exception
				Console.WriteLine("Failed after 3 retries: {0}", ex.Message)
			End Try
		End Sub
		Public Shared Sub FetchDataFromRemoteService()
			Throw New HttpRequestException("Failed to fetch data from remote service")
		End Sub
	End Class
End Namespace
VB   C#

在此範例中:

  • Handle<HttpRequestException>()``` 指定我們希望處理 HttpRequestException 並在發生時重試該操作。

  • WaitAndRetry ```()配置重试策略,有3次重试,每次重试間隔2秒的固定延遲 (指定的最長持續時間).

  • onRetry 委派在重试發生時記錄一條訊息。

Polly 重試(對於開發人員如何運作):圖 1

高級重試策略配置

指數退避

指數退避是一種流行的重試策略,其中請求和重試之間的延遲指數增加。Polly 提供了一種方便的方法來使用 WaitAndRetry 實現指數退避。()`.

var retryPolicy = Policy
    .Handle<HttpRequestException>()
    .WaitAndRetry(
        retryCount: 3,
        sleepDurationProvider: attempt => TimeSpan.FromSeconds(Math.Pow(2, attempt)),
        onRetry: (exception, retryCount, context) =>
        {
            Console.WriteLine($"Retry {retryCount} due to {exception.Message}");
        });
var retryPolicy = Policy
    .Handle<HttpRequestException>()
    .WaitAndRetry(
        retryCount: 3,
        sleepDurationProvider: attempt => TimeSpan.FromSeconds(Math.Pow(2, attempt)),
        onRetry: (exception, retryCount, context) =>
        {
            Console.WriteLine($"Retry {retryCount} due to {exception.Message}");
        });
Dim retryPolicy = Policy.Handle(Of HttpRequestException)().WaitAndRetry(retryCount:= 3, sleepDurationProvider:= Function(attempt) TimeSpan.FromSeconds(Math.Pow(2, attempt)), onRetry:= Sub(exception, retryCount, context)
	Console.WriteLine($"Retry {retryCount} due to {exception.Message}")
End Sub)
VB   C#

Polly 重试(開發者使用說明):圖2

使用斷路器重試

結合重試和斷路器可以進一步增強韌性,從而防止服務持續失敗時的重複重試。Polly 使您能夠輕鬆地結合重試和斷路器策略。

var circuitBreakerPolicy = Policy
    .Handle<HttpRequestException>()
    .CircuitBreaker(
        exceptionsAllowedBeforeBreaking: 3,
        durationOfBreak: TimeSpan.FromSeconds(30),
        onBreak: (ex, breakDelay) =>
        {
            Console.WriteLine($"Circuit broken due to {ex.Message}. Retry after {breakDelay.TotalSeconds} seconds.");
        },
        onReset: () =>
        {
            Console.WriteLine("Circuit reset.");
        });
var retryPolicy = Policy
    .Handle<HttpRequestException>()
    .WaitAndRetry(
        retryCount: 3,
        sleepDurationProvider: attempt => TimeSpan.FromSeconds(2),
        onRetry: (exception, retryCount, context) =>
        {
            Console.WriteLine($"Retry {retryCount} due to {exception.Message}");
        });
var policyWrap = Policy.Wrap(circuitBreakerPolicy, retryPolicy);
var circuitBreakerPolicy = Policy
    .Handle<HttpRequestException>()
    .CircuitBreaker(
        exceptionsAllowedBeforeBreaking: 3,
        durationOfBreak: TimeSpan.FromSeconds(30),
        onBreak: (ex, breakDelay) =>
        {
            Console.WriteLine($"Circuit broken due to {ex.Message}. Retry after {breakDelay.TotalSeconds} seconds.");
        },
        onReset: () =>
        {
            Console.WriteLine("Circuit reset.");
        });
var retryPolicy = Policy
    .Handle<HttpRequestException>()
    .WaitAndRetry(
        retryCount: 3,
        sleepDurationProvider: attempt => TimeSpan.FromSeconds(2),
        onRetry: (exception, retryCount, context) =>
        {
            Console.WriteLine($"Retry {retryCount} due to {exception.Message}");
        });
var policyWrap = Policy.Wrap(circuitBreakerPolicy, retryPolicy);
Dim circuitBreakerPolicy = Policy.Handle(Of HttpRequestException)().CircuitBreaker(exceptionsAllowedBeforeBreaking:= 3, durationOfBreak:= TimeSpan.FromSeconds(30), onBreak:= Sub(ex, breakDelay)
			Console.WriteLine($"Circuit broken due to {ex.Message}. Retry after {breakDelay.TotalSeconds} seconds.")
End Sub, onReset:= Sub()
			Console.WriteLine("Circuit reset.")
End Sub)
Dim retryPolicy = Policy.Handle(Of HttpRequestException)().WaitAndRetry(retryCount:= 3, sleepDurationProvider:= Function(attempt) TimeSpan.FromSeconds(2), onRetry:= Sub(exception, retryCount, context)
	Console.WriteLine($"Retry {retryCount} due to {exception.Message}")
End Sub)
Dim policyWrap = Policy.Wrap(circuitBreakerPolicy, retryPolicy)
VB   C#

在此範例中:

  • CircuitBreaker() 定義了一個斷路器策略,在發生 3 次異常後跳脫開關,並保持打開狀態 30 秒。
  • Policy.Wrap()將斷路器和重試策略結合為單一策略。

Polly 重试(開發人員的工作方式):圖 3

IronPDF 介紹

IronPDF for C# 是一個強大的C#庫,可以讓開發人員在其.NET應用程式中創建、編輯和操控PDF文件。無論您需要創建發票、報告或其他類型的PDF文件,IronPDF提供了一個直觀的API,簡化了這個過程。

使用IronPDF,您可以輕鬆地將HTML、CSS,甚至ASP.NET網頁轉換為PDF,這使其成為一個適用於廣泛應用的多功能工具。此外,它還提供了高級功能,如向PDF添加文本、圖像和互動元素,以及通過加密和數字簽名來保護文件。

Polly 重試與 IronPDF

在使用 IronPDF 時,可能會有需要從外部來源獲取數據或在生成 PDF 之前執行複雜操作的情況。

在這種情況下,您可能會遇到瞬態故障或臨時問題,這可能會導致 PDF 生成失敗。為了優雅地處理這些瞬態故障,您可以將 Polly 重試與 IronPDF 結合使用。

安裝 IronPDF 和 Polly

在開始之前,請確保在您的項目中安裝 IronPDF NuGet 套件。

Install-Package IronPdf

使用 Polly Retry 和 IronPDF

讓我們來看看一個範例,在生成 PDF 時使用 Polly Retry 處理暫時性故障的情況。在下面的例子中,我們將模擬從外部 API 獲取數據,然後根據這些數據生成 PDF。我們將使用 Polly 的 Retry 在發生失敗時執行數據獲取操作。

using System;
using System.Net.Http;
using System.Threading.Tasks;
using IronPdf;
using Polly;
namespace IronPdfWithPollyRetry
{
    public class Program
    {
        public static async Task Main(string[] args)
        {
            var retryPolicy = Policy
                .Handle<HttpRequestException>()
                .WaitAndRetryAsync(
                    3,//retry attempts
                    retryAttempt => TimeSpan.FromSeconds(2),//calculated retry delay
                    (exception, timeSpan, retryCount, context) =>
                    {
                        Console.WriteLine("Retry " + retryCount + " due to " + exception.Message);
                    });
            var pdf = await retryPolicy.ExecuteAsync(async () =>
            {
                var data = await FetchDataFromExternalApiAsync();
                return GeneratePdfFromData(data);
            });
            pdf.SaveAs("GeneratedDocument.pdf");
        }
        static async Task<string> FetchDataFromExternalApiAsync()
        {
            // Simulate fetching data from an external API
            await Task.Delay(100); // Simulate delay
            throw new HttpRequestException("Failed to fetch data from external API");
        }
        static PdfDocument GeneratePdfFromData(string data)
        {
            // Generate PDF using IronPDF based on the fetched data
            var htmlContent = "<html><body><h1>Data: " + data + "</h1></body></html>";
            var renderer = new ChromePdfRenderer();
            return renderer.RenderHtmlAsPdf(htmlContent);
        }
    }
}
using System;
using System.Net.Http;
using System.Threading.Tasks;
using IronPdf;
using Polly;
namespace IronPdfWithPollyRetry
{
    public class Program
    {
        public static async Task Main(string[] args)
        {
            var retryPolicy = Policy
                .Handle<HttpRequestException>()
                .WaitAndRetryAsync(
                    3,//retry attempts
                    retryAttempt => TimeSpan.FromSeconds(2),//calculated retry delay
                    (exception, timeSpan, retryCount, context) =>
                    {
                        Console.WriteLine("Retry " + retryCount + " due to " + exception.Message);
                    });
            var pdf = await retryPolicy.ExecuteAsync(async () =>
            {
                var data = await FetchDataFromExternalApiAsync();
                return GeneratePdfFromData(data);
            });
            pdf.SaveAs("GeneratedDocument.pdf");
        }
        static async Task<string> FetchDataFromExternalApiAsync()
        {
            // Simulate fetching data from an external API
            await Task.Delay(100); // Simulate delay
            throw new HttpRequestException("Failed to fetch data from external API");
        }
        static PdfDocument GeneratePdfFromData(string data)
        {
            // Generate PDF using IronPDF based on the fetched data
            var htmlContent = "<html><body><h1>Data: " + data + "</h1></body></html>";
            var renderer = new ChromePdfRenderer();
            return renderer.RenderHtmlAsPdf(htmlContent);
        }
    }
}
Imports System
Imports System.Net.Http
Imports System.Threading.Tasks
Imports IronPdf
Imports Polly
Namespace IronPdfWithPollyRetry
	Public Class Program
		Public Shared Async Function Main(ByVal args() As String) As Task
			Dim retryPolicy = Policy.Handle(Of HttpRequestException)().WaitAndRetryAsync(3, Function(retryAttempt) TimeSpan.FromSeconds(2), Sub(exception, timeSpan, retryCount, context)
				Console.WriteLine("Retry " & retryCount & " due to " & exception.Message)
			End Sub)
			Dim pdf = Await retryPolicy.ExecuteAsync(Async Function()
				Dim data = Await FetchDataFromExternalApiAsync()
				Return GeneratePdfFromData(data)
			End Function)
			pdf.SaveAs("GeneratedDocument.pdf")
		End Function
		Private Shared Async Function FetchDataFromExternalApiAsync() As Task(Of String)
			' Simulate fetching data from an external API
			Await Task.Delay(100) ' Simulate delay
			Throw New HttpRequestException("Failed to fetch data from external API")
		End Function
		Private Shared Function GeneratePdfFromData(ByVal data As String) As PdfDocument
			' Generate PDF using IronPDF based on the fetched data
			Dim htmlContent = "<html><body><h1>Data: " & data & "</h1></body></html>"
			Dim renderer = New ChromePdfRenderer()
			Return renderer.RenderHtmlAsPdf(htmlContent)
		End Function
	End Class
End Namespace
VB   C#

此C#代码演示了如何使用Polly库与IronPDF一起实施重试策略以生成PDF文档。Main方法使用Polly的WaitAndRetryAsync方法初始化一个重试策略。

這個策略指定它應該處理HttpRequestException,並在最初嘗試後重試操作最多3次,每次之間間隔2秒。如果重试失败,则会在控制台打印一条消息,指示重试尝试次数和异常消息。

Main方法中,重试策略逻辑是使用retryPolicy.ExecuteAsync异步执行的。()在這個執行過程中,兩個異步操作被鏈接在一起:FetchDataFromExternalApiAsync()GeneratePdfFromData(數據)如果 FetchDataFromExternalApiAsync()失敗 (因為它被有意地設置為引發模擬異常)重試策略將捕捉 HttpRequestException,記錄重試嘗試,並重試操作。

FetchDataFromExternalApiAsync()該方法模擬從外部 API 獲取數據並延遲,並且故意拋出HttpRequestException` 來模擬請求失敗。

Polly 重試(開發人員的工作原理):圖 4

結論

總之,Polly 的重試策略在處理瞬時故障和確保 C# 應用程序的健壯性方面非常有價值。它在配置重試次數、延遲和條件方面的靈活性,使得開發人員能夠根據具體需求定制彈性策略。

無論是獨立使用還是與其他庫結合使用,如 IronPDF,Polly 促使應用程式在暫時性故障中優雅地恢復運行,提升用戶體驗和軟體的可靠度。

通過整合 Polly 的重試功能,開發者能夠構建出更具彈性的系統,能夠適應並從短暫的問題中恢復,最終提高應用程式的整體質量和可靠性。

IronPDF 是市場上最好的 C# PDF 函式庫,它還提供了一個 試用授權 價格從 $749 美元起。

如需了解如何使用 IronPDF 進行 HTML 到 PDF 的轉換,請訪問以下網站 連結.

< 上一頁
C# iList(開發人員如何使用)
下一個 >
WebClient C#(它對開發人員的工作原理)

準備開始了嗎? 版本: 2024.10 剛剛發布

免費 NuGet 下載 總下載次數: 10,993,239 查看許可證 >