欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

@Async异步注解

程序员文章站 2022-04-30 20:45:31
...

前端:

 

<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core"%>
<%
String path = request.getContextPath();
String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/";
%>

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
  <head>
    <base href="<%=basePath%>">
    <meta charset="utf-8">
	<meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1, user-scalable=no">
    <title>RequestParam测试</title>

	<script type="text/javascript" src="<%=basePath %>js/jquery-1.8.3.min.js"></script>
    <script type="text/javascript" src="<%=basePath %>js/jquery.cookie.js"></script>
	<script type="text/javascript">	
    var timerId = null;//定时器ID

    $(document).ready(function () {
        /*
         定时轮询执行进度
         */
        timerId = setInterval(function () {
            getStatus();
        }, 1000);
        getStatus();
    });

    /**
     获取执行进度
     */
    function getStatus() {
        var statusUrl = '<%=basePath%>rpc/async/status';
        $.get(statusUrl, function (data) {
        	console.log(data);
            if (data == null || data == null || data == "null") {
                updateStatus("准备中");
                return ;
            }
            var status = data;         
            var temp = status.split("/");
            updateStatus(status);
            if (temp[0] ==temp[1]) {
                updateStatus("完成");
                clearInterval(timerId);//停止定时器
                clearStatus();//清理redis缓存
            }
        })
    }

    /**
     * 执行完成后,清理缓存
     */
    function clearStatus() {
        var clearStatusUrl = '<%=basePath%>rpc/async/clear';
        $.get(clearStatusUrl, function (data) {
        })
    }

    /**
     更新进度显示
     */
    function updateStatus(msg) {
        $("#status").html(msg);
    }
	</script>
</head>


<body>
<div id="msgBox">
    <span>请稍候,服务器正在处理中...</span>

    <h1>当前处理进度:<span style="color:red" id="status">准备中</span></h1>
</div>



</body>
</html>
    后台控制层:

	@RequestMapping(value = "/async/asyncTest")
    public String asyncTest(HttpServletRequest req,
                            HttpServletResponse resp,	 HttpSession session) throws Exception {
        asyncService.asyncMethod(	 session);
        return "async";
    }
    
    @RequestMapping(value = "/async/status")
    public void showAsyncStatus(HttpServletRequest req,
                                  HttpServletResponse resp,	 HttpSession session) throws Exception {
        String status = asyncService.getProcess(session);
        resp.getWriter().print(status);
        //return null;
    }

    @RequestMapping(value = "/async/clear")
    public void clearAsyncStatus(HttpServletRequest req,
                                   HttpServletResponse resp, HttpSession session) throws Exception {
        asyncService.clearCache(session);
        //resp.getWriter().print("ok");
        //System.out.println(session.getAttribute("cacheKey"));
        //return null;
    }
后台service:

package com.htxx.service.business;

import javax.servlet.http.HttpSession;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.scheduling.annotation.Async;
import org.springframework.stereotype.Service;

@Service
public class AsyncServiceImpl implements AsyncService{

    
    @Override
    @Async
    public void asyncMethod(	 HttpSession session) throws Exception {
        //模拟总有20个步骤,每个步骤耗时2秒
        int maxStep = 10;
        for (int i = 0; i < maxStep; i++) {
        	System.out.println(i);
            Thread.sleep(1000);
            //将执行进度放入缓存
            session.setAttribute("cacheKey", (i + 1) + "/" + maxStep);
        }
    }

    @Override
    public String getProcess(	 HttpSession session) throws Exception {
        return (String) session.getAttribute("cacheKey");
    }

    @Override
    public void clearCache(	 HttpSession session) throws Exception {
        //完成后,清空缓存
        session.setAttribute("cacheKey","0/10");
    	//session.removeAttribute("cacheKey");
    }

}
  浏览器:http://localhost:8090/MyLab/rpc/async/asyncTest

  在asyncTest方法里会调用service中一个for循环,这个for循环大约会执行10秒,然后再跳转到"async.jsp"

加上@async注解后,asyncTest方法不必等到for循环完全结束再跳转到"async.jsp",在jsp页面内有setInterval循环查询后台session内的值,

将结果显示在页面上

效果显示:

@Async异步注解@Async异步注解@Async异步注解

--------------------------------------------------------遇到的问题------------------------------------------------------------------------------------------------

加了注解没反应,等到for循环结束后才进入页面:

解决办法:

在springmvc配置文件内加:

  <task:annotation-driven executor="asyncExecutor" />  
 <task:executor id="asyncExecutor" pool-size="100-10000" queue-capacity="10"/>  
	
-----------------------------------------------------参考-------------------------------------------------------------------------------------------------------

http://www.cnblogs.com/yjmyzz/p/how-to-use-Async-annotation-in-spring-mvc.html