REST API в WordPress часто оставляют открытым по умолчанию, а потом удивляются лишним запросам, утечке служебных данных и шуму в логах. Полностью отключать его обычно плохая идея: Gutenberg, мобильные приложения, некоторые формы, поиск и внешние сервисы могут перестать работать. На практике чаще нужен не «рубильник», а аккуратное ограничение доступа для гостей.
Когда REST API действительно стоит ограничить
Сценарий обычно один из трех: сайт не использует публичные API-эндпоинты, в логах много запросов к /wp-json/ от ботов, или вы хотите скрыть служебные данные от неавторизованных посетителей. Если у вас есть фронтенд на React/Vue, интеграция с CRM или мобильное приложение, сначала проверьте, какие маршруты реально используются. Иначе можно сломать не только сторонний сервис, но и стандартные функции WordPress.
Что не стоит отключать вслепую
Не трогайте REST API, если:
- редактор блоков Gutenberg работает на сайте и редакторы входят в админку;
- есть формы, которые отправляют данные через REST;
- используются плагины с AJAX/REST-интеграцией;
- есть внешние клиенты, которые читают или пишут данные через API.
Диагностика: какие запросы идут к REST API и кто их делает
Перед изменениями полезно посмотреть, что именно запрашивается. В логах веб-сервера ищите обращения к /wp-json/, ?rest_route= и конкретным маршрутам вроде wp/v2/posts. Если запросы идут от гостей и не несут пользы для сайта, их можно ограничить. Если же они приходят от авторизованных пользователей или внутренних сервисов, блокировать нужно точечно.
Быстрая проверка из браузера тоже помогает: откройте /wp-json/ в режиме инкогнито. Если видите список маршрутов, API доступен для гостей. Это не ошибка само по себе, но хороший индикатор того, что публичная поверхность сайта шире, чем нужно.
Пошаговое решение: ограничить REST API только для авторизованных
Самый безопасный вариант — не отключать API целиком, а запретить доступ к REST-маршрутам для неавторизованных пользователей, оставив исключения для нужных эндпоинтов. Код лучше добавлять в мини-плагин или в functions.php дочерней темы, если у вас нет отдельного плагина для сайта.
<?php
add_filter( 'rest_authentication_errors', function( $result ) {
if ( ! empty( $result ) ) {
return $result;
}
if ( is_user_logged_in() ) {
return $result;
}
$request_uri = isset( $_SERVER['REQUEST_URI'] ) ? wp_unslash( $_SERVER['REQUEST_URI'] ) : '';
// Разрешаем только конкретные публичные маршруты, если они нужны.
$allowed_prefixes = array(
'/wp-json/oembed/1.0/',
'/wp-json/wp/v2/search',
);
foreach ( $allowed_prefixes as $prefix ) {
if ( strpos( $request_uri, $prefix ) !== false ) {
return $result;
}
}
return new WP_Error(
'rest_forbidden',
__( 'REST API доступен только авторизованным пользователям.', 'textdomain' ),
array( 'status' => 401 )
);
} );
Этот вариант работает как фильтр на уровне WordPress: он не ломает сам REST API, а возвращает ошибку только для гостей. Если вам нужен более жесткий режим, можно убрать исключения и оставить доступ только для авторизованных.
Если нужно закрыть только часть маршрутов
Иногда достаточно заблокировать только чтение записей, но оставить oEmbed или поиск. Тогда проверяйте не URI целиком, а сам запрос и маршрут. Это удобнее, если у вас есть публичный сайт, но вы не хотите отдавать список постов через API.
<?php
add_filter( 'rest_pre_dispatch', function( $result, $server, $request ) {
if ( is_user_logged_in() ) {
return $result;
}
$route = $request->get_route();
if ( strpos( $route, '/wp/v2/posts' ) === 0 ) {
return new WP_Error( 'rest_forbidden', 'Публичный доступ к записям через REST API закрыт.', array( 'status' => 403 ) );
}
return $result;
}, 10, 3 );
Сравнение подходов: плагин, код, серверный блок
| Подход | Когда подходит | Минус |
|---|---|---|
| Плагин безопасности | Если нужно быстро закрыть доступ без разработки | Может блокировать лишнее и конфликтовать с интеграциями |
| PHP-код в теме или мини-плагине | Если нужен контроль над исключениями | Нужно аккуратно тестировать после обновлений |
| .htaccess / nginx | Если надо отсечь шум до WordPress | Легко сломать редактор, oEmbed и внешние сервисы |
Для большинства проектов лучше начинать с PHP-ограничения внутри WordPress. Серверные правила уместны только тогда, когда вы точно знаете, какие маршруты не должны доходить до PHP вообще.
Проверка результата после внедрения
После добавления кода проверьте три вещи: гостевой доступ, работу админки и работу плагинов. Откройте /wp-json/ в инкогнито — должен вернуться отказ в доступе или пустой ответ в зависимости от вашей логики. Затем войдите в админку и откройте редактор записи: если Gutenberg грузится без ошибок, базовая совместимость сохранена.
Дополнительно проверьте:
- отправку форм на сайте, если они используют REST;
- поиск по сайту, если он завязан на
wp/v2/search; - внешние интеграции, которые читают данные через API;
- консоль браузера на наличие ошибок 401/403.
Частые ошибки и как их исправить
Сломали редактор блоков
Чаще всего это происходит, если REST API закрыли целиком без исключений. Gutenberg и часть интерфейса админки используют API для загрузки и сохранения данных. Решение простое: не блокируйте все маршруты, а оставьте доступ для авторизованных пользователей или добавьте исключения для нужных эндпоинтов.
Плагин продолжает работать, но с ошибками
Некоторые плагины делают запросы к REST API от имени гостя. Если после ограничения появились ошибки, посмотрите, какой маршрут вызывается, и добавьте точечное исключение. Не стоит сразу открывать весь API обратно — обычно достаточно разрешить один маршрут.
Блокировка сделана только в .htaccess
Серверное правило может не учитывать реальные сценарии WordPress и ломать доступ там, где он нужен. Если вы не уверены в конфигурации, перенесите логику в PHP: так проще управлять исключениями и отлаживать поведение.
Практические советы по безопасности и производительности
Если цель — уменьшить поверхность атаки, не ограничивайтесь REST API. Проверьте также XML-RPC, список авторов, публичные архивы и лишние endpoint'ы плагинов. Но не закрывайте всё подряд: чем агрессивнее фильтрация, тем выше шанс сломать функциональность.
Для сайтов с высокой нагрузкой полезно вести журнал отказов и смотреть, какие маршруты запрашиваются чаще всего. Это помогает понять, что можно закрыть без ущерба. Если у вас уже есть плагин для технической чистки и SEO-оптимизации, например Clearfy Pro, его удобно использовать как вспомогательный инструмент для отключения лишних поверхностей, но логику доступа к REST API лучше все равно держать в коде и проверять вручную.
И еще один практический момент: после изменений очистите кэш страницы и объектный кэш, если он есть. Иначе вы можете проверить старое поведение и решить, что код не сработал.