Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Azure deployment slots and database migrations

TLDR:

How can an app running in a staging slot know it is in staging and connect to a test database/run migrations on the test database? And, how can that same app in the staging slot automatically become aware it has been swapped to live production slot and is now responsible for live business operations? (So it can switch to using live db, migrate live db etc)

Long version:

The topic is covered partly by this question: Azure Web App deployment slots with database migration

But i didn't really get my answer there..

My app uses FluentMigrator, initiated by an event/code when the app is initialized, to runs database migrations. MSBuild used to do it, but now I'm fairly certain that it's called programmatically

It seems most sensible for:

  • production to have a slot-based app setting that points the code at the production db
  • staging to have a slot-based app setting that points the code at the staging db

I can't see any other way for production to remain functional while staging is being proven, if staging has migrations that wreck the DB for production's understanding; the two DBs have to be separate

So if the DBs are separate, surely the only (nearly) zero downtime way of switching the world to using the code in the staging slot is if the switch causes the app to reinitialise itself and changes it so it becomes pointing to the production DB, then fluentmigrator (which should also be called again) can apply the same set of migrations to production and the code in staging runs the business on the production db for a while..

..production codebase is updated and the swap back occurs. Production code never migrates the production db because it's already updated by the staging code by the time the new version in production fires up

The only other way I foresee things working out is to have two DBs, two slots, and you never perform a swap; you just deploy to staging, it updates the staging DB, you test and prove good, you deploy to production, it updates the produtcion DB, you verify app working.. and the world has suffered a minor amount of downtime while prod was building (or a major amount if the build failed)

Is there a mechanism for the former? When a swap occurs, how could the app be pointed to a new DB and how could migrations be run again?

If the latter is the only way, then deployment slots might as well just be another web app, right? A web app for staging and a web app for prod, to alleviate any confusion slots cause because of how they are represented in the portal..

like image 736
Caius Jard Avatar asked Jun 28 '17 17:06

Caius Jard


People also ask

What are Azure deployment slots?

Azure Functions deployment slots allow your function app to run different instances called "slots". Slots are different environments exposed via a publicly available endpoint. One app instance is always mapped to the production slot, and you can swap instances assigned to a slot on demand.

How many deployment slots are in standard App Service plan?

20 deployment slots (staged deployment)

How do I install deployment slots in Azure?

Testing in production is easy to set up. In the Azure Portal, choose the testing in production menu option in your App Service. Here, you can choose the deployment slots that you want to route traffic to (or add new ones) and assign a percentage of traffic to them. That's it!

How many slots does Azure cloud have?

Azure Cloud Service provides two slots (1) Production and (2) Staging.


1 Answers

It is possible to have a single production database shared by staging and production Azure App Service slots, and still having zero-downtime deployments.

To do this, you need to ensure that all your migrations are backwards compatible, such that the current and new versions of the web app can run simultaneously with the same database. This means you can deploy to the staging slot, perform your smoke tests against the production database, then swap the staging slot for the production slot.

Some rules that allow this to work:

  • New columns should be nullable or have a default value set
  • Columns cannot be dropped
  • Columns cannot be renamed

When you do need to make a destructive changes, such as dropping a column, you need to have 2 releases:

  1. A release that removes the dependency from the web app
  2. A release that performs the change to the database schema

This sounds like a pain, but in practice you probably won't find yourself making destructive changes that often.

like image 78
Cocowalla Avatar answered Sep 20 '22 21:09

Cocowalla