Что это вообще такое #
Если ты когда-нибудь просил AI-помощника (Claude, ChatGPT, Cursor) сделать тебе сайт, ты замечал одно и то же: получается вроде неплохо, но подозрительно «как у всех». Тёмно-синий фон, фиолетовый градиент в заголовке, карточки с лёгкой тенью, шрифт Inter. Узнаваемый «AI-look».
Причина банальная: большие языковые модели учились на одних и тех же
типичных шаблонах. Без отдельных указаний они выдают усреднённый
дизайн, в котором повторяются одни и те же стандартные ошибки:
градиент в заголовке через background-clip, серый текст на цветном
фоне, бесконечные одинаковые карточки в сетке, ноль характера.
Impeccable от Paul Bakaus решает именно эту задачу. Сам автор позиционирует его как «дизайн-словарь для AI-помощников по коду»: набор из одного навыка и 23 команд, которые дают AI и человеку общий понятийный аппарат. Каждая команда отвечает за свою дизайн-дисциплину: типографика, цвет, ритм пространства, взаимодействия, копирайтинг, элевация (тени и слои), анти-паттерны. Плюс отдельный список из 25 типичных «AI-ляпов», которые детектор ловит автоматически.
Что важно: impeccable — не библиотека CSS-токенов и не редактор макетов. Он живёт в твоём боевом коде, читает существующие исходники, рендеренный HTML, дизайн-документы, и вместе с AI правит то, что уже есть. Не «нарисуй мне сайт с нуля», а «доведи существующий до состояния, в котором он перестанет быть похожим на любой другой блог».
Я взялся применить это к собственному Hugo-блогу. Hugo — статический
генератор сайтов: ты пишешь посты в Markdown, конфиг и HTML-шаблоны,
он собирает готовые HTML-файлы. Дизайн жил в одном CSS-файле плюс
тема typo как git submodule. К апрелю накопилось ощущение
«работает, но как-то не так». Тёмная тема жила в одной палитре,
светлая — местами в другой. Страница «Обо мне» выглядела как
кусочек чужого SaaS-сайта, попавший в блог по ошибке.
Решил пройти все нужные команды и посмотреть, что инструмент реально ловит. Получилось пять заходов за вечер.
Фундамент: PRODUCT.md и DESIGN.md #
Первая команда — /teach. Это не «настройки», а короткое интервью:
кому пишешь, каким голосом, чем не должен быть сайт, какие
требования к доступности. На выходе два файла в корне проекта:
- PRODUCT.md — стратегический документ. Регистр (бренд или продукт), целевая аудитория, голос, анти-референсы, дизайн-принципы, планка доступности.
- DESIGN.md — визуальная спецификация. Цвета, шрифты, шкала пространства, шкала радиусов, компоненты.
Эти два файла потом читает каждая последующая команда. Без них
любой /audit или /polish даёт ответы вообще, не привязанные к
конкретному проекту.
Главное открытие здесь — раздел анти-референсов. PRODUCT.md заставляет ответить, чем сайт не должен быть. Я выписал четыре конкретных образца, которые не хочу повторять:
- Habr и VC.ru с их боковыми панелями, бейджами и блоками «читайте также» на пять экранов;
- Medium и Substack: безликий шаблон платформы, попап «подпишись», где ощущение «это любой блог»;
- современный SaaS с градиентами и стеклянными карточками;
- Dev.to и обычные GitHub Pages: стандартный markdown без типографики, синие ссылки, sans-serif, ноль характера.
Анти-референсы оказались полезнее обычных «делай как Stripe». «Как Stripe» — растяжимое: можно повторить любой кусок и сказать «вот видишь, похоже». «Не как Habr» — конкретный отказ. Каждое следующее дизайн-решение проверялось по этому списку и часто не проходило: «а не повторяю ли я сейчас Habr-ленту одинаковых превью?»
Дальше команда /document отсканировала существующий CSS и собрала
DESIGN.md. Здесь я первый раз ошибся — но об этом дальше.
Аудит: 11 из 20 на старте 📊 #
/audit — техническая проверка по пяти направлениям, каждое от 0
до 4 баллов: доступность, производительность, согласованность
дизайн-токенов, адаптивность, отсутствие шаблонных AI-ляпов.
Финальная оценка моего блога — 11 из 20. Между «нормально, но работы много» и «плохо». От «плохо» вытащило только производительность (Hugo и так быстрый, картинки грузятся лениво, шрифты с правильной стратегией загрузки).
Что нашлось:
Контраст вторичного текста проваливал стандарт WCAG AA в обеих
темах. Цвет #6272a4 на светлом фоне #f8f8f2 давал соотношение
контраста 3.92:1, на тёмном #282a36 — 3.33:1. Стандарт WCAG AA
требует минимум 4.5:1 для основного текста. Эта переменная использовалась
одновременно как цвет вторичного текста, как цвет ссылок в светлой
теме и как мета-информация. Поражено больше 40% не-основного контента
сайта.
Страница поиска в светлой теме выдавала белый текст на белом фоне.
В моём CSS заголовки результатов поиска имели цвет #f8f8f2
(захардкожен под тёмную тему). На светлой теме фон тоже #f8f8f2 —
белый на белом. Я этого не замечал, потому что почти всегда сижу в
тёмной теме. Половина посетителей видела пустые результаты поиска
полтора года.
Страница «Обо мне» — типичный SaaS-клон. Шрифт Inter (один из самых заезженных AI-выборов), фон с линейным градиентом, тяжёлая тень под аватаром. Все четыре анти-референса из PRODUCT.md в одном экране.
Кликабельные элементы меньше 44 на 44 пикселей. Кнопка переключения темы — 32–35 пикселей. У ссылок в навигации не было внутренних отступов, кликабельная зона = площадь самого текста. Стандарт WCAG 2.1 рекомендует минимум 44×44 для тача и моторной доступности.
У цитат border-left в 2 пикселя. Эта самая полоска слева у
«цитаты». В философии impeccable любая боковая полоска шире 1
пикселя — отдельный анти-паттерн (типичный «callout-style» из
старых книг по веб-дизайну).
Семь крупных проблем плюс несколько помельче. Чинилось всё в одном проходе: подняли цвет вторичного текста до читаемого, переписали страницу «Обо мне» с нуля без шрифта Inter и градиентов, сделали все статусы reading-секции чувствительными к теме, расширили кликабельные зоны. После — оценка поднялась до 18 из 20.
Без /audit я бы половину этих проблем не нашёл. Особенно поиск в
светлой теме: я не садился в светлую тему вживую неделями.
UX-ревью и кейс с фиктивным компонентом #
Дальше — /critique. Это уже не технический аудит, а ревью на
уровне дизайн-решений: правильно ли устроена главная как точка входа,
не теряется ли пост в ленте, нужен ли архив-по-годам, есть ли узкие
места в навигации.
Команда устроена так, что запускает два независимых ревью
одновременно. Один — отдельный AI-агент с фокусом на
пользовательский опыт; читает исходники и рендеренный HTML.
Второй — программный детектор npx impeccable --json, проверяющий
25 конкретных шаблонных AI-ляпов автоматически. И ключевое: они
не видят выводы друг друга. Это сделано специально — чтобы один
не подтверждал догадки другого.
Я к этому отнёсся скептически. Думал, что изоляция «для красоты».
Оказался неправ.
Отдельный AI-агент за пять минут нашёл вот что: в моей же DESIGN.md, которую я сам написал часом ранее, описан боковой sticky-блок «Содержание» как одна из ключевых деталей сайта. Подробно: фиксированное позиционирование, ширина 260 пикселей, рамка, скругление, размеры ссылок, активное состояние. И сразу следом: «один из главных компонентов сайта; обслуживает чтение длинных постов вторым по важности после самого текста».
А в layouts/_default/single.html (мой собственный шаблон страницы
поста) этого блока нет. Поиск по проекту: ноль вхождений
toc-sidebar, toc-sticky, TableOfContents. Только 190 строк
CSS-стилей, который никем не используется, потому что HTML-разметку
никто не выводит. Документация описывала то, чего на сайте не было.
Что произошло: при первом проходе /document я смотрел в CSS,
увидел проработанный sticky-блок и описал его в DESIGN.md как
рабочий компонент. Не проверил, что в шаблонах кто-то этот класс
выводит. CSS живёт, разметки нет — а я этого не заметил, потому что
неудобно увидеть, что я только что подробно описал то, чего не
существует.
Это та самая «слепая зона», когда видишь в собственной работе только то, что её подтверждает. Я писал код, я писал документацию по этому коду. Свою же работу мне «удобно» считать согласованной.
Отдельный AI-агент в /critique не видел ни моих рассуждений по
команде /document, ни моей DESIGN.md как авторитетного источника.
Он читал её как один из файлов проекта. И тут же подсветил
расхождение: «sticky TOC задокументирован как ключевой элемент,
не рендерится ни на одной странице».
Этот один пункт окупил весь подход с двумя независимыми ревью. Я зашил это в персональную память Claude Code как правило: прежде чем называть компонент ключевым в DESIGN.md, надо проверить, что он действительно рендерится в шаблонах, а не только в стилях. Стилевой блок без HTML-разметки — мёртвый код, не «компонент».
После этого /critique нашёл ещё несколько пунктов помельче:
- листинг прочитанных книг сделан карточной сеткой — это прямой анти-референс из моей же PRODUCT.md;
- три параллельных шаблона шапки и подвала на разных страницах с чуть разным поведением;
- текст страницы «Обо мне» написан в типичном LinkedIn-стиле: «Я исследую пересечения технологий, мышления и практики», «Автор · Инженер · Исследователь» — строго против моего же голоса;
- в публичной копии сайта засветилось имя поискового движка («Pagefind»), хотя пользователю это знать не нужно.
Всё, кроме текста «Обо мне», починили в этом же сеансе. Текст — это переписывание личного голоса, я сделал черновик, но коммитить не стал.
Полировка деталей 🎨 #
После /critique оставшиеся три команды — это работа другого
характера. Не «найди и почини», а «доведи до состояния, в котором
детали перестают раздражать».
Команда /harden («закалка») закрыла прямой пробел: на месте
английской заглушки темы «typo? Click here» теперь нормальная
страница 404 на русском с тремя осмысленными путями. Локализовал
раздел тегов: хлебные крошки теперь говорят «Главная / Теги», а не
«Tags». Расширил поддержку настройки «уменьшить движение» в
операционной системе — теперь обнуляются все плавные переходы, не
только прокрутка. Защитился от очень длинных заголовков (если в
название поста попадёт длинная ссылка без пробелов, сетка не
поедет).
Команда /polish («полировка») добавила состояния «при наведении» и
«при фокусе с клавиатуры» там, где их не было: теги статьи, ссылки
на соцсети в шапке главной, навигация пагинации, ссылки между
постами, кнопка копирования кода. Каждая ссылка теперь визуально
откликается на наведение через смену цвета — без сдвига, без тени,
по принципу «никакой фальшивой глубины» из моей же DESIGN.md.
Команда /typeset (типографика) — самая «невидимая» работа. Включил
кернинг (профессиональная регулировка расстояний между парами букв)
и лигатуры (где две буквы соединяются в один знак — fi, fl).
Включил табличные цифры на датах в ленте: цифры теперь одной ширины
и в столбце выстраиваются штамп-в-штамп. Добавил мягкие переносы
русских слов внутри статьи (без них длинные слова рвали строку
абзаца на узкой колонке). Тонко уплотнил трекинг (межбуквенный
интервал) на крупных заголовках 28-44 пикселя — Literata в больших
размерах без лёгкого негативного трекинга «дребезжит» как
кубики, с ним читается как один жест.
Каждая из тройки — 30-60 минут работы. Вместе они подняли качество с «работает» до «приятно читать».
Что я понял про инструмент #
Импеккейбл работает с локальными файлами, не с задеплоенным сайтом.
Команды читают исходники в репозитории, рендеренный HTML после
локальной сборки Hugo, и оба дизайн-документа. Прода нет ни в одной
команде, кроме /live (интерактивный режим в браузере), которую я
не использовал. То есть весь дизайн-цикл идёт у меня на ноутбуке, и
выкладка в боевой репозиторий — финальный шаг, не источник истины.
AI хорошо ловит противоречия в собственной работе, если ему дать
независимое ревью. Изоляция в /critique нужна не для эстетики
процесса. Самопроверка у языковой модели страдает тем же эффектом
подтверждения собственной правоты, что и у человека: ты видишь в
своей работе то, что её обосновывает, и не видишь того, что её
опровергает. Отдельный AI-агент в новой сессии, без моих рассуждений
в его контексте, читал DESIGN.md как просто один из файлов и тут
же поймал расхождение с шаблонами.
Анти-референсы выстреливают сильнее, чем референсы. «Не как Habr» — конкретный отказ, проверяемый автоматически. «Как Stripe» — растяжимое, можно подогнать любой результат. PRODUCT.md заставляет выписать четыре-пять анти-референсов, и каждое решение проверяется против них.
Метрики важнее ощущений. /audit дал 11 из 20. Это конкретное
число. После правок — 19. Я знаю, на сколько лучше. Бессчётный
«прогресс» — самообман: правишь, правишь, чувствуешь, что лучше. С
оценкой видно, что иногда нет.
Убывающая отдача наступает быстро. После пяти проходов половина
команд impeccable стали неуместными для моего блога. /animate,
/delight, /bolder, /overdrive — прямо конфликтуют с принципом
«без подкупа» из PRODUCT.md. /quieter, /distill — сайт уже
плоский и сдержанный, дальше пустая страница. /colorize — палитра
закрыта на 13 цветах. /optimize — Hugo уже выжат до предела.
Это знак, что инструмент сделал работу. Дальше — пиши посты, не правь дизайн.
Где AI ошибся, а где я #
За эту сессию я дважды слишком уверенно объявил причину явления на основании одного наблюдения. Это вообще частая ошибка и в инженерии, и в науке: одна точка наблюдений — не закономерность, это просто точка.
Первый случай. Один сборочный билд занял 9 минут вместо обычных 40-50 секунд. Я уверенно сказал: причина — что я только что добавил в подвал отметку реального времени сборки. Каждая страница теперь содержит уникальный текст в подвале, значит, утилита синхронизации (rsync) с проверкой по контрольной сумме перезаливает все 227 страниц целиком. Технически красивое объяснение, инженерно стройное. И неверное.
Следующий билд с той же отметкой времени занял 40 секунд. То есть 9-минутный билд был случайным выбросом — холодный старт исполнителя, сетевой сбой, что-то сторонне. Я экстраполировал из одной точки и готов был «починить» проблему, которой нет.
Второй случай. Я случайно удалил пустой файл content/posts/.md
(артефакт от прошлой попытки автоматического создания поста с битым
именем) после того, как назвал его «пустой стуб». Не прочитал
содержимое перед удалением. Файл был не пустой — 101 байт. После
удаления выяснилось, что в нём всё-таки лежал какой-то фронтматтер
(служебный заголовок поста с метаданными), которого я не увидел до
действия.
Оба случая зашиты в персональную память:
- Перед удалением читать каждый файл. Не отслеживается ли git — не значит «можно выкинуть».
- Прежде чем уверенно объявлять причину явления — собрать минимум две сравнимых точки. Один выброс ≠ закономерность.
Особенно полезно для вопросов производительности, где «фикс несуществующей проблемы» — это напрасные телодвижения и потеря доверия к собственным выводам.
Когда импеккейбл не нужен #
- На бренде, который требует «как у всех»: внутренний инструмент, служебная панель, прототип без идентичности.
- Когда нет 30-60 минут на интервью
/teachи сборку DESIGN.md. Без фундамента остальные команды дают ответы вообще, не для тебя. - На короткой одностраничной странице — обычная ручная работа быстрее.
- Когда дизайн уже отлажен и работает — повторное прохождение часто стоит дороже того, что находит.
Конкретные числа #
| Метрика | До | После |
|---|---|---|
| Технический аудит (баллы) | 11/20 | 19/20 |
| UX-ревью (баллы по 10 эвристикам Нильсена) | 24/40 | ~32/40 |
| Цвет фейлит стандарт WCAG AA | 7 случаев | 0 |
| Параллельных дизайн-систем | 2 (основная + SaaS на «Обо мне») | 1 |
| Захардкоженных шестнадцатеричных цветов вне токенов | 23+ | 0 |
| Кликабельные зоны меньше 44×44 | 5 | 0 |
| Шрифт-ошибка (отсутствующий шрифт первым в стеке) | да | нет |
| Боковой блок «Содержание» — задокументирован vs реально рендерится | 0 страниц | все длинные посты |
| Кастомная страница 404 | нет | есть, по-русски |
| Поддержка настройки «уменьшить движение» | частичная | полная |
Итог #
Импеккейбл не делает дизайн за тебя. Он даёт инструмент, через
который вы вместе с AI доводите дизайн до состояния, в котором вы
оба перестаёте делать стандартные ошибки. Аудиторская часть
(/audit, /critique) ловит сразу видимое. Доводочная часть
(/harden, /polish, /typeset) делает то, что в одиночку лень
довести до конца.
Стоимость: один вечер плюс умение зафиксировать собственный голос в PRODUCT.md и DESIGN.md. Срок отдачи: пока продолжаешь редактировать сайт. Каждое следующее обращение к AI («поправь шапку», «добавь страницу архива», «перепиши блок») идёт на фоне этих двух файлов, и шансы получить очередной AI-look уменьшаются.
Скрытая ценность инструмента в том, что он заставляет писать честно о собственном проекте. Анти-референсы зашиты в PRODUCT.md и зачитываются перед каждой правкой. Это ровно та дисциплина, которую я никогда не наводил руками.