SpringBoot内置Tomcat启动原理源码分析( 二 )


SpringBoot内置Tomcat启动原理源码分析

文章插图
 
 5、启动tomcat容器
创建webServer后在refresh()方法中的finishRefresh()完成tomcat的启动 。
最终会调用 TomcatWebServer中的start()方法启动tomcat容器 。
protected void finishRefresh() {// Clear context-level resource caches (such as ASM metadata from scanning).clearResourceCaches();// Initialize lifecycle processor for this context.initLifecycleProcessor();// Propagate refresh to lifecycle processor first.// 启动tomcatgetLifecycleProcessor().onRefresh();// Publish the final event.publishEvent(new ContextRefreshedEvent(this));// Participate in LiveBeansView MBean, if active.if (!NativeDetector.inNativeImage()) {LiveBeansView.registerApplicationContext(this);}}@Overridepublic void onRefresh() {startBeans(true);this.running = true;}private void startBeans(boolean autoStartupOnly) {Map<String, Lifecycle> lifecycleBeans = getLifecycleBeans();Map<Integer, LifecycleGroup> phases = new TreeMap<>();lifecycleBeans.forEach((beanName, bean) -> {if (!autoStartupOnly || (bean instanceof SmartLifecycle && ((SmartLifecycle) bean).isAutoStartup())) {int phase = getPhase(bean);phases.computeIfAbsent(phase,p -> new LifecycleGroup(phase, this.timeoutPerShutdownPhase, lifecycleBeans, autoStartupOnly)).add(beanName, bean);}});if (!phases.isEmpty()) {// 遍历启动phases.values().forEach(LifecycleGroup::start);}}public void start() {if (this.members.isEmpty()) {return;}if (logger.isDebugEnabled()) {logger.debug("Starting beans in phase " + this.phase);}Collections.sort(this.members);for (LifecycleGroupMember member : this.members) {doStart(this.lifecycleBeans, member.name, this.autoStartupOnly);}}private void doStart(Map<String, ? extends Lifecycle> lifecycleBeans, String beanName, boolean autoStartupOnly) {Lifecycle bean = lifecycleBeans.remove(beanName);if (bean != null && bean != this) {String[] dependenciesForBean = getBeanFactory().getDependenciesForBean(beanName);for (String dependency : dependenciesForBean) {doStart(lifecycleBeans, dependency, autoStartupOnly);}if (!bean.isRunning() &&(!autoStartupOnly || !(bean instanceof SmartLifecycle) || ((SmartLifecycle) bean).isAutoStartup())) {if (logger.isTraceEnabled()) {logger.trace("Starting bean '" + beanName + "' of type [" + bean.getClass().getName() + "]");}try {bean.start();}catch (Throwable ex) {throw new ApplicationContextException("Failed to start bean '" + beanName + "'", ex);}if (logger.isDebugEnabled()) {logger.debug("Successfully started bean '" + beanName + "'");}}}}//WebServerStartStopLifecycle 中start() 方法的实现public void start() {this.weServerManager.start();this.running = true;}void start() {this.handler.initializeHandler();this.webServer.start();this.applicationContext.publishEvent(new ReactiveWebServerInitializedEvent(this.webServer, this.applicationContext));}// 完成对tomcat的启动@Overridepublic void start() throws WebServerException {synchronized (this.monitor) {if (this.started) {return;}try {addPreviouslyRemovedConnectors();Connector connector = this.tomcat.getConnector();if (connector != null && this.autoStart) {performDeferredLoadOnStartup();}checkThatConnectorsHaveStarted();this.started = true;logger.info("Tomcat started on port(s): " + getPortsDescription(true) + " with context path '"+ getContextPath() + "'");}catch (ConnectorStartFailedException ex) {stopSilently();throw ex;}catch (Exception ex) {PortInUseException.throwIfPortBindingException(ex, () -> this.tomcat.getConnector().getPort());throw new WebServerException("Unable to start embedded Tomcat server", ex);}finally {Context context = findContext();ContextBindings.unbindClassLoader(context, context.getNamingToken(), getClass().getClassLoader());}}}同博客: SpringBoot内置Tomcat启动原理源码分析 - sun丶牧羊人 - 博客园




推荐阅读