9.框架SpringMVC

一、基本概念

        Spring MVC 是 Spring 提供的一个基于 MVC 设计模式的轻量级 Web 开发框架,本质上相当于 Servlet。Spring MVC 使用 MVC 架构模式的思想,将 Web 应用进行职责解构,把一个复杂的 Web 应用划分成模型(Model)、控制器(Contorller)以及视图(View)三层,有效地简化了 Web 应用的开发,降低了出错风险,同时也方便了开发人员之间的分工配合。

        导入依赖:

<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-webmvc</artifactId>
    <version>5.3.22</version>
</dependency>

二、工作流程

        Spring MVC工作流程如下:

        Spring MVC 的常用组件共有 6 个,它们分别是: DispatcherServlet(前端控制器)、HandlerMapping(处理器映射器)、HandlerAdapter(处理器适配器)、Handler(处理器)、ViewResolver(视图解析器)和 View(视图)。下表对各个组件的功能说明如下:

组件提供者说明
DispatcherServlet(前端控制器)由框架提供它是 Spring MVC 的核心,其本质就是一个 Servlet。
它负责将所有的请求进行统一分发,相当于一个 Spring MVC 的流程控制中心,控制整个流程的执行,对各个组件进行统一调度,以降低组件之间的耦合性,有利于组件之间的拓展。
HandlerMapping(处理器映射器)由框架提供负责根据请求的 url、method 等信息查找响应的 Handler 处理器(即 Controller 控制器方法)。
Handler(处理器)由开发人员提供也就是我们常说的 Controller 控制器,负责在 DispatcherServlet 的控制下,对具体的用户请求进行处理。
HandlerAdapter(处理器适配器)由框架提供它负责根据 HandlerMapping 映射器找到的处理器(Handler)信息,按照特定规则执行相关的处理器(Handler)方法。
ViewResolver(视图解析器)由框架提供通过 ModelAndView 对象中的 View 信息对逻辑视图名进行解析,将其解析成真正的视图 View(例如 ThymeleafView、InternalResourceView、RedirectView 等),并返回给 DispatcherServlet。
View(视图)View 对象本身由框架提供,但视图所对应的前端页面(例如 JSP、HTML)则需要开发人员自行编写将 Model 模型数据通过页面展示给用户。

 三、Servlet配置类

        Spring MVC 本质就是对 Servlet 的进一步封装,其核心组件是一个 DispatcherServelt。DispatcherServelt 是 Spring MVC 中请求最先到达的地方,负责请求在其他各个组件间的传递和加工。在此之前,像 DispatcherServlet 这样的 Servlet,都是通过 web.xml 文件来进行配置的。

        Spring 提供了一个 DispatcherServelt 的快速配置类AbstractAnnotationConfigDispatcher-ServletInitializer,它就是 WebApplicationInitializer 的实现类之一 ,其常用方法如下表。

方法说明
protected abstract Class<?>[] getRootConfigClasses();该方法用于设置 Spring 的配置类。
protected abstract Class<?>[] getServletConfigClasses();该方法用于设置 Spring MVC 的配置类。
 protected abstract String[] getServletMappings();该方法用于指定 DispatcherServelt 的映射规则,即 web.xml 中的 url-pattern。
protected Filter[] getServletFilters() 该方法用于添加各种过滤器(filter)。

        如果我们自定义的初始化类继承了 AbstractAnnotationConfigDispatcherServletInitializer 并将其部署到 Servlet 容器中,Servelt 容器会自动加载这个初始化类,并使用它来完成对 DispatcherServlet 和 Spring MVC 的配置工作。

//继承加载 springMVC前端控制器 和 web容器加载监听器
public class WebConfig extends AbstractAnnotationConfigDispatcherServletInitializer {

    //加载spring配置
    @Override
    protected Class<?>[] getRootConfigClasses() {
        return new Class []{SpringConfig.class};
    }
    //加载springMVC配置
    @Override
    protected Class<?>[] getServletConfigClasses() {
        return new Class[]{SpringMVCConfig.class};
    }
    //为dispatcherServlet设置请求路径
    @Override
    protected String[] getServletMappings() {
        return new String[]{"/"};
    }
    //添加请求和响应过滤器
    @Override
    protected Filter[] getServletFilters() {
        return null;
    }
}

四、SpringMVC配置类 

        我们可以通过一个实现了 WebMvcConfigurer 接口的配置类(标注 @Configuration 的类)对 Spring MVC 的部分组件进行配置,例如拦截器、格式化程序、视图控制器等。

方法说明
default void configureDefaultServletHandling(DefaultServletHandlerConfigurer configurer) {}将静态文件交给 Servlet 容器(Tomcat)内置的默认 Servlet 处理。
default void addInterceptors(InterceptorRegistry registry) {}添加 Spring MVC 拦截器,对请求进行拦截处理。
default void addResourceHandlers(ResourceHandlerRegistry registry) {}添加或修改静态资源(例如图片,js,css 等)映射;
Spring Boot 默认设置的静态资源文件夹就是通过重写该方法设置的。
default void addViewControllers(ViewControllerRegistry registry) {}主要用于实现无业务逻辑跳转,例如主页跳转,简单的请求重定向,错误页跳转等
default void configureMessageConverters(List<HttpMessageConverter<?>> converters) {}用于配置默认的消息转换器(转换 HTTP 请求和响应)。
default void extendMessageConverters(List<HttpMessageConverter<?>> converters) {}直接添加消息转换器,会关闭默认的消息转换器列表;
实现该方法即可在不关闭默认转换器的起提下,新增一个自定义转换器。
default void configureHandlerExceptionResolvers(List<HandlerExceptionResolver> resolvers) {}配置异常解析器。
//核心配置类
@Configuration
//SpringMVC注解扫描
@ComponentScan("com.lulu.controller")
//开启注解驱动
// <mvc:annotation-driven> 会自动向 Spring MVC 中注册
// RequestMappingHandlerMapping RequestMappingHandlerAdapter 以及 ExceptionHandlerExceptionResolver 三个Bean
// 其中 RequestMappingHandlerMapping 和 RequestMappingHandlerAdapter 都是控制器方法对请求进行分发的必须组件,为读写 JSON 数据提供支持
// 而 ExceptionHandlerExceptionResolver 则是 Spring MVC 的异常处理组件
// 除此之外 <mvc:annotation-driven> 标签还默认注册了一个 FormattingConversionServiceFactoryBean类型的Bean
// ConversionService 通过它,可以满足我们大多数的类型转换需求
@EnableWebMvc
public class SpringMVCConfig implements WebMvcConfigurer {}

 五、Controller

        DispatcherServlet 会拦截用户发送来的所有请求进行统一处理,但不同的请求有着不同的处理过程,例如登陆请求和注册请求就分别对应着登陆过程和注册过程,因此我们需要 Controller 来对不同的请求进行不同的处理。

@Controller//声明为controller
@RequestMapping("")//在类和方法上设置请求映射

         获取请求参数:

@RequestParam("")//在方法参数上设置参数映射,参数名相同可省略
@PathVariable("")//将请求路径以{}包括可通过该注解传递到参数上
@RequestBody//该注解将json字符串参数转换为对象

        获取cookie和session:

@CookieValue("")
@SessionAttribute("")

         转发与重定向:

//转发
//1.直接返回以forward:开头的转发路径字符串
//2.通过ModelAndView.setViewName("")设置1中的转发路径

//重定向
//1.直接返回以redirect:开头的重定向路径字符串
//2.通过ModelAndView.setViewName("")设置1中的重定向路径

          响应数据:

//方法返回字符串时,会默认进行请求转发,配置视图解析器后会进行页面跳转
//方法返回对象时,需要声明以下注解,对象会被解析为json字符串返回
@ResponseBody

