Статьи

WP API и OAuth — Использование WordPress без WordPress

В этом руководстве мы узнаем, как установить и использовать WP-API с OAuth — плагином WordPress, который использует конечные точки API, подобные REST, чтобы разрешить чтение содержимого WP неаутентифицированным пользователям и запись содержимого WP пользователям, которые проходят аутентификацию через OAuth. (или через Cookies для тем и плагинов).

WordPress Logo

Использование плагина не очень простое, а список предварительных требований довольно длинный, поэтому этот пост был написан, чтобы сделать его простым и относительно доступным (если вы контролируете свой собственный сервер).

Учебное пособие предполагает базовое знакомство с терминалом и с Vagrant для простоты разработки.

Установка

Как обычно, мы будем использовать надежный экземпляр SitePoint Homestead Improved для запуска и запуска новой среды:

git clone https://github.com/swader/homestead_improved hi_wp_github cd hi_wp_github sed -i '' "s@map\: \.@map\: $PWD@g" Homestead.yaml 

Последняя строка представляет собой ярлык, который делает текущую папку хост-машины общей для папки « Code » виртуальной машины. Я также изменил блок сайтов на:

 sites: - map: test.app to: /home/vagrant/Code/wptest 

Не забудьте test.app (или test.app вами URL) в файл /etc/hosts , как указано в инструкции .

Затем мы получаем новый экземпляр WP и работаем. Так как в Homestead уже установлен MySQL, это очень просто.

 cd ~/Code wget https://wordpress.org/latest.tar.gz tar -xvzf latest.tar.gz mv wordpress wptest cd wptest cp wp-config-sample.php wp-config.php 

После того, как мы соответствующим образом обновим wp-config.php и wp-config.php наши ключи и учетные данные базы данных, экземпляр WP будет готов и его можно будет завершить, запустив его в браузере.

WP-API

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

Одним из таких усилий является WP-API , REST-подобный набор конечных точек, встроенный в WP как плагин, чтобы внутренние компоненты установки WordPress могли быть доступны извне. Например, получить ваши сообщения в формате JSON так же просто, как pinging /wp-json/posts .

Его можно легко установить через менеджер плагинов по умолчанию — стабильная версия 1.2. * На момент написания этой статьи — так что давайте сделаем это.

Installing the wp-rest-api plugin

Если мы протестируем сразу после установки, URL /wp-json/posts должен создать массив JSON исходного сообщения «Hello World». Однако фактический процесс отправки (обновление и публикация) не так прост.

OAuth — сервер

К сожалению, как и во всем WP, даже их попытки быть современными уже устарели.

Таким образом, они используют OAuth1, а не OAuth2 для аутентификации. Для этого нам понадобится плагин OAuth1. Для этого нам понадобится обновление wp-cli , способ использовать команды WP из терминала:

 curl -O https://raw.githubusercontent.com/wp-cli/builds/gh-pages/phar/wp-cli.phar chmod +x wp-cli.phar sudo mv wp-cli.phar /usr/local/bin/wp 

Затем мы берем плагин OAuth:

 cd ~/Code/wptest git clone https://github.com/WP-API/OAuth1 wp-content/plugins/oauth-server 

Активируйте плагин (который теперь должен появиться в списке плагинов) и вернитесь в запуск терминала:

 wp oauth1 add 

Это должно создать комбинацию ключ / секрет, которая может использоваться для аутентификации OAuth:

 ID: 4 Key: xOp1fGMgouBl Secret: Sk7YcM48qsmcDPp2NSmna3kMEfTtDNfxpy43xjWp1mSP7ytw 

Помимо устаревшего подхода к протоколу, мы также вынуждены использовать 3-сторонний OAuth, а не что-то более простое, не похожее на интерфейс, например, 2-сторонний OAuth-поток. Для различий, прочитайте это обширное руководство . Надеюсь, это улучшится позже.

Хорошая новость заключается в том, что если вы являетесь владельцем сайта WP и разрешаете доступ через OAuth API для других — все готово! Это зависит от них, чтобы разработать клиента, и это то, что мы будем делать дальше.

OAuth — Клиент

