davedevelopment / phpmig

Simple migrations system for php
Other
568 stars 92 forks source link

Can you rename the migrations table? #139

Closed AlgyTaylor closed 5 years ago

AlgyTaylor commented 5 years ago

I've recently found myself wanting to merge two databases (both using phpmig) into one uber-database.

Is it possible to alter the name of the migration table during a migration? (possible as in either "yes, use this function" or "yes, edit this class and make a pull request")

As a more concrete example, I'd like to run this SQL:

ALTER TABLE migrationschema.migrations RENAME TO migrationschema.report_migrations;

So at the start of the migration, the table name is "migrations", but at the end of the migration it's called "report_migrations".

I tried to dynamically set the table name in a text file (so there's a file_put_contents('dbtablename.txt', 'report_migrations') type function call in there), but perhaps unsurprisingly this continues to use the original value rather than the updated value for the duration of the migration, which isn't really what I want....

EDIT There's a roundabout way of doing it by using two separate migrations and a bit of jiggery-pokery, I just wondered if it was possible to do it sans-pokery....

davedevelopment commented 5 years ago

My gut feeling is no and I would probably go with a split migration type thing.

AlgyTaylor commented 5 years ago

I went down the split-migration thing. It worked, so that's good. The key, though, is to run both migrations separately, something like

$ phpmig migrate -t 20181219104903
$ phpmig migrate

where the time is the date of the first migration. If you run both at the same time, it causes an error (I forget the message). The migration itself is probably too specific, but I've copy/pasted my comments below in case someone needs a rough 'how to' guide:

/**
 * Upwards migration
 * =================
 *
 * First migration
 * ---------------
 *
 * 1. Create a temporary copy of the ``migrations`` table with it's
 *    new name
 * 2. Copy the data from the existing ``migrations`` table to the
 *    temporary table
 * 3. Insert a new record in to the temporary table with the version
 *    number of this migration (the date in the filename).
 * 4. Alter the code to reference the new table name
 *
 * At this point, the migration code will update the old table
 * (``migration``) with details of when the update was completed.  However,
 * with our temporary table, the next time the code runs, it will
 * recognise that this migration has taken place.
 *
 * From this stage, we have achieved:
 *
 * - Altering the code to reference the new table
 *
 * Second migration
 * ----------------
 *
 * 1. Delete the temporary migrations table
 * 2. Rename the old table (``migrations``) to the new name
 *
 * This will ensure that we retain a complete record of the migrations we've
 * run, along with exact timestamps.
 *
 * From this stage, we have achieved:
 *
 * - Renamed the 'real' table
 * - Removed our temporary data
 *
 * Downwards migration
 * ===================
 *
 * Second migration (run first)
 * ----------------
 *
 * 1. Create a temporary copy of the renamed table under it's old name (``migrations``)
 * 2. Copy the data from the current table to the temporary table
 * 3. Remove the record for the current version from the temporary table
 * 4. Alter the code to reference the old table name
 *
 * First migration (run second)
 * ---------------
 *
 * 1. Delete the temporary migrations table
 * 2. Revert the new table to the old name (``migrations``)
 */