模板引擎 - Thymeleaf

  • 1. 模板引擎简介
  • 2. 模板引擎与 Thymeleaf 关系
  • 3. 模板引擎原理
  • 4. 使用流程
    • 流程一:通过 maven 引入依赖
    • 流程二:创建 HTML 模板文件
    • 流程三:编写 servlet 代码
    • 流程四:部署程序
  • 5. 理解只创建一个引擎实例?
    • (1) ServletContext
    • 代码示例:多个 servlet 共享数据
    • (2) 监听器
    • (3)修改 Thymeleaf 引擎初始化代码
  • 6. Thymeleaf 模板语法
    • (1)常用命令及功能
    • (2)设置标签文本
    • (3)设置标签属性
    • (4)条件判断
    • (5)循环

1. 模板引擎简介

模板引擎?你可能第一次听说模板引擎,估计你会禁不住想问:什么是模板引擎呢?

模板引擎(这里特指用于Web开发的模板引擎),是为了使用户界面与业务数据(内容)分离而产生的,它可以生成特定格式的文档,用于网站的模板引擎就会生成一个标准的html文档;

  • 从字面上理解:模板引擎最重要的就是 模板 二字,相当于做好一个模板后并套入对应位置的数据,最终以html的格式展示出来;
  • 将模板设计好之后直接填充数据即可,而不需要重新设计整个页面,这样就提高了页面以及代码的复用性;

2. 模板引擎与 Thymeleaf 关系

Java中模板引擎有许多,模板引擎作为动态网页发展进步的产物,在最初并且流传度最广的jsp就是一个模板引擎,但由于jsp的缺点比较多,所以很多人弃用jsp选用第三方的模板引擎,市面上开源的第三方的模板引擎也比较多,有Thymeleaf、FreeMaker、Velocity等模板引擎受众较广。

使用 Thymeleaf 优点:

  • 动静分离:Thymeleaf 使用 html 通过一些特定标签语法代表其含义,而且并未破坏html结构,即使无网络、不通过后端渲染也能在浏览器成功打开,大大方便了界面的测试和修改;

关系:Thymeleaf 是模板引擎的其中一种产品!!!

3. 模板引擎原理

  • 首先:客户端浏览器发起HTTP请求到 servlet中;
  • servlet 调用模板引擎组织 模板(静态不动的资源)+数据(动态的资源),将两者拼接为一个HTML字符串;
  • 将该HTML字符串返回给服务端;

4. 使用流程

流程一:通过 maven 引入依赖

  • maven 中央仓库搜索 Thymeleaf 并选择一个版本;

maven 中央仓库网址:https://mvnrepository.com/

进入之后,搜索 Thymeleaf:

  • 选择 3.0.12版本;

  • 拷贝依赖代码到 pox.xml 中并刷新;


同时需要使用servlet,因此也要引入servlet依赖包;

 <dependency><groupId>javax.servlet</groupId><artifactId>javax.servlet-api</artifactId><version>3.1.0</version><scope>provided</scope></dependency>

流程二:创建 HTML 模板文件

创建 hello.html , 放到 webapp/WEB-INF/templates 目录中;

<!doctype html>
<html lang="en">
<head><meta charset="UTF-8"><meta name="viewport"content="width=device-width, user-scalable=no, initial-scale=1.0, maximum-scale=1.0, minimum-scale=1.0"><meta http-equiv="X-UA-Compatible" content="ie=edge"><title>Document</title>
</head>
<body><h3>网页模板技术学习</h3><p th:text="${message}"></p>
</body>
</html>

流程三:编写 servlet 代码

操作步骤

  • 创建一个模板引擎;
  • 创建一个网页模板解析器;
  • 设置渲染时编码;
  • 设置网页模板文件路径的前缀与后缀;
  • 将模板解析器绑定到模板引擎中;
  • 创建一个web上下文(环境的语义,里面是map结构,存放键值对数据);
  • 设置键值对的数据;
  • 返回渲染后的网页字符串;
