Struts 2
  1. Struts 2
  2. WW-3765

Improve performance of FreeMarker Template caching

    Details

    • Flags:
      Patch

      Description

      Struts2 having option to enable the freemarker template caching with reloading the template with time delay which helps us to improve the performance.

      In our application we are using the strut2 in-built UI freemarker template. We need the caching option without reloading the templates after the specific time delay.

      Caching option is more powerful if we have an option for enabling\disabling the reload

      Proposed Solution

      Struts.xml
      <constant name="struts.freemarker.templatesCache.required" value="true"/>

      FreeMarkerManager.java

      protected boolean templateUpdateRequired;
      @Inject(STRUTS_FREEMARKER_TEMPLATES_RELOAD_REQUIRED)
      public void setTemplateUpdateRequired(String templateUpdateRequired)

      { this.templateUpdateRequired ="true".equals(templateUpdateRequired); }

      Update createConfiguration(ServletContext servletContext) Method
      configuration.setSetting(Configuration. TEMPLATE_RELOAD_ REQUIRED _KEY, templateUpdateRequired);

      Configuration.java

      String TEMPLATE_RELOAD_ REQUIRED _KEY= "template_reload_required";

      TemplateCache.Java

      protected boolean templateUpdateRequired;

      Update getTemplate(TemplateLoader loader, String name, Locale locale, String encoding, boolean parse) Method
      ...
      if (templateUpdateRequired !=false && now - cachedTemplate.lastChecked < delay) {

        Issue Links

          Activity

          Hide
          Vijayakannan added a comment -

          Caching option is more powerful if we have an option for enabling\disabling the reload

          Show
          Vijayakannan added a comment - Caching option is more powerful if we have an option for enabling\disabling the reload
          Hide
          Lukasz Lenart added a comment -

          Did you implemented that in your application ?

          Show
          Lukasz Lenart added a comment - Did you implemented that in your application ?
          Hide
          zhouyanming added a comment -

          there is a workaround,you can set updateDelay as large as possible
          <constant name="struts.freemarker.templatesCache.updateDelay" value="$

          {Long.MAX_VALUE}

          " />

          Show
          zhouyanming added a comment - there is a workaround,you can set updateDelay as large as possible <constant name="struts.freemarker.templatesCache.updateDelay" value="$ {Long.MAX_VALUE} " />
          Hide
          Vijayakannan added a comment -

          We are also using the same workaround in our project but it's not an optimal solution.
          During the performance testing with 800 concurrent user, the getTemplate() method in TemplateCache.java blocks 80 Threads(Deadlocks occur) and this is an major performance issue in our project. Our application should be available for 24/7 and expected concurrent user is more than 7000

          One worst day, this workaround will blocks the user threads even if we provide the max long value.

          We identified that the root cause of deadlocks is reloading the Freemaker template
          For the optimal solution, there should some option to enable\disable the reloading of Freemaker template with cache option

          Show
          Vijayakannan added a comment - We are also using the same workaround in our project but it's not an optimal solution. During the performance testing with 800 concurrent user, the getTemplate() method in TemplateCache.java blocks 80 Threads(Deadlocks occur) and this is an major performance issue in our project. Our application should be available for 24/7 and expected concurrent user is more than 7000 One worst day, this workaround will blocks the user threads even if we provide the max long value. We identified that the root cause of deadlocks is reloading the Freemaker template For the optimal solution, there should some option to enable\disable the reloading of Freemaker template with cache option
          Hide
          Philip Luppens added a comment -

          Just a quick question: isn't this controlled by the freemarker.properties file with a delay of -1?

          Show
          Philip Luppens added a comment - Just a quick question: isn't this controlled by the freemarker.properties file with a delay of -1?
          Hide
          zhouyanming added a comment -

          freemarker doesn't controll delay of -1,I have reported a feature request

          https://sourceforge.net/tracker/?func=detail&aid=3493744&group_id=794&atid=350794

          Show
          zhouyanming added a comment - freemarker doesn't controll delay of -1,I have reported a feature request https://sourceforge.net/tracker/?func=detail&aid=3493744&group_id=794&atid=350794
          Hide
          zhouyanming added a comment -

          @Vijayakannan,please try <constant name="struts.freemarker.mru.max.strong.size" value="0" /> to prevent deadlock,please see WW-3766

          Show
          zhouyanming added a comment - @Vijayakannan,please try <constant name="struts.freemarker.mru.max.strong.size" value="0" /> to prevent deadlock,please see WW-3766
          Hide
          Vijayakannan added a comment -

          if (delay<=0 || now - cachedTemplate.lastChecked < delay)
          This line changes in freemarker.cache.TemplateCache.java will really help us to avoid reloading of freemarker templates

          <constant name="struts.freemarker.mru.max.strong.size" value="0" />
          It's working fine.We need to do some more performance testing to ensure the same

          Thanks for your comments

          Show
          Vijayakannan added a comment - if (delay<=0 || now - cachedTemplate.lastChecked < delay) This line changes in freemarker.cache.TemplateCache.java will really help us to avoid reloading of freemarker templates <constant name="struts.freemarker.mru.max.strong.size" value="0" /> It's working fine.We need to do some more performance testing to ensure the same Thanks for your comments
          Hide
          Lukasz Lenart added a comment -

          Please report back results of your testing. Thanks!

          Show
          Lukasz Lenart added a comment - Please report back results of your testing. Thanks!
          Hide
          Daniel Dekany added a comment -

          If you set the delay to a sufficiently large value, such as Integer.MAX_VALUE, reloading should never occur due to the update delay (unless you run the server for 70 years). You can still have re-loadings however, if cache drops cached templates because the GC decides so. This can be prevented with using sufficiently large "hard" size in MruCacheStroage.

          (I surely hope you don't have a dead locks. That's when something freezes indefinitely because threads waiting on each other mutually.)

          Show
          Daniel Dekany added a comment - If you set the delay to a sufficiently large value, such as Integer.MAX_VALUE, reloading should never occur due to the update delay (unless you run the server for 70 years). You can still have re-loadings however, if cache drops cached templates because the GC decides so. This can be prevented with using sufficiently large "hard" size in MruCacheStroage. (I surely hope you don't have a dead locks. That's when something freezes indefinitely because threads waiting on each other mutually.)
          Hide
          Lukasz Lenart added a comment -

          @Vijayakannan any news?

          Show
          Lukasz Lenart added a comment - @Vijayakannan any news?
          Hide
          Vijayakannan added a comment -

          <constant name="struts.freemarker.mru.max.strong.size" value="0" />
          Our application move to production and don't able to validate the above changes due to code freeze

          The conclusion for performance issue is loading the template from struts jar and freemarker not able to identify the last modification time. to solve this we change to application path.

          Setup in our Production

          <constant name="struts.freemarker.mru.max.strong.size" value="250" />
          <constant name="struts.freemarker.templatesCache" value="true" />
          <constant name="struts.ui.templateDir" value="WEB-INF/template"/>
          <constant name="struts.freemarker.templatesCache.updateDelay" value="86400" />

          It's working fine in terms of performance

          The only problem in the above setup is parent "theme.properties" file inside the child folder is not recognized by freemarker. So we copy all the parent's freemarker template into child folder.

          Refer : https://issues.apache.org/jira/browse/WW-3764

          Thanks a lot for all your support.

          Show
          Vijayakannan added a comment - <constant name="struts.freemarker.mru.max.strong.size" value="0" /> Our application move to production and don't able to validate the above changes due to code freeze The conclusion for performance issue is loading the template from struts jar and freemarker not able to identify the last modification time. to solve this we change to application path. Setup in our Production <constant name="struts.freemarker.mru.max.strong.size" value="250" /> <constant name="struts.freemarker.templatesCache" value="true" /> <constant name="struts.ui.templateDir" value="WEB-INF/template"/> <constant name="struts.freemarker.templatesCache.updateDelay" value="86400" /> It's working fine in terms of performance The only problem in the above setup is parent "theme.properties" file inside the child folder is not recognized by freemarker. So we copy all the parent's freemarker template into child folder. Refer : https://issues.apache.org/jira/browse/WW-3764 Thanks a lot for all your support.
          Hide
          Lukasz Lenart added a comment -

          Thanks, I'll close the issue then. If you face the problem again, please open it. I still don't get the problem with theme.properties :/

          Show
          Lukasz Lenart added a comment - Thanks, I'll close the issue then. If you face the problem again, please open it. I still don't get the problem with theme.properties :/
          Hide
          Vijayakannan added a comment -

          The problem with theme.properties

          Getting File not Exception if i tried to load the struts default templates from application path "WEB-INF/template"

          SEVERE: Could not open template
          java.io.FileNotFoundException: Template /WEB-INF/template/xhtml/a.ftl not found.
          at freemarker.template.Configuration.getTemplate(Configuration.java:489)
          at freemarker.template.Configuration.getTemplate(Configuration.java:452)
          at org.apache.struts2.components.template.FreemarkerTemplateEngine.renderTemplate(FreemarkerTemplateEngine.java:96)
          at org.apache.struts2.components.UIBean.mergeTemplate(UIBean.java:559)
          at org.apache.struts2.components.ClosingUIBean.start(ClosingUIBean.java:59)
          at org.apache.struts2.components.Anchor.start(Anchor.java:132)

          I have updated this in https://issues.apache.org/jira/browse/WW-3764 WW-3764 issue too and we can track it @ WW-3764 itself.

          Thanks a lot

          Show
          Vijayakannan added a comment - The problem with theme.properties Getting File not Exception if i tried to load the struts default templates from application path "WEB-INF/template" SEVERE: Could not open template java.io.FileNotFoundException: Template /WEB-INF/template/xhtml/a.ftl not found. at freemarker.template.Configuration.getTemplate(Configuration.java:489) at freemarker.template.Configuration.getTemplate(Configuration.java:452) at org.apache.struts2.components.template.FreemarkerTemplateEngine.renderTemplate(FreemarkerTemplateEngine.java:96) at org.apache.struts2.components.UIBean.mergeTemplate(UIBean.java:559) at org.apache.struts2.components.ClosingUIBean.start(ClosingUIBean.java:59) at org.apache.struts2.components.Anchor.start(Anchor.java:132) I have updated this in https://issues.apache.org/jira/browse/WW-3764 WW-3764 issue too and we can track it @ WW-3764 itself. Thanks a lot

            People

            • Assignee:
              Lukasz Lenart
              Reporter:
              Vijayakannan
            • Votes:
              0 Vote for this issue
              Watchers:
              1 Start watching this issue

              Dates

              • Created:
                Updated:
                Resolved:

                Time Tracking

                Estimated:
                Original Estimate - 24h
                24h
                Remaining:
                Remaining Estimate - 24h
                24h
                Logged:
                Time Spent - Not Specified
                Not Specified

                  Development