
🔌 Подключение jQuery в WordPress: правильный способ
Вы ставите плагин, а он тянет свою копию jQuery. Ваша тема уже загрузила jQuery через wp_enqueue_script. Плагин, ещё раз, напрямую из CDN. На странице, две, а то и три версии одной библиотеки. Конфликты, раздутый размер, непредсказуемое поведение.
Проблема стара как сам WordPress, но до сих пор воспроизводится: разработчики копипастят <script src="jquery.js"> в header.php, «потому что так быстрее». Быстрее, до первого конфликта с плагином, который ждёт родную WP-версию.
С 2026 года WordPress поставляет jQuery 3.6.0 из коробки и даёт простой, детерминированный способ подключения, без дублирования, без ручного слежения за версиями. Ниже, единственно правильный путь, от базового wp_enqueue_script до безопасной замены на CDN-версию и режима noConflict.
💡 Быстрый обзор:
- Как WordPress уже загружает jQuery и почему не надо делать это руками
wp_enqueue_scriptс зависимостьюjquery, одна строка вfunctions.php- Когда и как безопасно заменить встроенную jQuery на CDN-версию (Google / cdnjs)
- Режим
noConflict: защита от коллизий с другими библиотеками - Советы для тем и плагинов: когда отменять встроенную jQuery НЕ надо
jQuery уже в ядре: что WordPress делает за вас
Начиная с версии 3.6, WordPress регистрирует jQuery под handle-ом jquery. Вам не нужно качать jquery.min.js, класть в папку темы и подключать <script>-тегом, ядро сделает это само, как только вы укажете jquery в зависимостях своего скрипта.
Текущая версия jQuery в ядре WordPress, 3.6.0. Она идёт в комплекте с jQuery Migrate (для обратной совместимости со старым кодом) и загружается только если какой-либо скрипт объявил jquery зависимостью. Нет зависимостей, jQuery на страницу не попадает, сайт не грузит лишнего.
Вот почему прямой <script src="/wp-content/themes/mytime/jquery.js"> в header.php, ошибка, а не shortcut. Вы обходите систему зависимостей, лишаете WP возможности управлять очерёдностью и получаете дубликат, когда плагин честно попросит jquery через wp_enqueue_script.
Правильный способ: wp_enqueue_script с зависимостью
Базовая механика умещается в одну строку внутри хука wp_enqueue_scripts. Вы пишете свой скрипт, а WordPress сам разбирается, когда и в каком порядке всё загрузить.
Создайте (или откройте) functions.php вашей темы и добавьте:
1 function mytheme_enqueue_scripts() { 2 wp_enqueue_script( 3 'mytheme-main', 4 get_template_directory_uri() . '/js/main.js', 5 array( 'jquery' ), 6 '1.0.0', 7 array( 8 'strategy' => 'defer', 9 'in_footer' => true, 10 ) 11 ); 12 } 13 add_action( 'wp_enqueue_scripts', 'mytheme_enqueue_scripts' );
Что здесь происходит:
mytheme-main, уникальный handle вашего скрипта. Придумайте свой, с префиксом темы.get_template_directory_uri() . '/js/main.js', путь к файлу. Можно и внешний CDN-URL.array( 'jquery' ), ключевой момент: вы говорите WP «мой скрипт зависит от jQuery». Ядро видит это и автоматически ставит jQuery в очередь перед вашим скриптом. Никаких<script>-тегов в шаблоне.'1.0.0', версия для cache busting. Меняйте при каждом обновлении скрипта.array( 'strategy' => 'defer', 'in_footer' => true ), с WordPress 6.3 параметр$argsпринимает массив.deferозначает «выполнить скрипт после построения DOM, но до DOMContentLoaded».in_footerставит скрипт в футер.
Старый синтаксис с булевым пятым параметром (true = в футер) всё ещё работает, но для новых проектов используйте массив, он читается понятнее и даёт контроль над async/defer.
Проверьте, что ваша тема вызывает wp_head() перед закрывающим </head> и wp_footer() перед </body>. Без этих вызовов wp_enqueue_script просто не сработает, это частая ловушка при переходе с древних тем.
Как заменить встроенную jQuery своей версией
Иногда родной версии недостаточно. Вы хотите jQuery 4.0.0 с CDN ради самых свежих исправлений, или вам нужна конкретная версия для совместимости с legacy-плагином. Заменить, можно, но аккуратно.
Ошибка: просто вызвать wp_enqueue_script('jquery', 'https://cdn.jsdelivr.net/npm/[email protected]/dist/jquery.min.js'). WordPress НЕ перезаписывает уже зарегистрированный handle, вы получите родную версию И CDN-версию на одной странице.
Правильная последовательность: сначала снять родной jquery с регистрации, потом зарегистрировать свой:
1 function mytheme_use_cdn_jquery() { 2 // Снимаем встроенную jQuery 3 wp_deregister_script( 'jquery' ); 4 5 // Регистрируем свою — из CDN 6 wp_register_script( 7 'jquery', 8 'https://cdn.jsdelivr.net/npm/[email protected]/dist/jquery.min.js', 9 array(), 10 '4.0.0', 11 true 12 ); 13 14 // Ставим в очередь 15 wp_enqueue_script( 'jquery' ); 16 } 17 add_action( 'wp_enqueue_scripts', 'mytheme_use_cdn_jquery' );
Три момента, о которых часто забывают:
Google Hosted Libraries. Альтернативный CDN от Google до сих пор жив и держит jQuery 3.7.1: https://ajax.googleapis.com/ajax/libs/jquery/3.7.1/jquery.min.js. Плюс, миллионы сайтов уже греют кеш браузера под этот URL. Минус, Google добавляет свои заголовки и обновляет версии не сразу после релиза.
cdnjs. Если нужна jQuery 4.0.0, берите с cdn.jsdelivr.net/npm/[email protected]/. cdnjs зеркалирует npm-пакет и отдаёт с правильными CORS-заголовками.
Не отменяйте jQuery в публичных темах. Если ваша тема уходит в репозиторий WordPress.org, используйте родную jQuery из ядра. Причина проста: когда на одном сайте встречаются тема (с CDN jQuery 4.0.0) и плагин (ждущий jQuery 3.6.0 из ядра), конфликт решает пользователь, а не разработчик. В коммерческих темах и кастомных проектах, заменяйте смело.
Режим noConflict: когда на странице больше одной библиотеки
jQuery по умолчанию занимает глобальную переменную $. Проблема в том, что $, популярное имя: его используют Prototype, MooTools и некоторые legacy-фреймворки. Если плагин или второй скрипт тоже претендует на $, побеждает тот, кто загрузился последним, остальные ломаются.
Защита, одной строкой в начале вашего скрипта:
1 var $j = jQuery.noConflict();
После этого $ освобождается для других библиотек, а ваш код работает через $j. Полный пример, боковая панель с анимацией при наведении:
1 jQuery(document).ready( function( $ ) { 2 // Здесь $ — это jQuery, но только внутри этой функции 3 $( '#sidebar li a' ).hover( 4 function() { 5 $( this ).stop().animate( { paddingLeft: '20px' }, 400 ); 6 }, 7 function() { 8 $( this ).stop().animate( { paddingLeft: '0' }, 400 ); 9 } 10 ); 11 } );
Здесь $ работает как jQuery внутри замыкания jQuery(document).ready(), а снаружи, свободен для других. Это чище, чем плодить переменные $j, $jq и $myJQ по всему коду.
Когда noConflict не нужен: если ваш сайт полностью на WordPress, без сторонних JS-фреймворков, и все плагины написаны под wp_enqueue_script, $ безопасен. Но включать noConflict в стандартный boilerplate темы, хорошая привычка, цена которой, одна строка.
Что делать разработчику плагинов
Если вы пишете плагин для публичного распространения, используйте только wp_enqueue_script с зависимостью от jquery. Никаких wp_deregister_script('jquery') внутри плагинов: вы не знаете, какую версию jQuery ждут другие плагины на том же сайте.
Правильный паттерн для плагина выглядит так:
1 function myplugin_frontend_scripts() { 2 wp_enqueue_script( 3 'myplugin-frontend', 4 plugins_url( '/js/frontend.js', __FILE__ ), 5 array( 'jquery' ), 6 MYPLUGIN_VERSION, 7 true 8 ); 9 } 10 add_action( 'wp_enqueue_scripts', 'myplugin_frontend_scripts' );
MYPLUGIN_VERSION, константа версии плагина. При каждом обновлении плагина браузер пользователя получит свежий скрипт, а не закешированный старый.
Административные скрипты (только в админке) вешайте на хук admin_enqueue_scripts, jQuery в админке тоже зарегистрирована под тем же handle jquery.
⁉️🤔 Частые вопросы
Почему мой jQuery-код не работает, хотя wp_enqueue_script вызван правильно?
Самая частая причина, тема не вызывает
wp_head()иwp_footer(). Без этих функций WordPress физически не может вставить<script>-теги в HTML. Откройтеheader.php, там должен быть<?php wp_head(); ?>перед</head>. Вfooter.php,<?php wp_footer(); ?>перед</body>. Если тема древняя и этих вызовов нет, добавьте, это безопасно. Все современные темы и плагины полагаются наwp_head/wp_footer, без них сломано не только подключение скриптов, но и SEO-плагины, шрифты и микроразметка.
Можно ли использовать jQuery 4.0.0 в WordPress, если ядро идёт с 3.6.0?
Да, через
wp_deregister_script+wp_register_script(см. раздел выше). Но учтите: jQuery 4.0.0 убрал поддержку IE 11 и ряд устаревших методов. Если ваш сайт или плагин полагается на jQuery Migrate, оставайтесь на версии из ядра или подключите Migrate явно. WordPress постепенно движется в сторону нативного JavaScript и React для редактора блоков, но jQuery останется в ядре ещё долго: слишком много тем и плагинов от неё зависят.
Плагин тянет свою jQuery, хотя я уже подключил через functions.php, что делать?
Плагин, скорее всего, жёстко вставил <script src="jquery..."> в обход wp_enqueue_script. Это ошибка плагина. Решения два: найти в коде плагина прямой вызов и заменить на wp_enqueue_script с зависимостью (если вы готовы патчить плагин), или написать автору плагина с просьбой исправить. Как временный костыль можно вызвать wp_dequeue_script или удалить хук плагина, но это лечит симптомы, а не причину.
Что быстрее: jQuery из ядра WordPress или с CDN?
Если браузер пользователя уже кешировал jQuery с CDN (Google или cdnjs), CDN-версия загрузится мгновенно, с кодом 304 Not Modified. Если нет, разница в скорости загрузки между ядром и CDN пренебрежимо мала для jQuery (файл порядка 85 КБ в gzip). Для высоконагруженных проектов CDN экономит трафик вашего сервера; для типового сайта на WordPress разницы нет.
Стоит ли отказываться от jQuery в пользу нативного JS
Короткий ответ: зависит от проекта. jQuery 4.0.0 в сжатом виде весит около 85 КБ, это не zero, но и не повод для паники. Современный нативный JS: querySelectorAll, fetch и classList покрывают 90% того, ради чего брали jQuery в 2015-м. Если вы пишете новую тему с нуля и не зависите от jQuery-плагинов, рассмотрите vanilla JS, он чище и быстрее.
Но если в проекте уже есть jQuery-зависимости (слайдеры, галереи, UI-компоненты плагинов), не усложняйте. WordPress всё равно загрузит jQuery, когда плагин её запросит. Пишите аккуратные wp_enqueue_script с зависимостями, не мешайте ядру управлять очерёдностью, и jQuery будет работать быстро и предсказуемо.
🔗 Документация wp_enqueue_script | 🔗 Документация wp_deregister_script



