• 第七章:(1)Spring Boot启动原理


    一、SpringBoot 启动原理

      运行一个主程序类的 main 方法:

    ---主程序运行---
    @SpringBootApplication
    public class SpringBoot07RunApplication {
    
        public static void main(String[] args) {
            SpringApplication.run(SpringBoot07RunApplication.class, args);
        }
    
    }
    
    ---SpringApplication---
    public static ConfigurableApplicationContext run(Object source, String... args) {
        return run(new Object[] { source }, args);
    }
    
    public static ConfigurableApplicationContext run(Object[] sources, String[] args) {
        return new SpringApplication(sources).run(args);
    }

      启动流程:

      1、创建 SpringApplication 对象

      2、运行 run 方法 

    二、创建 SpringApplication 对象

      创建 SpringApplication 应用:

    public SpringApplication(Object... sources) {
        initialize(sources);
    }
    
    private void initialize(Object[] sources) {
        //1、保存主配置类
        if (sources != null && sources.length > 0) {
            this.sources.addAll(Arrays.asList(sources));
        }
        
        //2、判断当前是否一个web应用
        this.webEnvironment = deduceWebEnvironment();
        
        //3、从类路径下找到META‐INF/spring.factories配置的所有ApplicationContextInitializer;然后保存起来
        setInitializers((Collection) getSpringFactoriesInstances(
                ApplicationContextInitializer.class));
                
        //4、从类路径下找到ETA‐INF/spring.factories配置的所有ApplicationListener        
        setListeners((Collection) getSpringFactoriesInstances(ApplicationListener.class));
        
        //5、决定主配置类:从多个配置类中找到有main方法的主配置类
        this.mainApplicationClass = deduceMainApplicationClass();
    }

      (1)保存主配置类

    if (sources != null && sources.length > 0) {
        this.sources.addAll(Arrays.asList(sources));
    }

      (2)判断当前是否一个 web 应用

    private boolean deduceWebEnvironment() {
        for (String className : WEB_ENVIRONMENT_CLASSES) {
            if (!ClassUtils.isPresent(className, null)) {
                return false;
            }
        }
        return true;
    }

      (3)加载类路径下找到META‐INF/spring.factories配置的所有ApplicationContextInitializer 组件

    //设置初始化器
    setInitializers((Collection) getSpringFactoriesInstances(ApplicationContextInitializer.class));
                    
    public void setInitializers(
            Collection<? extends ApplicationContextInitializer<?>> initializers) {
        this.initializers = new ArrayList<ApplicationContextInitializer<?>>();
        this.initializers.addAll(initializers);
    }
    
    private <T> Collection<? extends T> getSpringFactoriesInstances(Class<T> type) {
        return getSpringFactoriesInstances(type, new Class<?>[] {});
    }
    
    private <T> Collection<? extends T> getSpringFactoriesInstances(Class<T> type,
            Class<?>[] parameterTypes, Object... args) {
        ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
        // Use names and ensure unique to protect against duplicates
        Set<String> names = new LinkedHashSet<String>(
                SpringFactoriesLoader.loadFactoryNames(type, classLoader));
        List<T> instances = createSpringFactoriesInstances(type, parameterTypes,
                classLoader, args, names);
        AnnotationAwareOrderComparator.sort(instances);
        return instances;
    }
    
    public static List<String> loadFactoryNames(Class<?> factoryClass, ClassLoader classLoader) {
        String factoryClassName = factoryClass.getName();
        try {
            Enumeration<URL> urls = (classLoader != null ? classLoader.getResources(FACTORIES_RESOURCE_LOCATION) :
                    ClassLoader.getSystemResources(FACTORIES_RESOURCE_LOCATION));
            List<String> result = new ArrayList<String>();
            while (urls.hasMoreElements()) {
                URL url = urls.nextElement();
                Properties properties = PropertiesLoaderUtils.loadProperties(new UrlResource(url));
                String factoryClassNames = properties.getProperty(factoryClassName);
                result.addAll(Arrays.asList(StringUtils.commaDelimitedListToStringArray(factoryClassNames)));
            }
            return result;
        }
        catch (IOException ex) {
            throw new IllegalArgumentException("Unable to load [" + factoryClass.getName() +
                    "] factories from location [" + FACTORIES_RESOURCE_LOCATION + "]", ex);
        }
    }

        

      (4)从类路径下找到ETA‐INF/spring.factories配置的所有ApplicationListener 组件

    setListeners((Collection) getSpringFactoriesInstances(ApplicationListener.class));
    
    public void setListeners(Collection<? extends ApplicationListener<?>> listeners) {
        this.listeners = new ArrayList<ApplicationListener<?>>();
        this.listeners.addAll(listeners);
    }
    
    private <T> Collection<? extends T> getSpringFactoriesInstances(Class<T> type) {
        return getSpringFactoriesInstances(type, new Class<?>[] {});
    }
    
    private <T> Collection<? extends T> getSpringFactoriesInstances(Class<T> type,
            Class<?>[] parameterTypes, Object... args) {
        ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
        // Use names and ensure unique to protect against duplicates
        Set<String> names = new LinkedHashSet<String>(
                SpringFactoriesLoader.loadFactoryNames(type, classLoader));
        List<T> instances = createSpringFactoriesInstances(type, parameterTypes,
                classLoader, args, names);
        AnnotationAwareOrderComparator.sort(instances);
        return instances;
    }

        

      (5)决定主配置类

    private Class<?> deduceMainApplicationClass() {
        try {
            StackTraceElement[] stackTrace = new RuntimeException().getStackTrace();
            for (StackTraceElement stackTraceElement : stackTrace) {
                if ("main".equals(stackTraceElement.getMethodName())) {
                    return Class.forName(stackTraceElement.getClassName());
                }
            }
        }
        catch (ClassNotFoundException ex) {
            // Swallow and continue
        }
        return null;
    }

    三、运行 run 方法

      来到 SpringBootApplication 的 run 方法

    public static ConfigurableApplicationContext run(Object[] sources, String[] args) {
        return new SpringApplication(sources).run(args);
    }
    
    public ConfigurableApplicationContext run(String... args) {
        StopWatch stopWatch = new StopWatch();
        stopWatch.start();
        ConfigurableApplicationContext context = null;
        FailureAnalyzers analyzers = null;
        //AWT 相关
        configureHeadlessProperty();
        
        //1、获取SpringApplicationRunListeners;从类路径下META‐INF/spring.factories
        SpringApplicationRunListeners listeners = getRunListeners(args);
        //回调所有的获取SpringApplicationRunListener.starting()方法
        listeners.starting();
        
        try {
            //封装命令行参数
            ApplicationArguments applicationArguments = new DefaultApplicationArguments(args);
            
            
            //2、准备环境
            ConfigurableEnvironment environment = prepareEnvironment(listeners, applicationArguments);
            //创建环境完成后回调SpringApplicationRunListener.environmentPrepared();表示环境准备完成        
    
                    
            //打印 Banner 图        
            Banner printedBanner = printBanner(environment);
            
            
            //3、创建ApplicationContext;决定创建web的ioc还是普通的ioc
            context = createApplicationContext();
            
            
            //异常分析报告
            analyzers = new FailureAnalyzers(context);
            
            
            //4、准备上下文环境;将environment保存到ioc中;而且applyInitializers();
            // applyInitializers():回调之前保存的所有的ApplicationContextInitializer的initialize方法
            // 回调所有的SpringApplicationRunListener的contextPrepared();
            prepareContext(context, environment, listeners, applicationArguments, printedBanner);
            //prepareContext运行完成以后回调所有的SpringApplicationRunListener的contextLoaded();
            
            
            //5、刷新容器;ioc容器初始化(如果是web应用还会创建嵌入式的Tomcat)
            //扫描,创建,加载所有组件的地方;(配置类,组件,自动配置)
            refreshContext(context);
            
            
            //6、从ioc容器中获取所有的ApplicationRunner和CommandLineRunner进行回调
            //   ApplicationRunner先回调,CommandLineRunner再回调
            afterRefresh(context, applicationArguments);
            
            
            //7、所有的SpringApplicationRunListener回调finished方法
            listeners.finished(context, null);
            
            stopWatch.stop();
            if (this.logStartupInfo) {
                new StartupInfoLogger(this.mainApplicationClass)
                        .logStarted(getApplicationLog(), stopWatch);
            }
            
            //8、整个SpringBoot应用启动完成以后返回启动的ioc容器;
            return context;
        }
        catch (Throwable ex) {
            handleRunFailure(context, listeners, analyzers, ex);
            throw new IllegalStateException(ex);
        }
    }

      核心步骤:

      (1)获取所有的 SpringApplicationRunListener 组件,并回调 starting 方法

    //从类路径下META‐INF/spring.factories中获取SpringApplicationRunListener 组件
    private SpringApplicationRunListeners getRunListeners(String[] args) {
        Class<?>[] types = new Class<?>[] { SpringApplication.class, String[].class };
        return new SpringApplicationRunListeners(logger, getSpringFactoriesInstances(
                SpringApplicationRunListener.class, types, this, args));
    }
    
    //回调SpringApplicationRunListener的 starting 方法
    public void starting() {
        for (SpringApplicationRunListener listener : this.listeners) {
            listener.starting();
        }
    }

      (2)准备环境

    //准备环境
    private ConfigurableEnvironment prepareEnvironment(
            SpringApplicationRunListeners listeners,
            ApplicationArguments applicationArguments) {
        // Create and configure the environment
        //得到或者创建一个环境
        ConfigurableEnvironment environment = getOrCreateEnvironment();
        //配置环境
        configureEnvironment(environment, applicationArguments.getSourceArgs());
        
        //创建环境完成后回调SpringApplicationRunListener.environmentPrepared();表示环境准备完成
        listeners.environmentPrepared(environment);
        
        //是否为 web 环境
        if (!this.webEnvironment) {
            environment = new EnvironmentConverter(getClassLoader())
                    .convertToStandardEnvironmentIfNecessary(environment);
        }
        return environment;
    }
    public void environmentPrepared(ConfigurableEnvironment environment) {
        for (SpringApplicationRunListener listener : this.listeners) {
            listener.environmentPrepared(environment);
        }
    }

      (3)创建 ApplicationContext

    protected ConfigurableApplicationContext createApplicationContext() {
        Class<?> contextClass = this.applicationContextClass;
        if (contextClass == null) {
            try {
                contextClass = Class.forName(this.webEnvironment
                        ? DEFAULT_WEB_CONTEXT_CLASS : DEFAULT_CONTEXT_CLASS);
            }
            catch (ClassNotFoundException ex) {
                throw new IllegalStateException(
                        "Unable create a default ApplicationContext, "
                                + "please specify an ApplicationContextClass",
                        ex);
            }
        }
        //创建ApplicationContext;决定创建web的ioc还是普通的ioc
        return (ConfigurableApplicationContext) BeanUtils.instantiate(contextClass);
    }

      (4)准备上下文环境

    //准备上下文环境
    private void prepareContext(ConfigurableApplicationContext context,
            ConfigurableEnvironment environment, SpringApplicationRunListeners listeners,
            ApplicationArguments applicationArguments, Banner printedBanner) {
        //设置上下文环境    
        context.setEnvironment(environment);
        //通过后置处理器添加组件
        postProcessApplicationContext(context);
        
        //回调之前保存的所有的ApplicationContextInitializer的initialize方法
        applyInitializers(context);
        
        //回调所有的SpringApplicationRunListener的contextPrepared();
        listeners.contextPrepared(context);
    if (this.logStartupInfo) { logStartupInfo(context.getParent() == null); logStartupProfileInfo(context); } // Add boot specific singleton beans context.getBeanFactory().registerSingleton("springApplicationArguments", applicationArguments); if (printedBanner != null) { context.getBeanFactory().registerSingleton("springBootBanner", printedBanner); } // Load the sources Set<Object> sources = getSources(); Assert.notEmpty(sources, "Sources must not be empty"); load(context, sources.toArray(new Object[sources.size()])); //context 设置完毕后,回调所有的SpringApplicationRunListener的contextLoaded() listeners.contextLoaded(context); } protected void applyInitializers(ConfigurableApplicationContext context) { for (ApplicationContextInitializer initializer : getInitializers()) { Class<?> requiredType = GenericTypeResolver.resolveTypeArgument( initializer.getClass(), ApplicationContextInitializer.class); Assert.isInstanceOf(requiredType, context, "Unable to call initializer."); initializer.initialize(context); } } public void contextPrepared(ConfigurableApplicationContext context) { for (SpringApplicationRunListener listener : this.listeners) { listener.contextPrepared(context); } } public void contextLoaded(ConfigurableApplicationContext context) { for (SpringApplicationRunListener listener : this.listeners) { listener.contextLoaded(context); } }

      (5)刷新容器,IOC 容器初始化

    private void refreshContext(ConfigurableApplicationContext context) {
        refresh(context);
        if (this.registerShutdownHook) {
            try {
                context.registerShutdownHook();
            }
            catch (AccessControlException ex) {
                // Not allowed in some environments.
            }
        }
    }

      (6)从 IOC 容器中获取所有的ApplicationRunner和CommandLineRunner进行回调

    protected void afterRefresh(ConfigurableApplicationContext context,
            ApplicationArguments args) {
        callRunners(context, args);
    }
    
    private void callRunners(ApplicationContext context, ApplicationArguments args) {
        List<Object> runners = new ArrayList<Object>();
        runners.addAll(context.getBeansOfType(ApplicationRunner.class).values());
        runners.addAll(context.getBeansOfType(CommandLineRunner.class).values());
        AnnotationAwareOrderComparator.sort(runners);
        for (Object runner : new LinkedHashSet<Object>(runners)) {
            if (runner instanceof ApplicationRunner) {
                callRunner((ApplicationRunner) runner, args);
            }
            if (runner instanceof CommandLineRunner) {
                callRunner((CommandLineRunner) runner, args);
            }
        }
    }
    
    private void callRunner(ApplicationRunner runner, ApplicationArguments args) {
        try {
            (runner).run(args);
        }
        catch (Exception ex) {
            throw new IllegalStateException("Failed to execute ApplicationRunner", ex);
        }
    }
    
    private void callRunner(CommandLineRunner runner, ApplicationArguments args) {
        try {
            (runner).run(args.getSourceArgs());
        }
        catch (Exception ex) {
            throw new IllegalStateException("Failed to execute CommandLineRunner", ex);
        }
    }

      (7)所有的SpringApplicationRunListener回调finished方法

    public void finished(ConfigurableApplicationContext context, Throwable exception) {
        for (SpringApplicationRunListener listener : this.listeners) {
            callFinishedListener(listener, context, exception);
        }
    }

      (8)整个SpringBoot应用启动完成以后返回启动的ioc容器

    四、启动原理总结

       SpringApplication.run(主程序类)

      1、new SpringApplication(主程序类)

        (1)判断是否 web 应用;

        (2)加载并保存所有ApplicationContextInitializer( META-INF/spring.factories

        (3)加载并保存所有ApplicationListener

        (4)获取到主程序类

      2、run()

        (1)回调所有的SpringApplicationRunListener( META-INF/spring.factories)的starting
        (2)获取ApplicationArguments
        (3)准备环境&回调所有监听器( SpringApplicationRunListener )的environmentPrepared
        (4)打印banner信息
        (5)创建ioc容器对象

    AnnotationConfigEmbeddedWebApplicationContext( web环境容器)
    AnnotationConfigApplicationContext(普通环境容器)
    

      3、run()

        (1)准备环境
          ① 执行ApplicationContextInitializer. initialize()
          ② 监听器SpringApplicationRunListener回调contextPrepared
          ③ 加载主配置类定义信息
          ④ 监听器SpringApplicationRunListener回调contextLoaded
        (2)刷新启动IOC容器;
          ① 扫描加载所有容器中的组件
          ② 包括从META-INF/spring.factories中获取的所有EnableAutoConfiguration组件
        (3)回调容器中所有的ApplicationRunnerCommandLineRunner的run方法
        (4)监听器SpringApplicationRunListener回调finished;

      4、几个重要的事件回调机制

        配置在 META-INF/spring.factories

    ApplicationContextInitializer
    SpringApplicationRunListener

        只需要放在 IOC 容器中

    ApplicationRunner
    CommandLineRunner
    

      

    五、SpringBoot 事件监听机制

      根据上面的流程,可以实现自己的组件:

      (1)HelloApplicationContextInitializer

    //IOC容器的初始化
    public class HelloApplicationContextInitializer implements ApplicationContextInitializer<ConfigurableApplicationContext> {
        @Override
        public void initialize(ConfigurableApplicationContext applicationContext) {
            System.out.println("IOC容器初始化~~");
            System.out.println("ApplicationContextInitializer...initialize..."+applicationContext);
        }
    }

      (2)HelloSpringApplicationRunListener

    public class HelloSpringApplicationRunListener implements SpringApplicationRunListener {
    
        //必须有的构造器
        public HelloSpringApplicationRunListener(SpringApplication application, String[] args){
        }
    
        //创建IOC容器之前
        @Override
        public void starting() {
            System.out.println("准备开始创建IOC容器~~~");
            System.out.println("SpringApplicationRunListener...starting...");
        }
    
        //环境准备完毕
        @Override
        public void environmentPrepared(ConfigurableEnvironment environment) {
            System.out.println("环境准备完毕");
            Object os = environment.getSystemProperties().get("os.name");
            System.out.println("SpringApplicationRunListener...environmentPrepared.."+ os);
        }
    
        //准备上下文context
        @Override
        public void contextPrepared(ConfigurableApplicationContext context) {
            System.out.println("准备上下文 context");
            System.out.println("SpringApplicationRunListener...contextPrepared...");
        }
    
        //context 准备完毕
        @Override
        public void contextLoaded(ConfigurableApplicationContext context) {
            System.out.println("context 准备完毕");
            System.out.println("SpringApplicationRunListener...contextLoaded...");
        }
    
        //IOC容器创建完毕
        @Override
        public void finished(ConfigurableApplicationContext context, Throwable exception) {
            System.out.println("IOC容器创建完毕");
            System.out.println("SpringApplicationRunListener...finished...");
        }
    }

      (3)HelloApplicationRunner

    @Component
    public class HelloApplicationRunner implements ApplicationRunner {
        @Override
        public void run(ApplicationArguments args) throws Exception {
            System.out.println("ApplicationRunner...run....");
        }
    }

      (4)HelloCommandLineRunner

    @Component
    public class HelloCommandLineRunner implements CommandLineRunner {
        @Override
        public void run(String... args) throws Exception {
            System.out.println("CommandLineRunner...run..."+ Arrays.asList(args));
        }
    }

      进行配置:

      ApplicationContextInitializer 与 SpringApplicationRunListener 需要配置在 META-INF/spring.factories

    org.springframework.context.ApplicationContextInitializer=\
      com.njf.springboot.listener.HelloApplicationContextInitializer
    
    org.springframework.boot.SpringApplicationRunListener=\
      com.njf.springboot.listener.HelloSpringApplicationRunListener
    

         

       ApplicationRunner 和 CommandLineRunner 加在 IOC 容器中

      测试:

    D:\Java\JDK8\jdk1.8.0_231\bin\java.exe -XX:TieredStopAtLevel=1 -noverify -Dspring.output.ansi.enabled=always "-javaagent:D:\Java-IDE\JetBrains\IntelliJ IDEA 2021.1\lib\idea_rt.jar=7735:D:\Java-IDE\JetBrains\IntelliJ IDEA 2021.1\bin" -Dcom.sun.management.jmxremote -Dspring.jmx.enabled=true -Dspring.liveBeansView.mbeanDomain -Dspring.application.admin.enabled=true -Dfile.encoding=UTF-8 -classpath D:\Java\JDK8\jdk1.8.0_231\jre\lib\charsets.jar;D:\Java\JDK8\jdk1.8.0_231\jre\lib\deploy.jar;D:\Java\JDK8\jdk1.8.0_231\jre\lib\ext\access-bridge-64.jar;D:\Java\JDK8\jdk1.8.0_231\jre\lib\ext\cldrdata.jar;D:\Java\JDK8\jdk1.8.0_231\jre\lib\ext\dnsns.jar;D:\Java\JDK8\jdk1.8.0_231\jre\lib\ext\jaccess.jar;D:\Java\JDK8\jdk1.8.0_231\jre\lib\ext\jfxrt.jar;D:\Java\JDK8\jdk1.8.0_231\jre\lib\ext\localedata.jar;D:\Java\JDK8\jdk1.8.0_231\jre\lib\ext\nashorn.jar;D:\Java\JDK8\jdk1.8.0_231\jre\lib\ext\sunec.jar;D:\Java\JDK8\jdk1.8.0_231\jre\lib\ext\sunjce_provider.jar;D:\Java\JDK8\jdk1.8.0_231\jre\lib\ext\sunmscapi.jar;D:\Java\JDK8\jdk1.8.0_231\jre\lib\ext\sunpkcs11.jar;D:\Java\JDK8\jdk1.8.0_231\jre\lib\ext\zipfs.jar;D:\Java\JDK8\jdk1.8.0_231\jre\lib\javaws.jar;D:\Java\JDK8\jdk1.8.0_231\jre\lib\jce.jar;D:\Java\JDK8\jdk1.8.0_231\jre\lib\jfr.jar;D:\Java\JDK8\jdk1.8.0_231\jre\lib\jfxswt.jar;D:\Java\JDK8\jdk1.8.0_231\jre\lib\jsse.jar;D:\Java\JDK8\jdk1.8.0_231\jre\lib\management-agent.jar;D:\Java\JDK8\jdk1.8.0_231\jre\lib\plugin.jar;D:\Java\JDK8\jdk1.8.0_231\jre\lib\resources.jar;D:\Java\JDK8\jdk1.8.0_231\jre\lib\rt.jar;F:\My_Workspaceing\project\SpringBoot\spring-boot-07-run\target\classes;D:\RepMaven\repos\org\springframework\boot\spring-boot-starter-web\1.5.9.RELEASE\spring-boot-starter-web-1.5.9.RELEASE.jar;D:\RepMaven\repos\org\springframework\boot\spring-boot-starter\1.5.9.RELEASE\spring-boot-starter-1.5.9.RELEASE.jar;D:\RepMaven\repos\org\springframework\boot\spring-boot\1.5.9.RELEASE\spring-boot-1.5.9.RELEASE.jar;D:\RepMaven\repos\org\springframework\boot\spring-boot-autoconfigure\1.5.9.RELEASE\spring-boot-autoconfigure-1.5.9.RELEASE.jar;D:\RepMaven\repos\org\springframework\boot\spring-boot-starter-logging\1.5.9.RELEASE\spring-boot-starter-logging-1.5.9.RELEASE.jar;D:\RepMaven\repos\ch\qos\logback\logback-classic\1.1.11\logback-classic-1.1.11.jar;D:\RepMaven\repos\ch\qos\logback\logback-core\1.1.11\logback-core-1.1.11.jar;D:\RepMaven\repos\org\slf4j\jcl-over-slf4j\1.7.25\jcl-over-slf4j-1.7.25.jar;D:\RepMaven\repos\org\slf4j\jul-to-slf4j\1.7.25\jul-to-slf4j-1.7.25.jar;D:\RepMaven\repos\org\slf4j\log4j-over-slf4j\1.7.25\log4j-over-slf4j-1.7.25.jar;D:\RepMaven\repos\org\yaml\snakeyaml\1.17\snakeyaml-1.17.jar;D:\RepMaven\repos\org\springframework\boot\spring-boot-starter-tomcat\1.5.9.RELEASE\spring-boot-starter-tomcat-1.5.9.RELEASE.jar;D:\RepMaven\repos\org\apache\tomcat\embed\tomcat-embed-core\8.5.23\tomcat-embed-core-8.5.23.jar;D:\RepMaven\repos\org\apache\tomcat\tomcat-annotations-api\8.5.23\tomcat-annotations-api-8.5.23.jar;D:\RepMaven\repos\org\apache\tomcat\embed\tomcat-embed-el\8.5.23\tomcat-embed-el-8.5.23.jar;D:\RepMaven\repos\org\apache\tomcat\embed\tomcat-embed-websocket\8.5.23\tomcat-embed-websocket-8.5.23.jar;D:\RepMaven\repos\org\hibernate\hibernate-validator\5.3.6.Final\hibernate-validator-5.3.6.Final.jar;D:\RepMaven\repos\javax\validation\validation-api\1.1.0.Final\validation-api-1.1.0.Final.jar;D:\RepMaven\repos\org\jboss\logging\jboss-logging\3.3.1.Final\jboss-logging-3.3.1.Final.jar;D:\RepMaven\repos\com\fasterxml\classmate\1.3.4\classmate-1.3.4.jar;D:\RepMaven\repos\com\fasterxml\jackson\core\jackson-databind\2.8.10\jackson-databind-2.8.10.jar;D:\RepMaven\repos\com\fasterxml\jackson\core\jackson-annotations\2.8.0\jackson-annotations-2.8.0.jar;D:\RepMaven\repos\com\fasterxml\jackson\core\jackson-core\2.8.10\jackson-core-2.8.10.jar;D:\RepMaven\repos\org\springframework\spring-web\4.3.13.RELEASE\spring-web-4.3.13.RELEASE.jar;D:\RepMaven\repos\org\springframework\spring-aop\4.3.13.RELEASE\spring-aop-4.3.13.RELEASE.jar;D:\RepMaven\repos\org\springframework\spring-beans\4.3.13.RELEASE\spring-beans-4.3.13.RELEASE.jar;D:\RepMaven\repos\org\springframework\spring-context\4.3.13.RELEASE\spring-context-4.3.13.RELEASE.jar;D:\RepMaven\repos\org\springframework\spring-webmvc\4.3.13.RELEASE\spring-webmvc-4.3.13.RELEASE.jar;D:\RepMaven\repos\org\springframework\spring-expression\4.3.13.RELEASE\spring-expression-4.3.13.RELEASE.jar;D:\RepMaven\repos\org\slf4j\slf4j-api\1.7.25\slf4j-api-1.7.25.jar;D:\RepMaven\repos\org\springframework\spring-core\4.3.13.RELEASE\spring-core-4.3.13.RELEASE.jar com.njf.springboot.SpringBoot07RunApplication
    准备开始创建IOC容器~~~
    SpringApplicationRunListener...starting...
    环境准备完毕
    SpringApplicationRunListener...environmentPrepared..Windows 10
    
      .   ____          _            __ _ _
     /\\ / ___'_ __ _ _(_)_ __  __ _ \ \ \ \
    ( ( )\___ | '_ | '_| | '_ \/ _` | \ \ \ \
     \\/  ___)| |_)| | | | | || (_| |  ) ) ) )
      '  |____| .__|_| |_|_| |_\__, | / / / /
     =========|_|==============|___/=/_/_/_/
     :: Spring Boot ::        (v1.5.9.RELEASE)
    
    IOC容器初始化~~
    ApplicationContextInitializer...initialize...org.springframework.boot.context.embedded.AnnotationConfigEmbeddedWebApplicationContext@365c30cc: startup date [Thu Jan 01 08:00:00 CST 1970]; root of context hierarchy
    准备上下文 context
    SpringApplicationRunListener...contextPrepared...
    2021-12-20 19:08:49.269  INFO 520 --- [           main] c.n.s.SpringBoot07RunApplication         : Starting SpringBoot07RunApplication on niujifei with PID 520 (F:\My_Workspaceing\project\SpringBoot\spring-boot-07-run\target\classes started by niujifei in F:\My_Workspaceing\project\SpringBoot)
    2021-12-20 19:08:49.274  INFO 520 --- [           main] c.n.s.SpringBoot07RunApplication         : No active profile set, falling back to default profiles: default
    context 准备完毕
    SpringApplicationRunListener...contextLoaded...
    2021-12-20 19:08:49.336  INFO 520 --- [           main] ationConfigEmbeddedWebApplicationContext : Refreshing org.springframework.boot.context.embedded.AnnotationConfigEmbeddedWebApplicationContext@365c30cc: startup date [Mon Dec 20 19:08:49 CST 2021]; root of context hierarchy
    2021-12-20 19:08:50.860  INFO 520 --- [           main] s.b.c.e.t.TomcatEmbeddedServletContainer : Tomcat initialized with port(s): 8080 (http)
    2021-12-20 19:08:50.868  INFO 520 --- [           main] o.apache.catalina.core.StandardService   : Starting service [Tomcat]
    2021-12-20 19:08:50.870  INFO 520 --- [           main] org.apache.catalina.core.StandardEngine  : Starting Servlet Engine: Apache Tomcat/8.5.23
    2021-12-20 19:08:51.056  INFO 520 --- [ost-startStop-1] o.a.c.c.C.[Tomcat].[localhost].[/]       : Initializing Spring embedded WebApplicationContext
    2021-12-20 19:08:51.060  INFO 520 --- [ost-startStop-1] o.s.web.context.ContextLoader            : Root WebApplicationContext: initialization completed in 1732 ms
    2021-12-20 19:08:51.330  INFO 520 --- [ost-startStop-1] o.s.b.w.servlet.ServletRegistrationBean  : Mapping servlet: 'dispatcherServlet' to [/]
    2021-12-20 19:08:51.336  INFO 520 --- [ost-startStop-1] o.s.b.w.servlet.FilterRegistrationBean   : Mapping filter: 'characterEncodingFilter' to: [/*]
    2021-12-20 19:08:51.337  INFO 520 --- [ost-startStop-1] o.s.b.w.servlet.FilterRegistrationBean   : Mapping filter: 'hiddenHttpMethodFilter' to: [/*]
    2021-12-20 19:08:51.337  INFO 520 --- [ost-startStop-1] o.s.b.w.servlet.FilterRegistrationBean   : Mapping filter: 'httpPutFormContentFilter' to: [/*]
    2021-12-20 19:08:51.337  INFO 520 --- [ost-startStop-1] o.s.b.w.servlet.FilterRegistrationBean   : Mapping filter: 'requestContextFilter' to: [/*]
    2021-12-20 19:08:51.614  INFO 520 --- [           main] s.w.s.m.m.a.RequestMappingHandlerAdapter : Looking for @ControllerAdvice: org.springframework.boot.context.embedded.AnnotationConfigEmbeddedWebApplicationContext@365c30cc: startup date [Mon Dec 20 19:08:49 CST 2021]; root of context hierarchy
    2021-12-20 19:08:51.655  INFO 520 --- [           main] s.w.s.m.m.a.RequestMappingHandlerMapping : Mapped "{[/error]}" onto public org.springframework.http.ResponseEntity<java.util.Map<java.lang.String, java.lang.Object>> org.springframework.boot.autoconfigure.web.BasicErrorController.error(javax.servlet.http.HttpServletRequest)
    2021-12-20 19:08:51.656  INFO 520 --- [           main] s.w.s.m.m.a.RequestMappingHandlerMapping : Mapped "{[/error],produces=[text/html]}" onto public org.springframework.web.servlet.ModelAndView org.springframework.boot.autoconfigure.web.BasicErrorController.errorHtml(javax.servlet.http.HttpServletRequest,javax.servlet.http.HttpServletResponse)
    2021-12-20 19:08:51.678  INFO 520 --- [           main] o.s.w.s.handler.SimpleUrlHandlerMapping  : Mapped URL path [/webjars/**] onto handler of type [class org.springframework.web.servlet.resource.ResourceHttpRequestHandler]
    2021-12-20 19:08:51.678  INFO 520 --- [           main] o.s.w.s.handler.SimpleUrlHandlerMapping  : Mapped URL path [/**] onto handler of type [class org.springframework.web.servlet.resource.ResourceHttpRequestHandler]
    2021-12-20 19:08:51.703  INFO 520 --- [           main] o.s.w.s.handler.SimpleUrlHandlerMapping  : Mapped URL path [/**/favicon.ico] onto handler of type [class org.springframework.web.servlet.resource.ResourceHttpRequestHandler]
    2021-12-20 19:08:51.797  INFO 520 --- [           main] o.s.j.e.a.AnnotationMBeanExporter        : Registering beans for JMX exposure on startup
    2021-12-20 19:08:51.843  INFO 520 --- [           main] s.b.c.e.t.TomcatEmbeddedServletContainer : Tomcat started on port(s): 8080 (http)
    ApplicationRunner...run....
    CommandLineRunner...run...[]
    IOC容器创建完毕
    SpringApplicationRunListener...finished...
    2021-12-20 19:08:51.847  INFO 520 --- [           main] c.n.s.SpringBoot07RunApplication         : Started SpringBoot07RunApplication in 2.852 seconds (JVM running for 4.075)
  • 相关阅读:
    UICollectionView 布局
    ios 调用支付宝
    iOS POST 上传图片
    ios 判断字符串是否为空
    让写代码成为每天的习惯
    gocron_跨平台定时任务管理器
    monkey做安卓APP的黑盒自动化测试
    Android自动化测试框架分析
    联合查询中where 和and的区别
    JIRA中导出BUG列表是CSV格式的,打开后是乱码
  • 原文地址:https://www.cnblogs.com/niujifei/p/15707360.html
Copyright © 2020-2023  润新知