середа, 26 жовтня 2011 р.

Модель User в DataMapper(з BCryptHash) для Warden

В процесі написанні статті Модель User в DataMapper для Warden я натрапив на цікавий тип даних BCryptHash. В DataMapper він стає доступний, якщо включити гем dm-types. BCryptHash зберігається у базі даних як рядок, що представляє сіль, хеш і вартість паролю, використовуючи алгоритм bcrypt. Він пропонує альтернативу більш звичної пари значень хеш і сіль, які зберігаються у базі даних.


Змінюємо нашу модель User.
class User
  include DataMapper::Resource

  property :id,              Serial
  property :name,            String
  property :password,        BCryptHash

  timestamps :at

  attr_accessor :password_confirmation

  validates_presence_of     :name
  validates_uniqueness_of   :name
  validates_confirmation_of :password

  validates_with_method :password_non_blank
  
private

  def password_non_blank
    if password_confirmation.nil? || password_confirmation.empty?
      [ false, 'Missing password']
    else
      true
    end
  end

end


Нам залишилось лише, написати відкритий метод User#authenticate, який повертатиме екземпляр класу User, якщо передане коректне ім'я користувача і пароль.
def self.authenticate(name, password)
  user = first(:name => name)
  if user
    if user.password != password
      user = nil
    end
  end
  user
end

Всю роботу з хешованим паролями бере на себе BCryptHash. Ми ж працюємо з паролем(password), як зі звичайним текстовим полем.
А у базі даних він зберігається зашифрованим. Давайте перевіримо це:
$ sqlite3 -line project.db "select * from users"
        id = 1
      name = root
  password = $2a$10$YTc0yuAN/gGyws0cAgWh7.sXGsrTxi/XGGSBeDReIrSsBrzZCOtm6
created_at = 2011-10-26T17:21:21+03:00
updated_at = 2011-10-26T17:21:21+03:00

        id = 2
      name = user
  password = $2a$10$oyt4lSXR1QDMUuARQVDGn.ETroB6fvS0SvtsINtMIBIjPuDZ7wxPS
created_at = 2011-10-26T17:21:28+03:00
updated_at = 2011-10-26T17:21:28+03:00

Ця модель буде без змін працювати з кодом із попередньої статті. Тут можна подивитись на різницю коду. Як бачите вона не значна.

Повний код додатку можна подивитись тут.

Немає коментарів: