migrate icon indicating copy to clipboard operation
migrate copied to clipboard

Writing migrations for v3

Open alecmev opened this issue 7 years ago • 4 comments

I'm upgrading from v1 just now, and I'm trying to understand why migrations aren't wrapped in transactions anymore. I've seen the issues about some queries not working, so I can see the need for non-transactional migrations, but not to the point of making all migrations raw by default.

I assume the idea is that all migrations must be single-statement (judging by the Postgres examples), so they become "transactions" by themselves, but isn't this unsafer than v1, since you can write a multi-statement (intentionally or by accident) and forget to wrap it in BEGIN/COMMIT? Resulting in a messier cleanup if it goes wrong?

Also, making a separate up/down seems to be way too verbose. I've checked my project, and I have 752 semicolons (read statements, roughly) in its migrations. And it isn't even that large. So many files would make it much more challenging to analyze the evolution of a schema.

More so, having to do "1 statement = 1 file" would make simple things, like defining mutually referencing tables and whatnot, a bit harder. Could be mistaken though.

And then there's the extra step of having to "force" a migration if something goes wrong, instead of just correcting the failed migration and re-running it.

Do you have a real world example of a project using v3 with Postgres? Are you/they happier with v3?

alecmev avatar Jun 19 '17 19:06 alecmev

Thanks for your feedback!

One migration file can have multiple statements. It's up to the user to wrap several statements into transactions. Before that the driver was doing that which lead into conflicts. The current approach is cleaner. (No surprises)

Separate up/down migration files are handy, because existing database utilities continue to work. (again no surprises with custom markup introduced by migrate).

Force is a great protection to keep schemas in sync. If a migration fails in production, human input is always needed. I agree that in development the workflow could be smoother.

I can only speak for myself, but we are using migrate with postgres at @templarbit.

mattes avatar Jun 19 '17 21:06 mattes

It would be possible to create a new source driver that introduces custom markup to combine the up and down migration into one file.

mattes avatar Jun 19 '17 21:06 mattes

Thanks for a quick reply!

I understand that a single file can have multiple statements. My concern is that a user may forget to wrap it in BEGIN and COMMIT (being used to v1 or tools from other ecosystems, like Knex), and he will never notice the mistake, until the migration fails, likely leaving a mess behind.

About separate up/down files - sorry, I've phrased it wrong, I was talking about the "one SQL statement per file" approach advertised in the Postgres examples, and the way it's less human-readable than the regular approach of "one new feature = one new migration file". In my case that would be 752 files, which is a usability downgrade.

About forcing, I understand why it's there too, but with "everything runs in a transaction" in v1 there was no need in it at all. The less I need to remember / think about while doing something as dangerous as touching production data, the better.

Semi-offtopic: In general, I choose to never write down-migrations, because undoing a migration is never a simple task. If you want to go back on a production database, then it will be either super simple or it will require a custom migration (or even a standalone script), as to avoid data loss and whatnot. Can't see a pre-coded down file fitting all possible situations.

And the reason why I asked about a real world example was that I just wanted to know what kind of conventions or team policies people have with migrate v3. I'm not actively working on my project right now, so this is no big deal, but still, would be nice to know, for future reference. Basically, I'm just wondering what's behind the @TODO in MIGRATIONS.md 🙂

alecmev avatar Jun 19 '17 22:06 alecmev

I was also wondering about this: I think I slightly preferred the old style of the drivers doing it for us, but I can understand the reasoning.

At the very least, it'd be great if migrate create stuck the BEGIN; ... COMMIT; in to help us remember.

matthewmueller avatar Nov 13 '17 05:11 matthewmueller