<!--springmvc config-->
<!-- 包扫描 -->
<context:component-scan base-package="com.stan.hello"/>
<!-- 静态资源处理 -->
<mvc:default-servlet-handler />
<!-- springmvc 注解驱动 -->
<mvc:annotation-driven />
<!-- 配置视图解析器 -->
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver"
id="internalResourceViewResolver">
<property name="prefix" value="/WEB-INF/jsp/" />
<property name="suffix" value=".jsp" />
</bean>
二、注解开发
1、@requestMapping 注解
- 可以用在方法和类上,起到窄化请求的作用;
- 其中的属性还包含 method、param 和 header,都是更加精确请求的作用;
- @PathVariable 注解指定 url 占位符(/hello/{name})和方法参数之间的映射;
2、参数相关注解
(1)@RequestParam注解
- 作用就是将请求参数映射到方法参数;
- 注解有三个属性:value(请求参数的名字)、required(默认为true)、defaultValue(请参的默认值);
- 请求参数名称和方法参数名称相同的时候不用设置value的值即可完成映射,不同的时候要设置 value 的值为请求参数的名称;
- @RequestHeader 和 @CookieValue 注解:作用就是将请求头和cookie 的信息映射到方法的参数;注解的属性和用法都和requestParam 差不多;
(2)请求参数映射到 pojo
- 保证请求参数的名字和 pojo 的属性名一致即可自动完成映射,还支持级联属性;
- 名字不一则无法映射,相应的值为 null;
(3)方法参数还支持 servlet 的原生 API,支持的类型包括:
- request、response、session、Principal
- InputStream、outputStream、reader、writer
3、目标方法 pojo 类型入参过程
(1)@ModelAttribute注解:
- 这个注解标记的方法会在每个目标方法执行前被执行;
- 修饰目标方法参数:指定 pojo 的键名;
(2)pojo 入参过程
- key 和 pojo 保存在 implicitModel 中,进而保存到 request 中;
- 第一步先去 implicitModel(map) 中去找,用默认的键名去匹配(类名首字母小写),当然也可以用 @ModelAttribute 指定键名去匹配,找到了就入参;
- implicitModel 中的 pojo 对象来源于 @ModelAttribute 修饰的方法中存入到 map 中的 pojo 对象;
- implicitModel 中找不到,当前的 Controller 又用了 @SessionAttributes 注解进行修饰的话,就去 session 中根据相应的键名去匹配,找到入参,没有则抛出异常;
- 如果没有@SessionAttributes 或者键值不包括在注解的值里面的话,则会通过反射来创建一个新的 pojo 对象作为方法入参;
- 总结:键名-----implicitModel ------session-------(反射生成新对象)-------对象属性设置为相应的请求参数的值-------赋值给目标方法的参数
(3)使用@sessionAttributes 注解抛出异常的解决方法
- sessionAttributes 中的名称和方法参数 modelAttribute 中指定的名称不一致即可;
- 要么就是必须得有modelAttribute 标记的方法,保证能够取到sessionAttributes 名称对应的对象就不会抛异常;
- 干脆不用这个注解也可以;
4、模型数据处理
4.1 方法可以添加Map 或者 Model 类型的参数
4.2 方法返回 ModelAndView
- mv 可以包含视图和模型的信息;
- 最终这些数据都是存放到 request 域中;
4.3 再说 @sessionAttributes
- 注解的作用:就是将 request 域中的模型数据备份一份到 session,方便不同的请求之间共享;
- 使用时注意:这个注解是类注解,不能修饰方法;既可通过名称也可通过类型指定放到 session 中的数据(@SessionAttributes(value={"names"},types={Integer.class}));
- 示例请参考:https://www.cnblogs.com/caoyc/p/5635914.html
5、视图解析
5.1 视图解析流程
- 目标方法无论返回的是 string、model还是 mv,最终都是包装成 modelAndView返回;
- 视图的作用:渲染模型数据;
- 视图解析器的作用:将逻辑视图转换为物理视图;
- 常用的视图解析器:BeanNameViewResolver 和 InternalResourceViewResolver;配置多个解析器的话存在优先级的;
5.2 自定义视图和重定向
- 自定义视图:实现view 接口,重写 render 方法;最后还要在 springmvc 的配置文件中配置beanNameViewresolver,注意解析器的优先级;
- 转发和重定向:就是在 return 的 String 中加入前缀 forward: 或者 redirect:
- view-controller 标签:view-controller 可实现直接将请求跳转到视图,不用经过 controller;
三、RESTful风格CRUD
1、CRUD 示例
- 新增:/order post
- 删除:/order/1 delete
- 修改:/order/1 put
- 查询:/order/1 get
2、发送 put | delete 请求
- web xml 中配置 HiddenhttpMethodFilter;
- 表单中增加一个 name=_method value=delete 或 put 的隐藏域,发送 post 请求;
- a 标签的 get 请求转 post ,js中用return false 阻止 a 标签默认行为,再通过 ajax 发送一个 post 请求即可;
3、表单标签|静态资源映射配置
3.1 spring 表单标签
- 自带数据的回显功能;
- 数据回显的前提是 form 的commandName属性的值要和 request 域中存放的 pojo 对象的键值一致;
- 还支持级联属性的写法;
<form:form action="/mvc/rest/user" method="post" commandName="user">
编号:<form:input path="id"/><br>
姓名:<form:input path="name"/><br>
余额:<form:input path="balance"/><br>
<input type="submit" value="提交">
</form:form>
<!-- 如果request中取不到 user ,则会报异常,需要在之前手动加一个 user 进去 -->
3.2 静态资源映射配置
<mvc:default-servlet-handler></mvc:default-servlet-handler>
<mvc:annotation-driven></mvc:annotation-driven>
4、关于转发和重定向
- controller 方法里 return String 默认是作为逻辑视图,要进行 controller 间的转发或者重定向要在前面加上 forward 和 redirect;
- 关于转发和重定向的路径问题:绝对路径(/)默认就是在当前的项目下,相对路径是在当前的controller 内;
四、数据处理
1、数据绑定(DataBinder)
(1)基本流程
(2)数据转换:springmvc 内置了很多类型转换器,一般情况下不需要我们自己写;
(3)自定义类型转换器
- 第一步:实现 Converter<S,T>接口,重写方法实现想要的类型转换;
- 第二步:在 spring 的 ioc 容器中配置convertionService;
- 第三步:mvc:annotion-driven注解中配置convertionService,将这个注册到 springmvc 的上下文中;