You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@velocity.apache.org by he...@apache.org on 2007/11/14 23:42:43 UTC
svn commit: r595103 - in /velocity/texen/trunk/src/java/org/apache/texen:
Texen.java ant/TexenTask.java
Author: henning
Date: Wed Nov 14 14:42:43 2007
New Revision: 595103
URL: http://svn.apache.org/viewvc?rev=595103&view=rev
Log:
Factor out the actual Texen engine from the Ant task. Use Contributor and Log to tie the engine back into the task.
Added:
velocity/texen/trunk/src/java/org/apache/texen/Texen.java (with props)
Modified:
velocity/texen/trunk/src/java/org/apache/texen/ant/TexenTask.java
Added: velocity/texen/trunk/src/java/org/apache/texen/Texen.java
URL: http://svn.apache.org/viewvc/velocity/texen/trunk/src/java/org/apache/texen/Texen.java?rev=595103&view=auto
==============================================================================
--- velocity/texen/trunk/src/java/org/apache/texen/Texen.java (added)
+++ velocity/texen/trunk/src/java/org/apache/texen/Texen.java Wed Nov 14 14:42:43 2007
@@ -0,0 +1,431 @@
+package org.apache.texen;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import java.io.File;
+import java.io.Writer;
+import java.util.Collection;
+import java.util.Date;
+import java.util.HashSet;
+import java.util.Iterator;
+import java.util.Set;
+
+import org.apache.commons.collections.set.ListOrderedSet;
+import org.apache.commons.lang.StringUtils;
+import org.apache.tools.ant.BuildException;
+import org.apache.velocity.VelocityContext;
+import org.apache.velocity.app.VelocityEngine;
+import org.apache.velocity.context.Context;
+import org.apache.velocity.runtime.RuntimeConstants;
+import org.apache.velocity.runtime.resource.loader.ClasspathResourceLoader;
+
+/**
+ * This is the Texen engine.
+ *
+ * @author <a href="mailto:dev@velocity.apache.org">The Velocity developers community</a>
+ * @version $Id$
+ */
+public class Texen
+ implements TexenContributor
+{
+ private String templatePath = null;
+
+ private boolean useClasspath = false;
+
+ private boolean useResourceLoaderCache = false;
+
+ private int resourceLoaderModificationCheckInterval = 2;
+
+ private String logFile = null;
+
+ private File outputDirectory = null;
+
+ private String inputEncoding = "ISO-8859-1";
+
+ private String outputEncoding = "ISO-8859-1";
+
+ private String outputFileName = null;
+
+ private TexenLog log = null;
+
+ private String controlTemplate = null;
+
+ private Set contributors = ListOrderedSet.decorate(new HashSet());
+
+ private final VelocityEngine ve;
+
+ /**
+ * Returns a new Texen engine.
+ */
+ public Texen()
+ {
+ ve = new VelocityEngine();
+ contributors.add(this);
+ }
+
+ /**
+ * Set the input file encoding.
+ *
+ * @param inputEncoding Input file encoding. Must be a valid code set name.
+ */
+ public void setInputEncoding(final String inputEncoding)
+ {
+ this.inputEncoding = inputEncoding;
+ }
+
+ /**
+ * Set the name of the report logfile.
+ *
+ * @param logFile Name of the report logfile.
+ */
+ public void setLogFile(final String logFile)
+ {
+ this.logFile = logFile;
+ }
+
+ /**
+ * Set the output directory.
+ * @param outputDirectory A File object representing a directory. The directory must exists.
+ */
+ public void setOutputDirectory(final File outputDirectory)
+ {
+ this.outputDirectory = outputDirectory;
+ }
+
+ /**
+ * Set the output file encoding.
+ *
+ * @param outputEncoding Output file encoding. Must be a valid code set name.
+ */
+ public void setOutputEncoding(final String outputEncoding)
+ {
+ this.outputEncoding = outputEncoding;
+ }
+
+ /**
+ * Set the name of the Output File.
+ * @param outputFileName The name of the output file.
+ */
+ public void setOutputFileName(final String outputFileName)
+ {
+ this.outputFileName = outputFileName;
+ }
+
+ /**
+ * Sets the interval in which the resource loader will check for modifications of the source files.
+ *
+ * @param resourceLoaderModificationCheckInterval The interval in seconds.
+ */
+ public void setResourceLoaderModificationCheckInterval(
+ final int resourceLoaderModificationCheckInterval)
+ {
+ this.resourceLoaderModificationCheckInterval = resourceLoaderModificationCheckInterval;
+ }
+
+ /**
+ * Set the path for the templates to be used for rendering.
+ *
+ * @param templatePath The path for the templates to render.
+ */
+ public void setTemplatePath(final String templatePath)
+ {
+ this.templatePath = templatePath;
+ }
+
+ /**
+ * Set this value to true if you want to load templates and properties form
+ * the classpath.
+ *
+ * @param useClasspath True if you want to load templates and property files from the classpath.
+ */
+ public void setUseClasspath(final boolean useClasspath)
+ {
+ this.useClasspath = useClasspath;
+ }
+
+ /**
+ * Set this value to true if you want to cache the loaded templates.
+ *
+ * @param useResourceLoaderCache True if you want to cache the loaded templates.
+ */
+ public void setUseResourceLoaderCache(final boolean useResourceLoaderCache)
+ {
+ this.useResourceLoaderCache = useResourceLoaderCache;
+ }
+
+ protected String getInputEncoding()
+ {
+ return inputEncoding;
+ }
+
+ protected String getLogFile()
+ {
+ return logFile;
+ }
+
+ protected File getOutputDirectory()
+ {
+ return outputDirectory;
+ }
+
+ protected String getOutputEncoding()
+ {
+ return outputEncoding;
+ }
+
+ protected String getOutputFileName()
+ {
+ return outputFileName;
+ }
+
+ protected int getResourceLoaderModificationCheckInterval()
+ {
+ return resourceLoaderModificationCheckInterval;
+ }
+
+ protected String getTemplatePath()
+ {
+ return templatePath;
+ }
+
+ protected boolean isUseClasspath()
+ {
+ return useClasspath;
+ }
+
+ protected boolean isUseResourceLoaderCache()
+ {
+ return useResourceLoaderCache;
+ }
+
+ protected TexenLog getLog()
+ {
+ return log;
+ }
+
+ public void setLog(final TexenLog log)
+ {
+ this.log = log;
+ }
+
+ /**
+ * Sets the name of the control template.
+ *
+ * @param controlTemplate Name of the control template.
+ */
+ public void setControlTemplate(final String controlTemplate)
+ {
+ this.controlTemplate = controlTemplate;
+ }
+
+ public String getControlTemplate()
+ {
+ return controlTemplate;
+ }
+
+ /**
+ * Add all contributors in a given collection.
+ *
+ * @param contributors A collection containing Contributor elements.
+ */
+ public void addContributors(final Collection contributors)
+ {
+ this.contributors.addAll(contributors);
+ }
+
+
+ public Collection getContributors()
+ {
+ return contributors;
+ }
+
+ /**
+ * Initialize the Texen engine. Can be overridden by
+ * subclasses.
+ */
+ protected void init() throws Exception
+ {
+ setVelocityEngineProperties(ve);
+ ve.init();
+ }
+
+ /**
+ * Execute the input script with Velocity
+ *
+ * @throws BuildException
+ * BuildExceptions are thrown when required attributes are missing.
+ * Exceptions thrown by Velocity are rethrown as BuildExceptions.
+ */
+ public void execute()
+ throws Exception
+ {
+ init();
+
+ // Create the text generator.
+ Generator generator = Generator.getInstance();
+ generator.setVelocityEngine(ve);
+ generator.setOutputPath(getOutputDirectory());
+ generator.setInputEncoding(getInputEncoding());
+ generator.setOutputEncoding(getOutputEncoding());
+
+ if (getTemplatePath() != null)
+ {
+ generator.setTemplatePath(getTemplatePath());
+ }
+
+ // Make sure the output directory exists, if it doesn't
+ // then create it.
+ if (!getOutputDirectory().exists())
+ {
+ getOutputDirectory().mkdirs();
+ }
+
+ File path = new File(getOutputDirectory(), getOutputFileName());
+ getLog().info("Generating to file " + path);
+ Writer writer = generator.getWriter(path, getOutputEncoding());
+
+ // The generator and the output path should
+ // be placed in the init context here and
+ // not in the generator class itself.
+ Context c = initContext();
+
+ // Everything in the generator class should be
+ // pulled out and placed in here. What the generator
+ // class does can probably be added to the Velocity
+ // class and the generator class can probably
+ // be removed all together.
+ runPopulateContext(c);
+
+ writer.write(generator.parse(getControlTemplate(), c));
+ writer.flush();
+ writer.close();
+ generator.shutdown();
+
+ runCleanup();
+ }
+
+ protected Context initContext()
+ {
+ return new VelocityContext();
+ }
+
+ /**
+ * <p>Place useful objects into the initial context.</p>
+ *
+ * <p>TexenTask places <code>Date().toString()</code> into the
+ * context as <code>$now</code>. Subclasses who want to vary the
+ * objects in the context should override this method.</p>
+ *
+ * <p><code>$generator</code> is not put into the context in this
+ * method.</p>
+ *
+ * @param context The context to populate, as retrieved from
+ * {@link #initControlContext()}.
+ *
+ * @throws Exception Error while populating context. The {@link
+ * #execute()} method will catch and rethrow as a
+ * <code>BuildException</code>.
+ */
+ protected void runPopulateContext(final Context context)
+ throws Exception
+ {
+ for (Iterator it = contributors.iterator(); it.hasNext(); )
+ {
+ TexenContributor contributor = (TexenContributor) it.next();
+ contributor.populateContext(context);
+ }
+ }
+
+ protected void runCleanup()
+ {
+ for (Iterator it = contributors.iterator(); it.hasNext(); )
+ {
+ TexenContributor contributor = (TexenContributor) it.next();
+ contributor.cleanup();
+ }
+ }
+
+ /**
+ * A hook method called at the end of {@link #execute()} which can
+ * be overridden to perform any necessary cleanup activities (such
+ * as the release of database connections, etc.). By default,
+ * does nothing.
+ *
+ * @exception Exception Problem cleaning up.
+ */
+ public void cleanup()
+ {
+ }
+
+ /**
+ * <p>Place useful objects into the initial context.</p>
+ *
+ * <p>Texen places a Date object into the
+ * context as <code>$now</code>. Subclasses who want to vary the
+ * objects in the context should override this method.</p>
+ *
+ * <p><code>$generator</code> is not put into the context in this
+ * method.</p>
+ *
+ * @param context The context to populate, as retrieved from
+ * {@link #initControlContext()}.
+ *
+ * @throws Exception Error while populating context. The {@link
+ * #execute()} method will catch and rethrow as a
+ * <code>BuildException</code>.
+ */
+ public void populateContext(final Context context)
+ {
+ context.put("now", new Date());
+ }
+
+ /**
+ * Set the properties of the velocity engine.
+ * This may be overridden by a subclass.
+ *
+ * @param ve the velocity engine which properties should be set, not null.
+ *
+ * @throws NullPointerException if ve is null.
+ */
+ protected void setVelocityEngineProperties(VelocityEngine ve)
+ {
+ // Setup the Velocity Runtime.
+ if (StringUtils.isNotEmpty(getTemplatePath()))
+ {
+ ve.setProperty(RuntimeConstants.FILE_RESOURCE_LOADER_PATH, getTemplatePath());
+ }
+
+ if (isUseClasspath())
+ {
+ getLog().info("Using classpath");
+ ve.addProperty(VelocityEngine.RESOURCE_LOADER, "classpath");
+
+ String prefix = "classpath." + VelocityEngine.RESOURCE_LOADER;
+ ve.setProperty(prefix + ".class", ClasspathResourceLoader.class.getName());
+ ve.setProperty(prefix + ".cache", Boolean.valueOf(isUseResourceLoaderCache()));
+ ve.setProperty(prefix + ".modificationCheckInterval", String.valueOf(getResourceLoaderModificationCheckInterval()));
+ }
+
+ if (StringUtils.isNotEmpty(getLogFile()))
+ {
+ ve.setProperty(RuntimeConstants.RUNTIME_LOG, getLogFile());
+ }
+ }
+}
Propchange: velocity/texen/trunk/src/java/org/apache/texen/Texen.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: velocity/texen/trunk/src/java/org/apache/texen/Texen.java
------------------------------------------------------------------------------
svn:keywords = Id Author Date Revision
Modified: velocity/texen/trunk/src/java/org/apache/texen/ant/TexenTask.java
URL: http://svn.apache.org/viewvc/velocity/texen/trunk/src/java/org/apache/texen/ant/TexenTask.java?rev=595103&r1=595102&r2=595103&view=diff
==============================================================================
--- velocity/texen/trunk/src/java/org/apache/texen/ant/TexenTask.java (original)
+++ velocity/texen/trunk/src/java/org/apache/texen/ant/TexenTask.java Wed Nov 14 14:42:43 2007
@@ -16,31 +16,33 @@
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
- * under the License.
+ * under the License.
*/
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
-import java.io.Writer;
-import java.util.Date;
+import java.util.Collections;
import java.util.Iterator;
-import java.util.StringTokenizer;
import org.apache.commons.collections.ExtendedProperties;
+import org.apache.commons.collections.iterators.ArrayIterator;
+import org.apache.commons.lang.ArrayUtils;
+import org.apache.commons.lang.StringUtils;
+import org.apache.texen.Texen;
+import org.apache.texen.TexenContributor;
+import org.apache.texen.TexenFileResolver;
+import org.apache.texen.TexenLog;
+import org.apache.texen.TexenUtils;
import org.apache.tools.ant.BuildException;
import org.apache.tools.ant.Project;
import org.apache.tools.ant.Task;
import org.apache.velocity.VelocityContext;
-import org.apache.velocity.app.VelocityEngine;
import org.apache.velocity.context.Context;
import org.apache.velocity.exception.MethodInvocationException;
import org.apache.velocity.exception.ParseErrorException;
import org.apache.velocity.exception.ResourceNotFoundException;
-import org.apache.velocity.runtime.RuntimeConstants;
-import org.apache.texen.Generator;
-import org.apache.velocity.util.StringUtils;
/**
* An ant task for generating output by using Velocity
@@ -50,18 +52,10 @@
* @version $Id$
*/
public class TexenTask
- extends Task
+ extends Task
+ implements TexenLog, TexenContributor
{
/**
- * This message fragment (telling users to consult the log or
- * invoke ant with the -debug flag) is appended to rethrown
- * exception messages.
- */
- private final static String ERR_MSG_FRAGMENT =
- ". For more information consult the velocity log, or invoke ant " +
- "with the -debug flag.";
-
- /**
* This is the control template that governs the output.
* It may or may not invoke the services of worker
* templates.
@@ -72,13 +66,13 @@
* This is where Velocity will look for templates
* using the file template loader.
*/
- protected String templatePath;
+ protected File [] templatePaths = new File [0];
/**
* This is where texen will place all the output
* that is a product of the generation process.
*/
- protected String outputDirectory;
+ protected File outputDirectory;
/**
* This is the file where the generated text
@@ -89,13 +83,13 @@
/**
* This is the encoding for the output file(s).
*/
- protected String outputEncoding;
+ protected String outputEncoding = "ISO-8859-1";
/**
* This is the encoding for the input file(s)
* (templates).
*/
- protected String inputEncoding;
+ protected String inputEncoding = "ISO-8859-1";
/**
* <p>
@@ -129,29 +123,26 @@
* So initial context values can be set with
* properties file.
*/
- protected ExtendedProperties contextProperties;
+ protected ExtendedProperties contextProperties = new ExtendedProperties();
/**
* Property which controls whether the classpath
* will be used when trying to locate templates.
*/
- protected boolean useClasspath;
+ protected boolean useClasspath = false;
/**
* The LogFile (incl. path) to log to.
*/
- protected String logFile;
+ protected String logFile = null;
/**
* Property which controls whether the resource
* loader will be told to cache. Default false
*/
+ protected boolean useResourceLoaderCache = false;
- protected String useResourceLoaderCache = "false";
- /**
- *
- */
- protected String resourceLoaderModificationCheckInterval = "2";
+ protected int resourceLoaderModificationCheckInterval = 2;
/**
* [REQUIRED] Set the control template for the
@@ -164,41 +155,21 @@
}
/**
- * Get the control template for the
- * generating process.
- * @return The current control template.
- */
- public String getControlTemplate()
- {
- return controlTemplate;
- }
-
- /**
* [REQUIRED] Set the path where Velocity will look
* for templates using the file template
* loader.
* @param templatePath
* @throws Exception
*/
-
public void setTemplatePath(String templatePath) throws Exception
{
- StringBuffer resolvedPath = new StringBuffer();
- StringTokenizer st = new StringTokenizer(templatePath, ",");
- while ( st.hasMoreTokens() )
+ String [] paths = StringUtils.stripAll(StringUtils.split(templatePath, ','));
+ templatePaths = new File [paths.length];
+
+ for (int i = 0 ; i < paths.length; i++)
{
- // resolve relative path from basedir and leave
- // absolute path untouched.
- File fullPath = project.resolveFile(st.nextToken());
- resolvedPath.append(fullPath.getCanonicalPath());
- if ( st.hasMoreTokens() )
- {
- resolvedPath.append(",");
- }
+ templatePaths[i] = new File(paths[i]);
}
- this.templatePath = resolvedPath.toString();
-
- System.out.println(templatePath);
}
/**
@@ -208,34 +179,31 @@
* @return The template path.
*/
public String getTemplatePath()
+ throws IOException
{
- return templatePath;
- }
+ StringBuffer sb = new StringBuffer();
- /**
- * [REQUIRED] Set the output directory. It will be
- * created if it doesn't exist.
- * @param outputDirectory
- */
- public void setOutputDirectory(File outputDirectory)
- {
- try
+ for (Iterator it = new ArrayIterator(templatePaths); it.hasNext(); )
{
- this.outputDirectory = outputDirectory.getCanonicalPath();
- }
- catch (java.io.IOException ioe)
- {
- throw new BuildException(ioe);
+ File path = (File) it.next();
+ sb.append(path.getCanonicalPath());
+ if (it.hasNext())
+ {
+ sb.append(", ");
+ }
}
+
+ return sb.toString();
}
/**
- * Get the output directory.
- * @return The output directory.
+ * [REQUIRED] Set the output directory. It will be
+ * created if it doesn't exist.
+ * @param outputDirectory
*/
- public String getOutputDirectory()
+ public void setOutputDirectory(final File outputDirectory)
{
- return outputDirectory;
+ this.outputDirectory = outputDirectory;
}
/**
@@ -243,7 +211,7 @@
* generation process.
* @param outputFile
*/
- public void setOutputFile(String outputFile)
+ public void setOutputFile(final String outputFile)
{
this.outputFile = outputFile;
}
@@ -252,7 +220,7 @@
* Set the output encoding.
* @param outputEncoding
*/
- public void setOutputEncoding(String outputEncoding)
+ public void setOutputEncoding(final String outputEncoding)
{
this.outputEncoding = outputEncoding;
}
@@ -261,37 +229,18 @@
* Set the input (template) encoding.
* @param inputEncoding
*/
- public void setInputEncoding(String inputEncoding)
+ public void setInputEncoding(final String inputEncoding)
{
this.inputEncoding = inputEncoding;
}
/**
- * Get the output file for the
- * generation process.
- * @return The output file.
- */
- public String getOutputFile()
- {
- return outputFile;
- }
-
- /**
* Sets the log file.
* @param log
*/
- public void setLogFile(String log)
- {
- this.logFile = log;
- }
-
- /**
- * Gets the log file.
- * @return The log file.
- */
- public String getLogFile()
+ public void setLogFile(final String logFile)
{
- return this.logFile;
+ this.logFile = logFile;
}
/**
@@ -300,10 +249,10 @@
* generating process starts.
* @param file
*/
- public void setContextProperties( String file )
+ public void setContextProperties(final String file)
+ throws IOException
{
String[] sources = StringUtils.split(file,",");
- contextProperties = new ExtendedProperties();
// Always try to get the context properties resource
// from a file first. Templates may be taken from a JAR
@@ -314,60 +263,47 @@
for (int i = 0; i < sources.length; i++)
{
ExtendedProperties source = new ExtendedProperties();
+ InputStream inputStream = null;
try
{
// resolve relative path from basedir and leave
// absolute path untouched.
- File fullPath = project.resolveFile(sources[i]);
- log("Using contextProperties file: " + fullPath);
- source.load(new FileInputStream(fullPath));
- }
- catch (IOException e)
- {
- ClassLoader classLoader = this.getClass().getClassLoader();
+ File fullPath = getProject().resolveFile(sources[i]);
- try
+ if (fullPath.exists() && fullPath.isFile())
{
- InputStream inputStream = classLoader.getResourceAsStream(sources[i]);
-
- if (inputStream == null)
- {
- throw new BuildException("Context properties file " + sources[i] +
- " could not be found in the file system or on the classpath!");
- }
- else
- {
- source.load(inputStream);
- }
+ log("Using contextProperties file: " + fullPath);
+ inputStream = new FileInputStream(fullPath);
}
- catch (IOException ioe)
+ else
{
- source = null;
+ ClassLoader classLoader = this.getClass().getClassLoader();
+ inputStream = classLoader.getResourceAsStream(sources[i]);
+ }
+
+ if (inputStream == null)
+ {
+ throw new BuildException("Context properties file " + sources[i] + " could not be found in the file system or on the classpath!");
}
- }
- if (source != null)
+ source.load(inputStream);
+ }
+ finally
{
- for (Iterator j = source.getKeys(); j.hasNext(); )
+ if (inputStream != null)
{
- String name = (String) j.next();
- String value = StringUtils.nullTrim(source.getString(name));
- contextProperties.setProperty(name,value);
+ inputStream.close();
}
}
- }
- }
- /**
- * Get the context properties that will be
- * fed into the initial context be the
- * generating process starts.
- * @return The current context properties.
- */
- public ExtendedProperties getContextProperties()
- {
- return contextProperties;
+ for (Iterator it = source.getKeys(); it.hasNext(); )
+ {
+ String name = (String) it.next();
+ String value = StringUtils.trim(source.getString(name));
+ contextProperties.setProperty(name, value);
+ }
+ }
}
/**
@@ -375,7 +311,7 @@
*
* @param useClasspath true means the classpath will be used.
*/
- public void setUseClasspath(boolean useClasspath)
+ public void setUseClasspath(final boolean useClasspath)
{
this.useClasspath = useClasspath;
}
@@ -383,7 +319,7 @@
/**
* @param useResourceLoaderCache
*/
- public void setUseResourceLoaderCache(String useResourceLoaderCache)
+ public void setUseResourceLoaderCache(final boolean useResourceLoaderCache)
{
this.useResourceLoaderCache = useResourceLoaderCache;
}
@@ -391,10 +327,12 @@
/**
* @param resourceLoaderModificationCheckInterval
*/
- public void setResourceLoaderModificationCheckInterval(String resourceLoaderModificationCheckInterval)
+ public void setResourceLoaderModificationCheckInterval(final int resourceLoaderModificationCheckInterval)
{
this.resourceLoaderModificationCheckInterval = resourceLoaderModificationCheckInterval;
}
+
+
/**
* Creates a VelocityContext.
*
@@ -408,6 +346,16 @@
return new VelocityContext();
}
+ public void info(final String message)
+ {
+ log(message, Project.MSG_INFO);
+ }
+
+ public void error(final String message)
+ {
+ log(message, Project.MSG_ERR);
+ }
+
/**
* Execute the input script with Velocity
*
@@ -415,11 +363,11 @@
* BuildExceptions are thrown when required attributes are missing.
* Exceptions thrown by Velocity are rethrown as BuildExceptions.
*/
- public void execute ()
+ public void execute()
throws BuildException
{
// Make sure the template path is set.
- if (templatePath == null && useClasspath == false)
+ if (ArrayUtils.isEmpty(templatePaths) && useClasspath == false)
{
throw new BuildException(
"The template path needs to be defined if you are not using " +
@@ -444,230 +392,75 @@
throw new BuildException("The output file needs to be defined!");
}
- VelocityEngine ve = new VelocityEngine();
-
try
{
- setVelocityEngineProperties(ve);
- ve.init();
-
- // Create the text generator.
- Generator generator = createGenerator();
- generator.setVelocityEngine(ve);
- generator.setOutputPath(outputDirectory);
- generator.setInputEncoding(inputEncoding);
- generator.setOutputEncoding(outputEncoding);
-
- if (templatePath != null)
- {
- generator.setTemplatePath(templatePath);
- }
-
- // Make sure the output directory exists, if it doesn't
- // then create it.
- File file = new File(outputDirectory);
- if (! file.exists())
- {
- file.mkdirs();
- }
-
- String path = outputDirectory + File.separator + outputFile;
- log("Generating to file " + path, Project.MSG_INFO);
- Writer writer = generator.getWriter(path, outputEncoding);
-
- // The generator and the output path should
- // be placed in the init context here and
- // not in the generator class itself.
- Context c = initControlContext();
-
- // Everything in the generator class should be
- // pulled out and placed in here. What the generator
- // class does can probably be added to the Velocity
- // class and the generator class can probably
- // be removed all together.
- populateInitialContext(c);
-
- // Feed all the options into the initial
- // control context so they are available
- // in the control/worker templates.
- if (contextProperties != null)
- {
- Iterator i = contextProperties.getKeys();
-
- while (i.hasNext())
- {
- String property = (String) i.next();
- String value = StringUtils.nullTrim(contextProperties.getString(property));
-
- // Now lets quickly check to see if what
- // we have is numeric and try to put it
- // into the context as an Integer.
- try
- {
- c.put(property, new Integer(value));
- }
- catch (NumberFormatException nfe)
- {
- // Now we will try to place the value into
- // the context as a boolean value if it
- // maps to a valid boolean value.
- String booleanString =
- contextProperties.testBoolean(value);
-
- if (booleanString != null)
- {
- c.put(property, Boolean.valueOf(booleanString));
- }
- else
- {
- // We are going to do something special
- // for properties that have a ".file.contents"
- // suffix: for these properties will pull
- // in the contents of the file and make
- // them available in the context. So for
- // a line like the following in a properties file:
- //
- // license.file.contents = license.txt
- //
- // We will pull in the contents of license.txt
- // and make it available in the context as
- // $license. This should make texen a little
- // more flexible.
- final String FILE_CONTENTS = ".file.contents";
- if (property.endsWith(FILE_CONTENTS))
- {
- // We need to turn the license file from relative to
- // absolute, and let Ant help :)
- value = StringUtils.fileContentsToString(
- project.resolveFile(value).getCanonicalPath());
-
- property = property.substring(
- 0, property.indexOf(FILE_CONTENTS));
- }
-
- c.put(property, value);
- }
- }
- }
- }
+ Texen texen = new Texen();
+ texen.setInputEncoding(inputEncoding);
+ texen.setLogFile(logFile);
+ texen.setOutputDirectory(outputDirectory);
+ texen.setOutputEncoding(outputEncoding);
+ texen.setOutputFileName(outputFile);
+ texen.setResourceLoaderModificationCheckInterval(resourceLoaderModificationCheckInterval);
+ texen.setTemplatePath(getTemplatePath());
+ texen.setUseClasspath(useClasspath);
+ texen.setUseResourceLoaderCache(useResourceLoaderCache);
+ texen.setLog(this);
+ texen.setControlTemplate(controlTemplate);
+ texen.addContributors(Collections.singleton(this));
- writer.write(generator.parse(controlTemplate, c));
- writer.flush();
- writer.close();
- generator.shutdown();
- cleanup();
+ texen.execute();
}
- catch( BuildException e)
- {
- throw e;
- }
- catch( MethodInvocationException e )
+ catch(MethodInvocationException e)
{
throw new BuildException(
- "Exception thrown by '" + e.getReferenceName() + "." +
- e.getMethodName() +"'" + ERR_MSG_FRAGMENT,
- e.getWrappedThrowable());
- }
- catch( ParseErrorException e )
- {
- throw new BuildException("Velocity syntax error" + ERR_MSG_FRAGMENT ,e);
- }
- catch( ResourceNotFoundException e )
- {
- throw new BuildException("Resource not found" + ERR_MSG_FRAGMENT,e);
- }
- catch( Exception e )
- {
- throw new BuildException("Generation failed" + ERR_MSG_FRAGMENT ,e);
- }
- }
-
- /**
- * Retrieve a new instance of the generator. This may be overridden by a subclass.
- * @return
- */
- protected Generator createGenerator()
- {
- return Generator.getInstance();
- }
-
- /**
- * Set the properties of the velocity engine.
- * This may be overridden by a subclass.
- *
- * @param ve the velocity engine which properties should be set, not null.
- *
- * @throws NullPointerException if ve is null.
- */
- protected void setVelocityEngineProperties(VelocityEngine ve)
- {
- // Setup the Velocity Runtime.
- if (templatePath != null)
- {
- log("Using templatePath: " + templatePath, Project.MSG_VERBOSE);
- ve.setProperty(
- RuntimeConstants.FILE_RESOURCE_LOADER_PATH, templatePath);
- }
-
- if (useClasspath)
- {
- log("Using classpath");
- ve.addProperty(
- VelocityEngine.RESOURCE_LOADER, "classpath");
-
- ve.setProperty(
- "classpath." + VelocityEngine.RESOURCE_LOADER + ".class",
- "org.apache.velocity.runtime.resource.loader.ClasspathResourceLoader");
-
- ve.setProperty(
- "classpath." + VelocityEngine.RESOURCE_LOADER +
- ".cache", useResourceLoaderCache);
-
- ve.setProperty(
- "classpath." + VelocityEngine.RESOURCE_LOADER +
- ".modificationCheckInterval", resourceLoaderModificationCheckInterval);
- }
-
- if (this.logFile != null)
- {
- ve.setProperty(RuntimeConstants.RUNTIME_LOG, this.logFile);
- }
+ "Exception thrown by '" + e.getReferenceName() + "." + e.getMethodName()
+ + "'. For more information consult the velocity log, or invoke ant with the -debug flag.",
+ e.getWrappedThrowable());
+ }
+ catch(ParseErrorException e)
+ {
+ throw new BuildException("Velocity syntax error. For more information consult the velocity log, or invoke ant with the -debug flag.", e);
+ }
+ catch(ResourceNotFoundException e)
+ {
+ throw new BuildException("Resource not found. For more information consult the velocity log, or invoke ant with the -debug flag.", e);
+ }
+ catch (RuntimeException re)
+ {
+ throw re;
+ }
+ catch(Exception e)
+ {
+ throw new BuildException("Generation failed. For more information consult the velocity log, or invoke ant with the -debug flag.", e);
+ }
}
-
/**
- * <p>Place useful objects into the initial context.</p>
- *
- * <p>TexenTask places <code>Date().toString()</code> into the
- * context as <code>$now</code>. Subclasses who want to vary the
- * objects in the context should override this method.</p>
- *
- * <p><code>$generator</code> is not put into the context in this
- * method.</p>
- *
- * @param context The context to populate, as retrieved from
- * {@link #initControlContext()}.
+ * A hook method called at the end of {@link #execute()} which can
+ * be overridden to perform any necessary cleanup activities (such
+ * as the release of database connections, etc.). By default,
+ * does nothing.
*
- * @throws Exception Error while populating context. The {@link
- * #execute()} method will catch and rethrow as a
- * <code>BuildException</code>.
+ * @exception Exception Problem cleaning up.
*/
- protected void populateInitialContext(Context context)
- throws Exception
+ public void cleanup()
{
- context.put("now", new Date().toString());
}
/**
- * A hook method called at the end of {@link #execute()} which can
- * be overridden to perform any necessary cleanup activities (such
- * as the release of database connections, etc.). By default,
- * does nothing.
+ * Populate the context with the parameters from the Ant task.
*
- * @exception Exception Problem cleaning up.
+ * @see TexenContributor
*/
- protected void cleanup()
- throws Exception
+ public void populateContext(final Context context) throws Exception
{
+ TexenUtils.populateContext(contextProperties, context, new TexenFileResolver()
+ {
+
+ public File resolveFile(String value)
+ {
+ return getProject().resolveFile(value);
+ }
+ });
}
}