Spring中手动增加配置文件中占位符引用的变量
在项目中遇到一个这样的需求,项目的配置文件由外部传入,这时spring配置文件那些占位符变量该如何取值呢?
解决这个问题的做法有几种,我想到的大概有以下三种:
1.通过系统属性来实现,把外部传入的配置信息保存到系统属性,spring配置中的占位符可以获取到系统属性的值.这种做法很简单,调用System.setProperty() | setProperties()方法就可以实现。
2.把外部的配置信息动态写入到配置文件,生成配置文件之后再启动spring.spring的配置文件中需要把生成配置文件的配置写到PropertyPlaceholderConfigurer的location属性。这种方式有点绕,还可以更优雅一点。
3.我们知道spring配置文件中占位符替换是在PropertyPlaceholderConfigurer类中实现的,也就是说该类中必定维护了一种占位符变量与该值的Map数据结构(实际上是Properties,当然Properties本身就是基于Hashtable实现的),我们只需要找到该集合,在spring加载完其他配置文件以后往这个集合中添加我们自定义的配置,也可以同样解决这个需求.并且个人觉得这个方式相比之前两种都有意思点。
这篇文章我们主要讨论第三种实现方式,首先说解决办法,之后再简单说下这样的原因。解决办法就是自定义一个类,继承PropertyPlaceholderConfigurer,复写processProperties(),实际上该类是spring中的一个后处理器(BeanFactoryPostProcessor)。
import java.util.Map;
import java.util.Properties; import org.springframework.beans.BeansException;
import org.springframework.beans.factory.config.ConfigurableListableBeanFactory;
import org.springframework.beans.factory.config.PropertyPlaceholderConfigurer;
/**
* 扩展PropertyPlaceholderConfigurer类,不仅可以加载配置文件中的配置信息,还可以手动增加其他配置
* 使用该类前,在spring配置文件中增加如下配置:
<bean class=" com.xxx.aaa.context.ExternalPropertyResourceInjector">
<!-- 如果还要加载module.properties文件中的配置信息,添加如下配置 -->
<property name="locations">
<list>
<value>classpath:module.properties</value>
</list>
</property>
</bean>
注:该类是PropertyPlaceholderConfigurer的子类,如果配置了该类,无需在重复配置PropertyPlaceholderConfigurer * @see org.springframework.beans.factory.config.PropertyPlaceholderConfigurer
* @author Jack
*/
public class ExternalPropertyResourceInjector extends PropertyPlaceholderConfigurer { @Override
protected void processProperties(ConfigurableListableBeanFactory beanFactory, Properties props) throws BeansException {
Map<String,String> map = new HashMap<String,String>();
// map.put(key,value) ... 添加配置信息
props.putAll(map);
super.processProperties(beanFactory, props);
} }
配置bean:
<bean class=" com.xxx.aaa.context.ExternalPropertyResourceInjector">
<!-- 如果还要加载其他配置文件,配置locations属性即可
<property name="locations">
<list>
<value>classpath:module.properties</value>
</list>
</property>
-->
</bean>
上面说了解决的办法,现在来看下解决该问题两个关键的地方,其一,在于弄清楚spring在哪个地方替换配置文件中所使用到占位符?第二个关键在于找到spring加载占位符中变量值配置文件之后保存配置的集合。这两个点都需要对照源码才能找到.
这两个关键的地方都都可以从PropertyPlaceholderHelper可以入手.在replacePlaceholders()方法处设置断点,debug模式下可以清晰看到占位符的替换过程。

在parseStringValue()方法中的147行可以看到占位符取值来源何处.

