Author: rgielen
Date: Mon Jul 30 00:05:55 2007
New Revision: 560881

URL: http://svn.apache.org/viewvc?view=rev&rev=560881
Log:
WW-1661:
Backporting Freemarker template caching to 2.0.x tree

Modified:
    
struts/struts2/branches/STRUTS_2_0_X/core/src/main/java/org/apache/struts2/StrutsConstants.java
    
struts/struts2/branches/STRUTS_2_0_X/core/src/main/java/org/apache/struts2/components/template/FreemarkerTemplateEngine.java
    
struts/struts2/branches/STRUTS_2_0_X/core/src/main/java/org/apache/struts2/config/BeanSelectionProvider.java
    
struts/struts2/branches/STRUTS_2_0_X/core/src/main/resources/org/apache/struts2/default.properties

Modified: 
struts/struts2/branches/STRUTS_2_0_X/core/src/main/java/org/apache/struts2/StrutsConstants.java
URL: 
http://svn.apache.org/viewvc/struts/struts2/branches/STRUTS_2_0_X/core/src/main/java/org/apache/struts2/StrutsConstants.java?view=diff&rev=560881&r1=560880&r2=560881
==============================================================================
--- 
struts/struts2/branches/STRUTS_2_0_X/core/src/main/java/org/apache/struts2/StrutsConstants.java
 (original)
+++ 
struts/struts2/branches/STRUTS_2_0_X/core/src/main/java/org/apache/struts2/StrutsConstants.java
 Mon Jul 30 00:05:55 2007
@@ -76,6 +76,9 @@
     /** The org.apache.struts2.views.freemarker.FreemarkerManager 
implementation class */
     public static final String STRUTS_FREEMARKER_MANAGER_CLASSNAME = 
"struts.freemarker.manager.classname";
 
+    /** Cache Freemarker templates */
+    public static final String STRUTS_FREEMARKER_TEMPLATES_CACHE = 
"struts.freemarker.templatesCache";
+
     /** org.apache.struts2.views.velocity.VelocityManager implementation class 
*/
     public static final String STRUTS_VELOCITY_MANAGER_CLASSNAME = 
"struts.velocity.manager.classname";
 

Modified: 
struts/struts2/branches/STRUTS_2_0_X/core/src/main/java/org/apache/struts2/components/template/FreemarkerTemplateEngine.java
URL: 
http://svn.apache.org/viewvc/struts/struts2/branches/STRUTS_2_0_X/core/src/main/java/org/apache/struts2/components/template/FreemarkerTemplateEngine.java?view=diff&rev=560881&r1=560880&r2=560881
==============================================================================
--- 
struts/struts2/branches/STRUTS_2_0_X/core/src/main/java/org/apache/struts2/components/template/FreemarkerTemplateEngine.java
 (original)
+++ 
struts/struts2/branches/STRUTS_2_0_X/core/src/main/java/org/apache/struts2/components/template/FreemarkerTemplateEngine.java
 Mon Jul 30 00:05:55 2007
@@ -22,9 +22,7 @@
 
 import java.io.IOException;
 import java.io.Writer;
-import java.util.Iterator;
-import java.util.List;
-import java.util.Map;
+import java.util.*;
 
 import javax.servlet.ServletContext;
 import javax.servlet.http.HttpServletRequest;
@@ -33,6 +31,7 @@
 import org.apache.commons.logging.Log;
 import org.apache.commons.logging.LogFactory;
 import org.apache.struts2.ServletActionContext;
+import org.apache.struts2.StrutsConstants;
 import org.apache.struts2.views.freemarker.FreemarkerManager;
 
 import com.opensymphony.xwork2.inject.Inject;
@@ -41,8 +40,7 @@
 import com.opensymphony.xwork2.ActionInvocation;
 import com.opensymphony.xwork2.util.ValueStack;
 