Чтобы протестировать отправку в WP через WP-API, нам нужно «приложение», которое будет служить «отправителем». Для этого мы создаем новый проект в другой папке на виртуальной машине — идеально подходит для тестирования. Сначала мы редактируем файл Homestead.yaml виртуальной машины, чтобы включить новый сайт:

 sites: - map: test.app to: /home/vagrant/Code/wptest - map: test2.app to: /home/vagrant/Code/submitter 

Затем мы выходим из виртуальной машины с exit и повторно предоставляем с помощью vagrant provision а затем повторно переносим виртуальную vagrant ssh с помощью vagrant ssh . Теперь, когда наш виртуальный хост отправителя определен, давайте добавим в него простой файл index.php и (пока что) пустой файл callback.php .

 mkdir ~/Code/submitter touch ~/Code/submitter/index.php touch ~/Code/submitter/callback.php touch ~/Code/submitter/credentials.php cd ~/Code/submitter 

Файл учетных данных должен содержать ключи, которые мы получили из приложения WP:

 // credentials.php <?php return [ 'consumer_key' => 'xOp1fGMgouBl', 'consumer_secret' => 'Sk7YcM48qsmcDPp2NSmna3kMEfTtDNfxpy43xjWp1mSP7ytw' ]; 

Нам также понадобятся несколько установленных пакетов:

 composer require --dev symfony/var-dumper composer require guzzlehttp/guzzle:~5 

VarDumper помогает нам в отладке, а Guzzle 5 помогает нам отправлять запросы в WP-API. Мы могли бы использовать универсальный клиент OAuth, но почему бы не использовать Guzzle ?

 composer require guzzlehttp/oauth-subscriber 

Обратите внимание, что отправитель, который мы будем строить ниже, является всего лишь демонстрационным сценарием и должен использоваться только как вдохновение для реализации OAuth + WP-API в вашем собственном приложении, а не как полная демонстрационная версия приложения.

Еще одна вещь — по умолчанию WordPress блокирует перенаправления входа на внешние сайты (те, которые различаются по домену), поэтому необходимо добавить новый фильтр, который позволит это. Вернувшись в исходники приложения WP, откройте default-filters.php и добавьте куда-нибудь в файл следующее:

 add_filter( 'allowed_redirect_hosts' , 'my_allowed_redirect_hosts' , 10 ); function my_allowed_redirect_hosts($content){ $content[] = 'test2.app'; return $content; } 

Естественно, замените test2.app своим собственным URL, если вы использовали другой.

Аутентификация — Этап 1

Аутентификация с помощью WP API поверх OAuth — это то, чего полностью не хватает в документации, но это потому, что аутентификация OAuth является чем-то довольно специфичным и почти идентичным во всех проектах . Это не значит, что все просто. В основном мы будем следовать процедуре из этого поста , так или иначе.

Дайте index.php следующее содержимое:

 <?php require_once 'vendor/autoload.php'; session_start(); use GuzzleHttp\Client; use GuzzleHttp\Subscriber\Oauth\Oauth1; $client = new Client([ 'defaults' => ['auth' => 'oauth'] ]); $oauth = new Oauth1(include 'credentials.php'); $client->getEmitter()->attach($oauth); $callback = 'http://test2.app/callback.php'; $req = $client->createRequest("POST", 'http://test.app/oauth1/request', ['body' => ['oauth_callback' => $callback]]); try { $res = $client->send($req); parse_str($res->getBody()); $_SESSION['oauth_token'] = $oauth_token; $_SESSION['oauth_token_secret'] = $oauth_token_secret; header("Location: http://test.app/oauth1/authorize?oauth_token={$oauth_token}&oauth_callback=".$callback); } catch (\Exception $e) { dump($e); } 

Сначала мы определяем новый клиент Guzzle и устанавливаем его режим аутентификации по умолчанию как Oauth. Затем мы устанавливаем новый экземпляр клиента OAuth1 и даем ему ключ и секрет, которые мы получили ранее, запустив wp oauth1 add . Мы используем этот экземпляр в качестве источника и создаем из него запрос POST (также определяющий обратный вызов — URL-адрес, на который WP должен перенаправить нас после авторизации), который затем отправляется в наше приложение WP.

