7 шагов, 6 запретов и один валидатор: разбираю /dataviz в Claude Code

от автора

В начале июля в Claude Code появился встроенный скилл /dataviz. Я скормил ему датасет с рангами американских детских имён за 76 лет и один промпт. На выходе получил интерактивную страницу: график сам выбрал форму, палитра прошла математическую проверку, а наезжающие подписи модель нашла и починила без моего участия. Страница живая, можно потрогать: inforobot.space/dataviz/baby‑names. В этой статье разберу, как скилл устроен изнутри: какие решения он жёстко запрещает, что именно проверяет валидатор палитры и где заканчивается его компетенция.

Что внутри и что унесёшь: процедура /dataviz из семи шагов и почему цвет в ней выбирается последним; шесть запретов, которые скилл не даёт нарушить; что считает validate_palette.js — OKLCH, цветовая слепота, WCAG — с цифрами реального прогона; какие решения модель приняла сама и как обосновала; одна ошибка модели в данных и вывод, какую часть работы делегировать нельзя.

Что такое /dataviz

Скилл появился в Claude Code v2.1.198 первого июля 2026 года. Он встроенный: идёт вместе с CLI, ставить ничего не нужно. Официальный changelog описывает его одной строкой:

chart and dashboard design guidance with a runnable color-palette validator

За этой строкой скрывается любопытная конструкция. Если заглянуть внутрь (скиллы в Claude Code — это обычные папки с файлами), увидишь три слоя:

  • SKILL.md — процедура из семи шагов в жёстком порядке: от анализа данных до финального рендера. Модель обязана пройти их последовательно.

  • Reference‑файлы — справочники по формам графиков, палитрам и типографике, которые модель подгружает по мере надобности.

  • scripts/validate_palette.js — исполняемый скрипт. Ключевое слово — исполняемый: модель может проверить собственный выбор цветов кодом и получить объективный вердикт.

Первый шаг процедуры — определить «работу данных»: что читатель должен сделать с графиком. Вариантов пять: magnitude (сравнить величины), identity (различить и проследить сущности), polarity (увидеть отклонение от нуля или нормы), headline (считать одно число), change‑over‑time (увидеть динамику). Отдельно оговорено: иногда правильный ответ — вообще без графика, одна крупная цифра, stat tile.

А цвет в процедуре идёт последним из дизайн‑решений — после него остаётся только рендер. Формулировка из SKILL.md прямая:

Most bad charts pick colors first

Опытный аналитик и так начинает с данных: что с чем сравнивать, что показывать. Но генераторы графиков и работа в спешке устроены иначе — первым делом выбирается «красивая палитра», а вопрос, зачем график существует, откладывается на потом. Скилл фиксирует правильный порядок жёстко: сначала работа данных и форма, цвет — в самом конце.

Эксперимент: 76 лет детских имён и один промпт

Для теста я взял датасет popular‑baby‑names (MIT): топ-1000 американских имён по годам с 1880 по 2025, данные SSA. Датасет специально неудобный: в файлах только две колонки, Rank и Name. Чисел рождений нет. То есть построить столбики «сколько девочек назвали Olivia» физически невозможно — есть только порядок.

Промпт был один:

/dataviz данные в папках по годам, girl_names_YYYY.csv, колонки Rank и Name(только ранг, чисел нет). Покажи, как менялся ранг топ-5 женских имён2025 года на дистанции 1950–2025. Объясни, почему выбрал такую формуграфика и такие цвета

Дальше я только смотрел. Вот решения, которые модель приняла сама, с её обоснованиями из сессии.

Форма: rank‑trajectory, многолинейный график. Модель определила работу данных как identity плюс change‑over‑time: пять сущностей, которые нужно различить и проследить во времени. Её аргумент против столбиков:

Данные — ранг во времени, без чисел рождений. Ранг — это порядок, а не величина: складывать и сравнивать «площади» нечего.

Ось ранга перевёрнута: первое место наверху. Чтобы «выше на графике» означало «популярнее» без умственного пересчёта «меньше = лучше».

Шкала ранга логарифмическая. Это решение мне понравилось больше всего. Вся драма датасета — борьба внутри топ-15 в 2000–2020-х. На линейной шкале от 1 до 900 эти пересечения схлопнулись бы в тонкую полоску у верхней кромки. Лог‑шкала даёт каждому порядку величины равное место: путь Sophia с 848-го места и толкотня в пятёрке лидеров читаются одинаково хорошо.

Прямые подписи вместо легенды. Имя стоит у конца своей линии. Читателю не нужно бегать глазами по маршруту «цвет → легенда → имя».

Сами данные того стоили. Ранги пяти имён (сверил вручную с сырыми CSV):

ИМЯ

1950

1970

1990

2010

2025

Olivia

275

542

72

4

1

Charlotte

80

166

287

46

2

