Rails migration woes

Julkaistu

Who would tell me what’s the exact intended purpose of (insert your favorite MVC webapp framework here1) migrations. Yes, I know, using migrations you are supposed to maintain your schema and drag your production data with you as your app evolves. And yes, I know, you can do all kinds of fancy maintenance and data refactoring things in there too.

1 I’m looking this mess from Rails perspective.

There are quite a few things that puzzle me with this, but the seemingly very common habit of writing Rails app bootstrapper in migrations bugs me the most. (For now.) People do it (a lot) even though it’s got several downsides.

  • Bootstrapping the application becomes heavi… no, not heavily, totally coupled with the whole history of your schema manipulations. Bootstrapping process, instead of just sticking to what it really needs to do, ends up making a pilgrim through every step of evolution from simple amino acids to Osmo Soininvaara.
  • If you take the migrations strictly as schema migrations, they are inheretly run-once-code. If you use your models in migrations (which you most probably are going to do in your bootstrapping code and if you bootstrap with migrations…) and your application evolves you are sooner or later going to break you migrations or be bound to do serious hoop-jumping to keep them from not breaking. But why on earth do you even care to maintain run-once-code? I think you shoud not.

Another thing is the “downside” of a migration. Have you ever written a #down() for a non-trivial schema or data manipulation? Or have you ever even used a #down()? And what are they good for? If I want a safe (or heck, any) downgrade path for data, it’s a database dump and certainly not some snippet of code that might reverse the migration (or might not).

Now (and it may change any minute…) I think the Right™ way to go would be to maintain schema, bootstrapper and migrations separately. Schema would be the up-to-date and no-bullshit description of your
datastructures. Most frameworks maintain schema automatically for you when you create migrations. Bootstrapper would use schema description, application code and supporting dataset to bootstrap app. Migrations would be strictly for migrating schema and production data. And you should keep yourself from using app code in migrations.