В блоке try / catch мы превращаем ответ в две строки: $oauth_token и $oauth_token_secret , обе из которых нам нужны для продолжения процесса аутентификации. Мы сохраняем их в сеансе и переходим к шагу 2: файл callback.php .

Аутентификация — этап 2

Для второго этапа трехстороннего потока OAuth нам нужно создать файл callback.php .

Когда мы регистрируемся в WP и авторизуем наше приложение-отправитель, WP отправляет нас обратно по указанному нами URL-адресу обратного вызова. Также будут отправлены дополнительные параметры: oauth_token , oauth_verifier и wp_scope .

Мы используем верификатор и oauth_token чтобы отправить запрос конечной точке /access и получить токен доступа ( секретный ), который, наконец, позволит нам выполнять операции с базой данных.

 <?php require_once 'vendor/autoload.php'; session_start(); use GuzzleHttp\Client; use GuzzleHttp\Exception\ClientException; use GuzzleHttp\Subscriber\Oauth\Oauth1; $authToken = $_GET['oauth_token']; $authVerifier = $_GET['oauth_verifier']; $client = new Client(['defaults' => ['auth' => 'oauth']]); $oauth = new Oauth1( array_merge(include 'credentials.php', ['token' => $_SESSION['oauth_token']]) ); $client->getEmitter()->attach($oauth); if ($authToken == $_SESSION['oauth_token']) { $req = $client->createRequest("POST", 'http://test.app/oauth1/access', ['body' => ['oauth_verifier' => $authVerifier]]); try { $res = $client->send($req); $params = (string)$res->getBody(); parse_str($params); $_SESSION['oauth_token'] = $oauth_token; $_SESSION['oauth_token_secret'] = $oauth_token_secret; header("Location: makepost.php"); } catch (ClientException $e) { dump((string)$e->getResponse()->getBody()); } catch (\Exception $e) { dump($e); } } 

Аутентификация — этап 3

Наконец, давайте создадим файл makepost.php который мы будем использовать для создания образца поста в нашем приложении WP — если это makepost.php , это означает, что все работает просто отлично.

 <?php require_once 'vendor/autoload.php'; session_start(); use GuzzleHttp\Client; use GuzzleHttp\Exception\ClientException; use GuzzleHttp\Subscriber\Oauth\Oauth1; $client = new Client([ 'defaults' => ['auth' => 'oauth'] ]); $array = array_merge(include 'credentials.php', [ 'token' => $_SESSION['oauth_token'], 'token_secret' => $_SESSION['oauth_token_secret'] ]); $oauth = new Oauth1($array); $client->getEmitter()->attach($oauth); $post = [ 'title' => 'From outside!', 'content' => 'This post was submitted via the API!!!', 'status' => 'publish' ]; $req = $client->createRequest("POST", 'http://test.app/wp-json/posts', ['json' => $post]); try { $res = $client->send($req); dump((string)$res->getBody()); } catch (ClientException $e) { dump((string)$e->getResponse()->getBody()); } catch (\Exception $e) { dump($e); } 

У нас есть простая «запись» в виде массива с тремя полями, и по умолчанию используется режим «публикации», поэтому мы можем сразу увидеть ее на домашней странице нашего приложения WP без необходимости заходить в редактор и публиковать это вручную.

После выполнения сообщение должно быть видно на главном экране нашего приложения WP:

Post has been published

Конечно, три файла выше ( index.php , callback.php , makepost.php ) являются примерами использования OAuth и, вероятно, должны быть превращены во что-то более многократно используемое и связное, но для простого тестирования, если интеграция работает, они просто хорошо. Не бойтесь, хотя — мы будем обновлять это значительно в следующем посте.

Вывод

В этом руководстве мы установили и активировали WP-API и WP-Oauth, чтобы сделать нашу установку WP доступной для внешнего (аутентифицированного) мира. Как видите, это не совсем просто, но, надеюсь, это руководство помогло вам начать работу.

У вас уже был опыт работы с WP-API? Хотите увидеть больше примеров? Дайте нам знать!