<context-param> <param-name>contextConfigLocation</param-name> <param-value>classpath:applicationContext.xml,classpath:action-servlet.xml,classpath:applicationContext-security.xml</param-value> </context-param>
1、控制器Controller【多种可选,比如常用的AbstractController、AbstractCommonController等等,详细查看spring in action那本书】
2、处理器DispatcherServlet
3、上下文加载器ContextLoadListener
4、默认处理器映射Bean【可同时用多个,使用多个时候,优先级由order决定】
a)、BeanNameUrlHandlerMapping,默认(默认不用声明),直接按照名称查找(可选的有四种)
b)、SimpleUrlHandlerMapping 上下文配置文件中的定义的属性集合将控制器映射到URL
c)、ControllerCalssNameHandlerMapping 通过控制器的类名作为URL的基础将控制器映射到URL
d)、CommonsPathMapHandlerMapping
5、视图解析器Bean 将ModelAndView的第一个参数对应到具体的jsp,比如InternalResourceViewResolver使用比较简单
提问
1、怎么知道在HomePageController里就执行handleRequestInternal这个方法
2、如何对请求里的参数进行校验
3、提
默认情况下,和DispatcherServlet绑定的spring的配置文件例如springMVC.xml都
是在WEB-INF目录下,但是我们实际开发中不可能都放在这个目录下,所以需要配置
一下和DispatcherServlet绑定的spring的配置文件,这样开发更好更方便,怎么
配置呢,在配置DispatcherServlet的时候加一个参数init-param
<servlet> <servlet-name>roadrantz</servlet-name> <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class> <init-param> <param-name>contextConfigLocation</param-name> <param-value>classpath*:/config/roadrantz-servlet.xml</param-value> </init-param> <load-on-startup>1</load-on-startup> </servlet> <servlet-mapping> <servlet-name>roadrantz</servlet-name> <url-pattern>*.htm</url-pattern> </servlet-mapping>
同一个Controller里书写多个方法,想要调用不同方法,就需要配置方法名称解析器,
例如:
<bean id="paramMethodResolver" class="org.springframework.web.servlet.mvc.multiaction.ParameterMethodNameResolver"> <property name="paramName" value="action"></property> </bean>
然后在相应的Controller里面引入该方法名称解析器,例如:
<bean name="/muti.htm" class="com.test.controller.MultiController"> <!-- 配置方法名称解析器 --> <property name="methodNameResolver"> <ref bean="paramMethodResolver"/> </property> </bean>
请求的时候通过action参数来传递方法名称来指定调用的具体方法,例如:
http://localhost:8000/SpringMVC_Test2/muti.htm?action=add
spring mvc访问静态文件的时候,假如DispatcherServlet配置的访问路径匹配符为
/(匹配所有请求),那么这时spring mvc访问静态文件(Js、图片等)会有问题,访问
不到。需要在spring mvc的配置文件里加一段代码:
<mvc:resources location="/img/" mapping="/img/**"/>
这段代码告诉spring mvc img这个下面所有的文件直接访问就可以了,不要拦截了,
不要再去spring mvc的配置文件里去找相匹配的请求处理器了,直接访问就行了。
或者另一种解决方案是不要把DispatcherServlet配置的请求访问路径设置成全部
spring mvc最方便还是使用它的注解
如何开启注解:
<!-- spring mvc配置注解扫描包 --> <context:component-scan base-package=""></context:component-scan> <!-- 下面两个是spring mvc 注解的两个启动类(开启注解) --> <!-- 注解查找方法映射 --> <bean class="org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter"></bean> <!-- 注解查找类映射 --> <bean class="org.springframework.web.servlet.mvc.annotation.DefaultAnnotationHandlerMapping"></bean>
spring mvc常用注解:
@Controller【配置类】
@RequestMapping(value="/user/delUser.htm", method=RequestMethod.GET)【配置方法】
在类上面也可以配置@RequestMapping(value="/user"),这样访问某个方法的时候请求地址是类的加上方法的RequestMapping配置
更简洁的写法是:@RequestMapping("/user")
Controller里面的方法代码模板一般是这样的:
@RequestMapping(value="/user/delUser.htm", method=RequestMethod.GET) public ModelAndView delUser() { String result = "this is delUser-----------"; return new ModelAndView("annotation", "result", result); }
但是其实还可以更简洁:
@RequestMapping(value="/user/delUser.htm") public String delUser(HttpServletRequest request) { String result = "this is delUser-----------"; request.setAttribute("result",result); return "annotation"; }
这样岂不是变的更简单。
重点:spring 3.0里面提出了对开启注解的优化,可以通过如下配置来替换注解的两个启动类
<mvc:annotation-driven/>
配置上面这个之后,就不需要配置spring mvc注解的两个穷类了。
spring mvc传递参数:
在jsp标签里面的name名称和Controller里面的参数名称相同,然后就自动赋值了,想要在Controller里的方法返回的时候还带着
参数,那么就需要在Controller里的方法里将需要携带的参数放到request里面(每个方法里都可以有HttpServletRequest request
参数,方法返回时需要携带参数的时候就在此方法的参数列表里把此参数加上即可)。
下面讲解传递参数一些规则,例如:
public String addUser(String userName, String age, HttpServletRequest request) { request.setAttribute("userName", userName); request.setAttribute("age", age); return "/userManager"; }
这就是上面描述的传参方式;
public String addUser2(User user, HttpServletRequest request) { request.setAttribute("userName", user.getUserName()); request.setAttribute("age", user.getAge()); return "/userManager"; }
这种是针对参数个数比较多的情况下的时候直接定义一个实体,参数直接以实体形式传递(像这里就定义了一个User实体,
实体里面有String userName,String age两个参数),这种传参方式就简化了。只要jsp页面上有name为userNamen和age这两个名称
的标签即可。
下面讲解json格式传递参数:
下面讲解spring mvc文件上传功能:
上传文件解析器配置:
<bean id="mutipartResolver" class="org.springframework.web.multipart.commons.CommonsMultipartResolver"> <property name="defaultEncoding" value="utf-8"/> <property name="maxUploadSize" value="10485760000"/> <property name="maxInMemorySize" value="40960"/> </bean>
这篇文章描述了一些文件上传的相关知识:
http://blog.sina.com.cn/s/blog_8fb83eec0100wm1r.html
另外在文件上传的页面上的form表单里一定要标注出enctype="multipart/form-data"此属性。
并且也必须设置method="post",文件上传必须设置method属性。
(enctype属性表示在表单提交之前要对提交内容怎样编码,在上传文件的情况下一定要设成multipart/form-data)
<input type="file" name="file">
Spring通过对Servlet API的HttpServletRequest接口进行扩展,使其能够很好地处理文件上传。扩展后的接口名为
org.springframework.web.multipart.MultipartHttpServletRequest
interface MultipartHttpServletRequest extends HttpServletRequest{ public MultipartFile getFile(String name); public Map getFileMap(); public Iterator getFileName(); }
上传文件相关事例见SpringMVC_Test4项目(这种方式上传文件比较慢,这里面自己读取文件,而spring又提供了一种
另一种更快的上传方式,spring帮助我们读取文件,这种的会使上传速度变的更快,下面介绍这种更快的上传方式)
http://blog.csdn.net/a1314517love/article/details/24183273
上传更快的方式也是在SpringMVC_Test4项目里
下面讲解spring mvc和spring的集成:
web容器的启动顺序:
1、第一个加载context-param元素,表示根目录的参数,负责xml里边的一些文件的加载。
2、第二个启动Listener。
3、然后启动filter。
4、最后启动Servlet。
配置spring启动监听器org.springframework.web.context.ContextLoaderListener的时候,默认是自动去WEB-INF目录下去找
applicationContext.xml配置文件并加载,怎么修改这种默认规则呢?(我就不想把配置文件放在WEB-INF目录下,怎么办呢?)
在web.xml文件里采用下面这种方式配置,
<context-param> <param-name>contextConfigLocation</param-name> <param-value>classpath*:config/applicationContext.xml</param-value> </context-param>
然后web容器就会到指定的目录下去加载applicationContext.xml配置文件,而不会在默认的去WEB-INF目录下找相应的配置文件。
在servlet中获取context-param配置参数:String paramValue=getServletContext().getInitParameter("contextConfigLocation");
相关context-param配置的说明详见:
http://hain.iteye.com/blog/70731
http://zhidao.baidu.com/link?url=7iOp55M4bZRXMi3VvQluYHGR_oy0FJiyiOqblZTPHYwBG_fDGMimTFeNQHzKmSXTCdaDrXJ3lI45RaZRLUtIL_
http://blog.csdn.net/jubincn/article/details/9115205
spring mvc一些基本讲解:http://elf8848.iteye.com/blog/875830 (这里面主要看spring拦截器、全局异常处理等。最主要看
十一之后几节的内容,而且这里面也讲解了如何获取spring bean对象)
相关示例项目代码见网盘: http://pan.baidu.com/s/1eQrOVLK