昨天我写了一下SpringMVC最爱金丹的项目的配置流程,这样搭建完项目之后呢我发现我每个请求都得加个.do什么的后缀,这让我开发得很不爽,于是呢今天就想配置一下这个试图解释器,这样做的目的有两个:第一、在页面跳转的时候按照Resful风格的规定去掉页面路径上的后缀。第二,页面的跳转必须通过配置的试图解释器进行跳转不可以直接访问子页面。
接下来应该怎么做呢?需要配置试图解释器首先得知道哪个是我们需要的视图解释器,之前讲过SpringMVC默认给我们配置了一个视图解释器。既然是SpringMVC默认给的视图解释器当我们需要配置的时候就要去SpringMVC的包下面去找相关的信息了。
接着我就在view下面找到了JSP的视图解释器。接着我们就可以对它进行配置了。在配置之前首先得了解一下我们需要什么参数,还有这个类到底有什么功能。
* Convenient subclass of {@link UrlBasedViewResolver} that supports
* {@link InternalResourceView} (i.e. Servlets and JSPs) and subclasses
* such as {@link JstlView}.
从作者的注释上面可以看到这个类支持对JSP文件路径的的解析
* <p>BTW, it's good practice to put JSP files that just serve as views under
* WEB-INF, to hide them from direct access (e.g. via a manually entered URL).
* Only controllers will be able to access them then.
这段说明了这个可以类的配置可以把jsp放到WEB-INF目录下,我们就只能通过它来访问页面了。这样做可以防止用户跳过登录或者主页直接通过url跳转到主页或者其他的子页面。大大地增加了网站的安全性。
* @see #setPrefix
* @see #setSuffix
这些参数作者告诉了我们可以用过设置前后缀来指定动态资源存放的位置,我们的路径必须通过它来补全路径才能访问。
接着就把全路径写在了Spring的配置文件中,可是问题接踵而至,辣么,bean的name又是什么呢?在这里我们首先要清楚我们这个对象到底要交给谁去处理。
我们请求分发依赖的是DispacherServlet,请求的映射关系也是不仅仅依赖注解的实现,同时也依赖于DispacherServlet。既然作者把这两样的实现都对它有依赖了。那么视图解释器呢?
接着就打开了这个DispacherServlet这个类。于是答案就出来了。
/**
* Well-known name for the ViewResolver object in the bean factory for this namespace.
* Only used when "detectAllViewResolvers" is turned off.
* @see #setDetectAllViewResolvers
*/
public static final String VIEW_RESOLVER_BEAN_NAME = "viewResolver";
我看到这个类里面有这么一个参数作者说这个参数的对象在beanfactory里面被创建之后呢是为了这个明明空间,但是使用它的时候detectAllViewResolvers必须是关闭的。
接着又有疑问了这个setDetectAllViewResolvers又是个啥玩意儿呢?接着我又开始寻找
/**
* Set whether to detect all ViewResolver beans in this servlet's context. Otherwise,
* just a single bean with name "viewResolver" will be expected.
* <p>Default is "true". Turn this off if you want this servlet to use a single
* ViewResolver, despite multiple ViewResolver beans being defined in the context.
*/
public void setDetectAllViewResolvers(boolean detectAllViewResolvers) {
this.detectAllViewResolvers = detectAllViewResolvers;
}
这里作者又说了这里是是否扫描整个上下文里面所有关于视图解释器的bean对象,默认它们的name 是“viewResolver”。这里意思就是说SpringMVC默认支持同时配置多个视图解释器。
如果你希望只使用一个视图解释器的话可以把它设置成false。这样就只有一个试图解释器会生效了。
接着开始着手配置首先在SpringMVC基本框架已经搭好的基础上打开我们的配置文件。bean一个视图解释器。
<bean name="viewResolvers" class="org.springframework.web.servlet.view.InternalResourceViewResolver"></bean>
包的路径就是这个类的路径。那对象名呢?那么问题又回到最初了,到底是谁需要这个视图解释器?之前说过SpringMVC它默认给我们配置了一个
jsp的试图解释器。那什么时候用到它呢?那是我们在做请求分发的时候。请求首先会进入web.xml然后经过DispacherServlet处理过之后就到了Controller层
然后Controller调用Service代码····之后又回到Controller。然后又回到web.xml再跳转到页面。那我们又在这个地方只配置了一个Servlet。首当其冲就是
怀疑它了。于是我就可以展开对它的调查。打开之后发现了:
/**
* Well-known name for the ViewResolver object in the bean factory for this namespace.
* Only used when "detectAllViewResolvers" is turned off.
* @see #setDetectAllViewResolvers
*/
public static final String VIEW_RESOLVER_BEAN_NAME = "viewResolver";
果不其然这个类里面有了我们需要的答案。这个DispacherServlet启动时被调用之后它就会到Context容器之中收集它需要的对象
这里作者也说了。它会在启动之后在容器里面寻找叫做"viewResolver"这个名字的试图解释器。我们既然想把自己配置的视图解释器
赋予给这个DispacherServlet,那么bean这个对象的时候name属性命名为"viewResolver"不就可以了么。
这样对象就配好了那么接着我们需要配置这个对象的属性。查看一个对象的属性最快的方法就是Ctrl+鼠标左键点进去这个类里面
* @see #setPrefix
* @see #setSuffix
我们看到这两个参数之后就可以得知我们可以通过配置前后缀来让这个视图解释器在处理请求的时候帮我们加上前后缀。
<bean name="viewResolvers" class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<property name="prefix" value="/WEB-INF/view/" />
<property name="suffix" value=".jsp" />
</bean>
然后我们就需要去修改DispacherServlet的请求拦截规则修改一下
<servlet>
<servlet-name>dispatcherServlet</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:spring-*.xml</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>dispatcherServlet</servlet-name>
<url-pattern>/</url-pattern>
</servlet-mapping>
这样我们就把视图解释器配置好了。在这里有个地方值得我们注意的是:拦截规则的“ / “”和“ /* ”之间的区别
/拦截的是除了动态资源以外的资源,/*拦截的是所有的请求包括了动态和静态的资源。
这样视图解释器就全部配置好了。最后贴一下代码
web.xml代码:
<display-name>Spring-lianxi</display-name>
<servlet>
<servlet-name>dispatcherServlet</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:spring-*.xml</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>dispatcherServlet</servlet-name>
<url-pattern>/</url-pattern>
</servlet-mapping> <welcome-file-list>
<welcome-file>index.jsp</welcome-file>
</welcome-file-list>
SpringMVC配置文件代码:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:mvc="http://www.springframework.org/schema/mvc"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc-4.3.xsd"> <mvc:annotation-driven></mvc:annotation-driven> <mvc:default-servlet-handler/> <bean name="viewResolvers" class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<property name="prefix" value="/WEB-INF/view/" />
<property name="suffix" value=".jsp" />
</bean>
</beans>
SpringContext容器配置代码
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.1.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.3.xsd"> <context:component-scan base-package="cn.devil"></context:component-scan> </beans>
主页
<html>
<head>
<title>老 子 是 主 页</title>
</head> <body>
<a href="${pageContext.request.contextPath }/say">点我跳转页面</a>
</body>
</html>
跳转页面
<html>
<head>
<title>页 面 跳 转 成 功</title>
</head> <body>
Hello World!<br/>
<a href="${pageContext.request.contextPath }/goindex">点我回到首页</a>
</body>
</html>
Controller代码
@Controller
public class UserController { @RequestMapping("/say")
public String say() {
System.out.println("Hello World!");
return "hello";
} @RequestMapping("/goindex")
public String backToIndex() {
return "redirect:index.jsp";
}
}
文件的位置
OK大功告成。明天我打算开始在这个基础上写SpringMVC整合SpringJDBC