Freemarker原理解析

FreeMarker生成静态页原理

      FreeMarker适合于作为Web应用的表现层。freemarker大致原理是:将页面中所需要的样式放入FreeMarker文件中,然后将页面所需要的数据动态绑定,并放入Map中,通过调用FreeMarker模板文件解析类process()方法完成静态页面的生成。了解了上面的原理,接下来我就一步 步带您实现FreeMarker生成静态页面。

Freemarker原理解析 - 无殇 - 禅茶一味

一、 创建FreeMarker模板文件user.ftl
User.ftl
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
  <head>
  <meta http-equiv=Content-Type content="text/html; charset=utf-8">
    <title>user.ftl</title>
  </head>
  <body>
    ${user.userName}
    ${user.userPassword}

  </body>
</html>

二、 创建FreeMarker模板文件动态绑定的数据对象类User.java(Sring中pojo)
User.java
//..省略包的导入 
      public class User{
 private String userName;
private String userPassword;
…省略 getter()与setter方法

}

三、 创建FreeMarker模板文件解析器类FreeMarkertUtil
FreeMarkertUtil.java
//省略包的导入
Public class FreeMarkerUtil{
//templatePath模板文件存放路径
//templateName 模板文件名称
//filename 生成的文件名称

public static void  analysisTemplate ( String templatePath,String templateName,String fileName,Map<?,?>root ){
try {
   Configuration config=new Configuration();
  // 设置要解析的模板所在的目录,并加载模板文件
  config.setDirectoryForTemplateLoading(new File(templatePath));
   //设置包装器,并将对象包装为数据模型
   config.setObjectWrapper(new DefaultObjectWrapper());
  //获取模板,并设置编码方式,这个编码必须要与页面中的编码格式一致
 //否则会出现乱码
Template template=config.getTemplate(templateName,“UTF-8”);
   //合并数据模型与模板
   FileOutputStream fos = new FileOutputStream(fileName);
   Writer out = new OutputStreamWriter(fos,“UTF-8”);
       template.process(root, out);
      out.flush();
      out.close();
  } catch (IOException e) {
   e.printStackTrace();
  }catch (TemplateException e) {
   e.printStackTrace();
  }
 }
}

四、 创建FreeMarker生成静态页面测试类ClientTest.java
//..省略包的导入
public class ClientTest{
 public static void main(String[] args){
  User user=new User();
  user.setUserName("张三");
  user.setUserPassword("123");
  Map<String,Object> root=new HashMap<String, Object>();
  root.put("user", user);

  String templatesPath="D:/DevPlateForm/Eclipse/workspaces/freeMakerTest/src/templates";
  String templateFile="/user.ftl";
  String htmlFile=templatesPath+"/user.html";
    FreeMarkertUtil.analysisTemplate(templatesPath,templateFile,htmlFile,root);
}
}
注意: templatesPath为我机器上的FreeMarker模板文件存放路径。如果您要是测试的话,可以将此改为您创建的模板文件存放路径。好了,所有的工作都已经完成了,我们可以运行ClientTest类来测试了。
 本例在您的工程中运行时,必须导入freemarker.jar文件,否则不能编译。
 在我的工程中,您可以找到对应的文件。

五。freemarker变量值的获取

在Struts2框架下,Struts2框架充当了之前的Servlet角色,只要浏览器的请求经过Struts2处理后,Struts2都会自动加载FreeMarker模板,并使用数据模型来填充该模板,再将最后的HTML页面输出给客户端

Struts2解析FreeMarker模板中变量的顺序如下:
 1,FreeMarker模板内建的变量;
 2,ValueStack中的变量;
 3,ActionContext中的变量;
 4,HttpServletRequest中的属性;
 5,HttpSession中的属性;
 6,ServletContext范围的属性.

FreeMarker模板的内建变量有如下几个:
 1,stack:代表ValueStack本身,可通过如下方式来访问其中的变量"${stack.findString('ognl expr')}"
 2,action:代表刚刚执行过的Action实例
 3,response:代表HpptServletResponse实例
 4,res:代表HpptServletResponse实例
 5,request:代表HpptServletRequest实例
 6,req:代表HpptServletRequest实例
 7,session:代表HpptSession实例
 8,application:代表ServletContext实例
 9,base:代表用户请求的上下文路径.

六. 数据模式+模板=输出

      这些例子是在简单的HTML中加入了一些由${…}包围的特定代码,这些特定代码是FreeMarker的指令,而包含 FreeMarker的指令的文件就称为模板(Template)。
     至于user.name和latestProduct.name来自于 数据模型(data model )。数据模型由程序员编程来创建,向模板提供变化的信息,这些信息来自于数据库、文件,甚至于在程序中直接生成。 模板设计者不关心数据从那儿来,只知道使用已经建立的数据模型。

 1、下面是一个可能的数据模型: 
(root)
  |
  +- user = "Big Joe"
  |
  +- latestProduct
      |
      +- url = "products/greenmouse.html"
      |
      +- name = "green mouse"

数据模型类似于计算机的文件系统,latestProduct可以看作是目录。

2、数据模型 
(1)基础 
在快速入门中介绍了在模板中使用的三种基本对象类型:scalars、hashes 和sequences,其实还可以有其它更多的能力: 
scalars:存储单值 
hashes:充当其它对象的容器,每个都关联一个唯一的查询名字 
sequences:充当其它对象的容器,按次序访问 

方法:通过传递的参数进行计算,以新对象返回结果 
用户自定义FTL标记:宏和变换器

通常每个变量只具有上述的一种能力,但一个变量可以具有多个上述能力,如下面的例子: 
(root)
 |
 +- mouse = "Yerri"
     |
     +- age = 12
     |
     +- color = "brown">  
mouse既是scalars又是hashes,将上面的数据模型合并到下面的模板: 
${mouse}       <#-- use mouse as scalar -->
${mouse.age}   <#-- use mouse as hash -->
${mouse.color} <#-- use mouse as hash -->  
输出结果是: 
Yerri
12
brown 

(2)Scalar变量 
Scalar变量存储单值,可以是: 
字符串:简单文本,在模板中使用引号(单引号或双引号)括起 
数字:在模板中直接使用数字值 
日期:存储日期/时间相关的数据,可以是日期、时间或日期-时间(Timestamp);通常情况,日期值由程序员加到数据模型中,设计者只需要显示它们 
布尔值:true或false,通常在<#if …>标记中使用

(3)hashes 、sequences和集合 
有些变量不包含任何可显示的内容,而是作为容器包含其它变量,者有两种类型: 
hashes:具有一个唯一的查询名字和它包含的每个变量相关联 
sequences:使用数字和它包含的每个变量相关联,索引值从0开始 
集合变量通常类似sequences,除非无法访问它的大小和不能使用索引来获得它的子变量;集合可以看作只能由<#list …>指令使用的受限sequences

(4)方法 
方法变量通常是基于给出的参数计算值。 
下面的例子假设程序员已经将方法变量avg放到数据模型中,用来计算数字平均值: 
The average of 3 and 5 is: ${avg(3, 5)}
The average of 6 and 10 and 20 is: ${avg(6, 10, 20)}
The average of the price of python and elephant is: 
    ${avg(animals.python.price, animals.elephant.price)}

(5)宏和变换器 
宏和变换器变量是用户自定义指令(自定义FTL标记),会在后面讲述这些高级特性

(6)节点 
节点变量表示为树型结构中的一个节点,通常在XML处理中使用,会在后面的专门章节中讲

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值