我选择了 cmbaxter 建议的路径。我将示例代码放在这里是因为 cmets 似乎不支持代码。
我在配置文件中添加了一些特殊的语法,所以如果我想在我的配置文件中放入一个加密的密码,我会这样做:
my-app-config{
db-username="foo"
db-password="ENC(9yYqENpuCkkL6gpoVh7a11l1IFgZ0LovX2MBF9jn3+VD0divs8TLRA==)"
}
注意加密密码周围的“ENC()”包装。
然后我创建了一个配置工厂,它返回一个 DycryptingConfig 对象而不是类型安全配置:
import rzrelyea.config.crypto.DecryptingConfig;
import rzrelyea.config.crypto.KeyProvider;
public class ConfigFactory{
public static final Config makeDecryptingConfig(com.typesafe.config.Config config, KeyProvider keyProvider){
return new DecryptingConfig(config, keyProvider);
}
}
这是 DecryptingConfig 的代码:
import java.security.Key;
import static rzrelyea.config.Validators.require;
public class DecryptingConfig extends rzrelyae.config.Config {
private final com.typesafe.config.Config config;
private final Decryptor decryptor;
public DecryptingConfig(com.typesafe.config.Config config, KeyProvider keyProvider){
super(config);
require(keyProvider, "You must initialize DecryptingConfig with a non-null keyProvider");
this.config = config;
final Key key = keyProvider.getKey();
require(key, "KeyProvider must provide a non-null key");
decryptor = new Decryptor(config.getString("crypto-algorithm"), key, config.getString("encoding-charset"));
}
@Override
public String getString(String s) {
final String raw = config.getString(s);
if (EncryptedPropertyUtil.isEncryptedValue(raw)){
return decryptor.decrypt(EncryptedPropertyUtil.getInnerEncryptedValue(raw));
}
return raw;
}
显然,您需要实现自己的 rzrelyea.config.Config 对象、自己的 EncryptedPropertyUtil、自己的 Decryptor 和自己的 KeyProvider。我的 rzrelya.config.Config 实现将类型安全的配置对象作为构造函数参数,并将所有调用转发给它。里面有很多样板代码!但我认为将调用转发到接口而不是扩展 com.typesafe.config.impl.SimpleConfig 更好。你知道,更喜欢组合而不是继承,更喜欢代码而不是接口,而不是实现。您可以选择不同的路线。