velocity就是由template,engine,context组成。

1、首先创建一个template(如果是用在web上就是一个html文件),将需要参数化或实例化的地方用跟context有关的符号标记出来,标记时用velocity template language。而template应该可以是任意的文本。

2、给context设定一些值,这些值用来替换在template中被标记的地方。

3、利用engine将template中需要替换的地方用context中的值替换掉,也就是所谓的merge,从而得到该模板的实例。

Velocity的初始化有多种方式:

1、init()

2、init(Properties p)

3、init(String propertiesName)

第一种init()方式是最简单的方式,当我们的程序没有配置类似velocity.properties这样的文件的时候,就会使用默认的配置文件来初始化,

默认的配置文件的位置在org/apache/velocity/runtime/defaults/velocity.properties

应用在WEB的时候,默认的配置文件使用的是org/apache/velocity/tools/view/servlet/velocity.properties

在初始化前,velocity会把配置文件的属性和值读取后保存在内存中,初始化时,velocity将会初始化以下几个方面:

  1. Logging System 日志系统
  2. ResourceManager 资源加载器
  3. EventHandler 事件句柄
  4. Parser Pool 解析池
  5. Global Cache 全局缓存
  6. Velocimacro System 宏

Logging System

velocity会根据配置文件里的信息,查找一个名叫runtime.log.logsystem的属性,一旦配置文件中有配置这个属性,则会开始去创建日志系统。当velocity没有配置runtime.log.logsystem这个属性的时候,则会继续寻找runtime.log.logsystem.class这个属性,默认的velocity.properties配置文件中,这个属性的值按顺序依次为

  1. AvalonLogChute
  2. Log4JLogChute
  3. CommonsLogLogChute
  4. ServletLogChute
  5. JdkLogChute

当然,velocity不会使用那么多个日志系统,只会使用第一个能实例化的日志系统。如果之前的创建工作都失败的话,那么意味着用户没有设置值或者是没有找到类,velocity将会使用系统统默认的SystemLogChute来输出日志,这个日志系统使用System.err方式输出日志。一旦使用runtime.log.logsystem或者runtime.log.logsystem.class属性创建日志系统成功后,velocity就会把HoldingLogChute替换成新的日志系统。这样,日志的初始化才真正的结束。

ResourceManager 

资源加载器是velocity加载资源使用的一个工具。Velocity的配置文件里有个属性叫Resource.manager.class,默认的class是org.apache.velocity.runtime.resource.ResourceManagerImpl。Velocity会尝试初始化ResourceManagerImpl,其中会查找resource.loader这个属性,resource.loader这个属性是可以有多个的,每个Loader都会生效。

ResourceLoader一共有7种:

  1. ClasspathResourceLoader
  2. DataSourceResourceLoader
  3. FileResourceLoader
  4. JarResourceLoader
  5. StringResourceLoader
  6. URLResourceLoader
  7. WebappLoader

默认的是第3个FileResourceLoader。除了第7个webappLoader是velocity-tools包作为velocity的附属工具后来添加的,其余6个都velocity包自带的,如果觉得这些都不适用,你也可以自己实现一个。实现一个资源加载器只要继承ResourceLoader,实现它的几个方法就可以了。所谓的资源加载器指的就是velocity读取文件的方法,有直接从文件读取的,有从jar包中读取的,也有从类路径中读取的,基本上只要自己重写getResourceStream方法就可以。在初始化的过程中,会读取resource.manager.logwhenfound和resource.manager.cache.class这两个属性,同时,也会进行资源缓存的初始化操作。

EventHandler

用户可以自定义响应的事件,Velocity提供了对模板解析过程事件的处理,用户可以响应模板产生的事件。

org.apache.velocity.app.event.EventHandler,是一个最简单的接口。我们可以通过实现这个接口来处理页面上不同的信息。

1)、IncludeEventHandler

在使用#include(),#parse()语法的时候,允许开发修改include或者parse文件的路径(一般用于资源找不到的情况)。

IncludeEventHandler有两个实现类,分别是IncludeNotFound和IncludeRelativePath。

当找不到#include指令的文件时,IncludeNotFound类会去做一些处理,例如去增加一个eventhandler.include.notfound=notfound.vm的配置,当然,如果不存在notfound.vm,也会给出"Can't find include not found page"的提示。

2)、InvalidReferenceEventHandler

