使用RequestHandlerRetryAdvice重试Web服务操作

1.引言

有时在调用Web服务时,我们可能有兴趣在发生错误的情况下重试该操作。 使用Spring Integration时,我们可以使用RequestHandlerRetryAdvice类实现此功能。 此类将使我们在放弃并引发异常之前重试指定次数的操作。 这篇文章将向您展示如何完成此任务。

测试应用程序将调用Web服务,如果响应失败,它将等待指定的时间,然后重试,直到收到响应或达到重试限制为止。 如果达到限制,失败的请求将被存储到数据库中。 主要,这篇文章显示以下示例:

  • 使用出站网关调用Web服务
  • 配置重试建议以在必要时重试该操作
  • MongoDB集成。

该应用程序的源代码可以在github上找到。

您还可以在github上获取由应用程序调用的Web服务项目的源代码。

2.Web服务调用

用例 :客户端调用Web服务并接收响应。

grafic1

该请求通过“系统入口”网关进入消息传递系统。 然后,它到达出站网关,调用Web服务并等待响应。 收到响应后,将其发送到响应通道。

上图是此配置的结果:

<context:component-scan base-package="xpadro.spring.integration" /><!-- Initial service request -->
<int:gateway id="systemEntry" default-request-channel="requestChannel"service-interface="xpadro.spring.integration.gateway.ClientService" /><int:channel id="requestChannel"><int:queue />
</int:channel><int-ws:outbound-gateway id="marshallingGateway"request-channel="requestChannel" reply-channel="responseChannel"uri="http://localhost:8080/spring-ws/orders" marshaller="marshaller"unmarshaller="marshaller"><int:poller fixed-rate="500" />
</int-ws:outbound-gateway><oxm:jaxb2-marshaller id="marshaller" contextPath="xpadro.spring.integration.types" /><!-- Service is running - Response received -->
<int:channel id="responseChannel" /><int:service-activator ref="clientServiceActivator" method="handleServiceResult" input-channel="responseChannel" />

映射到响应通道的是一个服务激活器,它仅记录结果。

TestInvocation.java:将请求发送到入口网关

@ContextConfiguration({"classpath:xpadro/spring/integration/config/int-config.xml","classpath:xpadro/spring/integration/config/mongodb-config.xml"})
@RunWith(SpringJUnit4ClassRunner.class)
public class TestInvocation {private Logger logger = LoggerFactory.getLogger(this.getClass());@Autowiredprivate ClientService service;@Testpublic void testInvocation() throws InterruptedException, ExecutionException {logger.info("Initiating service request...");ClientDataRequest request = new ClientDataRequest();request.setClientId("123");request.setProductId("XA-55");request.setQuantity(new BigInteger("5"));service.invoke(request);logger.info("Doing other stuff...");Thread.sleep(60000);}
}

使用此配置,如果服务调用失败,则将引发MessagingException并将其发送到错误通道。 在下一节中,我们将添加重试配置。

3.添加重试建议

用例 :初始请求失败,因为该服务未激活。 我们将重试该操作,直到从服务收到响应为止。

在这种情况下,我们需要将重试建议添加到Web服务出站网关:

<int-ws:outbound-gateway id="marshallingGateway" interceptor="clientInterceptor"request-channel="requestChannel" reply-channel="responseChannel"uri="http://localhost:8080/spring-ws/orders" marshaller="marshaller"unmarshaller="marshaller"><int:poller fixed-rate="500" /><int-ws:request-handler-advice-chain><ref bean="retryAdvice" /></int-ws:request-handler-advice-chain>
</int-ws:outbound-gateway>

现在,Web服务出站网关会将调用委派给重试建议,重试建议将按指定的次数尝试操作多次,直到从服务获得响应为止。 让我们定义重试建议:

<bean id="retryAdvice" class="org.springframework.integration.handler.advice.RequestHandlerRetryAdvice" ><property name="retryTemplate"><bean class="org.springframework.retry.support.RetryTemplate"><property name="backOffPolicy"><bean class="org.springframework.retry.backoff.FixedBackOffPolicy"><property name="backOffPeriod" value="4000" /></bean></property><property name="retryPolicy"><bean class="org.springframework.retry.policy.SimpleRetryPolicy"><property name="maxAttempts" value="4" /></bean></property></bean></property>
</bean>

为了实现其目标,建议使用RetryTemplate,该模板由Spring Retry项目提供。 我们可以通过定义退避重试策略来自定义其行为。

退避政策 :在每次重试之间建立一段时间。 更有趣的类型是:

  • FixedBackOffPolicy :在我们的示例中使用。 每次重试之间将等待相同的指定时间。
  • ExponentialBackOffPolicy :从确定的时间量开始,它将使每次重试的时间加倍。 您可以通过建立乘数来更改默认行为。

