Spring boot tomcat

Posted by Yang Blog on May 11, 2022
1
2
3
4
5
6
7
8
9
10
11
---
layout:     post
title:      "Spring Boot Tomcat源码阅读"
subtitle:   " \"Spring Boot Tomcat源码阅读\""
author:     "tablesheep"
date:       2022-05-11 20:46:00
header-style: text
catalog: true
tags:
- Spring Boot
---

Spring Boot Tomcat源码阅读

整合思路:将Tomcat的配置变为Spring Bean(包含Spring Boot配置和编程配置),然后根据这些Bean配置Tomcat。

Tomcat创建流程

入口:ServletWebServerApplicationContext#createWebServer

描述:Spring Boot在 Servlet环境启动时,通过ServletWebServerApplication#createWebServer创建Tomcat内嵌容器

  • 创建ServletWebServerFactoryTomcatServletWebServerFactory

    • WebServerFactoryCustomizerBeanPostProcessor在初始化前拦截ServletWebServerFactory,通过一系列(有序)WebServerFactoryCustomizer配置ServletWebServerFactory

      包括但不限于

      • ServletWebServerFactoryCustomizer设置通用容器配置,见ServerProperties
      • TomcatServletWebServerFactoryCustomizerTomcatWebServerFactoryCustomizer设置Tomcat Servlet & 容器配置,见ServerProperties.Tomcat

      主要是将配置设置到TomcatServletWebServerFactory,或者通过Tomcat Customizer 设置

  • 通过ServletWebServerFactory#getWebServer创建并配置Tomcat,具体看源码

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    
    //TomcatServletWebServerFactory#getWebServer
    @Override
    public WebServer getWebServer(ServletContextInitializer... initializers) {
       if (this.disableMBeanRegistry) {
          Registry.disableRegistry();
       }
        //创建Tomcat&一系列配置
       Tomcat tomcat = new Tomcat();
       File baseDir = (this.baseDirectory != null) ? this.baseDirectory : createTempDir("tomcat");
       tomcat.setBaseDir(baseDir.getAbsolutePath());
       for (LifecycleListener listener : this.serverLifecycleListeners) {
          tomcat.getServer().addLifecycleListener(listener);
       }
       Connector connector = new Connector(this.protocol);
       connector.setThrowOnFailure(true);
       tomcat.getService().addConnector(connector);
        //配置Connector,执行TomcatProtocolHandlerCustomizer & TomcatConnectorCustomizer
       customizeConnector(connector);
       tomcat.setConnector(connector);
       tomcat.getHost().setAutoDeploy(false);
       configureEngine(tomcat.getEngine());
       for (Connector additionalConnector : this.additionalTomcatConnectors) {
          tomcat.getService().addConnector(additionalConnector);
       }
        //配置tomcat context 执行TomcatContextCustomizer
       prepareContext(tomcat.getHost(), initializers);
       return getTomcatWebServer(tomcat);
    }
    

Tomcat 配置

  • Web容器配置类:org.springframework.boot.autoconfigure.web.ServerProperties (配置文件控制)

  • Tomcat 配置类:org.springframework.boot.autoconfigure.web.ServerProperties.Tomcat(配置文件控制)

  • Tomcat Customizer类(编程式控制):

    • Tomcat Connector配置类: org.springframework.boot.web.embedded.tomcat.TomcatConnectorCustomizer
    • Tomcat Context配置类:org.springframework.boot.web.embedded.tomcat.TomcatContextCustomizer
    • Tomcat ProtocolHandler 配置类:org.springframework.boot.web.embedded.tomcat.TomcatProtocolHandlerCustomizer

    编程式控制Spring Boot Tomcat:Spring Boot提供了以上三个Tomcat Customizer配置,我们可以通过BeanPostProcessor等方式拦截ServletWebServerFactory,添加自定义的Tomcat Customizer