-
Notifications
You must be signed in to change notification settings - Fork 4
/
Copy pathCQRSExceptionTranslationMiddleware.cs
60 lines (52 loc) · 2.04 KB
/
CQRSExceptionTranslationMiddleware.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
using System.Collections.Immutable;
using LeanCode.Contracts;
using LeanCode.Contracts.Validation;
using LeanCode.CQRS.Execution;
using LeanCode.Logging;
using LeanCode.OpenTelemetry;
using Microsoft.AspNetCore.Http;
namespace LeanCode.CQRS.AspNetCore.Middleware;
public class CQRSExceptionTranslationMiddleware
{
private readonly ILogger<CQRSExceptionTranslationMiddleware> logger;
private readonly CQRSMetrics metrics;
private readonly RequestDelegate next;
public CQRSExceptionTranslationMiddleware(
ILogger<CQRSExceptionTranslationMiddleware> logger,
CQRSMetrics metrics,
RequestDelegate next
)
{
this.logger = logger;
this.metrics = metrics;
this.next = next;
}
public async Task InvokeAsync(HttpContext httpContext)
{
var cqrsMetadata = httpContext.GetCQRSObjectMetadata();
var cqrsPayload = httpContext.GetCQRSRequestPayload();
if (cqrsMetadata.ObjectKind != CQRSObjectKind.Command)
{
throw new InvalidOperationException("CQRSExceptionTranslationMiddleware may be used only for commands.");
}
try
{
await next(httpContext);
}
catch (CommandExecutionInvalidException ex)
{
using var activity = LeanCodeActivitySource.StartMiddleware("ExceptionTranslation");
activity?.SetTag("error.code", ex.ErrorCode);
var result = WrapInCommandResult(ex);
logger.Warning("Command {@Command} is not valid with result {@Result}", cqrsPayload.Payload, result);
var executionResult = ExecutionResult.WithPayload(result, StatusCodes.Status422UnprocessableEntity);
cqrsPayload.SetResult(executionResult);
metrics.CQRSFailure(CQRSMetrics.ValidationFailure);
}
}
private static CommandResult WrapInCommandResult(CommandExecutionInvalidException ex)
{
var error = new ValidationError(propertyName: "", ex.Message, ex.ErrorCode);
return new CommandResult(ImmutableList.Create(error));
}
}