Перейти к содержанию

data-атрибут

Определение

Data-атрибут – HTML-атрибут с префиксом data-*, валидный способ хранить произвольные данные в разметке любого элемента. В JavaScript доступен через element.dataset, в CSS – через селекторы [data-...] и функцию attr().

4 мин 41 Обновлено 12 августа

По стандарту HTML любой атрибут, имя которого начинается с префикса data-, валиден на любом элементе. Это официальный ответ на давнюю потребность разработчиков: положить рядом с элементом служебную информацию – идентификатор, состояние, настройку компонента, – не изобретая нестандартные атрибуты и не пряча данные в имена классов. Браузер такие атрибуты не отображает и никак не интерпретирует: они существуют для скриптов, стилей и автотестов. В отличие от атрибутов ARIA, которые описывают элемент для вспомогательных технологий, data-* – канал «для себя»: разработчик сам решает, что и зачем там хранить.

Как это работает

Имя после префикса пишут в kebab-case: латиница в нижнем регистре, цифры, дефисы – data-user-id, data-index-number. Стандарт допускает также точку, двоеточие и подчёркивание, но на практике держатся kebab-case: именно дефис участвует в преобразовании имени для JavaScript. В JavaScript такие атрибуты доступны через свойство element.dataset – объект DOMStringMap, в котором префикс data- отброшен, а дефисы превращены в camelCase: data-index-number читается как dataset.indexNumber. Преобразование работает в обе стороны: запись el.dataset.someDataAttr = "x" создаёт в разметке атрибут data-some-data-attr="x", причём dataset и HTML синхронны – изменение одного сразу видно в другом.

<article id="post" data-columns="3" data-index-number="12314">...</article>
const article = document.querySelector("#post");

article.dataset.columns;      // "3" – всегда строка
article.dataset.indexNumber;  // "12314" (data-index-number → indexNumber)

article.dataset.columns = 5;  // запишет data-columns="5"
delete article.dataset.indexNumber; // удалит атрибут из HTML

Три правила, о которые спотыкаются чаще всего:

  • Значения – всегда строки. Число 42 станет строкой "42", null – строкой "null". Числа приводят через Number(), сложные структуры хранят как JSON-строку и разбирают через JSON.parse.
  • Проверка наличия – через 'columns' in el.dataset или сравнение с undefined: отсутствующий атрибут не бросает ошибку, а просто возвращает undefined.
  • Поиск по атрибутуdocument.querySelectorAll('[data-columns]') находит все элементы с таким атрибутом, а '[data-columns="3"]' – только с конкретным значением.

getAttribute и dataset – в чём разница

Сравнение dataset и getAttribute
Критерийelement.datasetgetAttribute / setAttribute
ИмяcamelCase без префикса: dataset.userIdКак в разметке: getAttribute("data-user-id")
ДоступОбъектный: чтение, запись, deleteТри отдельных метода: get, set, removeAttribute
Область примененияТолько data-атрибутыЛюбые атрибуты элемента
Когда выбиратьОсновная работа с data-*: читаемее и корочеИмена без преобразований, универсальный код

Для единичных обращений разница в производительности на практике не имеет значения – выбирают по читаемости кода.

Зачем это нужно

  • JS-хуки – скрипт находит элементы по data-атрибуту, а не по классу: классы остаются стилям, и правка вёрстки не ломает JavaScript. Отдельный случай – хуки для автотестов вида data-testid.
  • Параметры для обработчиков – при делегировании событий один слушатель на контейнере читает из dataset кликнутого элемента, с каким объектом работать: data-user-id="42" вместо отдельного обработчика на каждую кнопку.
  • Состояния и варианты для CSS – селекторы атрибутов вида [data-variant="warning"] заменяют россыпь модификаторов-классов, а content: attr(data-tooltip) выводит значение атрибута в псевдоэлементе – так делают чистые CSS-тултипы.
  • Мост между JS и CSS – например, скрипт определяет тёмную тему через window.matchMedia() и записывает результат в data-атрибут на корневом элементе, а стили реагируют селектором по этому атрибуту.

