0

Users are able to create students in my database. Right now I have model validations for the presence of first_name and last_name. I have a method in my Student model for full_name.

def full_name
"#{first_name} #{last_name}"
end

I'm wondering what I have to do require uniqueness of full_name without limiting first or last names. I want to be able to have Tom Smith, Tom Wilson,Tom Clancy, but not an erroneous reentry of Tom Smith.

Arslan Ali
  • 17,418
  • 8
  • 58
  • 76
  • So from a design standpoint, are you sure you want to do this? Not only will you not be able to have two Tom Smiths, but with active model validations every name change will require loading every other persons first and last name to do a string comparison with them. – Austio Jul 04 '15 at 12:57
  • Try adding unique index on both first_name & last_name columns - Refer http://stackoverflow.com/questions/4123610/how-to-implement-a-unique-index-on-two-columns-in-rails – Wand Maker Jul 04 '15 at 13:00
  • Just a thought. There might legitimately be 2 Tom Smiths, or 3. Names aren't unique. – Elvn Jul 04 '15 at 13:05

2 Answers2

4

This would do

validates_uniqueness_of :first_name, scope: :last_name

You need to add an unique index to the students table as well to avoid race conditions.

add_index :students, [ :first_name, :last_name ], :unique => true

More info here.

Pavan
  • 33,316
  • 7
  • 50
  • 76
  • 1
    This is the best answer! – Rubyrider Jul 04 '15 at 13:04
  • That works, thanks. When I re-enter a name in the form, I get an error .."PG::UniqueViolation: ERROR: duplicate key value violates unique constraint "index_students_on_first_name_and_last_name" DETAIL: Key (first_name, last_name)=(Tom, Smith) already exists. ... What can I put on my create action to re-render the form with the message " student could not be created", or something similar? – Jeremy Walters Jul 04 '15 at 13:40
  • @JeremyWalters Try `validates_uniqueness_of :first_name, scope: :last_name, message: "student could not be created"` – Pavan Jul 04 '15 at 13:47
0

Can you try the following?

# student.rb
def full_name_uniqueness
     if Student.exists?(first_name: first_name, last_name: last_name)
       errors.add :base, "#{full_name} already exists" #change error key and message as you need
     end
end 

Now write a custom a validation #student.rb

validates :full_name_uniqueness
Rubyrider
  • 3,567
  • 1
  • 28
  • 34