当渲染页面的时候,一旦遇到非法的reference,就会触发此事件。开发者可以侦听此事件,用于错误的报告,或者修改返回的内容。

ReportInvalidReferences是它的一个实现类,用于报告无效的refenrences。如果在velocity的配置文件中使用了eventhandler.invalidreference.exception=true配置,在运行过程中碰到第一个无效的refenrences就会抛出ParseErrorRuntimeException异常,执行暂停。如果配置为false的话,则会将错误先收在InvalidReferenceInfo列表对象中,运行照旧。

3)、MethodExceptionEventHandler

渲染模板,一旦发现调用的方法抛出异常的时候,就会触发此事件。允许开发者处理这个异常,输出友好信息或者抛出异常。必须返回一个值用于模板的渲染。

4)、NullSetEventHandler

当使用#set()语法,设置一个null值的时候,会触发此事件。目前Velocity官方没有提供默认实现。

5)、ReferenceInsertionEventHandler

当渲染变量(reference)的时候,就会触发此事件。允许开发者返回更加友好的值--一般用于内容的escape,比如HtmlEscape等。

Parser Pool

Velocity会使用类似线程池的机制来解析页面。配置的key为parser.pool.class和parser.pool.size。默认的实现类为org.apache.velocity.util.SimplePoolVelocity。

velocity启动时需要创建模板解析器的个数. 默认为20个,对一般用户来说足够了. 即使这个值小了,Velocity也会运行时根据系统需要动态增加(但增加的不会装入解析池中). 新增时会在日志中输出信息。

Global Cache 全局缓存

开启全局缓存配置项  file.resource.loader.cache=true file.resource.loader.modificationCheckInterval=-1

Template t = getTemplate(stack, velocityManager.getVelocityEngine(), invocation, finalLocation, encoding);  

