文章目录
处理方法支持的参数类型
列举一些常用类型
- ServletRequest/HttpServletRequest 和ServletResponse/HttpServletResponse
- InputStream/OutputStream 和Reader/Writer
- WebRequest/NativeWebRequest
- HttpSession
- 命令/表单对象
- 模型Model、Map、ModelMap
- 基本数据类型,如int,String,double等,复杂数据类型,如自定义的POJO对象
1.基本数据类型和复杂数据类型
1.1 基本数据类型
- 方法的参数可以是任意基本数据类型,如果方法参数名与http中请求的参数名称相同时会进行自动映射
// 自动参数映射
@RequestMapping("/login")
public String login(Model model, int id, String name) {
model.addAttribute("message", "name=" + name + ",id=" + id);
return "login";
}
1.2 自定义数据类型
- 除了基本数据类型,也可以自定义的数据类型,如一个自定义的bean对象,Spring MVC会通过反射把请中的参数设置到对象中,注意字段值要与请求中的参数名相同。
// 自动参数映射自定义数据类型
@RequestMapping("/student")
public String student(Model model, Student student) {
model.addAttribute("message", student);
return "student";
}
1.3 数组、List集合、Map集合类型
- 以Map集合为例,同样要注意字段值要与请求中的参数名相同。
// Map类型
@RequestMapping("/product")
public String product(Model model, ProductMap map) {
model.addAttribute("message", map.getItems().get("p1") + "<br/>" + map.getItems().get("p2"));
return "product";
}
2.@RequestParam
@RequestParam可以实现请求参数绑定,Spring MVC会自动查找请求中的参数转类型并将与参数进行绑定。
public String requestParam(@RequestParam String username)
请求中包含username 参数(如/requestparam?username=zhang),则自动传入。
@RequestParam注解主要有哪些参数:
- value:参数名字,即入参的请求参数名字,如username表示请求的参数区中的名字为username的参数的值将传入
- required:是否必须,默认是true,表示请求中一定要有相应的参数,否则将报400错误码
- defaultValue:默认值,表示如果请求中没有同名参数时的默认值
public String requestParam(@RequestParam(value="username", required=true, defaultValue="zhang") String username)
3.@RequestBody(@ResponseBody)
@requestBody注解常用来处理content-type不是默认的application/x-www-form-urlcoded编码的内容,比如说:application/json或者是application/xml等。一般情况下来说常用其来处理application/json类型。
Spring默认的json协议解析由Jackson完成。要完成这个功能还需要修改配置环境,具体要求如下:
- 修改Spring MVC配置文件,启用mvc注解驱动功能,<mvc:annotation-driven />
- pom.xmlpom.xml 添加jackson依赖
<!--jackson-->
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
<version>2.7.4</version>
</dependency>
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-core</artifactId>
<version>2.7.4</version>
</dependency>
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-annotations</artifactId>
<version>2.7.4</version>
</dependency>
GET、POST方式提时, 根据request header Content-Type的值来判断:
- application/x-www-form-urlencoded, 可选(即非必须,因为这种情况的数据@RequestParam, @ModelAttribute也可以处理,当然@RequestBody也能处理);
- multipart/form-data, 使用@RequestBody不能处理这种格式的数据。
- application/json, application/xml等其他格式,必须使用@RequestBody来处理。
@RequestMapping(value = "/login")
//将请求中的数据写入User对象中
public String login(@RequestBody User user) {...}
PUT方式提交时, 根据request header Content-Type的值来判断:
- application/x-www-form-urlencoded, 必须;
- multipart/form-data, 不能处理;
- 其他格式, 必须;
@ResponseBody
@RequestBody的作用是让Spring MVC在收到客户端请求时将选择合适的转换器将参数转换成相应的对象。
4.@CookieValue
@CookieValue用于将请求的Cookie数据映射到功能处理方法的参数上。
public String test(@CookieValue(value="JSESSIONID", defaultValue="") String sessionId)
如上配置将自动将JSESSIONID 值入参到sessionId 参数上,defaultValue 表示Cookie 中没有JSESSIONID 时默认为空。
public String test2(@CookieValue(value="JSESSIONID", defaultValue="") Cookie sessionId)
传入参数类型也可以是javax.servlet.http.Cookie类型。
5.@RequestHeader
@RequestHeader 用于将请求的头信息区数据映射到功能处理方法的参数上。
@RequestMapping(value="/header")
public String test(@RequestHeader("User-Agent") String userAgent,
@RequestHeader(value="Accept") String[] accepts){
......
}
如上配置将自动将请求头“User-Agent”值入参到userAgent 参数上,并将“Accept”请求头值入参到accepts参数上。
@RequestHeader和@CookieValue也拥有和@RequestParam相同的三个参数,含义一样。
6.@PathVariable
@PathVariable用于将请求URL中的模板变量映射到功能处理方法的参数上。
@RequestMapping(value="/users/{userId}/topics/{topicId}")
public String test(@PathVariable(value="userId") int userId,
@PathVariable(value="topicId") int topicId){......}
如请求的 URL 为“控制器URL/users/123/topics/456”,则自动将URL 中模板变量{userId}和{topicId}绑定到通过@PathVariable注解的同名参数上,即入参后userId=123、topicId=456。
7.@ModelAttribute和@SessionAttributes
@ModelAttribute该注解有一下三个用法:
- 绑定请求参数到命令对象
放在功能处理方法的入参上时,用于将多个请求参数绑定到一个命令对象,从而简化绑定流程,而且自动暴露为模型数据用于视图页面展示时使用。
@RequestMapping(value = { "/ma" })
public ModelAndView ma(@ModelAttribute("dept") DeptEntity dept,Map map) {.........}
@ModelAttribute(“dept”) DeptEntity dept等价于model.addObject(“dept”,obj);
@ModelAttribute它的作用是将该绑定的命令对象以“dept”为名称添加到模型对象中供视图页面展示使用。我们此时可以在视图页面使用${dept.dname}来获取绑定的命令对象的属性。
- 暴露表单引用对象为模型数据
放在处理器的一般方法(非功能处理方法)上时,是为表单准备要展示的表单引用对象,该方法在执行功能处理方法(@RequestMapping 注解的方法)之前,自动添加到模型对象中,用于视图页面展示时使用或在处理方法中使用;
@ModelAttribute("dept")
public DeptEntity getDept(String dno) {
DeptEntity dept=new DeptEntity();
dept.setDno(Integer.parseInt(dno));
return dept;
}
如上代码会在执行功能处理方法之前执行,并将其自动添加到模型对象中。
1、先于处理方法执行
2、把方法的返回值放入model中
3、可以通过参数接收表单对象
- 暴露@RequestMapping 方法返回值为模型数据
放在功能处理方法的返回值上时,是暴露功能处理方法的返回值为模型数据,用于视图页面展示时使用。
@RequestMapping(value = { "/returnDept" })
Public @ModelAttribute("dept") DeptEntity returnDept() {
DeptEntity dept = new DeptEntity();
dept.setDno(304);
dept.setDname("研发部");
dept.setDloc("长江");
return dept;
}
此时没有设置viewname,该如何跳转?
RequestToViewNameTranslator类:
用于直接将请求转换为逻辑视图名。默认实现为DefaultRequestToViewNameTranslator。
总结:
1.把处理方法中的命令对象,放到model中。
2.把非处理方法的返回值,放到model中,必须注意该方法先于处理方法执行,同时其参数可以封装表单参数。
3.把处理方法的返回值,放入model中。
@SessionAttributes 绑定命令对象到session
有时候我们需要在多次请求之间保持数据,一般情况需要我们明确的调用HttpSession的API来存取会话数据,如多步骤提交的表单。
该注解有value、types两个属性,可以通过名字和类型指定要使用的attribute 对象;
@Controller
@RequestMapping("/user")
@SessionAttributes("user")
public class UserController {
@ModelAttribute("user")
public User getUser(){
User user = new User();
return user;
}
@RequestMapping(value = "/user")
public String handle1(@ModelAttribute("user") User user){
...
}
@RequestMapping(value = "/handle2")
public String handle2(ModelMap modelMap,SessionStatus sessionStatus){
...
}
}