Cum să folosești autentificarea OAuth cu REST API prin comenzi CURL?
Încerc să folosesc WordPress Rest Api cu autentificare pentru a obține mai multe date din API. Am instalat plugin-ul OAuth, plugin-ul rest-api și am obținut credențialele API din WP-CLI.
Am reușit să accesez date fără autorizare. Acesta funcționează:
// setăm endpoint-ul nostru
$domain = "http://localhost/wp-api";
$endpoint = $domain."/wp-json/wp/v2/posts/";
$curl = curl_init($endpoint);
curl_setopt_array($curl, [
CURLOPT_RETURNTRANSFER => true,
CURLOPT_URL => $endpoint,
]);
$response = curl_exec($curl);
$decoderesponse = json_decode($response, true);
?>
<pre>
<?php print_r($decoderesponse); ?>
</pre>
Dar nu reușesc să mă autentific cu credențialele. Iată încercarea mea. Nu sunt sigur dacă "key" și "secret" sunt corecte.
// Credențiale OAuth din wp-cli
$ID = "4";
$Key = "l8XZD9lX89kb";
$Secret = "UUbcc8vjUkGjuDyvK1gRTts9sZp2N8k9tbIQaGjZ6SNOyR4d";
// setăm endpoint-ul nostru
$domain = "http://localhost/wp-api";
$endpoint = $domain."/wp-json/wp/v2/posts/1/revisions";
$headers[] = "key=$Key";
$headers[] = "secret=$Secret";
$curl = curl_init($endpoint);
curl_setopt_array($curl, [
CURLOPT_HTTPHEADER => $headers,
CURLOPT_RETURNTRANSFER => true,
CURLOPT_URL => $endpoint,
]);
$response = curl_exec($curl);
$decoderesponse = json_decode($response, true);
?>
<pre>
<?php print_r($decoderesponse); ?>
</pre>
Rezultatul este
Array
(
[code] => rest_cannot_read
[message] => Ne pare rău, nu puteți vizualiza reviziile acestei postări.
[data] => Array
(
[status] => 401
)
)
Cum pot face să funcționeze? Mulțumesc.

