API-интерфейс WP REST требует пароль для конечной точки GET

8

У меня есть пользовательский тип записи, cardкоторый я раскрываю через WP REST API. Есть ли способ требовать аутентификацию с помощью cookie или заголовка Basic Auth? Я вижу аргумент в блоке метода POST для пароля, но я не уверен, как его использовать.

введите описание изображения здесь

YarGnawh
источник

Ответы:

9

Когда мы регистрируем маршрут отдыха с помощью register_rest_route(), тогда мы можем использовать permission_callbackпараметр с тем видом разрешения, который нам нужен.

Посмотрите, например, как WP_REST_Posts_Controller::register_routes()и WP_REST_Users_Controller::register_routes()реализовать разрешение обратного вызова.

Аргумент пароля, на который вы ссылаетесь, является паролем контента, который вы можете установить для каждого сообщения, и это не одно и то же.

Но так как вы хотите ориентироваться на существующие маршруты, например:

/wp/v2/cards
/wp/v2/cards/(?P<id>[\d]+)
/wp/v2/cards/...possibly some other patterns...

Вы можете попробовать, например, rest_dispatch_requestфильтр, чтобы настроить дополнительную проверку прав доступа для таких маршрутов.

Вот демонстрационный плагин:

add_filter( 'rest_dispatch_request', function( $dispatch_result, $request, $route, $hndlr )
{
    $target_base = '/wp/v2/cards';    // Edit to your needs

    $pattern1 = untrailingslashit( $target_base ); // e.g. /wp/v2/cards
    $pattern2 = trailingslashit( $target_base );   // e.g. /wp/v2/cards/

    // Target only /wp/v2/cards and /wp/v2/cards/*
    if( $pattern1 !== $route && $pattern2 !== substr( $route, 0, strlen( $pattern2 ) ) )
        return $dispatch_result;

    // Additional permission check
    if( is_user_logged_in() )  // or e.g. current_user_can( 'manage_options' )
        return $dispatch_result;

    // Target GET method
    if( WP_REST_Server::READABLE !== $request->get_method() ) 
        return $dispatch_result;

    return new \WP_Error( 
        'rest_forbidden', 
        esc_html__( 'Sorry, you are not allowed to do that.', 'wpse' ), 
        [ 'status' => 403 ] 
    );

}, 10, 4 );

где мы нацелены на маршруты GET /wp/v2/cardsи /wp/v2/cards/*GET, с дополнительными проверками прав доступа пользователей.

При отладке с помощью аутентификации файлов cookie WordPress, мы можем, например, проверить это напрямую с помощью:

https://example.tld/wp-json/wp/v2/cards?_wpnonce=9467a0bf9c

где одноразовая часть была сгенерирована из wp_create_nonce( 'wp_rest' );

Надеюсь это поможет!

birgire
источник
Я пытался сделать это общим для данной целевой базы, но, может быть, есть более простой способ обойти это? Я добавил пример возможности в качестве встроенного комментария @MarkKaplun
birgire
Может быть, даже проще удалить конечную точку для заданного пользовательского типа записи, с register_post_type_argsфильтром и e, g, установленным $args['show_in_rest'] = is_user_logged_in();для данного типа записи или на основе $args['rest_base']. Не уверен, что это нужно или рекомендуется ;-)
birgire
3

Поле «пароль», которое вы видите, на самом деле не для REST API, а для самой записи Post. Отдельные сообщения в WordPress могут быть защищены паролем, так что вам нужен пароль для просмотра их содержимого.

Эта форма индивидуального пост-пароля не является механизмом надежного пароля, это общий пароль. Пароль одинаков для всех пользователей, и он хранится в базе данных в незашифрованном и незашифрованном виде. Он никогда не задумывался как безопасный механизм каким-либо образом, это простой механизм для простого скрытия контента.

Если вы хотите использовать этот механизм с REST API, то это возможно. Например, если идентификатор отдельной записи равен 123, то запись может быть получена следующим образом:

http://example.com/wp-json/wp/v2/posts/123

Если это сообщение защищено паролем, то этот URL-адрес получит его:

http://example.com/wp-json/wp/v2/posts/123?password=example-pass

Ссылка: https://developer.wordpress.org/rest-api/reference/posts/#retrieve-a-post

Если вам нужна более сильная аутентификация на основе пользователей, тогда WordPress предлагает способ сделать посты «приватными». Этот параметр делает сообщения видимыми только для учетных записей пользователей, которые имеют возможность «read_private_posts», которая по умолчанию ограничена ролями Администратор и Редактор. (Примечание. Приватное только делает содержание публикации личным, их заголовки все еще могут быть доступны.)

Когда вы создаете пользовательский тип записи, эта же возможность отображается во множественном числе вашего типа (с использованием множественной_базы). Таким образом, для карточек почтового типа было бы аналогичное разрешение «read_private_cards», доступное для вас при желании назначать роли пользователя.

Теперь аутентификация на уровне пользователя фактически не встроена в REST API. Стандартная проверка подлинности на основе файлов cookie WordPress работает нормально, однако API не дает возможности получить этот файл cookie. Он примет его, если он присутствует, но вы должны выполнить обычный вход в систему, чтобы получить такой файл cookie. Если вам нужен какой-то другой подход к аутентификации, вам нужен плагин для него.

Существует четыре таких плагина. Это OAuth 1.0, пароли приложений, веб-токены JSON и плагин базовой аутентификации. Обратите внимание, что базовая аутентификация является самой простой, однако она также небезопасна и поэтому рекомендуется только для целей тестирования и разработки. Он не должен использоваться на живом производственном сервере.

Вы можете найти больше информации об этих плагинах здесь:

https://developer.wordpress.org/rest-api/using-the-rest-api/authentication/#authentication-plugins

эфирное масло
источник