从以上两点顺藤摸瓜就能找到spring加载配置文件并进行占位符替换的流程。
Spring中手动增加配置文件中占位符引用的变量的更多相关文章
- SQL 引号中的问号在PrepareStatement 中不被看作是占位符
SQL 引号中的问号在PrepareStatement 中不被看作是占位符. 如:SELECT P.NAME, S.YEAR, S.QUANTITY FROM SALES S LEFT JOIN PR ...
- spring boot 项目从配置文件中读取maven 的pom.xml 文件标签的内容。
需求: 将pom.xml 文件中的版本号读取到配置文件并打印到日志中. 第一步: 在pom.xml 中添加以下标签. 第二步: 将version 标签的值读取到配置文件中 这里使用 @@ 而不是 ...
- mybatis 中的 xml 配置文件中 ‘<’、 ‘>’ 处理
mybatis 中的 xml 配置文件中 '<'. '>' 处理 1.使用转义字符将 '<'. '>' 替换掉. 描述 字符 转义字符 小于号 < < 大于号 &g ...
- Spring源码解析之PropertyPlaceholderHelper(占位符解析器)
Spring源码解析之PropertyPlaceholderHelper(占位符解析器) https://blog.csdn.net/weixin_39471249/article/details/7 ...
- Spring import配置文件使用占位符
import使用占位符 连接池切换导入配置的代码: <import resource="classpath:META-INF/spring/spring-${db.connection ...
- spring 配置参数从配置文件中加载到PropertiesFactoryBean 和配置参数从数据库加载到PropertiesFactoryBean 的实现,及项目中的相关应用
1.加载.properties文件中的配置参数加载到PropertiesFactoryBean容器中 <bean id="configProperties" class=&q ...
- PHP中函数sprintf .vsprintf (占位符)
sprintf()格式化字符串写入一个变量中. vsprintf()格式化字符串些写入变量中. <?php $num1 = 123; $num2 = 456; $txt = vsprintf(& ...
- Spring中获取外部配置文件中的属性值
很多时候需要将配置信息从程序中剥离粗来,Spring现在提供的方法是通过@Value注解和<context:placeholder>来获取配置文件中的配置信息.这里给出一个简单的例子. 首 ...
- golang中打印格式化的一些占位符
package main import ( "fmt" ) func main() { var a byte = 255 // byte = uint8 rune = int32 ...
随机推荐
- webapi找到了与该请求匹配的多个操作
关于这个问题是路由在找方法的时候层没有指定对,同一个链接,同样的参数导致路由找不到方法导致的报错,可以在WebApiConfig中多配置一层,比如"api/{controller}/{act ...
- Head First Python学习笔记4——处理数据
有这么几组数据需要你处理: James 2-34,3:21,2.34,2.45,3.01,2:01,2:01,3:10,2-22 Julia 2.59,2.11,2:11,2:23,3-10,2-23 ...
- Html dom 赋值
1 <!DOCTYPE html> 2 <html lang="en"> 3 <head> 4 <meta charset="U ...
- js new Date() 获取时间
转载:https://www.cnblogs.com/xiaoshujiang/p/5518462.html 一,Date付给初始值,并构造new Date() Date 对象用于处理日期和时间.创建 ...
- Microsoft .NET Pet Shop 4: Migrating an ASP.NET 1.1 Application to 2.0
249 out of 297 rated this helpful - Rate this topic Gregory Leake Microsoft Corporation Alan Le, Ale ...
- Oracle ORA12514 监听程序当前无法识别连接描述符中请求的服务
在连接数据库的时候,有时会遇到一个“ORA12514:监听程序当前无法识别连接描述符中请求的服务”的错误,这个错误其实就是数据库动态注册(关于动态注册会在稍后讲解)不生效,导致监听器无法识别客户端连接 ...
- RabbitMQ--学习资源汇
1.RabbitMQ 实战教程 文集(alibaba) 2.RabbitMQ从入门到精通(9篇系列博文 )(anzhsoft2008 ) 3. RabbitMQ目录(nick's blog) 使用 ...
- 小tip: 某简单的字符重叠与图形生成----张鑫旭
引言 字符重叠不是什么稀奇的东西. 如1像素错位模拟阴影效果: 或者powerFloat中展示的带边框三角: 以及其他很多. 但是技术这东西不是豆腐,老了可以吃,臭了也可以吃:那我这里还拿着个说事作甚 ...
- 爬虫必备—Scrapy
一.Scrapy简介 Scrapy是一个为了爬取网站数据,提取结构性数据而编写的应用框架. 其可以应用在数据挖掘,信息处理或存储历史数据等一系列的程序中.其最初是为了页面抓取 (更确切来说, 网络抓取 ...
- 移动端meta标签设置
移动端meta标签设置 1.设置当前html文件的字符编码 <meta charset="UTF-8"> 1 2设置浏览器的兼容模式(让IE使用最新的浏览器渲染) &l ...