package org.example;import org.thymeleaf.TemplateEngine;
import org.thymeleaf.context.WebContext;
import org.thymeleaf.templateresolver.ServletContextTemplateResolver;import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;@WebServlet("/hello")public class HelloServlet extends HttpServlet {//模板引擎都是返回HTML,因此重写HTML@Overrideprotected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {//设置body格式与编码格式resp.setContentType("text/html; charset = utf-8");//1.创建一个模板引擎TemplateEngine engine = new TemplateEngine();//2.创建一个网页模板解析器ServletContextTemplateResolver resolver = new ServletContextTemplateResolver(getServletContext());//3.设置渲染时编码resolver.setCharacterEncoding("utf-8");//4.设置网页模板文件路径的前缀与后缀resolver.setPrefix("/WEB-INF/templates/");resolver.setSuffix(".html");//5.将模板解析器绑定到模板引擎中engine.setTemplateResolver(resolver);//6.创建一个web上下文(环境的语义,里面是map结构,可以存放键值对数据)WebContext webContext =new WebContext(req,resp,getServletContext());//7.设置键值对的数据:可以理解为:为网页模板定义了一个变量(变量名为message,值为hello模板引擎)webContext.setVariable("message","hello模板引擎");//模板引擎渲染网页模板:第一个参数为模板名称,第二个参数为web上下文(里面保存了数据)//会根据模板解析器设置的前缀+模板名称+后缀,为模板路径,查找到模板,再组织模板内容+数据//8.返回值就是渲染后的网页字符串String html =engine.process("hello",webContext);resp.getWriter().write(html);}
}

流程四:部署程序

通过 URL

http://127.0.0.1:8080/Thymeleaf-study/hello

访问服务器,可以看到网页显示:

此时,页面看起来仍是静态不变的,做如下更改:

 //此处为固定页面显示//webContext.setVariable("message","hello模板引擎");//设置动态变化的 msg=xxxwebContext.setVariable("message", req.getParameter("msg"));

这样就可以通过浏览器地址栏URL输入内容的不同而产生不同的效果!

代码分析

但以上 servlet 代码,执行效率并不高,且存在冗余!
原因:每次只要发送URL请求:就会创建一个模板引擎及解释器;

优化代码

将创建的模板引擎与解释器放置在init()方法中,该方法只调用一次!

package org.example;import org.thymeleaf.TemplateEngine;
import org.thymeleaf.context.WebContext;
import org.thymeleaf.templateresolver.ServletContextTemplateResolver;import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;@WebServlet("/hello")public class HelloServlet extends HttpServlet {//1.创建一个模板引擎TemplateEngine engine = new TemplateEngine();@Overridepublic void init() throws ServletException {//2.创建一个网页模板解析器ServletContextTemplateResolver resolver = new ServletContextTemplateResolver(getServletContext());//3.设置渲染时编码resolver.setCharacterEncoding("utf-8");//4.设置网页模板文件路径的前缀与后缀resolver.setPrefix("/WEB-INF/templates/");resolver.setSuffix(".html");//5.将模板解析器绑定到模板引擎中engine.setTemplateResolver(resolver);}//模板引擎都是返回HTML,因此重写HTML@Overrideprotected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {//设置body格式与编码格式resp.setContentType("text/html; charset = utf-8");//创建一个web上下文(环境的语义,里面是map结构,可以存放键值对数据)WebContext webContext =new WebContext(req,resp,getServletContext());//设置键值对的数据:可以理解为:为网页模板定义了一个变量(变量名为message,值为hello模板引擎)//此处为固定页面显示//webContext.setVariable("message","hello模板引擎");//设置动态变化的 msg=xxxwebContext.setVariable("message", req.getParameter("msg"));//模板引擎渲染网页模板:第一个参数为模板名称,第二个参数为web上下文(里面保存了数据)//会根据模板解析器设置的前缀+模板名称+后缀,为模板路径,查找到模板,再组织模板内容+数据//返回值就是渲染后的网页字符串String html =engine.process("hello",webContext);resp.getWriter().write(html);}
}

5. 理解只创建一个引擎实例?

