DispatcherHandler

Spring WebFlux,与 Spring MVC 类似,围绕前端控制器模式设计,其中一个中央 WebHandler,即 DispatcherHandler,提供了一个共享的请求处理算法,而实际工作由可配置的委托组件执行。此模型灵活,并支持各种工作流。

DispatcherHandler 从 Spring 配置中发现其所需的委托组件。它也被设计为一个 Spring bean,并实现了 ApplicationContextAware 以访问其运行的上下文。如果 DispatcherHandler 以 bean 名称 webHandler 声明,则它将依次被 WebHttpHandlerBuilder 发现,后者将构建一个请求处理链,如 WebHandler API 中所述。

WebFlux 应用程序中的 Spring 配置通常包含

配置会传递给 WebHttpHandlerBuilder 来构建处理链,如下例所示

  • Java

  • Kotlin

ApplicationContext context = ...
HttpHandler handler = WebHttpHandlerBuilder.applicationContext(context).build();
val context: ApplicationContext = ...
val handler = WebHttpHandlerBuilder.applicationContext(context).build()

生成的 HttpHandler 已可与服务器适配器一起使用。

特殊 Bean 类型

DispatcherHandler 委托给特殊 bean 来处理请求并呈现适当的响应。 “特殊 bean”指的是实现 WebFlux 框架约定的 Spring 管理的 Object 实例。这些通常带有内置约定,但您可以自定义它们的属性、扩展它们或替换它们。

下表列出了 DispatcherHandler 检测到的特殊 bean。请注意,还有一些在较低级别检测到的其他 bean(请参阅 Web Handler API 中的 特殊 bean 类型)。

Bean 类型 解释

HandlerMapping

将请求映射到处理程序。映射基于某些标准,具体细节因 HandlerMapping 实现而异——带注解的控制器、简单的 URL 模式映射等。

主要的 HandlerMapping 实现是用于 @RequestMapping 注解方法的 RequestMappingHandlerMapping,用于函数式端点路由的 RouterFunctionMapping,以及用于 URI 路径模式和 WebHandler 实例显式注册的 SimpleUrlHandlerMapping

HandlerAdapter

帮助 DispatcherHandler 调用映射到请求的处理程序,而不管处理程序实际如何调用。例如,调用带注解的控制器需要解析注解。HandlerAdapter 的主要目的是保护 DispatcherHandler 免受此类细节的影响。

HandlerResultHandler

处理处理程序调用的结果并完成响应。请参阅结果处理

WebFlux 配置

应用程序可以声明处理请求所需的基础设施 bean(列在Web Handler APIDispatcherHandler 下)。但是,在大多数情况下,WebFlux 配置是最佳起点。它声明了所需的 bean 并提供了更高级别的配置回调 API 来对其进行自定义。

Spring Boot 依赖 WebFlux 配置来配置 Spring WebFlux,并提供了许多额外的便捷选项。

处理

DispatcherHandler 按照以下方式处理请求

  • 每个 HandlerMapping 都被要求查找匹配的处理程序,并使用第一个匹配项。

  • 如果找到处理程序,它将通过适当的 HandlerAdapter 运行,该适配器将执行的返回值公开为 HandlerResult

  • HandlerResult 被传递给适当的 HandlerResultHandler,通过直接写入响应或使用视图进行渲染来完成处理。

结果处理

通过 HandlerAdapter 调用处理程序的返回值被封装为 HandlerResult,以及一些额外的上下文,并传递给第一个声称支持它的 HandlerResultHandler。下表显示了可用的 HandlerResultHandler 实现,所有这些都声明在 WebFlux 配置中。

结果处理程序类型 返回值 默认顺序

ResponseEntityResultHandler

ResponseEntity,通常来自 @Controller 实例。

0

ServerResponseResultHandler

ServerResponse,通常来自函数式端点。

0

ResponseBodyResultHandler

处理 @ResponseBody 方法或 @RestController 类中的返回值。

100

ViewResolutionResultHandler

