Когда тег <script> был впервые представлен, он использовался для добавления только самого базового уровня интерактивности на веб-страницы. Но сеть сильно изменилась, и тег <script> эволюционировал. Распространение JavaScript сделало его одним из самых важных тегов HTML. В этой статье подробно рассматривается тег <script>, включая рекомендации по его использованию на современных веб-страницах.
Указание языка сценариев
Хотя JavaScript является языком сценариев по умолчанию в Интернете, браузеры могут поддерживать любое количество дополнительных языков. Например, Internet Explorer также поддерживает язык сценариев, производный от Visual Basic с именем VBScript . Чтобы указать язык сценариев по выбору, используется атрибут «type» тега <script>. Технически, «тип» определяет MIME- тип сценария. В следующем примере используется «тип», чтобы указать MIME-тип JavaScript «text / javascript».
<script type = "text / javascript"> // код JavaScript здесь </ Скрипт>
В более старых версиях HTML необходимо было указывать значение «type». Однако, начиная с HTML5, по умолчанию «type» — «text / javascript». Это решение было принято, потому что W3C понял, что JavaScript является единственным универсально поддерживаемым языком сценариев. Поэтому теги HTML5 <script> можно сократить следующим образом.
<Скрипт> // код JavaScript здесь </ Скрипт>
Атрибут «язык»
Существует второй атрибут «language», который можно использовать для указания языка сценариев. В отличие от «типа», возможные значения «языка» никогда не были стандартизированы. Этот атрибут давно устарел , но некоторые до сих пор его используют. Он не должен использоваться ни при каких обстоятельствах.
Встроенные и внешние скрипты
Тег <script> позволяет встроить код непосредственно в HTML или включить из внешних файлов сценариев. Встроенные сценарии создаются путем размещения кода между тегами <script> и </ script> в файле HTML. Следующий код показывает пример встроенного <script>.
<Скрипт> // Встроенный код JavaScript здесь </ Скрипт>
Встроенные скрипты — это быстрый и простой способ добавления кода на веб-страницы. Тем не менее, большие скрипты могут также привести к загромождению HTML-файлов. Альтернативный подход — включить код во внешние файлы скриптов. На внешние файлы ссылается URL-адрес, указанный в атрибуте «src». В следующем примере показано, как включены внешние файлы сценариев. В этом примере внешний файл сценария называется external.js и находится в том же каталоге, что и файл HTML. Также обратите внимание, что закрывающий тег </ script> по-прежнему необходим.
<script src = "external.js"> </ script>
Совместимость с XHTML
Правила XHTML намного строже, чем правила HTML. Когда специальные символы XML (такие как & и <) используются в сценариях в файлах XHTML, они вызывают ошибки. Самый простой обходной путь — использовать внешние файлы сценариев. Однако, если вам просто нужно написать встроенные сценарии, вам нужно будет включить в файл разделы CDATA (символьные данные). В разделах CDATA специальные символы XML могут использоваться свободно. В следующем примере используется раздел CDATA, совместимый с синтаксисом XHTML и HTML. Обратите внимание, что XHTML также требует использования атрибута «type».
<script type = "text / javascript"> // <! [CDATA [ оповещение ((1 <2) && (3> 2)); //]]> </ Скрипт>
Динамическое внедрение тега скрипта
Динамическое внедрение тега script — это метод, при котором новые элементы <script> создаются во время выполнения. Когда новый <script> добавляется на страницу, его URL-адрес «src» автоматически загружается и выполняется. Следующий код показывает пример динамического внедрения тега сценария. В этом примере новый элемент <script> создается с помощью функции document.createElement (). Затем атрибутом «src» задается URL-адрес файла скрипта. Наконец, новый элемент добавляется в заголовок документа, вызывая загрузку и выполнение скрипта.
var script = document.createElement ("script"); script.setAttribute ("src", url); document.head.appendChild (сценарий);
заявка
Тег <script> не подчиняется той же политике происхождения . Веб-страницы могут использовать эту свободу для запроса межсайтовых данных. JSONP, метод создания межсайтовых AJAX-подобных запросов, широко использует динамическое внедрение тегов скриптов. В модели JSONP каждый запрос AJAX заменяется внедрением тега скрипта.
Атрибут «асинхронный»
При обнаружении тега <script> браузер останавливает свою работу и начинает загрузку / выполнение сценария. Такое поведение по умолчанию известно как синхронная блокировка . В течение этого периода блокировки пользователю может показаться, что страница не отвечает или работает медленно. Чтобы смягчить эту проблему, HTML5 ввел атрибут «async» для тегов <script>. «Async» — это логический атрибут, который, если он указан, указывает, что сценарий должен разблокировать остальную часть страницы и выполняться асинхронно. Согласно спецификации «async» следует использовать только с внешними файлами сценариев. К сожалению, «async» еще не поддерживается в Opera . В следующем примере показано, как используется атрибут «async».
<script src = "file.js" async = "async"> </ script>
Обычно async по умолчанию имеет значение false. Однако при работе с динамически внедряемыми сценариями значение по умолчанию становится истинным. Это может привести к проблемам, если сценарии с взаимозависимостями вставляются одновременно. Например, предположим, что на страницу добавляется сторонняя библиотека, созданная на медленном сервере. В то же самое время (почти) страница также внедряет скрипт, который делает вызовы в библиотеку. Поскольку сценарии являются асинхронными, второй файл потенциально может быть загружен и выполнен до того, как библиотека станет доступной. Решение состоит в том, чтобы сохранить порядок программ, установив «async» в false для обоих сценариев. Эта концепция иллюстрируется в следующем примере. В этом примере страница будет ожидать загрузки первого сценария, а затем перейдет ко второму сценарию.
var library = document.createElement ("script"); var local = document.createElement ("script"); library.async = false; local.async = false; library.setAttribute ("src", "remote-library-code.js"); local.setAttribute ("src", "local-file.js"); document.head.appendChild (библиотека); document.head.appendChild (местное); // используем код библиотеки
Атрибут «отсрочить»
Как указывалось ранее, теги <script> заставляют браузер блокировать остальную часть страницы во время обработки сценария. Это может привести к проблемам, если скрипт ссылается на элементы DOM, которые еще не закончили загрузку. В этом сценарии связанный с DOM код обычно помещается в обработчик событий, такой как загрузка окна или DOMContentLoaded . Другой вариант — отложить выполнение до тех пор, пока документ не будет проанализирован с использованием атрибута «defer». Как и «async», «defer» является логическим атрибутом, который должен использоваться только с внешними файлами сценариев. В следующем примере показано, как работает «отсрочка». В этом примере требуется файл HTML и отдельный файл JavaScript с именем defer.js. Источник HTML показан ниже.
<! DOCTYPE html> <html lang = "en"> <Голова> <title> Пример отсрочки </ title> <meta charset = "UTF-8" /> <script src = "defer.js" defer = "defer"> </ script> </ HEAD> <Тело> <span id = "message"> </ span> </ Body> </ Html>
Код для defer.js показан ниже. Если бы атрибут «defer» отсутствовал, этот код потерпел бы неудачу, потому что DOM не готов при доступе к элементу <span>.
var span = document.getElementById ("message"); span.textContent = "DOM готов к написанию сценариев!";
Можно указать как «async», так и «defer» для одного элемента <script>. Это возможно, так что браузеры, которые не поддерживают «асинхронность», могут использовать режим «отсрочки» вместо синхронной блокировки. Согласно спецификации «defer» отменяется «async». К сожалению, «отсрочка» также не поддерживается в Opera .
Вопросы производительности
Во всех примерах на этой странице показаны теги <script>, размещенные в заголовке документа. Это может фактически снизить производительность, поскольку остальная часть страницы блокируется во время обработки сценариев. Очевидно, что атрибуты «defer» и «async» предлагают одно решение. К сожалению, они пока не поддерживаются повсеместно. Второй вариант — по возможности перемещать теги <script> внизу тега <body> — обычно это нормально, если сценарий не вызывает document.write ().
Использование внешних файлов сценариев вместо встроенных сценариев — это еще один метод, который часто повышает производительность. Это приводит к уменьшению размера HTML-файлов за счет создания дополнительных HTTP-запросов. Однако файлы сценариев часто используются несколькими HTML-страницами и могут кэшироваться браузером. Общий результат — меньшая загрузка HTML без дополнительных запросов к серверу. Также помните, что скрипты могут быть загружены динамически после загрузки страницы.
То, что нужно запомнить
- Для тега <script> всегда требуется соответствующий тег </ script>.
- Язык сценариев указывается атрибутом «type». Не используйте атрибут «language». HTML5 по умолчанию «текст / JavaScript».
- Файлы XHTML должны использовать внешние файлы сценариев или разделы CDATA, чтобы разрешить использование специальных символов.
- Динамические инъекции тегов скрипта позволяют запрашивать ресурсы между сайтами.
- Атрибут «async» заставляет скрипт выполняться асинхронно с остальной части страницы. Это также может сохранить порядок для динамически вставленных скриптов.
- Атрибут «defer» может отложить выполнение скрипта, пока документ не будет готов.
- Переместите теги <script> в конец <body>, когда это возможно.
- Используйте внешние файлы сценариев, которые можно кэшировать и делиться между страницами.