上面优化后,还存在另一个问题?

当创建另一个 Servlet 时,还是需要创建一个 TemplateEngine 实例并进行初始化,因此,还是存在多个模板引擎对象与解析器对象的,但其实是完全没有必要的!!!

一个完整的项目中, 只需要创建一个 TemplateEngine, 并且只初始化一次即可~

为了达到这样的目的, 就需要使用 Servlet 中的 ServletContext 和 “监听器”;

(1) ServletContext

ServletContext 是一个 Servlet 程序中全局储存信息的空间, 服务器开始就存在, 服务器关闭才销毁;

  • Tomcat 在启动时,它会为每个Web app都创建一个对应的 ServletContext;
  • 一个Web应用中的所有 Servlet 共享同一个 ServletContext 对象;
  • 可以通过 HttpServlet.getServletContext() 或者HttpServletRequest.getServletContext() 获取到当前 webappServletContext 对象;

如下所示关系


ServletContext 对象的重要方法:

方法 功能
void setAttribute(String name,Object obj) 设置属性(键值对的形式)
Object getAttribute(String name) 根据属性名获取属性值, 如果 name 不存在, 返回 null
void removeAttribute(String name) 删除对应的属性

代码示例:多个 servlet 共享数据

(1) 创建一个 writeServlet类;

package org.example;import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;@WebServlet("/write")
public class writeServlet extends HttpServlet {// write?data=xxx@Overrideprotected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {String data = req.getParameter("data");//将数据写入servlet共享的上下文环境//获取当前servletContext对象ServletContext sc = getServletContext();//设置属性sc.setAttribute("d",data);resp.setContentType("text/html;charset=utf-8");resp.getWriter().write("写入context成功");}
}

(2) 创建一个 readServlet 类;

package org.example;import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;@WebServlet("/read")
public class readServlet extends HttpServlet {// write?data=xxx@Overrideprotected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {//获取当前servletContext对象ServletContext sc = getServletContext();//根据属性名,获取属性值Object data = sc.getAttribute("d");resp.setContentType("text/html;charset=utf-8");resp.getWriter().write("读取context:"+data);}
}

(3)通过ServletContext进行数据共享;

通过地址栏访问URL:http://localhost:8080/Thymeleaf-study/write?data=shd,可以看到写入成功标志,在http://localhost:8080/Thymeleaf-study/read访问可以读取写入的数据;

如下所示


(2) 监听器

监听器:属于一种设计模式;

使用监听器优点

  • 将事件发生和事件发生后需要执行的代码进行解耦合;
  • 事先注册一个函数或方法到监听器,在某个事件发生后,自动执行;

使用步骤

  • 创建一个类;
  • 添加@WebListener 注解,否则 Tomcat 不能识别;
  • 实现 ServletContextListener 接口, 并实现两个方法 contextInitializedcontextDestroyed

代码如下

package org.example;import javax.servlet.ServletContextEvent;
import javax.servlet.ServletContextListener;
import javax.servlet.annotation.WebListener;@WebListenerpublic class MyListener implements ServletContextListener {@Overridepublic void contextInitialized(ServletContextEvent sce) {}@Overridepublic void contextDestroyed(ServletContextEvent sce) {}
}

(3)修改 Thymeleaf 引擎初始化代码

