Magento Production Deployment and Rollback Strategy
A release-based Magento deployment model covering immutable artifacts, shared state, maintenance, cache and index work, smoke tests, rollback, and served verification.
A deployment succeeds only when the served store succeeds
A completed Composer command, a green CI job or a changed current symlink is not the customer outcome. Magento deployment crosses code, generated dependencies, static assets, configuration, writable shared state, caches, indexers, PHP workers, the web server and any edge cache. The release is complete only when the intended commit is active and representative storefront, Admin and API flows are healthy.
The safest model separates building from activation. Build and review an immutable release directory first. Activation then becomes a short, reversible change to the current pointer rather than a long series of edits inside the live document root.
[Merged commit]
v
[Build immutable release]
v
[Link shared config + media]
v
[Pre-activation checks]
v
[Atomic current symlink switch]
v
[Origin + edge + browser smoke tests]
| pass | fail
v v
[Keep release] [Switch to previous release]Define immutable and shared state explicitly
Code, vendor dependencies, generated factories and deployed static assets belong to the release. Environment configuration, customer media and other mutable operational state belong in reviewed shared locations. Writable runtime directories need deliberate ownership and permissions rather than a recursive permission command across the application.
This boundary makes rollback meaningful. If a release writes unversioned code into shared storage or mutates files in place, switching the symlink cannot restore the previous application state. Database changes need the same scrutiny because a code rollback cannot automatically reverse destructive schema or data changes.
- Release-owned: app code, vendor, generated code, pub/static and build manifest.
- Shared: env.php, config.php when managed outside releases, pub/media and approved secrets.
- Runtime writable: var, generated metadata where the deployment model requires it, and upload/cache paths with narrow ownership.
- Database: backward-compatible changes first, destructive cleanup only after old code can no longer run.
Build from the exact reviewed commit
Record the full commit SHA and release identifier before building. Install locked dependencies without development packages, compile DI for production mode, deploy only the required locales, and make the artifact read-only where practical. Do not copy a working tree with unrelated changes to production.
Whether setup:upgrade belongs before or after activation depends on migration compatibility and downtime design. The fixed requirement is that the decision is documented for that release and the rollback impact is understood before the command runs.
git archive <reviewed-commit> | tar -x -C "$release_dir"
composer install --no-dev --prefer-dist --no-interaction --optimize-autoloader
php bin/magento setup:di:compile
php bin/magento setup:static-content:deploy -f en_GB en_US
php bin/magento cache:cleanMake activation short and reversible
Before the switch, validate configuration links, media visibility, file ownership, free disk space, the Nginx configuration and required services. If maintenance mode is needed, enable it only for the smallest customer-facing window and define who will disable it on both success and rollback paths.
Switch current to the fully built release atomically. Reload services only when the change requires it. Clear or invalidate the narrowest cache layers necessary, then run the release smoke matrix. A blanket cache flush is sometimes required, but it should not substitute for understanding which layer serves the route.
Use a smoke matrix that represents the business
HTTP 200 on the homepage is weak evidence. A useful matrix includes a category and product page, search, cart, checkout entry, customer session boundary, a safe API method, required static assets and an Admin login or read-only Admin check when authorised. If the release changes indexers, cron, queues, payment, shipping or an integration, add those paths explicitly.
Check the origin and the publicly served response. A healthy origin behind a stale or broken edge cache is still a broken release. Confirm the active release ID and served asset hashes so a previous artifact is not mistaken for success.
- Expected status, canonical and robots behavior for public routes.
- CSS, JavaScript, fonts and images from the active artifact.
- PHP-FPM, Nginx, Magento and queue/cron logs during the smoke window.
- Maintenance state is off and the previous release remains available.
Rollback criteria must be decided before activation
Rollback is appropriate for critical customer-path failures, missing assets, a broken dependency graph, severe new errors, an incompatible configuration link or a release that cannot pass the agreed smoke matrix quickly. Continuing to patch the active release increases recovery time and destroys the immutability that made rollback safe.
Switch the current pointer to the known previous release, restore compatible cache or service state, disable maintenance mode, and rerun the same matrix. If the new release applied a backward-incompatible database change, symlink rollback may be unsafe. That is why database compatibility is a release-design decision, not an afterthought.
Post-release verification and monitoring
Keep the deployment open until immediate verification is complete, then monitor the signals most likely to reveal delayed failure.
- Verify status, metadata, sitemap and representative assets from the public hostname.
- Watch application, web-server and PHP error rates after activation.
- Confirm cron and consumers continue processing and indexers reach expected states.
- Review checkout, payment and integration callbacks without sending an unauthorised test order.
- Retain the release record: commit, release path, activation time, checks, operator and rollback point.
Continue with related work
Apply this to the store you are operating.
Share the Magento version, affected path, constraints and current evidence. The quote flow keeps this article as the source context.