繁体   English   中英

在 Spring Integration 中使用 Http Outbound Gateway 进行错误处理

[英]Error handling with Http Outbound Gateway in Spring Integration

我试图了解在 Spring Integration 中应该如何处理错误。 我找到了有关errorChannel 文档,我尝试使用它但未捕获异常。

这是我的 HTTP 出站网关:

<int-http:outbound-gateway id="orderRequestHttpGateway"
                               request-channel="orders-channel"
                               url="${url}"
                               http-method="POST"
                               expected-response-type="java.lang.String"
                               reply-timeout='5000'
                               reply-channel='pushed-channel'
                               charset="UTF-8">
</int-http:outbound-gateway>

我不明白我应该在哪里捕获这个组件抛出的异常(比如 500 HTTP 错误)

该路由由poller启动。 我尝试添加一个error-channel属性:

<int:inbound-channel-adapter channel="orders-trigger-channel" expression="''">
        <int:poller fixed-delay="${poller}" error-channel="errorChannel"/>
</int:inbound-channel-adapter>

我尝试使用自定义错误通道。 我还尝试覆盖现有的 errorChannel:

<int:channel id="errorChannel"/>
<int:outbound-channel-adapter id="errorChannelHandler"
                               ref="errorManager"
                               method="foo"
                               channel="errorChannel"/>

到目前为止,我一直收到MessageHandlingException并且我无法捕获它们以正确处理它们。

您只能在调用者线程中或在拥有try...catch的地方捕获异常 - Spring Integration 与纯 Java 没有什么不同:每当我们有try...catch时,我们都会捕获异常。

根据您的描述, <poller>上的error-channel="errorChannel"是要走的路,如果您没有任何其他线程向下游移动,则确实将这样的MessageHandlingException抛出给轮询器并包装到ErrorMessage中被发送到配置的那个errorChannel

它是一个MessageHandlingException因为我们在 Spring Integration 中处理Messaging ,这样的异常携带一些关于流和失败消息的上下文和重要信息。 您的500 HTTP error只是该消息中的一个cause 因此,当您捕获并处理ErrorMessage您应该查看其堆栈跟踪以获取要解析的信息。

另一方面,您可以通过ExpressionEvaluatingRequestHandlerAdviceRequestHandlerRetryAdvice缩小错误处理的范围: https : RequestHandlerRetryAdvice 。 html#message-handler-advice-chain

Int-http:outbound-gateway默认有error-handler ,你可以使用这个 error-handler 来处理outbound 的错误 在您的示例中,将错误处理程序添加到 int-http:outbound-gateway 中,示例名称为 errorHandler 类名,如下所示:

<int-http:outbound-gateway id="orderRequestHttpGateway"
                               request-channel="orders-channel"
                               url="${url}"
                               http-method="POST"
                               expected-response-type="java.lang.String"
                               reply-timeout='5000'
                               reply-channel='pushed-channel'
                               charset="UTF-8"
                               error-handler="nameOfErrorHandler">
</int-http:outbound-gateway>

然后使用 nameOfErrorHandler 创建新类,扩展DefaultResponseErrorHandler如下所示

@Component("nameOfErrorHandler")
public class NameOfErrorHandler extends DefaultResponseErrorHandler {
    public NameOfErrorHandler() {
    }

    public void handleError(ClientHttpResponse response) throws IOException {

        if (response.getStatusCode() == HttpStatus.BAD_REQUEST) {
            throw new AccessDeniedException("Custom Message");
        } else if (response.getStatusCode() == HttpStatus.FORBIDDEN) {
            throw new AccessDeniedException("Custom Message");
        } else if (response.getStatusCode() == HttpStatus.NOT_ACCEPTABLE) {
            throw new ChannelsLimitExceededException("Custom Message");
        } else if (response.getStatusCode() == HttpStatus.PROXY_AUTHENTICATION_REQUIRED) {
            throw new PerTransactionLimitExceeded("Custom Message");
        } else if (response.getStatusCode() == HttpStatus.REQUEST_TIMEOUT) {
            throw new DailyLimitExceededException("Custom Message");
        } else if (response.getStatusCode() == HttpStatus.CONFLICT) {
            throw new MonthlyLimitExceeded("Custom Message");
        } else if (response.getStatusCode() == HttpStatus.GONE) {
            throw new DuplicateReqIdException("Custom Message");
        } else {
            throw new AccessInternalException("Internal server error");
        }
    }
}

注意:这一切都会抛出新的一些异常,这些异常被链中定义的第一个错误通道捕获

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM