我有两个模块,一个模块从rest模板调用另一个模块。
(管理员调用notifServer)
notifServer有一个用@Async
注释的方法。我想在该方法中引发异常,但是管理员无法迅速获得响应,因此无法在admin处捕获异常方法。
我是spring和@Async流程的新手。我尝试将响应正文从NotifServer映射到C CompletableFuture.class
。
但是我仍然没有收到错误响应。
此代码来自管理员
ResponseEntity response = fcmRestTemplate.exchange(nsUrl + "/fcm/admin/" + bulkFcmId, HttpMethod.POST,
HttpEntityUtils.getHttpEntity(moduleCode), CompletableFuture.class);
if (response.getStatusCode() != HttpStatus.CREATED && response.getStatusCode() != HttpStatus.ACCEPTED) {
String errorMessage = ErrorResourceUtil.getErrorMessage((HashMap) response.getBody(),"Unable to send fcm");
setStatusToFailedByBulkFcmId(bulkFcmId);
throw new ClientException(errorMessage);
}
现在这是来自 NotifServer
JobExecution jobExecution = jobLauncher
.run(importJob, new JobParametersBuilder()
.addString("fullPathFileName", TMP_DIR)
.addString("batch_fcm_id", String.valueOf(id))
.addLong("time",System.currentTimeMillis())
.toJobParameters());
if(jobExecution.getStepExecutions().stream().map(StepExecution::getStatus).findFirst().get().equals(BatchStatus.ABANDONED)){
throw new ClientException("INVALID CSV");
这用@Async注释。
那么我有办法在Admin的响应正文中捕获客户端异常吗?
编辑 这是来自notifServer的API
@ResponseStatus(HttpStatus.CREATED)
@PostMapping(value = "/admin/{bulkFcmId}")
public void pushFCMByAdmin(@PathVariable Long bulkFcmId) {
fcmService.sendFcmByAdmin(bulkFcmId, AuthUtil.getCurrentUser());
}
然后sendFcmByAdmin具有@Async批注。
答案 0 :(得分:0)
在下面的代码中,您可以提供返回类型而不是CompletableFuture.class作为业务对象。由于您将CompletableFuture.class作为参数传递给交易所,因此它期望响应 返回值 ,类型为CompletableFuture.class。
ResponseEntity response = fcmRestTemplate.exchange(nsUrl + "/fcm/admin/" + bulkFcmId, HttpMethod.POST,
HttpEntityUtils.getHttpEntity(moduleCode), CompletableFuture.class);
if (response.getStatusCode() != HttpStatus.CREATED && response.getStatusCode() != HttpStatus.ACCEPTED) {
String errorMessage = ErrorResourceUtil.getErrorMessage((HashMap) response.getBody(),"Unable to send fcm");
setStatusToFailedByBulkFcmId(bulkFcmId);
throw new ClientException(errorMessage);
}
除了传递Completable Future之外,您还可以尝试如下创建它吗:
使用异步方法在admin中进行其余模板调用:
@Async
public CompletableFuture<List<BusinessObject>> getResponseAsynchronously(String value) {
String url = "https://restendpoint.eu/rest/v2/lang/" + value + "?fields=name";
BusinessObject[] response = restTemplate.getForObject(url, Country[].class);
return CompletableFuture.completedFuture(Arrays.asList(response));
}
然后在控制器中读取CompletableFuture,如下所示:
@GetMapping("")
public List<String> getAllDataFromRestCall() throws Throwable {
CompletableFuture<List<BusinessObject>> businessObjectsFuture = countryClient.getResponseAsynchronously("fr");
List<String> europeanFrenchSpeakingCountries;
try {
europeanFrenchSpeakingCountries = new ArrayList<>(businessObjectsFuture
.get()
.stream()
.map(Country::getName)
.collect(Collectors.toList()));
} catch (Throwable e) {
throw e.getCause();
}
return europeanFrenchSpeakingCountries;
}