zoukankan      html  css  js  c++  java
  • 【学习笔记】初识FreeMarker简单使用

    楔子:

       之前在和同事讨论,同事说“jsp技术太古老了,有几种页面技术代替,比如FreeMarker、Velocity、thymeleaf,jsp快废弃了……”云云。我这一听有点心虚……我在后端部分越刨越深,页面装配技术什么的好像只知道有jsp……趁放假自己补补课啦~

    简介:

      FreeMarker是一个模板引擎,一个基于模板生成文本输出的通用工具,纯Java编写。类似jsp,简单来讲就是模板加数据模型,然后输出页面。

    图片来自尚学堂课件,侵权删

    图片来自尚学堂课件,侵权删

      相对于jsp,FreeMarker的性能略差几十毫秒,但是复杂页面上性能比jsp更佳。

      而且最好的一点,我感觉应该是可以直接把美工写好的html放进模板中使用(无需加jsp头等),FreeMarker自带的一些标签用着也很简单。FreeMarker的模板文件格式为ftl,也可以直接用html

      FreeMarker可以应用更多的场景,与容器无关;而jsp要求有JVM环境,只能应用于web应用中。

    HelloWorld:

      第一个FreeMarker代码

    新建一个Java project,起名为 FreeMarker,在src外部新建一个文件夹命名为templates,如图:

    在templates中新建一个file,命名为first.ftl,添加如下代码(其中的表达式类似于EL表达式):

    hello,${user},这是你的第一个FreeMarker程序!

    下载FreeMarker.jar并引入项目

    新建FirstFreeMarker类,代码如下:

     1 package com.hellxz;
     2 
     3 import java.io.File;
     4 import java.io.IOException;
     5 import java.io.OutputStreamWriter;
     6 import java.io.Writer;
     7 import java.util.HashMap;
     8 import java.util.Map;
     9 
    10 import freemarker.template.Configuration;
    11 import freemarker.template.Template;
    12 import freemarker.template.TemplateException;
    13 
    14 /**
    15  * 第一个FreeMarker程序
    16  * 
    17  * @author hellxz
    18  */
    19 public class FirstFreeMarker {
    20 
    21     @SuppressWarnings({"rawtypes","unchecked"})
    22     public static void main(String[] args) throws IOException, TemplateException {
    23         // 创建Freemarker配置实例
    24         Configuration cfg = new Configuration();
    25         cfg.setDirectoryForTemplateLoading(new File("templates"));
    26 
    27         // 创建数据模型
    28         Map root = new HashMap();
    29         root.put("user", "老张");
    30 
    31         // 加载模板文件
    32         Template t1 = cfg.getTemplate("first.ftl");
    33 
    34         // 显示生成的数据,将合并后的数据打印到控制台
    35         Writer out = new OutputStreamWriter(System.out);
    36         t1.process(root, out);
    37         out.flush();
    38         out.close();
    39 
    40     }
    41 
    42 }

    运行代码,查看输出:

    hello,老张,这是你的第一个FreeMarker程序!

    测试举例:

    本例子基本涵盖了大部分FreeMarker特有的属性,参考Java语言不同点写就,相同点并没有测试。通过观察代码可以很清晰的看出这些函数、指令的使用方法

    新建一个Address类:

     1 package com.hellxz;
     2 
     3 /**
     4  * 地址
     5  * 
     6  * @author hellxz
     7  */
     8 public class Address {
     9 
    10     private String country; // 国家
    11     private String city; // 城市
    12 
    13     //getters & setters
    14     public String getCountry() {
    15         return country;
    16     }
    17 
    18     public void setCountry(String country) {
    19         this.country = country;
    20     }
    21 
    22     public String getCity() {
    23         return city;
    24     }
    25 
    26     public void setCity(String city) {
    27         this.city = city;
    28     }
    29 
    30     public Address(String country, String city) {
    31         this.country = country;
    32         this.city = city;
    33     }
    34 }

    新建一个TestFreeMarker类,代码如下:

     1 package com.hellxz;
     2 
     3 import java.io.File;
     4 import java.io.IOException;
     5 import java.io.OutputStreamWriter;
     6 import java.io.Writer;
     7 import java.util.ArrayList;
     8 import java.util.HashMap;
     9 import java.util.Map;
    10 import java.util.Random;
    11 
    12 import freemarker.template.Configuration;
    13 import freemarker.template.Template;
    14 import freemarker.template.TemplateException;
    15 
    16 /**
    17  * FreeMarker Test
    18  * 
    19  * @author hellxz
    20  */
    21 public class TestFreeMarker {
    22 
    23     @SuppressWarnings({ "rawtypes", "unchecked" })
    24     public static void main(String[] args) throws IOException, TemplateException {
    25         //1.创建配置文件
    26         Configuration conf = new Configuration();
    27         //2.设置模板目录
    28         conf.setDirectoryForTemplateLoading(new File("templates"));
    29         //3.数据模型
    30         Map<String,Object> map = new HashMap<>();
    31         map.put("user", "老张");
    32         map.put("random",new Random().nextInt(100));
    33         //新建一个list放入map中,用于测试遍历list操作
    34         ArrayList list = new ArrayList();
    35         list.add(new Address("中国","上海"));
    36         list.add(new Address("日本","东京"));
    37         map.put("list", list);
    38         //测试内建函数
    39         map.put("html5", "<b>大写的文字</b>");
    40         map.put("name", "hellxz");
    41         map.put("upper", "ABCDEF");
    42         //4.获取模板文件
    43         Template template = conf.getTemplate("a.ftl");
    44         //5.输出流
    45         Writer out = new OutputStreamWriter(System.out);
    46         //6.生成文件流输出
    47         template.process(map, out);
    48         out.flush();
    49         out.close();
    50     }
    51 }

    在templates文件夹下新建a.ftl

      1 hello,${user},今天看起来很精神嘛!
      2 ----------------------------------
      3 if分支语句测试:
      4 <#if user=="老张">
      5         老张!
      6 </#if>
      7 ----------------------------------
      8 if else 分支测试:
      9 <#if user=="老李">
     10         老李
     11 <#else>
     12         老张
     13 </#if>
     14 ----------------------------------
     15 if else if else 测试:
     16 因为大于小于号等会被转义,使用简写代替比较符号
     17 gt(great than的简写) 代替 >
     18 lt(less than的简写) 代替 <
     19 gte(great than equal的简写) 代替 >=
     20 lte (less than equal的简写) 代替 <=
     21 <#if random gt 80>
     22         优秀
     23 <#elseif random gt 60>
     24         及格
     25 <#else>
     26         不及格
     27 </#if>
     28 ----------------------------------
     29 遍历list测试:
     30 <#list list as addr>
     31         ${addr.country} ${addr.city}
     32 </#list>
     33 ----------------------------------
     34 include包含测试:
     35 <#include "include.txt"/>
     36 ----------------------------------
     37 macro无参函数(宏函数)测试:
     38 定义函数:
     39 <#macro m1>
     40     我是函数内容
     41 </#macro>
     42 调用函数测试:
     43 <@m1/><@m1/><#--这是注释内容:这里调用了两次函数-->
     44 ----------------------------------
     45 macro带参函数<#--(格式为"<#macro 函数名 [变量1 变量2 变量3 ……] </#macro>")-->:
     46 <#macro cc a b c>
     47     ${a}/${b}/${c}
     48 </#macro>
     49 调用测试<#--(格式为:"<@函数名 [变量1值 变量2值 变量3值 ……] </#macro>")-->:
     50 <@cc "中" "明" "月"/>
     51 ----------------------------------
     52 nested测试:
     53 用于一大段代码的嵌入
     54 <#macro border>
     55     <html>
     56         <head>
     57             <body>
     58                 <#nested/>
     59             </body>
     60         </head>
     61     </html>
     62 </#macro>
     63 向nested部分添加内容:
     64 <@border>
     65                 <h1>我是nested的内容</h1>
     66 </@border>
     67 ----------------------------------
     68 测试命名空间:
     69 <#import "b.ftl" as bb  />
     70 <@bb.copyright date="2010-2011" />
     71 ${bb.mail}
     72 <#assign mail="my@163.com"  />
     73 ${mail}
     74 <#assign mail="my@163.com" in bb  />
     75 ${bb.mail}
     76 -----------------------------------
     77 声明、指定变量assign:
     78 测试数据类型:
     79 <#assign ss="hellxz"/>
     80 文本型:${ss}
     81 <#assign s1=1 />
     82 数值型:${s1}
     83 <#assign s2=true/>
     84 布尔型:<#if s2>布尔型</#if>
     85 -------------------------------------
     86 字符串常见内建函数:
     87 html转义:${html5?html}
     88 cap_first(首字母大写):${name?cap_first}
     89 upper_case(转大写):${name?upper_case}
     90 lower_case(转小写):${upper?lower_case}
     91 数值常见内建函数:
     92 int(取整数部分)
     93 集合内建函数:
     94 size(取集合大小)
     95 ------------------------------------
     96 字符串空值处理:
     97 FreeMarker不支持空值,如果为空直接报错
     98 没有定义直接引用
     99 <#-- ${sss} 直接报错了-->
    100 空值处理:
    101 ${sss!}<#-- 为空则输出空字符串 -->
    102 ${sss!"default"} <#--设置默认值,为空自动使用-->
    103 ------------------------------------------
    104 ??布尔值处理
    105 <#if user??>
    106 如果该值存在,返回true,相当于 if user != null
    107 <#else>
    108 该值不存在返回false
    109 </#if>

    新建b.ftl 用于测试命名空间

    1 <#macro copyright date>
    2   <p>Copyright (C) ${date} 北京尚学堂.</p> 
    3 </#macro> 
    4 <#assign mail = "bjsxt@163.com">

    在templates下新建include.txt,用于测试include指令

    我是被包含的内容!

    运行TestFreeMarker,查看输出(这里为了方便比较,加上行号):

     1 hello,老张,今天看起来很精神嘛!
     2 ----------------------------------
     3 if分支语句测试:
     4         老张!
     5 ----------------------------------
     6 if else 分支测试:
     7         老张
     8 ----------------------------------
     9 if else if else 测试:
    10 因为大于小于号等会被转义,使用简写作为比较符号
    11 gt=great than = >
    12 lt=less than = <
    13 gte = great than equal = >=
    14 lte = less than equal = <=
    15         及格
    16 ----------------------------------
    17 遍历list测试:
    18         中国 上海
    19         日本 东京
    20 ----------------------------------
    21 include包含测试:
    22 我是被包含的内容!
    23 ----------------------------------
    24 macro无参函数(宏函数)测试:
    25 定义函数:
    26 调用函数测试:
    27     我是函数内容
    28     我是函数内容
    29 ----------------------------------
    30 macro带参函数:
    31 调用测试:
    32     中/明/33 ----------------------------------
    34 nested测试:
    35 用于一大段代码的嵌入
    36 向nested部分添加内容:
    37     <html>
    38         <head>
    39             <body>
    40                 <h1>我是nested的内容</h1>
    41             </body>
    42         </head>
    43     </html>
    44 ----------------------------------
    45 测试命名空间:
    46   <p>Copyright (C) 2010-2011 北京尚学堂.</p> 
    47 bjsxt@163.com
    48 my@163.com
    49 my@163.com
    50 -----------------------------------
    51 声明、指定变量assign:
    52 测试数据类型:
    53 文本型:hellxz
    54 数值型:1
    55 布尔型:布尔型
    56 -------------------------------------
    57 字符串常见内建函数:
    58 html转义:&lt;b&gt;大写的文字&lt;/b&gt;
    59 cap_first(首字母大写):Hellxz
    60 upper_case(转大写):HELLXZ
    61 lower_case(转小写):abcdef
    62 数值常见内建函数:
    63 int(取整数部分)
    64 集合内建函数:
    65 size(取集合大小)
    66 ------------------------------------
    67 字符串空值处理:
    68 FreeMarker不支持空值,如果为空直接报错
    69 没有定义直接引用
    70 空值处理:
    71 
    72 default 
    73 ------------------------------------------
    74 ??布尔值处理
    75 如果该值存在,返回true,相当于 if user != null

     看了一下漏了一个日期处理,这里补一下:

    map.put("date", new Date());

    a.ftl中模板写法:

    ${date?string("yyyy-MM-dd HH:mm:ss")}

    输出:

    2018-02-18 16:18:10

    字符串连接
    字符串连接有两种语法:
    1) 使用${..}#{..}在字符串常量内插入表达式的值;
    (2)  直接使用连接运算符“+”连接字符串。
    如,下面两种写法等效:
                  ${"Hello, ${user}"}                                                                                                               
                  ${"Hello, " + user + "!"}                                                                                                        
    有一点需要注意: ${..}只能用于文本部分作为插值输出,而不能用于比较等其他用途,如:
                  <#if ${isBig}>Wow!</#if>                                                                                                               
                  <#if "${isBig}">Wow!</#if>                                                                                                             
    应该写成:
                  <#if isBig>Wow!</#if>   

    截取子串
    截取子串可以根据字符串的索引来进行,如果指定一个索引值,则取得字符串该索引处的字符;如果指定两个索引值,则截取两个索引中间的字符串子串。如:
                  <#assign number="01234">
                  ${number[0]} <#-- 输出字符0 -->
                  ${number[0..3]} <#-- 输出子串“0123” -->

     

     本文为FreeMarker简单的语法使用,servlet以及struts部分见我的下篇博客

    http://www.cnblogs.com/hellxz/p/8453239.html

     

  • 相关阅读:
    DRUPAL-PSA-CORE-2014-005 && CVE-2014-3704 Drupal 7.31 SQL Injection Vulnerability /includes/database/database.inc Analysis
    WDCP(WDlinux Control Panel) mysql/add_user.php、mysql/add_db.php Authentication Loss
    Penetration Testing、Security Testing、Automation Testing
    Tomcat Server Configuration Automation Reinforcement
    Xcon2014 && Geekpwn2014
    phpMyadmin /scripts/setup.php Remote Code Injection && Execution CVE-2009-1151
    Linux System Log Collection、Log Integration、Log Analysis System Building Learning
    The Linux Process Principle,NameSpace, PID、TID、PGID、PPID、SID、TID、TTY
    Windows Management Instrumentation WMI Security Technology Learning
    IIS FTP Server Anonymous Writeable Reinforcement, WEBDAV Anonymous Writeable Reinforcement(undone)
  • 原文地址:https://www.cnblogs.com/hellxz/p/8452880.html
Copyright © 2011-2022 走看看