Spring MVC
- Spring MVC是Spring体系的轻量级Web MVC框架
- Spring MVC的核心Controller控制器,用于处理请求,产生响应
- Spring MVC基于Spring IOC容器运行,所有对象被IOC管理
环境配置
- Maven依赖:
spring-webmvc
- web.xml配置DispatcherServlet
- 配置applicationContext的mvc标记
- 开发Controller控制器
<!--引入Spring MVC-->
<dependencies>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>5.3.22</version>
</dependency>
</dependencies>
代码语言:javascript复制<!--DispatchServlet:对所有请求进行拦截-->
<servlet>
<servlet-name>springmvc</servlet-name>
<!--
DispatcherServlet是Spring MVC最核心的对象
DispatcherServlet用于拦截Http请求,
并根据请求的URL调用与之对应Controller方法,来完成Http请求的处理
-->
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<!--applicationContext.xml-->
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:applicationContext.xml</param-value>
</init-param>
<!--在Web应用启动时自动创建Spring IOC容器,并初始化DispatcherServlet-->
<load-on-startup>0</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>springmvc</servlet-name>
<!--“/”拦截所有请求-->
<url-pattern>/</url-pattern>
</servlet-mapping>
代码语言:javascript复制<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:mvc="http://www.springframework.org/schema/mvc"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:mv="http://www.springframework.org/schema/mvc"
xsi:schemaLocation="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.xsd
http://www.springframework.org/schema/mvc
http://www.springframework.org/schema/mvc/spring-mvc.xsd">
<!--
context:component-scan 标签作用
在Spring IOC初始化过程中,自动创建并管理com.hua.springmvc及子包中
拥有以下注解的对象.
@Repository 语义注解,说明当前类用于业务持久层,通长描述对应的Dao类
@Service 语义注解,说明当前类是Service业务服务类
@Controller 语义注解,说明当前类是MVC应用中的控制器类
@Component 组件注解,通常注解,被该注解描述的类将被IoC容器管理并实现
-->
<context:component-scan base-package="com.hua.springmvc"/>
<!--启用Spring MVC注解开发模式-->
<mvc:annotation-driven/>
<!--将图片/JS/CSS等静态资源排除在外,可提高执行效率-->
<mvc:default-servlet-handler/>
</beans>
注解 | 用途 |
---|---|
@GetMapping | 将当前方法绑定某个Get请求方式的URL |
@ResponseBody | 直接向响应输出字符串数据,不跳转页面 |
数据绑定
URL Mapping
- 将URL与Controller方法绑定
- 同过URL与方法绑定,SpringMVC便可通过Tomcat对外暴露服务
注解
@RequestMapping
- 通用绑定@GetMapping
- 绑定Get请求@PostMapping
- 绑定Post请求
接受请求参数
代码语言:javascript复制@Controller
@RequestMapping("/um") //定义类下所有方法的访问前缀
public class URLMappingController {
@GetMapping("/g")
//用用在方法上,不再区分Get/Post请求
//@RequestMapping(value = "/g", method = RequestMethod.GET)
@ResponseBody
//@RequestParam 专用于特殊描述的参数,要书写在参数之前。同时增加映射原始请求参数
public String getMapping(@RequestParam("manager_name")String managerName) {
System.out.println("manager_name:" managerName);
return "This is Get method";
}
@PostMapping("/p")
@ResponseBody
public String postMapping(String username, String password) {
System.out.println(username ":" password);
return "This is Post method";
}
@PostMapping("/p1")
@ResponseBody
public String PostMapping1(User user) {
System.out.println(user.getUsername() ":" user.getPassword());
return "This is Post method";
}
}
接收表单复合数据
- 如果要接受复合数据可以使用数组、LIst和Map接收,List集合接收数据是需要添加
@RequestParam
声明,Map接受符合数据会出现数据丢失的情况
@Controller
public class FormController {
// @PostMapping("/apply")
@ResponseBody
// 当值参数名n不存在的时候返回默认值ANON
public String Apply(@RequestParam(value = "n",defaultValue = "ANON") String name, String course, Integer[] purpose) {
System.out.println(name);
System.out.println(course);
for (Integer p : purpose) {
System.out.println(p);
}
return "success";
}
// @PostMapping("/apply")
@ResponseBody
// 使用List接收符合数据需要在参数前添加 @RequestParam 声明
public String Apply(String name, String course, @RequestParam List<Integer> purpose) {
System.out.println(name);
System.out.println(course);
for (Integer p : purpose) {
System.out.println(p);
}
return "success";
}
// @PostMapping("/apply")
@ResponseBody
public String Apply(Form form) {
return "success";
}
@PostMapping("/apply")
@ResponseBody
//使用Map接受复合数据会出现数据丢失
public String Apply(@RequestParam Map map) {
return "success";
}
}
关联对象赋值
在参数名称前加上对象
日期类型转换
@DateTimeFormat注解
用于表示日期转换与 SimpleDataFormat
相似
public String postMapping(String username, String password,@DateTimeFormat(pattern = "yyyy-MM-dd") Date createtime) {
System.out.println(username ":" password);
return "This is Post method";
}
实体类转换日期
这里也需要添加 @DateTimeFormat
代码语言:javascript复制@DateTimeFormat(pattern = "yyyy-MM-dd")
private Date createtime;
设置全局日期转换类
继承Converter接口,设置泛型<传入参数(K), 转换后的参数(V)>
代码语言:javascript复制public class MyDateConverter implements Converter<String, Date> {
public Date convert(String s) {
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
try {
Date d = sdf.parse(s);
return d;
} catch (ParseException e) {
return null;
}
}
}
代码语言:javascript复制<!--在这里额外添加属性 conversion-service="conversionService"-->
<mvc:annotation-driven conversion-service="conversionService"/>
<!-- 将前台传进的日期进行转换 -->
<bean id="conversionService" class="org.springframework.format.support.FormattingConversionServiceFactoryBean">
<property name="converters">
<set>
<bean class="com.hua.springmvc.converter.MyDateConverter"/>
</set>
</property>
</bean>
优先级问题
通常有全局转换器存在会优先选择转换器进行日期转换,没有转换器使用注解转换
中文乱码
- Get请求乱码 - server.xml增加
URIEncoding
属性 - Post请求乱码 - web.xml配置
CharacterEncodingFilter
- Response响应乱码 - Spring配置
StringHttpMessageConverter
Get请求乱码
打开 Tomcat/conf/server.xml
添加 URIEncoding="UTF-8"
Post请求乱码
代码语言:javascript复制<!--过滤器-->
<filter>
<filter-name>characterFilter</filter-name>
<!--将Post请求中的ISO-8859-1转换为UTF-8-->
<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>characterFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
Response响应乱码
代码语言:javascript复制<mvc:annotation-driven conversion-service="conversionService">
<!--设置消息转换器-->
<mvc:message-converters>
<!--进行文本消息转换-->
<bean class="org.springframework.http.converter.StringHttpMessageConverter">
<!--支持的媒体类型-->
<property name="supportedMediaTypes">
<list>
<!--response.setContentType("text/html;charset=utf-8")-->
<value>text/html;charset=utf-8</value>
</list>
</property>
</bean>
</mvc:message-converters>
</mvc:annotation-driven>
响应输出结果
@ResponseBody
- 产生响应文本ModelAndView
- 利用模板引擎渲染输出
@ResponseBody
- 直接产生响应体的数据,过程不干涉任何视图
- 可产生标准的字符串/JSON/XML等格式数据
- 产生的字符串被
StringHttpMessageConverter
影响
ModelAndView
代码语言:javascript复制指"模型(数据)"与"视图(界面)"对象 通过
ModelAndView
可将包含数据对象与引擎进行绑定 SpringMVC中默认的View是JSP,也可以配置其他模板引擎
@GetMapping("/view")
public ModelAndView showView() {
ModelAndView mav = new ModelAndView();
return mav;
}
mav.addObject()
方法设置的属性默认存放在当前请求中- 默认
ModelAndView
使用请求转发(forward)至页面 - 重定向使用new ModelAndView("redirect:/index.jsp")
String与ModelMap实现类似功能
代码语言:javascript复制//String与ModelMap
//Controller方法返回String的情况
//1. 方法被@ResponseBody描述,SpringMVC直接响应String字符串本身
//2. 方法不存在@ResponseBody,则SpringMVC处理String指代的视图(页面)
@GetMapping("/xxxx")
// @ResponseBody
public String showView1(Integer userId , ModelMap modelMap){
String view = "/um/view.jsp";
User user = new User();
if(userId == 1){
user.setUsername("lily");
}else if(userId == 2){
user.setUsername("smith");
}else if(userId == 3){
user.setUsername("lina");
}
modelMap.addAttribute("u", user);
return view;
}
SpringMVC整合Freemarker
1-引入依赖
代码语言:javascript复制<dependencies>
<dependency>
<groupId>org.freemarker</groupId>
<artifactId>freemarker</artifactId>
<version>2.3.28</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context-support</artifactId>
<version>5.1.9.RELEASE</version>
</dependency>
</dependencies>
2-启用Freemarker模板引擎
代码语言:javascript复制<bean id="ViewResolver" class="org.springframework.web.servlet.view.freemarker.FreeMarkerViewResolver">
<!--设置响应体输出,解决响应体中文乱码问题-->
<property name="contentType" value="text/html;charset=utf-8"/>
<!--指定Freemarker模板文件扩展名-->
<property name="suffix" value=".ftl"/>
</bean>
3-通知Freemarker文件在哪
代码语言:javascript复制<bean id="freemarkerConfig" class="org.springframework.web.servlet.view.freemarker.FreeMarkerConfigurer">
<!--定义Freemarker存放地址-->
<property name="templateLoaderPath" value="/WEB-INF/ftl"/>
<!--模板在渲染过程中的中文乱码问题-->
<property name="freemarkerSettings">
<props><prop key="defaultEncoding">UTF-8</prop></props>
</property>
</bean>