Emma

154

422

130

3

3

Amelia

357

445

194

41

4

Sophia

848

403

251

2

5

Все пять имён в середине века болтались в третьей‑восьмой сотне, а в 2025 году заняли места с первого по пятое подряд. Sophia прошла путь с 848-го места. История «возвращения классики» читается на графике сразу — линии взбираются из нижне‑левого угла к вершине.

десктоп‑версия графика

десктоп‑версия графика

Цвет: единственное решение, которое проверяется кодом

Теперь главная часть. Reference‑файлы скилла содержат набор правил, которые я бы назвал non‑negotiables — модель не имеет права их нарушать:

  • Никогда dual‑axis. Две оси Y с разными шкалами на одном графике скилл называет the #1 chart mistake. Причина: шкалы двух осей никак не связаны между собой, и их выбор — произвол автора. Растяни правую ось вдвое — линии «пересекутся» в другом месте, сожми — «совпадут»; данные те же, а история на графике другая. Читатель видит убедительную картинку и не видит, что её нарисовал выбор шкал. Тот же смысл честно передают два графика друг под другом с общей осью X.

  • Цвета берутся из пронумерованного списка, по порядку. В скилле лежит готовая палитра, где цвета стоят в определённой последовательности — «слотах»: слот 1 — синий, слот 2 — бирюзовый и дальше. Первая серия данных всегда получает цвет из слота 1, вторая — из слота 2, без перестановок. Смысл в том, что соседние цвета списка заранее подобраны различимыми — по светлоте и при дальтонизме. Начни выдёргивать цвета «по вкусу» — эти гарантии рассыпаются.

  • Не больше восьми цветов на графике. Если категорий больше восьми, всё лишнее объединяется в одну серую группу «Other». Девять и более цветов на одном графике читатель уже надёжно не различает.

  • Sequential‑палитра — один оттенок от светлого к тёмному. Для упорядоченных величин вроде «мало → много».

  • Diverging — два оттенка с серым центром. Для отклонений от нормы в обе стороны.

  • Никогда rainbow. Радужная палитра навязывает категориальное прочтение данным, у которых есть порядок.

Но правила в текстовом файле — это пожелания: модель может их прочитать и всё равно сделать по‑своему. Интересное начинается с validate_palette.js. Прежде чем использовать палитру, модель обязана прогнать её через скрипт, и тот считает четыре вещи:

  1. Lightness band в OKLCH. Светлота каждого цвета должна попадать в коридор: для светлой темы L от 0.43 до 0.77. Слишком светлый цвет утонет в фоне, слишком тёмный сольётся с текстом.

  2. Chroma floor. Chroma в OKLCH — это «сколько цвета в цвете»: у чистого серого она равна нулю, у кислотного оттенка высокая. Валидатор требует не меньше 0.1: более блеклый цвет на графике неотличим от серой сетки и от соседних таких же блеклых линий.

  3. Различимость при цветовой слепоте. Палитра прогоняется через матрицы симуляции Machado 2009 для трёх типов дальтонизма: протанопия, дейтеранопия, тританопия. Считается ΔE между соседними сериями (или всеми парами с флагом --pairs all).

  4. WCAG‑контраст против поверхности. Каждый цвет проверяется на контраст с фоном.

Отдельная умная деталь связана с пограничными случаями. ΔE — это числовая мера различия двух цветов: ноль — цвета одинаковые, чем больше число, тем легче их различить. Диапазон 8–12 после симуляции дальтонизма — серая зона: вроде разные, но полагаться на это нельзя. Такие пары валидатор пропускает с одним условием — цвет не единственный способ опознать линию. Если у линии есть подпись с именем, зазор или текстура, то читатель, который эти два цвета не различает, всё равно поймёт, где какая: он просто прочитает имя. В документации скилла это называется secondary encoding.

Для моего графика модель взяла пять слотов категориальной палитры скилла в фиксированном порядке: Olivia #2a78d6, Charlotte #1baf7a, Emma #eda100, Amelia #008300, Sophia #4a3aa7, поверхность #fcfcfb. Прогон валидатора:

  • PASS по lightness band, chroma floor и CVD‑разделению соседних пар; худшая пара при протанопии — #008300 против #eda100, ΔE 24.2, с запасом.

  • WARN по WCAG‑контрасту: бирюза #1baf7a даёт 2.74, жёлтый #eda100 — 2.11 при пороге 3:1. Порог — минимальный контраст графического элемента с фоном, обе линии до него не дотянули: на светлом фоне они бледнее нормы. Это предупреждение среднего уровня: до FAIL не дотягивает, потому что у каждой линии есть подпись и строка в таблице — линию можно опознать без цвета. Без этой компенсации палитру пришлось бы менять.

WARN закрылся той самой relief rule: у каждой линии есть прямая подпись, легенда и строка в таблице, поэтому ни одно имя не опознаётся только по цвету. Модель отдельно проговорила это в сессии — и текст подписей сделала чернильным, без цветовой кодировки.

терминал с выводом валидатора

терминал с выводом валидатора

Шаг седьмой: отрендери и посмотри глазами

Последний шаг процедуры сформулирован в духе «render and look at it before shipping». Валидатор проверяет только цвет. Геометрию, коллизии подписей и переполнения контейнеров никакой скрипт не считает — модель обязана открыть результат в браузере и посмотреть.

И этот шаг реально сработал. При первом рендере модель заметила, что подписи у рангов со второго по пятый наезжают друг на друга (в 2025 году все пять линий сходятся в одну точку топа — подписям физически тесно), переформатировала их в однострочные и увеличила минимальный зазор. Меня в этой петле не было.

Дальше — без отдельной просьбы в исходном промпте, но по моему уточнению «нужны веб и мобильная версии» — модель собрала адаптив: на узком экране прямые подписи заменяются легендой в столбик и точками на концах линий, тики оси прореживаются до [1, 10, 100, 900], подпись оси годов убирается совсем. И тёмную тему: для неё палитра пересчитана в отдельные тёмные шаги тех же оттенков, без механической инверсии, — и прогнана через валидатор ещё раз.

Финальный артефакт — standalone HTML на 28 КБ: весь CSS, JS и данные за 76 лет зашиты инлайн, ноль внешних запросов, страница работает без интернета.

Одна деталь из сессии отдельно порадовала меня как история про агентное поведение. Для OG‑превью нужен был PNG 1200×630. Скриншот‑тул браузерного расширения отдавал только мыльный JPEG ограниченного разрешения. Модель зашла с другой стороны: собрала превью как вектор 1200×630 прямо в странице, растеризовала через canvas в PNG, а когда выяснилось, что папка загрузок браузера недоступна из песочницы — подняла локальный POST‑сервер и отправила файл туда из браузера по base64. Чёткий PNG ровно 1200×630, полученный обходом трёх ограничений подряд.

Где заканчивается компетенция скилла

Теперь честная часть. У /dataviz есть граница, и она проходит в точном месте: из всех решений механически проверяется только цвет.

Смотри на асимметрию. Выбор палитры замкнут в петлю самопроверки: модель выбирает цвета → скрипт считает OKLCH, ΔE и контраст → модель видит вердикт → правит. Объективная математика на каждой итерации. А выбор формы графика — перевёрнутая лог‑ось, rank‑trajectory, прямые подписи — это эвристика модели в контексте. Все эти решения в моём прогоне оказались удачными, но проверить их было некому, кроме меня.

И модель действительно ошиблась — там, где валидатор её не страховал. В конце сессии она добавила примечание: SSA считает Sophia и Sofia разными именами, и Sofia в рейтинге стоит выше. Первая половина — правда, написания в данных действительно раздельные. Вторая — ошибка. Открываю CSV за 2025 год: Sophia на 5-м месте, Sofia на 9-м. Выше стоит Sophia.

Важно: сам график при этом чистый. Я выборочно сверил его точки с исходными CSV — например, 1996 год: Olivia № 34, Charlotte № 301, всё сходится. Модель не выдумала данные. Она выдумала вывод о данных — одну фразу, которую никакой скрипт не проверял.

Из этой асимметрии следует практический вывод, который переносится далеко за пределы /dataviz. Там, где у инструмента есть петля самопроверки, делегировать можно спокойно: ошибка будет поймана до тебя. Там, где решение принимается эвристикой — выбор формы, интерпретация данных, словесные выводы, — твоё суждение остаётся последним рубежом. /dataviz устроен ровно по этой границе: цвет он проверяет кодом, а форму выбирает «по опыту» и сам об этом честно предупреждает седьмым шагом «посмотри глазами».

Поэтому моя позиция: /dataviz — инструмент прототипирования. За один промпт и пару уточнений он выдаёт прототип уровня, на который вручную ушло бы несколько часов: с обоснованным выбором формы, провалидированной палитрой, адаптивом и тёмной темой. Но подпись под результатом ставит пользователь — тот, кто проверил форму, данные и выводы там, где скрипта нет.

Что в итоге

Если хочется потрогать руками: обнови Claude Code до актуальной версии, набери /dataviz и дай ему свои данные — интереснее всего скармливать неудобные датасеты, где «очевидный» график невозможен. Живой результат моего прогона — inforobot.space/dataviz/baby‑names, исходный датасет — popular‑baby‑names.


Про эксперименты с агентами, скиллами и Claude Code я регулярно пишу в телеграм‑канале «Я и мой друг робот» — там был короткий анонс этого эксперимента, а следующий прогон /dataviz уже лежит в черновиках.

ссылка на оригинал статьи https://habr.com/ru/articles/1058312/