如何通过'Bcrypt'Gem比较解密密码和加密密码

时间:2017-06-27 10:43:07

标签: ruby-on-rails ruby encryption bcrypt bcrypt-ruby

我正在尝试对一些帖子的评论使用简单的身份验证。

用户输入带有即时ID和密码的评论

我用'bcrypt'gem来存储数据库中的密码。

在comments_controller.rb

中这样
@comment = Comment.new(comment_params)
bcrypted_pwd = BCrypt::Password.create(@comment.user_pwd)
@comment.user_pwd = bcrypted_pwd

我使用data-confirm-modal gem来确认用户想要删除他们的评论时的数据

在这部分中,我必须解密用户输入密码以与数据库中的加密密码进行比较

我如何解密密码,有没有什么好方法可以做到这一点?

2 个答案:

答案 0 :(得分:11)

ency_pass = BCrypt::Password.create("testing")
new_pass = "testing"

让我们来看看我们如何比较两个bcrypt哈希值,一个来自数据库&一个来自用户输入(如表格或类似的东西)

BCrypt::Password.new(ency_pass) == new_pass
# true
BCrypt::Password.new(ency_pass) == "testing2"
#false

左边的部分(BCrypt::Password.new)是一个BCrypt对象,它将存储在数据库中的哈希作为参数。

右侧的部分(new_pass)只是用户尝试登录的纯文本密码。

让我们理解这些事情:

BCrypt使用称为“salt”的东西,这是一个随机值,用于增加预先计算出的哈希值的安全性。 salt存储在哈希本身中。 BCrypt定义了自己的==方法,该方法知道如何提取“salt”值,以便在比较密码时将其考虑在内。

BCrypt#==从存储的散列中获取“salt”值,然后使用此盐散列明文密码(用户输入),以便在密码有效时两个散列都相同。

如果您要查看源代码,它将看起来像这样:

def ==(secret)
 super(
  BCrypt::Engine.hash_secret(secret, @salt)
 )
end

请记住,super会在父类上调用相同的方法(在本例中为==)。 BCrypt :: Password的父类是String。

答案 1 :(得分:0)

  

我如何解密密码,有没有什么好方法可以做到这一点?

你不能。您只能解密加密的内容。 Bcrypt不是加密算法,它是一种哈希算法。你不能反转哈希。这显然是不可能的。 (并且证据甚至很难,高中生可以理解。)