Search code examples
rubysinatradatamapper

validates_confirmation_of :password


I have this code, that works, but I'm not really sure how?

It validates passwords but how does it do this?

I know what an attr_reader and accessor are but don't really understand how datamapper knows to compare :password with :password_confirmation? What magic is datamapper performing?

Here is my user model:

require 'data_mapper'
require 'dm-postgres-adapter'
require 'bcrypt'

class User

  include BCrypt
  include DataMapper::Resource

  property :id, Serial
  property :username, String
  property :email, String
  property :password_digest, Text

  validates_confirmation_of :password

  attr_reader :password
  attr_accessor :password_confirmation

  def password=(password)
    @password = password
    self.password_digest = BCrypt::Password.create(password)
  end

end

Here is my controller post:

post '/sign-up' do
    new_user = User.create(:username => params[:username], :email => params[:email], :password => params[:password], :password_confirmation => params[:password_confirmation])
    session[:user_id] = new_user.id
    redirect '/welcome'
  end

Solution

  • Well, here's the docs for validates_confirmation_of

    The "magic" happening is only that data-mapper will search for a field with the same name of the one you passed in the validates_confirmation_of (in this case :password) with _confirmation in the end and verify if they are equal.

    For example validates_confirmation_of :email will make datamapper look for an attribute email_confirmation and compare if it's equal to :email.

    attr_reader and attr_accessor

    The attr_reader and attr_acessor are just 'shortcuts' to define methods and instance variables.

    • attr_reader: creates a method that gets the attribute
    • attr_writer: creates a method that sets the attribute
    • attr_accessor: creates both

    For example:

    class Person
    
       attr_reader :name
       attr_accessor :gender
    
    end
    

    Is the same thing of:

    class Person
    
      def name
        @name
      end
    
      def gender=(gender)
        @gender = gender
      end
    
      def gender
        @gender
      end
    
    end