springboot+freemarker,导出html给前端

255 阅读3分钟

简单介绍

概述

FreeMarker 是一款 模板引擎: 即一种基于模板和要改变的数据, 并用来生成输出文本(HTML网页,电子邮件,配置文件,源代码等)的通用工具。 它不是面向最终用户的,而是一个Java类库,是一款程序员可以嵌入他们所开发产品的组件

适用场景

  • **模板化文档生成:**FreeMarker 是一个模板引擎,适用于生成具有固定格式的文档,比如发票、报告或合同。这些文档的结构和格式是固定的,但内容可以动态变化。
  • **内容动态填充:**使用 FreeMarker,你可以创建 Word 文档模板,并在运行时将数据填充到模板中,生成最终的 Word 文件。例如,生成个性化的信件或文档报告。
  • **简单文档生成:**适用于文档结构较为简单的场景,比如只包含文本和基本格式的文档。

准备工作

开发环境

正式开始之前,依然给出本文所基于的环境,避免环境问题可能给大家带来的影响。

  • JDK 17(理论上推荐不低于 1.8 版本)
  • IDEA INTELLIJ
  • SpringBoot 2.x

添加 FreeMarker 依赖

<!--freemarker模板依赖-->
<dependency>
  <groupId>org.springframework.boot</groupId>
  <artifactId>spring-boot-starter-freemarker</artifactId>
</dependency>

添加 FreeMarker 相关配置

添加依赖后,我们需要在项目配置文件 application.yml 中添加 FreeMarker 的相关配置。

spring:
  freemarker:
#    模板路径
    template-loader-path: template-loader-path: classpath:/static/templates/
#    模板后缀名
    suffix: .ftl
#    页面编码
    charset: utf-8
#    页面缓存
    cache: false
#    文档类型
    content-type: text/html

代码实现

模板

hello,${name}!

controller导出到前端

import com.example.freemarker.util.ExportWordUtil;
import com.example.freemarker.util.HtmlUtils;
import lombok.extern.log4j.Log4j2;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.time.LocalDate;
import java.util.HashMap;
import java.util.Map;


/**
 * FreeMarker测试案例
 *
 * @PACKAGE_NAME: com.example.freemarker.controller
 * @author: zqy
 * @DATE: 2024/8/30 15:47
 */
@Controller
@RequestMapping
@Log4j2
public class HelloController {

    @GetMapping("/freemarker")
    public String hello(Model model) {
        log.info("日志测试:{}", LocalDate.now());
        model.addAttribute("name", "world");
        return "test";
    }
}

遇到的坑

debug可以进入接口,return的时候报错404

网上很多都说是模板yml中配置的问题,但是我的配置都是正确的,后面发现是pom文件中标签中没有配置识别.ftl文件导致的

原有配置:

        <resources>
            <resource>
                <directory>src/main/resources</directory>
                <includes>
                    <include>**/*.yml</include>
                    <include>**/*.properties</include>
                    <include>**/*.xml</include>
                </includes>
                <filtering>true</filtering>
            </resource>
            <resource>
                <directory>src/main/java</directory>
                <includes>
                    <include>**/*.xml</include>
                    <include>**/*.json</include>
                    <include>**/**</include>
                </includes>
            </resource>
        </resources>

可以发现src/main/resources路径下没有配置识别.ftl类型文件

更改之后配置:

        <resources>
            <resource>
                <directory>src/main/resources</directory>
                <includes>
                    <include>**/*.yml</include>
                    <include>**/*.properties</include>
                    <include>**/*.xml</include>
<!--                    <include>**/*.ftl</include>-->
                    <include>**/**</include>
                </includes>
                <filtering>true</filtering>
            </resource>
            <resource>
                <directory>src/main/java</directory>
                <includes>
                    <include>**/*.xml</include>
                    <include>**/*.json</include>
                    <include>**/*.ftl</include>
                    <include>**/**</include>
                </includes>
            </resource>
        </resources>

增加了<include>**/**</include>,对任意类型的文件都可以识别了

前端接收到结果不渲染页面,返回字符串

原因:在接口类上使用了注解@RestController,这个注解等于@Controller+@ResponseBody,@responseBody注解的作用是将controller的方法返回的对象通过适当的转换器转换为指定的格式之后,写入到response对象的body区,通常用来返回JSON数据或者是XML数据。因此,注意在使用此注解之后不会再走视图处理器,而是直接将数据写入到输入流中,他的效果等同于通过response对象输出指定格式的数据。