重试策略 :确定将重试失败操作的次数。 一些类型:

  • SimpleRetryPolicy :在我们的示例中使用。 指定重试次数限制。
  • ExceptionClassifierRetryPolicy :允许我们根据引发的异常来建立不同的maxAttempts。
  • TimeoutRetryPolicy :将继续重试,直到达到超时为止。

4,不走运,记录失败的请求

用例 :服务将无法恢复,无法将请求存储到数据库中。

adv1

配置的最后部分如下:

<!-- Log failed invocation -->
<int:service-activator ref="clientServiceActivator" method="handleFailedInvocation" input-channel="errorChannel" output-channel="logChannel" /><int:channel id="logChannel" /><bean id="mongoDbFactory" class="org.springframework.data.mongodb.core.SimpleMongoDbFactory"><constructor-arg><bean class="com.mongodb.Mongo"/></constructor-arg><constructor-arg value="test"/>
</bean><int-mongodb:outbound-channel-adapter id="mongodbAdapter" channel="logChannel"collection-name="failedRequests" mongodb-factory="mongoDbFactory" />

订阅错误通道的服务激活器将检索失败的消息并将其发送到出站适配器,出站适配器会将其插入到mongoDB数据库中。 服务激活器:

public Message<?> handleFailedInvocation(MessagingException exception) {logger.info("Failed to succesfully invoke service. Logging to DB...");return exception.getFailedMessage();
}

如果我们未能成功从服务获得响应,则该请求将存储到数据库中:

mongodb

六,结论

我们已经了解了Spring Integration如何从Spring Retry项目获得支持以实现操作的重试。 我们使用了int-ws:request-handler-advice-chain ,但是'int'命名空间也支持此元素,以将该功能添加到其他类型的端点。

参考:在XavierPadró的Blog博客上,我们的JCG合作伙伴 Xavier Padro 使用RequestHandlerRetryAdvice重试了Web服务操作 。

翻译自: https://www.javacodegeeks.com/2014/02/retry-web-service-operations-with-requesthandlerretryadvice.html

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/364861.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

ASP.NET MVC如何做一个简单的非法登录拦截

摘要&#xff1a;做网站的时候&#xff0c;经常碰到这种问题&#xff0c;一个没登录的用户&#xff0c;却可以通过localhost:23244/Main/Index的方式进入到网站的内部&#xff0c;查看网站的信息。我们知道&#xff0c;这是极不安全的&#xff0c;那么如何对这样的操作进行拦截…

无法创建java虚拟机_创建java虚拟机失败的解决方法

创建java虚拟机失败的解决方法解决问题的步骤&#xff1a;1、从eclipse文件夹中打开eclipse.ini文件2、修改–launcher.XXMaxPermSize属性3、将值改为512m即可配置文件格式&#xff1a;-startupplugins/org.eclipse.equinox.launcher_1.3.0.v20120522-1813.jar--launcher.libra…

java 泛型嵌套泛型_Java泛型嵌套

package com.study.generics;//泛型的嵌套使用public class GenericsDemo06 {public static void main(String []args) {GenericsComputer computer new GenericsComputer("联想笔记本电脑","联想");GenericsPeople people new GenericsPeople(computer)…

[18/11/24]类和对象

1、类和对象 类可以看做是一个模版&#xff0c;或者图纸&#xff0c;系统根据类的定义来造出对象。我们要造一个汽车&#xff0c;怎么样造?类就是这个图纸&#xff0c;规定了汽车的详细信息&#xff0c;然后根据图纸将汽车造出来。 类&#xff1a;class。 对象&#xff1a;Obj…

小程序如何传数组数据到vs后台中

首先小程序要跟vs运行的状态打通&#xff0c;首先要修改配置&#xff0c;也就是说调试的时候&#xff0c;小程序一使用Post请求后台的方法时就能让vs进入调试状态。 1.修改vs中的配置&#xff0c;注意这个.vs文件&#xff0c;如图&#xff1a; 找到这个文件 然后打开这个文件&a…

使用Spring的Hibernate构建Java Web应用程序

这篇文章将展示如何在Spring环境中使用带有Hibernate ORM的MYSQL DB创建学生注册应用程序。 这是一个简单的应用程序&#xff0c;旨在在注册期间从用户收集输入详细信息&#xff0c;将详细信息保存在MYSQL DB中&#xff0c;并在登录期间对它们进行身份验证。 1.使用Maven模板创…

201771010102 常惠琢 《面向对象程序设计(java)》第十三周学习总结

实验十三 图形界面事件处理技术 实验时间 2018-11-22 1、实验目的与要求 (1) 掌握事件处理的基本原理&#xff0c;理解其用途&#xff1b; (2) 掌握AWT事件模型的工作机制&#xff1b; (3) 掌握事件处理的基本编程模型&#xff1b; (4) 了解GUI界面组件观感设置方法&#xff1…

