EJB的异步相当简单。其实就是在方法上加个@Asynchronous
异步方法有两种返回类型,一是void,一是Future<T>,我个人建议还是返回void。因为返回Future<T>还需要等待结果,就是同步了,所以没有了异步意义。就比如下面的代码,就是一个典型的带异步调用的无状态EJB。因为返回的是void,所以可以不处理返回值。
package asyncejb;
import java.time.LocalDateTime;
import javax.ejb.Asynchronous;
import javax.ejb.Stateless;
@Stateless
public class AsyncEjb {
@Asynchronous
public void run(){
System.out.println("EJB "+LocalDateTime.now());
}
}
在servlet中调用的话。
package asyncejb;
import java.io.IOException;
import java.time.LocalDateTime;
import javax.ejb.EJB;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
@WebServlet("/async.html")
public class AsyncServlet extends HttpServlet{
private static final long serialVersionUID = 1L;
@EJB
private AsyncEjb asyncEjb;
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
asyncEjb.run();
System.out.println("Servlet " +LocalDateTime.now());
}
}
可以根据控制台打印信息知道,在代码顺序上,虽然是先调用EJB,后调用servlet,但是先执行的还是servlet,后执行的是EJB。
10:12:13,670 INFO [stdout] (default task-5) Servlet 2016-01-18T10:12:13.670
10:12:13,673 INFO [stdout] (EJB default - 3) EJB 2016-01-18T10:12:13.673
其实异步的用处在哪呢?
异步是用于大批量的任务,可以直接返回结果,避免了用户的等待。
但是J2EE中异步操作太多了,servlet可以异步,EJB可以异步,CDI可以异步,自己写个线程也可以异步。