首页 > 编程知识 正文

springmvc框架搭建,spring框架开发流程

时间:2023-05-05 10:00:23 阅读:192825 作者:4364

Spring MVC(一)框架设计及流程 SpringMVC框架设计

框架设计图如下

上图是SpringMVC框架运行的流程。处理请求先到达控制器(Controller),控制器的作用是进行请求转发,这样它会根据请求的内容去访问模型层(Model);在现今互联网体系中,数据主要从数据库和NoSQL中来,而且对于数据库而言往往还存在事务的机制,为了适应这样的变化,设计者会把模型层再细分为两层,即服务层(Service)和数据访问层(DAO);当控制器获取到由模型层返回的数据后,将数据渲染到视图中,这样就能够展示给用户了。

SpringMVC流程

流程图

流程和组件是SpringMVC的核心。

SpringMVC的流程都是围绕着DispatcherServlet而工作的。严格来说,springMVC处理请求并非一定需要经过全流程,有时候一些流程并不存在,比如我们加入@ResponseBody注解时,是没有经过视图解析器和视图渲染的,关于这个后面会讨论到。

首先,在Web服务器启动的过程中,如果在Spring Boot的机制下启用SpirngMVC,它就开始初始化一些重要组件,如DispactherServlert、HandlerAdatper的实现类RequestMappingHandlerAdatper等对象组件。关于组件的初始化,我们在spring-webmvc-xxx.jar包的属性文件DispatcherServler.properties,它定义的对象都是在SpringMVC开始时就初始化,并且存放在SpringIoC容器中。其源码如下

DispatcherServler.properties源码

# Default implementation classes for DispatcherServlet's strategy interfaces.# Used as fallback when no matching beans are found in the DispatcherServlet context.# Not meant to be customized by application developers.#国际化解析器org.springframework.web.servlet.LocaleResolver=org.springframework.web.servlet.i18n.AcceptHeaderLocaleResolver#主题解析器org.springframework.web.servlet.ThemeResolver=org.springframework.web.servlet.theme.FixedThemeResolver# HandlerMapping实例org.springframework.web.servlet.HandlerMapping=org.springframework.web.servlet.handler.BeanNameUrlHandlerMapping,org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping#处理器适配器org.springframework.web.servlet.HandlerAdapter=org.springframework.web.servlet.mvc.HttpRequestHandlerAdapter,org.springframework.web.servlet.mvc.SimpleControllerHandlerAdapter,org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter#处理器异常解析器org.springframework.web.servlet.HandlerExceptionResolver=org.springframework.web.servlet.mvc.method.annotation.ExceptionHandlerExceptionResolver,org.springframework.web.servlet.mvc.annotation.ResponseStatusExceptionResolver,org.springframework.web.servlet.mvc.support.DefaultHandlerExceptionResolver#策略视图名称转换器,当没有返回视图逻辑名称的时候,通过它可以生成默认的视图名称org.springframework.web.servlet.RequestToViewNameTranslator=org.springframework.web.servlet.view.DefaultRequestToViewNameTranslator#视图解析器org.springframework.web.servlet.ViewResolver=org.springframework.web.servlet.view.InternalResourceViewResolver#FlashMap管理器,不常用org.springframework.web.servlet.FlashMapManager=org.springframework.web.servlet.support.SessionFlashMapManager

这些组件会在SpringMVC得到初始化,所以我们并不需要太多的配置就能够开发SpringMVC程序。

普通视图

定义控制器

