2016-05-17 15 views
4

パスワードの暗号化と認証に暗号https://nodejs.org/api/crypto.htmlを使用しています。私はパスワード変更ページで作業しており、ユーザーが提供するパスワードが既存のパスワードと同じハッシュを持っているかどうかを判断する問題を抱えています。以下は私のコードです。2つのパスワードハッシュを比較する - nodejs

var createSalt = function createSalt() { 
    return crypto.randomBytes(128).toString('base64'); 
}; 

var hashPwd = function hashPwd(salt, pwd) { 
    var hmac = crypto.createHmac('sha256', salt); 
    return hmac.update(pwd).digest('hex'); 
}; 

//use password , create salt, hash and compare with the existing 
var salt = createSalt(); 
var passHash = hashPwd(salt,data.Password); 
console.log('the password is', user.PassHash === passHash); 

上記のコンソールメッセージが既存のユーザーパスワードと一致する場合は、真であると予想されます。しかし、2つのハッシュはまったく一致していないようです。どうしたらいいですか?どのようにこれを達成するのですか?私は、新しいパスワードを変更する前に、ユーザーのパスワードが既存のパスワードと一致していることを確認したい。どんな助けもありがとう。

答えて

4

あなたの問題は塩にあると思います。通常は、最初にハッシュした塩を保管して、もう一度再使用しなければなりません。塩の理由は、ハッカーが侵入したシステムから(虹のテーブル攻撃を使用して)ハッカーがそれを取得する場合、ハッシュが元のパスにマップされないようにすることです。あなたは

var salt = crypto.randomBytes(128).toString('base64'); 

var hashPwd = function hashPwd(salt, pwd) { 
    var hmac = crypto.createHmac('sha256', salt); 
    return hmac.update(pwd).digest('hex'); 
}; 

//use password , create salt, hash and compare with the existing 
var passHash = hashPwd(salt,data.Password); 
console.log('the password is', user.PassHash === passHash); 

をしようとした場合それは限り、あなたは(あなたがHTTP要求に応答するために呼び出される関数の範囲外salt VARを保存すると仮定した場合)、サーバーを再起動しないように働くだろうWhy do we use the "salt" to secure our passwords?

を参照してください。 。

より良い解決策(imo)は、bcryptがやっていることです。ここでは、パスワードごとに塩を生成しますが、パスワードが正しいことを確認するために、compareを使用します。これは、ハッシュに格納されているsaltを使用します。この方法では、各パスワードに異なる塩を使用することができます。つまり、塩が漏出しても心配する必要はありません。

npm install bcrypt 

...

var bcrypt = require('bcrypt'); 
var hash = bcrypt.hashSync("my password"); 

bcrypt.compareSync("my password", hash); // true 
bcrypt.compareSync("not my password", hash); // false 

compareAsyncおよびその他の非同期の変種があります。 iwein https://www.npmjs.com/package/bcrypt-nodejs

+0

ああおかげで、私は同じ塩権を使用する必要があります。も参照してください。私は新しい塩を作る代わりに、私は既存のパスワードのものを使うべきだということを意味します。 ? –

+0

@NuruSalihuうん、それは私がそれを理解する方法です。あなたの塩が盗まれた場合は、すべてのパスワードをリセットして塩を再生成する必要があります。しばしば暗号ライブラリは、あなたが再び塩を渡さずにパスを比較することができます(彼らはハッシュされたパスの中に塩を保存します)。 bcryptはこれをたとえばhttp://stackoverflow.com/questions/6832445/how-can-bcrypt-have-built-in-saltsで行います。 – iwein

0
UserSchema.pre('save', function (next) { 
    if (this.password) { 
    const salt = bcrypt.genSaltSync(10);//or your salt constant 
    this.password = bcrypt.hashSync(this.password, salt); 
    } 
    next(); 
}); 
あなたのコントローラで

const result = bcrypt.compareSync(req.body.password, your_hash_password); 
     if (result){ 
     return res.json(message: "success"); 
     } else { 
     return res.status(400).json("Bad request. Password don't match "); 
     }