1.9 View Technologies

Spring WebFlux中视图技术的使用是可插入的,无论您决定使用Thymeleaf,Groovy标记模板,JSP还是其他技术,主要取决于配置更改。 本章介绍与Spring WebFlux集成的视图技术。 我们假设您已经熟悉View Resolution。

1.9.1 Thymeleaf

Thymeleaf是一种现代的服务器端Java模板引擎,它强调可以通过双击在浏览器中预览的自然HTML模板,这对于独立处理UI模板(例如,由设计人员)而无需使用非常有用。 正在运行的服务器。 如果要替换JSP,Thymeleaf提供了最广泛的功能集之一,以使这种过渡更加容易。 Thymeleaf是积极开发和维护的。 有关更完整的介绍,请参见Thymeleaf项目主页。

Thymeleaf与Spring MVC的集成由Thymeleaf项目管理。 该配置涉及一些Bean声明,例如ServletContextTemplateResolver,SpringTemplateEngine和ThymeleafViewResolver。 有关更多详细信息,请参见Thymeleaf + Spring。

1.9.2 FreeMarker

Apache FreeMarker是一个模板引擎,用于生成从HTML到电子邮件等的任何类型的文本输出。 Spring框架具有内置的集成,可以将Spring MVC与FreeMarker模板一起使用。

View配置

以下示例显示如何将FreeMarker配置为一种视图技术:

@Configuration
@EnableWebFlux
public class WebConfig implements WebFluxConfigurer {

    @Override
    public void configureViewResolvers(ViewResolverRegistry registry) {
        registry.freemarker();
    }

    // Configure FreeMarker...

    @Bean
    public FreeMarkerConfigurer freeMarkerConfigurer() {
        FreeMarkerConfigurer configurer = new FreeMarkerConfigurer();
        configurer.setTemplateLoaderPath("/WEB-INF/freemarker");
        return configurer;
    }
}

您的模板需要存储在上例所示的FreeMarkerConfigurer指定的目录中。 给定上述配置,如果您的控制器返回欢迎的视图名称,则解析器将查找/WEB-INF/freemarker/welcome.ftl模板。

FreeMarker Configuration

您可以通过在FreeMarkerConfigurer bean上设置适当的bean属性,将FreeMarker的“设置”和“ SharedVariables”直接传递给FreeMarker配置对象(由Spring管理)。 freemarkerSettings属性需要一个java.util.Properties对象,而freemarkerVariables属性需要一个java.util.Map。 以下示例显示了如何使用FreeMarkerConfigurer:

@Configuration
@EnableWebFlux
public class WebConfig implements WebFluxConfigurer {

    // ...

    @Bean
    public FreeMarkerConfigurer freeMarkerConfigurer() {
        Map<String, Object> variables = new HashMap<>();
        variables.put("xml_escape", new XmlEscape());

        FreeMarkerConfigurer configurer = new FreeMarkerConfigurer();
        configurer.setTemplateLoaderPath("classpath:/templates");
        configurer.setFreemarkerVariables(variables);
        return configurer;
    }
}

有关设置和变量应用于Configuration对象的详细信息,请参见FreeMarker文档。

1.9.3 Script Views

Spring框架具有内置的集成,可以将Spring MVC与可以在JSR-223 Java脚本引擎之上运行的任何模板库一起使用。 我们已经在不同的脚本引擎上测试了以下模板库:

Scripting LibraryScripting Engine

Handlebars

Nashorn

Mustache

Nashorn

React

Nashorn

EJS

Nashorn

ERB

JRuby

String templates

Jython

Kotlin Script templating

Kotlin

集成任何其他脚本引擎的基本规则是,它必须实现ScriptEngine和Invocable接口。

Requirements

您需要在类路径上具有脚本引擎,其细节因脚本引擎而异:

  • Java 8+随附了Nashorn JavaScript引擎。 强烈建议使用可用的最新更新版本。

  • 应该将JRuby添加为对Ruby支持的依赖。

  • 应该将Jython添加为对Python支持的依赖项。

  • 应该添加org.jetbrains.kotlin:kotlin-script-util依赖项和包含org.jetbrains.kotlin.script.jsr223.KotlinJsr223JvmLocalScriptEngineFactory行的META-INF / services / javax.script.ScriptEngineFactory文件。 有关更多详细信息,请参见此示例。

