从hibernate使用MySql PASSWORD()函数

时间:2015-01-17 20:28:31

标签: java mysql database hibernate password-encryption

我使用PrimeFaces将旧的Java桌面摇摆应用程序重写为JSF应用程序。

旧的应用程序没有使用hibernate,但我决定在新的应用程序中使用它。一切正常但问题是当我想使用MySql的函数密码()来保存密码时使用hibernate。

有没有办法做到这一点,因为如果我可以在不更改密码的情况下将数据从旧数据库导入新数据库,那就太好了。

我设法使用此代码段启动登录工作:

public User login(String username, String password) {

    User result = null;

    Session session = HibernateUtil.getSessionFactory().openSession();
    try {
        String sql = "select s from User where username=:username and password=password(:password)";
        Query query = session.createQuery(sql);
        query.setString("username", username);
        query.setString("password", password);

        result = (User) query.uniqueResult();

        if (result != null) {
            Hibernate.initialize(result.getUserData());
        }
    }
    finally {
        session.close();
    }

    return result;
}

但是这是新用户注册的问题,因为我不知道如何存储密码。我用来将用户保存到数据库的代码如下:

public User addUser(User obj) {
    Session session = HibernateUtil.getSessionFactory().openSession();

    try {
        session.save(obj);
        session.flush();
    }
    finally {
        session.close();
    }
    return obj;
}

我知道我可以用老式的方式编写整个insert语句,但是那时使用hibernate的重点是什么,代码看起来很难看。此外,我对登录片段也不满意。 我也尝试在插入后用触发器更新密码,但我一直收到错误:

Updating of NEW row is not allowed in after trigger

所以我放弃了这种方法,因为它丑陋而且不起作用。

我应该只使用jasypt或任何其他库来加密应用程序中的密码并完成它吗?或者是我的问题有一个优雅的解决方案。

2 个答案:

答案 0 :(得分:1)

使用Jasypt EncryptedStringType要方便得多,因为您将密码哈希委托给UserType。

这样您的应用程序逻辑就不必处理与密码相关的职责(就像使用非便携式PASSWORD SQL函数的SELECT一样)。

UserType也会处理对INSERT / UPDATE的实际密码进行哈希处理。

所以,Jasypt是一个更好的选择。

答案 1 :(得分:1)

对于散列密码,不应该使用MySql函数password()!来自文档:

  

PASSWORD()函数由MySQL中的身份验证系统使用   服务器;你不应该在你自己的应用程序中使用它。

计算速度快且无保留,这使得非常不安全。而是将散列保留为服务器端语言,并使用一个库,该库使用慢速散列函数,其成本因子如BCrypt,PBKDF2或SCrypt。一个着名的Java库是jBCrypt