[Spring Boot] (7), configuration file loading location

Spring Boot startup scans the application.properties/yml files in the following locations as the Spring Boot default configuration files:

Spring Boot official documentation chapter: Loading the application.properties configuration file

  • External, in the /config subdirectory relative to the directory where the application is running

  • External, in the directory where the application runs

  • Built-in, in the resources/config package

  • Built-in, in the classpath root directory (under the resources directory)


Source code analysis

ConfigFileApplicationListener.class

public class ConfigFileApplicationListener
		implements EnvironmentPostProcessor, SmartApplicationListener, Ordered {

    //...
    
    //default configuration file name
    private static final String DEFAULT_NAMES = "application";

    // Note the order is from least to most specific (last one wins)
	private static final String DEFAULT_SEARCH_LOCATIONS = "classpath:/,classpath:/config/,file:./,file:./config/";
    
    public static final String CONFIG_LOCATION_PROPERTY = "spring.config.location";
    
    public static final String CONFIG_NAME_PROPERTY = "spring.config.name";
    
    //...
}

ConfigFileApplicationListener.load()

public void load() {
        this.propertiesLoader = new PropertySourcesLoader();
        this.activatedProfiles = false;
        this.profiles = Collections.asLifoQueue(new LinkedList<Profile>());
        this.processedProfiles = new LinkedList<Profile>();

        //As mentioned in the previous section, the environment activated by the current profiles will be obtained, the default is default
        Set<Profile> initialActiveProfiles = initializeActiveProfiles();
        this.profiles.addAll(getUnprocessedActiveProfiles(initialActiveProfiles));
        if (this.profiles.isEmpty()) {
            for (String defaultProfileName : this.environment.getDefaultProfiles()) {
                Profile defaultProfile = new Profile(defaultProfileName, true);
                if (!this.profiles.contains(defaultProfile)) {
                    this.profiles.add(defaultProfile);
                }
            }
        }

        this.profiles.add(null);

        while (!this.profiles.isEmpty()) {
            Profile profile = this.profiles.poll();
            //Get the search path of the configuration file
            for (String location : getSearchLocations()) {
                if (!location.endsWith("/")) {
                    // location is a filename already, so don't search for more
                    // filenames
                    load(location, null, profile);
                }
                else {
                    for (String name : getSearchNames()) {
                        load(location, name, profile);
                    }
                }
            }
            this.processedProfiles.add(profile);
        }

        addConfigurationProperties(this.propertiesLoader.getPropertySources());
    }

ConfigFileApplicationListener.getSearchLocations()

private Set<String> getSearchLocations() {
    Set<String> locations = new LinkedHashSet<String>();
    //User-defined configuration file, loaded first, specified by spring.config.location
    if (this.environment.containsProperty(CONFIG_LOCATION_PROPERTY)) {
        for (String path : asResolvedSet(
            this.environment.getProperty(CONFIG_LOCATION_PROPERTY), null)) {
            if (!path.contains("$")) {
                path = StringUtils.cleanPath(path);
                if (!ResourceUtils.isUrl(path)) {
                    path = ResourceUtils.FILE_URL_PREFIX + path;
                }
            }
            locations.add(path);
        }
    }
    
    //get search path
    locations.addAll(
        asResolvedSet(ConfigFileApplicationListener.this.searchLocations,
                      DEFAULT_SEARCH_LOCATIONS));
    return locations;
}

ConfigFileApplicationListener.asResolvedSet()

private Set<String> asResolvedSet(String value, String fallback) {
    List<String> list = Arrays.asList(StringUtils.trimArrayElements(
        StringUtils.commaDelimitedListToStringArray(value != null
                                                    ? this.environment.resolvePlaceholders(value) : fallback)));
    //Reverse the elements, so the search path is actually the opposite of the order defined by DEFAULT_SEARCH_LOCATIONS.
    Collections.reverse(list);
    return new LinkedHashSet<String>(list);
}

ConfigFileApplicationListener.getSearchNames()

private Set<String> getSearchNames() {
    //If there is a configuration with spring.config.name in the environment, use this value as the configuration file name
    if (this.environment.containsProperty(CONFIG_NAME_PROPERTY)) {
        return asResolvedSet(this.environment.getProperty(CONFIG_NAME_PROPERTY),
                             null);
    }
	//Get the default configuration file name, the default is application
    return asResolvedSet(ConfigFileApplicationListener.this.names, DEFAULT_NAMES);
}

PropertySourcesLoader.getAllFileExtensions()

public Set<String> getAllFileExtensions() {
    Set<String> fileExtensions = new LinkedHashSet<String>();
    //Get the suffix names of all configuration files, which are properties, xml, yml, yaml
    for (PropertySourceLoader loader : this.loaders) {
        fileExtensions.addAll(Arrays.asList(loader.getFileExtensions()));
    }
    return fileExtensions;
}

So in fact, Spring Boot supports four configuration file formats:

  • properties

  • xml

  • marl

  • yaml

    And xml is used less, yml and yaml are actually the same format, so properties and yml are commonly used.


PropertySourcesLoader.doLoadIntoGroup()

private PropertySource<?> doLoadIntoGroup(String identifier, String location,
				Profile profile) throws IOException {
    Resource resource = this.resourceLoader.getResource(location);
    PropertySource<?> propertySource = null;
    StringBuilder msg = new StringBuilder();
    if (resource != null && resource.exists()) {
        String name = "applicationConfig: [" + location + "]";
        String group = "applicationConfig: [" + identifier + "]";
        propertySource = this.propertiesLoader.load(resource, group, name,
                                                    (profile == null ? null : profile.getName()));
        if (propertySource != null) {
            msg.append("Loaded ");
            handleProfileProperties(propertySource);
        }
        else {
            msg.append("Skipped (empty) ");
        }
    }
    else {
        msg.append("Skipped ");
    }
    msg.append("config file ");
    msg.append(getResourceDescription(location, resource));
    if (profile != null) {
        msg.append(" for profile ").append(profile);
    }
    if (resource == null || !resource.exists()) {
        msg.append(" resource not found");
        this.logger.trace(msg);
    }
    else {
        this.logger.debug(msg);
    }
    return propertySource;
}

Summarize

  • Read the configuration files with the suffixes of properties, xml, yml, yaml from the four locations: file:./config/, file:./, classpath:/config/, classpath:/

  • The priority is from high to low. For the same attribute configuration, the high-priority configuration will override the low-priority configuration; for other different attribute configurations, they will complement each other.

  • In the case of the same priority, there are application.properties and application.yml at the same time, then the properties in application.properties will override the properties in application.yml, because properties are loaded before yml.

​When viewing the source code, in the getSearchLocations() code, you are prompted to change the default configuration file location through spring.config.location : After the project is packaged, use the command line parameter --spring.config.location=… To start the project, it is used to specify the new location of the configuration file, so that the specified new configuration file and the default loaded configuration file in the package work together to complement the configuration.

1java -jar spring-boot-02-config-SNAPSHOT.jar --spring.config.location=F

Before writing this blog post, the blogger encountered an unsolvable problem, see the link: Spring Boot loading configuration file priority problem ?


=====================Make an advertisement, welcome to pay attention =====================

QQ:
412425870
WeChat public account: Cay Classroom

csdn blog:
http://blog.csdn.net/caychen
Code cloud:
https://gitee.com/caychen/
github:
https://github.com/caychen

Click on the group number or scan the QR code to join the QQ group:

328243383 (1 group)




Click on the group number or scan the QR code to join the QQ group:

180479701 (2 groups)




Guess you like

Origin http://43.154.161.224:23101/article/api/json?id=325709137&siteId=291194637