package org.example;import org.thymeleaf.TemplateEngine;
import org.thymeleaf.templateresolver.ServletContextTemplateResolver;import javax.servlet.ServletContext;
import javax.servlet.ServletContextEvent;
import javax.servlet.ServletContextListener;
import javax.servlet.annotation.WebListener;@WebListenerpublic class MyListener implements ServletContextListener {@Overridepublic void contextInitialized(ServletContextEvent sce) {//1. 先获取context对象ServletContext context = sce.getServletContext();//2. 创建Templateengine对象TemplateEngine engine = new TemplateEngine();//3.创建解析器对象ServletContextTemplateResolver resolver = new ServletContextTemplateResolver(context);//4.设置resolver的一些属性resolver.setCharacterEncoding("utf-8");resolver.setPrefix("/WEB-INF/templates/");resolver.setSuffix(".html");//5.绑定 resolver 和 engineengine.setTemplateResolver(resolver);//6.将 engine 放到 ServletContext中,供其他servlet使用context.setAttribute("engine",engine);}@Overridepublic void contextDestroyed(ServletContextEvent sce) {}
}

后续的 Servlet 直接从 ServletContext 中获取到 engine 对象即可;

6. Thymeleaf 模板语法

(1)常用命令及功能

命令 功能
th:text 在标签体中展示表达式求值结果的文本内容
th:[HTML标签属性] 设置任意的 HTML 标签属性的值
th:if 当表达式的结果为真时则显示内容,否则不显示
th:each 循环访问元素

(2)设置标签文本

   <p th:text="${message}"></p>

最后结果:将webContext 设置的键值对数据,键为message的值设置到标签内容中;

(3)设置标签属性

常见的属性

  • href
  • src
  • class
  • style…

如设置链接 a 标签的 href 属性:

前端代码

 <a th:href="${a1}">百度</a><a th:href="${a2}">搜狗</a>

servlet代码

 package org.example;import org.thymeleaf.TemplateEngine;
import org.thymeleaf.context.WebContext;
import org.thymeleaf.templateresolver.ServletContextTemplateResolver;import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;@WebServlet("/hello")public class HelloServlet extends HttpServlet {//1.创建一个模板引擎TemplateEngine engine = new TemplateEngine();@Overridepublic void init() throws ServletException {//2.创建一个网页模板解析器ServletContextTemplateResolver resolver = new ServletContextTemplateResolver(getServletContext());//3.设置渲染时编码resolver.setCharacterEncoding("utf-8");//4.设置网页模板文件路径的前缀与后缀resolver.setPrefix("/WEB-INF/templates/");resolver.setSuffix(".html");//5.将模板解析器绑定到模板引擎中engine.setTemplateResolver(resolver);}//模板引擎都是返回HTML,因此重写HTML@Overrideprotected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {//设置body格式与编码格式resp.setContentType("text/html; charset = utf-8");//创建一个web上下文(环境的语义,里面是map结构,可以存放键值对数据)WebContext webContext =new WebContext(req,resp,getServletContext());//设置键值对的数据:webContext.setVariable("a1","http://www.baidu.com");webContext.setVariable("a2","http://www.sogou.com");//模板引擎渲染网页模板:第一个参数为模板名称,第二个参数为web上下文(里面保存了数据)//会根据模板解析器设置的前缀+模板名称+后缀,为模板路径,查找到模板,再组织模板内容+数据//返回值就是渲染后的网页字符串String html =engine.process("hello",webContext);resp.getWriter().write(html);}
}

(4)条件判断

 条件判断 th:if :根据条件决定该标签是否显示;
 <p th:if="${islogin}">已经登陆</p>

webContext.setVariable("islogin",true);传入的值为true时,就显示为:已经登陆,否则不显示;

网页显示

(5)循环

       th:each 循环的构造出多个元素;
 <ul><li th:each="name : ${names}"><span th:text="${name}"></span></li></ul>
  webContext.setVariable("names", Arrays.asList("张三","李四","王五"));

网页显示结果

模板引擎 - Thymeleaf相关推荐

  1. Spring Boot (四)模板引擎Thymeleaf集成

    一.Thymeleaf介绍 Thymeleaf是一种Java XML / XHTML / HTML5模板引擎,可以在Web和非Web环境中使用.它更适合在基于MVC的Web应用程序的视图层提供XHTM ...

  2. 六十四、SpringBoot中的模板引擎Thymeleaf

    @Author:Runsen 来源:尚硅谷 下面建议读者学习尚硅谷的B站的SpringBoot视频,我是学雷丰阳视频入门的. 具体链接如下:B站尚硅谷SpringBoot教程 文章目录 使用Sprin ...

  3. Spring Boot 最佳实践(四)模板引擎Thymeleaf集成

    ## 一.Thymeleaf介绍 Thymeleaf是一种Java XML / XHTML / HTML5模板引擎,可以在Web和非Web环境中使用.它更适合在基于MVC的Web应用程序的视图层提供X ...

  4. JavaWeb~模板引擎Thymeleaf总结

    文章目录 模板引擎是什么 有哪些常见的模板引擎 Thymeleaf使用流程 常用标签 链接表达式@{...} 变量表达式${...} 选择变量表达*{...} 消息表达式#{...}(了解) 回顾:几 ...

  5. 模板引擎 Thymeleaf 语法

    模板引擎 Thymeleaf 1. Thymeleaf 简介 Thymeleaf[taɪm lif],百里香叶,是一个流行的模板引擎,该模板引擎采用 Java 语言开发.Java 中常见的模板引擎有 ...

  6. SpringBoot-web开发(三): 模板引擎Thymeleaf

    [SpringBoot-web系列]前文: SpringBoot-web开发(一): 静态资源的导入(源码分析) SpringBoot-web开发(二): 页面和图标定制(源码分析) 目录 1. 引入 ...

  7. Spring boot(五)模板引擎 Thymeleaf

    Thymeleaf 是一款用于渲染 XML/XHTML/HTML 5 内容的模板引擎.类似 JSP.Velocity.FreeMaker 等,它也可以轻易的与 Spring MVC 等 Web 框架进 ...

  8. 模板引擎——Thymeleaf

    模板引擎 JSP.Velocity.Freemarker.Thymeleaf 1.引入thymeleaf: <dependency><groupId>org.springfra ...

  9. 前端模板引擎Thymeleaf快速入门

    文章目录 1. Thymeleaf特点 2. 提供数据 3. 引入启动器 4. 静态页面 5. 测试 6.模板缓存 1. Thymeleaf特点 简单说, Thymeleaf 是一个跟 Velocit ...

  10. SpringBoot入门:新一代Java模板引擎Thymeleaf(理论)

    Spring Boot 提供了spring-boot-starter-web来为Web开发予以支持,spring-boot-starter-web为我们提供了嵌入的Tomcat以及SpringMVC的 ...

最新文章

  1. bigquery使用教程_如何使用Python和Google BigQuery构建机器人以自动执行您的笨拙任务...
  2. Tomcat问题 无法启动
  3. Angular——基本使用
  4. C++实现类不可复制
  5. isfull mysql_MySQL数据库之MySQL 出现 The table is full 的解决方法
  6. 给路灯按上“电话卡”,从此不仅只照明还给管理员“打电话”
  7. Java面试题整理二(侧重SSH框架)
  8. python功能二维表合并,一维表内嵌元祖合并以及取交集,并集,差集
  9. JavaScript学习第八天笔记(Function)
  10. C语言中报段错误(核心已转储)的常见问题
  11. 87-非阻塞 connect
  12. java 程序员发展
  13. 通信新人,该如何写日报?
  14. Cobalt Strike 的 Profile 文件解析
  15. CSV保存身份证后再打开后4位0000的解决办法
  16. MATLAB数据分析(插值运算和曲线拟合)
  17. 跟小博老师一起学习MyBatis ——MyBatis搭建运行环境
  18. 【最优化】最优化的相关条件
  19. Navicat操作mysql遇问题1142-create command denied to user×××的解决
  20. 把自己当成人物是最傻的表现zz

热门文章

  1. 什么是弱网测试?为什么要进行弱网测试?怎么进行弱网测试?
  2. python——基于Pandas读取asc文件并保存为csv格式
  3. 易观分析联合中小银行联盟发布海南数字经济指数,敬请期待!
  4. wps安装Mathtype插件遇到的问题
  5. 移动吉比特H2-2光猫超级用户与密码
  6. 失败产品手册:一款影音娱乐平台的败局
  7. MT4跟单软件的API跟单模式有多少种?
  8. 使用UIImageView实现加载GIF图片
  9. 有哪些芯片可以测量交流信号?可以测量哪些参数?
  10. FIT2CLOUD飞致云正式推出X-Lab孵化器,首期发布两款开源软件