З відпочинком V2 (WP4.7) як обмежуються певні дієслова?


20

Я маю на меті обмежити певні дієслова RESTUL для користувальницького типу публікації. Наприклад, враховуючи спеціальний тип публікації словника, я хотів би сказати:

Матриця дозволу

+-------+---+----------+
|index  | X | GET      |
|show   | O | GET      |
|create | X | POST     |
|update | X | PATCH/PUT|
|delete | X | DELETE   |
+-------+---+----------+

Схоже, V2 не забезпечує такий рівень контролю. Я пройшов через джерело, і, як я бачу, немає жодних гачків / фільтрів, які б ввійшли до змін дозволів.

Моє поточне рішення полягає в наступному. Це компроміси класу, де ви можете завантажити матрицю спеціальних типів публікацій проти дозволених дій. Потім це можна викликати у rest_prepare_vocabularyфільтрі, знищуючи відповідь, якщо дозволи не вирівнюються.

Проблема

Я не вважаю, що це розумне рішення. Це означає, що дозволи вирішуються в двох місцях (в одному, в основній, оскільки вони все ще застосовуються) і в моїх фільтрах.

В ідеалі це було б на рівні конфігурації, а саме там, де визначені користувацькі типи публікацій.

Іншими словами, я вважаю за краще вводити правила (по рядках exclude_from_search, publicly_queryableі т. Д.), А не виконувати поштовий запит "фрагмент".

Поточне рішення (працює, але не бажано)

Access.php

class Access
{
    function __construct($permissions) {
        $this->permissions = $permissions;
    }

    protected function hasId($request) {
        return ! is_null($request->get_param('id'));
    }

    protected function resolveType($request) {
        $method = strtoupper($request->get_method());

        if($method === 'GET' && $this->hasId($request)) {
            return 'show';
        } else if($method === 'GET') {
            return 'index';
        } else if($method === 'DELETE') {
            return 'delete';
        } else if($method === 'POST') {
            return 'create';
        } else if($method === 'PATCH') {
            return 'update';
        }
    }

    function validate($type, $request) {
        return in_array($this->resolveType($request), $this->permissions[$type]);
    }
}

function.php

// bootstrap the permissions for this particular 
// application
// 
$access = new Access([
    'vocabulary' => ['show'],
]);

add_filter('rest_prepare_vocabulary', 'validate_permissions', 30, 3);
function validate_permissions($response, $post, $request) {
    global $access;

    // Give access->validate the type + request data 
    // and it will figure out if this is allowed
    //
    if( ! $access->validate($post->post_type, $request)) {
        $response->set_data([]);
        $response->set_status(403);
    }

    return $response;
};

1
Чому ви створили примірник Accessу глобальному масштабі? Вам це потрібно в іншому місці? Якщо ви відповісте на це так , ви можете замість цього приєднати його до фільтра.
кайзер

3
Справедливе запитання - Вищенаведене - це лише фрагмент, я використовую композитор та PSR4 для автоматичного завантаження, щоб намалювати модулі класу в батьківський клас додатків, серед яких був би описаний вище фрагмент, - тому він насправді не є глобальним глобальним, він буде розділений на імена \Appта доступ насправді\App\Services\Access
Кріс

1
Я сам не досліджував цю проблему, але ви перевірили Trac на квиток або створили його, якщо його немає?
Здається, що

1
Я не дуже розумію проблему. "Це означає, що дозволи дозволяються вирішуватись у двох місцях (одному, в основному, оскільки вони все ще застосовуються) та в моїх фільтрах. В ідеалі, це було б на рівні конфігурації, а саме там, де визначені спеціальні типи публікацій." Чи можете ви пояснити, що ви тут маєте на увазі? Вибачте, якщо я дурний!
Jim Maguire

2
Я спростовую це питання. Я не розумію, чому 18 людей проти цього. Це незрозуміло.
Jim Maguire

Відповіді:


1

Я пройшов через джерело, і, як я бачу, немає жодних гачків / фільтрів, які б ввійшли до змін дозволів.

Я розумію, що це було навмисне дизайнерське рішення.

Хоча API REST був розроблений як розширюваний, не рекомендується змінювати основні кінцеві точки таким чином, як ви запитуєте.

У цьому розділі посібника з REST API є деяка обмежена інформація , але суть його полягає в тому, що в міру старіння API більше коду (будь то основний чи третій), почне залежати від конкретних дій, які доступні та забезпечують стандарт відповіді.

Натомість слід створити спеціальний контролер.

Спеціальні типи публікацій можна надати користувацькому контролеру, вказавши ім'я класу в rest_controller_classаргументі доregister_post_type() .

Огляд того, як повинні працювати власні контролери, можна знайти в посібнику з API REST .

Ще щось, про що слід пам’ятати, - це те, що якщо ви створите спеціальний контролер, який розширює абстрактний WP_REST_Controllerклас для типу публікації, який підтримує редагування, автоматично буде створено ряд конкретних кінцевих точок редагування типу публікації.

Якщо він не розширює WP_REST_Controllerклас, register_routes()метод не викликається, тому вам доведеться вручну реєструвати власні маршрути.

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.