WP REST API часто пытаются «закрыть» целиком, когда на сайте появляются лишние запросы, боты или подозрительная активность. Это плохая идея, если на сайте работает редактор блоков, мобильное приложение, внешняя интеграция или WooCommerce. Гораздо надёжнее ограничивать не сам API, а конкретные маршруты и сценарии доступа.
Ниже — рабочий подход: сначала понять, какие запросы реально нужны, потом закрыть лишнее, а после проверить, что редактор, формы и магазин продолжают работать.
Когда REST API действительно стоит ограничивать
Полностью отключать REST API имеет смысл редко. Чаще проблема выглядит так: на сайте много запросов к /wp-json/, в логах видны обращения к публичным маршрутам, а часть плагинов использует API для фронтенда. Если просто поставить жёсткий запрет, можно получить неочевидные поломки: не загружается блок-редактор, не работают автосохранение, поиск товаров, некоторые формы и интеграции.
Ограничение обычно нужно в одном из трёх случаев:
- нужно скрыть публичные данные, которые не должны быть доступны без авторизации;
- боты массово дергают отдельные маршруты и создают нагрузку;
- на сайте есть кастомные endpoints, которые должны работать только для авторизованных пользователей или по токену.
Диагностика: что именно открыто и кто это использует
Перед изменениями проверьте, какие маршруты реально вызываются. Это можно сделать через логи веб-сервера, плагины мониторинга запросов или временно через фильтр в коде. Если у вас уже есть логирование в wp-config.php, удобно посмотреть, не сыпятся ли ошибки из-за сторонних запросов к API.
Что проверить в первую очередь
- открывается ли
/wp-json/в браузере без авторизации; - есть ли обращения к маршрутам WooCommerce, например
/wp-json/wc/v3/или фронтенд-эндпоинтам плагинов; - не использует ли тема или конструктор REST API для подгрузки контента;
- не ломается ли редактор блоков после тестового ограничения.
Если сайт на WooCommerce, не забывайте: магазин и связанные плагины нередко используют REST API для синхронизации и фронтенд-логики. Закрывать всё подряд здесь особенно рискованно.
Пошаговое решение: ограничиваем только нужные маршруты
Самый практичный вариант — оставить API доступным, но закрыть отдельные маршруты для неавторизованных пользователей. Для этого подходит фильтр rest_endpoints. Он позволяет удалить из списка конкретные endpoints до того, как WordPress отдаст ответ.
Пример: скрыть стандартные маршруты пользователей
Если вам не нужно, чтобы гости видели список пользователей или детали профилей, можно убрать соответствующие маршруты:
<?php
add_filter( 'rest_endpoints', function( $endpoints ) {
if ( ! is_user_logged_in() ) {
unset( $endpoints['/wp/v2/users'] );
unset( $endpoints['/wp/v2/users/(?P<id>[\\d]+)'] );
}
return $endpoints;
} );Этот вариант не отключает REST API целиком, а только убирает часть публичной поверхности. Для большинства сайтов это безопаснее, чем глобальный запрет.
Пример: закрыть кастомный маршрут для гостей
Если у вас есть собственный endpoint, лучше проверять права доступа внутри callback. Это надёжнее, чем пытаться фильтровать всё снаружи.
<?php
add_action( 'rest_api_init', function() {
register_rest_route( 'site/v1', '/private-data', array(
'methods' => 'GET',
'callback' => 'site_get_private_data',
'permission_callback' => function() {
return current_user_can( 'manage_options' );
},
) );
} );
function site_get_private_data( WP_REST_Request $request ) {
return rest_ensure_response( array(
'status' => 'ok',
'data' => 'secret',
) );
}Ключевой момент здесь — permission_callback. Без него маршрут может оказаться доступным шире, чем вы планировали.
Если нужно ограничить доступ по авторизации
Иногда достаточно разрешить endpoint только залогиненным пользователям. Тогда проверка выглядит проще:
<?php
add_action( 'rest_api_init', function() {
register_rest_route( 'site/v1', '/account-summary', array(
'methods' => 'GET',
'callback' => 'site_account_summary',
'permission_callback' => function() {
return is_user_logged_in();
},
) );
} );Если нужна более тонкая логика, используйте current_user_can() с конкретной capability, а не просто проверку логина.
Сравнение подходов: плагин, код или серверный запрет
| Подход | Когда подходит | Минус |
|---|---|---|
Код через rest_endpoints и permission_callback | Нужно закрыть отдельные маршруты без поломки редактора и интеграций | Требует поддержки в теме или мини-плагине |
| Плагин для безопасности | Если нужен интерфейс и быстрый контроль без правки кода | Может быть слишком общий и конфликтовать с другими настройками |
| Запрет на уровне сервера | Если нужно грубо закрыть доступ к части URL | Легко сломать Gutenberg, WooCommerce и внешние сервисы |
Если вы уже используете набор для чистки сайта и SEO-оптимизации вроде Clearfy Pro, проверьте, не дублирует ли он часть нужных вам ограничений. Но для точечного контроля маршрутов код обычно предсказуемее.
Проверка результата после внедрения
После изменения кода не ограничивайтесь открытием главной страницы. Проверьте именно те сценарии, которые завязаны на API.
Чек-лист проверки
- откройте
/wp-json/в режиме гостя и убедитесь, что видны только разрешённые маршруты; - проверьте вход в редактор записей и автосохранение;
- создайте тестовый заказ в WooCommerce и посмотрите, не появляются ли ошибки в консоли;
- если есть кастомные формы или фронтенд-виджеты, протестируйте их отправку и загрузку данных;
- посмотрите журнал ошибок PHP и логи веб-сервера на предмет 403/500 после изменений.
Если маршрут должен быть закрыт, но всё ещё отвечает гостю, значит фильтр не сработал на нужном этапе или endpoint регистрируется другим плагином позже вашего кода.
Частые ошибки и как их исправить
Отключают REST API целиком
Это самая частая ошибка. В результате ломаются блоки, редактор, некоторые темы и плагины. Исправление простое: не трогайте весь API, если проблема только в нескольких маршрутах.
Проверяют только is_user_logged_in()
Для административных или чувствительных данных этого мало. Пользователь может быть залогинен, но не иметь нужных прав. Используйте current_user_can() с подходящей capability.
Ставят запрет на уровне .htaccess без теста
Серверное правило может заблокировать не только нежелательные запросы, но и легитимные обращения фронтенда. Если очень нужен такой уровень, сначала проверьте его на staging-копии.
Не учитывают сторонние плагины
Некоторые плагины используют REST API для поиска, фильтров, синхронизации и уведомлений. Если после ограничения что-то перестало работать, ищите конкретный маршрут, а не откатывайте всё изменение целиком.
Практические советы по безопасности и производительности
Если цель — снизить шум и поверхность атаки, полезнее сочетать точечное ограничение API с базовой защитой админки и нормальным логированием. Не полагайтесь на один фильтр как на «броню».
- закрывайте только те маршруты, которые действительно не нужны гостям;
- для приватных endpoints всегда задавайте
permission_callback; - не храните секреты в ответах REST API, если они не нужны на фронтенде;
- проверяйте изменения на staging перед выкладкой на боевой сайт;
- после внедрения следите за ошибками 401/403 и жалобами пользователей на редактор или корзину.
Если задача шире, чем точечное ограничение маршрутов, иногда проще вынести часть логики в отдельный мини-плагин, чем держать код в functions.php. Так проще откатить изменения и не потерять их при смене темы.