开发学院

您的位置:首页>教程>正文

教程正文

Thymeleaf 3.0教程:12 内嵌(二)

12.2 文本内嵌

  文本内联与我们刚刚看到的表达式内联功能非常相似,但是它实际上增加了更多的功能。它必须用th:inline="text "显式启用。

  文本内联不仅允许我们使用刚才看到的相同的内联表达式,而且实际上处理标签体就像它们是在文本模板模式下处理的模板一样,这允许我们执行基于文本的模板逻辑(不仅仅是输出表达式)。

  我们将在关于文本模板模式的下一章中看到更多这方面的内容。

12.3 JavaScript内嵌

  JavaScript内联允许在以HTML模板模式处理的模板中更好地集成JavaScript <script >块。

  与文本内联一样,这实际上等同于处理脚本内容,就像它们是JAVASCRIPT模板模式中的模板一样,因此文本模板模式的所有功能(参见下一章)都将唾手可得。然而,在本节中,我们将集中讨论如何使用它将Thymeleaf表达式的输出添加到我们的JavaScript块中。

  必须使用th:inline="javascript"命令显式启用此模式:

<script th:inline="javascript">
    ...
    var username = [[${session.user.name}]];
    ...
</script>

  这将导致:

<script th:inline="javascript">
    ...
    var username = "Sebastian \"Fruity\" Applejuice";
    ...
</script>

  在上面的代码中需要注意两件重要的事情:

  首先,JavaScript内联不仅会输出所需的文本,还会用引号将它括起来,并用JavaScript转义它的内容,以便表达式结果以格式良好的JavaScript文字输出。

  第二,发生这种情况是因为我们输出了转义的${session.user.name}表达式,即使用了双括号表达式:[[${session.user.name}]]。相反,如果我们使用像这样的非转义符:

<script th:inline="javascript">
    ...
    var username = [(${session.user.name})];
    ...
</script>

  结果如下:

<script th:inline="javascript">
    ...
    var username = Sebastian "Fruity" Applejuice;
    ...
</script>

  这是格式错误的JavaScript代码。但是,如果我们通过附加内联表达式来构建脚本的一部分,输出一些未转义的东西可能是我们需要的,所以手边有这个工具是很好的。

JavaScript自然模板

  所提到的JavaScript内联机制的智能远不止是应用JavaScript特定的转义并将表达式结果作为有效文本输出。

  例如,我们可以在JavaScript注释中包装(转义)内联表达式,如:

<script th:inline="javascript">
    ...
    var username = /*[[${session.user.name}]]*/ "Gertrud Kiwifruit";
    ...
</script>

  Thymeleaf将忽略我们在注释之后和分号之前写的所有内容(在本例中为‘Gertrud Kiwifruit’),因此执行该操作的结果将与我们没有使用包装注释时完全一样:

<script th:inline="javascript">
    ...
    var username = "Sebastian \"Fruity\" Applejuice";
    ...
</script>

  但是再仔细看看原始模板代码:

<script th:inline="javascript">
    ...
    var username = /*[[${session.user.name}]]*/ "Gertrud Kiwifruit";
    ...
</script>

  请注意这是如何有效的JavaScript代码。当您以静态方式打开模板文件时(不在服务器上执行),它将完美地执行。

  所以我们这里有一种方法来做JavaScript自然模板!

高级内联评估和JavaScript序列化

  关于JavaScript内联需要注意的一件重要事情是,这个表达式求值是智能的,并不限于字符串。Thymeleaf将正确地用JavaScript语法编写以下类型的对象:

  Strings

  Numbers

  Booleans

  Arrays

  Collections

  Maps

  Beans (使用getter和setter方法的对象)

  例如,如果我们有以下代码:

<script th:inline="javascript">
    ...
    var user = /*[[${session.user}]]*/ null;
    ...
</script>

  该${session.user}表达式将计算为用户对象,Thymeleaf将正确地将其转换为Javascript语法:

<script th:inline="javascript">
    ...
    var user = {"age":null,"firstName":"John","lastName":"Apricot",
                "name":"John Apricot","nationality":"Antarctica"};
    ...
</script>

  这种JavaScript序列化是通过实现org.thymeleaf.standard.serializer.IStandardJavaScriptSerializer接口来完成的,该接口可以在模板引擎使用的标准方言的实例中配置。

  这个JS序列化机制的默认实现将在类路径中查找Jackson库,如果存在的话,将使用它。如果没有,它将应用一个内置的序列化机制,该机制覆盖大多数场景的需求,并产生类似的结果(但是灵活性较低)。