rails验证belongs_to关系

时间:2011-05-05 18:05:39

标签: ruby-on-rails

鉴于Person拥有电话的简单关系。电话只包含一个必须唯一的电话号码!

    class Telephone < ActiveRecord::Base
      validates_presence_of :contact_id
      belongs_to :contact

      validates :telephone, {:presence => true, :uniqueness => true}
    end


  class Contact < ActiveRecord::Base
    has_many :telephones
    validates_associated :telephones
    has_many :emails 
    has_many :addresses

    validates_presence_of :firstname 

    accepts_nested_attributes_for :telephones, :allow_destroy=>true

    validates_presence_of :lastname
  end


    test "telephone number must be unique" do
      john = contacts :johndoe #johndoe is a person with 1 existing number
      2.times do
        john.telephones.build :telephone=> "123" # 123 doesnt exist yet
      end
      puts Telephone.count # this gives 1
      john.save
      puts Telephone.count # this gives 3 !!!! ???
      assert not(john.valid?) # This validates unless I remove the save above
    end

有人可以解释这个测试的结果。

  1. 只是打电话有效?失败了,但是在rdoc中提到了(必须先保存)
  2. 先保存确实有效吗?通过
  3. 但是现在我实际上在数据库中有3条记录符合我的独特要求。

    有更好的方法吗?我不明白这个测试的结果,这真的违背了我的期望。

1 个答案:

答案 0 :(得分:1)

好的,如果您阅读ruby文档,您会注意到他们提到验证模型不足以实现唯一性。您必须尽可能使用数据库唯一约束。否则,当使用两个进程/线程/无论是否进行验证检查,传递为唯一,然后插入相同的值时,都是可能的。

tl; dr:向db列添加唯一约束。