Skip to content

Commit 1e47428

Browse files
Refactor PolicyFactory and event handler retry logic
- Updated `CreatePolicy` method to set default `withFallBack` to `false` and `retryDelay` to 2 seconds. Removed fallback policy logic. - Simplified calls to `PolicyFactory.CreatePolicy` in event handlers by removing hardcoded retry count, relying on defaults. - Enhanced logging in retry policy to provide detailed error information. - Modified `HandleSpecificDomainEvent` methods for consistent application of retry policies across domain events.
1 parent a1374f2 commit 1e47428

5 files changed

Lines changed: 23 additions & 36 deletions

File tree

TransactionProcessor.BusinessLogic/Common/PolicyFactory.cs

Lines changed: 7 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -13,17 +13,13 @@
1313
namespace TransactionProcessor.BusinessLogic.Common;
1414

1515
public static class PolicyFactory{
16-
public static IAsyncPolicy<Result> CreatePolicy(Int32 retryCount=5, TimeSpan? retryDelay = null, String policyTag="", Boolean withFallBack=true) {
16+
public static IAsyncPolicy<Result> CreatePolicy(Int32 retryCount=5, TimeSpan? retryDelay = null, String policyTag="", Boolean withFallBack=false) {
1717

18-
TimeSpan retryDelayValue = retryDelay.GetValueOrDefault(TimeSpan.FromSeconds(1));
18+
TimeSpan retryDelayValue = retryDelay.GetValueOrDefault(TimeSpan.FromSeconds(2));
1919

2020
AsyncRetryPolicy<Result> retryPolicy = CreateRetryPolicy(retryCount, retryDelayValue, policyTag);
2121

22-
IAsyncPolicy<Result> policyWrap = withFallBack switch {
23-
true => CreateFallbackPolicy(policyTag, retryPolicy),
24-
_ => retryPolicy
25-
};
26-
return policyWrap;
22+
return retryPolicy;
2723
}
2824

2925
public static async Task<Result> ExecuteWithPolicyAsync(Func<Task<Result>> action, IAsyncPolicy<Result> policy, String policyTag = "")
@@ -52,29 +48,15 @@ public static async Task<Result> ExecuteWithPolicyAsync(Func<Task<Result>> actio
5248
private static AsyncRetryPolicy<Result> CreateRetryPolicy(int retryCount, TimeSpan retryDelay, String policyTag)
5349
{
5450
return Policy<Result>
55-
.Handle<WrongExpectedVersionException>()
56-
.Or<RpcException>(ex => ex.StatusCode == StatusCode.DeadlineExceeded)
51+
.HandleResult(result => !result.IsSuccess && String.Join("|",result.Errors).Contains("Append failed due to WrongExpectedVersion")) // Retry if the result is not successful
52+
.OrResult(result => !result.IsSuccess && String.Join("|", result.Errors).Contains("DeadlineExceeded")) // Retry if the result is not successful
5753
.WaitAndRetryAsync(retryCount,
5854
_ => retryDelay, // Fixed delay
59-
(exception, timeSpan, retryCount, context) =>
55+
(result, timeSpan, retryCount, context) =>
6056
{
6157
context["RetryCount"] = retryCount;
62-
Logger.LogWarning($"{policyTag} - Retry {retryCount} due to {exception.Exception.GetType().Name}. Waiting {timeSpan} before retrying...");
63-
});
64-
}
65-
66-
private static AsyncPolicyWrap<Result> CreateFallbackPolicy(String policyTag, AsyncRetryPolicy<Result> retryPolicy)
67-
{
68-
var fallbackPolicy = Policy<Result>
69-
.Handle<Exception>() // Catch-all for exceptions that aren't retried
70-
.FallbackAsync(
71-
fallbackValue: Result.Failure("An error occurred, no retry required."), // Ensure a valid Result return
72-
onFallbackAsync: (exception, context) =>
73-
{
74-
Logger.LogWarning($"{policyTag} - Non-retryable exception encountered: {exception.Exception.GetType().Name}");
75-
return Task.CompletedTask;
58+
Logger.LogWarning($"{policyTag} - Retry {retryCount} due to unsuccessful result {String.Join(".",result.Result.Errors)}. Waiting {timeSpan} before retrying...");
7659
});
7760

78-
return fallbackPolicy.WrapAsync(retryPolicy);
7961
}
8062
}

TransactionProcessor.BusinessLogic/EventHandling/MerchantDomainEventHandler.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -61,7 +61,7 @@ public async Task<Result> Handle(IDomainEvent domainEvent,
6161
private async Task<Result> HandleSpecificDomainEvent(CallbackReceivedEnrichedEvent domainEvent,
6262
CancellationToken cancellationToken)
6363
{
64-
IAsyncPolicy<Result> retryPolicy = PolicyFactory.CreatePolicy(2, policyTag: "MerchantSettlementDomainEventHandler - MerchantFeeSettledEvent");
64+
IAsyncPolicy<Result> retryPolicy = PolicyFactory.CreatePolicy(policyTag: "MerchantSettlementDomainEventHandler - MerchantFeeSettledEvent");
6565

6666
return await PolicyFactory.ExecuteWithPolicyAsync(async () => {
6767
if (domainEvent.TypeString == typeof(CallbackHandler.DataTransferObjects.Deposit).ToString()) {

TransactionProcessor.BusinessLogic/EventHandling/MerchantSettlementDomainEventHandler.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -32,7 +32,7 @@ public async Task<Result> Handle(IDomainEvent domainEvent,
3232

3333
private async Task<Result> HandleSpecificDomainEvent(SettlementDomainEvents.MerchantFeeSettledEvent domainEvent,
3434
CancellationToken cancellationToken) {
35-
IAsyncPolicy<Result> retryPolicy = PolicyFactory.CreatePolicy(2, policyTag: "MerchantSettlementDomainEventHandler - MerchantFeeSettledEvent");
35+
IAsyncPolicy<Result> retryPolicy = PolicyFactory.CreatePolicy(policyTag: "MerchantSettlementDomainEventHandler - MerchantFeeSettledEvent");
3636

3737
return await PolicyFactory.ExecuteWithPolicyAsync(async () => {
3838
MerchantStatementCommands.AddSettledFeeToMerchantStatementCommand command = new(domainEvent.EstateId, domainEvent.MerchantId, domainEvent.FeeCalculatedDateTime, domainEvent.CalculatedValue, domainEvent.TransactionId, domainEvent.FeeId);

TransactionProcessor.BusinessLogic/EventHandling/MerchantStatementDomainEventHandler.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -52,7 +52,7 @@ public async Task<Result> Handle(IDomainEvent domainEvent,
5252
private async Task<Result> HandleSpecificDomainEvent(MerchantStatementDomainEvents.StatementGeneratedEvent domainEvent,
5353
CancellationToken cancellationToken) {
5454

55-
IAsyncPolicy<Result> retryPolicy = PolicyFactory.CreatePolicy(2, policyTag: "MerchantStatementDomainEventHandler - StatementGeneratedEvent");
55+
IAsyncPolicy<Result> retryPolicy = PolicyFactory.CreatePolicy(policyTag: "MerchantStatementDomainEventHandler - StatementGeneratedEvent");
5656

5757
return await PolicyFactory.ExecuteWithPolicyAsync(async () => {
5858
MerchantStatementCommands.EmailMerchantStatementCommand command = new(domainEvent.EstateId, domainEvent.MerchantId, domainEvent.MerchantStatementId);
@@ -63,7 +63,7 @@ private async Task<Result> HandleSpecificDomainEvent(MerchantStatementDomainEven
6363

6464
private async Task<Result> HandleSpecificDomainEvent(TransactionDomainEvents.TransactionHasBeenCompletedEvent domainEvent,
6565
CancellationToken cancellationToken) {
66-
IAsyncPolicy<Result> retryPolicy = PolicyFactory.CreatePolicy(2, policyTag: "MerchantStatementDomainEventHandler - TransactionHasBeenCompletedEvent");
66+
IAsyncPolicy<Result> retryPolicy = PolicyFactory.CreatePolicy(policyTag: "MerchantStatementDomainEventHandler - TransactionHasBeenCompletedEvent");
6767

6868
return await PolicyFactory.ExecuteWithPolicyAsync(async () => {
6969
MerchantStatementCommands.AddTransactionToMerchantStatementCommand command = new(domainEvent.EstateId, domainEvent.MerchantId, domainEvent.CompletedDateTime, domainEvent.TransactionAmount, domainEvent.IsAuthorised, domainEvent.TransactionId);

TransactionProcessor.BusinessLogic/EventHandling/TransactionDomainEventHandler.cs

Lines changed: 12 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -59,7 +59,7 @@ public async Task<Result> Handle(IDomainEvent domainEvent,
5959
private async Task<Result> HandleSpecificDomainEvent(FloatDomainEvents.FloatCreditPurchasedEvent domainEvent,
6060
CancellationToken cancellationToken) {
6161

62-
IAsyncPolicy<Result> retryPolicy = PolicyFactory.CreatePolicy(2, policyTag: "TransactionDomainEventHandler - FloatCreditPurchasedEvent");
62+
IAsyncPolicy<Result> retryPolicy = PolicyFactory.CreatePolicy(policyTag: "TransactionDomainEventHandler - FloatCreditPurchasedEvent");
6363

6464
return await PolicyFactory.ExecuteWithPolicyAsync(async () => {
6565
FloatActivityCommands.RecordCreditPurchaseCommand command =
@@ -72,7 +72,7 @@ private async Task<Result> HandleSpecificDomainEvent(FloatDomainEvents.FloatCred
7272

7373
private async Task<Result> HandleSpecificDomainEvent(TransactionDomainEvents.TransactionCostInformationRecordedEvent domainEvent, CancellationToken cancellationToken){
7474

75-
IAsyncPolicy<Result> retryPolicy = PolicyFactory.CreatePolicy(2, policyTag: "TransactionDomainEventHandler - TransactionCostInformationRecordedEvent");
75+
IAsyncPolicy<Result> retryPolicy = PolicyFactory.CreatePolicy(policyTag: "TransactionDomainEventHandler - TransactionCostInformationRecordedEvent");
7676

7777
return await PolicyFactory.ExecuteWithPolicyAsync(async () => {
7878
FloatActivityCommands.RecordTransactionCommand command = new(domainEvent.EstateId,
@@ -84,14 +84,19 @@ private async Task<Result> HandleSpecificDomainEvent(TransactionDomainEvents.Tra
8484

8585
private async Task<Result> HandleSpecificDomainEvent(TransactionDomainEvents.TransactionHasBeenCompletedEvent domainEvent,
8686
CancellationToken cancellationToken) {
87-
CalculateFeesForTransactionCommand command = new(domainEvent.TransactionId, domainEvent.CompletedDateTime, domainEvent.EstateId, domainEvent.MerchantId);
87+
88+
IAsyncPolicy<Result> retryPolicy = PolicyFactory.CreatePolicy(policyTag: "TransactionDomainEventHandler - TransactionHasBeenCompletedEvent");
8889

89-
return await this.Mediator.Send(command, cancellationToken);
90+
return await PolicyFactory.ExecuteWithPolicyAsync(async () => {
91+
CalculateFeesForTransactionCommand command = new(domainEvent.TransactionId, domainEvent.CompletedDateTime, domainEvent.EstateId, domainEvent.MerchantId);
92+
93+
return await this.Mediator.Send(command, cancellationToken);
94+
}, retryPolicy, "TransactionDomainEventHandler - TransactionHasBeenCompletedEvent");
9095
}
9196

9297
private async Task<Result> HandleSpecificDomainEvent(TransactionDomainEvents.MerchantFeePendingSettlementAddedToTransactionEvent domainEvent,
9398
CancellationToken cancellationToken) {
94-
IAsyncPolicy<Result> retryPolicy = PolicyFactory.CreatePolicy(2, policyTag: "TransactionDomainEventHandler - MerchantFeePendingSettlementAddedToTransactionEvent");
99+
IAsyncPolicy<Result> retryPolicy = PolicyFactory.CreatePolicy(policyTag: "TransactionDomainEventHandler - MerchantFeePendingSettlementAddedToTransactionEvent");
95100

96101
return await PolicyFactory.ExecuteWithPolicyAsync(async () => {
97102
SettlementCommands.AddMerchantFeePendingSettlementCommand command =
@@ -105,7 +110,7 @@ private async Task<Result> HandleSpecificDomainEvent(TransactionDomainEvents.Mer
105110

106111
private async Task<Result> HandleSpecificDomainEvent(TransactionDomainEvents.SettledMerchantFeeAddedToTransactionEvent domainEvent,
107112
CancellationToken cancellationToken) {
108-
IAsyncPolicy<Result> retryPolicy = PolicyFactory.CreatePolicy(2, policyTag: "TransactionDomainEventHandler - SettledMerchantFeeAddedToTransactionEvent");
113+
IAsyncPolicy<Result> retryPolicy = PolicyFactory.CreatePolicy(policyTag: "TransactionDomainEventHandler - SettledMerchantFeeAddedToTransactionEvent");
109114

110115
return await PolicyFactory.ExecuteWithPolicyAsync(async () => {
111116
AddSettledFeeToSettlementCommand command = new AddSettledFeeToSettlementCommand(
@@ -117,7 +122,7 @@ private async Task<Result> HandleSpecificDomainEvent(TransactionDomainEvents.Set
117122
private async Task<Result> HandleSpecificDomainEvent(SettlementDomainEvents.MerchantFeeSettledEvent domainEvent,
118123
CancellationToken cancellationToken)
119124
{
120-
IAsyncPolicy<Result> retryPolicy = PolicyFactory.CreatePolicy(2, policyTag: "TransactionDomainEventHandler - MerchantFeeSettledEvent");
125+
IAsyncPolicy<Result> retryPolicy = PolicyFactory.CreatePolicy(policyTag: "TransactionDomainEventHandler - MerchantFeeSettledEvent");
121126

122127
return await PolicyFactory.ExecuteWithPolicyAsync(async () => {
123128
AddSettledMerchantFeeCommand command = new(domainEvent.TransactionId, domainEvent.CalculatedValue,

0 commit comments

Comments
 (0)