我想在一个列上指定一个唯一的索引,但我还需要允许NULL
个值(多个记录可以有NULL
个值).在使用PostgreSQL进行测试时,我发现我可以有一条NULL
值的记录,但下一条记录会导致一个问题:
irb(main):001:0> u=User.find(5)
User Load (111.1ms) SELECT "users".* FROM "users" WHERE "users"."id" = $1 LIMIT 1 [["id", 5]]
=> #<User id: 5, email: "a@b.com", created_at: "2013-08-28 09:55:28", updated_at: "2013-08-28 09:55:28">
irb(main):002:0> u.email=nil
=> nil
irb(main):003:0> u.save
(1.1ms) BEGIN
User Exists (4.8ms) SELECT 1 AS one FROM "users" WHERE ("users"."email" IS NULL AND "users"."id" != 5) LIMIT 1
(1.5ms) ROLLBACK
=> false
如果数据库设置为NULL
,那么它会判断是否存在列,如果第一个列的id为User
,那么它会查看.有没有一种方法,不仅数据库可以允许,Rails也不会像上面那样先判断?
这个 idea 是用户不必输入邮箱,但如果他们输入,我需要能够通过他们的邮箱找到用户.我知道我可以创建另一个模型来将用户与邮箱联系起来,但我更愿意采用上述方式.
UPDATE: Here's the migration code I had created to add the email
column:
class AddEmailToUsers < ActiveRecord::Migration
def change
add_column :users, :email, :string
add_index :users, :email, :unique => true
end
end
下面是我添加到User
型号的代码:
validates :email, uniqueness: true
我忘了我在User
型号上加了validates
个电话.所以Rails首先判断是有道理的.我想唯一的另一个问题是,数据库拥有唯一索引和NULL
个字段是否安全?有没有办法在Rails中指定我想要验证的邮箱是唯一的,除非是nil
?