开发者

How to disable freemarker caching in Spring MVC

I'm using spring mvc v3 with freemarker views and cannot disable caching. I tried by setting cache to false in viewResolver element in (spring-servlet.xml) b开发者_开发问答ut didn't work.

Basically what I'd like to the do some changes in freemarker and see these changes in the browser with refresh only (w/o restarting the application)

Any hints how to do that?


In my XML the following was successful:

<bean id="freemarkerMailConfiguration" class="org.springframework.ui.freemarker.FreeMarkerConfigurationFactoryBean">
    <property name="templateLoaderPaths" value="classpath:emailtemplates/task,classpath:emailtemplates/user"/>
    <!-- Activate the following to disable template caching -->
    <property name="freemarkerSettings" value="cache_storage=freemarker.cache.NullCacheStorage" />
</bean>

This is my mail config, but the freemarkerConfig should be interesting four you, too.


I dont use to configure freemarker with xml configurations but with @Configuration annotated classes; cause i rather the Spring-Boot´ style. So you can disable the freemarker´s cache like this:

@Bean
public FreeMarkerConfigurer freeMarkerConfigurer() throws IOException, TemplateException
{
    FreeMarkerConfigurer configurer = new FreeMarkerConfigurer()
    {

        @Override
        protected void postProcessConfiguration(freemarker.template.Configuration config) throws IOException, TemplateException
        { 
            ClassTemplateLoader classTplLoader = new ClassTemplateLoader(context.getClassLoader(), "/templates"); 
            ClassTemplateLoader baseMvcTplLoader = new ClassTemplateLoader(FreeMarkerConfigurer.class, ""); //TODO tratar de acceder a spring.ftl de forma directa
            MultiTemplateLoader mtl = new MultiTemplateLoader(new TemplateLoader[]
            { 
                classTplLoader,
                baseMvcTplLoader
            });
            config.setTemplateLoader(mtl);
            config.setCacheStorage(new NullCacheStorage()); 
        }
    };
    configurer.setDefaultEncoding("UTF-8"); 
    configurer.setPreferFileSystemAccess(false);
    return configurer;
}

The key is in:

config.setCacheStorage(new NullCacheStorage());

But you can also use this instruction instead:

config.setTemplateUpdateDelayMilliseconds(0);

It should work for you.


In application.properties:

spring.freemarker.cache=false


As defined by the manual :

If you change the template file, then FreeMarker will re-load and re-parse the template automatically when you get the template next time. However, since checking if the file has been changed can be time consuming, there is a Configuration level setting called ``update delay''. This is the time that must elapse since the last checking for a newer version of a certain template before FreeMarker will check that again. This is set to 5 seconds by default. If you want to see the changes of templates immediately, set it to 0.

After searching around, the configuration key was in the freemarker.template.Configuration javadocs, at the setSetting(key, value) method. So, in short, just set the config template_update_delay to 0 for immediate change detection.

<bean id="freemarkerConfig" class="org.springframework.web.servlet.view.freemarker.FreeMarkerConfigurer">
  <property name="templateLoaderPath" value="/WEB-INF/ftl/"/>
  <property name="freemarkerSettings">
        <props>
            <prop key="template_update_delay">0</prop>
            <prop key="default_encoding">UTF-8</prop>
        </props>
  </property>
</bean>


Did you check the FreeMarker documentation, which contains some hints regarding how to influence template caching at the FreeMarker Configuration level. I'm not sure if you have access to the FreeMarker Configuration object from inside Spring MVC, but if you have, then the documentation page mentioned above could point you towards a possible solution.


I wasted the last two days (note entirely for this project) trying to disable the cache. It turns out I have the two options antiJARLocking and antiResourceLocking set in my context.xml. Then the templates will ALWAYS be cached


I had the same problem which I could solve only by implementing a custom template loader. Here is the working code:

protected void init() throws Exception {
    freemarkerConfig = new Configuration();
    freemarkerConfig.setObjectWrapper(ObjectWrapper.DEFAULT_WRAPPER);
    freemarkerConfig.setTemplateLoader(new CacheAgnosticTemplateLoader(new DefaultResourceLoader(), pdfTemplatePath));
}

protected static class CacheAgnosticTemplateLoader extends SpringTemplateLoader {
    public CacheAgnosticTemplateLoader(ResourceLoader resourceLoader, String templateLoaderPath) {
        super(resourceLoader, templateLoaderPath);
    }

    @Override
    public long getLastModified(Object templateSource) {
        // disabling template caching
        return new Date().getTime();
    }
}


It seems that in the recently released FreeMarker version 2.3.17, a legal and simpler way to do it has appeared: freemarker.cache.NullCacheStorage.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