Spring MVC

内容纲要

MVC(架构模式)

Spring MVC

  • Spring MVC是Spring体系的轻量级Web MVC框架
  • Spring MVC的核心Controller控制器,用于处理请求产生响应
  • Spring MVC基于Spring IOC容器运行,所有对象被IOC管理

    Spring 5.X 版本变化

  • Spring 5.x最低要求JDK8与J2EE 7(Servlet 3.1/Tomcat 8.5+)
  • Spring 5.x支持JDK8/9,可以使用新特性
  • Spring 5.x最重要的新特性支持响应式编程

    Spring MVC环境配置

    1. Maven依赖spring-webmvc
<repositories>
    <repository>
        <id>aliyun</id>
        <name>aliyun</name>
        <url>https://maven.aliyun.com/repository/public</url>
    </repository>
</repositories>
<dependencies>
    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-webmvc</artifactId>
        <version>5.1.9.RELRASE</version>
    </dependency>
</dependencies>
  1. web.xm|配置DispatcherServlet
<!--DispatchServlet
    DispatcherServlet是Spring MVC最核心的对象
    DispatcherServlet用于拦截Http请求, 
    并根据请求的URL调用与之对应的controller方法,来完成Ht tp请求的处理
-->
<servlet>
    <servlet-name>springmvc</servlet-name>
    <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
</servlet>
<servlet-mapping>
    <servlet-name>springmvc</servlet-name>
    <!--/代表拦截所有请求-->
    <url-pattern>/</url-pattern>
</servlet-mapping>
  1. 配置applicationContext的mvc标记
<!--
    context ;component-scan标签作用
    在Spring I0C 初始化过程中,自动创建并管理com. imooc. springmvc及子包中
    拥有以下注解的对象.
    @Repository 属于Dao 与数据发生直接交互的类
    @Service    属于Service 业务逻辑类
    @Controller 属于Spring IOC 描述Spring IOC的控制器类
    @Component  无法确定属于Dao,Service还是pring IOC 使用@Component进行说明就可以了
-->
<context:component-scan base-package="fun.afterglow.springmvc"></context:component-scan>
<!--启用Spring MVC的注解开发模式-->
<mvc:annotation-driven/>
<!--将img/Js/CSS等静态资源排除在外,可提高执行效率-->
<mvc:default-servlet-handler/>
  1. 开发Controller控制器
@Controller
public class TestController {
    //    将当前这个方法绑定某个get方式请求的URL    locallhost/t
    @GetMapping("/t")
    //   直接向响应输出字符串数据,不跳转页面
    @ResponseBody
    public String test() {
        return "Hello";
    }
}

Spring MVC处理示意图

Spring MVC数据绑定

URL Mapping(URL映射)

  • URL Mapping指将URL与Controller方法绑定
  • 通过将URL与方法绑定SpringMVC便可通过Tomcat对外暴露服务
  • 注解
  • @RequestMapping -通用绑定
  • @GetMapping -绑定Get请求
  • @PostMapping -绑定Post请求
@Controller
@RequestMapping("/um")  //放在类上面是做全局处理,为左右的路径千加相关地址
public class URLMappingController {
//    @GetMapping("/get")
//    @RequestMapping("/get") //作用在方法上,不在区分get/post请求
    @RequestMapping(value = "/get",method = RequestMethod.GET)  //设置RequestMapping的get请求与@GetMapping("/get")等价
    @ResponseBody
    public String getMapping(){
        return "getMapping";
    }
    @PostMapping("/post")
    @ResponseBody
    public String postMapping(){
        return "postMapping";
    }
}

接收请求参数

  • 使用Controller方法参数接收
//(@RequestParam("manger_name") String mangerName)作为请求中的manger_name会被动态的注解为mangerName
-------------------------------------------
<form action= "/m1" method="post" >
<input name= "username"/>
<input name= " password"/>
</form>
@PostMapping("/m1")
@ResponseBody
public String post(String username , Long password){
return username + ":" + password;
}
  • 使用Java Bean接收数据
@PostMapping("/post1")
@ResponseBody
public String postMapping1(User user){
    return user.getUsername()+":"+user.getPassword();
}

接收表单复合数据

  • 利用数组或者List接收请求中的复合数据
//数组
@PostMapping("/apply")
@ResponseBody
//@RequestParam(value = "n" ,defaultValue = "ANON")设置默认值
public String apply(@RequestParam(value = "n" ,defaultValue = "ANON") String name, String course, Integer[] purpose){
    return name+":"+course+":"+purpose[0]+":"+purpose[1]+":"+purpose[2]+":"+purpose[3];
}
//list
@PostMapping("/apply")
@ResponseBody
//@RequestParam(value = "n" ,defaultValue = "ANON")设置默认值
public String apply(@RequestParam(value = "n" ,defaultValue = "ANON") String name, String course,@RequestParam List<Integer> purpose){
    String abc="";
    for(Integer p : purpose){
        System.out.println(p);
    }
    return name+":"+course+":"+abc;
}
//对象
@PostMapping("/apply")
@ResponseBody
public String apply(Form form){
    for (Integer p : form.getPurpose()){
        System.out.println(p);
    }
    return form.getName()+":"+form.getCourse();
}
  • 利用@RequestParam为参数设置默认值
    @RequestParam(value = "n" ,defaultValue = "ANON")设置默认值
  • 使用Map对象接收请求参数及注意事项
    使用map接收数据千万不要接收复合数据,他之后接收到第一个数据,其他的都不会接收到,会导致数据丢失
@PostMapping("/apply")
@ResponseBody
public String apply(@RequestParam Map map){
    System.out.println(map);
    return "ok";
}

