Spring MVC 异步测试
从spring3.2开始,支持servlet3的异步请求,这对于处理耗时的请求如缓慢的数据库查询是非常有好处的,不至于很快的耗光servlet的线程池,影响可扩展性。
让我们先来了解一下servlet是怎么处理异步操作的:
- 通过调用request.startAsync(),ServletRequest就变成异步模式。主要的影响是Servlet、Filter会退出,但是Response保持打开用来完成请求处理。
- 调用request.startAsync()返回AsyncContext实例,可进一步控制异步处理。例如,它提供dispatch方法,可
以从应用线程调用以分发请求回Servlet容器。异步调度和forward的方式是相似的,但是异步调度是由应用线程到Servlet容器线程产生的,
而forward的方式是同时发生在相同的Servlet容器线程。 - ServletRequest提供当前的DispatcherType,它可以用来在异步调度中区分正在处理的初始请求线程是Servlet还是Filter。
接着来看一下callable是怎么处理异步操作的:
- Controller返回一个Callable实例;
- Spring MVC开始异步处理并在一个单独的线程中,提交Callable实例给TaskExecutor处理;
- DispatcherServlet和所有的Filter退出请求线程但是response保存打开;
- Callable返回结果,Spring MVC分发请求回Servlet容器;
- DispatcherServlet重新调用并继续处理从Callable实例中异步返回的结果。
现在来看一下代码是怎么实现的
1、pom.xml
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>javax.servlet-api</artifactId>
<version>3.1.0</version>
</dependency> <dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context-support</artifactId>
<version>3.2.13.RELEASE</version>
</dependency> <dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>3.2.13.RELEASE</version>
</dependency>
2、applicationContext-mvc.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"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:mvc="http://www.springframework.org/schema/mvc"
xmlns:task="http://www.springframework.org/schema/task"
xsi:schemaLocation="
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc.xsd
http://www.springframework.org/schema/task http://www.springframework.org/schema/task/spring-task.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd
"> <context:component-scan base-package="com.test"/> <mvc:annotation-driven>
<!-- 配置超时时间 -->
<mvc:async-support default-timeout="3000">
<!-- 这里可以配置callable或者deferred-result拦截器 -->
</mvc:async-support>
</mvc:annotation-driven>
</beans>
3、web.xml , 当有 很多 filter 时,filter 也一定要添加异步支持
<?xml version="1.0" encoding="UTF-8"?>
<web-app
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"
version="3.0"> <filter>
<filter-name>characterEncodingFilter</filter-name>
<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>
<init-param>
<param-name>forceEncoding</param-name>
<param-value>true</param-value>
</init-param>
</filter> <filter-mapping>
<filter-name>characterEncodingFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping> <servlet>
<servlet-name>DispatcherServlet</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath*:applicationContext-mvc.xml</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
<async-supported>true</async-supported>
</servlet> <servlet-mapping>
<servlet-name>DispatcherServlet</servlet-name>
<url-pattern>/</url-pattern>
</servlet-mapping>
</web-app>
web.xml需要声明web-app_3_0.xsd和version=”3.0″,启用异步支持<async-supported>true</async-supported>
4、CallableController.java
package com.test.controller; import org.springframework.stereotype.Controller;
import org.springframework.ui.ModelMap;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.servlet.ModelAndView; import java.util.concurrent.Callable; /**
* spring实现方式:
* 1、把任务提交给Executor异步执行
*/
@Controller
public class CallableController { @RequestMapping(value = "/callable1", method = RequestMethod.GET)
public Callable<String> callable1(final ModelMap modelMap) {
return new Callable<String>() {
public String call() throws Exception {
Thread.sleep(2 * 1000L); //暂停2秒return "hello callable";
}
};
}
}
5,tomcat 部分,如果 tomcat 部署有 session 分页式缓存插件,则在插件配置的地方,也要添加异步支持:
<!-- redis 缓存支持 -->
<Valve className="com.radiadesign.catalina.session.RedisSessionHandlerValve" asyncSupported="true" />
<Manager className="com.radiadesign.catalina.session.RedisSessionManager"
host="localhost"
port="6379"
database="0"
maxInactiveInterval="60" />
6, 启动服务,测试:
http://localhost:8088/test/callable1
7, rsp:
hello callable
Spring MVC 异步测试的更多相关文章
- Spring mvc异步处理
基于Servlet3.0的异步处理,springmvc的异步处理 控制器返回callable, spring mvc异步处理,将callable提交到TaskExecutor 使用一个隔离线程进行执 ...
- Spring MVC 异步处理请求,提高程序性能
原文:http://blog.csdn.net/he90227/article/details/52262163 什么是异步模式 如何在Spring MVC中使用异步提高性能? 一个普通 Servle ...
- Spring MVC如何测试Controller(使用springmvc mock测试)
在springmvc中一般的测试用例都是测试service层,今天我来演示下如何使用springmvc mock直接测试controller层代码. 1.什么是mock测试? mock测试就是在测试过 ...
- Spring MVC的测试
测试是保证软件质量的关键. 与 Spring MVC 相关的测试,主要涉及控制器的测试. 为了测试Web项目通常不需要启动项目,需要一些Servlet相关的一些模拟对象,比如MockMVC.MockH ...
- spring mvc 异步 DeferredResult
当一个请求到达API接口,如果该API接口的return返回值是DeferredResult,在没有超时或者DeferredResult对象设置setResult时,接口不会返回,但是Servlet容 ...
- Spring MVC 异步请求 Callable
对于有的请求业务处理流程可能比较耗时,比如长查询,远程调用等,主线程会被一直占用,而tomcat线程池线程有限,处理量就会下降 servlet3.0以后提供了对异步处理的支持,springmvc封装了 ...
- spring mvc 和ajax异步交互完整实例
Spring MVC 异步交互demo: 1.jsp页面: <%@ page language="java" contentType="text/html; cha ...
- spring3 jsp页面使用<form:form modelAttribute="xxxx" action="xxxx">报错,附连接数据库的spring MVC annotation 案例
在写一个使用spring3 的form标签的例子时,一直报错,错误信息为:java.lang.IllegalStateException: Neither BindingResult nor plai ...
- Unit Testing of Spring MVC
试验1:做的条目不发现首先,我们必须确保我们的应用是工作性质所做条目不发现.我们可以写的测试以确保通过以下步骤: 1.配置的模拟对象时抛出一个todonotfoundexception findbyi ...
随机推荐
- day67
昨日回顾 1 orm 创建表,新增字段,修改,删除字段,不能创建数据库 -字段属性phone=models.CharField(max_length=64,null=True) -null=Tru ...
- 微信小程序开发 [00] 写在前面的话,疯狂唠唠
我总是喜欢在写东西之前唠唠嗑,按照惯例会在博文的开篇写这么一段"写在前面的话",这次却为了这个唠嗑单独开了一篇文,大概预想着要胡说八道的话有点多. 前段时间突然对小程序来了兴趣,说 ...
- 20155304《网络对抗》MSF基础应用
20155304<网络对抗>MSF基础应用 实践内容 本实践目标是掌握metasploit的基本应用方式,重点常用的三种攻击方式的思路.具体需要完成: 1.1一个主动攻击实践,如ms08_ ...
- 20155339 Exp6 信息搜集与漏洞扫描
20155339 Exp6 信息搜集与漏洞扫描 实验后回答问题 (1)哪些组织负责DNS,IP的管理. 全球根服务器均由美国政府授权的ICANN统一管理,负责全球的域名根服务器.DNS和IP地址管理. ...
- Android开发——进程间通信之Messenger
0. 前言 不论是Android还是其他操作系统,都会有自己的IPC机制,所谓IPC(Inter-Process Communication)即进程间通信.首先线程和进程是很不同的概念,线程是CPU ...
- MiZ702学习笔记8——让MiZ702变身PC的方法
首先你需要一个安装好的linux系统,这里我用的是Ubuntu的虚拟机.VMWare的话,选择较高版本的成功率会高些(当然根据自己电脑的配置进行选择). 打开Ubuntu的虚拟机,找到一个叫做Disk ...
- linux 升级 5.0.2内核
1.下载 wet https://cdn.kernel.org/pub/linux/kernel/v5.x/linux-5.0.2.tar.xz -o /usr/src/ cd /usr/src ta ...
- C#Unit单元测试之读取Web.config文件
长期一来,我们所完成的项目都没有写单元测试,今天我一时兴起,决定给自己写的代码写单元测试,简单的测试代码分分钟完成了,一运行测试,就懵逼了.没能达到我的预期效果,而是出现图1所示错误. 图1:单元测试 ...
- [CF966F]May Holidays[分块+虚树]
题意 给定 \(n\) 个点的树,初始所有颜色都是 \(0\) ,每个点有一个阈值 \(t\) ,每次可能会让一个点的颜色异或1,问每次操作之后有多少个点满足子树内的颜色为 \(1\) 的点的个数 \ ...
- Flask学习-Flask app接受第一个HTTP请求
一.__call__() 在Flask app启动后,一旦uwsgi收到来自web server的请求,就会调用后端app,其实此时就是调用app的__call__(environ,start_res ...