Să mergem pas cu pas aici. Se pare că încerci să folosești OAuth doar pentru autentificare, dar înainte de a face asta trebuie să obții Tokenul de Acces care va fi folosit pentru autentificare atunci când faci apelurile către API.
Deoarece acesta folosește OAuth versiunea 1, pentru a obține Tokenul de Acces trebuie să faci următoarele:
- Mai întâi, configurează o aplicație, fă un apel către site pentru a obține Tokenul de Cerere (credentiale temporare) folosind ID-ul Client și Secretul pentru aplicație
- În al doilea rând, fă un apel către site pentru a Autoriza aplicația cu Tokenul de Cerere din primul pas (interfață utilizator, vezi mai jos).
- În al treilea rând, după ce autorizarea a fost finalizată, faci un apel către site pentru a obține Tokenul de Acces (acum că aplicația a fost autorizată)
Recomand să folosești Postman pentru primii pași, deoarece aceștia trebuie finalizați doar o singură dată. Postman va gestiona și generarea timestamp
, nonce
și oauth signature
, așa că dacă nu folosești o bibliotecă OAuth, atunci ar trebui să folosești Postman. Odată ce ai Tokenul de Acces poți face apelurile prin CURL fără nicio bibliotecă.
Primul Pas (configurarea aplicației)
Instalează pluginul WP OAuth 1, activează-l, apoi mergi la elementul din meniu Utilizatori > Aplicații. Adaugă o nouă aplicație, completează numele și descrierea. Pentru callback fie URL-ul pentru redirecționarea utilizatorului (după autorizare), fie oop
pentru fluxul Out-of-Band care va redirecționa către o pagină internă care afișează tokenul de verificare (în loc să redirecționeze).
https://github.com/WP-API/OAuth1/blob/master/docs/basics/Registering.md
Pentru a trece la al doilea pas, trebuie făcut un apel către site-ul tău, folosind ID-ul Client și Secretul Client din aplicația creată, pentru a obține credentiale temporare (Tokenul de Cerere).
Deschide Postman, creează un nou apel către http://website.com/oauth1/request
, apasă pe fila Authorization, selectează OAuth 1.0 din meniul derulant, introdu Client Key, Client Secret, setează metoda de semnătură la HMAC-SHA1
, activează add params to header, encode oauth signature, apoi apasă Update Request
Postman va genera automat semnătura, nonce-ul și timestamp-ul pentru tine și le va adăuga în header (le poți vizualiza sub fila Headers).
Apasă Send și ar trebui să primești un răspuns care include oauth_token
și oauth_token_secret
:
Aceste valori vor fi folosite în pasul următor pentru a autoriza aplicația sub contul tău de utilizator WordPress.
Al Doilea Pas (autorizarea aplicației)
Pasul de autorizare trebuie finalizat doar o singură dată, acest pas este orientat către utilizator și este cel cu care toată lumea este familiarizată. Acest pas este necesar pentru că folosești OAuth1, iar aplicația trebuie asociată cu un cont de utilizator WordPress. Gândește-te când un site îți permite să te autentifici cu Facebook... te redirecționează către Facebook unde te autentifici și apeși "Autorizează"... acest lucru trebuie făcut, doar prin site-ul tău WordPress.
Recomand să folosești browserul tău web pentru acest pas, deoarece poți seta ușor variabilele în URL, iar acest lucru oferă pagina "Autorizează" pentru a autoriza aplicația.
Deschide browserul tău web și tastează URL-ul către site-ul tău, astfel:
http://website.com/oauth1/authorize
Acum adaugă la acest URL, oauth_consumer_key
(ID Client), oauth_token
și oauth_token_secret
(din pasul anterior). În exemplul meu, acesta este URL-ul complet:
http://website.com/oauth1/authorize?oauth_consumer_key=TUPFNj1ZTd8u&oauth_token=J98cN81p01aqSdFd9rjkHZWI&oauth_token_secret=RkrMhw8YzXQljyh99BrNHmP7phryUvZgVObpmJtos3QExG1O
Odată ce apeși pe Autorizează, vei primi un alt ecran cu tokenul de verificare. În exemplul meu, acesta este tokenul de verificare returnat E0JnxjjYxc32fMr2AF0uWsZm
Al Treilea Pas (obținerea tokenului de acces)
Acum că am autorizat aplicația, trebuie să facem un ultim apel pentru a obține Tokenul de Autorizare care va fi folosit pentru a face toate apelurile către API. La fel ca în primul pas, voi folosi Postman (deoarece semnătura trebuie să fie HMAC-SHA1), iar acest lucru face ca acești pași să fie de 100 de ori mai ușor de finalizat.
Deschide din nou Postman și schimbă URL-ul în http://website.com/oauth1/access
Asigură-te că adaugi Tokenul și Secretul Tokenului (valorile din primul pas), apoi apasă pe Params pentru a afișa casetele de sub URL. În partea stângă tastează oauth_verifier și în partea dreaptă, introdu codul din al doilea pas, Tokenul de Verificare
Asigură-te că apeși Update Request, apoi apasă Send și ar trebui să primești un răspuns înapoi cu oauth_token
și oauth_token_secret
... acestea sunt de ce ai nevoie pentru a face apelurile către API! Aruncă-le pe cele inițiale din pasul 1, păstrează acestea în codul tău sau într-un alt loc sigur.
Poți apoi face un apel către API către site-ul tău, setând headerele cu tokenul returnat și secretul tokenului.
Poți transmite acest lucru în mai multe moduri, prin headerul Authorization, în parametrii GET sau POST (dacă este codificat ca application/x-www-form-urlencoded). Ține minte că TREBUIE să transmiți semnătura, timestamp-ul și nonce-ul. Nu mi-am dat seama cât de lung va fi acest răspuns, așa că voi actualiza mâine cu un exemplu despre cum să faci asta cu codul tău.
Recomand cu tărie instalarea Rest API log pentru a putea vizualiza jurnalul apelurilor API și a vedea ce a fost trimis, returnat etc. Acest lucru va ajuta enorm la depanare.

Știu, există multe tutoriale cu Postman sau instrumente similare, dar nu găsesc niciun tutorial care să acopere întregul proces folosind funcționalitățile CURL, adică cod PHP pur. Asta este ceea ce vreau.

