springboot整合Freemarker动态生成JSON

news2024/9/30 11:39:49

什么是Freemarker

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

模板编写为FreeMarker Template Language (FTL)。它是简单的,专用的语言, 不是 像PHP那样成熟的编程语言。 那就意味着要准备数据在真实编程语言中来显示,比如数据库查询和业务运算, 之后模板显示已经准备好的数据。在模板中,你可以专注于如何展现数据, 而在模板之外可以专注于要展示什么数据。

实现代码

创建一个test.json

{
  "fileId": "${id}",
  "name": "${name}",
  "date": "<#if date??>${date?string('yyyy-MM-dd HH:mm:ss')}<#else></#if>",
  "id": "${id}"
}

Freemarker工具类


import freemarker.template.Configuration;
import freemarker.template.Template;
import freemarker.template.TemplateException;

import java.io.*;
import java.nio.charset.StandardCharsets;

/**
 * Freemarker工具类
 * @author zhou
 */
public class MyFreemarkerUtil {

    private final static String ENCODING = "utf-8";

    /**
     * resources下的目录
     */
    private final static String BASE_PACKAGE_PATH = "/freemarker";

    private static final MyFreemarkerUtil INSTANCE = new MyFreemarkerUtil();

    private final Configuration configuration;

    /**
     * 应该使用单实例配置(也就是说,它是单例的)。
     * 请注意不管一个系统有多少独立的组件来使用 FreeMarker,它们都会使用他们自己私有的 Configuration 实例。
     * 不需要重复创建 Configuration实例; 它的代价很高,尤其是会丢失缓存。Configuration实例就是应用级别的单例。
     * 注意Configuration实例有缓存
     */
    private MyFreemarkerUtil() {
        // org.freemarker version
        configuration = new Configuration(Configuration.VERSION_2_3_30);
        configuration.setDefaultEncoding(ENCODING);
        //选择模板保存路径resources下
        configuration.setClassForTemplateLoading(MyFreemarkerUtil.class, BASE_PACKAGE_PATH);
    }

    public static MyFreemarkerUtil getInstance() {
        return INSTANCE;
    }

    /**
     * 根据ftl模板生成字符串
     * @param data
     * @param ftlName
     * @return
     */
    public static String generateStr(Object data, String ftlName) throws IOException, TemplateException {
        // 输出文档路径及名称
        //以utf-8的编码读取ftl文件
        MyFreemarkerUtil instance = MyFreemarkerUtil.getInstance();
        Template template = instance.configuration.getTemplate(ftlName, ENCODING);
        StringWriter out = new StringWriter();
        template.process(data, out);
        return out.toString();
    }

    /**
     * 根据ftl模板生成文件
     * @param data
     * @param ftlName
     * @param outFilePath
     */
    public static void generateFile(Object data, String ftlName, String outFilePath) throws IOException {
        MyFreemarkerUtil instance = MyFreemarkerUtil.getInstance();
        Template template = instance.configuration.getTemplate(ftlName);
        File file = new File(outFilePath);
        try (FileOutputStream fileOutputStream = new FileOutputStream(file);
             OutputStreamWriter outputStream = new OutputStreamWriter(fileOutputStream, StandardCharsets.UTF_8)
        ) {
            StringWriter out = new StringWriter();
            template.process(data, out);
            String content = out.toString();
            outputStream.write(content);
            outputStream.flush();
            fileOutputStream.flush();
        } catch (IOException | TemplateException e) {
            e.printStackTrace();
        }
    }

}

main

    public static void main(String[] args) throws IOException, TemplateException {
        // 假设我们有一个Map来表示数据模型
        Map<String, Object> datas = new HashMap<>();
        datas.put("id", 30);
        datas.put("name", "name");
        datas.put("date", null);
        String s = MyFreemarkerUtil.generateStr(datas, "test.json");
        JSONObject jsonObject = JSONObject.parseObject(s);
        System.out.println(jsonObject);
    }

代码升级版

FreemarkerConfigurationBuildFatroy

import freemarker.template.Configuration;

import java.io.File;
import java.io.IOException;

