java

关注公众号 jb51net

关闭
首页 > 软件编程 > java > SpringBoot整合Thymeleaf模板引擎

SpringBoot整合Thymeleaf模板引擎的实战指南

作者:张老师技术栈

本文介绍了如何在SpringBoot项目中集成Thymeleaf模板引擎,包括添加Maven依赖,配置application.properties,以及创建简单的Controller和HTML模板,实现动态数据展示,需要的朋友可以参考下

SpringBoot 不推荐用 JSP,官方推荐的模板引擎是 Thymeleaf。这篇讲 Thymeleaf 的核心语法和实际项目中的最佳实践。

一、为什么用 Thymeleaf 而不是 JSP

对比ThymeleafJSP
语法标准 HTML,浏览器可直接打开需要服务器解析
前后端分离天然支持 HTML 属性语法耦合度高
与 SpringBoot 集成✅ 原生支持❌ 需要额外配置
国际化✅ 内置支持✅ 支持
性能缓存后性能好一般

二、基础配置

1. 引入依赖

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-thymeleaf</artifactId>
</dependency>
<dependency>
    <groupId>nz.net.ultraq.thymeleaf</groupId>
    <artifactId>thymeleaf-layout-dialect</artifactId>
</dependency>

2. 配置

spring:
  thymeleaf:
    cache: false          # 开发时关闭缓存
    prefix: classpath:/templates/
    suffix: .html
    mode: HTML
    encoding: utf-8
    servlet:
      content-type: text/html

3. 目录结构

src/main/resources/templates/
├── fragments/           # 公共片段
│   ├── header.html
│   └── footer.html
├── layout/              # 布局模板
│   └── base.html
├── index.html           # 页面
├── product.html
└── error/
    ├── 404.html
    └── 500.html

三、核心语法

1. 变量取值

<!-- Controller 传值 -->
<p th:text="${message}">默认文本</p>
<p th:text="${user.name}">张三</p>
<p th:text="${user.age > 18 ? '成年' : '未成年'}">成年</p>
<!-- 对象属性 -->
<div th:object="${user}">
    <p th:text="*{name}">姓名</p>
    <p th:text="*{age}">年龄</p>
</div>

2. 条件判断

<!-- if-unless -->
<p th:if="${user != null}">用户已登录</p>
<p th:unless="${user != null}">未登录</p>
<!-- switch-case -->
<div th:switch="${user.role}">
    <p th:case="'admin'">管理员</p>
    <p th:case="'user'">普通用户</p>
    <p th:case="*">未知角色</p>
</div>

3. 循环遍历

<table>
    <thead>
        <tr>
            <th>序号</th>
            <th>名称</th>
            <th>价格</th>
        </tr>
    </thead>
    <tbody>
        <tr th:each="product, stat : ${productList}">
            <td th:text="${stat.count}">1</td>
            <td th:text="${product.name}">商品名</td>
            <td th:text="${#numbers.formatDecimal(product.price, 0, 2)}">0.00</td>
        </tr>
    </tbody>
</table>

循环状态变量:

stat.index     → 从 0 开始的索引
stat.count     → 从 1 开始的计数
stat.size      → 总数量
stat.first     → 是否是第一个
stat.last      → 是否是最后一个
stat.odd       → 是否是奇数行
stat.even      → 是否是偶数行

4. URL 链接

<!-- 绝对路径 -->
<script th:src="@{/js/app.js}"></script>
<link th:href="@{/css/style.css}" rel="external nofollow"  rel="external nofollow"  rel="stylesheet"/>
<!-- 带参数 -->
<a th:href="@{/product/detail(id=${product.id})}" rel="external nofollow" >详情</a>
<!-- 多参数 -->
<a th:href="@{/product/list(page=${page}, size=20)}" rel="external nofollow" >下一页</a>
<!-- RESTful 风格 -->
<a th:href="@{/product/{id}(id=${product.id})}" rel="external nofollow" >详情</a>

四、布局与组件复用

1. 定义布局模板 (layout/base.html)

<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org"
      xmlns:layout="http://www.ultraq.net.nz/thymeleaf/layout">
<head>
    <meta charset="UTF-8">
    <title th:text="${title}">默认标题</title>
    <link th:href="@{/css/style.css}" rel="external nofollow"  rel="external nofollow"  rel="stylesheet"/>