您需要具有脚本模板库。 针对Javascript的一种方法是通过WebJars。

Script Templates

您可以声明一个ScriptTemplateConfigurer bean来指定要使用的脚本引擎,要加载的脚本文件,调用呈现模板的函数等等。 以下示例使用Mustache模板和Nashorn JavaScript引擎:

@Configuration
@EnableWebFlux
public class WebConfig implements WebFluxConfigurer {

    @Override
    public void configureViewResolvers(ViewResolverRegistry registry) {
        registry.scriptTemplate();
    }

    @Bean
    public ScriptTemplateConfigurer configurer() {
        ScriptTemplateConfigurer configurer = new ScriptTemplateConfigurer();
        configurer.setEngineName("nashorn");
        configurer.setScripts("mustache.js");
        configurer.setRenderObject("Mustache");
        configurer.setRenderFunction("render");
        return configurer;
    }
}

使用以下参数调用render函数:

  • String template:模板内容

  • Map model:视图模型

  • RenderingContext renderingContext:RenderingContext,用于访问应用程序上下文,语言环境,模板加载器和URL(自5.0起)

Mustache.render()与该签名本地兼容,因此您可以直接调用它。

如果您的模板技术需要一些自定义,则可以提供一个实现自定义渲染功能的脚本。 例如,Handlerbars需要在使用模板之前先对其进行编译,并且需要使用polyfill来模拟某些服务器端脚本引擎中不可用的浏览器功能。

以下示例显示了如何执行此操作:

@Configuration
@EnableWebFlux
public class WebConfig implements WebFluxConfigurer {

    @Override
    public void configureViewResolvers(ViewResolverRegistry registry) {
        registry.scriptTemplate();
    }

    @Bean
    public ScriptTemplateConfigurer configurer() {
        ScriptTemplateConfigurer configurer = new ScriptTemplateConfigurer();
        configurer.setEngineName("nashorn");
        configurer.setScripts("polyfill.js", "handlebars.js", "render.js");
        configurer.setRenderFunction("render");
        configurer.setSharedEngine(false);
        return configurer;
    }
}

当您将非线程安全脚本引擎与不是为并发设计的模板库一起使用时,例如,在Nashorn上运行的Handlebars或React,必须将sharedEngine属性设置为false。 在这种情况下,由于此错误,需要Java 8u60或更高版本。

polyfill.js仅定义Handlebars正常运行所需的window对象,如下所示:

var window = {};

这个基本的render.js实现在使用模板之前先对其进行编译。 生产就绪的实现还应该存储任何重用的缓存模板或预编译的模板。 您可以在脚本方面进行操作(并处理所需的任何自定义,例如管理模板引擎配置)。 以下示例显示了如何执行此操作:

function render(template, model) {
    var compiledTemplate = Handlebars.compile(template);
    return compiledTemplate(model);
}

1.9.4 JSON and XML

出于内容协商的目的,根据客户端请求的内容类型,能够在使用HTML模板呈现模型或以其他格式(例如JSON或XML)呈现模型之间进行切换非常有用。为了支持此操作,Spring WebFlux提供了HttpMessageWriterView,您可以使用它插入spring-web中的任何可用编解码器,例如Jackson2JsonEncoder,Jackson2SmileEncoder或Jaxb2XmlEncoder。

与其他视图技术不同,HttpMessageWriterView不需要ViewResolver,而是配置为默认视图。您可以配置一个或多个此类默认视图,并包装不同的HttpMessageWriter实例或Encoder实例。在运行时使用与请求的内容类型匹配的内容。

在大多数情况下,模型包含多个属性。要确定要序列化的对象,可以使用模型属性的名称配置HttpMessageWriterView进行渲染。如果模型仅包含一个属性,则使用该属性。

最后更新于