接上篇文章-SpringMVC教程1[原理分析及注解方式的使用]
一、基本操作
1.响应请求的方式
序号 | 响应方式 | 说明 |
1 | 不响应 | void+@ResponseBody注解 |
2 | ModelAndView | 通过setViewName方法 |
3 | 直接指定响应页面 | 返回值为String类型,返回结果指定跳转地址 |
4 | 重定向 | 跳转地址前加redirect:前缀即可 |
5 | HttpServletRequest 和HttpServletResponse | 形参中声明这两个变量。然后通过相关api跳转 |
1.1ModelAndView
/**
* 查询方法
* @return
*/
("/query")
public ModelAndView query(){
System.out.println("波波烤鸭:query");
ModelAndView mv = new ModelAndView();
mv.setViewName("/index.jsp");
return mv;
}1.2返回void
返回值为void时,方法中可以不用做任何返回,例如下面代码:
("/test1")
public void test1() {
System.out.println("test1");
}此时,在浏览器端请求/test1接口,springmvc会默认去查找和方法同名的页面作为方法的视图返回。 如果确实不需要该方法返回页面,可以使用@ResponseBody注解,表示一个请求到此为止。
("/test1")
public void test1() {
System.out.println("test1");
}1.3返回一个字符串
返回一个真正的字符串
/**
* 返回一个字符串
* @return
*/
("/hello")
public String hello(){
return "hello";
}![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_springmvc](https://file.cfanz.cn/uploads/png/2022/07/04/1/e9CCd8885E.png)
返回一个跳转页面名称
不需要加 @ResponseBody
/**
* 返回一个字符串
* @return
*/
("/hi")
public String hello(){
return "/index.jsp";
}![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_springmvc_02](https://file.cfanz.cn/uploads/png/2022/07/04/1/2da6Y2d97I.png)
配置视图解析器
<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"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc-4.3.xsd
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.3.xsd">
<!-- 开启注解 -->
<mvc:annotation-driven></mvc:annotation-driven>
<!-- 开启扫描 -->
<context:component-scan base-package="com.dpb.controller"></context:component-scan>
<!-- 配置视图解析器 -->
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<!-- 配置响应地址的前后缀 -->
<property name="prefix" value="/user"/>
<property name="suffix" value=".jsp"/>
</bean>
</beans>响应的代码:
/**
* 返回一个字符串
* @return
*/
("/hello")
public String hello1(){
// 视图解析器解析的时候会自动拼接上 /user 和 .jsp
return "/hello";
}![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_spring_03](https://file.cfanz.cn/uploads/png/2022/07/04/1/2857Z537K3.png)
重定向跳转
/**
* 返回一个字符串
* @return
*/
("/delete")
public String delete(){
System.out.println("波波烤鸭:删除数据操作....");
// 重定向
return "redirect:/user/query";
}
/**
*
* @return
*/
("/query")
public String query(){
System.out.println("波波烤鸭:query");
return "/hello";
}![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_springmvc_04](https://file.cfanz.cn/uploads/png/2022/07/04/1/WaN6bX9442.png)
返回路径注意: 返回的字符带"/“表示从根目录下开始找,不带”/"从当前目录下查找
1.4通过Request和Response对象处理
/**
* HttpServletRequest和HttpServletResponse的使用
* @return
* @throws IOException
*/
("/query")
public void query(HttpServletRequest request,HttpServletResponse response) throws IOException{
System.out.println("波波烤鸭:query");
System.out.println(request);
System.out.println(response);
response.sendRedirect(request.getContextPath()+"/user/hello.jsp");
}![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_mvc_05](https://file.cfanz.cn/uploads/png/2022/07/04/1/M1J9aOG572.png)
1.5 @RequestMapping的说明
- 映射路径
是个@RequestMapping最基本的功能,用法:
("/delete")
public String delete(){
System.out.println("波波烤鸭:删除数据操作....");
return "/hello";
}- 窄化请求
窄化请求用来限定请求路径,即将@RequestMapping放在类上,这样,方法的请求路径是类上的@ReqmestMapping+方法上的@RequestMapping![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_mvc_06](https://file.cfanz.cn/uploads/png/2022/07/04/1/Y2QO039U43.png)
- 请求方法限定
![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_springmvc_07](https://file.cfanz.cn/uploads/png/2022/07/04/1/f57K69b2c9.png)
![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_mvc_08](https://file.cfanz.cn/uploads/png/2022/07/04/1/2E9YU22H3X.png)
2.参数绑定
序号 | 类型 | 说明 |
1 | 基本数据类型 | 直接在形参中声明 |
2 | 简单对象 | 直接在形参中声明 |
3 | 包装对象 | 通过"."处理,比如 user.name |
4 | 集合类型 | 不能直接在形参中声明,只能在对象中使用 |
5 | 数组类型 | 可以在形参中声明,也可以在对象中使用 |
6 | Date类型 | 需要自定义转换器 |
2.1基本数据类型
Java基本数据类型+String
使用基本数据类型时,参数的名称必须和浏览器传来的参数的key一致,这样才能实现自动映射
/**
* 接收参数
* 基本数据类型
* @param id
* @param name
* @return
*/
("add")
public String add(int id,String name){
System.out.println(id+"---"+name);
return "/hello";
}![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_基本数据类型_09](https://file.cfanz.cn/uploads/png/2022/07/04/1/F8f7PG1P2Y.png)
如果参数名和浏览器传来的key不一致,可以通过@RequestParam来解决。如下
/**
* 接收参数
* 基本数据类型
* 请求参数如果和形参名称不一致可以通过@RequestParam类指定
* @param id
* @param name
* @return
*/
("add")
public String add(int id,("username")String name){
System.out.println(id+"---"+name);
return "/hello";
}![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_mvc_10](https://file.cfanz.cn/uploads/png/2022/07/04/1/98011947Qe.png)
加了@RequestParam之后,如果未重新指定参数名,则默认的参数名依然是原本的参数名。
通过也要注意,添加了@RequestParam注解后,对应的参数默认将成为必填参数。如果没有传递相关的参数,则会抛出如下异常:
![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_springmvc_11](https://file.cfanz.cn/uploads/png/2022/07/04/1/V95V9QK32Z.png)
此时,如果不想传递该参数,需要明确指定,指定方式有两种:
- 通过required属性指定该参数不是必填的
/**
* 接收参数
* 基本数据类型
* 请求参数如果和形参名称不一致可以通过@RequestParam类指定
* @param id
* @param name
* @return
*/
("add")
public String add(int id
,(value="username",required=false)String name){
System.out.println(id+"---"+name);
return "/hello";
}![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_mvc_12](https://file.cfanz.cn/uploads/png/2022/07/04/1/O695C151f1.png)
2. 通过defaultValue属性给该参数指定一个默认值
/**
* 接收参数
* 基本数据类型
* 请求参数如果和形参名称不一致可以通过@RequestParam类指定
* @param id
* @param name
* @return
*/
("add")
public String add(int id
,(value="username",defaultValue="kaoya")String name){
System.out.println(id+"---"+name);
return "/hello";
}![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_springmvc_13](https://file.cfanz.cn/uploads/png/2022/07/04/1/IJ7F2R6V70.png)
2.2对象
2.2.1简单对象
1.创建Book对象
public class Book {
private int id;
private String name;
private String author;
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getAuthor() {
return author;
}
public void setAuthor(String author) {
this.author = author;
}
}2.设置形参为Book对象接收数据
public class BookController {
/**
* 是@RequestMapping(value = "/doReg",method = RequestMethod.POST)的简写,
* 但是@PostMaping只能出现在方法上,不能出现在类上
* @param book
* @return
*/
//@RequestMapping("/add")
("/add")
public String add(Book book){
System.out.println(book);
return "/index.jsp";
}
}3.表单传递数据
<form action="/add" method="post">
<table>
<tr>
<td>编号</td>
<td><input type="text" name="id"></td>
</tr>
<tr>
<td>书名</td>
<td><input type="text" name="name"></td>
</tr>
<tr>
<td>作者</td>
<td><input type="text" name="author"></td>
</tr>
<tr>
<td><input type="submit" value="添加"></td>
</tr>
</table>
</form>![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_mvc_14](https://file.cfanz.cn/uploads/png/2022/07/04/1/GR674689NT.png)
![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_spring_15](https://file.cfanz.cn/uploads/png/2022/07/04/1/3cb99T966a.png)
2.2.2包装对象
1.book对象包含Author对象![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_mvc_16](https://file.cfanz.cn/uploads/png/2022/07/04/1/25898085YC.png)
2.表单提交数据
<form action="add" method="post">
<table>
<tr>
<td>编号</td>
<td><input type="text" name="id"></td>
</tr>
<tr>
<td>书名</td>
<td><input type="text" name="name"></td>
</tr>
<tr>
<td>作者年龄</td>
<td><input type="text" name="author.age"></td>
</tr>
<tr>
<td>作者姓名</td>
<td><input type="text" name="author.name"></td>
</tr>
<tr>
<td>作者性别</td>
<td><input type="text" name="author.sex"></td>
</tr>
<tr>
<td><input type="submit" value="添加"></td>
</tr>
</table>
</form>![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_spring_17](https://file.cfanz.cn/uploads/png/2022/07/04/1/672587QCDH.png)
3.结果![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_mvc_18](https://file.cfanz.cn/uploads/png/2022/07/04/1/756P876XS4.png)
2.3数组集合类型
- 数组
表单中直接传递多个参数:
<form action="user/doReg" method="post">
<table>
<tr>
<td>用户名</td>
<td><input type="text" name="username"></td>
</tr>
<tr>
<td>用户密码</td>
<td><input type="password" name="password"></td>
</tr>
<tr>
<td>兴趣爱好</td>
<td><input type="checkbox" name="favorites" value="zuqiu">足球
<input type="checkbox" name="favorites" value="lanqiu">篮球 <input
type="checkbox" name="favorites" value="pingpang">乒乓球</td>
</tr>
<tr>
<td><input type="submit" value="注册"></td>
</tr>
</table>
</form>("/doReg")
public String doReg(String username
,String password,String[] favorites){
System.out.println(username+"---"+password);
for (String f : favorites) {
System.out.println(f);
}
return "/index.jsp";
}![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_基本数据类型_19](https://file.cfanz.cn/uploads/png/2022/07/04/1/4T5fP7Q2YP.png)
![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_基本数据类型_20](https://file.cfanz.cn/uploads/png/2022/07/04/1/2R12fDf4Ja.png)
这里的参数类型,只能使用数组,不能使用集合。如果非要用集合,可以自定义参数类型转换。
2.集合
除了自定义参数类型转换,如果想要使用集合去接收参数,也可以将集合放到一个包装类中。
public class User {
private String username;
private String password;
private List<String> favorites;
public String toString() {
return "User{" + "username='" + username + '\'' + ", password='" + password + '\'' + ", favorites=" + favorites
+ '}';
}
public String getUsername() {
return username;
}
public void setUsername(String username) {
this.username = username;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
public List<String> getFavorites() {
return favorites;
}
public void setFavorites(List<String> favorites) {
this.favorites = favorites;
}
}![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_spring_21](https://file.cfanz.cn/uploads/png/2022/07/04/1/K275e2E0Z3.png)
这样,集合中也能收到传递来的参数。
总结:
1.数组(无论是基本数据类型还是对象数组)都可以直接写在接口参数中。
2.集合(无论是基本数据类型还是对象)都需要一个包装类将其包装起来,不能直接写在接口参数中。
3.对于基本数据类型,数组和集合在表单中的写法是一样的
4.对于对象数据类型,数组和集合在表单中的写法是一样的
2.4Date类型
接收数据类型是Date类型的需要通过转换器进行接收
("/update")
public String update(Date d){
System.out.println(d);
return "/index.jsp";
}如果不转换直接访问提交会爆400错误![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_springmvc_23](https://file.cfanz.cn/uploads/png/2022/07/04/1/0bc897NF97.png)
创建自定义的转换器
/**
* 自定义转换器
*
* @author dpb【波波烤鸭】
*
*/
public class DateConvert implements Converter<String,Date>{
public Date convert(String msg) {
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
try {
return sdf.parse(msg);
} catch (ParseException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return null;
}
}配置转换器
<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"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc-4.3.xsd
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.3.xsd">
<!-- 开启注解 -->
<mvc:annotation-driven conversion-service="formattingConversionServiceFactoryBean"></mvc:annotation-driven>
<!-- 开启扫描 -->
<context:component-scan base-package="com.dpb.controller"></context:component-scan>
<!-- 配置视图解析器 -->
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<!-- 配置响应地址的前后缀
<property name="prefix" value="/user"/>
<property name="suffix" value=".jsp"/>-->
</bean>
<!-- 配置转换器 -->
<bean id="formattingConversionServiceFactoryBean"
class="org.springframework.format.support.FormattingConversionServiceFactoryBean">
<property name="converters">
<set>
<bean class="com.dpb.convert.DateConvert"/>
</set>
</property>
</bean>
</beans>![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_mvc_24](https://file.cfanz.cn/uploads/png/2022/07/04/1/CU9B85c9T8.png)
![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_spring_25](https://file.cfanz.cn/uploads/png/2022/07/04/1/5B8F6d9794.png)
3.响应数据
3.1ModelAndView
3.2HttpServletRequest
3.3HttpSession
3.4Map
("/query1")
public String query1(Map<String,Object> map){
map.put("msg", "map --> value");
return "/index.jsp";
}![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_mvc_26](https://file.cfanz.cn/uploads/png/2022/07/04/1/312CO1e2ff.png)
![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_springmvc_27](https://file.cfanz.cn/uploads/png/2022/07/04/1/58c33498HW.png)
3.5Model
("/query2")
public String query2(Model model){
model.addAttribute("msg", "model --> value");
return "/index.jsp";
}![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_spring_28](https://file.cfanz.cn/uploads/png/2022/07/04/1/L576ff7f6O.png)
3.6ModelMap
("/query3")
public String query3(ModelMap mm){
mm.addAttribute("msg", "modelMap --> value");
return "/index.jsp";
}![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_mvc_29](https://file.cfanz.cn/uploads/png/2022/07/04/1/I0d6He387a.png)
注意:@SessionAttributes将数据保存在session作用域中,上面几个传值都是request作用域![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_springmvc_30](https://file.cfanz.cn/uploads/png/2022/07/04/1/dWdYM8c749.png)
![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_springmvc_31](https://file.cfanz.cn/uploads/png/2022/07/04/1/771763R9L7.png)
![在这里插入图片描述 SpringMVC教程2[处理及响应请求]_mvc_32](https://file.cfanz.cn/uploads/png/2022/07/04/1/I01861AY98.png)
4.post方式中文乱码问题处理
在web.xml文件中添加如下代码即可
<!-- spring框架提供的字符集过滤器 -->
<!-- spring Web MVC框架提供了org.springframework.web.filter.CharacterEncodingFilter用于解决POST方式造成的中文乱码问题 -->
<filter>
<filter-name>encodingFilter</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>encodingFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
