写在前面:
freemarker作为springmvc一种视图格式,默认情况下SpringMVC支持freemarker视图格式。
需要创建Spring Boot+Freemarker工程用于测试模板。课程来自黑马程序员,便于后续复盘,自己整理了一下。
代码实现:
创建一个freemarker-test的测试工程用于后续学习。我的工程目录如下:
首先是pom.xml:
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>com.freemarker</groupId>
<artifactId>freemarker</artifactId>
<version>1.0-SNAPSHOT</version>
</parent>
<artifactId>freemarker-test</artifactId>
<properties>
<maven.compiler.source>8</maven.compiler.source>
<maven.compiler.target>8</maven.compiler.target>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-freemarker</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
</dependency>
<dependency>
<groupId>org.apache.commons</groupId>
<artifactId>commons-io</artifactId>
<version>1.3.2</version>
</dependency>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.12</version>
<scope>test</scope>
</dependency>
</dependencies>
<build>
<finalName>freemarker-test</finalName>
</build>
</project>
其次是用于测试的实体类:
package com.freemarker.pojo;
import lombok.Data;
@Data
public class Person {
private String name;
private int age;
private double height;
private double weight;
}
控制层:
package com.freemarker.controller;
import com.freemarker.pojo.Person;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.GetMapping;
@Controller
public class freemarkerTestController {
@GetMapping("/testFreemarker")
public String test01(Model model){
//1.纯文本形式的参数
model.addAttribute("name", "张三");
//2.实体类参数
Person person = new Person();
person.setName("李四");
person.setAge(18);
person.setHeight(123.45);
person.setWeight(67);
model.addAttribute("person", person);
return "test_01";
}
}
启动类:
package com.freemarker;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
@SpringBootApplication
public class testApplication {
public static void main(String[] args) {
SpringApplication.run(testApplication.class, args);
}
}
配置文件:
在resource下面新建一个templates文件夹,【切记:一定是templates!!一定是templates!!一定是templates!!我在创建时候创建成了template,导致一直无法运行成功】。
这是test_01.ftl 【文件名要和控制层中的返回值一致】:
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>这是一个freemarker的测试文件</title>
</head>
<body>
<b>普通文本展示</b><br><br>
Hello ${name} <br>
<hr>
<b>实体类数据展示</b><br/>
姓名:${person.name}<br/>
年龄:${person.age}
身高:${person.height}
体重:${person.weight}
<hr>
</body>
</html>
这是application.yml的配置:
server:
port: 12138 #服务端口
spring:
application:
name: freemarker-test #指定服务名
freemarker:
cache: false #关闭模板缓存,方便测试
settings:
template_update_delay: 0 #检查模板更新延迟时间,设置为0表示立即检查,如果时间大于0会有缓存不方便进行模板测试
suffix: .ftl #指定Freemarker模板文件的后缀名
一切就绪以后,在浏览器中输入http://localhost:12138/testFreemarker即可运行:
FTL指令:
1、遍历list集合
基本格式:
<#list ></#list>
代码实现:
控制层:
@GetMapping("/list")
public String listTest(Model model){
Person person1 = new Person();
person1.setName("李四");
person1.setAge(18);
person1.setHeight(123.45);
person1.setWeight(67);
Person person2 = new Person();
person2.setName("王五");
person2.setAge(19);
person2.setHeight(123.45);
person2.setWeight(78);
ArrayList<Person> personList = new ArrayList<>();
personList.add(person1);
personList.add(person2);
model.addAttribute("personList", personList);
return "test_02";
}
test_02.ftl:
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>freemarker学习之list</title>
</head>
<body>
<#-- list 数据的展示 -->
<b>遍历列表中的数据展示</b>
<br>
<br>
<table>
<tr>
<td>序号</td>
<td>姓名</td>
<td>年龄</td>
<td>身高</td>
<td>体重</td>
</tr>
<#--遍历person集合-->
<#list personList as pl>
<tr>
<td>${pl_index + 1}</td> <#--index默认从0开始,所以加1-->
<td>${pl.name}</td>
<td>${pl.age}</td>
<td>${pl.height}</td>
<td>${pl.weight}</td>
</tr>
</#list>
</table>
<hr>
</body>
</html>
运行结果:
2、遍历Map
1)前置语法
获取Map中数据方式一:通过map['keyname'].property
<a href="###">方式一:通过map['keyname'].property</a><br/>
输出person1的信息:<br/>
姓名:${personMap['person1'].name}<br/>
年龄:${personMap['person1'].age}<br/>
身高:${personMap['person1'].height}<br/>
体重:${personMap['person1'].weight}<br/>
<br/>
获取Map中数据方式二:通过map.keyname.property
<a href="###">方式二:通过map.keyname.property</a><br/>
输出person2的学生信息:<br/>
姓名:${personMap.person2.name}<br/>
年龄:${personMap.person2.age}<br/>
身高:${personMap.person2.height}<br/>
体重:${personMap.person2.weight}<br/>
<br/>
遍历Map中的数据:
<a href="###">遍历map中两个学生信息:</a><br/>
<table>
<tr>
<td>序号</td>
<td>姓名</td>
<td>年龄</td>
<td>身高</td>
<td>体重</td>
</tr>
<#list personMap?keys as key>
<tr>
<td>${key_index + 1}</td> <#--index默认从0开始,所以加1-->
<td>${personMap[key].name}</td>
<td>${personMap[key].age}</td>
<td>${personMap[key].height}</td>
<td>${personMap[key].weight}</td>
</#list>
</tr>
2)代码实现
控制层:
@GetMapping("/map")
public String mapTest(Model model){
Person person1 = new Person();
person1.setName("李四");
person1.setAge(18);
person1.setHeight(123.45);
person1.setWeight(67);
Person person2 = new Person();
person2.setName("王五");
person2.setAge(19);
person2.setHeight(123.45);
person2.setWeight(78);
Map<String, Person> personMap = new HashMap<>();
personMap.put("person1", person1);
personMap.put("person2", person2);
model.addAttribute("personMap", personMap);
return "test_03";
}
test_03.ftl:
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>freemarker学习之map</title>
</head>
<body>
<#-- Map 数据的展示 -->
<b>map数据的展示</b>
<br/><br/>
<a href="###">方式一:通过map['keyname'].property</a><br/>
输出person1的信息:<br/>
姓名:${personMap['person1'].name}<br/>
年龄:${personMap['person1'].age}<br/>
身高:${personMap['person1'].height}<br/>
体重:${personMap['person1'].weight}<br/>
<br/>
<a href="###">方式二:通过map.keyname.property</a><br/>
输出person2的学生信息:<br/>
姓名:${personMap.person2.name}<br/>
年龄:${personMap.person2.age}<br/>
身高:${personMap.person2.height}<br/>
体重:${personMap.person2.weight}<br/>
<br/>
<a href="###">遍历map中两个学生信息:</a><br/>
<table>
<tr>
<td>序号</td>
<td>姓名</td>
<td>年龄</td>
<td>身高</td>
<td>体重</td>
</tr>
<#list personMap?keys as key>
<tr>
<td>${key_index + 1}</td> <#--index默认从0开始,所以加1-->
<td>${personMap[key].name}</td>
<td>${personMap[key].age}</td>
<td>${personMap[key].height}</td>
<td>${personMap[key].weight}</td>
</#list>
</tr>
</table>
<hr>
</body>
</html>
运行结果:
3、if指令
<#if >
<#else >
</if>
使用list指令中测试数据模型,使用if指令,将李四的数据变为红色。
test_02.ftl:
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>freemarker学习之list</title>
</head>
<body>
<#-- list 数据的展示 -->
<b>遍历列表中的数据展示</b>
<br>
<br>
<table>
<tr>
<td>序号</td>
<td>姓名</td>
<td>年龄</td>
<td>身高</td>
<td>体重</td>
</tr>
<#--遍历person集合-->
<#list personList as pl>
<#if pl.name="李四">
<tr style="color: red">
<td>${pl_index + 1}</td> <#--index默认从0开始,所以加1-->
<td>${pl.name}</td>
<td>${pl.age}</td>
<td>${pl.height}</td>
<td>${pl.weight}</td>
</tr>
<#else >
<tr>
<td>${pl_index + 1}</td> <#--index默认从0开始,所以加1-->
<td>${pl.name}</td>
<td>${pl.age}</td>
<td>${pl.height}</td>
<td>${pl.weight}</td>
</tr>
</#if>
</#list>
</table>
<hr>
</body>
</html>
运行结果:
输出静态化文件:
1、创建测试类
import com.freemarker.pojo.Person;
import com.freemarker.testApplication;
import freemarker.template.Configuration;
import freemarker.template.Template;
import freemarker.template.TemplateException;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.test.context.junit4.SpringRunner;
import java.io.FileWriter;
import java.io.IOException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Map;
@SpringBootTest(classes = testApplication.class)
@RunWith(SpringRunner.class)
public class freemarkerTest {
@Autowired
private Configuration configuration;
@Test
public void test() throws IOException, TemplateException {
Template template = configuration.getTemplate("test_02.ftl");
/**
* 合成方法
*
* 第一个参数 模型数据
* 第二个参数 输出流
*
*/
template.process(getData(), new FileWriter("e:/list.html"));
}
// getData中的代码来自控制层,只需要把控制层中放入model的数据放入Map中即可
private Map getData(){
Map<String, Object> map = new HashMap<>();
Person person1 = new Person();
person1.setName("李四");
person1.setAge(18);
person1.setHeight(123.45);
person1.setWeight(67);
Person person2 = new Person();
person2.setName("王五");
person2.setAge(19);
person2.setHeight(123.45);
person2.setWeight(78);
ArrayList<Person> personList = new ArrayList<>();
personList.add(person1);
personList.add(person2);
//将原来model中的数据存入map
// model.addAttribute("personList", personList);
map.put("personList", personList);
// return "test_02";
return map;
}
}
2、修改配置文件,添加模板文件的存放位置
server:
port: 12138 #服务端口
spring:
application:
name: freemarker-test #指定服务名
freemarker:
cache: false #关闭模板缓存,方便测试
settings:
template_update_delay: 0 #检查模板更新延迟时间,设置为0表示立即检查,如果时间大于0会有缓存不方便进行模板测试
suffix: .ftl #指定Freemarker模板文件的后缀名
template-loader-path: classpath:/templates #当前模板存放位置
3、输出结果
4、注意事项
在创建测试类的时候,可能会没有@RunWith注解,可以看下是否引入了这个依赖
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.12</version>
<scope>test</scope>
</dependency>