LoginSignup
34
17

More than 3 years have passed since last update.

【Ruby On Rails】DBに一意性を与えるユニーク制約(unique)の正しい記述場所

Posted at

備忘録です。

ユニーク制約とは

一意性制約のことです。DBにおいてデータを追加や更新する際の制約。カラムに独自性を与えます。

例えば、ユニーク制約を適用することで、ユーザーが新規登録をする際に、既に登録されているemailアドレスと同じアドレスで登録しようとした場合にエラーを返すことができます。

uniqueの書き方

add_index :テーブル名, [:カラム名1, :カラム名2, :カラム名3, ...(続く)], unique: true

テーブル名をcontents、カラム名をpart_idとwordとした場合は次のようになります。

add_index :contents, [:part_id, :word], unique: true

記述場所

以下のように、マイグレーションファイルのchangeメソッド内に記述するようにしましょう。

マイグレーションファイル
class CreateContents < ActiveRecord::Migration[6.0]
  def change
    create_table :contents do |t|
      t.integer :part_id, null: false
      t.string  :word, null: false
      t.references :user, null: false, foreign_key: true
      t.timestamps
    end
    add_index :contents, [:part_id, :word], unique: true #この行です。
  end
end

記述場所を間違えた場合

例えば、次のようにchangeメソッドから外して記述してみます。

マイグレーションファイル
class CreateContents < ActiveRecord::Migration[6.0]
  def change
    create_table :contents do |t|
      t.integer :part_id, null: false
      t.string  :word, null: false
      t.references :user, null: false, foreign_key: true
      t.timestamps
    end
  end
  add_index :contents, [:part_id, :word], unique: true #この行です。
end

この状態でrails db:migrateを実行するとエラーが出ます。

% rails db:migrate
-- add_index(:contents, [:part_id, :word], {:unique=>true})
-- add_index(:contents, [:part_id, :word], {:unique=>true})
rails aborted!
ActiveRecord::StatementInvalid: Mysql2::Error: Table 'hoge_development.contents' doesn't exist
34
17
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
34
17