1

When I login with a username and password by BCrypt checks no problem, everything is fine.

But when I go through the process of recovering password and try to login with the new password the BCrypt never returns true.

The code I have is as follows:

before_save :encrypt_password
before_update :encrypt_password

def authenticate
   player = Player.find_by(mail: self.mail)
   unless player.nil?
   current_password = BCrypt::Password.new(player.password)
   if current_password == self.password
    player
   else
     nil
   end
 end
end

private
def encrypt_password
    unless self.password.nil?
    self.password = BCrypt::Password.create(self.password)
end

I'm using rails 4

Ismael Abreu
  • 16,443
  • 6
  • 61
  • 75
aperez
  • 121
  • 1
  • 13

1 Answers1

3

You don't need the before_update callback.

When creating a new record (user in this case), only before_save is triggered. So you get the right behavior.

But when updating a record, both before_update and before_save are triggered, which means your password column is encrypted twice. That's why you get unexpected behavior.

Check this page for more information about callbacks.


What's more, I think it's a bad idea to make password a real column in database. All you need is a column called encrypted_password in database and making password a virtual attribute.

So you can write encrypt_password method like this:

def encrypt_password
    unless self.password.nil?
    self.encrypt_password = BCrypt::Password.create(self.password)
end

Which gave you no chance to make a mistake like you just made.

Jun Zhou
  • 3,060
  • 1
  • 20
  • 31