Servlet规范中,通过ServeltContext来注册Filter、Servlet,这里分析Filter,Servlet是相同逻辑

springboot2.0中,我们通过

FilterRegistrationBean将指定得filter来实现ServeltContext注册filter

FilterRegistrationBean的实例化过程

public FilterRegistrationBean(T filter, ServletRegistrationBean... servletRegistrationBeans) {
super(servletRegistrationBeans);
Assert.notNull(filter, "Filter must not be null");
this.filter = filter;
} super的实例化
AbstractFilterRegistrationBean(ServletRegistrationBean... servletRegistrationBeans) {
Assert.notNull(servletRegistrationBeans, "ServletRegistrationBeans must not be null");
Collections.addAll(this.servletRegistrationBeans, servletRegistrationBeans);
}

可知FilterRegistrationBean得实例化过程就是将Filter保存到servletRegistrationBeans(一个set)中

再分析FilterRegistrationBean类

FilterRegistrationBean的父类是一个ServletContextInitializer,他有一个方法onStartup(ServletContext servletContext)
其结果最终会调用
servletContext.addFilter(this.getOrDeduceName(filter), filter)
现在看看ServletContextInitializer.onStartup的调用地方
springboot启动
new SpringApplication(XXApplication.class).run(XXApplication.class,args)
调用
refreshContext(context); -> refresh(context); -> ((AbstractApplicationContext) applicationContext).refresh();
-> ServletWebServerApplicationContext.onRefresh(); -> createWebServer(); WebServer webServer = this.webServer;
ServletContext servletContext = getServletContext();
if (webServer == null && servletContext == null) {
ServletWebServerFactory factory = getWebServerFactory();
this.webServer = factory.getWebServer(getSelfInitializer());
}

再分析getSelfInitializer方法

prepareWebApplicationContext(servletContext);
registerApplicationScope(servletContext);
WebApplicationContextUtils.registerEnvironmentBeans(getBeanFactory(),servletContext);
for (ServletContextInitializer beans :getServletContextInitializerBeans()) {
              //调用ServletContextInitializer的onStartup方法
              beans.onStartup(servletContext); 
}
-> getServletContextInitializerBeans()
-> new ServletContextInitializerBeans(getBeanFactory())
-> addAdaptableBeans(beanFactory)

 

addAdaptableBeans(ListableBeanFactory beanFactory) 代码如下:
MultipartConfigElement multipartConfig = getMultipartConfig(beanFactory);
//将servlet类的bean包装为ServletRegistrationBean
addAsRegistrationBean(beanFactory, Servlet.class,new ServletRegistrationBeanAdapter(multipartConfig));
//将Filter的bean包装为FilterRegistrationBean
addAsRegistrationBean(beanFactory, Filter.class,new FilterRegistrationBeanAdapter());
for (Class<?> listenerType : ServletListenerRegistrationBean.getSupportedTypes()) {
  addAsRegistrationBean(beanFactory, EventListener.class,(Class<EventListener>) listenerType,new ServletListenerRegistrationBeanAdapter());
}

这里提一下,如果Servlet的bean实例名为dispatcherServlet,且该实例在seen集合中(seen集合为自定义配置的实例,通过ServletContextInitializerBeans.addServletContextInitializerBean入口可以查看源码),则设置默认值为  /

String url = (totalNumberOfSourceBeans != 1) ? "/" + name + "/" : "/";
if (name.equals(DISPATCHER_SERVLET_NAME)) {
url = "/"; // always map the main dispatcherServlet to "/"
}
ServletRegistrationBean<Servlet> bean = new ServletRegistrationBean<>(source,url);
bean.setName(name);
bean.setMultipartConfig(this.multipartConfig);
return bean;

 

总结:springboot启动时,会将所有的 FilterRegistrationBean、ServletRegistrationBean以及被spring管理的Servlet和Filter的实例,通过ServletContext注册Servlet以及Filter

如果不希望filter自动注册,可以通过以下方式:

 @Bean
public FilterRegistrationBean registration(@Qualifier("loginFilter") LoginFilter loginFilter) {
FilterRegistrationBean registration = new FilterRegistrationBean(loginFilter);
registration.setEnabled(false);
return registration;
}

 

 
												

