Как сделать столбец уникальным и проиндексировать его при переходе на Ruby on Rails? - PullRequest
378 голосов
/ 20 сентября 2009

Я хотел бы сделать столбец unique в сценарии миграции Ruby on Rails. Каков наилучший способ сделать это? Также есть способ индексировать столбец в таблице?

Я бы хотел использовать unique столбцы в базе данных, а не просто :validate_uniqueness_of.

Ответы [ 8 ]

635 голосов
/ 20 сентября 2009

Краткий ответ:

add_index :table_name, :column_name, unique: true

Чтобы проиндексировать несколько столбцов вместе, вы передаете массив имен столбцов вместо одного имени столбца,

add_index :table_name, [:column_name_a, :column_name_b], unique: true

Для более детального управления существует метод "execute", который выполняет прямой SQL.

Вот и все!

Если вы делаете это вместо обычных проверок старой модели, просто проверьте, как это работает. Я не уверен, что сообщение об ошибке пользователю будет таким же хорошим. Вы всегда можете сделать оба.

118 голосов
/ 13 марта 2014

рельсы генерируют миграцию add_index_to_table_name имя_ столбца: uniq

или

рельсы генерируют миграцию add_column_name_to_table_name имя_ столбца: строка: uniq: index

создает

class AddIndexToModerators < ActiveRecord::Migration
  def change
    add_column :moderators, :username, :string
    add_index :moderators, :username, unique: true
  end
end

Если вы добавляете индекс к существующему столбцу, удалите или прокомментируйте строку add_column или поставьте галочку

add_column :moderators, :username, :string unless column_exists? :moderators, :username
39 голосов
/ 10 марта 2017

Поскольку это еще не было упомянуто, но отвечает на вопрос, который у меня возник, когда я нашел эту страницу, вы также можете указать, что индекс должен быть уникальным при добавлении через t.references или t.belongs_to:

create_table :accounts do |t|
  t.references :user, index: { unique: true } # or t.belongs_to

  # other columns...
end

(по крайней мере, на Rails 4.2.7)

25 голосов
/ 13 апреля 2018

Если вы создаете новую таблицу, вы можете использовать встроенный ярлык:

  def change
    create_table :posts do |t|
      t.string :title, null: false, index: { unique: true }
      t.timestamps
    end
  end
12 голосов
/ 10 ноября 2016

Я использую Rails 5, и приведенные выше ответы отлично работают; вот еще один способ, который также работал для меня (имя таблицы :people и имя столбца :email_address)

class AddIndexToEmailAddress < ActiveRecord::Migration[5.0]
  def change
    change_table :people do |t|
      t.index :email_address, unique: true
    end
  end
end
1 голос
/ 28 июля 2017
add_index :table_name, :column_name, unique: true

Чтобы проиндексировать несколько столбцов вместе, вы передаете массив имен столбцов вместо одного имени столбца.

0 голосов
/ 28 декабря 2018

Если вы пропустили добавление уникального в столбец БД, просто добавьте эту проверку в модель, чтобы проверить, является ли поле уникальным:

class Person < ActiveRecord::Base
  validates_uniqueness_of :user_name
end

см. Здесь Выше только для целей тестирования, пожалуйста, добавьте index , изменив столбец БД, как предложено @ Nate

Пожалуйста, обратитесь к этому с индексом для получения дополнительной информации

0 голосов
/ 05 января 2017

Возможно, вы захотите добавить имя для уникального ключа, так как много раз имя по умолчанию unique_key по rails может быть слишком длинным, для которого БД может выдать ошибку.

Чтобы добавить имя для вашего индекса, просто используйте опцию name:. Запрос на миграцию может выглядеть примерно так -

add_index :table_name, [:column_name_a, :column_name_b, ... :column_name_n], unique: true, name: 'my_custom_index_name'

Подробнее - http://apidock.com/rails/ActiveRecord/ConnectionAdapters/SchemaStatements/add_index

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...