FlywayDB - afterBaseline - flyway

I have a clean DB that I want to run a "seeding" script on after the initial V1 migration.
Will the afterBaseline callback be called after an initial migration to a clean DB?

This appears to only be called after the baseline command is executed, and not after the initial migration.
The solution I took was to create a "V2" migration that contained my DML/seeding data.

Related

EF Core Model Snapshot out of sync between add-migration and update

I'm using EF Core and code migrations. It's my understanding that the snapshot file is supposed to be the "target database" to build future migration files off of.
Situation:
1) I did an add-migration to create a migration after some changes. This updated the modelsnapshot which I guess is the expected behavior.
2) I then realized I realized I mis-typed one of my fields. Instead of a string it was supposed to be a byte[]
3) I made the changes to the classes
4) I did add-migration again.
Now the DataSnapshot seems to be out of sync because the new add-migration does not include this type file change.
It doesn't seem like I can do a remove-migration because no migration was actually applied to any database.
I know in EF6, this was a fine way to do it because it always targeted an actual database for the changes and not this snapshot file. So just deleting the change file and remaking the change file was good enough.
This is the second time I've had to make some change to a migration file after realizing there was an issue (without actually running the update against anything) and both times were just incredible pains to try to fix the issue without wiping out all my previous migrations and starting over.
My question is how do I handle this now? Should I be deleting both the change file and the snapshot file every time I do backtrack on an add migration?
I'm really concerned that I'm missing something here because now I have to make sure that not only is the change file correct but also the current snapshot is correct as well and if that snapshot ever goes out of sync, then I have to go and manually update it to
Probably have solved this by now, but I just ran into this.
Not sure if this is exactly the same issue, but this is how I understand it.
update-database is a DB action and updates your DB to current version or target migration.
remove-migration is an EF action and updates your migration stack and updates your snapshot.
To downversion I had to update database then remove migration down to the intended target.
At this point adding a new migration gave me the expected set of changes, where as before it was giving me none.
This appeared to do what I expected from EF doing update-database and update-database -target
The only thing I think you can actually do wrong in this case is delete your migration files before doing the update, because the down steps are indicated in the migration files, so it wont be able to complete this step if you remove the files. If you have the files, you can freely target migrations to set your current DB state.
I believe the confusing part is that the snapshot was previously used on every migration, where as now there's one snapshot for "last migration"

How to skip a particular script from execution in flyway

I have merged some code in git repository with three scripts(V1,V2,V3) for Flyway), and I have later found out that there is a problem in the script (V2). I don't want to modify the script V2, I just want to skip the execution of the script V2 by Flyway.
One simple solution would be to change the sql file name so that it is not taken into account anymore by Flyway (Eg. V2_scriptname -> OLD_V2_scriptname). That should do it if changing the sql file name is an option.

What is the best way to remove repeatable scripts from Flyway Migrations

I am currently using the Flyway Command Line tool to manage our scripts which will be invoked via our release process triggered from our CI Build server.
The issue is I have 274 repeatable migrations covering package specs, package bodies, functions, procedures, views and materialised views.
When I run migrate everything works as expected with migrations executing followed by any changed repeatable migrations but lets say in the next release we want to delete a object which one of the repeatable migrations maintains. For example, we want to remove the repeatable script that defined ProcedureOne (ie R__ProcedureOne.sql).
To do this I would have a new migration script (V3.1.5.1.01__DropProcedureOne.sql) but I would also remove the repeatable migration script so the object isn't created again and maintained.
However, executing flyway info shows the R__ProcedureOne.sql script with the status of MISSING.
While I agree it is missing it is a deliberate action to have it deleted as it is no longer required opposed to being misplaced.
I am aware of the migrate option ignoreMissingMigrations but i think using this introduces risk and could mask genuine missing files.
What is the general guidance on how best to remove a repeatable scripts?
I suggest that you simply keep the file but make it empty (ie zero bytes). Alternatively have a comment in the file that explains that the object it represents has been removed.
As for actually removing it, another option from what you suggested could be to update the repeatable migration to remove itself then update again to zero length. This has the advantage of being able to be replayed into an empty database; since repeatable migrations are applied after versioned the procedure in your example won't exist to be dropped. The disadvantage is running two migrations.

Any way to "compress" Flyway migrations?

