目前我需要spring bean的jsp 2.0标签使用此代码:
ac = WebApplicationContextUtils.getWebApplicationContext( servletContext);
ac.getBeansOfType(MyRequestedClass.class);
我只是得到第一个匹配的bean。
这段代码工作正常,但有一个不希望出现的缺点,我花了大约一半的页面渲染时间查找spring bean,因为每次调用一个标签时都会发生这种情况。我想也许可以将bean放入应用程序范围或至少是会话范围。但是,处理这个问题的最聪明方法是什么?
答案 0 :(得分:11)
我的第一个想法是,你确定春天的电话很贵吗?这些东西经过了大量优化,因此在尝试优化之前确保它确实存在问题。
假设 是一个问题,那么替代方案就是exposeContextBeansAsAttributes
的{{1}}和exposedContextBeanNames
属性。您可以使用其中一个(但不是两个)将部分或全部bean作为JSP属性公开。
这引发了实际将Spring bean注入标记类的可能性。例如,在Spring上下文中,您可以:
InternalResourceViewResolver
您的JSP:
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<property name="exposeContextBeansAsAttributes" value="true"/>
</bean>
<bean id="myBean" class="com.x.MyClass"/>
如果<MyTag thing="${myBean}"/>
定义类型MyTag
的属性thing
,那么MyClass
spring bean应该作为普通的JSP属性注入。
答案 1 :(得分:8)
更简单的方法是在标记类上使用@Configurable批注,这会使Spring在标记初始化时自动连接依赖项。然后可以使用@AutoWired批注标记任何所需的依赖项,即使标记未在Spring容器中初始化,Spring也会依赖于依赖关系。
答案 2 :(得分:5)
实现此目的的另一种方法是使用静态属性来保存依赖项。如下所示:
public class InjectedTag extends SimpleTagSupport {
//In order to hold the injected service, we have to declare it as static
private static AService _service;
/***/
@Override
public void doTag() throws IOException {
getJspContext().getOut().
write("Service injected: " + _service + "<br />");
}
public void setService(AService service) {
_service = service;
}
}
在你的applicationcontext中,你必须注册两者,以便JSP标记有一次机会由Spring启动。我们带着神奇的去......
<bean id="aService" class="com.foo.AService">
<!-- configure the service. -->
</bean>
<bean class="com.foo.InjectedTag" >
<property name="service"><ref local="aService"/></property>
</bean>
很酷,现在我们的JSP标签中可以看到服务:)