问题描述
我想为Spring MVC中的几个URL添加缓存控制指令(同时设置公共和最大使用时间),我想仅通过applicationContext.xml进行这些更改。
I want to add cache-control directive (set both public and max-age seconds) for a couple of URLs in Spring MVC and I want to do those changes via applicationContext.xml only.
我正在尝试设置 org.springframework.web.servlet.mvc.WebContentInterceptor
的地图属性 cacheControlMappings
,但是唯一的问题是没有属性设置方法的类的设计。解决方法是,我使用 org.springframework.beans.factory.config.MethodInvokingBean
调用 addCacheMapping
方法。
I am trying to set the map property cacheControlMappings
of org.springframework.web.servlet.mvc.WebContentInterceptor
, but the only problem is the design of the class which has no setter method for the property. As a workaround, I am invoking the addCacheMapping
method using the org.springframework.beans.factory.config.MethodInvokingBean
.
我在spring-mvc-config.xml中的配置如下-
我在创建 CacheControl
bean如下,并且通过调试验证了此bean是否已成功创建,并已在应用程序上下文中填充了适当的值。
My configuration in spring-mvc-config.xml is as follows -I am creating a CacheControl
bean as follows, and I verified by debugging that this bean gets created successfully with appropriate values populated in the application context.
<bean id="cacheControlFactory" class="org.springframework.http.CacheControl" factory-method="maxAge">
<constructor-arg index="0" value="3600"/>
<constructor-arg index="1">
<value type="java.util.concurrent.TimeUnit">SECONDS</value>
</constructor-arg>
</bean>
<bean id="myCacheControl" class="org.springframework.beans.factory.config.MethodInvokingFactoryBean">
<property name="targetObject">
<ref bean="cacheControlFactory"/>
</property>
<property name="targetMethod">
<value>cachePublic</value>
</property>
</bean>
然后我希望调用此方法- public void addCacheMapping(CacheControl cacheControl,String ...
,这会将条目添加到地图 WebContentInterceptor
的路径) cacheControlMappings
。
Then I wish to invoke this method - public void addCacheMapping(CacheControl cacheControl, String... paths)
of WebContentInterceptor
which will add entries to the map cacheControlMappings
.
我验证了以编程方式调用此方法的效果很好,因此如果我从XML调用它,它应该可以正常工作吗?但是我正尝试这样做,如下所示,但这对我来说不起作用,并且我在最终地图中添加了零个条目。
I verified that calling this method programmatically works great, so it should work fine if I invoke it from the XML right? But I am trying to do the same, as shown below, but this does not work for me, and I get zero entries added to the final map.
<bean class="org.springframework.beans.factory.config.MethodInvokingBean">
<property name="targetObject">
<ref bean="webContentInterceptor"/>
</property>
<property name="targetMethod">
<value>addCacheMapping</value>
</property>
<property name="arguments">
<list>
<ref bean="myCacheControl" />
<value>/home</value>
<value>/dp/**</value>
<value>/**/b/*</value>
</list>
</property>
</bean>
为什么上述对 MethodInvokingBean
的调用不起作用?我是否以任何方式设置了错误的论点?可变参数是否需要其他处理?在服务器启动期间,我也看不到任何错误。
Why does the above invocation with MethodInvokingBean
not work? Am I setting the arguments wrong in any way? Do the varargs need a different handling? I don't see any errors thrown either during server startup.
此外,我知道此SO线程(),其中所接受的答案提到XML本身无法执行此操作。我想通过尝试实施上述解决方案来再次确认这是否正确,但是它不起作用,但是我不明白为什么。
Also, I am aware of this SO thread (How to set Cache-control: private with applicationContext.xml in Spring 4.2 or later ) where the accepted answer mentions there is no way to do this in the XML itself. I wanted to re-confirm if that is correct by trying to implement above solution but it is not working, but I don't see why.
推荐答案
正如我所怀疑的那样,参数的填充方式存在问题。弹簧注入中的varargs必须作为一个显式列表而不是参数的重载给出(就像在Java中那样)。
As I had suspected, there was an issue in the way the arguments were getting populated. The varargs in a spring injection need to be given as an explicit list instead of an overload of arguments (like it's done in Java).
所以调用这种方法的正确方法-
So the correct way to invoke such a method -
public void addCacheMapping(CacheControl cacheControl, String... paths)
春季applicationContext.xml中的
如下-
in spring applicationContext.xml is as follows -
<bean class="org.springframework.beans.factory.config.MethodInvokingFactoryBean">
<property name="targetObject">
<ref bean="webContentInterceptor"/>
</property>
<property name="targetMethod">
<value>addCacheMapping</value>
</property>
<property name="arguments">
<list>
<ref bean="myCacheControl" />
<list>
<value>/home</value>
<value>/dp/**</value>
<value>/**/b/*</value>
</list>
</list>
</property>
</bean>
如您所见,我现在使用了 MethodInvokingFactoryBean
。 MethodInvokingBean
对我不起作用。
As you can see I have now used MethodInvokingFactoryBean
. Somehow MethodInvokingBean
did not work for me.
这篇关于如何在Spring 5 Xml中的WebContentInterceptor中设置cacheControlMappings的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!