透明地持久保存并从数据库中检索加密的数据

自从我在这里发表上一个帖子以来已经有两个多月了,但是今年六月和七月非常忙碌而密集。 首先, Confitura的组织(欧洲最大的Java开发人员免费会议)参加了我所有的免费晚会,然后在相当紧张的住院期间,我们的第二个儿子出生了。 但是,现在,我将尝试再次定期写博客,请继续关注。

在本文中,我将简要介绍如何使用Jasypt库以一种简单,透明的方式将加密的数据存储在数据库中并检索已解密的数据。 我们的用例将是存储Twitter Api凭据,以便它们在我们的数据库中是安全的,但仍易于检索并用于在我们的时间轴中发布更新。

因此,我们有一个简单的实体来代表我们的设置项:

@Entity
public class SettingsItem implements Serializable {

    @Id
    @GeneratedValue(strategy = javax.persistence.GenerationType.AUTO)
    private Integer id;

    private String name;
    private String encryptedValue;
}

在此表中,我们将存储Twitter消费者密钥,Twitter访问令牌等的值。

我们想要实现的是,当我们创建具有值作为纯文本的SettingItem对象,然后对其进行持久化时,将自动执行加密,因此在数据库中我们已对String进行了加密。 当然,当我们从数据库中检索数据时,我们希望开箱即用地看到解密的String,而无需付出额外的努力。

Jasypt进行救援

jasypt-small

Jasypt是一个用Java编写的简单加密库。 它使开发人员免于处理低级配置细节,并使整个加密过程变得简单而直接。 而且现在最有趣的是,它还与Hibernate很好地集成在一起,可以对存储在数据库中的数据进行无缝加密/解密。

设定

要使用Jasypt及其Hibernate集成模块,我们必须在pom中添加以下两项:

<dependency>
        <groupId>org.jasypt</groupId>
        <artifactId>jasypt</artifactId>
        <version>1.9.0</version>
    </dependency>
    <dependency>
        <groupId>org.jasypt</groupId>
        <artifactId>jasypt-hibernate4</artifactId>
        <version>1.9.0</version>
    </dependency>

自订类型

然后,我们必须在实体中声明自定义的Hibernate类型(@TypeDef):

@TypeDef(
        name="encryptedString",
        typeClass=EncryptedStringType.class,
        parameters= {
                // value will be used later to register encryptor
                @Parameter(name="encryptorRegisteredName", value="STRING_ENCRYPTOR")
        }
)
@Entity
public class SettingsItem implements Serializable {
   // (...)
}

然后在同一个类中,我们可以标记我们的ActivatedValue字段以使用此自定义类型:

@Type(type="encryptedString")
    private String encryptedValue;

注册加密器

我们快完成了。 我们要做的最后一件事是在HibernatePBEEncryptorRegistry类中注册加密器。 这可以在我们的应用程序的初始化类(例如ServletContext)中完成,也可以仅在具有main(String [] args)方法的类中完成:

String password = System.getProperty("jasypt.password");

    StandardPBEStringEncryptor strongEncryptor = new StandardPBEStringEncryptor();
    strongEncryptor.setPassword(password);
    HibernatePBEEncryptorRegistry registry =
            HibernatePBEEncryptorRegistry.getInstance();
    registry.registerPBEStringEncryptor("STRING_ENCRYPTOR", strongEncryptor);

这里重要的一点是,通过使用System.getProperty()或System.getenv(),我们可以安全地配置我们的加密机制,通过在服务器计算机上设置适当的值在运行时提供密码。

摘要

作为总结,一个简短的通过测试表明我们的解决方案有效:

public class SettingsItemRepositoryShould extends IntegrationTest {

    @Autowired
    private SettingsItemRepository repository;

    @BeforeClass
    public static void init() {
        StandardPBEStringEncryptor strongEncryptor = new StandardPBEStringEncryptor();
        strongEncryptor.setPassword("JohnDoe");

        HibernatePBEEncryptorRegistry registry =
                HibernatePBEEncryptorRegistry.getInstance();
        registry.registerPBEStringEncryptor("STRING_ENCRYPTOR", strongEncryptor);
    }

    @Test
    public void shouldEncryptAndDecryptValue() {
        // Given
        String settingName = "test";
        String value = "EncryptMe";

        // When
        repository.save(new SettingsItem(settingName, value));

        // Then
        SettingsItem settingsItem = repository.findByName(settingName);
        assertThat(settingsItem.getEncryptedValue()).isEqualTo(value);
    }
}


翻译自: https://www.javacodegeeks.com/2013/08/transparently-persist-and-retrieve-encrypted-data-from-database.html

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

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值