java类属性扩展,使用Groovy在Java属性中进行变量扩展

I frequently use standard Java property files for configuring my Groovy applications. One feature I have been missing is the ability to use variables as part of the property value so they can be expand dynamically during use. I thought I could provide this functionality using the following design:

Use a special format to annotate the properties that should be expanded. I have chosen to enclose such templates in double exclamation marks (!!). These property values are essentially a template to be expanded with the local variables

Before using the properties in the application, use the groovy 'evaluate' method to expand application variables in the template

Re-assign the original property key to the new value before use

So, if I have a property file config.properties with properties like:

version=2.3

local_lib=!!${env['GROOVY_HOME']}/${configProps.getProperty('version')}/lib!!

The local_lib property will be expanded from the GROOVY_HOME environment variable and the version property value.

In my application, I have coded this as follows:

//Load the environment variables and configuration file

env=System.getenv()

configFile=new File('config.properties')

configProps= new Properties()

configProps.load(configFile.newDataInputStream())

//Replace configuration property values with their expanded equivalent

configProps.each{

//if a property value is a template we evaluate it

if (it.value.startsWith('!!')){

valTemplate=it.value.replace('!!','"')

it.value=evaluate(valTemplate)

}

}

//then we use the expanded property values

This seems to work. When I do

println configProps

I see that the value is expanded and not null

However, the getProperty method for the expanded property returns null.

assert configProps.getProperty('local_lib')=='C:\\DEVTOOLS\\groovy-2.4.7/2.3/lib'

| | |

| null false

[local_lib:C:\DEVTOOLS\groovy-2.4.7/2.3/lib, version:2.3]

What is causing this discrepancy? I would have expected to return the value shown in the property map.

解决方案

Your local_lib value looks like a String, but it isn't. It is a GString, only lazily coerced to String as needed (like when printing out the configProps map value).

Thus, a little known effect of Properties.getProperty() takes effect here. When the actual map value is not a String, Properties.getProperty() returns null.

So, in order to get the desired behavior, you need to coerce the GString to String before you store the value in the property map. Like so:

it.value=evaluate(valTemplate).toString()

or

it.value=evaluate(valTemplate) as String

Then you should see the desired results downstream.

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值