@Dan9 Sincer să fiu, asta nu este chiar posibil... cel puțin nu cu OAuth1, în principal pentru că trebuie să AUTORIZI aplicația sub un cont de utilizator. Toți ceilalți pași sunt ușor de făcut cu CURL, problema este folosirea CURL pentru a te autentifica ca utilizator WordPress (ceea ce înseamnă că trebuie să stochezi credențiale în fișierul tău PHP, ceea ce NU este o idee bună), ȘI să autorizezi aplicația, ceea ce ai putea modifica în codul OAuth1, dar sincer, dacă vrei să folosești CURL pentru a face TOTUL... gândești problema greșit și ar trebui să găsești o altă soluție sau metodă.

@Dan9 cu ceea ce încerci să faci, ar trebui să folosești OAuth2 server în loc de OAuth1, în principal pentru că OAuth2 are funcționalități noi, inclusiv tipul de acordare Client Credential, care evită trecerea prin toți acești pași http://bshaffer.github.io/oauth2-server-php-docs/grant-types/client-credentials/

@Dan9 dacă ești 100% hotărât să obții ajutor pentru a face asta prin OAuth1, folosind CURL, cred că este posibil cu câteva modificări de cod, dar așa cum am menționat, asta înseamnă că trebuie să salvezi USERNAME-ul și PAROLA unui utilizator în fișierul PHP. Dacă ești de acord cu asta, dă-mi de știre și voi scrie un tutorial pentru a face asta folosind CURL, nu vreau să-mi pierd timpul scriind tutorialul dacă ai de gând să folosești OAuth2 sau nu mai ai nevoie de asta.

@Dan9 ei bine... asta e ideea... dacă ai de gând să folosești OAuth1, trebuie să asociezi un Cont de Utilizator WordPress. Practic, gândește-te la Token-ul de Acces ca la o cheie API... "Cheia API" trebuie să fie asociată cu un cont de utilizator... acum dacă folosești un cont standard pe care l-ai configurat, depinde de tine... dar oricum, când folosești OAuth1, TREBUIE să fie asociat cu un cont de utilizator, de aici și procesul lung pentru a obține token-ul de acces.

De aceea am recomandat să folosești OAuth2 pentru că poți utiliza tipul de acordare client credentials, apoi doar faci un apel CURL cu acele credențiale, și îți returnează un token de acces (fără să fie nevoie să treci prin procesul lung de autorizare). Iată toate tipurile de acordare OAuth2: http://bshaffer.github.io/oauth2-server-php-docs/overview/grant-types/

Adaug acest răspuns pentru a vă oferi ajutor în înțelegerea modului de a realiza acest lucru. După cum am menționat în comentariile mele, dacă intenționați să utilizați OAuth1, TREBUIE să-l asociați cu un cont de utilizator, nu există altă cale.
Mai întâi, trebuie să utilizați CURL pentru a vă autentifica pe site cu un nume de utilizator și parolă pentru WordPress, stocați cookie-ul pentru a-l putea utiliza în apelul CURL către OAuth (asigurați-vă că actualizați apelul CURL pentru a include cookie-ul):
https://stackoverflow.com/questions/724107/wordpress-autologin-using-curl-or-fsockopen-in-php
Apoi, efectuați apelul către OAuth folosind CURL cu ID-ul clientului și secretul clientului, pentru a obține token-ul temporar OAuth și secretul (Token de cerere)
Pentru a face acest apel (și apelul pentru a obține token-ul de acces), trebuie să configurați corect apelul CURL. Consultați sfârșitul acestui răspuns pentru cod și referințe.
După ce obțineți token-ul temporar OAuth și secretul (Token de cerere), faceți un apel CURL POST la această adresă URL a site-ului dvs.:
http://website.com/oauth1/authorize
Apoi, va trebui să extrageți toate valorile din HTML-ul returnat pentru pagina de autorizare și apoi să trimiteți propriul POST către URL-ul de acțiune al formularului.
https://stackoverflow.com/questions/35363815/how-to-get-a-value-input-from-html-returned-of-curl
Mai exact, acestea trebuie incluse în datele POST pentru a completa "autorizarea" prin trimiterea către http://domain.com/wp-login.php?action=oauth1_authorize
_wpnonce
-- Aceasta este valoarea nonce pentru formularul care urmează să fie trimis, aceasta TREBUIE extrasă din input-ul HTML și trimisă cu POST-ul dvs.consumer
-- Acesta este un input ascuns în HTML (aceasta este o referință la un ID de postare, deci trebuie extras din input-ul HTML)oauth_token
-- Acesta este un input ascuns în HTML (dar ar trebui să-l aveți deja)wp-submit
-- Aceasta trebuie setată la valoareaauthorize
Iată un exemplu de HTML generat pentru pagina de autentificare:
<form name="oauth1_authorize_form" id="oauth1_authorize_form" action="http://website.com/wp-login.php?action=oauth1_authorize" method="post">
<h2 class="login-title">Conectare My Auth</h2>
<div class="login-info">
<p>Bună <strong>admin</strong>,<br/> "Demo OAuth Meu" dorește să se conecteze la Site Exemplu.</p>
</div>
<input type="hidden" name="consumer" value="5428" /><input type="hidden" name="oauth_token" value="i1scugFXyPENniCP4kABKtGb" /><input type="hidden" id="_wpnonce" name="_wpnonce" value="ca9b267b4f" /><input type="hidden" name="_wp_http_referer" value="/wp-login.php?action=oauth1_authorize&oauth_consumer_key=TUPFNj1ZTd8u&oauth_token=i1scugFXyPENniCP4kABKtGb&oauth_token_secret=gzqW47pHG0tilFm9WT7lUgLoqN2YqS6tFFjUEiQoMgcmG2ic" /> <p class="submit">
<button type="submit" name="wp-submit" value="authorize" class="button button-primary button-large">Autorizează</button>
<button type="submit" name="wp-submit" value="cancel" class="button button-large">Anulează</button>
</p>
</form>
După ce trimiteți POST-ul cu toate aceste valori/date, acesta este HTML-ul care va fi returnat cu codul de autorizare (deci trebuie să extrageți valoarea din interiorul blocului <code>
:
<div id="login">
<h1><a href="https://wordpress.org/" title="Powered by WordPress" tabindex="-1">Site Exemplu</a></h1>
<p>Tokenul dvs. de verificare este <code>yGOYFpyawe8iZmmcizqVIw3f</code></p> <p id="backtoblog"><a href="http://website.com/">← Înapoi la Site Exemplu</a></p>
</div>
Odată ce aveți tokenul de verificare, puteți face un apel către /oauth1/access
folosind tokenul de verificare, tokenul oauth și secretul tokenului oauth. Tokenul de verificare trebuie pus în datele POST ca oauth_verifier
Aceasta va returna noul dvs. Token de acces permanent și VOILA!
Exemplu de cod CURL
Mai jos este un exemplu de cod pentru a face apelul CURL, cea mai importantă parte fiind modul în care este generat oauth_signature
:
https://oauth1.wp-api.org/docs/basics/Signing.html
function buildBaseString($baseURI, $method, $params){
$r = array();
ksort($params);
foreach($params as $key=>$value){
$r[] = "$key=" . rawurlencode($value);
}
return $method."&" . rawurlencode($baseURI) . '&' . rawurlencode(implode('&', $r));
}
function buildAuthorizationHeader($oauth){
$r = 'Authorization: OAuth ';
$values = array();
foreach($oauth as $key=>$value)
$values[] = "$key=\"" . rawurlencode($value) . "\"";
$r .= implode(', ', $values);
return $r;
}
// Adăugați request, authorize, etc. la sfârșitul URL-ului în funcție de apelul pe care îl faceți
$url = "http://domain.com/oauth/";
$consumer_key = "ID CLIENT AICI";
$consumer_secret = "SECRET CLIENT AICI";
$oauth = array( 'oauth_consumer_key' => $consumer_key,
'oauth_nonce' => time(),
'oauth_signature_method' => 'HMAC-SHA1',
'oauth_callback' => 'oob',
'oauth_timestamp' => time(),
'oauth_version' => '1.0');
$base_info = buildBaseString($url, 'GET', $oauth);
$composite_key = rawurlencode($consumer_secret) . '&' . rawurlencode($oauth_access_token_secret);
$oauth_signature = base64_encode(hash_hmac('sha1', $base_info, $composite_key, true));
$oauth['oauth_signature'] = $oauth_signature;
$header = array(buildAuthorizationHeader($oauth), 'Expect:');
$options = array( CURLOPT_HTTPHEADER => $header,
CURLOPT_HEADER => false,
CURLOPT_URL => $url,
CURLOPT_RETURNTRANSFER => true,
CURLOPT_SSL_VERIFYPEER => false);
$feed = curl_init();
curl_setopt_array($feed, $options);
$json = curl_exec($feed);
curl_close($feed);
$return_data = json_decode($json);
print_r($return_data);
Acest site explică exact cum să codificați semnătura OAuth și cum să trimiteți folosind CURL (recomand citirea întregii pagini): https://hannah.wf/twitter-oauth-simple-curl-requests-for-your-own-data/
Mai multe resurse despre generarea semnăturii OAuth1: https://stackoverflow.com/questions/24613277/oauth-signature-generation-using-hmac-sha1
Alte resurse: http://collaboradev.com/2011/04/01/twitter-oauth-php-tutorial/

Cum pot obține Client ID și Client secret și să le asociez cu un utilizator valid? În prezent, doar administratorii pot crea o aplicație nouă și acest lucru se întâmplă doar prin panoul de administrare. Apropo, am încercat să generez oauth_signature
cum mi-ai spus, dar, cumva, răspunsul este întotdeauna json_oauth1_signature_mismatch
.

@Dan9 da, așa este, administratorii trebuie să creeze aplicația, altfel ar fi o problemă majoră de securitate să permiti crearea de aplicații de către utilizatori anonimi. Iată câteva site-uri despre semnătură http://wordpress.stackexchange.com/questions/185511/oauth-signature-does-not-match https://github.com/WP-API/OAuth1/issues/34 https://github.com/WP-API/OAuth1/issues/27

Știu că vin puțin târziu la discuție, dar poți folosi wp_remote_get și _post?
Eu trag și postez conținut cu instalarea mea WordPress folosind aceste funcții:
Aceasta este ideea generală din codex-ul WordPress:
$response = wp_remote_post( $url, array(
'body' => $data,
'httpversion' => '1.0',
'sslverify' => false,
'headers' => array(
'Authorization' => 'Basic ' . base64_encode( $username . ':' . $password ),
),
) );
Iată un exemplu mai specific:
$url='http://WWW.EXEMPLU AICI.';
$response = wp_remote_post( $url, array(
'method' => 'POST',
'timeout' => 45,
'redirection' => 5,
'httpversion' => '1.0', //necesar pentru a primi un răspuns
'blocking' => true,
'headers' => array('Authorization' => 'Basic ' . base64_encode( 'TOKENUL MEU' . ':' . '' )),
'body' => $body // în array
'cookies' => array()
)
);
if ( is_wp_error( $response ) ) {
$error_message = $response->get_error_message();
echo "Ceva nu a funcționat: $error_message";
} else {
// echo 'Răspuns:<pre>';
// print_r( $response );
// echo '</pre>';
$responseBody = json_decode($response['body'],true);
echo $responseBody['message'];
}
}
}
Trucul este codificarea numelui de utilizator și parolei. Adesea, în funcție de API, numele de utilizator și parola vor fi fie goale, fie vor fi tokenurile tale.
De exemplu, în cazul meu specific de mai sus, antetele erau
'headers' => array('Authorization' => 'Basic ' . base64_encode( 'TOKENULMEU' . ':' . '' ))
și am lăsat parola goală. Dar asta depinde de sistemul API pe care îl folosești.

Actualizare: Din ce am citit, trebuie să faci mai multe cereri curl pentru a obține access_token, pe care apoi îl folosești pentru interogare
- Obținerea Credențialelor Temporare: Clientul primește un set de credențiale temporare de la server.
- Autorizare: Utilizatorul "autorizează" token-ul de cerere pentru a accesa contul său.
- Schimb de Token: Clientul schimbă credențialele temporare pe termen scurt pentru un token pe termen lung.
