当前位置: 首页> 健康> 养生 > 探索 Java 中的 DeferredResult<Object>

探索 Java 中的 DeferredResult<Object>

时间:2025/7/10 13:03:44来源:https://blog.csdn.net/weixin_44976692/article/details/140619973 浏览次数:0次

个人名片
在这里插入图片描述
🎓作者简介:java领域优质创作者
🌐个人主页:码农阿豪
📞工作室:新空间代码工作室(提供各种软件服务)
💌个人邮箱:[2435024119@qq.com]
📱个人微信:15279484656
🌐个人导航网站:www.forff.top
💡座右铭:总有人要赢。为什么不能是我呢?

  • 专栏导航:

码农阿豪系列专栏导航
面试专栏:收集了java相关高频面试题,面试实战总结🍻🎉🖥️
Spring5系列专栏:整理了Spring5重要知识点与实战演练,有案例可直接使用🚀🔧💻
Redis专栏:Redis从零到一学习分享,经验总结,案例实战💐📝💡
全栈系列专栏:海纳百川有容乃大,可能你想要的东西里面都有🤸🌱🚀

目录

      • 探索 Java 中的 DeferredResult<Object>
        • 1. 什么是 DeferredResult<Object>?
        • 2. 使用场景
        • 3. 基本使用方法
          • 3.1 配置异步支持
          • 3.2 控制器方法中使用 DeferredResult<Object>
          • 3.3 处理超时和错误
        • 4. 高级使用方法
          • 4.1 结合异步结果处理器
          • 4.2 使用 DeferredResult 结合 Spring WebFlux
        • 5. 实际应用案例
          • 案例一:文件上传
          • 案例二:调用外部服务
        • 6. 结论

探索 Java 中的 DeferredResult

在现代 Web 应用程序开发中,异步处理是提升应用性能和响应速度的重要手段。Java 提供了多种方式来实现异步处理,其中 DeferredResult<Object> 是 Spring 框架中用于处理异步请求的一种强大工具。本文将深入探讨 DeferredResult<Object> 的概念、使用场景以及具体实现方法,帮助开发者更好地理解和应用这一工具。

1. 什么是 DeferredResult?

DeferredResult<Object> 是 Spring MVC 中提供的用于异步请求处理的类。它允许我们将请求的处理逻辑从 Servlet 容器的线程中分离出来,从而避免阻塞 Servlet 容器的线程,提升应用的并发处理能力。

通常情况下,Spring MVC 控制器方法会同步处理 HTTP 请求,并在处理完成后返回一个视图或数据。然而,对于一些需要长时间处理的请求,如果同步处理会导致线程阻塞,进而影响服务器的性能和响应速度。在这种情况下,DeferredResult<Object> 提供了一种优雅的异步处理方式。

2. 使用场景

DeferredResult<Object> 适用于以下场景:

  • 长时间处理的请求:例如,调用外部服务、执行复杂计算或处理大文件上传等需要较长时间才能完成的操作。
  • 提升并发处理能力:通过异步处理,可以释放 Servlet 容器的线程,提升服务器的并发处理能力。
  • 避免线程阻塞:在处理长时间操作时,避免线程阻塞,提高系统的整体性能。
3. 基本使用方法

下面通过一个简单的示例,演示如何在 Spring MVC 中使用 DeferredResult<Object> 处理异步请求。

3.1 配置异步支持

首先,需要确保 Spring MVC 支持异步请求处理。在 Spring 配置类或 XML 配置文件中启用异步支持:

import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.EnableWebMvc;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;@Configuration
@EnableWebMvc
public class WebConfig implements WebMvcConfigurer {// 其他配置
}
3.2 控制器方法中使用 DeferredResult

在控制器方法中返回 DeferredResult<Object>,并在异步处理完成后设置结果:

import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.context.request.async.DeferredResult;import java.util.concurrent.ForkJoinPool;@RestController
@RequestMapping("/async")
public class AsyncController {@GetMapping("/process")public DeferredResult<Object> process() {DeferredResult<Object> deferredResult = new DeferredResult<>(5000L, "Request Timeout");ForkJoinPool.commonPool().submit(() -> {try {// 模拟长时间处理Thread.sleep(3000);deferredResult.setResult("Processing complete");} catch (InterruptedException e) {deferredResult.setErrorResult(e.getMessage());}});return deferredResult;}
}

在上述示例中,DeferredResult<Object> 设置了超时时间为 5000 毫秒,并指定了超时后的默认返回值 "Request Timeout"。在 ForkJoinPool 的线程中,模拟了一个长时间处理操作(休眠 3 秒),然后设置了处理结果 "Processing complete"

3.3 处理超时和错误

可以通过设置超时回调和错误回调来处理请求超时和错误情况:

deferredResult.onTimeout(() -> {deferredResult.setErrorResult("Request Timeout");
});deferredResult.onError((Throwable t) -> {deferredResult.setErrorResult(t.getMessage());
});
4. 高级使用方法
4.1 结合异步结果处理器

Spring 提供了 CallableDeferredResultProcessingInterceptor 用于进一步增强异步请求处理的功能。可以通过自定义拦截器来处理更多场景,例如在请求开始时记录日志、在请求完成时进行清理等。

import org.springframework.web.context.request.async.DeferredResultProcessingInterceptor;
import org.springframework.web.context.request.async.AsyncRequestInterceptor;public class CustomDeferredResultInterceptor extends DeferredResultProcessingInterceptor {@Overridepublic <T> void beforeConcurrentHandling(NativeWebRequest request, DeferredResult<T> deferredResult) {// 请求开始时的逻辑}@Overridepublic <T> void afterCompletion(NativeWebRequest request, DeferredResult<T> deferredResult) {// 请求完成时的逻辑}
}

然后在配置类中注册拦截器:

import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
import org.springframework.web.servlet.config.annotation.InterceptorRegistry;@Configuration
public class WebConfig implements WebMvcConfigurer {@Overridepublic void addInterceptors(InterceptorRegistry registry) {registry.addInterceptor(new CustomDeferredResultInterceptor());}
}
4.2 使用 DeferredResult 结合 Spring WebFlux

Spring WebFlux 是 Spring 5 引入的响应式编程框架,可以与 DeferredResult 结合使用,以实现更加复杂的异步处理逻辑。

import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.context.request.async.DeferredResult;
import reactor.core.publisher.Mono;@RestController
public class WebFluxController {@GetMapping("/webflux")public DeferredResult<Object> handle() {DeferredResult<Object> deferredResult = new DeferredResult<>();Mono.just("Hello, WebFlux!").doOnSuccess(deferredResult::setResult).doOnError(deferredResult::setErrorResult).subscribe();return deferredResult;}
}

在这个示例中,我们使用了 Mono 进行异步处理,并将结果设置到 DeferredResult 中。

5. 实际应用案例
案例一:文件上传

在文件上传的场景中,处理大文件可能需要较长时间,使用 DeferredResult<Object> 可以避免阻塞主线程:

import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.context.request.async.DeferredResult;
import org.springframework.web.multipart.MultipartFile;import java.util.concurrent.ForkJoinPool;@RestController
public class FileUploadController {@PostMapping("/upload")public DeferredResult<Object> upload(@RequestParam("file") MultipartFile file) {DeferredResult<Object> deferredResult = new DeferredResult<>();ForkJoinPool.commonPool().submit(() -> {try {// 模拟文件处理Thread.sleep(5000);deferredResult.setResult("File uploaded successfully");} catch (InterruptedException e) {deferredResult.setErrorResult(e.getMessage());}});return deferredResult;}
}
案例二:调用外部服务

在调用外部服务时,响应时间可能较长,使用 DeferredResult<Object> 可以提高系统的并发处理能力:

import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.context.request.async.DeferredResult;import java.util.concurrent.CompletableFuture;@RestController
public class ExternalServiceController {@GetMapping("/external")public DeferredResult<Object> callExternalService() {DeferredResult<Object> deferredResult = new DeferredResult<>();CompletableFuture.supplyAsync(() -> {// 模拟调用外部服务try {Thread.sleep(4000);return "External service response";} catch (InterruptedException e) {return "Error: " + e.getMessage();}}).thenAccept(deferredResult::setResult);return deferredResult;}
}
6. 结论

DeferredResult<Object> 是 Spring MVC 提供的一个强大的异步处理工具,能够有效提高应用程序的并发处理能力,避免长时间操作阻塞主线程。通过本文的介绍,您应该已经了解了 DeferredResult<Object> 的基本概念、使用方法以及实际应用场景。在实际开发中,灵活运用 DeferredResult<Object> 可以大大提升系统的性能和用户体验。希望本文能够帮助您更好地理解和应用这一工具,为您的项目带来更多的价值。

关键字:探索 Java 中的 DeferredResult<Object>

版权声明:

本网仅为发布的内容提供存储空间,不对发表、转载的内容提供任何形式的保证。凡本网注明“来源:XXX网络”的作品,均转载自其它媒体,著作权归作者所有,商业转载请联系作者获得授权,非商业转载请注明出处。

我们尊重并感谢每一位作者,均已注明文章来源和作者。如因作品内容、版权或其它问题,请及时与我们联系,联系邮箱:809451989@qq.com,投稿邮箱:809451989@qq.com

责任编辑: