I have a pipeline that has jobs that deploy a database migration and then updates a K8s deployment. I want to use GitLab features where possible, and GitLab’s environments do support rollbacks.
However, clicking “rollback” simply runs the selected previous deployments pipeline again. For the most part this works perfectly however, in the case one is rolling from version N to N-1, generally database migrations must be performed by version N as it has specific knowledge of how to unwind the N changes to revert to N-1 safely.
The alternative is to put a when:manual job into every deployment that does the rollback to a previous version, but the sequencing becomes confusing as there are now multiple actions that must be undertaken in GitLab to successfully rollback, only some of which reflect in the Environments summary so the Environment can easily end up in an inconsistent state.
Also it means every pipeline gets stuck, forever with a cog icon and we want green ticks to assure us deployments have succeeded. The cog implies an outstanding action to finish the deployment.
The rollback environment features aren’t particularly detailed in their documentation; so there is some ‘grain of salt’ to be taken with this.
Since triggering the rollback only does the deploy actions in your pipeline, you would need to alter your deploy to have a version check and if the deploying version is behind the deployed version, rollback the database migrations to the deploying version.
In all normal production deployments, your new deploy action will be ahead of the current database version, and so the action should not need to do anything.
With your deployment action built with this kind of robustness, then the “click button rollback” (or the auto rollback option, if you’re a Gitlab Ultimate customer) should work without manual interaction.
GitLab’s rollback only redeploys code, not DB-aware rollbacks. The best practice is to keep migrations forward-only and create a separate rollback job or pipeline that explicitly handles down migrations before redeploying the older version. This avoids stuck pipelines and keeps environments consistent.