一般情况下,spring boot项目为了能够实时刷新配置信息,都会把配置文件放在nacos之类的配置中心上。但是这样就会存在一个问题,一些比较敏感的配置信息,比如数据库密码,一旦被泄露,就会有严重的数据安全问题。因此,我们可以通过对敏感信息进行加密处理,然后在项目中再自动解密,就可以解决此类问题。
首先,引入ulisesbocchio包,这个包就实现了我们需要的这个功能。配置信息如下:
<dependency>
<groupId>com.github.ulisesbocchio</groupId>
<artifactId>jasypt-spring-boot-starter</artifactId>
<version>3.0.3</version>
</dependency>
<dependency>
<groupId>com.github.ulisesbocchio</groupId>
<artifactId>jasypt-spring-boot</artifactId>
<version>3.0.3</version>
</dependency>
然后呢,我们需要写一个类,来实现ulisesbocchio包的EncryptablePropertyResolver接口。这个接口就一个方法,就是如何解密。在这里,我们是用SM4对称加密算法来做的。SM4算法相关的实现可参考这篇文章:
【Java加解密系列】- SM4加解密
代码如下,实现逻辑是判断配置项是否是以(testcipher)为前缀的,符合这个条件的会用SM4算法进行解密,就得到配置信息的明文啦。
public class TestEncryptablePropertyResolver implements EncryptablePropertyResolver {
public static final String ENCODED_PASSWORD_PREFIX = "(testcipher)";
public static final String SM4_KEY = "pn94j31omdjtxfp4";
private static final Logger LOGGER = LoggerFactory.getLogger(TestEncryptablePropertyResolver.class);
public TestEncryptablePropertyResolver() {
super();
}
@Override
public String resolvePropertyValue(String s) {
if (null != s && s.startsWith(ENCODED_PASSWORD_PREFIX)) {
try {
byte[] data = Base64.decodeBase64(s.substring(ENCODED_PASSWORD_PREFIX.length()));
byte[] decryptedBytes = Sm4Utils.decrypt(data, SM4_KEY.getBytes("UTF-8"));
return new String(decryptedBytes).trim();
} catch (Exception e) {
LOGGER.error("resolve property failed:{}", e.getMessage(), e);
return s;
}
}
return s;
}
}
然后还需要有一个配置类,注入我们上面的TestEncryptablePropertyResolver类。
@Configuration
public class EncryptablePropertyResolverConfig {
@Bean(name = "encryptablePropertyResolver")
public EncryptablePropertyResolver encryptablePropertyResolver() {
return new TestEncryptablePropertyResolver();
}
}
就是这么简单,就实现了配置信息加密。下面,我们来测试一下,写个测试类,启动的时候会直接把配置信息打出来:
@Component
public class TestValue {
private static final Logger LOGGER = LoggerFactory.getLogger(TestValue.class);
@Value("${project.test.password}")
private String password;
@PostConstruct
public void init() {
LOGGER.info("password value:{}", password);
}
}
我们在配置文件中的配置是加密之后的信息:
project:
test:
password: (testcipher)7Hw/0HxUMdDAikdLb2GrBA==
启动时,打印日志如下:
可以看到,项目启动的时候,直接把配置信息明文打出来了,实现了解密后的配置信息自动解密。