W3docs

Атрибуты и свойства

Разница между HTML-атрибутами и DOM-свойствами в JavaScript: getAttribute, setAttribute, hasAttribute, removeAttribute, синхронизация value/href, boolean-атрибуты и data-* через dataset.

Чтобы в совершенстве владеть JavaScript, необходимо понимать, как он взаимодействует с объектной моделью документа (DOM). В этом руководстве рассматриваются атрибуты и свойства DOM: как их читать, изменять и синхронизировать для динамического управления веб-страницами.

Введение в DOM в JavaScript

DOM представляет веб-страницу в виде иерархического дерева объектов, позволяя языкам программирования, таким как JavaScript, взаимодействовать с содержимым, стилями и структурой страницы. Каждый элемент HTML-документа отражён в DOM в виде объекта, и у этих объектов есть свойства и атрибуты, которыми можно управлять с помощью JavaScript.

Различия между атрибутами и свойствами

Несмотря на то что термины «атрибуты» и «свойства» нередко используются как синонимы, в контексте DOM они имеют разные значения:

  • Атрибуты: определяются в HTML-коде и предоставляют дополнительную информацию об HTML-элементах. Атрибуты всегда являются string-значениями; доступ к ним осуществляется с помощью таких методов, как getAttribute() и setAttribute().
  • Свойства: характеристики DOM-объектов, представляющих HTML-элементы. Свойства могут быть любого типа данных — boolean, string, число — и доступны напрямую через точечную нотацию.

Если кратко: атрибут — это то, что вы написали в HTML-источнике; свойство — это то, во что браузер разобрал этот атрибут и что представляет на JavaScript-объекте. Для простых случаев вроде id они выглядят одинаково, но это две разные вещи.

Примечание о синхронизации: для большинства стандартных атрибутов (например, id, class) изменение атрибута обновляет соответствующее свойство и наоборот. Однако такая синхронизация не гарантирована везде, и некоторые важные атрибуты намеренно её нарушают (см. Когда синхронизация нарушается ниже).

Пример кода: доступ к атрибутам и свойствам

<!-- snippet: html-result -->

<div id="demo" class="sample" data-level="1">Hello, World!</div>
<br />
<div>first getAttributes result (data-level): <span id="1"></span></div>
<div>className property: <span id="2"></span></div>
<script>
  const demoElement = document.getElementById("demo");
  const span1 = document.getElementById("1");
  const span2 = document.getElementById("2");

  // Accessing an attribute
  let classAttribute = demoElement.getAttribute("data-level");  // Output: "1"
  span1.innerHTML = classAttribute;
  
  // Accessing a property
  // Note: 'class' is a reserved keyword in JS, so the property is named 'className'
  const classNameProperty = demoElement.className;  // Output: "sample"
  span2.innerHTML = classNameProperty;
</script>

Методы работы с атрибутами

Каждый элемент предоставляет четыре стандартных метода для работы с атрибутами по имени. Они всегда оперируют string-значениями и напрямую соответствуют HTML-источнику:

МетодЧто делает
elem.getAttribute(name)Возвращает значение атрибута в виде string или null, если атрибут отсутствует
elem.setAttribute(name, value)Добавляет атрибут или перезаписывает его значение
elem.hasAttribute(name)Возвращает boolean: существует ли атрибут?
elem.removeAttribute(name)Удаляет атрибут полностью

Имена атрибутов нечувствительны к регистру (id и ID — одно и то же), а каждое значение считывается как string, даже если оно выглядит как число.

Установка атрибутов

Используйте метод setAttribute(), чтобы добавить новый атрибут или изменить значение существующего атрибута HTML-элемента.

Пример кода: установка атрибутов

<!-- snippet: html-result -->

<div id="demo" class="sample">Hello, World!</div>
<br />
<div>className property after change: <span id="span1"></span></div>
<script>
  const demoElement = document.getElementById("demo");
  const span1 = document.getElementById("span1");
  
  // Changing the attribute
  demoElement.setAttribute("class", "changed");
  // The property updates automatically due to attribute-property synchronization
  span1.innerHTML = demoElement.className;
</script>

Этот фрагмент кода изменяет атрибут class элемента div на значение «changed».

Удаление атрибутов

Чтобы полностью удалить атрибут из HTML-элемента, используйте метод removeAttribute(). Это полезно, когда нужно лишить элемент определённого поведения или стиля, заданного атрибутом.

Комбинируйте его с hasAttribute() для условного выполнения:

