CustomResults.cs 2.7 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970
  1. using SharedKernel.Results;
  2. namespace Web.Api.Common;
  3. public static class CustomResults
  4. {
  5. public static IResult Problem(Result result)
  6. {
  7. if (result.IsSuccess)
  8. {
  9. throw new InvalidOperationException();
  10. }
  11. return Results.Problem(
  12. title: GetTitle(result.Error),
  13. detail: result.Error.Description,
  14. type: GetType(result.Error.Type),
  15. statusCode: GetStatusCode(result.Error.Type),
  16. extensions: GetErrors(result)
  17. );
  18. static string GetTitle(Error error) => error.Type switch
  19. {
  20. ErrorType.Validation => error.Code,
  21. ErrorType.Problem => error.Code,
  22. ErrorType.Unauthorized => error.Code,
  23. ErrorType.NotFound => error.Code,
  24. ErrorType.Forbidden => error.Code,
  25. ErrorType.Conflict => error.Code,
  26. ErrorType.MethodNotAllowed => error.Code,
  27. _ => "Server failure"
  28. };
  29. static string GetType(ErrorType errorType) => errorType switch
  30. {
  31. ErrorType.Validation => "https://tools.ietf.org/html/rfc7231#section-6.5.1",
  32. ErrorType.Problem => "https://tools.ietf.org/html/rfc7231#section-6.5.1",
  33. ErrorType.Unauthorized => "https://tools.ietf.org/html/rfc7235#section-3.1",
  34. ErrorType.NotFound => "https://tools.ietf.org/html/rfc7231#section-6.5.4",
  35. ErrorType.Forbidden => "https://tools.ietf.org/html/rfc7231#section-6.5.3",
  36. ErrorType.Conflict => "https://tools.ietf.org/html/rfc7231#section-6.5.8",
  37. ErrorType.MethodNotAllowed => "https://tools.ietf.org/html/rfc7231#section-6.5.5",
  38. _ => "https://tools.ietf.org/html/rfc7231#section-6.6.1"
  39. };
  40. static int GetStatusCode(ErrorType errorType) => errorType switch
  41. {
  42. ErrorType.Validation or ErrorType.Problem => StatusCodes.Status400BadRequest,
  43. ErrorType.Unauthorized => StatusCodes.Status401Unauthorized,
  44. ErrorType.NotFound => StatusCodes.Status404NotFound,
  45. ErrorType.Forbidden => StatusCodes.Status403Forbidden,
  46. ErrorType.Conflict => StatusCodes.Status409Conflict,
  47. ErrorType.MethodNotAllowed => StatusCodes.Status405MethodNotAllowed,
  48. _ => StatusCodes.Status500InternalServerError
  49. };
  50. static Dictionary<string, object?>? GetErrors(Result result)
  51. {
  52. if (result.Error is not ValidationError validationError)
  53. {
  54. return null;
  55. }
  56. return new Dictionary<string, object?>
  57. {
  58. { "errors", validationError.Errors }
  59. };
  60. }
  61. }
  62. }