-
Notifications
You must be signed in to change notification settings - Fork 111
/
Program.cs
105 lines (87 loc) · 3.28 KB
/
Program.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
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
using Hellang.Middleware.ProblemDetails;
using Microsoft.AspNetCore.Mvc;
var builder = WebApplication.CreateBuilder(args);
builder.Services.AddControllers();
builder.Services.AddEndpointsApiExplorer();
builder.Services.AddSwaggerGen();
// Configure problem details
builder.Services.AddProblemDetails(options =>
{
// Only include exception details in a development environment. There's really no need
// to set this as it's the default behavior. It's just included here for completeness :)
options.IncludeExceptionDetails = (ctx, ex) => builder.Environment.IsDevelopment();
// This will map UserNotFoundException to the 404 Not Found status code and return custom problem details.
options.Map<UserNotFoundException>(ex => new ProblemDetails
{
Title = "Could not find user",
Status = StatusCodes.Status404NotFound,
Detail = ex.Message,
});
// This will map NotImplementedException to the 501 Not Implemented status code.
options.MapToStatusCode<NotImplementedException>(StatusCodes.Status501NotImplemented);
// You can configure the middleware to re-throw certain types of exceptions, all exceptions or based on a predicate.
// This is useful if you have upstream middleware that needs to do additional handling of exceptions.
options.Rethrow<NotSupportedException>();
// You can configure the middleware to ingore any exceptions of the specified type.
// This is useful if you have upstream middleware that needs to do additional handling of exceptions.
// Note that unlike Rethrow, additional information will not be added to the exception.
options.Ignore<DivideByZeroException>();
// Because exceptions are handled polymorphically, this will act as a "catch all" mapping, which is why it's added last.
// If an exception other than NotImplementedException and HttpRequestException is thrown, this will handle it.
options.MapToStatusCode<Exception>(StatusCodes.Status500InternalServerError);
});
var app = builder.Build();
// Add ProblemDetailsMiddleware to the application pipeline
app.UseProblemDetails();
app.UseRouting();
if (app.Environment.IsDevelopment())
{
app.UseSwagger();
app.UseSwaggerUI();
}
app.MapGet("/maptodetail", () =>
{
throw new UserNotFoundException();
});
app.MapGet("/maptostatus", () =>
{
throw new NotImplementedException();
});
app.MapGet("/rethrow", () =>
{
throw new NotSupportedException("Invalid operation");
});
app.MapGet("/ignore", () =>
{
throw new DivideByZeroException();
});
app.MapGet("/error", () =>
{
throw new Exception();
});
app.MapGet("/result", () =>
{
var problem = new OutOfCreditProblemDetails
{
Type = "https://example.com/probs/out-of-credit",
Title = "You do not have enough credit.",
Detail = "Your current balance is 30, but that costs 50.",
Instance = "/account/12345/msgs/abc",
Balance = 30.0m,
Accounts = { "/account/12345", "/account/67890" }
};
return Results.BadRequest(problem);
});
app.Run();
public class OutOfCreditProblemDetails : ProblemDetails
{
public OutOfCreditProblemDetails()
{
Accounts = new List<string>();
}
public decimal Balance { get; set; }
public ICollection<string> Accounts { get; }
}
public class UserNotFoundException : Exception
{
}