if (demoElement.hasAttribute("disabled")) {
  demoElement.removeAttribute("disabled");
}

Переназначение свойств

Свойства DOM-элементов можно легко переназначить напрямую с помощью точечной нотации, что обеспечивает более гибкое управление характеристиками элемента.

Пример кода: изменение свойств

<!-- snippet: html-result -->

<div id="demo" class="sample">Hello, World!</div>
<br />
<div>className property after change: <span id="span1"></span></div>
<script>
  const demoElement = document.getElementById("demo");
  const span1 = document.getElementById("span1");

  // Changing the property
  // Note: 'class' is a reserved keyword in JS, so the property is named 'className'
  demoElement.className = "changed";
  span1.innerHTML = demoElement.className;
</script>

В этом примере изменяется свойство className элемента div, что демонстрирует, как свойства можно использовать для динамического управления характеристиками элемента.

Когда синхронизация атрибута и свойства нарушается

У удобного взаимного отображения есть исключения, которые необходимо знать — иначе можно потратить часы на отладку.

Свойство value у полей ввода

Атрибут value хранит начальное (исходное) значение из HTML. Свойство value хранит текущее значение, которое вводит пользователь. После того как пользователь редактирует поле, они расходятся: свойство меняется, атрибут — нет.

// <input id="name" value="initial">
const input = document.getElementById("name");
// user types "Alice" into the field...

input.getAttribute("value"); // "initial"  — still the HTML default
input.value;                 // "Alice"     — the live, current value

То же самое применимо к <input type="checkbox">: атрибут checked — это начальное состояние, свойство checked — то, отмечен ли элемент прямо сейчас.

Свойство href у ссылок

Для элемента <a href="/page"> метод getAttribute("href") возвращает именно то, что вы написали ("/page"), тогда как свойство href возвращает полностью разрешённый абсолютный URL ("https://example.com/page").

// <a id="link" href="/page">
const link = document.getElementById("link");
link.getAttribute("href"); // "/page"
link.href;                 // "https://example.com/page"

Практическое правило: используйте методы атрибута, когда вам нужно исходное значение точно в том виде, в каком оно написано; используйте свойство, когда нужно живое разобранное значение от браузера.

Boolean-атрибуты

Некоторые HTML-атрибуты — disabled, checked, required, readonly, selected — являются boolean: само их наличие означает true, независимо от значения. disabled="" и disabled="false" оба отключают элемент.

В JavaScript соответствующее свойство является настоящим boolean-значением, что удобнее для переключения:

button.disabled = true;   // adds the attribute, disables the button
button.disabled = false;  // removes the attribute, enables it

Избегайте setAttribute("disabled", false) — поскольку атрибут присутствует, элемент остаётся отключённым. Вместо этого устанавливайте свойство.

Пользовательские атрибуты данных

Разработчики могут определять пользовательские атрибуты с префиксом data- — это стандартный, ориентированный на будущее способ прикрепить дополнительную информацию к элементу, не изобретая нестандартных атрибутов. Для чтения и записи они используют свойство dataset вместо getAttribute.

При именовании происходит преобразование из kebab-case в HTML в camelCase в JavaScript: data-author становится dataset.author, а data-order-statusdataset.orderStatus. Можно также записывать значения в dataset, чтобы создавать или обновлять соответствующий data-* атрибут.

Пример кода: пользовательские атрибуты данных

<!-- snippet: html-result -->

<div id="demo" data-author="Jane Doe" data-year="2022">Information Panel</div>
<br />
<div>author: <span id="1"></span></div>
<div>year: <span id="2"></span></div>
<script>
  const element = document.getElementById("demo");
  const span1 = document.getElementById("1");
  const span2 = document.getElementById("2");
  span1.innerHTML = element.dataset.author;
  span2.innerHTML = element.dataset.year;
</script>

Заключение

Понимание атрибутов и свойств DOM позволяет динамически управлять элементами страницы и создавать более богатые интерактивные приложения. Помните ключевое различие: атрибуты — это string-значения из вашего HTML-источника, тогда как свойства — это живые типизированные значения на DOM-объекте; и некоторые атрибуты (value, href, boolean-атрибуты) намеренно их разделяют.

Для углублённого изучения обратитесь к связанным главам:

Практика

Практика
Какие утверждения точно описывают различия между атрибутами и свойствами в DOM, как объяснено в учебнике JavaScript?
Какие утверждения точно описывают различия между атрибутами и свойствами в DOM, как объяснено в учебнике JavaScript?
Was this page helpful?