/**
 * @author zhou
 */
public class FreemarkerConfigurationBuildFatroy {

    private final static String ENCODING = "utf-8";
    
    /**
     * resources下的目录
     */
    private final static String BASE_PACKAGE_PATH = "/freemarker";

    /**
     * 选择模板保存路径(本地磁盘)
     * @param filePath
     * @return
     * @throws IOException
     */
    public static Configuration getConfigurationForFile(String filePath) throws IOException {
        // org.freemarker version
        Configuration configuration = new Configuration(Configuration.VERSION_2_3_30);
        configuration.setDefaultEncoding(ENCODING);
        // 选择模板保存路径(本地磁盘)
        configuration.setDirectoryForTemplateLoading(new File(filePath));
        return configuration;
    }

    /**
     * 选择模板保存路径resources下
     */
    public static Configuration getConfigurationForClass(){
        // org.freemarker version
        Configuration configuration = new Configuration(Configuration.VERSION_2_3_30);
        configuration.setDefaultEncoding(ENCODING);
        // 选择模板保存路径resources下
        configuration.setClassForTemplateLoading(FreemarkerConfigurationBuildFatroy.class, BASE_PACKAGE_PATH);
        return configuration;
    }
    
}

import freemarker.template.Configuration;
import freemarker.template.Template;
import freemarker.template.TemplateException;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.io.IOException;
import java.io.StringWriter;
import java.util.Map;

/**
 * @author zhou
 */
public class FreemarkerBean {

    private final static String ENCODING = "utf-8";

    private static final Logger logger = LoggerFactory.getLogger(FreemarkerBean.class);

    private final Configuration configuration;

    public FreemarkerBean(Configuration configuration) {
        this.configuration = configuration;
    }

    public Template getTemplate(String ftlName) throws IOException {
        return configuration.getTemplate(ftlName, ENCODING);
    }

    /**
     * 动态构建前端展示组件的JSON格式
     * @param datas
     * @param ftlPath
     * @return
     */
    public String buildJsonStr(Map<String, Object> datas, String ftlPath) {
        try {
            Template template = getTemplate(ftlPath);
            StringWriter out = new StringWriter();
            template.process(datas, out);
            return out.toString();
        } catch (IOException | TemplateException e) {
            logger.error("buildJsonStr error {}", e.getMessage());
            // 自行处理异常...
            
        }
    }

    public void init() {
        logger.info("FreemarkerBean ... init...");
    }

    public void detory() {
        logger.info("FreemarkerBean ... destory...");
    }

}
    public static void main(String[] args){
        // 假设我们有一个Map来表示数据模型
        Map<String, Object> datas = new HashMap<>();
        datas.put("name", "name");
        datas.put("date", null);
        datas.put("id", 30);
        Configuration configuration = FreemarkerConfigurationBuildFatroy.getConfigurationForClass();
        FreemarkerBean freemarkerBean = new FreemarkerBean(configuration);
        String s = freemarkerBean.buildJsonStr(datas, "test.json");
        System.out.println(s);
    }

注意

链接: Freemarker介绍和语法

Warning!
不需要重复创建 Configuration 实例; 它的代价很高,尤其是会丢失缓存。Configuration 实例就是应用级别的单例。
在这里插入图片描述

常用语法

在这里插入图片描述

数字内建函数

给出数字的绝对值

给出数字的绝对值。比如 x?abs ,如果 x 是 -5,会得到5。
该内建函数从 FreeMarker 2.3.20 版本开始存在。

保留位数

<#assign x = 1.234>
${x?string["0"]}
${x?string["0.#"]}
${x?string["0.##"]}
${x?string["0.###"]}

输出
1
1.2
1.23
1.234
<#setting number_format=",##0.00">
<#setting locale="en_US">
US people write:     ${12345678}
<#setting locale="hu">
German people write: ${12345678}

输出
US people write:     12,345,678.00
German people write: 12.345.678,00
1
1
1
1

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2179519.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

node实现大文件切片上传的方法