-import freemarker.template.Configuration;
-import freemarker.template.SimpleHash;
+import freemarker.template.*;
 
 /**
  * Freemarker based template engine.
@@ -51,6 +49,10 @@
     static Class bodyContent = null;
     private FreemarkerManager freemarkerManager;
 
+    private final HashMap<String, freemarker.template.Template> templates = 
new HashMap<String, freemarker.template.Template>();
+    private final HashSet<String> missingTemplates = new HashSet<String>();
+    private boolean freemarkerCaching = false;
+
     static {
         try {
             bodyContent = 
ClassLoaderUtil.loadClass("javax.servlet.jsp.tagext.BodyContent",
@@ -88,16 +90,35 @@
         freemarker.template.Template template = null;
         String templateName = null;
         Exception exception = null;
-        for (Iterator iterator = templates.iterator(); iterator.hasNext();) {
-            Template t = (Template) iterator.next();
+        for (Object template1 : templates) {
+            Template t = (Template) template1;
             templateName = getFinalTemplateName(t);
-            try {
-                // try to load, and if it works, stop at the first one
-                template = config.getTemplate(templateName);
-                break;
-            } catch (IOException e) {
-                if (exception == null) {
-                    exception = e;
+            if (freemarkerCaching) {
+                if (!isTemplateMissing(templateName)) {
+                    try {
+                        template = findInCache(templateName);  // look in 
cache first
+                        if (template == null) {
+                            // try to load, and if it works, stop at the first 
one
+                            template = config.getTemplate(templateName);
+                            addToCache(templateName, template);
+                        }
+                        break;
+                    } catch (IOException e) {
+                        addToMissingTemplateCache(templateName);
+                        if (exception == null) {
+                            exception = e;
+                        }
+                    }
+                }
+            } else {
+                try {
+                    // try to load, and if it works, stop at the first one
+                    template = config.getTemplate(templateName);
+                    break;
+                } catch (IOException e) {
+                    if (exception == null) {
+                        exception = e;
+                    }
                 }
             }
         }
@@ -153,5 +174,41 @@
 
     protected String getSuffix() {
         return "ftl";
+    }
+
+    protected void addToMissingTemplateCache(String templateName) {
+        synchronized(missingTemplates) {
+            missingTemplates.add(templateName);
+        }
+    }
+
+    protected boolean isTemplateMissing(String templateName) {
+        synchronized(missingTemplates) {
+            return missingTemplates.contains(templateName);
+        }
+    }
+
+    protected void addToCache(String templateName,
+        freemarker.template.Template template) {
+        synchronized(templates) {
+            templates.put(templateName, template);
+        }
+    }
+
+    protected freemarker.template.Template findInCache(String templateName) {
+        synchronized(templates) {
+            return templates.get(templateName);
+        }
+    }
+
+    /**
+     * Enables or disables Struts caching of Freemarker templates. By default 
disabled.
+     * Set struts.freemarker.templatesCache=true to enable cache
+     * @param cacheTemplates "true" if the template engine should cache 
freemarker template
+     * internally
+     */
+    @Inject(StrutsConstants.STRUTS_FREEMARKER_TEMPLATES_CACHE)
+    public void setCacheTemplates(String cacheTemplates) {
+        freemarkerCaching = "true".equals(cacheTemplates);
     }
 }

Modified: 
struts/struts2/branches/STRUTS_2_0_X/core/src/main/java/org/apache/struts2/config/BeanSelectionProvider.java
URL: 
http://svn.apache.org/viewvc/struts/struts2/branches/STRUTS_2_0_X/core/src/main/java/org/apache/struts2/config/BeanSelectionProvider.java?view=diff&rev=560881&r1=560880&r2=560881
==============================================================================
--- 
struts/struts2/branches/STRUTS_2_0_X/core/src/main/java/org/apache/struts2/config/BeanSelectionProvider.java
 (original)
+++ 
struts/struts2/branches/STRUTS_2_0_X/core/src/main/java/org/apache/struts2/config/BeanSelectionProvider.java
 Mon Jul 30 00:05:55 2007
@@ -163,6 +163,7 @@
         if 
("true".equalsIgnoreCase(props.getProperty(StrutsConstants.STRUTS_DEVMODE))) {
             props.setProperty(StrutsConstants.STRUTS_I18N_RELOAD, "true");
             props.setProperty(StrutsConstants.STRUTS_CONFIGURATION_XML_RELOAD, 
"true");
+            
props.setProperty(StrutsConstants.STRUTS_FREEMARKER_TEMPLATES_CACHE, "false");
             // Convert struts properties into ones that xwork expects
             props.setProperty("devMode", "true");
         } else {

Modified: 
struts/struts2/branches/STRUTS_2_0_X/core/src/main/resources/org/apache/struts2/default.properties
URL: 
http://svn.apache.org/viewvc/struts/struts2/branches/STRUTS_2_0_X/core/src/main/resources/org/apache/struts2/default.properties?view=diff&rev=560881&r1=560880&r2=560881
==============================================================================
--- 
struts/struts2/branches/STRUTS_2_0_X/core/src/main/resources/org/apache/struts2/default.properties
 (original)
+++ 
struts/struts2/branches/STRUTS_2_0_X/core/src/main/resources/org/apache/struts2/default.properties
 Mon Jul 30 00:05:55 2007
@@ -164,6 +164,10 @@
 ### MUST extends off org.apache.struts2.views.freemarker.FreemarkerManager
 
#struts.freemarker.manager.classname=org.apache.struts2.views.freemarker.FreemarkerManager
 
+### Enables caching of FreeMarker templates
+### Has the same effect as copying the templates under WEB_APP/templates
+struts.freemarker.templatesCache=false
+
 ### See the StrutsBeanWrapper javadocs for more information
 struts.freemarker.wrapper.altMap=true
 


Reply via email to