vue中使用codemirror

https://blog.csdn.net/oumaharuki/article/details/79268498 别人的记载&#xff0c;写的很不错&#xff0c;还有下载的方法 以下是自己使用过的&#xff0c;做出来的例子&#xff1a; 做出来的效果图&#xff1a; 记住使用之前要npm下载哦 npm install vue-codemirror --s…

使用不可序列化的属性序列化Java对象

人们可能有多种原因想要使用自定义序列化而不是依赖Java的默认序列化。 最常见的原因之一是为了提高性能&#xff0c;但是编写自定义序列化的另一个原因是不支持默认序列化机制。 具体来说&#xff0c;如本博文所述&#xff0c;自定义序列化可用于允许将较大的对象序列化&#…

使用Spring跟踪异常–第2部分–委托模式

在上一个博客中 &#xff0c;我开始谈论需要弄清楚您的应用程序在生产环境中是否行为异常。 我说过&#xff0c;监视应用程序的一种方法是检查其日志文件是否存在异常&#xff0c;如果发现异常&#xff0c;则采取适当的措施。 显然&#xff0c;日志文件会占用数百兆的磁盘空间&…

aix java home_java程序员工作日子一(java_home 配置)

安装 JDK 和设置 JAVA_HOME如果您尚未在系统中安装 Java Development Kit (JDK) 和/或尚未设置 JAVA_HOME&#xff0c;则在尝试安装 Java CAPS 之前&#xff0c;需要安装 JDK 并设置 JAVA_HOME。以下任务提供了在 UNIX 或 Windows 系统上安装 JDK 和设置 JAVA_HOME 所需的信息。…

MySQL 开启远程访问权限 | 宝塔系统

1.进入 MySQL 管理菜单 2.选择权限为所有人 转载于:https://www.cnblogs.com/Skrillex/p/10728681.html

基于vue实现百度离线地图

基于vue实现百度离线地图 1. 百度地图API文件获取 有网络 的情况下&#xff0c;需引入百度地图API文件。如下&#xff1a; <script type"text/javascript" src"http://api.map.baidu.com/api?v3.0&ak您的密钥"></script> 无网络 的情况下…

日期插件rolldate.js的使用

日期插件rolldate.js的使用 下载地址&#xff1a;http://www.jq22.com/jquery-info19834 效果&#xff1a; 代码&#xff1a; <!DOCTYPE html> <html lang"en"><head><meta charset"UTF-8" /><meta name"viewport" …

Java8中 Parallel Streams 的陷阱 [译]

转载自https://www.cnblogs.com/imyijie/p/4478074.html Java8 提供了三个我们渴望的重要的功能:Lambdas 、 Stream API、以及接口的默认方法。不过我们很容易滥用它们甚至破坏自己的代码。 今天我们来看看Stream api&#xff0c;尤其是 parallel streams。这篇文章概述了其中的…

ObjectStreamClass:监视Java对象的序列化

ObjectStreamClass可以是有用的类&#xff0c;用于分析JVM中加载的序列化类的序列化特征。 这篇文章介绍了此类提供的有关已加载序列化类的一些信息。 ObjectStreamClass提供了两个用于查找类的静态方法&#xff1a; lookup&#xff08;class&#xff09;和lookupAny&#xff…

00005在java结果输出_Java-005-运算符详解

计算机的最基本用途之一就是执行数学运算,作为一门计算机语言Java也提供了套丰富的运算符来操纵变量, 可以把运算符分成以下几组算术运算符、关系运算符、位运算符、逻辑运算符、赋值运算符、其他运算符。①算术运算符用在数学表达式中它们的作用和在数学中的作用一样 表格中的…

鼠标拖动改变DIV等网页元素的大小的最佳实践

1.初次实现 1.1 html代码 <html xmlns"http://www.w3.org/1999/xhtml" xml:lang"en" lang"en"><head><meta http-equiv"Content-Type" content"text/html; charsetutf-8" /><title>div change wid…

[WC2006]水管局长

水管局长 题目链接&#xff1a;https://www.luogu.org/problemnew/show/P4172#sub LCT 显然两个点的路径上的边最大要最小在该图最小生成树上 正删倒加&#xff0c;倒着做变成加边操作 加边时判断一下是否能形成更优的生成树&#xff0c;用LCT删除和连接操作即可 1 #include<…

JDBC 4.0鲜为人知的Clob.free()和Blob.free()方法

在会议上谈论jOOQ时&#xff0c;我总是展示此幻灯片&#xff0c;其中包含许多人们经常犯的非常常见的JDBC错误&#xff1a; 此图中的六个常见的JDBC错误 您可以找到错误吗&#xff1f; 其中一些是显而易见的&#xff0c;例如&#xff1a; 第4行&#xff1a;由于第3行的连接…