Respuestas:
La respuesta corta para versiones antiguas de Rails (ver otras respuestas para Rails 4+):
add_index :table_name, :column_name, unique: true
Para indexar varias columnas juntas, pasa una matriz de nombres de columna en lugar de un solo nombre de columna,
add_index :table_name, [:column_name_a, :column_name_b], unique: true
Si obtiene "el nombre del índice ... es demasiado largo", puede agregarlo name: "whatever"
al método add_index para acortar el nombre.
Para un control detallado, hay un " execute
" método que ejecuta SQL directo.
¡Eso es!
Si está haciendo esto como un reemplazo para las validaciones regulares de modelos antiguos, verifique cómo funciona. El informe de errores al usuario probablemente no será tan bueno sin las validaciones a nivel de modelo. Siempre puedes hacer las dos cosas.
indexed columns are not unique
error al intentar crear un índice único, puede deberse a que los datos en la tabla ya contienen duplicados. Intente eliminar los datos duplicados y vuelva a ejecutar la migración.
, :name => "whatever"
al add_index
método para acortar el nombre.
los rieles generan migración add_index_to_table_name column_name: uniq
o
los rieles generan migración add_column_name_to_table_name column_name: string: uniq: index
genera
class AddIndexToModerators < ActiveRecord::Migration
def change
add_column :moderators, :username, :string
add_index :moderators, :username, unique: true
end
end
Si está agregando un índice a una columna existente, elimine o comente la add_column
línea, o marque
add_column :moderators, :username, :string unless column_exists? :moderators, :username
add_index...
y no add_column...
.
Como esto aún no se ha mencionado pero responde a la pregunta que tuve cuando encontré esta página, también puede especificar que un índice debe ser único al agregarlo a través de t.references
o t.belongs_to
:
create_table :accounts do |t|
t.references :user, index: { unique: true } # or t.belongs_to
# other columns...
end
(a partir de al menos Rails 4.2.7
)
Estoy usando Rails 5 y las respuestas anteriores funcionan muy bien; Aquí hay otra forma que también funcionó para mí (el nombre de la tabla es :people
y el nombre de la columna es :email_address
)
class AddIndexToEmailAddress < ActiveRecord::Migration[5.0]
def change
change_table :people do |t|
t.index :email_address, unique: true
end
end
end
Es posible que desee agregar un nombre para la clave única, ya que el nombre predeterminado de unique_key por rieles puede ser demasiado largo para que la base de datos pueda arrojar el error.
Para agregar nombre a su índice, simplemente use la name:
opción. La consulta de migración podría verse así:
add_index :table_name, [:column_name_a, :column_name_b, ... :column_name_n], unique: true, name: 'my_custom_index_name'
Más información: http://apidock.com/rails/ActiveRecord/ConnectionAdapters/SchemaStatements/add_index
Si no agregó una columna única a la base de datos, simplemente agregue esta validación en el modelo para verificar si el campo es único:
class Person < ActiveRecord::Base
validates_uniqueness_of :user_name
end
consulte aquí arriba solo para fines de prueba, agregue el índice cambiando la columna de base de datos como lo sugiere @Nate
consulte esto con el índice para obtener más información