Маркеры окружений DEV/STAGING/PROD — 5 способов перестать ломать продакшен
Ты нажимаешь «Удалить все аккаунты», думая, что находишься на staging. Это был продакшен. Это случается с каждым DevOps и инженером хотя бы раз. Пять техник визуальной маркировки окружения, чтобы ты больше не попал в эту ловушку.
Способ 1 — красный баннер сверху
Самый очевидный и самый эффективный. Полоса наверху каждой страницы, которую невозможно проигнорировать:
body::before {
content: "ОКРУЖЕНИЕ DEV — данные могут быть не продакшен";
position: fixed;
top: 0; left: 0; right: 0;
background: repeating-linear-gradient(
-45deg, #dc2626, #dc2626 12px, #b91c1c 12px, #b91c1c 24px
);
color: #fff;
text-align: center;
padding: 6px 12px;
font: 700 13px/1.4 ui-monospace, monospace;
letter-spacing: .5px;
z-index: 999999;
text-shadow: 0 1px 2px rgba(0,0,0,.3);
}
/* Отступ body, чтобы контент не уезжал под баннер */
body { padding-top: 32px !important; }
Повторяющийся градиент создаёт узор «предупреждающей ленты», как на стройплощадках — по эволюции это означает опасность. Без градиента это была бы обычная информационная полоса; с ним её никто не игнорирует.
Способ 2 — плавающий бейдж в углу
Баннер сверху агрессивен и занимает место. Иногда хочется чего-то более деликатного — небольшого бейджа в углу:
body::after {
content: "DEV";
position: fixed;
bottom: 16px; left: 16px;
background: #dc2626;
color: #fff;
padding: 6px 12px;
border-radius: 8px;
font: 700 12px ui-monospace, monospace;
letter-spacing: 1px;
z-index: 999999;
box-shadow: 0 4px 12px rgba(220, 38, 38, .4);
pointer-events: none; /* не блокировать клики */
}
Закреплён в углу, виден, но ненавязчив. pointer-events: none критически важен — без него бейдж блокировал бы кнопки под ним.
Способ 3 — замена фавикона
Баннер помогает, только когда ты смотришь на страницу. Вкладка браузера видна даже после Cmd+Tab. Замени фавикон:
// Генерируем новый фавикон (красный круг с буквой D)
const canvas = document.createElement('canvas');
canvas.width = 32; canvas.height = 32;
const ctx = canvas.getContext('2d');
ctx.fillStyle = '#dc2626';
ctx.beginPath();
ctx.arc(16, 16, 14, 0, Math.PI * 2);
ctx.fill();
ctx.fillStyle = '#fff';
ctx.font = 'bold 18px sans-serif';
ctx.textAlign = 'center';
ctx.textBaseline = 'middle';
ctx.fillText('D', 16, 17);
// Удаляем старые фавиконы
document.querySelectorAll('link[rel*="icon"]').forEach(el => el.remove());
// Добавляем новый
const link = document.createElement('link');
link.rel = 'icon';
link.type = 'image/png';
link.href = canvas.toDataURL();
document.head.appendChild(link);
Красная D во вкладке, всегда видна. Работает и в закладках — закладки staging и продакшена становятся тривиально различимыми.
Способ 4 — тонкий оттенок вьюпорта
Самый изящный — лёгкий цветной оверлей, который придаёт всей странице едва заметный оттенок:
/* Оранжевый оттенок для STAGING, красный для DEV */
html::before {
content: '';
position: fixed;
inset: 0;
background: rgba(245, 158, 11, .04);
pointer-events: none;
z-index: 999998;
mix-blend-mode: multiply;
}
rgba(..., .04) = почти невидим, но через несколько секунд мозг знает «что-то иначе». Через несколько дней замечаешь это мгновенно. Без агрессивности баннера.
Способ 5 — префикс в заголовке вкладки
Вкладка браузера показывает document.title. Добавь префикс:
// Префикс заголовка + внимание к SPA, меняющим его динамически
const PREFIX = '[DEV] ';
function ensurePrefix() {
if (!document.title.startsWith(PREFIX)) {
document.title = PREFIX + document.title;
}
}
ensurePrefix();
// SPA часто меняют заголовок при смене маршрута
new MutationObserver(ensurePrefix)
.observe(document.querySelector('title'), { childList: true });
MutationObserver ловит SPA, переписывающие заголовок при смене маршрута. Без observer'а префикс исчезает после первой навигации.
Ловушки
- Не применяй это в продакшене — URL-паттерн должен быть узким:
https://staging.*,https://*-dev.*,http://localhost:*. Не*. - Конфликт z-index — некоторые cookie-баннеры или модальные окна используют z-index 9999. Твои маркеры должны быть выше (999999 должно хватить).
- Стили для печати — баннер появится в распечатанном PDF. Добавь
@media print { body::before { display: none } }, чтобы его пропустить. - iframe — страница, встроенная в iframe, не наследует CSS родителя. URL-паттерн должен совпадать и с содержимым iframe, чтобы маркер появился внутри.
Как подключить это к JustZix
- Установи JustZix.
- Папка «Маркеры окружений». Правило для окружения:
- Паттерн
https://*-staging.company.com/*→ способ 1 (баннер) + способ 3 (фавикон). - Паттерн
http://localhost:*/*→ способ 2 (бейдж) + способ 5 (префикс заголовка).
- Паттерн
- Ссылка для импорта всей команде — у всех одинаковые маркеры окружений.
Установи JustZix бесплатно и перестань ломать продакшен из-за «случайных кликов».
Оцени эту статью
Оценок пока нет — оцени первым.