![](/img/trans.png)
[英]How to get details of Spring Boot @Async method's rejected task?
[英]Spring boot async: get HttpServletRequest inside async method
我已在 Spring Boot 應用程序中啟用異步:
@Configuration
@EnableAsync
public class BackOfficeConfiguration {}
我創建了這個異步方法:
@Async
public void importDocuments() {}
importDocuments
代碼只是:
@Async
public void importDocuments() {
// Do something
// Get current request context
ServletRequestAttributes requestAttributes =
(ServletRequestAttributes) RequestContextHolder.currentRequestAttributes();
HttpServletRequest request = requestAttributes.getRequest();
}
在RequestContextHolder.currentRequestAttributes()
,spring boot 給我這個異常:
java.lang.IllegalStateException: No thread-bound request found: 您是指實際 Web 請求之外的請求屬性,還是在原始接收線程之外處理請求? 如果您實際上是在 Web 請求中操作並且仍然收到此消息,則您的代碼可能在 DispatcherServlet/DispatcherPortlet 之外運行:在這種情況下,請使用 RequestContextListener 或 RequestContextFilter 來公開當前請求。
如何在異步方法中獲取當前的HttpServletRequest
?
如果您在方法上使用 @Async,則意味着該方法會拋出另一個新線程(單獨的線程)。 這意味着,它與您當前的請求無關。 (那是兩條路)。 如果你想從請求中獲取一些數據,你必須從請求中獲取你想要的數據並將其作為副本保存。 因為,完成后請求數據將被刪除。 如果您在那里傳遞了引用,則在訪問數據時會出現錯誤,例如No thread-bound request found
。 您必須創建一個Cloneable
對象並將數據填充到該對象中並在調用 Async 方法之前獲取一個克隆,並通過傳遞該對象來調用 Async 方法。 那么您就有了該數據的副本,您可以在新線程中使用它(@Async 方法)。 如下所示的 Cloneable 類。
public class CloneableClass implements Cloneable {
//
private ServletRequestAttributes requestAttributes;
//getters
//setters
@Override
public CloneableClass clone() {
try {
CloneableClass clone = (CloneableClass) super.clone();
return clone;
} catch (CloneNotSupportedException e) {
throw new AssertionError();
}
}
}
閱讀更多https://docs.oracle.com/javase/8/docs/api/java/lang/Cloneable.html
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.