Springboot基础知识(10)- 整合 Thymeleaf 模板、国际化
1. 整合 Thymeleaf 模板
Spring Boot 推荐使用 Thymeleaf 作为其模板引擎。SpringBoot 为 Thymeleaf 提供了一系列默认配置,项目中一但导入了 Thymeleaf 的依赖,相对应的自动配置 (ThymeleafAutoConfiguration) 就会自动生效,因此 Thymeleaf 可以与 Spring Boot 完美整合 。
Spring Boot 通过 ThymeleafAutoConfiguration 自动配置类对 Thymeleaf 提供了一整套的自动化配置方案,该自动配置类的部分源码如下。
1 @Configuration(proxyBeanMethods = false) 2 @EnableConfigurationProperties({ThymeleafProperties.class}) 3 @ConditionalOnClass({TemplateMode.class, SpringTemplateEngine.class}) 4 @AutoConfigureAfter({WebMvcAutoConfiguration.class, WebFluxAutoConfiguration.class}) 5 public class ThymeleafAutoConfiguration { 6 7 }
ThymeleafAutoConfiguration 使用 @EnableConfigurationProperties 注解导入了 ThymeleafProperties 类,该类包含了与 Thymeleaf 相关的自动配置属性,其部分源码如下。
1 @ConfigurationProperties(prefix = "spring.thymeleaf") 2 public class ThymeleafProperties { 3 private static final Charset DEFAULT_ENCODING; 4 public static final String DEFAULT_PREFIX = "classpath:/templates/"; 5 public static final String DEFAULT_SUFFIX = ".html"; 6 private boolean checkTemplate = true; 7 private boolean checkTemplateLocation = true; 8 private String prefix = "classpath:/templates/"; 9 private String suffix = ".html"; 10 private String mode = "HTML"; 11 private Charset encoding; 12 private boolean cache; 13 14 ... 15 }
ThymeleafProperties 通过 @ConfigurationProperties 注解将配置文件(application.properties/application.yml) 中前缀为 spring.thymeleaf 的配置和这个类中的属性绑定。
在 ThymeleafProperties 中还提供了以下静态变量:
DEFAULT_ENCODING:默认编码格式
DEFAULT_PREFIX:视图解析器的前缀
DEFAULT_SUFFIX:视图解析器的后缀
与 Spring Boot 其他自定义配置一样,我们可以在 application.properties/application.yml 中修改以 spring.thymeleaf 为前缀的属性,以实现修改 Spring Boot 对 Thymeleaf 的自动配置。
Spring Boot 整合 Thymeleaf 模板引擎,需要以下步骤:
引入依赖
创建模板文件,并放在在指定目录下
1) 引入依赖
修改 pom.xml:
1 <project ... > 2 ... 3 <dependencies> 4 ... 5 6 <!-- Thymeleaf --> 7 <dependency> 8 <groupId>org.springframework.boot</groupId> 9 <artifactId>spring-boot-starter-thymeleaf</artifactId> 10 </dependency> 11 12 ... 13 </dependencies> 14 15 ... 16 </project>
在IDE中项目列表 -> SpringbootWeb -> 点击鼠标右键 -> Maven -> Reload Project
2) 创建模板文件
根据 ThymeleafProperties 配置属性可知,Thymeleaf 模板的默认位置在 resources/templates 目录下,默认的后缀是 html,即只要将 HTML 页面放在“classpath:/templates/”下,Thymeleaf 就能自动进行渲染。
示例,在 “ Springboot基础知识(08)- spring-boot-starter-web(Web启动器)” 里 SpringbootWeb 项目基础上,修改如下。
(1) 创建 src/main/resources/templates/common.html 文件
1 <div th:fragment="fragment-header" id="fragment-header-id"> 2 <p>Header</p> 3 </div> 4 <div th:fragment="fragment-banner" id="fragment-banner-id"> 5 <p>Banner</p> 6 <hr /> 7 </div> 8 <div th:fragment="fragment-footer(var)" id="fragment-footer-id"> 9 <hr /> 10 <p th:text="${var}">Footer</p> 11 </div>
注:若 src/main/resources/templates 目录不存在,手动创建各级目录,下同。
(2) 创建 src/main/resources/templates/demo.html 文件
1 <!DOCTYPE html> 2 <html lang="en" xmlns:th="http://www.thymeleaf.org"> 3 <head> 4 <meta charset="UTF-8"> 5 <title>Demo</title> 6 </head> 7 <body> 8 9 <div th:replace="common::fragment-header"></div> 10 11 <div th:include="common::fragment-banner"></div> 12 13 <div id="content"> 14 <h3 th:text="'Welcome ' + ${name}">Welcome</h3> 15 16 <div th:object="${user}" > 17 <p th:text="*{firstName}">firstName</p> 18 </div> 19 </div> 20 21 <div th:insert="common::fragment-footer(var='Copyright 2020')"></div> 22 23 </body> 24 </html>
(3) 创建 src/main/java/com/example/entity/User.java 文件
1 package com.example.entity; 2 3 import org.springframework.stereotype.Component; 4 import org.springframework.boot.context.properties.ConfigurationProperties; 5 6 @Component 7 @ConfigurationProperties(prefix = "user") 8 public class User { 9 private String firstName; 10 private Integer age; 11 12 public User() { 13 14 } 15 16 public String getFirstName() { 17 return firstName; 18 } 19 public void setFirstName(String firstName) { 20 this.firstName = firstName; 21 } 22 23 public Integer getAge() { 24 return age; 25 } 26 public void setAge(Integer age) { 27 this.age = age; 28 } 29 @Override 30 public String toString() { 31 return "User {" + 32 "firstName = " + firstName + 33 ", age = " + age + 34 '}'; 35 } 36 }
(4) 创建 src/main/java/com/example/controller/IndexController.java 文件
1 package com.example.controller; 2 3 import java.util.Map; 4 import org.springframework.stereotype.Controller; 5 import org.springframework.web.bind.annotation.RequestMapping; 6 7 import com.example.entity.User; 8 9 @Controller 10 public class IndexController { 11 @Autowired 12 User user; 13 14 @RequestMapping("/demo") 15 public String demo(Map<String, Object> map) { 16 17 user.setFirstName("Tester"); 18 user.setAge(21); 19 20 map.put("name", "admin"); 21 map.put("user", user); 22 return "demo"; 23 } 24 }
访问 http://localhost:9090/demo,页面显示:
Header
Banner
----------------------
Welcome admin
Tester
-----------------------
Copyright 2020
2. 国际化
国际化(Internationalization 简称 I18n,其中 “I” 和 “n” 分别为首末字符,18 则为中间的字符数)是指软件开发时应该具备支持多种语言和地区的功能。
换句话说就是,开发的软件需要能同时应对不同国家和地区的用户访问,并根据用户地区和语言习惯,提供相应的、符合用具阅读习惯的页面和数据,例如,为中国用户提供汉语界面显示,为美国用户提供提供英语界面显示。
在 Spring 项目中实现国际化,通常需要以下步骤:
(1) 编写国际化资源(配置)文件;
(2) 使用 ResourceBundleMessageSource 管理国际化资源文件;
(3) 在页面获取国际化内容;
1) 编写国际化资源文件
在 src/main/resources 下创建一个 i18n 的目录,并在该目录中按照国际化资源文件命名格式分别创建以下三个文件:
login.properties:无语言设置时生效
login_en_US.properties:英语时生效
login_zh_CN.properties:中文时生效
以上国际化资源文件创建完成后,IDEA 会自动识别它们,并转换成 Resource Bundle 模式。
打开 login.properties,点击窗口底部 Resource Bundle 标签,然后点击 “+” 号,创建 Username 和 Password 属性。
修改后的 login.properties 文件
login.title=Login(default)
login.password=Password(default)
login.username=Username(default)
修改后的 login_en_US.properties 文件
login.title=Login
login.password=Password
login.username=Username
修改后的 login_zh_CN.properties 文件
login.title=登录
login.password=密码
login.username=用户名
2) 使用 ResourceBundleMessageSource 管理国际化资源文件
Spring Boot 已经对国际化资源文件的管理提供了默认自动配置,我们这里只需要在 Spring Boot 全局配置文件中,使用配置参数 “spring.messages.basename” 指定我们自定义的国际资源文件的基本名即可,当指定多个资源文件时,用逗号分隔。
修改 src/main/resources/application.properties 文件,添加如下内容:
spring.messages.basename=i18n.login
spring.messages.encoding=UTF-8
注:Spring Boot 根据浏览器放出的请求头的 Accept-Language 来自动选择资源文件,比如 Accept-Language: zh-CN 映射到 login_zh_CN.properties,Accept-Language: en-US 映射到 login_en_US.properties,其它值会默认映射到 login.properties。
3) 在页面获取国际化内容
页面使用 Tymeleaf 模板,可以通过表达式 #{...} 获取国际化内容,例如:
<p th:text="#{login.username}">Username</p>
示例,在上文 SpringbootWeb 项目基础上,代码如下。
(1) 创建 src/main/resources/templates/login.html 文件
1 <!DOCTYPE html> 2 <html lang="en" xmlns:th="http://www.thymeleaf.org"> 3 <head> 4 <meta charset="UTF-8"> 5 <title>Login</title> 6 </head> 7 <body> 8 9 <h3 th:text="#{login.title}">Login</h3> 10 11 <p><span th:text="#{login.username}">Username</span>: 12 <input type="text" name="username" value="" /></p> 13 <p><span th:text="#{login.password}">Password</span>: 14 <input type="text" name="password" value="" /></p> 15 16 </body> 17 </html>
(2) 创建 src/main/java/com/example/controller/UserController.java 文件
1 package com.example.controller; 2 3 import org.springframework.stereotype.Controller; 4 import org.springframework.web.bind.annotation.RequestMapping; 5 6 @Controller 7 @RequestMapping("/user") 8 public class UserController { 9 @RequestMapping("/login") 10 public String login() { 11 return "login"; 12 } 13 }
访问 http://localhost:9090/user/login,中文浏览器会显示:
登录
用户名:
密码:
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】凌霞软件回馈社区,博客园 & 1Panel & Halo 联合会员上线
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】博客园社区专享云产品让利特惠,阿里云新客6.5折上折
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 微软正式发布.NET 10 Preview 1:开启下一代开发框架新篇章
· 没有源码,如何修改代码逻辑?
· PowerShell开发游戏 · 打蜜蜂
· 在鹅厂做java开发是什么体验
· WPF到Web的无缝过渡:英雄联盟客户端的OpenSilver迁移实战