2017-09-02 30 views
1

我們使用devise.rb以下BCrypt ::錯誤:: InvalidHash(無效哈希)制訂1.5.4的Rails 2.2.5

config.encryptor = :bcrypt 

我們想改變這

config.encryptor = :authlogic_sha512 

還寫了代碼來解密舊密碼,並在登錄時將其散列爲新密碼(在會話控制器內部)

但是,在更新密碼後,在註銷和登錄時,它會給出錯誤

BCrypt::Errors::InvalidHash (invalid hash): 

如果我註釋掉錯誤的原始點,則此錯誤隨機出現。所以我認爲設計配置或user.rb模型有問題。

用戶模型具有以下行:

devise :database_authenticatable, :registerable, :confirmable, 
    :recoverable, :rememberable, :trackable, :validatable, :omniauthable, :omniauth_providers => [:auth0, :google_oauth2] 

因此步驟的順序是這樣的:

  1. 用戶信息是那裏的DB(現有用戶)。密碼與bcrypt
  2. 用戶登錄,並在會話控制器加密,我們重新哈希密碼SHA512並將其存儲在encrypted_pa​​ssword場
  3. 用戶跡象出
  4. 用戶的跡象,在***無法登錄由於'invalid_hash'錯誤。

任何想法可能是什麼問題在這裏?提前致謝。

編輯:代碼爲第2步的要求上面:

class Users::SessionsController < Devise::SessionsController 
... 
... 
email = params[:user]['login'] 

@user = User.find_by_email(email) 
return if @user.nil? 
# Get old password and salt 
bcrypt = BCrypt::Password.new(@user.encrypted_password) 
salt = bcrypt.salt 

pwd = params[:user]['password'] 

pass = ::BCrypt::Engine.hash_secret("#{pwd}#{Devise.pepper}", salt) 
# If passwords, match, re-hash it with SHA-512 
if @user.encrypted_password == pass 
    @user.password_digest = ::Devise::Encryptors::AuthlogicSha512.digest(pass, Devise.stretches, salt, Devise.pepper) 
    @user.password_salt = salt 
    @user.save! 
end 

我還添加了 'password_digest' 和 'password_salt' 在db表,但我的 '救!'方法然後失敗,'未通過額外的參數'。

+0

#2的實際源代碼可能會有所幫助,因爲這可能是問題所在。我假設你重寫Devise的'SessionController'?怎麼樣? –

+0

@ma_il按要求添加代碼。 – Farhad

回答

0

它看起來像你假設用戶密碼與BCrypt哈希,即使它已經在第一次運行中轉換爲Authlogic。你可以檢查是否@user.password_digest.present?,如果是這樣的話,你應該從參數中檢查密碼。

此外,在爲Authlogic創建摘要時,您將採用pass中的已加密值並再次對其進行散列處理。相反,在創建authlogic摘要時,它也只需要params中的密碼。

+0

password_digest會在哪裏設置?每當我嘗試訪問它時,都會說'訪問受保護字段時出錯'。對不起noob問題,但我是新來的紅寶石。 password_digest是否也是'用戶'數據庫表中的一個字段?那麼password_salt呢? – Farhad

+0

u.password_digest.present? NoMethodError:保護方法'password_digest'要求# <用戶:0x007f822415abf0> – Farhad