当前位置: 首页 > news >正文

springboot与Freemarker

 1 基本使用

1.1 介绍

        FreeMarker 是一款模板引擎: 即一种基于模板和要改变的数据,并用来生成输出文本(HTML网页,电子邮件,配置文件,源代码等)的通用工具。 是一个Java类库。

        FreeMarker 被设计用来生成 HTML Web 页面,特别是基于 MVC 模式的应用程序,将视图从业务逻辑中抽离处理,业务中不再包括视图的展示,而是将视图交给 FreeMarker 来输出。虽然 FreeMarker 具有一些编程的能力,但通常由 Java 程序准备要显示的数据,由 FreeMarker 生成页面,通过模板显示准备的数据(如下图):

  • 能够生成各种文本:HTML、XML、RTF、Java 源代码等等
  • 易于嵌入到你的产品中:轻量级;不需要 Servlet 环境
  • 插件式模板载入器:可以从任何源载入模板,如本地文件、数据库等等
  • 可以按你所需生成文本:保存到本地文件;作为 Email 发送;从 Web 应用程序发送它返回给 Web 浏览器

1.2 引入依赖

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-freemarker</artifactId>
        </dependency>

1.3 编写模版

        根据 Spring Boot 约定,模板文件应该放在 src/main/resources 目录下的 templates 目录中。下面模板只是简单地输出了 Model 中的 title 属性。

<!DOCTYPE html>
<html>
<head>
    <meta charset="UTF-8">
    <title>Freemarker</title>
</head>
<body>
Hello ${title}!
</body>
</html>

1.4 配置属性

        Spring Boot 提供了很多配置属性,可用于在 application.yaml | properties 中定制 Freemarker。 这些属性都以 spring.freemarker 开头。freemarker必要配置如下:

  freemarker:
    template-loader-path: classpath:/templates  # classpath:  一定不能漏写
    cache: false
    charset: UTF-8
    check-template-location: true
    content-type: text/html
    expose-request-attributes: false
    expose-session-attributes: false
    request-context-attribute: req
    suffix: .ftl

        下面列举常见配置项。

  freemarker:
    # 启用 freemarker 模板
    enabled: true
    # 是否缓存
    cache: false
    # Content Type
    content-type: text/html
    # 编码,默认utf-8
    charset: utf-8
    # 模板后缀
    suffix: .ftl
    # 引用 request 的属性名称
    request-context-attribute: request
    # 是否暴露 request 域中的属性
    expose-request-attributes: false
    # 是否暴露session域中的属性
    expose-session-attributes: false
    # request 域中的属性是否可以覆盖 controller 的 model 的同名项。默认 false,如果发生同名属性覆盖的情况会抛出异常
    allow-request-override: true
    # session 域中的属性是否可以覆盖 controller 的 model 的同名项。默认 false,如果发生同名属性覆盖的情况会抛出异常
    allow-session-override: true
    # 暴露官方提供的宏
    expose-spring-macro-helpers: true
    # 启动时检查模板位置是否有效
    check-template-location: true
    # 优先加载文件系统的模板
    prefer-file-system-access: true
    # 模板所在位置(目录)
    template-loader-path:
      - classpath:/templates/
    settings:
      datetime_format: yyyy-MM-dd HH:mm:ss      # date 输出格式化
      template_update_delay: 30m                # 模板引擎刷新时间
      default_encoding: utf-8                   # 默认编码

1.5 定义 Controller

        在 ModelAndView 对象的构造函数中指定要渲染的视图(模板),不需要添加 .ftl 后缀,因为已经统一在配置文件中定义了。

package com.ywz.project;

import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.servlet.ModelAndView;

@Controller
public class IndexController {

    @GetMapping("/index")
    public ModelAndView index () {
        // 创建 ModelAndView 对象,并指定视图名称
        ModelAndView modelAndView = new ModelAndView("index/index");
        // 添加 title 属性到 Model
        modelAndView.addObject("title", "Freemarker");
        return modelAndView;
    }
}

