记Spring HTTP Invoker远程调用的使用(二)基于Servlet方式,配置servlet映射url-pattern实现

目录
前言

一、概念

二、代码实现

[1. 服务端实现](#1. 服务端实现)

[2. 客户端实现](#2. 客户端实现)


前言

本篇接上一篇记Spring HTTP Invoker远程调用的使用(一)基于Url映射方式,DispatcherServlet统一处理实现-CSDN博客https://blog.csdn.net/u011529483/article/details/141678510?spm=1001.2014.3001.5501

之后,讲解Spring HTTP Invoker配置servlet的实现方式。


一、概念

Spring HTTP Invoker是spring框架中的一个远程调用模型,基于HTTP协议的远程调用。使用java的序列化机制在网络上传递对象。由Spring提供服务端和客户端。

两种实现方式:

1.基于Url映射方式,客户端远程请求的方式同SpringMVC的controller类似,所有的请求通过在web.xml中的 org.springframework.web.servlet.DispatcherServlet统一处理,根据url映射查找跟请求的url匹配的bean配置(本文通过applicationContext-servers.xml文件管理服务端bean)
2.基于Servlet方式,由org.springframework.web.context.support.HttpRequestHandlerServlet去拦截url- pattern匹配的请求,查找对应的bean配置(本文通过applicationContext-servers.xml文件管理服务端bean)。

二、代码实现

1. 服务端实现

步骤:

编写User.java实体对象类,

编写Q1001Service.java接口类和接口实现类

配置applicationContext-servers.xml文件和web.xml文件

关于服务端接口类的代码这里就不描述了,请参考上一篇文章。这里直接讲配置。

applicationContext-servers.xml文件配置:

XML 复制代码
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">

    <bean id="q1001ServiceImpl" class="com.wqbr.shoservice.q1001.service.impl.Q1001ServiceImpl"/>

    <bean name="q1001Service" class="org.springframework.remoting.httpinvoker.HttpInvokerServiceExporter">
        <property name="service" ref="q1001ServiceImpl" />
        <property name="serviceInterface" value="com.wqbr.shoservice.q1001.service.Q1001Service" />
    </bean>
</beans>

重点看name="q1001Service"的bean,实现org.springframework.remoting.httpinvoker.HttpInvokerServiceExporter类,并指定接口类和注入接口实现类。

web.xml文件配置:

XML 复制代码
<?xml version="1.0" encoding="UTF-8"?>

<web-app version="3.0" xmlns="http://java.sun.com/xml/ns/javaee"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://java.sun.com/xml/ns/javaee
   http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd">
  <!--  https://blog.csdn.net/qyb19970829/article/details/110100544 配置时注意关于spring容器加载顺序的问题,
   applicationContext.xml,spring-security.xml,springmvc.xml 即这几个配置文件加载顺序
   -->
  <!--字符编码过滤器一定要放在前面,在web.xml中配置Spring提供的过滤器类-->
  <filter>
    <filter-name>encodingFilter</filter-name> <!--encodingFilter 这个命名不要修改-->
    <filter-class>org.springframework.web.filter.CharacterEncodingFilter</filter-class>
    <async-supported>true</async-supported>
    <init-param>
      <param-name>encoding</param-name>
      <param-value>UTF-8</param-value>
    </init-param>
  </filter>

  <filter-mapping>
    <filter-name>encodingFilter</filter-name>
    <url-pattern>/*</url-pattern>
  </filter-mapping>

  <!--配置Spring的监听器,启动spring容器-->
  <!--配置加载类路径的配置文件,注意加载顺序-->
  <context-param>
    <param-name>contextConfigLocation</param-name>
    <param-value>
      classpath:spring/applicationContext.xml
      classpath:spring/applicationContext-servers.xml
    </param-value>
  </context-param>
  <display-name>Archetype Created Web Application</display-name>
  <listener>
    <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
  </listener>


  <!--远程接口配置-->
  <servlet>
    <servlet-name>q1001Service</servlet-name>
    <servlet-class>org.springframework.web.context.support.HttpRequestHandlerServlet</servlet-class>
  </servlet>
  <servlet-mapping>
    <servlet-name>q1001Service</servlet-name>
    <url-pattern>/q1001Service</url-pattern>
  </servlet-mapping>

</web-app>

重点是加载了applicationContext-servers.xml文件到Spring,接受Spring对applicationContext-servers.xml文件中bean的管理。

并指定了远程接口配置的servlet,实现org.springframework.web.context.support.HttpRequestHandlerServlet类,指定url-pattern请求,HttpRequestHandlerServlet类负责进行servlet-name与applicationContext-servers.xml文件中的bean(q1001Service)进行匹配。从而调用到服务端提供的实现方法。

2. 客户端实现

步骤:

编写控制器MyTestController.java来远程调用服务

配置applicationContext-clients.xml文件和web.xml文件

关于客户端控制器的代码这里就不描述了,请参考上一篇文章。这里直接讲配置。

applicationContext-clients.xml文件配置:

XML 复制代码
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
	xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	   xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">

	<bean id="httpInvokerRequestExecutor" class="org.springframework.remoting.httpinvoker.HttpComponentsHttpInvokerRequestExecutor">
		<property name="connectTimeout" value="3000" /> <!--连接超时时间,毫秒。-->
		<property name="readTimeout" value="9000" /> <!--从服务器读取响应的超时时间,毫秒。9000=9秒-->
	</bean>
	<!--除了以上配置,还可以配置多线程调用-->

	<bean id="q1001Service" class="org.springframework.remoting.httpinvoker.HttpInvokerProxyFactoryBean">
		<!--<property name="serviceUrl" value="http://192.168.1.86:7001/shoservice-1.0.0/q1001Service" />-->
		<property name="serviceUrl" value="http://127.0.0.1:7001/shoservice-1.0.0/q1001Service" />
		<property name="serviceInterface" value="com.wqbr.shoservice.q1001.service.Q1001Service" />
		<!-- 使用Apache的HttpComponents客户端来设置httpInvokerRequestExecutor属性。设置超时时间,防止远程请求异常时拖累服务响应,导致应用卡住。默认HttpInvokerProxy使用的JDK的HTTP功能  -->
		<property name="httpInvokerRequestExecutor" ref="httpInvokerRequestExecutor" />
	</bean>

</beans>

指定了id="q1001Service"的bean,实现org.springframework.remoting.httpinvoker.HttpInvokerProxyFactoryBean代理工厂,指定serviceUrl请求服务端服务的路径 和 serviceInterface服务端提供服务的接口类,注入id="httpInvokerRequestExecutor"的bean,设置相关属性使应用的请求更加合理,遇到请求服务异常时及时释放避免影响应用的性能等。

web.xml文件配置:

XML 复制代码
<?xml version="1.0" encoding="UTF-8"?>

<web-app version="3.0" xmlns="http://java.sun.com/xml/ns/javaee"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://java.sun.com/xml/ns/javaee
   http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd">
  <!--  https://blog.csdn.net/qyb19970829/article/details/110100544 配置时注意关于spring容器加载顺序的问题,
   applicationContext.xml,spring-security.xml,springmvc.xml 即这几个配置文件加载顺序
   -->
  <!--字符编码过滤器一定要放在前面,在web.xml中配置Spring提供的过滤器类-->
  <filter>
    <filter-name>encodingFilter</filter-name> <!--encodingFilter 这个命名不要修改-->
    <filter-class>org.springframework.web.filter.CharacterEncodingFilter</filter-class>
    <async-supported>true</async-supported>
    <init-param>
      <param-name>encoding</param-name>
      <param-value>UTF-8</param-value>
    </init-param>
  </filter>

  <filter-mapping>
    <filter-name>encodingFilter</filter-name>
    <url-pattern>/*</url-pattern>
  </filter-mapping>

  <!--配置Spring的监听器,启动spring容器-->
  <!--配置加载类路径的配置文件,注意加载顺序-->
  <context-param>
    <param-name>contextConfigLocation</param-name>
    <param-value>
      classpath:spring/applicationContext.xml
      classpath:spring/applicationContext-clients.xml
    </param-value>
  </context-param>
  <display-name>Archetype Created Web Application</display-name>
  <listener>
    <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
  </listener>

  <!--配置前端控制器,对浏览器发送的请求进行统一处理-->
  <servlet>
    <servlet-name>dispatcherServlet</servlet-name>
    <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
    <!--加载springmvc.xml配置文件的位置和名称,配置的是Spring配置-->
    <init-param>
      <!--contextConfigLocation:上下文配置路径,固定值-->
      <param-name>contextConfigLocation</param-name>
      <!--classpath:类路径,指的是Java和resources文件夹-->
      <!--springmvc.xml:指的是配置文件的名称:需要配置springmvc.xml,在下面。
      spring默认配置文件为applicationContext.xml。当中配置spring创建容器时要扫描的包 已经整合到springmvc.xml中-->
      <param-value>
        classpath:spring/springmvc.xml
      </param-value>
    </init-param>
    <!--配置启动加载-->
    <load-on-startup>1</load-on-startup>
  </servlet>
  <servlet-mapping>
    <servlet-name>dispatcherServlet</servlet-name>
    <url-pattern>/</url-pattern>
  </servlet-mapping>

  <!--开启项目时打开的页面-->
    <welcome-file-list>
      <welcome-file>/login.jsp</welcome-file>
    </welcome-file-list>

  <!--设置session超时,单位分钟 默认30分钟-->
  <!--  <session-config>-->
  <!--    <session-timeout>2</session-timeout>-->
  <!--  </session-config>-->

</web-app>

重点是加载applicationContext-clients.xml文件到Spring,这样在Controller中才能调用到applicationContext-clients.xml文件指定的bean。


到此本文讲述完毕,运行方式同上一篇。运行结果为:成功调用到远程服务。


模拟两个错误场景,错误场景1. 设置客户端调用服务的路径错误,这时运行结果如下:

到达连接超时时间<property name="connectTimeout" value="3000" />报connect timed out,释放连接。

错误场景2.设置服务端实现方法线程等待,睡眠时间超过客户端的<property name="readTimeout" value="9000" />设置。

这时运行结果如下:

报Read timed out异常,客户端调用时达到 <property name="readTimeout" value="9000" />设置的时间后报异常,释放请求。

完结!谢谢关注。

相关推荐
Miketutu8 分钟前
Spring MVC消息转换器
java·spring
小小虫码2 小时前
项目中用的网关Gateway及SpringCloud
spring·spring cloud·gateway
esmember4 小时前
电路研究9.2.6——合宙Air780EP中HTTP——HTTP GET 相关命令使用方法研究
网络·网络协议·http·at指令
带刺的坐椅7 小时前
无耳科技 Solon v3.0.7 发布(2025农历新年版)
java·spring·mvc·solon·aop
霸王蟹10 小时前
http和https的区别?
网络·笔记·网络协议·学习·http·https
精通HelloWorld!10 小时前
使用HttpClient和HttpRequest发送HTTP请求
java·spring boot·网络协议·spring·http
LUCIAZZZ11 小时前
基于Docker以KRaft模式快速部署Kafka
java·运维·spring·docker·容器·kafka
泪不是Web妳而流11 小时前
BurpSuite抓包与HTTP基础
网络·经验分享·网络协议·安全·http·网络安全·学习方法
拾忆,想起11 小时前
如何选择Spring AOP的动态代理?JDK与CGLIB的适用场景
spring boot·后端·spring·spring cloud·微服务
zhuyasen11 小时前
多维度详细比较 kratos、go-zero、goframe、sponge 框架
后端·http·微服务·rpc·golang