Network Security Internet Technology Development Database Servers Mobile Phone Android Software Apple Software Computer Software News IT Information

In addition to Weibo, there is also WeChat

Please pay attention

WeChat public account

Shulou

[SpringBoot] exception handling mechanism of source code analysis SpringBoot

2025-01-17 Update From: SLTechnology News&Howtos shulou NAV: SLTechnology News&Howtos > Internet Technology >

Share

Shulou(Shulou.com)06/03 Report--

WeChat account: GitShare

Official account of Wechat: a straw that loves to toss.

If you have any questions or suggestions, please leave a message on the official account [1]

Previous continuation

In order to help the majority of SpringBoot users to "know what it is, but also need to know why", the author will deeply analyze the SpringBoot2.0.0.RELEASE version through a series of SpringBoot articles, so that you can have a deep understanding of its internal working principle.

Text

When SpringBoot starts, all available SpringBootExceptionReporter is found and loaded with the following source code:

/ / 7 use SpringFactoriesLoader to find and load all available SpringBootExceptionReporter in the application's classpath

ExceptionReporters = getSpringFactoriesInstances (

SpringBootExceptionReporter.class

New Class [] {ConfigurableApplicationContext.class}, context)

Continue to view the source code of the getSpringFactoriesInstances method:

Private Collection getSpringFactoriesInstances (Class type

Class [] parameterTypes, Object... Args) {

ClassLoader classLoader = Thread.currentThread () .getContextClassLoader ()

/ / find and load all the names of the SpringBootExceptionReporter configured in META-INF/spring.factories under the classpath path

Set names = new LinkedHashSet (SpringFactoriesLoader.loadFactoryNames (type, classLoader))

/ / instantiate all SpringBootExceptionReporter

List instances = createSpringFactoriesInstances (type, parameterTypes, classLoader, args, names)

/ / sort

AnnotationAwareOrderComparator.sort (instances)

/ / return the result

Return instances

}

The code is not difficult to look at, and it is also loaded through Spring's Factories mechanism, which has been explained in detail in previous articles.

SpringBootExceptionReporter@FunctionalInterface

Public interface SpringBootExceptionReporter {

/ * *

* report the startup failure to the user.

, /

Boolean reportException (Throwable failure)

}

SpringBootExceptionReporter is a callback interface that supports custom reporting of SpringApplication startup errors.

There is only one way to report startup failure.

In fact, the current category: org.springframework.boot.diagnostics.FailureAnalyzers

Used to trigger FailureAnalyzer and FailureAnalysisReporter instances loaded from spring.factories.

FailureAnalyzers1, instantiate FailureAnalyzersFailureAnalyzers (ConfigurableApplicationContext context) {

This (context, null)

}

FailureAnalyzers (ConfigurableApplicationContext context, ClassLoader classLoader) {

Assert.notNull (context, "Context must not be null")

This.classLoader = (classLoader = = null? Context.getClassLoader (): classLoader)

This.analyzers = loadFailureAnalyzers (this.classLoader)

PrepareFailureAnalyzers (this.analyzers, context)

}

Get class loader

Load and instantiate all FailureAnalyzer

Find and load all FailureAnalyzer through Spring's Factories mechanism

The org.springframework.boot.diagnostics.FailureAnalyzer configuration in load / META/spring.factories is as follows:

# Failure Analyzers

Org.springframework.boot.diagnostics.FailureAnalyzer=\

Org.springframework.boot.diagnostics.analyzer.BeanCurrentlyInCreationFailureAnalyzer,\

Org.springframework.boot.diagnostics.analyzer.BeanNotOfRequiredTypeFailureAnalyzer,\

Org.springframework.boot.diagnostics.analyzer.BindFailureAnalyzer,\

Org.springframework.boot.diagnostics.analyzer.BindValidationFailureAnalyzer,\

Org.springframework.boot.diagnostics.analyzer.UnboundConfigurationPropertyFailureAnalyzer,\

Org.springframework.boot.diagnostics.analyzer.ConnectorStartFailureAnalyzer,\

Org.springframework.boot.diagnostics.analyzer.NoUniqueBeanDefinitionFailureAnalyzer,\

Org.springframework.boot.diagnostics.analyzer.PortInUseFailureAnalyzer,\

Org.springframework.boot.diagnostics.analyzer.ValidationExceptionFailureAnalyzer,\

Org.springframework.boot.diagnostics.analyzer.InvalidConfigurationPropertyNameFailureAnalyzer,\

Org.springframework.boot.diagnostics.analyzer.InvalidConfigurationPropertyValueFailureAnalyzer

Prepare all the FailureAnalyzer

Private void prepareAnalyzer (ConfigurableApplicationContext context

FailureAnalyzer analyzer) {

If (analyzer instanceof BeanFactoryAware) {

((BeanFactoryAware) analyzer) .setBeanFactory (context.getBeanFactory ())

}

If (analyzer instanceof EnvironmentAware) {

((EnvironmentAware) analyzer) .setEnvironment (context.getEnvironment ())

}

}

Preparation phase: depending on the type of FailureAnalyzer, set its BeanFactory or Environment attribute value.

2 、 FailureAnalyzer@FunctionalInterface

Public interface FailureAnalyzer {

/ * *

* returns the analysis of a given fault, or null if it cannot be analyzed.

, /

FailureAnalysis analyze (Throwable failure)

}

Used to analyze the fault and provide diagnostic information that can be displayed to the user.

3 、 AbstractFailureAnalyzer

FailureAnalyzer abstract base class, is a generic class, the generic parameter is a subclass of Throwable. It implements the analyze method, and the source code is as follows:

@ Override

