You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Spring3下如何通过Jasypt编程获取解析解密后的属性值?

问题解决:Spring3中通过Jasypt加密的属性无法从Environment获取解密后的值

问题背景

在Spring3中配置Jasypt的EncryptablePropertyPlaceholderConfigurer后,依赖加密属性的Bean能正常获取解密后的值,但调用ApplicationContext.getEnvironment().getProperty("spring.datasource.password")时,要么拿到未解析的占位符字符串${some.encrypted.string},要么返回null,无法获取解密后的实际值。

核心原因

EncryptablePropertyPlaceholderConfigurer是Spring传统PropertyPlaceholderConfigurer的子类,它的工作逻辑是在Bean初始化阶段直接替换Bean定义中的占位符,不会将解析后的解密属性注册到Spring的Environment属性源中,因此从Environment无法直接获取到处理后的属性值。

解决方案

方法1:自定义子类暴露解析后的属性

由于EncryptablePropertyPlaceholderConfigurer的getProperty()方法是protected的,我们可以自定义子类暴露该方法,直接从配置器中获取解析后的解密属性:

  1. 自定义配置器子类:
import org.jasypt.spring3.properties.EncryptablePropertyPlaceholderConfigurer;

public class ExposedEncryptablePropertyConfigurer extends EncryptablePropertyPlaceholderConfigurer {
    // 暴露获取解析后属性的方法
    public String getResolvedProperty(String key) {
        return super.getProperty(key);
    }
}
  1. 修改XML配置中的Bean类:
<bean id="propertyPlaceholderConfigurer"
      class="com.yourpackage.ExposedEncryptablePropertyConfigurer">
    <constructor-arg ref="configurationEncryptor"/>
    <!-- 其他原有配置保持不变 -->
    <property name="searchSystemEnvironment" value="true"/>
    <property name="ignoreResourceNotFound" value="true"/>
    <property name="systemPropertiesModeName" value="SYSTEM_PROPERTIES_MODE_OVERRIDE"/>
    <property name="locations">
        <list>
            <value>file:${spring.config.additional-location}</value>
            <value>classpath:application.properties</value>
        </list>
    </property>
</bean>
  1. 编程获取解密后的值:
final ClassPathXmlApplicationContext ctx = new ClassPathXmlApplicationContext("jasypt.xml");
ExposedEncryptablePropertyConfigurer configurer = ctx.getBean(ExposedEncryptablePropertyConfigurer.class);
// 获取解密后的属性值
String decryptedPassword = configurer.getResolvedProperty("spring.datasource.password");

方法2:使用Spring3.1+兼容的属性配置器(推荐)

如果你的项目基于Spring3.1及以上版本,可以使用Jasypt提供的EncryptablePropertySourcesPlaceholderConfigurer,它会将解析后的解密属性注册到Environment的属性源中,这样就能直接通过Environment获取值:

  1. 修改XML配置中的Bean类:
<bean id="propertyPlaceholderConfigurer"
      class="org.jasypt.spring31.properties.EncryptablePropertySourcesPlaceholderConfigurer">
    <constructor-arg ref="configurationEncryptor"/>
    <!-- 其他原有配置保持不变 -->
    <property name="searchSystemEnvironment" value="true"/>
    <property name="ignoreResourceNotFound" value="true"/>
    <property name="systemPropertiesModeName" value="SYSTEM_PROPERTIES_MODE_OVERRIDE"/>
    <property name="locations">
        <list>
            <value>file:${spring.config.additional-location}</value>
            <value>classpath:application.properties</value>
        </list>
    </property>
</bean>
  1. 直接从Environment获取解密后的值:
final ClassPathXmlApplicationContext ctx = new ClassPathXmlApplicationContext("jasypt.xml");
String decryptedPassword = ctx.getEnvironment().getProperty("spring.datasource.password");

方法3:手动解密(不推荐,繁琐)

如果上述方法都无法使用,可以手动获取加密器,自行处理占位符和解密逻辑:

final ClassPathXmlApplicationContext ctx = new ClassPathXmlApplicationContext("jasypt.xml");
StandardPBEStringEncryptor encryptor = ctx.getBean(StandardPBEStringEncryptor.class);

// 先获取spring.datasource.password对应的占位符内容
String placeholder = ctx.getEnvironment().getProperty("spring.datasource.password");
if (placeholder != null && placeholder.startsWith("${") && placeholder.endsWith("}")) {
    // 提取占位符中的属性key
    String propertyKey = placeholder.substring(2, placeholder.length() - 1);
    // 获取原始加密字符串
    String encryptedValue = ctx.getEnvironment().getProperty(propertyKey);
    if (encryptedValue != null && encryptedValue.startsWith("ENC(") && encryptedValue.endsWith(")")) {
        // 去掉ENC()包裹,解密
        String rawEncrypted = encryptedValue.substring(4, encryptedValue.length() - 1);
        String decryptedPassword = encryptor.decrypt(rawEncrypted);
        return decryptedPassword;
    }
}
return null;

版本注意事项

  • Spring3.0.x版本:只能使用方法1或方法3;
  • Spring3.1+版本:优先使用方法2,更符合Spring环境属性管理的设计。

内容的提问来源于stack exchange,提问作者user3258911

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.14 05:15:37