Когда data-атрибуты не подходят

Data-* – канал для служебных, а не смысловых данных. Скринридеры и другие вспомогательные технологии могут не иметь доступа к значениям data-атрибутов, поэтому видимый или важный по смыслу контент должен лежать в обычной разметке – это базовое правило доступности. Для описания элементов ассистивным технологиям есть отдельные атрибуты, например aria-label. Поисковые краулеры тоже могут не индексировать значения data-атрибутов – контент, который должен попасть в поиск, в них прятать нельзя. Наконец, data-атрибуты – не база данных: большие и сложные структуры держат в состоянии приложения или получают с сервера, а в разметке оставляют только ключи и короткие параметры.

Пример

Классика делегирования: список пользователей, у каждого кнопка «Открыть». Вместо обработчика на каждую кнопку – один на документе, а параметры лежат в разметке:

<button data-user-id="42">Открыть</button>
<button data-user-id="43">Открыть</button>
document.addEventListener("click", (e) => {
  const btn = e.target.closest("[data-user-id]");
  if (btn) {
    openUser(Number(btn.dataset.userId)); // dataset вернёт строку "42"
  }
});

CSS-часть – вариант оформления и тултип из атрибута:

.callout[data-variant="warning"] {
  border-color: rgb(235 15 15); /* значение селектора – в кавычках, даже число */
}

.hint::after {
  content: attr(data-tooltip);
}

На Битрикс-проектах data-атрибуты – основной способ передать данные из PHP-шаблона компонента в JavaScript: идентификаторы элементов инфоблока, параметры для целей Метрики, настройки слайдеров. Шаблон выводит атрибуты в вёрстку, скрипт читает dataset – без глобальных переменных и инлайн-скриптов на каждый элемент. Такой код переживает редизайн: пока имена data-атрибутов на месте, JS-логика не зависит от классов и структуры вёрстки, и правки дизайнера не превращаются в тикеты про сломанные скрипты.

Частые вопросы

Чем data-атрибуты отличаются от просто выдуманных атрибутов?

По стандарту HTML на любом элементе валидны только пользовательские атрибуты с префиксом data-. Атрибут с произвольным именем без префикса – нестандартная разметка: браузер её обычно переживёт, но валидатор укажет ошибку. Префикс data- гарантирует, что имя не столкнётся со стандартными атрибутами HTML.

Как прочитать data-атрибут в JavaScript?

Через element.dataset: атрибут data-index-number доступен как dataset.indexNumber – префикс отбрасывается, дефисы превращаются в camelCase. Альтернатива – element.getAttribute('data-index-number'), где имя пишется точно как в разметке.

Почему data-index-number читается как dataset.indexNumber?

dataset – объект DOMStringMap, который отображает имена по правилу: префикс data- отбрасывается, а каждая пара «дефис + строчная буква» превращается в заглавную букву (camelCase). При записи преобразование обратное: dataset.userId = '42' создаст в HTML атрибут data-user-id='42'.

Можно ли хранить в data-атрибуте число или объект?

Значение атрибута – всегда строка: число 42 при чтении вернётся как строка '42', null – как строка 'null'. Числа приводят через Number() или parseInt(), а объекты и массивы кладут в атрибут JSON-строкой и разбирают через JSON.parse. Для больших структур данных data-атрибуты не подходят.

Что лучше – dataset или getAttribute?

dataset удобнее при работе именно с data-атрибутами: объектный доступ, автоматический camelCase, удаление через delete. getAttribute универсален – работает с любыми атрибутами и не преобразует имена. Для единичных обращений разницы в производительности на практике нет, выбирают по читаемости кода.

Можно ли использовать data-атрибуты в CSS?

Да, двумя способами. Селекторы атрибутов вида [data-variant='warning'] стилизуют элемент по значению, причём значение пишется в кавычках даже для чисел. Функция attr() выводит значение в псевдоэлементе: content: attr(data-tooltip) – так делают чистые CSS-тултипы без JavaScript.

Когда data-атрибуты использовать нельзя?

Для видимого и смыслового контента: скринридеры могут не иметь доступа к значениям data-атрибутов, а поисковые краулеры – не индексировать их. Такие данные должны лежать в обычной разметке или в aria-атрибутах. Также data-атрибуты не подходят для больших объёмов и сложных структур данных – это не база данных.

Связанные термины

a11y (веб-доступность) a11y – нумероним слова accessibility: между «a» и «y» стоит 11 букв. Обозначает веб-доступность – проектирование сайтов, пригодных для людей с ограничениями зрения, слуха, моторики и когнитивных функций. Главный стандарт – WCAG. ARIA ARIA (WAI-ARIA, Accessible Rich Internet Applications) – стандарт W3C: атрибуты role и aria-*, передающие вспомогательным технологиям роль, свойства и состояния элементов интерфейса. Актуальная версия – 1.2 (2023). window.matchMedia() window.matchMedia() – метод JavaScript, который проверяет, соответствует ли документ CSS-медиазапросу. Возвращает MediaQueryList со свойством matches и событием change для слежения за брейкпоинтами и темой ОС. Делегирование событий Приём в JavaScript, когда один обработчик вешается на контейнер и ловит события от всех потомков через всплытие, определяя цель методом event.target.closest(). Псевдоэлемент ::before ::before – CSS-псевдоэлемент, который создаёт «виртуального» первого ребёнка элемента и вставляет в него сгенерированный контент через обязательное свойство content. Без content не отображается; на img и input не работает.

Материалы по теме

Что почитать дальше по этой теме

Статья Что боты находят на сайте, а вы – нет Боты ходят по изнанке сайта, куда живой человек не забредёт, и фиксируют в логах то, чего не видно ни в Метрике, ни на витрине: падающие с ошибкой 500 страницы каталога, битый файл с 747 обращениями, поток сканеров секретов. Разбираю на реальных логах, что искать и как чинить. 7 мин 216 22 июля 2026 Инструкция Как выгрузить и читать access-логи, если хостинг хранит их три дня Access-лог – единственное место, где виден весь трафик сайта, включая ИИ-ботов, которых не замечают счётчики. Разбираю на практике: где взять логи, как не потерять их из-за ротации, какие команды показывают ботов, ошибки и подозрительную активность. 7 мин 170 21 июля 2026 Флагманский гайд AI-анализ email-обращений: методика на стыке Яндекс.Метрики и Claude Code Классический email-трекинг отвечает на вопрос «откуда пришло обращение». AI-слой отвечает на вопросы, которые раньше требовали ручного аналитика: значим ли email на фоне звонков, форм и мессенджеров, почему один источник даёт качественные обращения, а другой – пустые, какие сегменты визитов предшествуют письму, что написать в ответ с учётом пути пользователя. Здесь – как я собираю это на уже имеющемся стеке: Logs API Метрики, PostgreSQL и Claude Code, без новых платных сервисов. 11 мин 297 26 мая 2026 Флагманский гайд Майкор: ИИ-аудит проекта по 4 точкам контакта Майкор – это перекрёстный ИИ-аудит проекта в 4 точках контакта: сайт, контекстная реклама, AI-поиск и Яндекс.Карты. Я анализирую каждую систему и смотрю связки между ними – где маркетинг рассказывает одно, реклама ведёт на другое, а AI-системы цитируют третий номер телефона. В одном из моих аудитов медицинской клиники в Москве у организации в индексе AI-сервисов оказалось 6 разных номеров и всего 7 упоминаний на 64 проверочных запроса – при том, что в обычной выдаче Яндекса клиника была в топ-1. Майкор закрывает такие разрывы за один аудит вместо четырёх раздельных. 16 мин 501 13 мая 2026 Гайд FAQPage Schema: как разметить блок частых вопросов и попасть в AI-ответы FAQPage schema – один из самых эффективных типов разметки для попадания в AI-ответы. Страницы с FAQPage schema цитируются AI-поисковиками в 2,7 раза чаще. В этом гайде – формат разметки, правила написания ответов для AI, реализация на 1С-Битрикс и типичные ошибки, которые обнуляют эффект. 8 мин 331 25 апреля 2026