• SpringBoot Profile源码介绍


    进入上一篇使用profile的load()方法(ConfigFileApplicationListener类中)

    1、initializeProfiles();

    1)进入initializeProfiles方法。初始化Profiles,将所有的profile增加到prifiles集合中

    		private void initializeProfiles() {
    			// The default profile for these purposes is represented as null. We add it
    			// first so that it is processed first and has lowest priority.
    			this.profiles.add(null);
    			Set<Profile> activatedViaProperty = getProfilesActivatedViaProperty();
    			this.profiles.addAll(getOtherActiveProfiles(activatedViaProperty));
    			// Any pre-existing active profiles set via property sources (e.g.
    			// System properties) take precedence over those added in config files.
    			addActiveProfiles(activatedViaProperty);
    			if (this.profiles.size() == 1) { // only has null profile
    				for (String defaultProfileName : this.environment.getDefaultProfiles()) {
    					Profile defaultProfile = new Profile(defaultProfileName, true);
    					this.profiles.add(defaultProfile);
    				}
    			}
    		}
    

      


    2、load(profile, this::getPositiveProfileFilter, addToLoaded(MutablePropertySources::addLast, false));

    遍历prifles,

    第一个prifile为空,进入load方法

    	private void load(Profile profile, DocumentFilterFactory filterFactory, DocumentConsumer consumer) {
    			getSearchLocations().forEach((location) -> {
    				boolean isFolder = location.endsWith("/");
    				Set<String> names = isFolder ? getSearchNames() : NO_SEARCH_NAMES;
    				names.forEach((name) -> load(location, name, profile, filterFactory, consumer));
    			});
    		}
    

     

    进入getSearchLocations方法,获得如下图,classpath:/等查询路径

     然后遍历上一步获取的查询路径

     进入names.forEach((name) -> load(location, name, profile, filterFactory, consumer))的load方法,name值为application

    然后进入loadForFileExtension(loader, location + name, "." + fileExtension, profile, filterFactory,      consumer);

     

     最终进入load(loader, prefix + fileExtension, profile, profileFilter, consumer);这个方法

    private void load(PropertySourceLoader loader, String location, Profile profile, DocumentFilter filter,
    				DocumentConsumer consumer) {
    			try {
    				Resource resource = this.resourceLoader.getResource(location);
    				if (resource == null || !resource.exists()) {
    					if (this.logger.isTraceEnabled()) {
    						StringBuilder description = getDescription("Skipped missing config ", location, resource,
    								profile);
    						this.logger.trace(description);
    					}
    					return;
    				}
    				if (!StringUtils.hasText(StringUtils.getFilenameExtension(resource.getFilename()))) {
    					if (this.logger.isTraceEnabled()) {
    						StringBuilder description = getDescription("Skipped empty config extension ", location,
    								resource, profile);
    						this.logger.trace(description);
    					}
    					return;
    				}
    				String name = "applicationConfig: [" + location + "]";
    				List<Document> documents = loadDocuments(loader, name, resource);
    				if (CollectionUtils.isEmpty(documents)) {
    					if (this.logger.isTraceEnabled()) {
    						StringBuilder description = getDescription("Skipped unloaded config ", location, resource,
    								profile);
    						this.logger.trace(description);
    					}
    					return;
    				}
    				List<Document> loaded = new ArrayList<>();
    				for (Document document : documents) {
    					if (filter.match(document)) {
    						addActiveProfiles(document.getActiveProfiles());
    						addIncludedProfiles(document.getIncludeProfiles());
    						loaded.add(document);
    					}
    				}
    				Collections.reverse(loaded);
    				if (!loaded.isEmpty()) {
    					loaded.forEach((document) -> consumer.accept(profile, document));
    					if (this.logger.isDebugEnabled()) {
    						StringBuilder description = getDescription("Loaded config file ", location, resource, profile);
    						this.logger.debug(description);
    					}
    				}
    			}
    			catch (Exception ex) {
    				throw new IllegalStateException("Failed to load property " + "source from location '" + location + "'",
    						ex);
    			}
    		}
    

      

    然后进入List<Document> documents = loadDocuments(loader, name, resource);

    private List<Document> loadDocuments(PropertySourceLoader loader, String name, Resource resource)
    				throws IOException {
    			DocumentsCacheKey cacheKey = new DocumentsCacheKey(loader, resource);
    			List<Document> documents = this.loadDocumentsCache.get(cacheKey);
    			if (documents == null) {
    				List<PropertySource<?>> loaded = loader.load(name, resource);
    				documents = asDocuments(loaded);
    				this.loadDocumentsCache.put(cacheKey, documents);
    			}
    			return documents;
    		}
    

      

    进入List<PropertySource<?>> loaded = loader.load(name, resource); 加载后的属性如下图所示

     

    3、resetEnvironmentProfiles(this.processedProfiles);

    设置激活的prifile有哪些

    		private void resetEnvironmentProfiles(List<Profile> processedProfiles) {
    			String[] names = processedProfiles.stream()
    					.filter((profile) -> profile != null && !profile.isDefaultProfile()).map(Profile::getName)
    					.toArray(String[]::new);
    			this.environment.setActiveProfiles(names);
    		}
    

      


    4、load(null, this::getNegativeProfileFilter, addToLoaded(MutablePropertySources::addFirst, true));

    防止前面循环没有进入,load默认的profile


    5、addLoadedPropertySources(); 将获得的profile的属性增加到属性源中

    
    
    	private void addLoadedPropertySources() {
    			MutablePropertySources destination = this.environment.getPropertySources();
    			List<MutablePropertySources> loaded = new ArrayList<>(this.loaded.values());
    			Collections.reverse(loaded);
    			String lastAdded = null;
    			Set<String> added = new HashSet<>();
    			for (MutablePropertySources sources : loaded) {
    				for (PropertySource<?> source : sources) {
    					if (added.add(source.getName())) {
    						addLoadedPropertySource(destination, lastAdded, source);
    						lastAdded = source.getName();
    					}
    				}
    			}
    		}
    
    
    

      如下图所示

     
  • 相关阅读:
    「Kafka」Kafka中offset偏移量提交
    「Flink」Flink中的时间类型
    Hash存储模型、B-Tree存储模型、LSM存储模型介绍
    「Flink」RocksDB介绍以及Flink对RocksDB的支持
    「Flink」理解流式处理重要概念
    「Flink」Flink 1.9 WebUI运行作业界面分析
    「Spark」Spark SQL Thrift Server运行方式
    「Flink」配置使用Flink调试WebUI
    Django基础篇之简介和项目创建
    在python文件中操作django orm提示环境变量设置问题
  • 原文地址:https://www.cnblogs.com/linlf03/p/12389396.html
Copyright © 2020-2023  润新知