1:使用Callable的異步調用
@GetMapping("/call")
public Callable<String> call() {
log.info("getResult");
Callable<String> callable = new Callable<String>() {
@Override
public String call() throws Exception {
return "success";
}
};
return callable;
}
2:使用DeferredResult的異步方法,逾時傳回預設資訊
@GetMapping("/get")
public DeferredResult<ResponseMsg<String>> get() {
log.info("getResult");
DeferredResult<ResponseMsg<String>> result = new DeferredResult<>(OUT_OF_TIME, response);
result.onTimeout(() -> {
log.info("調用逾時");
});
result.onCompletion(() -> {
log.info("調用完成");
});
// 并發,加鎖
synchronized (taskQueue) {
taskQueue.put(result);
}
return result;
}
TaskQueue類
@Slf4j
@Component
public class TaskQueue {
private static final int QUEUE_LENGTH = 10000;
private BlockingQueue<Task> queue = new LinkedBlockingDeque<>(QUEUE_LENGTH);
// take put會阻塞隊列;
// offer 是帶時間參數的add;
// poll 是帶時間參數的peek;
private AtomicLong atom = new AtomicLong(0);
/*
public void put(DeferredResult<ResponseMsg<String>> result){
Long taskId = atom.incrementAndGet();
log.info("任務加入隊列,id為:{}", taskId);
queue.offer(new Task(taskId, result));
}
public Task take() {
Task task = queue.poll();
log.info("獲得任務:{}", task);
return task;
}
*/
public void put(DeferredResult<ResponseMsg<String>> result) {
Long taskId = atom.incrementAndGet();
log.info("任務加入隊列,id為:{}", taskId);
try {
queue.put(new Task(taskId, result));
} catch (InterruptedException e) {
e.printStackTrace();
}
}
public Task take() {
Task task = null;
try {
task = queue.take();
} catch (InterruptedException e) {
e.printStackTrace();
}
log.info("獲得任務:{}", task);
return task;
}
}
3:使用WebAsyncTask異步任務,其中需要實作線程排程
@GetMapping("/async")
public WebAsyncTask<String> async() {
WebAsyncTask<String> webAsyncTask = new WebAsyncTask<String>(1000, new Callable<String>() {
@Override
public String call() throws Exception {
// 業務邏輯處理
Thread.sleep(5000);
String message = "username:wangbinghua";
return message;
}
});
webAsyncTask.onCompletion(new Runnable() {
@Override
public void run() {
System.out.println("調用完成");
}
});
webAsyncTask.onTimeout(new Callable<String>() {
@Override
public String call() throws Exception {
System.out.println("業務處理逾時");
return "<h1>Time Out</h1>";
}
});
return webAsyncTask;
}
4:CompletionStage異步調用
@GetMapping(path = "/search")
public CompletionStage<List<String>> search() {
CompletionStage<List<String>> result = CompletableFuture.completedFuture(List.of("success", "error"));
/*
* try { List<String> lists=result.toCompletableFuture().get(); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch
* (ExecutionException e) { // TODO Auto-generated catch block e.printStackTrace(); }
*/
return result;
}
5:ListenableFuture,不過此類已經被标記為過時了。使用CompletableFuture代替
@RequestMapping(value = "/list")
public ListenableFuture<String> list() {
ListenableFutureTask<String> ListenableFuture = new ListenableFutureTask<>(() -> {
return String.valueOf(System.currentTimeMillis());
});
Executors.newSingleThreadExecutor().submit(ListenableFuture);
return ListenableFuture;
}
換成CompletableFuture
public CompletableFuture<String> complete() {
CompletableFuture<String> completableFuture = CompletableFuture.supplyAsync(() -> {
return String.valueOf(System.currentTimeMillis());
});
return completableFuture;
}