Обработка исключений в Spring 5 Reactive kotlin - PullRequest
0 голосов
/ 27 июня 2018

Я врезался в стену и не нашел никакого разумного решения, так что, возможно, кто-то попробует. Я написал простой сервис, интегрирующийся с github, и мне было трудно понять, как правильно работать с исключениями в реактивном слове. Как только я получил ожидаемую ошибку статуса 404 от Github, я хотел бы выдать свое собственное исключение и представить его клиенту вместо действительного ответа, я проверяю статусы кода ответа от github, и единственное, что я получаю на своем сайте, это:

2018-06-26 21: 45: 08.286 ПРЕДУПРЕЖДЕНИЕ 8336 --- [ctor-http-nio-2] .a.w.r.e.DefaultErrorWebExceptionHandler: не удалось обработать запрос [GET http://localhost:8080/repositories/sh1nen/no-exist]: Ответ статус 404

Вот мой простой метод, отвечающий за выполнение запросов и обработку кодов ошибок соответствующим образом.

fun findSpecificOwnerRepository(owner: String, repositoryName: String) = webClient
    .get()
    .uri("/repos/$owner/$repositoryName")
    .retrieve()
    .onStatus({ httpStatus -> HttpStatus.NOT_FOUND == httpStatus }, { Mono.error(RepositoryNotFoundException(reason = "Repository $repositoryName not found.")) })
    .onStatus({ httpStatus -> HttpStatus.SERVICE_UNAVAILABLE == httpStatus }, { Mono.error(RepositoryNotFoundException(reason = "Service unavailable.")) })
    .bodyToMono(GithubRepositoryResponse::class.java)

Вот мое пользовательское исключение, которое в основном не представляет ресурсов на моем сайте для представления:

internal class RepositoryNotFoundException(
    status: HttpStatus = HttpStatus.NOT_FOUND,
    reason: String? = null,
    throwable: Throwable? = null) : ResponseStatusException(status, reason, throwable)

И сама конечная точка, которую я нажимаю, чтобы получить ответ:

@GetMapping("{owner}/{repositoryName}")
fun findSpecificOwnerRepository(@PathVariable owner: String, @PathVariable repositoryName: String) = githubClient
    .findSpecificOwnerRepository(owner, repositoryName)

Я хотел бы получить 404 с жестко закодированным сообщением. Нужен ли какой-нибудь специальный @ExceptionHandler в контроллере для обработки моего пользовательского исключения?

  1. Есть ли шанс реализовать ситуацию, когда, например, github не в состоянии справиться с запросами, которые я обслуживаю, и выдает в этом случае также какое-то исключение? Как это можно реализовать?

1 Ответ

0 голосов
/ 05 июля 2018

Я не уверен, что вы действительно что-то упустили для пункта 1), поскольку исключение, которое вы расширяете, должно, естественно, привести к 404 вашим клиентам, если я правильно помню.

Что касается пункта 2, все зависит от того, как ваш источник обрабатывает ограничение скорости. В случае с GitHub, он вернет 403, как только вы достигнете пределов скорости попадания, но вы можете быть очень осторожны и проверить пользовательские заголовки. Смотри https://developer.github.com/v3/#rate-limiting

Таким образом, самый простой способ, которым это будет реализовано, это onStatus. В качестве альтернативы, вы можете проверить весь ответ и действовать соответствующим образом, используя exchange вместо retrieve и flatMap, получая в результате Mono (который генерирует весь ответ сервера).

...