关联对象赋值

复杂内容表单

用户名:<input name= "username">
密码: <input name=" password">
------------------------------
姓名:<input name="name" >
身份证号: <input name="idno" >
过期时间: <input name="expire">

面向对象设计


日期类型转换

@DateTimeFormat(pattern = "yyyy-MM-dd") Date createTime 按照指定的格式将前台输入的字符串转换为Date对象
-------------------------------
private String username;
private String password;
@DateTimeFormat(pattern = "yyyy-MM-dd")
private Date createTime;

全局默认时间转换器

如果时间转换器和@DateTimeFormat同时存在,springmvc默认是使用springMVC
两个一般不要同时使用,最好是选其一

<mvc:annotation-driven conversion-service="conversionService"/>
    <!--将img/Js/CSS等静态资源排除在外,可提高执行效率-->
    <mvc:default-servlet-handler/>
    <bean id="conversionService" class="org.springframework.format.support.FormattingConversionServiceFactoryBean">
        <property name="converters">
            <set>
                <bean class="fun.afterglow.springmvc.converter.MyDateConverter"></bean>
            </set>
        </property>
    </bean>
---------------------------------------------
public class MyDateConverter implements Converter<String,Date> {
    @Override
    public Date convert(String s) {
        SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd");
        try {
            Date date = simpleDateFormat.parse(s);
            return date;
        } catch (ParseException e) {
            return null;
        }
    }
}

请求中的中文乱码

中文乱码的配置

  • Get请求乱码- server.xml增加URIEncoding属性
  • 在tomcat的server.xml文件中找到端口设置一行,在末尾加上URLEncoding = "UTF-8",8.5以后的版本默认UTF-8
  • Post请求乱码- web.xml配置CharacterEncodingFilter
<filter>
    <filter-name>characterFilter</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>characterFilter</filter-name>
    <url-pattern>/*</url-pattern>
</filter-mapping>
  • Response响应乱码- Spring配置StringHttpMessageConverter
<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 -产生响应文本
  • @ResponseBody直接产生响应体的数据,过程不涉及任何视图
  • @ResponseBody可产生标准字符串/JSON/XML等格式数据
  • @ResponseBody被StringHttpMessageConverter所影响
  • ModelAndView -利用模板引擎渲染输出
  • ModelAndView对象是指"模型(数据)与视图(界面)"对象
  • 通过ModelAndView可将包含数据对象与模板引擎进行绑定
  • SpringMVC中默认的View是JSP;也可以配置其他模板引擎

    ModelAndView

  • mav.addObject()方法设置的属性默认存放在当前请求中
  • 默认ModelAndView使用请求转发(forward)至页面
  • 重定向使用new ModelAndView("redirect:/index.jsp")
  • 当跳转页面和Controller处理关系不是很紧密的时候使用页面重定向
    在路径上尽量使用用/开头的绝对路径的JSP
@GetMapping("/view")
public ModelAndView showView(Integer userId){
    //当跳转页面和Controller处理关系不是很紧密的时候使用页面重定向
    ModelAndView modelAndView = new ModelAndView("redirect:/view.jsp");
    User user = new User();
    if(userId == 1){
        user.setUsername("张三");
    }else if (userId == 2){
        user.setUsername("李四");
    }
    modelAndView.addObject("u",user);
    return modelAndView;
}

String与ModelAndView

//Controller.方法返回string的情况
//1.方法被@ResponseBody描述, SpringMVC 直接响应String字符串本身
//2.方法不存在@ResponseBody,则Spr ingMVC处理String指代的视图(页面)
@GetMapping("/xxxx")
//    @ResponseBody
public String showViwe1(Integer userId, ModelMap modelMap) {
    String view = "/view.jsp";
    User user = new User();
    if (userId == 1) {
        user.setUsername("张三");
    } else if (userId == 2) {
        user.setUsername("李四");
    }
    modelMap.addAttribute("u", user);
    return view;
}

SpringMVC整合Freemarker

  1. pom.xml引入依赖
<dependency>
    <groupId>org.freemarker</groupId>
    <artifactId>freemarker</artifactId>
    <version>2.3.29</version>
</dependency>
<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-context-support</artifactId>
    <version>5.2.3.RELEASE</version>
</dependency>
  1. 启动Freemarker模板引擎
    <bean id="ViewResolver" class="org.springframework.web.servlet.view.freemarker.FreeMarkerViewResolver">
    <!--设置响应输出,并解决中文乱码-->
    <property name="contentType" value="text/html;charset=utf-8"></property>
    <!--指定Freemarker模板文件扩展名-->
    <property name="suffix" value=".ftl"/>
    </bean>
  2. 配置Freemarker参数
    <bean id="freemarkerConfig" class="org.springframework.web.servlet.view.freemarker.FreeMarkerConfigurer">
    <!--设置模板保存的目录-->
    <property name="templateLoaderPath" value="/WEB-INF/ftl/"/>
    <!--其他模板引擎设置-->
    <property name="freemarkerSettings">
        <props>
            <!--设置Freemarker脚本与数据渲染时使用的字符集-->
            <prop key="defaultEncofing">UTF-8</prop>
        </props>
    </property>
    </bean>
@Controller
@RequestMapping("/fm")
public class FreemarkerController {
    @GetMapping("/test")
    public ModelAndView showTest(){
        ModelAndView modelAndView = new ModelAndView("/test");
        User user = new User();
        user.setUsername("张三");
        modelAndView.addObject("u",user);
        return modelAndView;
    }
}
THE END
分享
二维码
< <上一篇
下一篇>>