Spring PropertyPlaceholderHelper详解

简介: 《读尽源码》
  • 类全路径: org.springframework.util.PropertyPlaceholderHelper

parseStringValue

  • org.springframework.util.PropertyPlaceholderHelper#parseStringValue 这个方法是主要方法
protected String parseStringValue(
      String value, PlaceholderResolver placeholderResolver, @Nullable Set<String> visitedPlaceholders) {
   // 占位符所在位置
   int startIndex = value.indexOf(this.placeholderPrefix);
   if (startIndex == -1) {
      return value;
   }
   // 返回值
   StringBuilder result = new StringBuilder(value);
   while (startIndex != -1) {
      // 寻找结尾占位符
      int endIndex = findPlaceholderEndIndex(result, startIndex);
      if (endIndex != -1) {
         // 返回值切分留下中间内容
         String placeholder = result.substring(startIndex + this.placeholderPrefix.length(), endIndex);
         String originalPlaceholder = placeholder;
         if (visitedPlaceholders == null) {
            visitedPlaceholders = new HashSet<>(4);
         }
         if (!visitedPlaceholders.add(originalPlaceholder)) {
            throw new IllegalArgumentException(
                  "Circular placeholder reference '" + originalPlaceholder + "' in property definitions");
         }
         // Recursive invocation, parsing placeholders contained in the placeholder key.
         // 递归获取占位符内容
         placeholder = parseStringValue(placeholder, placeholderResolver, visitedPlaceholders);
         // Now obtain the value for the fully resolved key...
         // 解析占位符内容获得真正的属性值
         String propVal = placeholderResolver.resolvePlaceholder(placeholder);
         if (propVal == null && this.valueSeparator != null) {
            int separatorIndex = placeholder.indexOf(this.valueSeparator);
            if (separatorIndex != -1) {
               String actualPlaceholder = placeholder.substring(0, separatorIndex);
               String defaultValue = placeholder.substring(separatorIndex + this.valueSeparator.length());
               propVal = placeholderResolver.resolvePlaceholder(actualPlaceholder);
               if (propVal == null) {
                  propVal = defaultValue;
               }
            }
         }
         if (propVal != null) {
            // Recursive invocation, parsing placeholders contained in the
            // previously resolved placeholder value.
            propVal = parseStringValue(propVal, placeholderResolver, visitedPlaceholders);
            result.replace(startIndex, endIndex + this.placeholderSuffix.length(), propVal);
            if (logger.isTraceEnabled()) {
               logger.trace("Resolved placeholder '" + placeholder + "'");
            }
            startIndex = result.indexOf(this.placeholderPrefix, startIndex + propVal.length());
         }
         else if (this.ignoreUnresolvablePlaceholders) {
            // Proceed with unprocessed value.
            startIndex = result.indexOf(this.placeholderPrefix, endIndex + this.placeholderSuffix.length());
         }
         else {
            throw new IllegalArgumentException("Could not resolve placeholder '" +
                  placeholder + "'" + " in value \"" + value + "\"");
         }
         visitedPlaceholders.remove(originalPlaceholder);
      }
      else {
         startIndex = -1;
      }
   }
   return result.toString();
}Copy to clipboardErrorCopied

在这里还需要关注一个接口

  • 占位符解析.
@FunctionalInterface
public interface PlaceholderResolver {
   /**
    * Resolve the supplied placeholder name to the replacement value.
    * @param placeholderName the name of the placeholder to resolve
    * @return the replacement value, or {@code null} if no replacement is to be made
    */
   @Nullable
   String resolvePlaceholder(String placeholderName);
}Copy to clipboardErrorCopied

占位符解析请查看: PlaceholderResolver

findPlaceholderEndIndex

  • 寻找结尾占位符索引
/**
 * 寻找结尾占位符索引
 */
private int findPlaceholderEndIndex(CharSequence buf, int startIndex) {
   int index = startIndex + this.placeholderPrefix.length();
   int withinNestedPlaceholder = 0;
   while (index < buf.length()) {
      if (StringUtils.substringMatch(buf, index, this.placeholderSuffix)) {
         if (withinNestedPlaceholder > 0) {
            withinNestedPlaceholder--;
            index = index + this.placeholderSuffix.length();
         }
         else {
            return index;
         }
      }
      else if (StringUtils.substringMatch(buf, index, this.simplePrefix)) {
         withinNestedPlaceholder++;
         index = index + this.simplePrefix.length();
      }
      else {
         index++;
      }
   }
   return -1;
}


相关文章
|
7月前
|
XML Java 开发者
【Spring】Spring是什么?
【Spring】Spring是什么?
【Spring】Spring是什么?
|
2月前
|
XML Java 数据格式
Spring介绍
【10月更文挑战第9天】
|
6月前
|
XML Java 数据格式
|
缓存 Java 数据库连接
|
7月前
|
Java 测试技术 容器
初识spring
初识spring
32 0
|
7月前
|
存储 Java 数据库
【Spring】——Spring简单 读和取(一)
【Spring】——Spring简单 读和取
80 0
【Spring】——Spring简单 读和取(一)
|
7月前
|
存储 设计模式 Java
【Spring】——Spring简单 读和取(二)
【Spring】——Spring简单 读和取
64 0
【Spring】——Spring简单 读和取(二)
|
7月前
|
前端开发 Java 开发者
【Spring】 ——初识Spring
【Spring】 ——初识Spring
59 0
|
Java Spring 容器
Spring中那些BeanFactoryPostProcessors详解(一)
Spring中那些BeanFactoryPostProcessors详解(一)
62 0
|
XML 开发框架 Java
Spring详细总结1
1.Spring简介 1.1 Spring概述 (1)Spring 是最受欢迎的企业级 Java 应用程序开发框架,数以百万的来自世界各地的开发人员使用Spring 框架 来创建性能好(spring为我们提供对象的创建)、易于测试(整合了Junit)、可重用的代码(例如把事务的代码放到切面中, 再把切面作用于方法中)。
193 0
Spring详细总结1