@RequestMapping(value = "/person")@Controllerpublic class PersonController { //注入用户服务类 @Autowired PersonService personService; //展示人员详情 @RequestMapping("/details") public ModelAndView details(Long id) { //访问模型层得到数据 Person perosn = personService.getPerson(id); //模型和视图 ModelAndView mv = new ModelAndView(); //定义模型视图 mv.setViewName("person/details"); //加入数据模型 mv.addObject("person", perosn); //返回视图 return mv; }}

@Controller:表明这是一个控制器

@RequestMapping:代表请求路径和控制器(或方法)的映射关系,它会在Web服务启动SpringMVC的时,就被扫描到HandlerMapping的机制中存储,之后再用户发起请求被DispatcherServlert拦截后,通过URI和其他的条件,通过HandlerMapper机制就能够找到对应的控制器或其方法进行响应。只是通过HandlerMapping返回的是一个HandlerExecutionChain对象,源码如下

HandlerExecutionChain源码

public class HandlerExecutionChain { //日志 private static final Log logger = LogFactory.getLog(HandlerExecutionChain.class); //处理器 private final Object handler; //拦截器数组 @Nullable private HandlerInterceptor[] interceptors; //拦截器列表 @Nullable private List<HandlerInterceptor> interceptorList; //拦截器当前下标 private int interceptorIndex; //....}

HandlerExecutionChain对象包含一个处理器(handler)。这里的处理器就是对控制器(controller)的包装。因为我们的控制器方法可能存在参数,那么处理器就可以读入http和上下文的相关参数,然后再传递给控制器方法。而在控制器执行完成返回后,处理器又可以通过配置信息和对控制器的返回结果进行处理。可以看出,处理器包含了控制器方法的逻辑,此外还有处理器的拦截器(interceptor),这样就能够通过拦截处理器进一步增强处理器的功能。

得到了处理器(handler)。还需要去运行,但是我们有普通的http请求,也有按BeanName的请求,设置是WebSocket的请求,所以它还需要一个适配器去运行HandlerExecutionChain对象包含的处理器,这就是HandlerAdapter接口定义的实现类。从源码中可以看到SpringMVC中最常用的HandlerAdapter的实现类,便是HttpRequestHandlerAdapter。通过请求的类型,DispatcherServlet就会找到它来执行Web请求的HandlerExecutionChain对象包含的内容,这样就能够执行我们的处理器(handler)了。

在处理器调用控制器时,它首先通过模型层得到数据,再放入数据模型中,最后将返回模型和视图对象(ModelAndView),这里控制器设置的视图名称设置为"person/details"这样就走到了视图解析器(ViewResolver),去解析视图逻辑名称了。

SpringMVC的ViewResolver的实现类是InternalResourceViewResolver,为了定制,我们可以在application.properties文件中进行配置

spring.mvc.view.prefix=/spring.mvc.view.suffix=.html

通过这样的配置,就能能在Spring Boot机制下定织InternalResouceViwResolver这个视图解析器的初始化,也就是在返回视图名称之后,它会以前缀(prefix)和后缀(suffix)以及视图的名称组成全路径定位视图。例如,在控制器返回的"person/details",这里前缀为/,等于spring boot默认路径"/src/main/resources/templates",那么它就会找到"/src/main/resources/templates/person.html"作为视图。

视图解析器定位到视图后,视图的作用是将数据模型(Model)渲染,这样就能够响应数据的请求。这一步就是视图将数据模型渲染(View)出来,用来展示给用户看。

/person/details.html

<!DOCTYPE html><html xmlns:th="http://www.thymeleaf.org"><head> <meta charset="UTF-8"> <meta charset="UTF-8"> <title>用户详情</title></head><body><center> <table border="1"> <tr> <td>标签</td> <td>值</td> </tr> <tr> <td>用户编号</td> <td th:text="${person.id}"></td> </tr> <tr> <td>用户名称</td> <td th:text="${person.personName}"></td> </tr> <tr> <td>用户备注</td> <td th:text="${person.note}"></td> </tr> </table></center></body></html>

这里因为我们的控制器里绑定数据模型的时候,属性名称为person,而属性为person对象,所以就有了${person.id}代表perosn对象的id属性,其余属性是一样的。

流程如下

JSON视图

有时候我们需要的只是JSON数据集,因为目前前后台分离的趋势,使用JSON已经是主流的方式。正如@ResponseBody注解表明方法一样,springMVC会把数据转换为JSON数据集,但是这里不谈@ResponseBody,因为它会采用处理器内部的机制。这里先用MappingJackson2JsonView转换出JSON。

//使用json视图 @RequestMapping("/detailsForJson") public ModelAndView detailsForJson(Long id) { Person person = personService.getPerson(id); ModelAndView mv = new ModelAndView(); MappingJackson2JsonView jsonView = new MappingJackson2JsonView(); mv.setView(jsonView); mv.addObject("person", person); return mv; }

其流程如下

流程中我们可以看到并没有视图解析器,是因为MappingJackson2JsonView是一个非逻辑视图。它不需要视图解析器进行定位,它的作用只是将数据模型渲染为JSON数据集来响应请求。

版权声明:该文观点仅代表作者本人。处理文章:请发送邮件至 三1五14八八95#扣扣.com 举报,一经查实,本站将立刻删除。