001: /*
002: * Copyright 2002-2005 the original author or authors.
003: *
004: * Licensed under the Apache License, Version 2.0 (the "License");
005: * you may not use this file except in compliance with the License.
006: * You may obtain a copy of the License at
007: *
008: * http://www.apache.org/licenses/LICENSE-2.0
009: *
010: * Unless required by applicable law or agreed to in writing, software
011: * distributed under the License is distributed on an "AS IS" BASIS,
012: * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013: * See the License for the specific language governing permissions and
014: * limitations under the License.
015: */
016:
017: package org.springframework.web.servlet.view.velocity;
018:
019: import java.io.IOException;
020:
021: import org.apache.velocity.app.VelocityEngine;
022: import org.apache.velocity.exception.VelocityException;
023: import org.apache.velocity.runtime.resource.loader.ClasspathResourceLoader;
024:
025: import org.springframework.beans.factory.InitializingBean;
026: import org.springframework.context.ResourceLoaderAware;
027: import org.springframework.ui.velocity.VelocityEngineFactory;
028:
029: /**
030: * JavaBean to configure Velocity for web usage, via the "configLocation"
031: * and/or "velocityProperties" and/or "resourceLoaderPath" bean properties.
032: * The simplest way to use this class is to specify just a "resourceLoaderPath";
033: * you do not need any further configuration then.
034: *
035: * <pre>
036: * <bean id="velocityConfig" class="org.springframework.web.servlet.view.velocity.VelocityConfigurer">
037: * <property name="resourceLoaderPath"><value>/WEB-INF/velocity/</value></property>
038: * </bean></pre>
039: *
040: * This bean must be included in the application context of any application
041: * using Spring's VelocityView for web MVC. It exists purely to configure Velocity;
042: * it is not meant to be referenced by application components but just internally
043: * by VelocityView. Implements VelocityConfig to be found by VelocityView without
044: * depending on the bean name of the configurer. Each DispatcherServlet can define
045: * its own VelocityConfigurer if desired.
046: *
047: * <p>Note that you can also refer to a preconfigured VelocityEngine instance, for
048: * example one set up by VelocityEngineFactoryBean, via the "velocityEngine" property.
049: * This allows to share a VelocityEngine for web and email usage, for example.
050: *
051: * <p>This configurer registers the "spring.vm" Velocimacro library for web views
052: * (contained in this package and thus in spring.jar), which makes all macros
053: * defined in it implicitly available:
054: *
055: * <pre>
056: * #springBind("person.age")
057: * age is ${status.value}</pre>
058: *
059: * @author Rod Johnson
060: * @author Juergen Hoeller
061: * @author Darren Davison
062: * @see #setConfigLocation
063: * @see #setVelocityProperties
064: * @see #setResourceLoaderPath
065: * @see #setVelocityEngine
066: * @see org.springframework.ui.velocity.VelocityEngineFactoryBean
067: * @see VelocityView
068: */
069: public class VelocityConfigurer extends VelocityEngineFactory implements
070: VelocityConfig, InitializingBean, ResourceLoaderAware {
071:
072: /** the name of the resource loader for Spring's bind macros */
073: private static final String SPRING_MACRO_RESOURCE_LOADER_NAME = "springMacro";
074:
075: /** the key for the class of Spring's bind macro resource loader */
076: private static final String SPRING_MACRO_RESOURCE_LOADER_CLASS = "springMacro.resource.loader.class";
077:
078: /** the name of Spring's default bind macro library */
079: private static final String SPRING_MACRO_LIBRARY = "org/springframework/web/servlet/view/velocity/spring.vm";
080:
081: private VelocityEngine velocityEngine;
082:
083: /**
084: * Set a preconfigured VelocityEngine to use for the Velocity web config, e.g.
085: * a shared one for web and email usage, set up via VelocityEngineFactoryBean.
086: * If this is not set, VelocityEngineFactory's properties (inherited by this
087: * class) have to be specified.
088: * @see org.springframework.ui.velocity.VelocityEngineFactoryBean
089: */
090: public void setVelocityEngine(VelocityEngine velocityEngine) {
091: this .velocityEngine = velocityEngine;
092: }
093:
094: /**
095: * Initialize VelocityEngineFactory's VelocityEngine
096: * if not overridden by a preconfigured VelocityEngine.
097: * @see #createVelocityEngine
098: * @see #setVelocityEngine
099: */
100: public void afterPropertiesSet() throws IOException,
101: VelocityException {
102: if (this .velocityEngine == null) {
103: this .velocityEngine = createVelocityEngine();
104: }
105: }
106:
107: /**
108: * Provides a ClasspathResourceLoader in addition to any default or user-defined
109: * loader in order to load the spring Velocity macros from the class path.
110: * @see org.apache.velocity.runtime.resource.loader.ClasspathResourceLoader
111: */
112: protected void postProcessVelocityEngine(
113: VelocityEngine velocityEngine) {
114: velocityEngine.setProperty(SPRING_MACRO_RESOURCE_LOADER_CLASS,
115: ClasspathResourceLoader.class.getName());
116: velocityEngine.addProperty(VelocityEngine.RESOURCE_LOADER,
117: SPRING_MACRO_RESOURCE_LOADER_NAME);
118: velocityEngine.addProperty(VelocityEngine.VM_LIBRARY,
119: SPRING_MACRO_LIBRARY);
120: if (logger.isInfoEnabled()) {
121: logger.info("ClasspathResourceLoader with name '"
122: + SPRING_MACRO_RESOURCE_LOADER_NAME
123: + "' added to configured VelocityEngine");
124: }
125: }
126:
127: public VelocityEngine getVelocityEngine() {
128: return this.velocityEngine;
129: }
130:
131: }
|