Public FailureAnalysis analyze (Throwable failure) {

/ / 1. Get an exception of type type in the exception stack in failure

T cause = findCause (failure, getCauseType ())

If (cause! = null) {

/ / 2. If it is not equal to null, then analyze

Return analyze (failure, cause)

}

/ / 3. Cannot be parsed, null is returned

Return null

}

Get an exception of type type in the exception stack in failure.

Protected final E findCause (Throwable failure, Class type) {

While (failure! = null) {

If (type.isInstance (failure)) {

Return (E) failure

}

Failure = failure.getCause ()

}

Return null

}

The concrete realization of AbstractFailureAnalyzer

AbstractInjectionFailureAnalyzer: an abstract base class for analyzing injection exceptions.

3. BeanCurrentlyInCreationFailureAnalyzer: for BeanCurrentlyInCreationException. Analyze BeanCurrentlyInCreationException (circular dependency).

3.3.The BeanNotOfRequiredTypeFailureAnalyzer: analyze the BeanNotOfRequiredTypeException abnormality.

BindFailureAnalyzer: analyze the BindException exception.

BindValidationFailureAnalyzer: analyze BindValidationException or BindException exceptions.

ConnectorStartFailureAnalyzer: analyze ConnectorStartFailedException (thrown when tomcat port is occupied) exception.

DataSourceBeanCreationFailureAnalyzer: analyze the DataSourceBeanCreationException exception.

HikariDriverConfigurationFailureAnalyzer: it analyzes Hikari configuration failures caused by the use of the unsupported "dataSourceClassName" attribute.

3.9. InvalidConfigurationPropertyNameFailureAnalyzer: analyze InvalidConfigurationPropertyNameException anomalies.

3.10. InvalidConfigurationPropertyValueFailureAnalyzer: analyze the InvalidConfigurationPropertyValueException exception.

3.11. NoUniqueBeanDefinitionFailureAnalyzer: analyze the NoUniqueBeanDefinitionException exception and implement the BeanFactoryAware interface.

3.12. PortInUseFailureAnalyzer: analyze the PortInUseException (thrown when the port is occupied when the jetty,undertow container starts).

3.13. UnboundConfigurationPropertyFailureAnalyzer: analyze the BindException exception.

3.14. ValidationExceptionFailureAnalyzer: the generic parameter is ValidationException (triggered when validation-related annotations are used, but no relevant implementation is added, it is generally not easy to trigger, because once a spring-boot-starter-web dependency is added, hibernate-validator will be added).

4. Failure report (FailureAnalysisReporter) @ FunctionalInterface

Public interface FailureAnalysisReporter {

/ * *

* report the failure result (failureAnalysis) to the user

, /

Void report (FailureAnalysis analysis)

}

Failed result reporting API, which reports the failed result information to the user

In fact, the current category: LoggingFailureAnalysisReporter

Public final class LoggingFailureAnalysisReporter implements FailureAnalysisReporter {

Private static final Log logger = LogFactory

.getLog (LoggingFailureAnalysisReporter.class)

@ Override

Public void report (FailureAnalysis failureAnalysis) {

If (logger.isDebugEnabled ()) {

Logger.debug ("Application failed to start due to an exception"

FailureAnalysis.getCause ()

}

If (logger.isErrorEnabled ()) {

Logger.error (buildMessage (failureAnalysis))

}

}

Private String buildMessage (FailureAnalysis failureAnalysis) {

StringBuilder builder = new StringBuilder ()

Builder.append (String.format ("% n% n"))

Builder.append (String.format ("* * n"))

Builder.append (String.format ("APPLICATION FAILED TO START%n"))

Builder.append (String.format ("* *% n% n"))

Builder.append (String.format ("Description:%n%n"))

Builder.append (String.format ("% s% n", failureAnalysis.getDescription ()

If (StringUtils.hasText (failureAnalysis.getAction () {

Builder.append (String.format ("% nAction:%n%n"))

Builder.append (String.format ("% s% n", failureAnalysis.getAction ()

}

Return builder.toString ()

}

}

Print the failure error message by means of a log.

Summary

Spring code uses a lot of design patterns, so it is always read around, and I feel that it is less readable. Today, I originally wanted to draw the relevant class diagram of the exception handling mechanism, but found that the relationship between the interface and the class here is relatively simple, so I am lazy. If you are not clear enough through this article, you can draw a picture of the class, which will help you understand.

Postscript

In order to help the majority of SpringBoot users to "know what it is, but also need to know why", the author will deeply analyze the SpringBoot2.0.0.RELEASE version through a series of SpringBoot articles, so that you can have a deep understanding of its internal working principle.

List of historical articles in this series

1. [SpringBoot] use SpringBoot to quickly build and start the project

2. [SpringBoot] explain the startup process of SpringBoot application in detail

3. [SpringBoot] in-depth analysis of the application type identification mechanism of SpringBoot

4. [SpringBoot] analyze the Spring Factories mechanism in SpringBoot deeply and simply.

5. [SpringBoot] explain in detail the first three steps of the run method of SpringApplication in SpringBoot

6. [SpringBoot] illustrate the Environment mechanism of Spring

7. [SpringBoot] Source code parsing the construction process of SpringBoot application Environment

8. [SpringBoot] Banner mechanism of source code parsing SpringBoot

9. [SpringBoot] illustrate the application context mechanism of SpringBoot

Welcome to subscribe "Shulou Technology Information " to get latest news, interesting things and hot topics in the IT industry, and controls the hottest and latest Internet news, technology news and IT industry trends.

Views: 0

*The comments in the above article only represent the author's personal views and do not represent the views and positions of this website. If you have more insights, please feel free to contribute and share.

Share To

Internet Technology

Wechat

© 2024 shulou.com SLNews company. All rights reserved.

12
Report