切片上传定义 文件切片上传&#xff0c;也称为分片上传&#xff0c;是一种处理大文件上传的有效方法。该方法通过将大文件分割成多个较小的部分&#xff08;即切片或分片&#xff09;&#xff0c;然后分别上传这些切片到服务器&#xff0c;最后在服务器上将这些切片合并成原始文…

新手教学系列——用 VSCode 实现高效远程开发

随着软件开发环境日益复杂,远程开发已成为许多开发者的日常工作方式。尤其当项目需要直接在服务器上运行或本地计算资源有限时,能够使用一款便捷、强大的工具至关重要。在众多 IDE 中,VSCode 因其轻量、灵活且支持丰富插件,成为远程开发的理想选择。本文将详细介绍如何通过…

【Vue3】状态仓库持久化

前言 由于 vuex 和 pinia 是将数据存储到内存中的&#xff0c;所以刷新页面后数据会丢失。如果想要持久化存储&#xff0c;就需要将数据同步到 WebStorage。可以使用现有的插件或者自己手写一个插件&#xff0c;本文对二者均有介绍。 其中手写插件案例使用两个简单模块&#…

【PyTorch】图像目标检测

图像目标检测是什么 Object Detection 判断图像中目标的位置 目标检测两要素 分类&#xff1a;分类向量 [p0, …, pn]回归&#xff1a;回归边界框 [x1, y1, x2, y2] 模型如何完成目标检测 将3D张量映射到两个张量 分类张量&#xff1a;shape为 [N, c1]边界框张量&#xf…

【选择”丹摩“深入探索智谱AI的CogVideoX:视频生成的新前沿】

文章目录 一、CogVideoX模型概述二、变革性的3D变分自编码器三、先进的3D旋转位置编码四、端到端的视频理解模型五、丹摩平台的环境配置简单介绍六、开发者的展望示例代码&#xff1a;与CogVideoX的交互 2024年8月6日&#xff0c;智谱AI宣布其开源视频生成模型CogVideoX&#x…

16、斑马设备的ppocer-4进行文字识别和opencv-mobile中文显示

基本思想:手上有个斑马设备,是客户的,简单记录一下开发过程和工程项目,同时记录跟着android小哥学习了很多anroid的知识,转ppocr-4参考之前的ppocr-3转换即可,整个框架仍然使用c++ ncnn jni框架推理和现实,图像库使用opencv-mobile 一、首先转paddle-cor-4 到ncnn的框架…

E34.【C语言】位段练习题

1.题目 分析下列代码中位段在内存中的排布(已知测试平台为VS2022) struct S {int a : 2;int b : 5;int c : 10;int d : 30; };int main() {struct S s { 0 };return 0; } 有关位段的知识点见64.【C语言】再议结构体(下)文 2.提示 VS满足:由低地址向高地址存储,按浪费空间…

新书推荐——《深度学习精粹与PyTorch实践》

深度学习绝非不可窥探的黑箱!深入理解其模型和算法的实际运作机制&#xff0c;是驾驭并优化结果的关键。你无需成为数学专家或资深数据科学家,同样能够掌握深度学习系统内部的工作原理。 本书旨在通过深入浅出的方式&#xff0c;为你揭示这些原理&#xff0c;让你在理解和解释…

C++系列-继承

&#x1f308;个人主页&#xff1a;羽晨同学 &#x1f4ab;个人格言:“成为自己未来的主人~” 继承的概念和定义 继承是面向对象程序设计使代码可以复用的最重要的手段&#xff0c;它允许程序员在保持原有类特性的基础上进行拓展&#xff0c;增加功能&#xff0c;这样可以…

SSL VPN | Easyconnect下载安装使用 (详尽)

EasyConnect是一款远程连接工具&#xff0c;为用户提供简便、快捷的远程访问和控制解决方案。 目录 下载 安装 使用 卸载 下载 通过链接进入官网技术支持板块 深信服技术支持-简单、高效、自助化服务 (sangfor.com.cn)https://support.sangfor.com.cn/ 选择软件下载 在安…

获取本函数所在代码域内的所有局部变量和值以字典形式返回locals()

