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

How to understand the way springboot loads META-INF/spring.factories

2025-01-19 Update From: SLTechnology News&Howtos shulou NAV: SLTechnology News&Howtos > Development >

Share

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

This article focuses on "how to understand how springboot loads META-INF/spring.factories". Interested friends may wish to have a look at it. The method introduced in this paper is simple, fast and practical. Now let the editor take you to learn how to understand the way springboot loads META-INF/spring.factories.

Catalogue

Springboot loads META-INF/spring.factories

User application Application

What is the significance of establishing META-INF/spring.factories files

How do we usually inject Bean into the container

Springboot loads META-INF/spring.factories user application ApplicationConfigurableApplicationContext context = SpringApplication.run (NacosSpringBootYamlApplication.class, args)

SpringApplication class

Public static ConfigurableApplicationContext run (Class primarySource, String... Args) {return run (new Class [] {primarySource}, args);} / / where Class is the array public static ConfigurableApplicationContext run (Class [] primarySources, String [] args) {return new SpringApplication (primarySources) .run (args);} public SpringApplication (Class...) PrimarySources) {this (null, primarySources);} public SpringApplication (ResourceLoader resourceLoader, Class...) PrimarySources) {this.resourceLoader = resourceLoader; Assert.notNull (primarySources, "PrimarySources must not be null"); this.primarySources = new LinkedHashSet (Arrays.asList (primarySources)); / / here is the instance of SpringMvcApplication this.webApplicationType = WebApplicationType.deduceFromClasspath (); / / deduce (inferred) web type (servlet, reactive, NoWeb) setInitializers ((Collection) getSpringFactoriesInstances (ApplicationContextInitializer.class)) / / loading the contents of all spring.factories files into the cache finds all ApplicationContextInitializer implementation classes declared in * META-INF/spring.factories* and instantiating setListeners ((Collection) getSpringFactoriesInstances (ApplicationListener.class)); / / finding all ApplicationListener implementation classes declared in * META-INF/spring.factories* and instantiating this.mainApplicationClass = deduceMainApplicationClass () / / get the class object that currently executes the main method. Here is the instance of SpringMvcApplication.

Load all the spring.factories under the classLoader into the cache

If the cache already exists, the data is returned directly according to key.

/ * * key: key value of spring.factories: grouping different value of the same key into list according to key * / private static Map loadSpringFactories (@ Nullable ClassLoader classLoader) {MultiValueMap result = cache.get (classLoader); if (result! = null) {/ / has been processed and returned to return result directly } / / url: / / FileGear peg repositoryGetWork repositoryGetWork Springframe spring.factories try 5.1.9.RELEASEGRELEASE.jarpaste try MEMETA INFleSpringSpring.faceting try {/ / get the file Enumeration urls = (RELEASE! = null? ClassLoader.getResources (FACTORIES_RESOURCE_LOCATION): ClassLoader.getSystemResources (FACTORIES_RESOURCE_LOCATION)); result = new LinkedMultiValueMap (); while (urls.hasMoreElements ()) {URL url = urls.nextElement (); UrlResource resource = new UrlResource (url); Properties properties = PropertiesLoaderUtils.loadProperties (resource) / / get the content of spring.factories for (Map.Entry entry: properties.entrySet ()) {/ / key: key value of spring.factories: value String factoryClassName of spring.factories = ((String) entry.getKey ()). Trim (); / / key for of spring.factories (String factoryName: StringUtils.commaDelimitedListToStringArray ((String) entry.getValue () {/ / value separates result.add (factoryClassName, factoryName.trim ()) based on commas / / factoryClassName is actually the key of spring.factories because value is a List type MultiValueMap value has multiple}} cache.put (classLoader, result); return result;} catch (IOException ex) {throw new IllegalArgumentException ("Unable to load factories from location [" + FACTORIES_RESOURCE_LOCATION + "]", ex);}}

Flow chart

What is the significance of creating a META-INF/spring.factories file? how do we inject Bean into the container @ Configuration@EnableConfigurationProperties (HelloProperties.class) public class HelloServiceAutoConfiguration {@ Autowired HelloProperties helloProperties; @ Bean public HelloService helloService () {HelloService service = new HelloService (); service.setHelloProperties (helloProperties); return service;}}

Generally, the configuration file is created using @ Configuration, in which @ Bean is used to load bean.

Or use the @ Compont annotation to inject a class into a class

Note:

At the entrance of our main program:

@ SpringBootApplication what's in this comment

Target (ElementType.TYPE) @ Retention (RetentionPolicy.RUNTIME) @ Documented@Inherited@SpringBootConfiguration@EnableAutoConfiguration@ComponentScan (excludeFilters = {@ Filter (type = FilterType.CUSTOM, classes = TypeExcludeFilter.class), @ Filter (type = FilterType.CUSTOM, classes = AutoConfigurationExcludeFilter.class)}) public @ interface SpringBootApplication {

Note @ EnableAutoConfiguration inside

The @ ComponentScan annotation refers to the basepackage where the entry program class that scans the @ SpringBootApplication annotation resides

All bean with @ Component annotations to inject into the container.

But

If you add the jar package that maven coordinates depend on, how do you add Bean outside the root directory of the project?

This is when the role of the annotation @ EnableAutoConfiguration comes.

The class AutoConfigurationImportSelector is imported:

There is a method in this class

/ * Return the auto-configuration class names that should be considered. By default * this method will load candidates using {@ link SpringFactoriesLoader} with * {@ link # getSpringFactoriesLoaderFactoryClass ()}. * @ param metadata the source metadata * @ param attributes the {@ link # getAttributes (AnnotationMetadata) annotation * attributes} * @ return a list of candidate configurations * / protected List getCandidateConfigurations (AnnotationMetadata metadata, AnnotationAttributes attributes) {List configurations = SpringFactoriesLoader.loadFactoryNames (getSpringFactoriesLoaderFactoryClass (), getBeanClassLoader ()); Assert.notEmpty (configurations, "No auto configuration classes found in META-INF/spring.factories. If you "+" are using a custom packaging, make sure that file is correct. "); return configurations;}

The @ EnableAutoConfiguration annotation registers the bean outside the project package. On the other hand, the spring.factories file is used to record the bean class names that need to be registered outside the project package.

Why do you need spring.factories files

Because the entry file in our entire project will only scan the @ Compont @ Configuration annotations in the whole project.

However, if we refer to other jar packages, and other jar packages only have annotations such as @ Bean or @ Compont, they will not be scanned.

Unless the jar package you introduced does not have Bean loaded into the container

So we load it by writing the / META-INF/spring.factories file.

At this point, I believe you have a deeper understanding of "how to understand the way springboot loads META-INF/spring.factories". You might as well do it in practice. Here is the website, more related content can enter the relevant channels to inquire, follow us, continue to learn!

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

Development

Wechat

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

12
Report