本文已参与「新人创作礼」活动,一起开启掘金创作之路。
1. springMVC 的请求过程****
Spring MVC就是Spring框架对MVC设计模式的实现,通过Spring MVC ,我们可以快速的构建灵活、松耦合的web服务。再具体介绍Spring MVC 之前,我们先看一下它的请求处理过程:
-
请求会首先发送到DispatchServlet,这是spring的前置Servlet,它会接收请求并转发给spring的MVC controller,也就是业务controller
-
DispatchServlet通过HandlerMapping确定将请求转发给哪个controller,HandlerMapping主要通过请求中的URL确定映射关系的
-
DispatchServlet将请求转发给确定的controller之后,controller负责处理这个请求,一般会通过调用service层进行业务逻辑处理
-
当controller处理完请求后,它会把业务处理结果封装成model,为了使处理结果的model在页面上更好的展示,controller还会指定展示model对应的view(比如一个JSP页面),当controller确定了model和view之后,会把它们以请求的形式再转发给DispatchServlet
-
DispatchServlet通过查询ViewResolver找到view对应的页面
-
DispatchServlet最终把model交给页面进行渲染
-
页面对model进行渲染,将结果展示到客户端,整个请求结束
Spring MVC的核心就是DispatchServlet,配置Spring MVC的过程就是配置DispatchServlet的过程
2. Spring如何解决循环依赖的****
答:Spring通过三级缓存解决了循环依赖,其中一级缓存为单例池(singletonObjects),二级缓存为早期曝光对象earlySingletonObjects,三级缓存为早期曝光对象工厂(singletonFactories)。
当A、B两个类发生循环引用时,在A完成实例化后,就使用实例化后的对象去创建一个对象工厂,添加到三级缓存中,如果A被AOP代理,那么通过这个工厂获取到的就是A代理后的对象,如果A没有被AOP代理,那么这个工厂获取到的就是A实例化的对象。
当A进行属性注入时(注入B),会去创建B,同时B又依赖了A,所以创建B的同时又会去调用getBean(a)来获取需要的依赖,此时的getBean(a)会从缓存中获取:
第一步:先获取到三级缓存中的工厂;
第二步:调用对象工工厂的getObject方法来获取到对应的对象,得到这个对象后将其注入到B中。紧接着B会走完它的生命周期流程,包括初始化、后置处理器等。
第三步:当B创建完后,会将B再注入到A中,此时A再完成它的整个生命周期。至此,循环依赖结束!
Spring是通过递归的方式获取目标bean及其所依赖的bean的;
Spring实例化一个bean的时候,是分两步进行的,首先实例化目标bean,然后为其注入属性。