Re: migrations ignoring record changes

Rick DeNatale
Mon, 07 Jan 2008 22:45:07 -0000

On Jan 7, 2008 2:14 PM, Rob Biedenharn
<Rob-GBZH0y1GwQfnZcttdmLDtcI/UQi/AW5J@public.gmane.org>
wrote:
>
> In general, you have to tell ActiveRecord that it needs to rethink the
> columns that the database has:
>
>         User.reset_column_information
>
> But in this case, there''s not really a need to get the model
involved.
>
>         User.update_all([''first_name = ?, last_name = ?'',
"First", "Last"])
>
> will do the same think (and a lot faster, too!)

I''m not sure that this is what''s going on though.

> > On Jan 7, 12:30 pm, Josh
<jjkie...-Re5JQEeQqe8AvxtiuMwx3w@public.gmane.org> wrote:

> >> Before updating to rails 2, i was able to do something like this:
> >>
> >> class AddFirstNameAndLastNameToUsers < ActiveRecord::Migration
> >>  def self.up
> >>    add_column :users, :first_name, :string
> >>    add_column :users, :last_name, :string
> >>    User.find(:all).each do |user|
> >>      user.first_name = ''First''

If AR wasn''t rereading the table definition, then that user.first_name
should have raised a method_missing exception wouldn''t it.

UNLESS, his model already had defined first_name
On the other hand I notice that he''s using save instead of save! so we
don''t know whether or not any validations are failing.

In any event, it should be pointed out that it''s not a good idea to
let migrations find AR classes this way, because migrations can fail
or worse when the model class changes.

The safe way to do this is to do something like

class AddFirstNameAndLastNameToUsers < ActiveRecord::Migration

    class User < ActiveRecord::Base
    end
    ...

You can of course add relationship declarations and even methods if
you need them to the user class (which will actually be
 AddFirstNameAndLastNameToUsers::User)

The point is that the behaviour of the model class is effectively
frozen for this point in the migration stream.

--
Rick DeNatale

My blog on Ruby