Yanıtlar:
add_index :people, [:firstname, :lastname, :dob], :unique => true
Howmanyofme.com'a göre, sadece Amerika Birleşik Devletleri'nde "John Smith adında 46.427 kişi var". Bu yaklaşık 127 yıl sürüyor. Bu, bir insanın ortalama ömrünün çok üzerinde olduğundan, DOB çatışmasının matematiksel olarak kesin olduğu anlamına gelir.
Söylediğim tek şey, benzersiz alanların belirli bir kombinasyonunun gelecekte aşırı kullanıcı / müşteri hayal kırıklığına yol açabileceğidir.
Uygunsa, ulusal kimlik numarası gibi gerçekten benzersiz bir şey düşünün.
(Bu partiye çok geç kaldığımı fark ettim, ama gelecekteki okuyuculara yardımcı olabilir.)
Dizin olmadan bir kısıtlama eklemek isteyebilirsiniz. Bu, hangi veritabanını kullandığınıza bağlı olacaktır. Postgres için örnek taşıma kodu aşağıdadır. (tracking_number, carrier)
kısıtlama için kullanmak istediğiniz sütunların bir listesidir.
class AddUniqeConstraintToShipments < ActiveRecord::Migration
def up
execute <<-SQL
alter table shipments
add constraint shipment_tracking_number unique (tracking_number, carrier);
SQL
end
def down
execute <<-SQL
alter table shipments
drop constraint if exists shipment_tracking_number;
SQL
end
end
Ekleyebileceğiniz farklı kısıtlamalar vardır. Dokümanları okuyun
add_index
yöntemi kullanmakla aynı olduğunda IMHO'nun ham SQL'e düşmesine gerek yoktur . ;)
pg_constraint
tabloya eklenmediğinden, kısıtlamaya ada göre başvuramayacağınızı unutmayın .
Merhaba Sütunlara geçişinizde benzersiz bir dizin ekleyebilirsiniz.
add_index(:accounts, [:branch_id, :party_id], :unique => true)
veya her sütun için benzersiz dizinler ayırın
Kullanıcılar ve yayınlar arasındaki bir birleştirme tablosunun tipik örneğinde:
create_table :users
create_table :posts
create_table :ownerships do |t|
t.belongs_to :user, foreign_key: true, null: false
t.belongs_to :post, foreign_key: true, null: false
end
add_index :ownerships, [:user_id, :post_id], unique: true
İki benzer kayıt oluşturmaya çalışmak bir veritabanı hatası (benim durumumda Postgres) atar:
ActiveRecord::RecordNotUnique: PG::UniqueViolation: ERROR: duplicate key value violates unique constraint "index_ownerships_on_user_id_and_post_id"
DETAIL: Key (user_id, post_id)=(1, 1) already exists.
: INSERT INTO "ownerships" ("user_id", "post_id") VALUES ($1, $2) RETURNING "id"
örneğin bunu yapmak:
Ownership.create!(user_id: user_id, post_id: post_id)
Ownership.create!(user_id: user_id, post_id: post_id)
Tamamen çalıştırılabilir örnek: https://gist.github.com/Dorian/9d641ca78dad8eb64736173614d97ced
db/schema.rb
oluşturulan: https://gist.github.com/Dorian/a8449287fa62b88463f48da986c1744a
Tamlık uğruna ve karışıklığı önlemek için burada aynı şeyi yapmanın 3 yolu vardır:
Rails 5.2+ içindeki sütun kombinasyonuna adlandırılmış benzersiz bir kısıtlama ekleme
Diyelim ki bir reklamverene ait olan ve reference_code sütununa sahip Konumlar tablosumuz var ve her reklamveren için yalnızca 1 referans kodu istiyorsunuz. böylece bir sütun kombinasyonuna benzersiz bir kısıtlama eklemek ve adlandırmak istersiniz.
Yapmak:
rails g migration AddUniquenessConstraintToLocations
Göçünüzü şu tek astar gibi görünmesini sağlayın:
class AddUniquenessConstraintToLocations < ActiveRecord::Migration[5.2]
def change
add_index :locations, [:reference_code, :advertiser_id], unique: true, name: 'uniq_reference_code_per_advertiser'
end
end
VEYA bu blok sürümü.
class AddUniquenessConstraintToLocations < ActiveRecord::Migration[5.2]
def change
change_table :locations do |t|
t.index ['reference_code', 'advertiser_id'], name: 'uniq_reference_code_per_advertiser', unique: true
end
end
end
VEYA bu ham SQL sürümü
class AddUniquenessConstraintToLocations < ActiveRecord::Migration[5.2]
def change
execute <<-SQL
ALTER TABLE locations
ADD CONSTRAINT uniq_reference_code_per_advertiser UNIQUE (reference_code, advertiser_id);
SQL
end
end
Bunlardan herhangi biri aynı sonuca sahip olacak, schema.rb