springboot 2.1.3.RELEASE添加filter,servlet源码学习的更多相关文章

  1. SpringBoot源码学习系列之嵌入式Servlet容器

    目录 1.博客前言简单介绍 2.定制servlet容器 3.变换servlet容器 4.servlet容器启动原理 SpringBoot源码学习系列之嵌入式Servlet容器启动原理 @ 1.博客前言 ...

  2. 源码学习系列之SpringBoot自动配置(篇二)

    源码学习系列之SpringBoot自动配置(篇二)之HttpEncodingAutoConfiguration 源码分析 继上一篇博客源码学习系列之SpringBoot自动配置(篇一)之后,本博客继续 ...

  3. SpringBoot源码学习系列之SpringMVC自动配置

    目录 1.ContentNegotiatingViewResolver 2.静态资源 3.自动注册 Converter, GenericConverter, and Formatter beans. ...

  4. Spring源码学习:第1步--在Spring源码中添加最简单的Demo代码

    为了最大程度地贴近Spring源码并进行学习,一种比较直接的做法是:直接在Spring源码中加入Demo代码,并进行调试. 参照以前使用Spring的经验,Spring最简单的使用方法是:一个实体类. ...

  5. XJar: Spring-Boot JAR 包加/解密工具,避免源码泄露以及反编译

    XJar: Spring-Boot JAR 包加/解密工具,避免源码泄露以及反编译 <?xml version="1.0" encoding="UTF-8" ...

  6. 源码学习系列之SpringBoot自动配置(篇一)

    源码学习系列之SpringBoot自动配置源码学习(篇一) ok,本博客尝试跟一下Springboot的自动配置源码,做一下笔记记录,自动配置是Springboot的一个很关键的特性,也容易被忽略的属 ...

  7. SpringBoot源码学习系列之异常处理自动配置

    SpringBoot源码学习系列之异常处理自动配置 1.源码学习 先给个SpringBoot中的异常例子,假如访问一个错误链接,让其返回404页面 在浏览器访问: 而在其它的客户端软件,比如postm ...

  8. SpringBoot源码学习1——SpringBoot自动装配源码解析+Spring如何处理配置类的

    系列文章目录和关于我 一丶什么是SpringBoot自动装配 SpringBoot通过SPI的机制,在我们程序员引入一些starter之后,扫描外部引用 jar 包中的META-INF/spring. ...

  9. Servlet源码初探

    年底,公司的事情告一段落,就来捣鼓一下这个Servlet源码,为下一步的spingmvc源码初探做准备 1.Servlet接口 public interface Servlet { void init ...

随机推荐

  1. ELK教程3:logstash的部署、SpringBoot整合ELK+Filebeat

    本篇文章主要讲解如下安装Logstash,logstash依赖于Java环境,首先安装Java,安装脚本如下: yum install java logstash安装 Logstash的安装脚本如下: ...

  2. (7)Go切片

    切片 切片(Slice)是一个拥有相同类型元素的可变长度的序列.它是基于数组类型做的一层封装.它非常灵活,支持自动扩容. 切片是一个引用类型,它的内部结构包含地址.长度和容量.切片一般用于快速地操作一 ...

  3. mysql lower()函数

    mysql> select " DFREF"; +--------+ | DFREF | +--------+ | DFREF | +--------+ row in set ...

  4. linux下将终端的输入存入文件中

    代码很简单: #include <stdlib.h> #include <fcntl.h> #include <stdio.h> #include <unis ...

  5. Echarts 入门操作

    Echarts具有丰富的图表,可以说是数据可视化的神器: 1.下载Echarts 到官网或者点击以下文字[下载Echarts]即可下载: ①官网下载地址:https://echarts.baidu.c ...

  6. POP IM 产品分析报告

    一.   体验环境 产品名称:POP IM 软件版本:v2.4.0 手机系统:一加5T Android 9 体验时间:2019.10.22-2019.10.31 二.   产品简介 1.   产品定位 ...

  7. 第06组 Alpha冲刺(4/4)

    队名:福大帮 组长博客链接:https://www.cnblogs.com/mhq-mhq/p/11913386.html 作业博客 :https://edu.cnblogs.com/campus/f ...

  8. 剑指offer:平衡二叉树

    题目描述: 输入一棵二叉树,判断该二叉树是否是平衡二叉树. 思路分析: 首先要明确平衡二叉树的定义.平衡二叉是左右子树的高度差小于等于1,且左右子树都为平衡二叉树.这里就存在一个递归判断左右子树是否为 ...

  9. 搭建高可用rabbitmq集群及spring boot实现集群配置

    java spring boot配置: //具体参看了配置的源码 org.springframework.boot.autoconfigure.amqp.RabbitProperties //Rabb ...

  10. Python3基础 yield 创建生成器

             Python : 3.7.3          OS : Ubuntu 18.04.2 LTS         IDE : pycharm-community-2019.1.3    ...