Как мне возвращать ошибки в asp. net core API - PullRequest
1 голос
/ 20 июня 2020

Я работаю над своим частным проектом, используя. Net Core и Angular, и у меня есть небольшая проблема с тем, как мне возвращать ошибки.

Мой бэкэнд имеет слои (контроллеры, службы, репозитории и сущность). Я создал общий объект ответа, который хочу вернуть. В моем методе обслуживания я устанавливаю различные ошибки, такие как «NotFound» или «Внутренняя ошибка сервера» в качестве StatusCode.

Я не хочу переключать регистр на StatusCode и возвращать другую ошибку на основе этого в контроллере, потому что я не думаю, что это хорошее решение. Возврат объекта ApiResponse приведет к тому, что у меня всегда будет код 200, и чтобы знать, есть ли какая-либо ошибка, мне нужно проверить код состояния возвращенного объекта в Angular. Не знаю, хорошее ли это решение.

И я хочу сохранить эти слои. Я хочу, чтобы контроллер просто обрабатывал запрос, служба имела все logi c и репозиторий для выполнения действий CRUD.

Итак, как мне возвращать ошибки из моего уровня обслуживания в контроллер?

Это одна из версий моего метода контроллера.

    [Authorize]
    [ApiValidationFilter]
    [HttpPost("updateFacebookUrl/")]
    public async Task<ApiResponse> UpdateFacebookURL([FromBody] UpdateURLVm updateURLVm)
    {
      return await _userInfoService.UpdateFacebookURL(updateURLVm);
    }

И это вторая версия моего метода контроллера.

    [Authorize]
    [ApiValidationFilter]
    [HttpPost("updateInstagramUrl/")]
    public async Task<IActionResult> UpdateInstagramURL([FromBody] UpdateURLVm updateURLVm)
    {
      var result = await _userInfoService.UpdateInstagramURL(updateURLVm);

      if (result.StatusCode != (int)HttpStatusCode.OK)
      {
        return BadRequest(result);
      }

      return Ok(result);
    }

Это мой метод обслуживания.

    public ApiResponse UpdateInstagramURL(UpdateURLVm updateURLVm)
    {
      try
      {
        var user = _unitOfWork.userRepository.FindByCondition(x => x.Id == updateURLVm.UserId).FirstOrDefault();

        if (user == null)
          return new ApiResponse((int)HttpStatusCode.NotFound, "User not found");

        user.Instagram = updateURLVm.URL;

        _unitOfWork.userRepository.Update(user);
        _unitOfWork.Complete();

        return new ApiResponse((int)HttpStatusCode.OK);
      }
      catch (Exception ex)
      {
        return new ApiResponse((int)HttpStatusCode.InternalServerError, "Something went wrong");
      }
    }

Возврат объект.

 public class ApiResponse
  {
    public int StatusCode { get; private set; }

    [JsonProperty(DefaultValueHandling = DefaultValueHandling.Ignore)]
    public string Message { get; private set; }

    [JsonProperty(DefaultValueHandling = DefaultValueHandling.Ignore)]
    public object Result { get; private set; }

    public ApiResponse(int statusCode, string message)
        : this(statusCode)
    {
      this.Message = message;
    }

    public ApiResponse(object result) :
      this(200)
    {
      Result = result;
    }

    public ApiResponse(int statusCode)
    {
      this.StatusCode = statusCode;
    }
  }

1 Ответ

0 голосов
/ 20 июня 2020

Я бы выбрал исключение в своей основной службе или репозитории и позволил бы промежуточному программному обеспечению обработать его. ApiError - это мой собственный класс, и некоторые вещи могут быть не такими, как это было написано с. NET Core 2.2 Я полагаю, вы используете 3.x. И быстрое примечание (если можно) эти URL-адреса конечных точек api не очень RESTful ..

   public void Configure(IApplicationBuilder app, IHostingEnvironment env)
    {
        app.UseExceptionHandler(appBuilder =>
        {
            appBuilder.Run(async context => {
                var ex = context.Features.Get<IExceptionHandlerPathFeature>();
                if (ex?.Error is NullReferenceException)
                    context.Response.StatusCode = 404;
                else if (ex?.Error is InvalidOperationException)
                    context.Response.StatusCode = 400;
                else
                    context.Response.StatusCode = 500;

                context.Response.ContentType = "application/json";

                ApiError error = new ApiError()
                {
                    Code = context.Response.StatusCode,
                    Message = env.IsDevelopment() ? ex?.Error.Message : "An unexpected error happened. Try again later."
                };

                await context.Response.WriteAsync(JsonConvert.SerializeObject(error)).ConfigureAwait(false);
            });
        });
   }
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...