ruby-on-rails - 设计数据库迁移 - Ruby on Rails

标签 ruby-on-rails ruby devise

我有一个 Ruby on Rails (4.2.1) 应用程序,它使用 Devise (3.5.1) 对用户进行身份验证,我们正在 Rails (5.0.0) 中重建此应用程序,并且我们正在使用 Devise (4.2.0)。当我将用户表从旧应用程序复制到新应用程序时,就会出现问题,然后在新应用程序中我无法使用旧数据登录。在 devise.rb 初始化程序中,我在两个应用程序中使用相同的 secret_key,因此不确定为什么我无法使用旧数据登录新应用程序,有什么想法吗?

最佳答案

首先,使用 rails console 确保问题与密码有关,而不是应用程序 - 即,您的用户模型的 valid_password? 调用将失败,并显示正确的密码。

设计使用this默认情况下生成密码哈希的方法:

def self.digest(klass, password)
  if klass.pepper.present?
    password = "#{password}#{klass.pepper}"
  end
  ::BCrypt::Password.create(password, cost: klass.stretches).to_s
end

它使用 klass.pepper 添加到您的密码(如果存在)。这里的 klass 是你的模型(例如用户),可以是 configured使用胡椒:

Besides :stretches, you can define :pepper, :encryptor, :confirm_within, :remember_for, :timeout_in, :unlock_in among other options.

成本是新密码存储的盐生成的复杂性,因此应该只影响新哈希值的生成,并且不会影响先前生成的密码的验证。

Devise 使用此方法将输入密码与存储的哈希值进行比较:

   def self.compare(klass, hashed_password, password)
      return false if hashed_password.blank?
      bcrypt   = ::BCrypt::Password.new(hashed_password)
      if klass.pepper.present?
        password = "#{password}#{klass.pepper}"
      end
      password = ::BCrypt::Engine.hash_secret(password, bcrypt.salt)
      Devise.secure_compare(password, hashed_password)
    end

只需在两个应用程序版本中对其进行调试即可查看此方法中的哪些输入参数可能不同,例如如果您为模型定义了不同的胡椒,则对于相同的 hashed_value,bcrypt.salt 在两个应用中是不同的。

至于从现有存储的散列密码中获取盐的位置,它实际上是 simple 。存储的字符串简单地由 $ 符号分割:

# call-seq:
#   split_hash(raw_hash) -> version, cost, salt, hash
#
# Splits +h+ into version, cost, salt, and hash and returns them in that order.
def split_hash(h)
  _, v, c, mash = h.split('$')
  return v.to_str, c.to_i, h[0, 29].to_str, mash[-31, 31].to_str
end

关于ruby-on-rails - 设计数据库迁移 - Ruby on Rails,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/38193606/

相关文章:

ruby-on-rails - Rails 验证是否存在两个字段之一 (XOR)

ruby - 如何用使用rails3-generators的工厂替换固定装置?

ruby-on-rails - 设计测试助手 - sign_in 不起作用

ruby-on-rails - 从 Rails 到 Phoenix 共享身份验证/数据?

ruby-on-rails - 保护rails中的隐藏变量?

ruby-on-rails - Rails/Ruby 错误地显示变量未定义

javascript - 让 Carrierwave 和 jpegcam 发挥出色?

ruby-on-rails - 使用 RSpec 测试 URL(正则表达式)验证

ruby-on-rails - 为嵌套路由包装命名路由助手

ruby-on-rails - rails, rspec, capybara, webkit/selenium, devise, 在每次请求后注销