【小白从小学Python、C、Java】 【考研初试复试毕业设计】 【Python基础AI数据分析】 获取本函数所在代码域内的 所有局部变量和值 以字典形式返回 locals() 选择题 关于以下代码输出的结果说法正确的是&#xff1f; a 10 def x(): b 20 print(locals()) print("【执行…

二值图像的面积求取的两种方法及MATLAB实现

一、引言 面积在数字图像处理中经常用到&#xff0c;在MATLAB中&#xff0c;计算二值图像的面积通常可以通过两种主要方法实现&#xff1a;遍历法和直接利用bwarea函数。下面将分别介绍这两种方法的原理和相应的MATLAB代码示例。 二、遍历法计算二值图像面积的原理和MATLAB代码…

护眼落地台灯品牌前十名:十大全网超高热度品牌汇总

十大护眼路灯台灯有哪些&#xff1f;在众多照明灯具产品中&#xff0c;护眼落地台灯能够提供适合多场景、大氛围的舒适照明&#xff0c;对于学生、工作群体来说能够有效的提高光线质量&#xff0c;减少不良光线带来的近视风险。可是市场品牌繁多&#xff0c;很容易选购到劣质的…

golang web笔记-2.请求request

什么是request http消息分为request&#xff08;请求&#xff09; 和 response&#xff08;响应&#xff09; request&#xff1a;在go中是一个struct&#xff0c;代表了客户段发送的http请求&#xff0c;已可以通过request 的方法访问请求中的cookie、URL、User Agent&#xf…

【论文阅读笔记】TOOD: Task-aligned One-stage Object Detection

论文代码&#xff1a;https://github.com/fcjian/TOOD 文章目录 论文小结论文简介论文方法Task-aligned Head&#xff08;T-Head&#xff09;T-Head伪代码解释 Task Alignment Learning&#xff08;TAL&#xff09;Task-aligned Sample AssignmentTask-aligned Loss 论文实验消…

STM32F1+HAL库+FreeTOTS学习15——互斥信号量

STM32F1HAL库FreeTOTS学习15——互斥信号量 1. 优先级翻转2. 互斥信号量3. 相关API函数&#xff1b;3.1 互斥信号量创建3.2 获取信号量3.3 释放信号量3.4 删除信号量 4. 操作实验1. 实验内容2. 代码实现3. 运行结果 上期我们介绍了数值信号量。这一期我们来介绍互斥信号量 1. 优…

Hadoop FileSystem Shell 常用操作命令

提示&#xff1a;本文章只总结一下常用的哈&#xff0c;详细的命令大家可以移步官方的文档&#xff08;链接贴在下面了哈&#x1f923;&#xff09;— HDFS官方命令手册链接。 目录 1. cat 命令&#xff1a;查看 HDFS 文件内容2. put 命令&#xff1a;将本地文件上传到 HDFS3.…

基于VirtualBox和Ubuntu的虚拟环境搭建

VirtualBox简介 VirtualBox 是一款开源虚拟机软件。 是由德国 Innotek 公司开发&#xff0c;由Sun Microsystems公司出品的软件&#xff0c;使用Qt编写&#xff0c;在 Sun 被 Oracle 收购后正式更名成 Oracle VM VirtualBox。简单易用&#xff0c;可虚拟的系统包括Windows&…

浅谈汽车智能座舱如何实现多通道音频

一、引言 随着汽车智能座舱的功能迭代发展&#xff0c;传统的 4 通道、6 通道、8 通道等音响系统难以在满足驾驶场景的需求&#xff0c;未来对于智能座舱音频质量和通道数会越来越高。接下来本文将浅析目前智能座舱如何实现音频功放&#xff0c;以及如何实现多路音频功放方案。…

Library介绍(三)

环境描述 工作条件 一般lib文件里面包含了芯片的工作条件即operation conditions&#xff0c;其指定了工艺&#xff08;process&#xff09;、温度&#xff08;temperature&#xff09;和电压&#xff08;voltage&#xff09;&#xff0c;见图1。 其中&#xff0c;process代表了…