Spring source code analysis XV: basic components of spring cloud
Spring cloud does not have only one project, but the general name of the ecosystem composed of many projects, such as
- spring-cloud-netflix : integration of open source components
- spring-cloud-gateway : Gateway
- spring-cloud-kubernetes : Yes kubernetes Integration of
- spring-cloud-config : distributed configuration
- spring-cloud-sleuth : Distributed Link Tracking
- spring-cloud-openfeign : service call
But these projects all rely on one basic project spring-cloud-commons,
Spring cloud commons mainly has three modules
- Spring cloud context: build a Bootstrap container and make it the parent container of the container built by the original spring boot program, so the way to use spring cloud is similar to that of spring boot
- Spring cloud Commons: it provides an abstract layer code for service registration and discovery, load balancing, fuse and other functions in microservices. This abstract layer is independent of the specific implementation. These functions can be implemented by different technologies
- Spring cloud loadbalancer: a client load balancer, similar to Ribbon, used to replace Ribbon (Ribbon has entered maintenance mode)
1. spring-cloud-context
The component is still loaded through the Spring Factories extended loading mechanism, which is set at spring.factories
# Attribute auto assembly org.springframework.boot.autoconfigure.EnableAutoConfiguration=\ org.springframework.cloud.autoconfigure.ConfigurationPropertiesRebinderAutoConfiguration,\ org.springframework.cloud.autoconfigure.LifecycleMvcEndpointAutoConfiguration,\ org.springframework.cloud.autoconfigure.RefreshAutoConfiguration,\ org.springframework.cloud.autoconfigure.RefreshEndpointAutoConfiguration,\ org.springframework.cloud.autoconfigure.WritableEnvironmentEndpointAutoConfiguration # Application listener org.springframework.context.ApplicationListener=\ org.springframework.cloud.bootstrap.BootstrapApplicationListener,\ org.springframework.cloud.bootstrap.LoggingSystemShutdownListener,\ org.springframework.cloud.context.restart.RestartListener # Spring Cloud initialization component org.springframework.cloud.bootstrap.BootstrapConfiguration=\ org.springframework.cloud.bootstrap.config.PropertySourceBootstrapConfiguration,\ org.springframework.cloud.bootstrap.encrypt.EncryptionBootstrapConfiguration,\ org.springframework.cloud.autoconfigure.ConfigurationPropertiesRebinderAutoConfiguration,\ org.springframework.boot.autoconfigure.context.PropertyPlaceholderAutoConfiguration # Spring Boot initialization registration org.springframework.boot.BootstrapRegistryInitializer=\ org.springframework.cloud.bootstrap.RefreshBootstrapRegistryInitializer,\ org.springframework.cloud.bootstrap.TextEncryptorConfigBootstrapper # Environmental post-processing org.springframework.boot.env.EnvironmentPostProcessor=\ org.springframework.cloud.bootstrap.encrypt.DecryptEnvironmentPostProcessor,\ org.springframework.cloud.util.random.CachedRandomPropertySourceEnvironmentPostProcessor
- ConfigurationPropertiesRebinderAutoConfiguration
Automatic configuration assembly of configurationpropertiesbinder - LifecycleMvcEndpointAutoConfiguration
Automatic configuration and assembly of some MVC terminal components - RefreshAutoConfiguration
Auto assemble spring.cloud.refresh configuration - RefreshEndpointAutoConfiguration
Automatic configuration assembly of some refreshable context data terminal components - WritableEnvironmentEndpointAutoConfiguration
Automatic configuration assembly of WritableEnvironmentEndpoint - BootstrapApplicationListener
Cloud application initialization - LoggingSystemShutdownListener
Log extension processing - RestartListener
Application restart information record - PropertySourceBootstrapConfiguration
Configuration property processing during Cloud application initialization - EncryptionBootstrapConfiguration
Initialization configuration of encrypted transmission - RefreshBootstrapRegistryInitializer
Add BootstrapContext Cloud initialization context object to application context object ApplicationContext - TextEncryptorConfigBootstrapper
Text encryption configuration initialization - DecryptEnvironmentPostProcessor
Decryption of encrypted information in transmission - CachedRandomPropertySourceEnvironmentPostProcessor
Support for random value attribute source random.xxx in configuration
The following mainly analyzes the bootstrap applicationlistener and propertysourcebootstrap configuration
1.1. BootstrapApplicationListener
BootstrapApplicationListener
The main function of is to extend the loading location of the configuration file and add the loading component of spring.factories
public class BootstrapApplicationListener implements ApplicationListener<ApplicationEnvironmentPreparedEvent>, Ordered { @Override public void onApplicationEvent(ApplicationEnvironmentPreparedEvent event) { // ... code omitted // Initialize context context = bootstrapServiceContext(environment, event.getSpringApplication(), configName); // ... code omitted } // Initialize context private ConfigurableApplicationContext bootstrapServiceContext(ConfigurableEnvironment environment, final SpringApplication application, String configName) { // ... code omitted String configLocation = environment.resolvePlaceholders("${spring.cloud.bootstrap.location:}"); String configAdditionalLocation = environment .resolvePlaceholders("${spring.cloud.bootstrap.additional-location:}"); Map<String, Object> bootstrapMap = new HashMap<>(); // Extend spring.cloud.bootstrap.location configuration to spring.config.location if (StringUtils.hasText(configLocation)) { bootstrapMap.put("spring.config.location", configLocation); } // Extend the spring.cloud.bootstrap.additional-location configuration to spring.config.additional-location if (StringUtils.hasText(configAdditionalLocation)) { bootstrapMap.put("spring.config.additional-location", configAdditionalLocation); } // ... code omitted // Add the loading component 'org.springframework.cloud.bootstrap.bootstrappconfiguration' of 'spring.factories' through bootstrappimportselector` builder.sources(BootstrapImportSelectorConfiguration.class); } }
public class BootstrapImportSelector implements EnvironmentAware, DeferredImportSelector { @Override public String[] selectImports(AnnotationMetadata annotationMetadata) { // ... code omitted // Load the components specified by 'org. Springframework. Cloud. Bootstrap. Bootstrap configuration' through SpringFactoriesLoader List<String> names = new ArrayList<>( SpringFactoriesLoader.loadFactoryNames(BootstrapConfiguration.class, classLoader)); // spring.cloud.bootstrap.sources in the configuration is also loaded as a bootstrap configuration component names.addAll(Arrays.asList(StringUtils .commaDelimitedListToStringArray(this.environment.getProperty("spring.cloud.bootstrap.sources", "")))); // ... code omitted } }
1.2. PropertySourceBootstrapConfiguration
PropertySourceBootstrapConfiguration
The main functions of are log, Profile and configuration processing for spring cloud
public class PropertySourceBootstrapConfiguration implements ApplicationContextInitializer<ConfigurableApplicationContext>, Ordered { @Override public void initialize(ConfigurableApplicationContext applicationContext) { // ... code omitted MutablePropertySources propertySources = environment.getPropertySources(); // ... code omitted // The distributed configuration function of spring cloud config depends on the custom configuration loading process insertPropertySources(propertySources, composite); // Process the log configuration specified by logging.config String logConfig = environment.resolvePlaceholders("${logging.config:}"); LogFile logFile = LogFile.get(environment); reinitializeLoggingSystem(environment, logConfig, logFile); // Set logging level setLogLevels(applicationContext, environment); // Environment that handles spring.profiles.active activation handleIncludedProfiles(environment); } }
1.3. @BootstrapConfiguration
This annotation is the main annotation of Spring Cloud context, which is used to initialize Spring Cloud components
// Automatic loading is realized through the 'bootstrap importselector' described above. It is used in 'spring.factories' // `Org. Springframework. Cloud. Bootstrap. Bootstrap configuration ` configured class public @interface BootstrapConfiguration {}
2. spring-cloud-commons
The component is still loaded through the Spring Factories extended loading mechanism, which is set at spring.factories
# Attribute auto assembly org.springframework.boot.autoconfigure.EnableAutoConfiguration=\ org.springframework.cloud.client.CommonsClientAutoConfiguration,\ org.springframework.cloud.client.ReactiveCommonsClientAutoConfiguration,\ org.springframework.cloud.client.discovery.composite.CompositeDiscoveryClientAutoConfiguration,\ org.springframework.cloud.client.discovery.composite.reactive.ReactiveCompositeDiscoveryClientAutoConfiguration,\ org.springframework.cloud.client.discovery.simple.SimpleDiscoveryClientAutoConfiguration,\ org.springframework.cloud.client.discovery.simple.reactive.SimpleReactiveDiscoveryClientAutoConfiguration,\ org.springframework.cloud.client.hypermedia.CloudHypermediaAutoConfiguration,\ org.springframework.cloud.client.loadbalancer.AsyncLoadBalancerAutoConfiguration,\ org.springframework.cloud.client.loadbalancer.LoadBalancerAutoConfiguration,\ org.springframework.cloud.client.loadbalancer.reactive.LoadBalancerBeanPostProcessorAutoConfiguration,\ org.springframework.cloud.client.loadbalancer.reactive.ReactorLoadBalancerClientAutoConfiguration,\ org.springframework.cloud.client.serviceregistry.ServiceRegistryAutoConfiguration,\ org.springframework.cloud.commons.httpclient.HttpClientConfiguration,\ org.springframework.cloud.commons.util.UtilAutoConfiguration,\ org.springframework.cloud.configuration.CompatibilityVerifierAutoConfiguration,\ org.springframework.cloud.client.serviceregistry.AutoServiceRegistrationAutoConfiguration,\ org.springframework.cloud.commons.security.ResourceServerTokenRelayAutoConfiguration # Environmental post-processing org.springframework.boot.env.EnvironmentPostProcessor=\ org.springframework.cloud.client.HostInfoEnvironmentPostProcessor # error analysis org.springframework.boot.diagnostics.FailureAnalyzer=\ org.springframework.cloud.configuration.CompatibilityNotMetFailureAnalyzer
- CommonsClientAutoConfiguration
Automatic configuration and assembly of DiscoveryClient and LoadBalancerClient - ReactiveCommonsClientAutoConfiguration
Automatic configuration and assembly of ReactiveDiscoveryClient and ReactiveLoadBalancer - CompositeDiscoveryClientAutoConfiguration
Automatic configuration and assembly of compositediscovery client - ReactiveCompositeDiscoveryClientAutoConfiguration
Automatic configuration and assembly of reactivecompositediscovery client - SimpleDiscoveryClientAutoConfiguration
Automatic configuration and assembly of simplediscovery client - SimpleReactiveDiscoveryClientAutoConfiguration
Automatic configuration and assembly of simplereactive discovery client - CloudHypermediaAutoConfiguration
Automatic configuration and assembly of spring.cloud.hypermedia - AsyncLoadBalancerAutoConfiguration
Automatic configuration and assembly of asynchronous load balancing - LoadBalancerAutoConfiguration
Automatic configuration and assembly of Blocking Load Balancing - LoadBalancerBeanPostProcessorAutoConfiguration
Automatic configuration and assembly of load balancing post-processing - ReactorLoadBalancerClientAutoConfiguration
Automatic configuration and assembly of Reactive load balancing - ServiceRegistryAutoConfiguration
Register ServiceRegistryEndpoint - HttpClientConfiguration
Http client configuration - UtilAutoConfiguration
Automatic configuration assembly of spring.cloud.util - CompatibilityVerifierAutoConfiguration
Automatic configuration and assembly of spring.cloud.compatibility-verifier - AutoServiceRegistrationAutoConfiguration
Automatic configuration and assembly of spring.cloud.service-registry.auto-registration - ResourceServerTokenRelayAutoConfiguration
Automatic configuration and assembly of spring.cloud.mvc.token-relay - HostInfoEnvironmentPostProcessor
Automatically add spring.cloud.client.hostname and spring.cloud.client.ip-address configuration properties - CompatibilityNotMetFailureAnalyzer
Cloud error analysis and processing
2.1. @EnableDiscoveryClient & @LoadBalanced
These two annotations are the main annotations of spring cloud commons, @ EnableDiscoveryClient is used to add a service discovery client, and @ LoadBalanced is used to mark that the request is load balanced
// Automatically instantiate 'EnableDiscoveryClientImportSelector' and load it into the Spring IOC container // Instantiate the class annotated with ` @ EnableDiscoveryClient ', but do not actually register and discover @Import(EnableDiscoveryClientImportSelector.class) public @interface EnableDiscoveryClient {}
// There is no processing, just defining annotations public @interface LoadBalanced {}
@EnableDiscoveryClient and @ LoadBalanced have no substantive processing. They just define the annotation specification and leave it to other components to implement
3. spring-cloud-loadbalancer
The component is still loaded through the Spring Factories extended loading mechanism, which is set at spring.factories
# Attribute auto assembly org.springframework.boot.autoconfigure.EnableAutoConfiguration=\ org.springframework.cloud.loadbalancer.config.LoadBalancerAutoConfiguration,\ org.springframework.cloud.loadbalancer.config.BlockingLoadBalancerClientAutoConfiguration,\ org.springframework.cloud.loadbalancer.config.LoadBalancerCacheAutoConfiguration,\ org.springframework.cloud.loadbalancer.security.OAuth2LoadBalancerClientAutoConfiguration,\ org.springframework.cloud.loadbalancer.config.LoadBalancerStatsAutoConfiguration
- LoadBalancerAutoConfiguration
Automatic configuration and assembly of spring.cloud.loadbalancer - BlockingLoadBalancerClientAutoConfiguration
Automatic configuration assembly of Blocking Load Balancing client - LoadBalancerCacheAutoConfiguration
Automatic configuration and assembly of spring.cloud.loadbalancer.cache - OAuth2LoadBalancerClientAutoConfiguration
Automatic configuration and assembly of spring.cloud.oauth2.load-balanced - LoadBalancerStatsAutoConfiguration
Automatic configuration and assembly of spring.cloud.loadbalancer.stats
Here we mainly analyze loadbalancenautoconfiguration
3.1. LoadBalancerAutoConfiguration
LoadBalancerAutoConfiguration
The main function of spring.cloud.loadbalancer is to complete the automatic configuration and assembly of spring.cloud.loadbalancer and instantiate the load balancing component
// Inherit the annotation of 'LoadBalancerClients' @LoadBalancerClients // Auto assemble 'spring.cloud.loadbalancer' configuration @EnableConfigurationProperties(LoadBalancerProperties.class) // Use 'spring.cloud.loadbalancer.enabled' to start this component @ConditionalOnProperty(value = "spring.cloud.loadbalancer.enabled", havingValue = "true", matchIfMissing = true) public class LoadBalancerAutoConfiguration { // ... code omitted }
Because loadbalancenautoconfiguration inherits LoadBalancerClients
So take a look at LoadBalancerClients
// Automatically instantiate 'LoadBalancerClientConfigurationRegistrar' and load it into the Spring IOC container @Import(LoadBalancerClientConfigurationRegistrar.class) public @interface LoadBalancerClients { // ... code omitted }
Let's see LoadBalancerClientConfigurationRegistrar
public class LoadBalancerClientConfigurationRegistrar implements ImportBeanDefinitionRegistrar { @Override public void registerBeanDefinitions(AnnotationMetadata metadata, BeanDefinitionRegistry registry) { // Get @ LoadBalancerClients annotation Map<String, Object> attrs = metadata.getAnnotationAttributes(LoadBalancerClients.class.getName(), true); if (attrs != null && attrs.containsKey("value")) { // Get the value specified by value in the annotation and register the bean component definition AnnotationAttributes[] clients = (AnnotationAttributes[]) attrs.get("value"); for (AnnotationAttributes client : clients) { registerClientConfiguration(registry, getClientName(client), client.get("configuration")); } } // ... code omitted // Get @ LoadBalancerClient annotation Map<String, Object> client = metadata.getAnnotationAttributes(LoadBalancerClient.class.getName(), true); // Get the value specified by name/value in the annotation and register the bean component definition String name = getClientName(client); if (name != null) { registerClientConfiguration(registry, name, client.get("configuration")); } } }
3.2. @LoadBalancerClients & @LoadBalancerClient
These two annotations are the main annotations of spring cloud loadbalancer, which are used to add load balancing clients
// Automatically instantiate 'LoadBalancerClientConfigurationRegistrar' and load it into the Spring IOC container // Automatically process classes marked with ` @ loadbalancerclients ` & ` @ loadbalancerclient ` annotations @Import(LoadBalancerClientConfigurationRegistrar.class) public @interface LoadBalancerClients { // ... code omitted }
// Automatically instantiate 'LoadBalancerClientConfigurationRegistrar' and load it into the Spring IOC container // Automatically process classes marked with ` @ loadbalancerclients ` & ` @ loadbalancerclient ` annotations @Import(LoadBalancerClientConfigurationRegistrar.class) public @interface LoadBalancerClient { // ... code omitted }
follow-up
More blogs, see https://github.com/senntyou/blogs
Author: Deep (@ senntyou)
Copyright notice: free reproduction - non commercial - non derivative - keep signature( Creative sharing 3.0 License)