//注意!当控制器方法的返回类型为void时,会把RequestMapping中指定的映射路径作为逻辑视图名称然后解 //析为物理地址去访问。此时,可以通过在void方法上声明HttpServletResponse对象避免解析

        共享数据:

//使用ModelAndView向request域对象中共享数据,ModelAndView主要由 model(模型)和 view(视图)两 
//部分组成;其中,model负责数据共享,而view则主要用于设置视图,实现页面跳转,转发,重定向
public ModelAndView share(){
    ModelAndView mv=new ModelAndView();
    mv.addObject("",new Object());
    mv.setViewName("");
    return mv;
}

//使用Model向request域对象中共享数据
@GetMapping("/share")
public String share(Model model){
    model.addAttribute("book",new Book());
    return "";
}


//此外还可以在方法上声明HttpServletRequest向request域对象中共享数据,
//声明HttpSession向sesion域对象中共享数据,
//通过两者获取ServletContext对象可以向application域对象中共享数据,
//其他方法通过声明域对象参数即可获取共享数据

六、RESTful

        RESTful(REST 风格)是一种当前比较流行的互联网软件架构模式,它充分并正确地利用 HTTP 协议的特性,为我们规定了一套统一的资源获取方式,以实现不同终端之间(客户端与服务端)的数据访问与交互。

 

七、配置组件

        类型转换器:一般情况下,Spring MVC 内置的类型转换器就可以满足我们日常的开发需求,但对于一些较为复杂类型的转换,例如 String 转换 Date 类型,以及开发人员自定义格式的数据的转换等,需要我们根据自身的需求开发自定义类型转换器来转换。

public class MyConverter implements Converter<String,String> {
    @Override
    public String convert(String s) {
        return null;
    }
}

        拦截器:在 Spring MVC 中,拦截器的作用与 Servlet 中的过滤器类似,它主要用于拦截用户请求并做相应的处理,例如通过拦截器,我们可以执行权限验证、记录请求信息日志、判断用户是否已登录等操作。

public class MyInterceptor implements HandlerInterceptor {
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        return HandlerInterceptor.super.preHandle(request, response, handler);
    }

    @Override
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
        HandlerInterceptor.super.postHandle(request, response, handler, modelAndView);
    }

    @Override
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
        HandlerInterceptor.super.afterCompletion(request, response, handler, ex);
    }

}

        视图解析器:Spring MVC 的控制器方法支持 ModelAndView、ModelMap、View、String 多种类型的返回值,但无论控制器方法的返回值是哪种类型,Spring MVC 内部最终都会将它们封装成一个 ModelAndView 对象。ModelAndView 对象由 model(模型数据)和 view(视图)两部分组成,但这里的 view 通常并不是一个真正的 View 视图对象,而仅仅是一个 String 类型的逻辑视图名(View Name)而已,例如“success”、“index”等。这种情况下,Spring MVC 就需要借助 ViewResolver(视图解析器)将 ModelAndView 对象中逻辑视图名解析为真正的 View 视图对象,然后才能响应给客户端展示。

        异常处理器:Spring MVC 提供了一个名为 HandlerExceptionResolver 的异常处理器接口,它可以对控制器方法执行过程中出现的各种异常进行处理。Srping MVC 为 HandlerException- Resolver 接口提供了多个不同的实现类,其中最常用的实现类如下。

  • DefaultHandlerExceptionResolver
  • ResponseStatusExceptionResolver
  • ExceptionHandlerExceptionResolver
  • SimpleMappingExceptionResolver

        其中,ExceptionHandlerExceptionResolver、ResponseStatusExceptionResolver 和 DefaultHandlerExceptionResolver 是 Spring MVC 的默认异常处理器。如果程序发生异常,Spring MVC 会按照 ExceptionHandlerExceptionResolver → ResponseStatusExceptionResolver → DefaultHandlerExceptionResolver 的顺序,依次使用这三个异常处理器对异常进行解析,直到完成对异常的解析工作为止。

        文件上传解析器:Spring MVC 提供了一个名为 MultipartResolver 的文件解析器,来实现文件上传功能。MultipartResolver 本身是一个接口,该接口共有两个实现类:StandardServlet- MultipartResolver 和 CommonsMultipartResolver 。注意:当我们在 Spring MVC 的配置文件中对 CommonsMultipartResolver 的 Bean 进行定义时,必须指定这个 Bean 的 id为 multipart- Resolver,否则就无法完成文件的解析和上传工作。

        Spring MVC 主要配置如下:

//核心配置类
@Configuration
//springMVC注解扫描
@ComponentScan({"web.controller"})
//开启注解驱动
// <mvc:annotation-driven> 会自动向 Spring MVC 中注册
// RequestMappingHandlerMapping RequestMappingHandlerAdapter 以及 ExceptionHandlerExceptionResolver 三个Bean
// 其中 RequestMappingHandlerMapping 和 RequestMappingHandlerAdapter 都是控制器方法对请求进行分发的必须组件,为读写 JSON 数据提供支持
// 而 ExceptionHandlerExceptionResolver 则是 Spring MVC 的异常处理组件
// 除此之外 <mvc:annotation-driven> 标签还默认注册了一个 FormattingConversionServiceFactoryBean类型的Bean
// ConversionService 通过它,可以满足我们大多数的类型转换需求
@EnableWebMvc
public class SpringMVCConfig implements WebMvcConfigurer {
    //视图解析器解析视图后需要在应用内部访问静态资源,
    //这时请求路径无需进行映射,DispatcherServlet找不到该映射,会交给Tomcat提供的默认的servlet处理
    @Override
    public void configureDefaultServletHandling(DefaultServletHandlerConfigurer configurer) {
        configurer.enable();
    }
    //配置类型转换器和格式化器(输入数据转换为对象)
    @Override
    public void addFormatters(FormatterRegistry registry) {
        WebMvcConfigurer.super.addFormatters(registry);
    }
    //配置拦截器
    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        WebMvcConfigurer.super.addInterceptors(registry);
    }
    //配置视图控制器(直接进行页面跳转)
    @Override
    public void addViewControllers(ViewControllerRegistry registry) {
        registry.addViewController("/index").setViewName("index");
        registry.addViewController("/error").setViewName("error");
    }
    //配置视图解析器(解析逻辑视图并返回)
    @Override
    public void configureViewResolvers(ViewResolverRegistry registry) {
        InternalResourceViewResolver viewResolver =new InternalResourceViewResolver();
        viewResolver.setPrefix("/WEB-INF/page/");
        viewResolver.setSuffix(".html");
        registry.viewResolver(viewResolver);
    }
    //配置默认异常处理器
    @Override
    public void configureHandlerExceptionResolvers(List<HandlerExceptionResolver> resolvers) {
        WebMvcConfigurer.super.configureHandlerExceptionResolvers(resolvers);
    }
    //配置文件上传解析器
    @Bean
    public MultipartResolver multipartResolver(){
        CommonsMultipartResolver resolver=new CommonsMultipartResolver();
        resolver.setDefaultEncoding("utf-8");
        resolver.setMaxUploadSize(1024);
        return resolver;
    }
    //配置静态资源访问映射
    @Override
    public void addResourceHandlers(ResourceHandlerRegistry registry) {
        WebMvcConfigurer.super.addResourceHandlers(registry);
    }
    //配置默认响应信息转换器
    @Override
    public void configureMessageConverters(List<HttpMessageConverter<?>> converters) {
        WebMvcConfigurer.super.configureMessageConverters(converters);
    }
    //处理跨域
    @Override
    public void addCorsMappings(CorsRegistry registry) {
        WebMvcConfigurer.super.addCorsMappings(registry);
    }
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值