We are using Flyway to migrate the database schema and we already have more than 100 migration scripts.
Once we "squashed" multiple migrations into a single first-version migration, this is ok during development, as we drop and recreate the schema. But in production this wouldn't work, as Flyway won't be able to validate the migrations.
I couldn't find any documentation or best practice of what to do in this case. The problem is that the file quantity increases constantly, I don't want to see thousands of migration files everytime, essentially if production is already in the latest version. I mean, the migration scripts that have a version number that is lower than the version in production are irrelevant to us, it would be awesome if we could squash those files into a single migration.
We are using MySQL.
How should we handle this?
Isn't that what re-baselining would do?
I'm still new to flyway, but this is how I think it would work. Please test the following first before taking my word for it.
Delete the schema_version table.
Delete your migration scripts.
Run flyway baseline
(this recreates the schema_version table and adds a baseline record as version 1)
Now you're good to go. Bear in mind that you will not be able to 'migrate' to any prior version as you've removed all of your migration scripts, but this might not be a problem for you.
Step by step solution:
drop table schema_version;
Export database structure as a script via MySQL Workbench, for example. Name this script V1__Baseline.sql
Delete all migration scripts and add V1__Baseline.sql to your scripts folder, so it is the only script available for Flyway
Run Flyway's "baseline" command
Done
We do this to allow us to compress scripts for building new DB in dev environments but also run against existing production DB without having to log on and delete the flyway_version_history table, and we can keep the scripts (mainly for reference):
Compress all the scripts to a new script e.g. V1 to V42 into a new scripts V43.
Convert V1 to V42 to text files by putting .txt on the end.
Set the baseline to 43.
Set flyway to ignore missing migrations.
In script V43 use an 'if' block to protect the create/insert statements so that they don't run for the existing production database. We use postgres so it is something like this:
DO $$
DECLARE
flywayVersion INTEGER;
BEGIN
SELECT coalesce(max(installed_rank), 0) INTO flywayVersion FROM flyway_schema_history;
RAISE NOTICE 'flywayVersion = %', flywayVersion;
IF flywayVersion = 0 THEN
RAISE NOTICE 'Creating the DB from scratch';
CREATE TABLE...
.....
END IF;
END$$;
The flyway command looks something like this:
Flyway.configure()
.dataSource(...)
.baselineVersion("43")
.ignoreMissingMigrations(true)
.load()
.migrate()
I haven't tried this, but what if you deleted all the migrations, create a new migration that creates the new starting point as version 1, set it as the baseline version -- and then modify your configuration to use a different table (e.g. flyway_schema_history_2)?
In existing databases, Flyway will see that you have a non-empty schema with no (recognized) flyway table and ignore the baseline migration. In new environments it will run the baseline migration too.
Am I missing anything?
(Of course a separate problem is how to generate the "compressed" migration. If you don't need any seed data you can just do a schema-only backup of your database and use that. If your migrations populate data too you will probably have to work that out manually.)
I think this article answers your question best:
https://medium.com/att-israel/flyway-squashing-migrations-2993d75dae96
For postgres a reusable script has been created that you could execute every so many months for instance. You can of course adapt the script to MySQL specific things instead of postgres:
https://github.com/the-serious-programmer/flyway-postgres-squash-script

Error while updating database code first EF

I have a .net MVC project which works with Code first approach, I need to add a new table and the migration folder already exists and contains a lot of migrations files that have been made before; when I run Add-Migration:
Unable to generate an explicit migration because the following
explicit migrations are pending:
[201304230714010_InformationalMessage, 201305231312259_Remove
hardcoded currencies ]. Apply the pending explicit migrations before
attempting to generate a new explicit migration.
So I run Update-Database –Verbose it gives me error:
There is already an object named 'InformationalMessage' in the
database.
which seems that it goes to execute the migrations files again and it is normal to give me that error as it already exist.
Can anyone help me to how to update this code with my new table?
Error says you are already having pending migration so first run the pending migration and then run your migration.
update-database -verbose (run first pending migration).
Add-migration <nameOfMigration> (add your migration).
Update-database -verbose (run your migration in the last).
I've run into that occasionally. What I do is comment out the CreateTable command for that migration in the Up() and Down() methods. When I need a production script I am usually rolling my changes up into a single update anyways.
Temporarily add DropTable("InformationalMessage") to your copy of the 201304230714010_InformationalMessage migration – be warned, this will lose any data currently in that table, but should get you to a point where you can add your new migration … if this is a concern, make a backup of the actual table data while working on your migration.
You either need to run "update-database" from the package manager console to push your changes to the database OR you can delete the pending migration file ([201304230714010_left]) from your Migrations folder and then re-run "add-migration" to create a brand new migration based off of your edits.

Resources