001: /**********************************************************************************
002: * $URL: https://source.sakaiproject.org/svn/velocity/tags/sakai_2-4-1/tool/src/java/org/sakaiproject/vm/VelocityServlet.java $
003: * $Id: VelocityServlet.java 7247 2006-03-29 21:09:51Z ggolden@umich.edu $
004: ***********************************************************************************
005: *
006: * Copyright (c) 2003, 2004, 2005, 2006 The Sakai Foundation.
007: *
008: * Licensed under the Educational Community License, Version 1.0 (the "License");
009: * you may not use this file except in compliance with the License.
010: * You may obtain a copy of the License at
011: *
012: * http://www.opensource.org/licenses/ecl1.php
013: *
014: * Unless required by applicable law or agreed to in writing, software
015: * distributed under the License is distributed on an "AS IS" BASIS,
016: * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
017: * See the License for the specific language governing permissions and
018: * limitations under the License.
019: *
020: **********************************************************************************/package org.sakaiproject.vm;
021:
022: import java.io.FileNotFoundException;
023: import java.io.IOException;
024: import java.util.Enumeration;
025: import java.util.Properties;
026:
027: import javax.servlet.ServletConfig;
028: import javax.servlet.http.HttpServletRequest;
029: import javax.servlet.http.HttpServletResponse;
030:
031: import org.apache.velocity.Template;
032: import org.apache.velocity.app.Velocity;
033: import org.apache.velocity.context.Context;
034: import org.apache.velocity.exception.ParseErrorException;
035: import org.apache.velocity.exception.ResourceNotFoundException;
036:
037: /**
038: * <p>
039: * Responds with the expansion of a Velocity Template. The template and context references are specified in the request.
040: * </p>
041: */
042: public class VelocityServlet extends
043: org.apache.velocity.servlet.VelocityServlet {
044:
045: /**
046: * Called by the VelocityServlet init(). We want to set a set of properties so that templates will be found in the webapp root. This makes this easier to work with as an example, so a new user doesn't have to worry about config issues when first
047: * figuring things out
048: */
049: protected Properties loadConfiguration(ServletConfig config)
050: throws IOException, FileNotFoundException {
051: // load the properties as configured in the servlet init params
052: Properties p = super .loadConfiguration(config);
053:
054: /*
055: * first, we set the template path for the FileResourceLoader to the root of the webapp. This probably won't work under in a WAR under WebLogic, but should under tomcat :)
056: */
057:
058: String path = config.getServletContext().getRealPath("/");
059:
060: if (path == null) {
061: System.out
062: .println(" SampleServlet.loadConfiguration() : unable to "
063: + "get the current webapp root. Using '/'. Please fix.");
064:
065: path = "/";
066: }
067:
068: p.setProperty(Velocity.FILE_RESOURCE_LOADER_PATH, path);
069:
070: /**
071: * and the same for the log file
072: */
073:
074: p.setProperty("runtime.log", path
075: + p.getProperty("runtime.log"));
076:
077: return p;
078: }
079:
080: /**
081: * <p>
082: * main routine to handle a request. Called by VelocityServlet, your responsibility as programmer is to simply return a valid Template
083: * </p>
084: *
085: * @param ctx
086: * a Velocity Context object to be filled with data. Will be used for rendering this template
087: * @return Template to be used for request
088: */
089: public Template handleRequest(HttpServletRequest request,
090: HttpServletResponse response, Context ctx) {
091: // Note: Velocity doesn't like dots in the context names, so we change them to '_'
092:
093: // load the context with attributes
094: Enumeration e = request.getAttributeNames();
095: while (e.hasMoreElements()) {
096: String name = (String) e.nextElement();
097: String vName = escapeVmName(name);
098: Object value = request.getAttribute(name);
099:
100: ctx.put(vName, value);
101: // log("--> context (attribute): " + vName + " = " + value);
102: }
103:
104: // if the javax.servlet.include.servlet_path attribute exists, use this value as the template
105: String templatePath = (String) request
106: .getAttribute("javax.servlet.include.servlet_path");
107:
108: // if not there, try our special include
109: if (templatePath == null) {
110: templatePath = (String) request
111: .getAttribute("sakai.vm.path");
112: }
113:
114: // if not there, use the servletpath
115: if (templatePath == null) {
116: templatePath = request.getServletPath();
117: }
118:
119: Template template = null;
120: try {
121: // log("--> template path: " + templatePath);
122: template = getTemplate(templatePath);
123: } catch (ParseErrorException ex) {
124: log("Exception reading vm template: " + templatePath + " "
125: + ex);
126: } catch (ResourceNotFoundException ex) {
127: log("Exception reading vm template: " + templatePath + " "
128: + ex);
129: } catch (Exception ex) {
130: log("Exception reading vm template: " + templatePath + " "
131: + ex);
132: }
133:
134: return template;
135:
136: } // handleRequest
137:
138: /**
139: * Change any characters that Velocity doesn't like in the name to '_' to make a valid Velocity name
140: *
141: * @param name
142: * The name to convert.
143: * @return The name converted to a valid Velocity name.
144: */
145: protected String escapeVmName(String name) {
146: char[] chars = name.toCharArray();
147:
148: // make sure first character is valid (alpha)
149: if (!Character.isLetter(chars[0])) {
150: chars[0] = 'X';
151: }
152:
153: // replace any other invalid characters
154: for (int i = 1; i < chars.length; i++) {
155: char c = chars[i];
156: if (!(Character.isLetterOrDigit(c) || (c == '_') || (c == '-'))) {
157: chars[i] = '_';
158: }
159: }
160:
161: return new String(chars);
162:
163: } // escapeVmName
164:
165: } // class VelocityServlet
|