1.6 启动项目通过浏览器访问

2 FreeMarker 数据类型

        FreeMarker模板中的数据类型由如下几种:

  • 布尔型:等价于java的Boolean类型,不同的是不能直接输出,可转化为字符串输出
  • 日期型:等价于java的Date类型,不同的是不能直接输出,需要转换为字符串再输出
  • 数值型:等价于java中int,float,double等数值类型   (有三种显示形式:数值型(默认)、货币型、百分比型)
  • 字符型:等价于java中的字符串,有很多内置函数
  • sequence类型:等价于java中的数组,list,set等集合类型
  • hash类型:等价于java中的Map类型

2.1 布尔类型

modelAndView.addObject("flag", true);
<h4>FreeMarker 数据类型</h4>
<#--
    FreeMarker 数据类型
        布尔类型
            在freeMarker页面中不能直接输出,如果要输出需要转换成字符串
            方式一:?c
            方式二:?string 或 ?string('为true时显示的内容','为false时显示的内容')
            方式三:?then('为true时显示的内容','为false时显示的内容')
-->
<h5>布尔类型</h5><br/>
${flag?c}<br/>
${flag?string}<br/>
${flag?string('yes','no')}<br/>
${flag?string('喜欢','不喜欢')}<br/>

${flag?then('yes','no')}<br/>
${flag?then('喜欢','不喜欢')}<br/>

2.2 日期类型

modelAndView.addObject("createDate",new Date());
<#--
    数据类型:日期类型
        在freemarker中日期类型不能直接输出:如果输出要先转成日期型或字符串
        1.年月日   ?date
        2.时分秒   ?time
        3.年月日时分秒 ?datetime
        4.指定格式   ?string ("自定义格式")
                    y: 年 M:月 d:日
                    H: 时 m:分 s:秒
-->
 
<#-- 输出日期格式 -->
    ${createDate?date} <br/>
<#-- 输出时间格式 -->
    ${createDate?time}<br/>
<#-- 输出日期时间格式 -->
    ${createDate?datetime} <br/>
<#-- 输出格式化日期格式 -->
    ${createDate?string("yyyy年MM月dd日 HH:mm:ss")}<br/>

2.3 数值类型

        modelAndView.addObject("age", 18);
        modelAndView.addObject("salary", 10000);
        modelAndView.addObject("avg", 0.545);
