← Blog

August 3, 2026 · 5 min read

How to Put Your Magento 2 Store in Maintenance Mode Without Locking Yourself Out of Admin

Running bin/magento maintenance:enable feels safe — until you realize it just locked you out of /admin too, the one place you'd actually go to fix whatever you were maintaining. Here's why that happens, and the fix that doesn't require remembering anything.

Why maintenance mode locks out admin too

Magento's maintenance-mode check lives in \Magento\Framework\App\Bootstrap::assertMaintenance() — code that runs before Magento has resolved whether a request is frontend or adminhtml. There's no "area" yet to exempt admin from, so the core mechanism is genuinely all-or-nothing: it blocks every request except the IPs you explicitly allow-listed with bin/magento maintenance:allow-ips.

In practice, that means the sequence has to go: allow-list your own IP, then enable maintenance mode. Do it in the other order — or from a machine whose IP changed since you last allow-listed it — and you're locked out of /admin with no way back in short of deleting var/.maintenance.flag directly on the server.

This isn't a rare mistake. It's the natural order to reach for under pressure — a store is having an issue, you want maintenance mode on now, and allow-listing your own IP first is an easy step to skip when you're not thinking about it as a separate action from turning maintenance on.

The actual fix: gate by area, not globally

The structural fix is to move the real gating decision to after Magento has resolved which area a request belongs to, and exempt adminhtml unconditionally at that point — so turning maintenance mode on can never lock anyone out of admin, regardless of whether their IP is allow-listed. Core's own mechanism can't do this by itself, since the blocking check runs before that resolution exists.

A module can: neutralize the early, pre-area check with a plugin, then re-implement the real gate downstream as a plugin on the front controller — one that already knows the current area and can skip adminhtml outright while still blocking the storefront, GraphQL, and the REST/SOAP APIs exactly like core used to.

What you get on top of that

  • A maintenance page you actually control — title, message, background image, logo, and social links — instead of the stock static error page.
  • A live countdown to a scheduled auto-disable time, so the page tells visitors when to check back instead of just "come back later."
  • The option to point maintenance mode at a full CMS Page (Page Builder) instead, for complete design freedom.
  • API awareness: webapi_rest/webapi_soap/GraphQL clients get a small JSON response instead of an HTML page, so integrations fail cleanly instead of trying to parse a maintenance page as JSON.

Toggle it, build the page, and never worry about the admin lockout again.

See Maintenance Mode — from $29