Introduction
Before we begin, you should take a look at one of my previous articles “How to solve Symfony 5 and Doctrine Migrations Bundle 3 upgrade error: Unrecognized options “dir_name, namespace” under “doctrine_migrations”.” That article covers the base case when you don’t have any migrations and, technically, everything worked fine — until actual migrations needed to be migrated to the new Doctrine Bundle version.
This article covers what needs to be done in order to update existing migrations.
Update for existing migrations
If you have followed the first article, you will encounter further post-update issues if you have migrations that were already executed before the Doctrine bundle upgrade. To resolve the issues, follow these steps:
Make sure to have the correct environment loaded
This was covered in the original article, but let’s make sure it’s done before proceeding. If you had any other environment set in the .env
file, the upgrade could rewrite it and set the environment back to dev
. Make sure to revert it back to the proper environment (In my case, it was local
).
Move the existing migration files
Move (cut and paste) your existing migrations (their .php
files) to the new Doctrine migrations folder.
Previous Doctrine migrations folder was src/Migrations
while the new one is migrations
(relative to your project root directory). To make sure you’re using the correct folder, open config/packages/doctrine_migrations.yaml
file and look for migration_paths
configuration option. It should contain the following (new) namespace definition and its directory 'DoctrineMigrations': '%kernel.project_dir%/migrations'
.
Sync Doctrine metadata storage
Run php bin/console doctrine:migrations:sync-metadata-storage
.
Doctrine changed its migrations version database table in version 3.0. The default table name in 2.x was migration_versions
and the new table name is doctrine_migration_versions
. The table structure is different in 3.0 as well — a new column execution_time
is introduced which contains an amount of milliseconds the migration took when it was executed. The sync-metadata-storage
command should create the new doctrine_migration_versions
database table for you.
Import data from the old migration versions table
The previous command set up the new default Doctrine migrations database table. The only thing left to do now is to let Doctrine know that you’ve already executed some migrations in the previous version.
To do that, run the following MySQL query:
INSERT INTO doctrine_migration_versions (version, executed_at, execution_time) SELECT concat("DoctrineMigrations\\Version", version), executed_at, 1 FROM migration_versions;
This query does a couple of things:
version
column in the old table contained only migration timestamp (ex.20200820072236
). The new Doctrine bundle supports multiple namespaces, the default one beingDoctrineMigrations
. So, in order to transfer the old migrations to the new table, we’re addingDoctrineMigrations\Version
as a prefix in order to get the new format:DoctrineMigrations\Version2020082007226
We are adding a sample value
1
as the value of newexecution_time
column. You can put anything here, since it only marks the amount of milliseconds a migration took when executed.
Cleanup the old table
If everything up until now went smoothly, the old migration_versions
table is now obsolete. But, before deleting it, verify that the migrations are upgraded successfully with php bin/console doctrine:migrations:status
. If Executed Unavailable
value is 0
we should be fine.
Just as a precaution, export the structure and data of the old migration_versions
table. After a breaking, backwards incompatible change like this, you never know if anything else is going to break in the future.
You can now delete migration_versions
table from the database.
Conclusion
We have done the following:
Moved the old migration
php
files to the new migrations directory;Synced Doctrine migrations metadata storage;
Let Doctrine create the new default
doctrine_migration_versions
;Convert to the new format and import the old migrations to the new database table;
Verify that the upgrade went smoothly;
Backup (export) the old
migration_versions
database table and then delete it.
That’s it for now. This should conclude the Doctrine migrations bundle upgrade to version 3.0.
Top comments (3)
As noted in the migrations bundle upgrade notes
Instead of manually migrating data, you can simply specify the
table_name
.If your project did not originally specify its own table definition configuration, you will need to configure the table name after the upgrade:
This is probably the way I will go, as I would rather avoid the step of executing the SQL query to migrate data manually. Thanks for the extra tip on top of this nice article.
Thank you mate, this helped me navigate better what to run at which stage. Appreciated it.