148

I have a Products table and want to add a column:

t.references :imageable, :polymorphic => true

I was trying to generate migration for this by doing:

$ rails generate migration AddImageableToProducts imageable:references:polymorphic

but I am obviously doing it wrong. Can anybody make any suggestion? Thanks

When I try to manually put it in after generating the migration, I did it like this:

class AddImageableToProducts < ActiveRecord::Migration
  def self.up
    add_column :products, :imageable, :references, :polymorphic => true
  end

  def self.down
    remove_column :products, :imageable
  end
end

and it still hasn't worked

railslearner
  • 1,761
  • 2
  • 14
  • 18
  • 2
    Not an answer, but to avoid confusion, are you sure you want this column on Products? The rails guide even has a Products example and the column is on Pictures http://guides.rubyonrails.org/association_basics.html#polymorphic-associations – atomkirk Oct 31 '15 at 12:20
  • This can be handy: `:references{polymorphic}`. For example, `rails generate migration AddImageableToProducts imageable:references:{polymorphic}`. [Source](https://til.hashrocket.com/posts/kaawvv04xh-generate-a-migration-with-polymorphic-association) – floer32 Mar 08 '21 at 22:06

4 Answers4

316

What you are trying to do is not yet implemented in the stable version of rails so Michelle's answer is the right one for now. But this feature will be implemented in rails 4 and is already available in the edge version as follows (according to this CHANGELOG):

$ rails generate migration AddImageableToProducts imageable:references{polymorphic}

Some shells may need {polymorphic} escaped with a \:

$ rails generate migration AddImageableToProducts imageable:references\{polymorphic\}
jprofitt
  • 10,874
  • 4
  • 36
  • 46
simon-olivier
  • 3,439
  • 2
  • 14
  • 6
  • 2
    Tried this on 4.2, and I'm not sure if this is a bug, zsh, or something else, but the commandline was interpretted as a series of references (as types) with each letter of polymorphic, like: t.referencesp :imagable, treferenceso :imagable, etc. – OzBarry Apr 07 '15 at 18:09
  • 14
    @OzBarry, in zsh you'd need to escape the braces: $ rails generate migration AddImageableToProducts imageable:references\{polymorphic\} – chad_ Jun 01 '15 at 16:17
  • 6
    For anyone curious, this generates a migration with change method containing: `add_reference :products, :imageable, polymorphic: true, index: true` – stevenspiel May 19 '16 at 15:32
  • 2
    Incase anyone trying to use the same in scaffold, this works with scaffold as well. Thanks! rijks – sghosh968 Oct 06 '16 at 18:34
  • 2
    `{polymorphic}` needs to be escaped with the fish shell, e.g. `\{polymorphic\} ` – Dorian Oct 16 '17 at 09:53
122

Before Rails 4 there was no built-in generator for polymorphic associations. If you are using an early version of Rails generate a blank migration and then modify it by hand according to your needs.

Update: You'll need to specify which table you're changing. According to this SO answer:

class AddImageableToProducts < ActiveRecord::Migration
  def up
    change_table :products do |t|
      t.references :imageable, polymorphic: true
    end
  end

  def down
    change_table :products do |t|
      t.remove_references :imageable, polymorphic: true
    end
  end
end

Rails 4 added a generator for polymorphic associations (see simon-olivier answer)

notapatch
  • 6,569
  • 6
  • 41
  • 45
Michelle Tilley
  • 157,729
  • 40
  • 374
  • 311
  • Thank you very much Brandon. I was able to run the migration. I was wondering though, after you make :polymorphic => true and you open schema.rb are you supposed to see it in the schema as well? – railslearner Apr 04 '11 at 05:45
  • After you run the migration, `schema.rb` should be updated, but it won't say anything about `polymorphic`. Instead, you should see the actual fields that Rails uses (the [Rails Guides](http://guides.rubyonrails.org/association_basics.html#polymorphic-associations) have more info). – Michelle Tilley Apr 04 '11 at 15:44
  • 2
    How do you add index to the `references` column? Do I need to index that? – mrudult Apr 20 '14 at 18:20
  • @mrudult If I'm not mistaken, you do need to add them yourselves if you need them. You can just add indexes as normal in the migration file to `imageable_type` and/or `imageable_id` as necessary. – Michelle Tilley Apr 20 '14 at 18:23
  • Well if I try `add_index :products, :imageable, unique: true ` It throws `PG::UndefinedColumn: ERROR: column "imageable" does not exist`. I think I need to manually add indexes for the two columns which are generated. Trying that. – mrudult Apr 20 '14 at 18:29
  • 2
    Yup. adding index to `imageable_id` and `imageable_type` worked. Thanks for your help. – mrudult Apr 20 '14 at 18:31
  • You should also index this as well: `t.references :imageable, polymorphic: true, index: true` – Nate Bird Jun 21 '17 at 14:32
49

You could also do the following:

class AddImageableToProducts < ActiveRecord::Migration
  def change
    add_reference :products, :imageable, polymorphic: true, index: true
  end
end
freddyrangel
  • 1,353
  • 1
  • 11
  • 20
20

You can try rails generate migration AddImageableToProducts imageable:references{polymorphic}

hutusi
  • 437
  • 6
  • 14