Spring MVC で Callable 使って非同期リクエストを処理する時に嵌りました。とりえあず、これが対策後のコントローラ。
@Controller
public class SampleController {
@ModelAttribute("sample")
public String sample(HttpServletRequest request) {
if (WebAsyncUtils.getAsyncManager(request).hasConcurrentResult()) {
return null;
}
return "sample";
}
@GetMapping("/sample")
@ResponseBody
public Callable<String> get() {
return () -> "sample";
}
}
ModelAttribute の中で hasConcurrentResult を検証しているのですが、モデルの初期化がリクエストの処理前だけでなく、Callable の中身の処理が終わった後に再度実行されてしまうため、hasConcurrentResult で判定しています。
普通にモデルを作るだけならこの処理は不要だと思うのですが、リソースがない場合に例外を出すような処理をしていて、削除処理を Callable で実装すると、削除リクエスト内で例外が発生してしまいます。
どうしてこうなるか WebAsyncManager#startCallableProcessing と RequestMappingHandlerAdapter#invokeHandlerMethod を追ったのですが、他に対策が思いつかなかったので一時的な対策になってしまいました。