VelocityResult.java :
protected Template getTemplate(ValueStack stack, VelocityEngine velocity, ActionInvocation invocation, String location, String encoding) throws Exception {
if (!location.startsWith("/")) {
location = invocation.getProxy().getNamespace() + "/" + location;
} Template template = velocity.getTemplate(location, encoding); return template;
} VelocityEngine.java
public Template getTemplate(String name, String encoding)
throws ResourceNotFoundException, ParseErrorException, Exception
{
return ri.getTemplate( name, encoding );
} RuntimeInstance.java
public Template getTemplate(String name, String encoding)
throws ResourceNotFoundException, ParseErrorException, Exception
{
requireInitialization(); return (Template)
resourceManager.getResource(name,
ResourceManager.RESOURCE_TEMPLATE, encoding);
} ResourceManagerImpl.java
public Resource getResource(final String resourceName, final int resourceType, final String encoding)
throws ResourceNotFoundException,
ParseErrorException,
Exception
{
String resourceKey = resourceType + resourceName;
Resource resource = globalCache.get(resourceKey); ResourceCacheImpl.java
public Resource get( Object key )
{
return (Resource) cache.get( key );
}

Velocimacro(宏配置)

当Velocity engine运行时,会载入一个全局的宏文件。所有模板都可访问该宏文件(Velocimacros). 这个文件位置在相对于资源文件的根目录下。velocity默认的配置项为velocimacro.library=VM_global_library.vm。此外,还有一些其他配置来处理宏的不同使用情况,例如:

velocimacro.permissions.allow.inline=true定义在模板中是否可用#macro()指令定义一个新的宏。默认为true,表示所有的vm都可以新建宏,但是要注意可能会把全局的宏配置给替换掉。

velocimacro.permissions.allow.inline.to.replace.global=false控制用户定义的宏是否可以可以替换Velocity的全局宏。

velocimacro.library.autoreload=false控制宏是否自动载入。当值为true时宏将根据是否修改而决定是否需要重新加载,这个特性可在调试时很方便,不需重启你的服务器。

Velocity初始化过程解析的更多相关文章

  1. 解析Java类和对象的初始化过程

    类的初始化和对象初始化是 JVM 管理的类型生命周期中非常重要的两个环节,Google 了一遍网络,有关类装载机制的文章倒是不少,然而类初始化和对象初始化的文章并不多,特别是从字节码和 JVM 层次来 ...

  2. [转载]解析 Java 类和对象的初始化过程

    原文地址:http://www.ibm.com/developerworks/cn/java/j-lo-clobj-init/index.html 由一个单态模式引出的问题谈起 类的初始化和对象初始化 ...

  3. Velocity工作原理解析和优化

    在MVC开发模式下,View离不开模板引擎,在Java语言中模板引擎使用得最多是JSP.Velocity和FreeMarker,在MVC编程开发模式中,必不可少的一个部分是V的部分.V负责前端的页面展 ...

  4. 【初探Spring】------Spring IOC(三):初始化过程---Resource定位

    我们知道Spring的IoC起到了一个容器的作用,其中装得都是各种各样的Bean.同时在我们刚刚开始学习Spring的时候都是通过xml文件来定义Bean,Spring会某种方式加载这些xml文件,然 ...

  5. 【初探Spring】------Spring IOC(二):初始化过程---简介

    首先我们先来看看如下一段代码 ClassPathResource resource = new ClassPathResource("bean.xml"); DefaultList ...

  6. Spring IoC容器的初始化过程

    Spring IoC容器的初始化包括 BeanDefinition的Resource定位.载入和注册 这三个基本的过程.IoC容器的初始化过程不包含Bean依赖注入的实现.Bean依赖的注入一般会发生 ...

  7. Spring IoC容器初始化过程学习

    IoC容器是什么?IoC文英全称Inversion of Control,即控制反转,我么可以这么理解IoC容器: 把某些业务对象的的控制权交给一个平台或者框架来同一管理,这个同一管理的平台可以称为I ...

  8. IoC容器的初始化过程

    1.简单来说,IoC容器的初始化是由前面介绍的refresh()方法来启动的,这个方法标志着IoC容器的正式启动. 2.具体来说,这个启动包括BeanDefinition的Resource定位.载入和 ...

  9. Spring之IOC容器初始化过程

    Ioc容器的初始化是由refresh()方法来启动的,这个方法标志着Ioc容器的正式启动. 具体来说这个启动过程包括三个基本过程: 1.BeanDifinition的Resource定位 2.Bean ...

随机推荐

  1. wp8.1 sqlite Error - Deployment optimization failed due to an assembly that's not valid.

    这里我们使用的sqlite的版本为3.8.5,vs2013在发布的时候出现 Error - Deployment optimization failed due to an assembly that ...

  2. shell脚本参数中有空格

    shell脚本参数中有空格 在shell脚本中如果有空格的处理如下: sh test.sh "hello word" echo $1 得到的是hello,而不是hello word ...

  3. 使用 pdf.js 查看发票时,显示不了台头和印章的解决办法

    系统中使用了 pdf.js 来查看 PDF 文件,发现在查看 电子发票时, 缺失了很多信息, 刚开始以为是 PDF.JS 的 BUG, 后来调试发现只需要在 IIS 里添加一个 bcmap 后缀的 m ...

  4. 解决IIS中Login failed for user 'NT AUTHORITY\ANONYMOUS LOGON'.

  5. 201621123023《Java程序设计》第10周学习总结

    一.本周学习总结 1.1 以你喜欢的方式(思维导图或其他)归纳总结集合与泛型相关内容. 二.书面作业 本次PTA作业题集异常 1. 常用异常 结合题集题目7-1回答 1.1 自己以前编写的代码中经常出 ...

  6. GO学习笔记 - 包内首字母大写的名称是被导出的,才能被其它包代码调用!

    在GO语言的任意包内,如果名称的首字母是大写的,意味着这个名称被导出,在其它包中可以使用“包名.名称”方式来调用,如果名称首字母不是大写,那么只能在这个包内部使用!这个概念还真是和以往接触的编程语言的 ...

  7. ElasticSearch学习笔记(三)logstash安装和logstash-input-jdbc插件

    ElasticSearch的索引可以手动添加索引的,就是类似下面这样添加的 PUT /movies/movie/1 { "title": "The Godfather&q ...

  8. SpringBoot idea maven打包war及运行war包

    pom.xml修改打包类型pom改为war <artifactId>Test02</artifactId> <packaging>war</packaging ...

  9. Working with Metal—Overview

    看完这个 WWDC 之后的总结. Metal 可以在单位时间内提供 10 倍的 draw call 调用. Background About Draw Call 每一次 draw call 调用都必须 ...

  10. 使用TortoiseSVN客户端管理IntelliJ IDEA项目的方法

    使用TortoiseSVN客户端管理IntelliJ IDEA项目的方法 今天在打开一个使用SVN管理的项目时,IntelliJ IDEA提示: Can't use Subversion comman ...