在某些MVC框架中,如果您希望执行某些代码并渲染部分局部视图,则可以从视图中调用控制器操作。我不确定在Spring MVC中执行此操作的正确方法是什么
我想拥有一组JSP模板。其中一些将是页面布局,其中一些将是小组件,如分页器,登录框,菜单,标签云等等。这些组件中的每一个都需要一些bean或控制器操作来将一些数据设置到ViewAndModel中,以便视图可以使用它
问题是我不想在每次调用中设置所有这些对象。我的注册管理员只关心注册处理。所以现在我该怎么做呢?如何从视图中调用DI bean或控制器以准备部分视图?或者我应该创建一些映射?或者我是从完全错误的角度来解决问题的?
答案 0 :(得分:38)
如果您希望这样做,Spring-MVC可以将应用程序上下文的bean公开给视图层。
例如,可以指示InternalResourceViewResolver
公开上下文中的每个bean,或者只显示指定的bean。请查看exposeContextBeansAsAttributes和exposedContextBeanNames属性。
例如,假设您希望将bean beanA
和beanB
公开给您的JSP。您可以在上下文中声明视图解析器:
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<property name="exposedContextBeanNames">
<list>
<value>beanA</value>
<value>beanB</value>
</list>
</property>
</bean>
或者,只是暴露每个bean:
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<property name="exposeContextBeansAsAttributes" value="true"/>
</bean>
这是否是一个好主意是另一个问题,但Spring确实为您提供了选择。
答案 1 :(得分:5)
IMO 在viewResolver bean配置中添加使用exposedContextBeanNames(也有可能使用全局标志,而不建议使用)
<bean id="viewResolver"
class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<property name="exposedContextBeanNames">
<list>
<value>beanName</value>
</list>
在JSP中使用
${beanName.property}
答案 2 :(得分:3)
使用InternalResourceViewResolver的一个关键部分似乎是Spring在处理jsp页面时需要参与代码流。 如果您直接访问jsp页面或绕过任何基于Spring的操作(例如,可能是由于web.xml中的登录配置而内部转发到jsp页面),那么这将无效。
但是,可以配置您的应用程序,以便某些bean可以访问任何可以通过ServletContext(也称为applicationScope)访问的bean。 使用ServletContextAttributeExporter类。
在弹簧配置中,添加:
<bean id="mybean" .../>
<bean class="org.springframework.web.context.support.ServletContextAttributeExporter">
<property name="attributes">
<map>
<entry key="attrname" value-ref="mybean"/>
</map>
</property>
</bean>
然后,在JSP页面中,您可以使用以下命令访问该bean:
${applicationScope.attrname}
或者如果您知道在更具体的范围内没有“attrname”属性,只需:
${attrname}
显然,这将无法引用请求或会话范围bean,但如果您需要访问单例bean,那么它可以很好地工作。
答案 3 :(得分:3)
您可以使用spring:eval
代码:
...
<spring:eval expression="@properties.getProperty('myProp')" var="myProp" />
${myProp}
...
其中@properties
是Spring Context中属性的bean名称。请注意,此方法不使用exposedContextBeanNames
,因此它可以与Tiles视图一起使用,例如(TilesViewResolver
没有这样的属性)。
答案 4 :(得分:0)
永远不要从jsp视图访问业务组件;像sitemesh这样的东西可以用来将多个视图合二为一。 Jsps也不应该直接调用控制器方法
答案 5 :(得分:0)
基于注解的方法解决 JSP 中 Spring bean 的使用问题。
Spring MVC + JSP 瓦片:
SQL> set serveroutput on;
SQL> begin
2 getallorders2('A101');
3 end;
4 /
A101, basant, 32000, O101, 04.02.2021
PL/SQL procedure successfully completed.
SQL>
在我的 .jsp 中:
@Bean
public ViewResolver tilesViewResolver() {
final UrlBasedViewResolver = new UrlBasedViewResolver();
...
viewResolver.setExposeContextBeansAsAttributes(true);
viewResolver.setExposedContextBeanNames("myBean");
return viewResolver;
}