SpringMVC - 03SpringMVC请求参数
(1)获取请求参数
客户端请求参数的格式是: key=value&key=value......
服务器要获取请求的参数,有时还需要进行数据的封装。SpringMVC可以接收如下类型的参数:
1.基本类型参数 2.POJO类型参数 3.数组类型参数 4.集合类型参数
(1.1)获得基本类型参数
Controller 中业务方法的参数名称要与请求参数的name一致,参数值会自动映射匹配。
@RequestMapping("/quick11") @ResponseBody public void save11(String username, int age) throws Exception { System.out.println(username); System.out.println(age); }
请求URL地址: http://localhost:8080/user/quick11?username=zzz&age=11
(1.2)获取POJO类型参数
Controller中业务方法的POJO参数的属性名与请求参数的name一致,参数自动映射匹配。
public class User { private String username; private int age; // 省略 getter/setter/toString...... } //-------------------------------------- @RequestMapping("/quick12") @ResponseBody public void save12(User user) throws Exception { System.out.println(user); }
请求URL地址: http://localhost:8080/user/quick12?username=zzz&age=11
(1.3)获取数组类型参数
@RequestMapping("/quick13") @ResponseBody public void save13(String[] strs) throws Exception { System.out.println(Arrays.asList(strs)); }
请求URL地址: http://localhost:8080/user/quick13?strs=aaa&strs=bbb&strs=vvv
(1.4)获取集合类型参数
方式一:
public class UserVO { private List<User> userList; // 省略其他代码 } //------------------------------------------ @RequestMapping("/quick14") @ResponseBody public void save14(UserVO userVO) { System.out.println(userVO); }
<%@ page contentType="text/html;charset=UTF-8" language="java" %> <html> <head> <title>Title</title> </head> <body> <form action="${pageContext.request.contextPath}/user/quick14" method="post"> <input type="text" name="userList[0].username"><br/> <input type="text" name="userList[0].age"><br/> <input type="text" name="userList[1].username"><br/> <input type="text" name="userList[1].age"><br/> <input type="submit" value="提交"> </form> </body> </html>
点击"提交"后,页面跳转到 http://localhost:8080/user/quick14。
Console打印 UserVO{userList=[User{username='zhangsan', age=19}, User{username='kk', age=132}]}
方式二:
当使用ajax提交时,可以指定contentType为json形式,那么在方法参数位置使用@RequestBody可以直接接收集合数据而无需使用POJO进行包装。
<%@ page contentType="text/html;charset=UTF-8" language="java" %> <html> <head> <title>Title</title> <script src="${pageContext.request.contextPath}/js/jquery-3.5.1.js"></script> <script> var userList = new Array(); userList.push({username:"zhangsan",age:19}); userList.push({username:"lisi",age:22}); $.ajax({ type: "POST", url: "${pageContext.request.contextPath}/user/quick15", data: JSON.stringify(userList), contentType: "application/json;charset=utf-8" }); </script> </head> <body> </body> </html>
@RequestMapping("/quick15") @ResponseBody public void save15(@RequestBody List<User> userList) { System.out.println(userList); }
请求URL地址: http://localhost:8080/ajax.jsp , 报错如下
22-Nov-2020 18:10:09.348 警告 [http-nio-8080-exec-2] org.springframework.web.servlet.DispatcherServlet.noHandlerFound No mapping found for HTTP request with URI [/js/jquery-3.5.1.js] in DispatcherServlet with name 'DispatcherServlet'
在web.xml文件中添加资源访问配置
<mvc:resources mapping="/js/**" location="/js/"/>
<mvc:default-servlet-handler/>
Console打印 [User{username='zhangsan', age=19}, User{username='lisi', age=22}]
当有新增的资源时 新增<mvc:resources mappint="/img/**" location="/img/"/>。 可以使用mvc注解统一设置。 <mvc:default-servlet-handler/>
(1.5)请求数据乱码问题
当post请求时,中文数据会出现乱码,我们可以设置一个过滤器来进行编码的过滤。
<filter> <filter-name>CharacterEncodingFilter</filter-name> <filter-class>org.springframework.web.filter.CharacterEncodingFilter</filter-class> <init-param> <param-name>encoding</param-name> <param-value>UTF-8</param-value> </init-param> </filter> <filter-mapping> <filter-name>CharacterEncodingFilter</filter-name> <url-pattern>/*</url-pattern> </filter-mapping>
(1.6)参数绑定注解@RequestParam
当请求参数名称与Controller的业务方法参数名称不一致时,就需要通过@RequestParam注解显示的绑定。
@RequestMapping("/quick16") @ResponseBody public void save16(@RequestParam(value = "name",required = false,defaultValue = "beax") String username) { System.out.println(username); }
请求URL地址: http://localhost:8080/user/quick16?name=zhangsan
> 注解@RequestParam参数:
value: 指定请求参数名称
required: 指定的请求参数是否必须包括,默认为true,提交时没有此参数则会报错
defaultValue: 当没有指定请求参数时,则使用指定的默认值赋值。
(1.7)获取Restful风格的参数
Restful是一种软件架构风格、设计风格,而不是标准,只是提供了一组设计原则和约束条件。
主要用于客户端和服务器交互类的软件,基于这个风格设计的软件可以更简洁,更有层次,更易于实现缓存机制等。
Restful风格的请求是使用 "url + 请求方式",表示一次请求目的地,HTTP协议里面四个表示操作方式的动词如下:
- GET: 用于获取资源 /user/1 GET: 得到 id=1的user
- POST: 用于新建资源 /user POST: 新增user
- PUT: 用于更新资源 /user/1 PUT: 更新id=1的user
- DELETE:用于删除资源 /user/1 DELETE: 删除id=1的user
> 获得Restful风格的参数
上述url地址/user/1中的1就是要获得的请求参数。在SpringMVC中可以使用占位符进行参数绑定。
地址/user/1可以写成/user/{id},占位符{id}对应的就是1的值。在业务方法中使用@PathVariable注解进行占位符的匹配获取工作。
@RequestMapping(value = "/quick17/{username}") @ResponseBody public void save17(@PathVariable(value = "username") String username){ System.out.println("save17 -->" + username); }
请求URL地址: http://localhost:8080/user/quick17/zhangsan17 Console打印 "save17 -->zhangsan17"。
(1.8)自定义类型转换器
SpringMVC默认已经提供了一些常用的类型转换器,例如:将客户端提交的字符串转换成int型进行参数设置。
但不是所有的数据类型都提供了转换器。没有提供的就需要自定义转换器。例如:日期类型的数据需要自定义转换器。
@RequestMapping("/quick18") @ResponseBody public void save18(Date date){ System.out.println("save18 -->" + date); }
请求URL地址: http://localhost:8080/user/quick18?date=2020/11/12 结果正常:save18 -->Thu Nov 12 00:00:00 CST 2020
请求URL地址: http://localhost:8080/user/quick18?date=2020-11-12 请求错误,需自定义类型转换器。
22-Nov-2020 18:42:40.997 璀﹀憡 [http-nio-8080-exec-4] org.springframework.web.servlet.handler.AbstractHandlerExceptionResolver.resolveException Resolved [org.springframework.web.method.annotation.MethodArgumentTypeMismatchException: Failed to convert value of type 'java.lang.String' to required type 'java.util.Date';
nested exception is org.springframework.core.convert.ConversionFailedException: Failed to convert from type [java.lang.String] to type [java.util.Date] for value '2020-11-12'; nested exception is java.lang.IllegalArgumentException]
> 定义转换器类实现Converter接口
public class DateConverter implements Converter<String, Date> { public Date convert(String dateStr){ SimpleDateFormat format = new SimpleDateFormat("yyyy-MM-dd"); Date date = null; try { date = format.parse(dateStr); } catch (ParseException e) { e.printStackTrace(); } return date; } }
> 在spring-mvc.xml配置文件中声明转换器,引入转换器
<bean id="conversionService2" class="org.springframework.context.support.ConversionServiceFactoryBean"> <property name="converters"> <list> <bean class="com.bearpx.spring.mvc.converter.DateConverter"></bean> </list> </property> </bean> // 在 annotation-driven 中引用转换器 <mvc:annotation-driven conversion-service="conversionService2"/> // 不能与<mvc:annotation-driven/>共存
请求URL地址: http://localhost:8080/user/quick18?date=2020-11-12 解析正常,但是原来的date=2020/11/12 不能解析了。
(1.9)获取请求头
> @RequestHeader
使用@RequestHeader可以获取请求头信息,相当于web阶段的request.getHeader(name)。
@RequestHeader注解的属性如下:
> value: 请求头的名称
> required: 是否必须携带此请求头
@RequestMapping("/quick19") @ResponseBody public void save19(HttpServletRequest request, HttpServletResponse response, HttpSession session){ System.out.println("save19 -->" + request); System.out.println("save19 -->" + response); System.out.println("save19 -->" + session); }
@RequestMapping("/quick20") @ResponseBody public void save20(@RequestHeader(value = "User-Agent",required = false) String user_agent){ System.out.println(user_agent); }
> @CookieValue
使用@CookieValue可以获得指定Cookie的值。
@CookieValue注解的属性如下:
> value: 指定cookie的名称
> required: 是否必须携带此cookie
@RequestMapping("/quick21") @ResponseBody public void save21(@CookieValue(value = "JSESSIONID") String jsessionId){ System.out.println(jsessionId); }