CharSequenceViewModelMapRendering 或任何其他 Object 都被视为模型属性。

另请参阅 视图解析

Integer.MAX_VALUE

异常

HandlerAdapter 实现可以在内部处理调用请求处理程序(例如控制器方法)时产生的异常。但是,如果请求处理程序返回一个异步值,则异常可能会被延迟。

HandlerAdapter 可以将其异常处理机制公开为在其返回的 HandlerResult 上设置的 DispatchExceptionHandler。当设置此项时,DispatcherHandler 也会将其应用于结果的处理。

HandlerAdapter 也可以选择实现 DispatchExceptionHandler。在这种情况下,DispatcherHandler 会将其应用于在处理程序映射之前(例如,在处理程序映射期间)或更早(例如,在 WebFilter 中)发生的异常。

另请参阅“注解控制器”部分中的异常或 WebHandler API 部分中的异常

视图解析

视图解析支持使用 HTML 模板和模型向浏览器呈现,而无需将您绑定到特定的视图技术。在 Spring WebFlux 中,视图解析通过一个专用的 HandlerResultHandler 支持,该处理程序使用 ViewResolver 实例将字符串(表示逻辑视图名称)映射到 View 实例。然后使用 View 渲染响应。

Web 应用程序需要使用视图渲染库来支持此用例。

处理

传递给 ViewResolutionResultHandlerHandlerResult 包含来自处理程序的返回值和在请求处理期间添加了属性的模型。返回值按以下方式之一处理

  • StringCharSequence:要通过配置的 ViewResolver 实现列表解析为 View 的逻辑视图名称。

  • void:根据请求路径选择默认视图名称(减去前导和尾随斜杠),并将其解析为 View。当未提供视图名称(例如,返回模型属性)或异步返回值(例如,Mono 完成为空)时,也会发生同样的情况。

  • Rendering:用于视图解析场景的 API。在 IDE 中使用代码补全探索选项。

  • ModelMap:要添加到请求模型的额外模型属性。

  • 任何其他:任何其他返回值(除了由 BeanUtils#isSimpleProperty 确定的简单类型)都被视为要添加到模型中的模型属性。属性名称通过约定从类名派生,除非存在处理程序方法 @ModelAttribute 注解。

模型可以包含异步、响应式类型(例如,来自 Reactor 或 RxJava)。在渲染之前,AbstractView 将此类模型属性解析为具体值并更新模型。单值响应式类型解析为单个值或无值(如果为空),而多值响应式类型(例如,Flux<T>)被收集并解析为 List<T>

配置视图解析就像向 Spring 配置中添加一个 ViewResolutionResultHandler bean 一样简单。WebFlux 配置为视图解析提供了专用的配置 API。

有关与 Spring WebFlux 集成的视图技术的更多信息,请参阅视图技术

重定向

视图名称中特殊的 redirect: 前缀允许您执行重定向。UrlBasedViewResolver(及其子类)将其识别为需要重定向的指令。视图名称的其余部分是重定向 URL。

效果与控制器返回 RedirectViewRendering.redirectTo("abc").build() 相同,但现在控制器本身可以根据逻辑视图名称进行操作。像 redirect:/some/resource 这样的视图名称是相对于当前应用程序的,而像 redirect:https://example.com/arbitrary/path 这样的视图名称则重定向到绝对 URL。

与 Servlet 堆栈不同,Spring WebFlux 不支持“转发”调度,因此不支持 forward: 前缀。

内容协商

ViewResolutionResultHandler 支持内容协商。它将请求媒体类型与每个选定 View 支持的媒体类型进行比较。使用第一个支持请求媒体类型的 View

为了支持 JSON 和 XML 等媒体类型,Spring WebFlux 提供了 HttpMessageWriterView,这是一个特殊的 View,它通过 HttpMessageWriter 渲染。通常,您会通过 WebFlux 配置将这些配置为默认视图。如果默认视图与请求的媒体类型匹配,则始终会选择并使用它们。

© . This site is unofficial and not affiliated with VMware.