Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Does rename_column take care of indexes?

Say, we have something like this:

add_column :users, :single, :boolean add_index :users, :single 

and then later we do

rename_column :users, :single, :married 

Will ActiveRecord and/or the database handle the renaming of the index as well or do I have to manually drop the index and add it again?

like image 313
randomguy Avatar asked Jul 18 '11 12:07

randomguy


People also ask

How do you rename an index in Oracle?

To rename an index in Oracle SQL, you use the ALTER INDEX command: ALTER INDEX index_name RENAME TO new_index_name; You can replace the index_name with the current name of the index, and the new_index_name with the new name for your index.

How to modify column name IN MySQL?

Rename MySQL Column with the CHANGE Statement Enter the following command in your MySQL client shell to change the name of the column and its definition: ALTER TABLE table_name CHANGE old_column_name new_col_name Data Type; You can change the data type of the column or keep the existing one.

How do I rename a column in PostgreSQL?

The syntax to rename a column in a table in PostgreSQL (using the ALTER TABLE statement) is: ALTER TABLE table_name RENAME COLUMN old_name TO new_name; table_name.


1 Answers

For PostgreSQL, rename_column is implemented as a simple ALTER TABLE ... RENAME COLUMN ... and that does preserve the indexes.

The MySQL versions (both of them) do an ALTER TABLE ... CHANGE ... and that also preserves the indexes.

The SQLite version appears to copy the entire table (with indexes), drop the old one, and then copy the copy back to the original table name. The copying does appear to handle the column rename while copying the indexes:

def copy_table(from, to, options = {})   #...   copy_table_indexes(from, to, options[:rename] || {}) 

and inside copy_table_indexes:

columns = index.columns.map {|c| rename[c] || c }.select do |column|   to_column_names.include?(column) end 

So, the standard drivers will preserve your indexes when you do a rename_column and the SQLite driver goes to some effort to do so.

The API documentation doesn't specify any particular behavior though so other drivers may do other things. The closest the documentation comes to saying anything about indexes is this in active_record/migration.rb:

rename_column(table_name, column_name, new_column_name): Renames a column but keeps the type and content.

I think any driver would preserve the indexes but there's no guarantee; a driver writer would certainly be foolish not to preserve the indexes.

This isn't a definitive or authoritative answer but your indexes should be preserved if you use the standard PostgreSQL, MySQL (either one of them), or SQLite drivers.


Note that even though the index itself survives the column renaming there's no guarantee that the index name will be changed. This shouldn't be a problem unless you're doing something (such as manually dropping it) that cares about the index name rather than what columns are involved.

The above behavior changed in Rails 4:

  • In Rails 4.0 when a column or a table is renamed the related indexes are also renamed. If you have migrations which rename the indexes, they are no longer needed.

So ActiveRecord will automatically rename indexes to match the new table or column names when you rename the table or column. Thanks to sequielo for the heads-up on this.

like image 61
mu is too short Avatar answered Sep 20 '22 18:09

mu is too short