</head>
<body>
    <!-- 顶部导航 -->
    <div th:replace="fragments/header :: header"></div>
    <!-- 页面主体内容 -->
    <div layout:fragment="content">
        默认内容
    </div>
    <!-- 底部 -->
    <div th:replace="fragments/footer :: footer"></div>
</body>
</html>

2. 公共片段 (fragments/header.html)

<div th:fragment="header">
    <nav>
        <a th:href="@{/}" rel="external nofollow"  rel="external nofollow" >首页</a>
        <a th:href="@{/product/list}" rel="external nofollow" >商品</a>
        <a th:href="@{/about}" rel="external nofollow" >关于</a>
    </nav>
</div>

3. 子页面使用布局

<html xmlns:th="http://www.thymeleaf.org"
      xmlns:layout="http://www.ultraq.net.nz/thymeleaf/layout"
      layout:decorate="~{layout/base}">
<!-- 只需填写内容部分 -->
<div layout:fragment="content">
    <h1 th:text="${product.name}">商品名称</h1>
    <p th:text="'¥' + ${product.price}">价格</p>
</div>

五、表单处理

<form th:action="@{/product/save}" th:object="${product}" method="post">
    <input type="hidden" th:field="*{id}"/>
    <label>名称:</label>
    <input type="text" th:field="*{name}"/>
    <p th:if="${#fields.hasErrors('name')}" th:errors="*{name}">错误提示</p>
    <label>价格:</label>
    <input type="text" th:field="*{price}"/>
    <label>分类:</label>
    <select th:field="*{category}">
        <option th:each="cat : ${categories}" 
                th:value="${cat}" 
                th:text="${cat}">分类</option>
    </select>
    <button type="submit">提交</button>
</form>

六、内置工具方法

<!-- 日期格式化 -->
<p th:text="${#dates.format(now, 'yyyy-MM-dd HH:mm:ss')}">2026-07-06</p>
<!-- 数字格式化 -->
<p th:text="${#numbers.formatDecimal(price, 0, 2)}">0.00</p>
<!-- 字符串截断 -->
<p th:text="${#strings.abbreviate(description, 50)}">描述</p>
<!-- 集合大小 -->
<p th:text="${#lists.size(productList)}">0</p>
<!-- 是否包含 -->
<p th:if="${#strings.contains(name, '手机')}">手机类商品</p>
<!-- 生成随机数 -->
<p th:text="${#uris.escapePath(uri)}">编码后URL</p>

七、秒杀系统页面整合

<!-- product/list.html -->
<html layout:decorate="~{layout/base}">
<div layout:fragment="content">
    <h1>秒杀商品列表</h1>
    <div class="product-grid">
        <div class="card" th:each="p : ${products}">
            <h3 th:text="${p.productName}">名称</h3>
            <p class="desc" th:text="${p.productDesc}">描述</p>
            <span class="original" th:text="'¥' + ${p.price}">原价</span>
            <span class="seckill" th:text="'¥' + ${p.seckillPrice}">秒杀价</span>
            <button th:attr="data-id=${p.id}" 
                    th:disabled="${p.stock <= 0}"
                    onclick="doSeckill(this)">
                立即抢购
            </button>
        </div>
    </div>
</div>
</html>

八、错误页面

SpringBoot 自动识别 templates/error/ 下的页面:

<!-- error/404.html -->
<!DOCTYPE html>
<html>
<head><title>404</title></head>
<body>
    <h1>404 - 页面未找到</h1>
    <p th:text="${error}">错误信息</p>
    <a th:href="@{/}" rel="external nofollow"  rel="external nofollow" >返回首页</a>
</body>
</html>

九、性能优化

spring:
  thymeleaf:
    cache: true           # 生产开启缓存
    check-template-location: true
    cacheable: true

总结

Thymeleaf 的核心套路:

取值:th:text / th:value
条件:th:if / th:unless
循环:th:each
链接:th:href / th:src
布局:layout:decorate / th:replace
表单:th:object / th:field

对于秒杀系统这种前后端不分离的项目,Thymeleaf 完全够用,而且开发效率比前后端分离高。

以上就是SpringBoot整合Thymeleaf模板引擎的实战指南的详细内容,更多关于SpringBoot整合Thymeleaf模板引擎的资料请关注脚本之家其它相关文章!

您可能感兴趣的文章:
阅读全文