<#--
    数据类型:数值类型
        在freemarker中数值类型可以直接输出;
        1.转字符串
          普通字符串   ?c
          货币型字符串  ?string.currency
          百分比型字符串 ?string.percent
         2.保留浮点型数值指定小数位(#表示一个小数位)
          ?string["0.##"
-->
<#-- 直接输出数值型 -->
${age} <br/>
${salary} <br/>
${avg} <br/>
 
<#-- 将数值转换成字符串类型 -->
${salary?c} <br/>
 
<#-- 将数值转化成货币类型字符串 -->
${salary?string.currency} <br/>
 
<#-- 将数值转化成百分比类型的字符串 -->
${avg?string.percent} <br/>
 
<#-- 将浮点型的数值转换成指定小数位输出(四舍五入) -->
${avg?string["0.##"]} <br/>

2.4 字符串类型

        modelAndView.addObject("msg", "Hello");
        modelAndView.addObject("msg2", "freemarker");
<#--
    数据类型:字符串类型
        在freemarker中字符串类型可以直接输出:
        1.截取字符串(左闭右开)?substring(start,end)
        2.首字母小写输出 ?uncap_first
        3.首字母大写输出 ?cap_first
        4.字母转小写输出 ?lower_case
        5.字母转大写输出 ?upper_case
        6.获取字符串长度 ?length
        7.是否以指定字符开头(boolean 类型) ?starts_with("xx")?string
        8.是否以指定字符结尾(boolean 类型) ?ends_with("xx")?string
        9.获取指定字符的索引 ?index_of("xx")
        10.去除字符串前后空格 ?trim
        11.替换指定字符串 ?replace("xx","xx")
-->
 
${msg} -- ${msg2} <br/>
${msg?string} -- ${msg2?string} <br/>
<#--1.截取字符串(左闭右开)?substring(start,end)-->
${msg?substring(0,2)}<br/>
<#--2.首字母小写输出 ?uncap_first-->
${msg?uncap_first}<br/>
<#--3.首字母大写输出 ?cap_first-->
${msg?cap_first}<br/>
<#--4.字母转小写输出 ?lower_case-->
${msg?lower_case}<br/>
<#--5.字母转大写输出 ?upper_case-->
${msg2?upper_case}<br/>
<#--6.获取字符串长度 ?length-->
${msg?length}<br/>
<#--7.是否以指定字符开头(boolean 类型) ?starts_with("xx")?string-->
${msg?starts_with("a")?string}<br/>
<#--8.是否以指定字符结尾(boolean 类型) ?ends_with("xx")?string-->
${msg?ends_with("o")?string}<br/>
<#--9.获取指定字符的索引 ?index_of("xx")-->
${msg2?index_of("m")}<br/>
<#--10.去除字符串前后空格 ?trim-->
${msg2?trim}<br/>
<#--11.替换指定字符串 ?replace("xx","xx")-->
${msg?replace("he","we")}<br/>

2.5 空值类型

        modelAndView.addObject("str1", null);
        modelAndView.addObject("str2", "");
<#--
字符串空值情况处理:
        FreeMarker的变量必须赋值,否则就会抛出异常。而对于FreeMarker来说,null值和不存在的变量是完全一样的,因为FreeMarker无法理解null值。
        FreeMarker提供两个运算符来避免空值:
 
①!:指定缺失变量的默认值
    ${value!}:如果value值为空,则默认值是空字符串
    ${value!"默认值"}:如果value值为空,则默认值是字符串“默认值”
 
②??:判断变量是否存在
    如果变量存在,返回true,否则返回false
    ${(value??)?string}
 
-->
 
 
<#-- 如果值不存在,直接输出会报错 -->
<#-- ${bb}-->
 
<#-- 值为null的数据 -->
<#--${str1}<br/>-->
 
<#-- 值为空字符串的数据 -->
${str2}<br/>
<#-- 使用!,当值不存在时,默认显示空字符串 -->
${str!}<br/>
<#-- 使用!"xx",当值不存在时,默认显示指定字符串 -->
${str!"这是一个默认值"}<br/>
<#-- 使用??,判断字符串是否为空;返回布尔类型,如果想要输出,需要将布尔类型转换成字符串-->
${(str??)?string}<br/>

2.6 sequence类型

        //序列类型 (数组、List、Set)
        //数组操作
        String[] stars = new String[]{"周杰伦","林俊杰","陈奕迅","五月天"};
        modelAndView.addObject("stars",stars);
        
        //List操作
        List<String> citys = Arrays.asList("上海","北京","杭州","深圳");
        modelAndView.addObject("cityList",citys);
        
        //JavaBean集合
        List<User> userList = new ArrayList<>();
        userList.add(new User(1,"zhangsan",22));
        userList.add(new User(2,"lisi",18));
        userList.add(new User(3,"wangwu",20));
        modelAndView.addObject("userList",userList);
<#--
    FreeMarker 数据类型
        序列类型 (数组、List、Set)
        通过list指令输出序列
        <#list 序列名 as 元素名>
            ${元素名}
        </#list>
 
        获取序列的长度        ${序列名?size}
        获取序列元素的下标     ${元素名?index}
        获取第一个元素        ${序列名?first}
        获取最后一个元素       ${序列名?last}
 
 
        倒序输出    序列名?reverse
        升序输出    序列名?sort
        降序输出    序列名?sort?reverse
        指定字段名排序   序列名?sort_by("字段名")
    注:一般是JavaBean集合,对应的字段名需要提供get方法
-->
 
<#-- 数组操作 -->
<#list stars as star>
    下标:${star?index}-姓名:${star}<br/>
</#list>
 
获取序列的长度:  ${stars?size}<br/>
获取第一个元素:   ${stars?first}<br/>
获取最后一个元素:  ${stars?last}<br/>
 
<#-- List操作 -->
<#list cityList as city>
    ${city}-
</#list>
<br/>
<#--倒序输出    序列名?reverse-->
<#list cityList?reverse as city>
    ${city}-
</#list>
<br/>
<#--升序输出    序列名?sort-->
<#list cityList?sort as city>
    ${city}-
</#list>
<br/>
<#--降序输出    序列名?sort?reverse-->
<#list cityList?sort?reverse as city>
    ${city}-
</#list>
<br/>
 
<#list userList as user>
    编号:${user.id}&nbsp;姓名:${user.username}&nbsp;${user.age}<br/>
</#list>
 
<#--指定字段名排序   序列名?sort_by("字段名")-->
<#list userList?sort_by("age") as user>
    编号:${user.id}&nbsp;姓名:${user.username}&nbsp;${user.age}<br/>
</#list>

2.7 Hash类型

        //Map操作
        Map<String, String> cityMap = new HashMap<>();
        cityMap.put("sh", "上海");
        cityMap.put("bj", "北京");
        cityMap.put("sz", "深圳");
        modelAndView.addObject("cityMap", cityMap);
<#--
    数据类型:hash类型
        key遍历输出
            <#list hash?keys as key>
                ${key} -- ${hash[key]}
            </#list>
         value遍历输出
            <#list hash?values as value>
                ${value}
            </#list>
-->
<#-- key遍历输出 -->
<#list cityMap?keys as key>
    ${key} -- ${cityMap[key]} <br/>
</#list>
 
<#--value遍历输出-->
<#list cityMap?values as value>
    ${value}<br/>
</#list>

相关文章:

  • DeepSeek专题:以专业角度详细讲讲Deepseek-R1的高质量数据合成过程⌛
  • PyCharm2024使用Python3.12在Debug时,F8步进时如同死机状态
  • Pytorch深度学习教程_3_初识pytorch
  • 美团商家版 验证码 分析
  • 视觉大模型VIT
  • 用Python构建Mad Libs经典文字游戏
  • Jvascript网页设计案例:通过js实现一款密码强度检测,适用于等保测评整改
  • 01:整型数据类型存储空间大小
  • Java语言在微服务架构中的应用研究
  • 大模型驱动的业务自动化
  • 代码随想录 第一章 数组 704.二分查找
  • LangChain大模型应用开发:提示词工程应用与实践
  • PHP 面向对象编程
  • win32汇编环境,对话框中使用月历控件示例一
  • vLLM专题(三)-快速开始
  • 二叉搜索树的实现(C++)
  • SSL 连接
  • 网剧《一念逍遥》正式启动筹备
  • 1. 对比 LVS 负载均衡群集的 NAT 模式和 DR 模式,比较其各自的优势 。2. 基于 openEuler 构建 LVS-DR 群集。
  • DeepSeek 教我 C++ (3) : Optional / Variant 使用的应该注意的细节
  • 风雨天涯梦——《袁保龄公牍》发微
  • 云南威信麟凤镇通报“有人穿‘警察’字样雨衣参与丧事”:已立案查处
  • 特朗普访中东绕行以色列,专家:凸显美以利益分歧扩大
  • 万科:存续债券均正常付息兑付
  • 香港暂停进口美国北达科他州一地区禽肉及禽类产品
  • 水豚“豆包”出逃已40天,扬州茱萸湾景区追加悬赏