CURL in PHP does not send a POST query - php

I am trying to send a POST query to a web-page, but unfortunately it does not work. Below is my code:
<?php
$url_ref = "http://www.wunschgrundstueck.de/immobilien/wohnung-suchen.html?sp_was=wohnungen_m&lses=1";
$url = "http://www.wunschgrundstueck.de/immobilien/suchergebnis/wohnungen.html";
$fields = array(
'id_land' => 'DEU',
'id_bundesland' => '7',
'id_landkreis'=> '186',
'id_gemeinde'=>'5234',
'su_anb' => '0',
'sp_was' => 'wohnungen_m',
'sp_wo' => 'Frankfurt am Main',
'sp_ort_land' => 'DEU',
'sp_ort_bula' => '7',
'sp_ort_lakr' => '186',
'sp_ort_geme' => '5234',
'sp_ort_teil' => '0',
'sp_ort_umkreis' => '0',
'miete' => 'on',
'su_wohn_preis_miete_art' => '1',
);
$fields_string;
//url-ify the data for the POST
foreach($fields as $key=>$value) { $fields_string .= $key.'='.$value.'&'; }
rtrim($fields_string,'&');
echo $fields_string;
//open connection
$curl = curl_init($url);
curl_setopt($curl, CURLOPT_POST, true);
curl_setopt($curl, CURLOPT_HEADER, 0);
curl_setopt($curl, CURLOPT_REFERER, $url_ref);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($curl, CURLOPT_FOLLOWLOCATION, 1);
curl_setopt($curl, CURLOPT_AUTOREFERER, true);
curl_setopt($curl,CURLOPT_USERAGENT,'Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.17 (KHTML, like Gecko) Chrome/24.0.1312.52 Safari/537.17');
curl_setopt($curl,CURLOPT_POST,count($fields));
curl_setopt($curl,CURLOPT_POSTFIELDS,$fields_string);
$result = curl_exec($curl);
?>
Unfortunately, it seems that I do something wrong because the result that is returned is not the one I am expecting. What puzzles me a lot is that if I send the same request using the LiveHTTP headers plugin for firefox then I get the correct result. I then tried to send the request with WFetch, and then I receive a 301 Moved permanently error. This is the HTTP Post headers/fields that I tested with HTTPLive from firefox where it works correctly and with WFetch where I get the 301 error.
Host: www.wunschgrundstueck.de\r\n
User-Agent: Mozilla/5.0 (Windows NT 6.1; WOW64; rv:26.0) Gecko/20100101 Firefox/26.0\r\n
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8\r\n
Accept-Language: de-de,de;q=0.8,en-us;q=0.5,en;q=0.3\r\n
Accept-Encoding: gzip, deflate\r\n
Referer: http://www.wunschgrundstueck.de/immobilien/landkreis_frankfurt_am_main/wohnungen.html?s=1\r\n
Connection: keep-alive\r\n
Content-Type: application/x-www-form-urlencoded\r\n
\r\n
id_land=DEU&id_bundesland=7&id_landkreis=186&id_gemeinde=&id_ortsteil=&gemeid_bereich=&su_suchart=erweitert&su_anb=0&sp_was=wohnungen&sp_wo=&sp_ort_land=DEU&sp_ort_bula=7&sp_ort_lakr=186&sp_ort_geme=0&sp_ort_teil=0&sp_wo_ausl=&miete=on&su_wohnfl_wohn_von=&su_wohnfl_wohn_bis=&su_wohn_preis_von_kauf=&su_wohn_preis_bis_kauf=&su_wohn_preis_miete_art=1&su_wohn_preis_von_miete=&su_wohn_preis_bis_miete=&su_zimmer_wohn_anz_von=&su_zimmer_wohn_anz_bis=&su_filter_wohntyp=&su_wohn_etage_von=&su_wohn_etage_bis=&su_wohn_filter_anzbad=&su_wohn_filter_anzschlaf=&su_wohn_filter_baf_det=&su_wohn_filter_moebliert=&submit=Ergebnisse+zeigen+%BB\r\n
\r\n

I don't see you urlencode the key-value pairs you assembly $fields_string from. This might be the reason why you're not getting expected results as some fields have spaces that need to be urlencoded.
That said, you don't need to assembly the post data manually, curl will do that for you if provided an array:
curl_setopt($curl, CURLOPT_POSTFIELDS, $fields);
On a sidenote: 301 is not an error; it's a redirection code, which WFetch doesn't follow automatically, while your browser does.

Related

PHP Setting custom header starting with ':'

I need to setup some custom headers start with ":".
$option['headers'][] = ":authority: example.com"; //<-- Here is the problem
$option['headers'][] = "accept-encoding: gzip, deflate, br";
$option['post'] = json_encode(array("Domain"=>"example.com"));
$url = "https://www.google.com";
$ch = curl_init($url);
curl_setopt($ch,CURLOPT_USERAGENT, "Mozilla/5.0 (Windows NT 6.1; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/62.0.3202.62 Safari/537.36");
curl_setopt($ch,CURLOPT_FOLLOWLOCATION,1);
curl_setopt($ch,CURLOPT_COOKIEFILE,"file.cookie");
curl_setopt($ch,CURLOPT_COOKIEJAR,"file.cookie");
curl_setopt($ch,CURLOPT_SSL_VERIFYHOST, 0);
curl_setopt($ch,CURLOPT_SSL_VERIFYPEER, 0);
curl_setopt($ch,CURLOPT_HEADER,0);
curl_setopt($ch,CURLOPT_VERBOSE, true);
curl_setopt($ch,CURLOPT_RETURNTRANSFER,1);
curl_setopt($ch, CURLOPT_POST, 1);
curl_setopt($ch, CURLOPT_POSTFIELDS, $option['post']);
curl_setopt($ch, CURLOPT_HTTPHEADER, $option['headers']);
$getdata = curl_exec($ch);
I try to replace the ":" with chr(58) but same problem. I get error 55 and from log "* Failed sending HTTP POST request". If I comment first line is working, but I really need that header. I'm stuck here. Any solutions?
:authority: looks like an HTTP/2 psuedo header, and you can't set them like this with curl. curl will however pass it on itself and it will use the same content as it would set for Host: to make it work the same way, independently of which HTTP version that is eventually used (it will also work with HTTP/3).

cURL ignores CURLOPT_HTTPHEADER

Okay, i have some website which i should parse...
Firstly, i open debugger in Firefox hitting F12, and look at Network tab, then enter needed website, and reading first root GET request, like
Doman => website.com
File => /
I get there all the request headers and write them into php array manually, then in code i call
curl_setopt($curl, CURLOPT_HTTPHEADER, $headerArray);
and also other options, then call
curl_exec();
while inspecting the Network tab in Firefox, i see that request headers are maybe such as default, and no specific headers written manually into array were sent. Similar problem with CURLOPT_COOKIEFILE and CURLOPT_COOKIEJAR, cookies are just written to cookie file on server, but in fact, there are another cookies in next request instead of previously saved in cookies file.
Actual request headers in browser's inspector:
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Encoding: gzip, deflate
Accept-Language: ru-RU,ru;q=0.8,en-US;q=0.5,en;q=0.3
Cache-Control: max-age=0
Connection: keep-alive
Cookie: _ga=GA1.1.1951751996.1563984714; _gid=GA1.1.1564173251.1563984714; _userGUID=0:jyhg490v:AIQdD2Qpm9rmbla1U93mK2a45CFRe49c; jv_enter_ts_2VumZAPpbr=1563984717382; jv_visits_count_2VumZAPpbr=1; .....
Host: localhost
Upgrade-Insecure-Requests: 1
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:68.0) Gecko/20100101 Firefox/68.0
PHP Code:
<?php
$headers = ['Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8',
'Accept-Language: ru-RU,ru;q=0.8,en-US;q=0.5,en;q=0.3',
'Cache-Control: max-age=0',
'Connection: keep-alive',
'Cookie: visid_incap_1987259....,
'Host: website.com',
'TE: Trailers',
'Upgrade-Insecure-Requests: 1',
'User-Agent: Mozilla/5.0 (compatible; Googlebot/2.1; +http://www.google.com/bot.html)'];
$curl = curl_init("https://www.website.com/");
curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false);
curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, false);
curl_setopt($curl, CURLOPT_HTTPHEADER, $headers);
curl_setopt($curl, CURLOPT_COOKIEFILE, dirname(__FILE__)."/cookies.txt");
curl_setopt($curl, CURLOPT_COOKIEJAR, dirname(__FILE__)."/cookies.txt");
echo curl_exec($curl);
?>
You will not be able to see the headers send CURL in the Browser Dev Tools. All requests are executed on the server side. Your headers are sent successfully. You can check it out like this:
curl_setopt($curl, CURLINFO_HEADER_OUT, true);
$sentHeaders = curl_getinfo($curl, CURLINFO_HEADER_OUT);
print_r($sentHeaders);

How to work with file_get_contents for m3u8 file?

I wrote a PHP code that sends 3 GET Requests, one after the other
The purpose of the code is to get the content from the m3u8 file,
But in the last GET Request I get an error.
PHP:
<?php
//1. Create a proper token for the m3u8 to work
$opts = array(
'http'=>array(
'method'=>"GET",
'header'=>"Referer: http://www.hotstar.com",
"User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:51.0) Gecko/20100101 Firefox/51.0"
));
$context = stream_context_create($opts);
$url = "http://www.hotstar.com/get_cdn_token.php";
$data = file_get_contents($url, false, $context);
$values = json_decode($data, true);
$url = $values['token'];
//2. Send another GET request along with the token, to pull the master m3u8
$opts = array(
'http'=>array(
'method'=>"GET",
'header'=>"Referer: http://www.hotstar.com",
"User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:51.0) Gecko/20100101 Firefox/51.0"
));
$context = stream_context_create($opts);
$url = "https://secure-getcdn.hotstar.com/AVS/besc?hotstarauth=$url&action=GetCDN&appVersion=5.0.40&asJson=Y&channel=TABLET&id=1000055355&type=VOD";
$data = file_get_contents($url, false, $context);
$values = json_decode($data, true);
$link = $values['resultObj']['src'];
//3. Get the m3u8 content
$opts = array(
'http'=>array(
'method'=>"GET",
'header'=>"User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:51.0) Gecko/20100101 Firefox/51.0"
));
$context = stream_context_create($opts);
$url = "$link";
$data = file_get_contents($url, false, $context);
echo $data;
Through Inspect Element I accept the result:
#EXTM3U
#EXT-X-STREAM-INF:PROGRAM-ID=1,BANDWIDTH=241000,RESOLUTION=320x180,CODECS="avc1.66.30, mp4a.40.2",CLOSED-CAPTIONS=NONE
https://staragvod1-vh.akamaihd.net/i/videos/plus/sns/1365/1000055355_,16,180,400,800,1300,2000,3000,4500,_STAR.mp4.csmil/index_1_av.m3u8?null=0&id=AgC0lfI2aGb2DFFZW1pBPartIAq++S+ee++3UM8jU49rfzGeMpTl2IaWB4PCyZ0c2yGZOtSqAhal4g%3d%3d
#EXT-X-STREAM-INF:PROGRAM-ID=1,BANDWIDTH=461000,RESOLUTION=416x234,CODECS="avc1.66.30, mp4a.40.2",CLOSED-CAPTIONS=NONE
https://staragvod1-vh.akamaihd.net/i/videos/plus/sns/1365/1000055355_,16,180,400,800,1300,2000,3000,4500,_STAR.mp4.csmil/index_2_av.m3u8?null=0&id=AgC0lfI2aGb2DFFZW1pBPartIAq++S+ee++3UM8jU49rfzGeMpTl2IaWB4PCyZ0c2yGZOtSqAhal4g%3d%3d
#EXT-X-STREAM-INF:PROGRAM-ID=1,BANDWIDTH=861000,RESOLUTION=640x360,CODECS="avc1.66.30, mp4a.40.2",CLOSED-CAPTIONS=NONE
https://staragvod1-vh.akamaihd.net/i/videos/plus/sns/1365/1000055355_,16,180,400,800,1300,2000,3000,4500,_STAR.mp4.csmil/index_3_av.m3u8?null=0&id=AgC0lfI2aGb2DFFZW1pBPartIAq++S+ee++3UM8jU49rfzGeMpTl2IaWB4PCyZ0c2yGZOtSqAhal4g%3d%3d
#EXT-X-STREAM-INF:PROGRAM-ID=1,BANDWIDTH=1360000,RESOLUTION=720x404,CODECS="avc1.66.30, mp4a.40.2",CLOSED-CAPTIONS=NONE
https://staragvod1-vh.akamaihd.net/i/videos/plus/sns/1365/1000055355_,16,180,400,800,1300,2000,3000,4500,_STAR.mp4.csmil/index_4_av.m3u8?null=0&id=AgC0lfI2aGb2DFFZW1pBPartIAq++S+ee++3UM8jU49rfzGeMpTl2IaWB4PCyZ0c2yGZOtSqAhal4g%3d%3d
#EXT-X-STREAM-INF:PROGRAM-ID=1,BANDWIDTH=2060000,RESOLUTION=1280x720,CODECS="avc1.77.30, mp4a.40.2",CLOSED-CAPTIONS=NONE
https://staragvod1-vh.akamaihd.net/i/videos/plus/sns/1365/1000055355_,16,180,400,800,1300,2000,3000,4500,_STAR.mp4.csmil/index_5_av.m3u8?null=0&id=AgC0lfI2aGb2DFFZW1pBPartIAq++S+ee++3UM8jU49rfzGeMpTl2IaWB4PCyZ0c2yGZOtSqAhal4g%3d%3d
#EXT-X-STREAM-INF:PROGRAM-ID=1,BANDWIDTH=3060000,RESOLUTION=1600x900,CODECS="avc1.77.30, mp4a.40.2",CLOSED-CAPTIONS=NONE
https://staragvod1-vh.akamaihd.net/i/videos/plus/sns/1365/1000055355_,16,180,400,800,1300,2000,3000,4500,_STAR.mp4.csmil/index_6_av.m3u8?null=0&id=AgC0lfI2aGb2DFFZW1pBPartIAq++S+ee++3UM8jU49rfzGeMpTl2IaWB4PCyZ0c2yGZOtSqAhal4g%3d%3d
#EXT-X-STREAM-INF:PROGRAM-ID=1,BANDWIDTH=4562000,RESOLUTION=1920x1080,CODECS="avc1.77.30, mp4a.40.2",CLOSED-CAPTIONS=NONE
https://staragvod1-vh.akamaihd.net/i/videos/plus/sns/1365/1000055355_,16,180,400,800,1300,2000,3000,4500,_STAR.mp4.csmil/index_7_av.m3u8?null=0&id=AgC0lfI2aGb2DFFZW1pBPartIAq++S+ee++3UM8jU49rfzGeMpTl2IaWB4PCyZ0c2yGZOtSqAhal4g%3d%3d
Through PHP I get the error:
Warning: file_get_contents(https://staragvod1-vh.akamaihd.net/i/videos/plus/sns/1365/1000055355_,16,180,400,800,1300,2000,3000,4500,_STAR.mp4.csmil/master.m3u8?hdnea=st=1515937603~exp=1515938203~acl=/*~hmac=c5f9294a198233a9751edbca51631c9cb12db63a08a69499c20d1208bd07aca8): failed to open stream: HTTP request failed! HTTP/1.0 403 Forbidden in **** on line 37
How do I arrange this please?
Your file needs a login to be accessed, for that you need a cookie mechanism on your file. This can be done with php-curl, or with curl alone in the shell.
Here is a php-curl snippet that can help you on this case.
There is more to do with curl. Anyway, the system needs an additional php package for this to works.
sudo apt install php-curl
$handle = curl_init();
$url = "https//lalala.com/file/files/oups.m3u";
$domain = preg_replace("(^https?://)", "", $url );
$header = array('Accept-Language: fr,fr-fr;q=0.8,en-us;q=0.5,en;q=0.3');
curl_setopt($handle, CURLOPT_URL, $url);
curl_setopt($handle, CURLINFO_HEADER_OUT, 1);
curl_setopt($handle, CURLOPT_USERAGENT, 'Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:55.0) Gecko/20100101 Firefox/55.0.1');
curl_setopt($handle, CURLOPT_FOLLOWLOCATION, false);
curl_setopt($handle, CURLOPT_NOSIGNAL, true);
curl_setopt($handle, CURLOPT_RETURNTRANSFER, false);
curl_setopt($handle, CURLOPT_HTTPHEADER, $header);
curl_setopt($handle, CURLOPT_HEADER, false);
header('Content-Type: text/html');
header("Access-Control-Allow-Origin: *");
$result = curl_exec($handle);
var_dump($result);
See https://curl.haxx.se/libcurl/c/CURLOPT_USERAGENT.html for more details about php-curl.
See https://curl.haxx.se/libcurl/c/CURLOPT_COOKIE.html for how to setup cookies.

curl fail when request in server

I have 1 REST api :
http://www.animemobile.com/service/v2/mobile2.php?episode_id=47272
I use curl to request it, in my PC with xampp, it works well and returns the correct results. This is results from my PC with xampp:
[
{
"Title":"English Subbed",
"link":"\/[HorribleSubs] Pascal-sensei - 01 [720p]_af.mp4?
st=14GwNjlMxuI8524DS56IUA&e=1495183034"
}
]
I use
/[HorribleSubs] Pascal-sensei - 01 [720p]_af.mp4?
st=14GwNjlMxuI8524DS56IUA&e=1495183034
to create a link as:
http://st2.anime1.com/[HorribleSubs]%20Pascal-sensei%20-
%2001%20[720p]_af.mp4?st=14GwNjlMxuI8524DS56IUA&e=1495183034.
This link is a video that can be played when request from browser (now).
But when I use the curl in my SERVER, it still works well but does not return the correct results. This is results from my Server:
[
{
"Title":"English Subbed",
"link":"\/[HorribleSubs] Pascal-sensei - 01 [720p]_af.mp4?
st=ghDP4290fsBNdmfsSKCD=1495195645"
}
]
When I use
/[HorribleSubs] Pascal-sensei - 01 [720p]_af.mp4?
st=ghDP4290fsBNdmfsSKCD=1495195645
to create a link as:
http://st2.anime1.com/[HorribleSubs]%20Pascal-sensei%20-
%2001%20[720p]_af.mp4?%20st=ghDP4290fsBNdmfsSKCD=1495195645.
It doesn't play on my browser.
This is my curl:
$c = curl_init();
curl_setopt($c, CURLOPT_URL, $url);
curl_setopt($c, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($c, CURLOPT_ENCODING, 'gzip,deflate');
curl_setopt($c, CURLINFO_HEADER_OUT, true);
$headers = [
'Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8',
'Accept-Encoding: gzip, deflate, sdch',
'Accept-Language: vi,en-US;q=0.8,en;q=0.6',
'Cache-Control: max-age=0',
'Connection: keep-alive',
'Cookie: __cfduid=d7bf11c717fbcd54ec9b259e301a966d71480412679',
'Host: www.animemobile.com',
'Upgrade-Insecure-Requests: 1',
'User-Agent: Mozilla/5.0 (Windows NT 6.3; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/58.0.3029.110 Safari/537.36'
];
curl_setopt($c, CURLOPT_HTTPHEADER, $headers);
$data = curl_exec($c);
What is the problem here? Please help me!
Edit1: If you want to test the results, you need to request the REST-api again because it had limited time for link to be created. Important that request the REST-api on PC returns correct results but request from server returns wrong results although they look very similar!

Pinterest login with PHP and cURL not working

I have been trying to make cURL login into pinterest.com for the last 17 hours straight, have tried countless and countless different ways just with cURL but it does not work at all.
My current code only goes to the page but the data is not posted, so it does not login just takes me to the login page.
This first code is using USERPWD which is where it takes me to the login page but it does not login.
error_reporting(E_ALL);
ini_set("display_errors", 1);
$url = "https://www.pinterest.com/login/";
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_USERAGENT, "Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.8.1.6) Gecko/20070725 Firefox/2.0.0.6");
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, 0);
curl_setopt($ch, CURLOPT_AUTOREFERER, 1);
curl_setopt($ch, CURLOPT_MAXREDIRS, 5);
curl_setopt($ch, CURLOPT_CONNECTTIMEOUT, 10);
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false); // allow https verification if true
curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, 2); // check common name and verify with host name
curl_setopt($ch, CURLOPT_SSLVERSION,3); //
curl_setopt($ch, CURLOPT_CAINFO, getcwd() . "pin.pem"); // allow ssl cert direct comparison
curl_setopt($ch, CURLOPT_COOKIESESSION, TRUE); // set new cookie session
curl_setopt($ch, CURLOPT_COOKIEJAR, "cookies.txt");
curl_setopt($ch, CURLOPT_COOKIEFILE, "cookies.txt");
curl_setopt($ch, CURLOPT_USERPWD, "email:password");
curl_setopt($ch, CURLOPT_SSLVERSION,3);
// grab URL and pass it to the browser
curl_exec($ch);
// close cURL connection, save cookie file, free up system resources
curl_close($ch);
and if I switch it from CURLOPT_USERPWD to
curl_setopt($ch, CURLOPT_POSTFIELDS, 'username_or_email=$email&password=$password');
it just displays a blank page.
The pin.pem is the X.509 Certificate (PEM) file.
Any direction to make this work would be greatly appreciated it.
Edit
new code but leaves blank page and I got the output with a few arrays and displays this:
Array ( [url] => https://www.pinterest.com/login/ [content_type] => [http_code] => 0 [header_size] => 0 [request_size] => 0 [filetime] => -1 [ssl_verify_result] => 0 [redirect_count] => 0 [total_time] => 0.036169 [namelookup_time] => 3.3E-5 [connect_time] => 0.036186 [pretransfer_time] => 0 [size_upload] => 0 [size_download] => 0 [speed_download] => 0 [speed_upload] => 0 [download_content_length] => -1 [upload_content_length] => -1 [starttransfer_time] => 0 [redirect_time] => 0 [certinfo] => Array ( ) [redirect_url] => )
error_reporting(E_ALL);
ini_set("display_errors", 1);
$email = 'email';
$password = 'password';
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, 'https://www.pinterest.com/login/');
curl_setopt($ch, CURLOPT_USERAGENT, 'Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.8.1.6) Gecko/20070725 Firefox/2.0.0.6');
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, 0);
curl_setopt($ch, CURLOPT_AUTOREFERER, 1);
curl_setopt($ch, CURLOPT_MAXREDIRS, 5);
curl_setopt($ch, CURLOPT_CONNECTTIMEOUT, 10);
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, TRUE);
curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, 2);
curl_setopt($ch, CURLOPT_SSLVERSION,3); //
curl_setopt($ch, CURLOPT_CAINFO, getcwd() . 'pin.pem');
curl_setopt($ch, CURLOPT_COOKIESESSION, TRUE);
curl_setopt($ch, CURLOPT_COOKIEJAR, 'cookies.txt');
curl_setopt($ch, CURLOPT_COOKIEFILE, 'cookies.txt');
curl_setopt($ch, CURLOPT_POSTFIELDS, 'username_or_email=$email&password=$password');
curl_setopt($ch, CURLOPT_SSLVERSION,3);
curl_exec($ch);
$output=#curl_exec($ch);
$info = #curl_getinfo($ch);
echo $output;
print_r($info);
curl_close($ch);
The Pinterest login process isn't quite that simple. They use a CSRF token which you must extract and send with your login, along with the username and password in the POST body.
Here is what an actual login request to Pinterest looks like, so you will need to emulate this with cURL.
POST /resource/UserSessionResource/create/ HTTP/1.1
Host: www.pinterest.com
User-Agent: Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:28.0) Gecko/20100101 Firefox/28.0
Accept: application/json, text/javascript, */*; q=0.01
Accept-Language: en-US,en;q=0.5
Accept-Encoding: gzip, deflate
DNT: 1
Content-Type: application/x-www-form-urlencoded; charset=UTF-8
X-CSRFToken: 2rjgN4Qv67pN4wX91kTr4eIkgF54CzJH
X-NEW-APP: 1
X-APP-VERSION: 737af79
X-Requested-With: XMLHttpRequest
Referer: https://www.pinterest.com/login/
Content-Length: 300
Cookie: csrftoken=2rjgN4Qv67pN4wX91kTr4eIkgF54CzJH; _pinterest_sess="aPgJnrIBzvSKLUY/4H5UocshliA47GkkGtHLQwo1H4IcQv58vrdazclonByOb4fWCzb3a3nycKjQzDc6SkCB9eBKoejaLiCjkKLk/QAFRn2x1pvHFlFM+1EoD01/yFxmeQKlvULYU9+qf4D6Mkj8A=="; _track_cm=1;
Connection: keep-alive
Pragma: no-cache
Cache-Control: no-cache
source_url=%2Flogin%2F&data=%7B%22options%22%3A%7B%22username_or_email%22%3A%22YOU%40YOUROMAIN.COM%22%2C%22password%22%3A%22YOURPASSWORD%22%7D%2C%22context%22%3A%7B%7D%7D&module_path=App()%3ELoginPage()%3ELogin()%3EButton(class_name%3Dprimary%2C+text%3DLog+In%2C+type%3Dsubmit%2C+size%3Dlarge)
The source_url data in the request is the POST body (urlencoded). Take note that username_or_email is your login (I put YOU%40YOURDOMAIN.COM) and password is the password.
What you will have to do is make a GET request to /login/ to establish a session and cookies in the cURL session. Then using the same cURL handle, you can switch to a POST request, set CURLOPT_POSTFIELDS with the data from the source_url...... line.
You will probably also need to set the headers X-CSRFToken, X-NEW-APP, X-APP-VERSION, and X-Requested-With to match the above (except you will need to figure out how to get the correct CSRF Token value).
Unfortunately I don't have the time right now to make a working example, the next paragraph may help. You will need to use your browser to help you debug some of the HTTP requests to figure out all the requests you may need to make to get all the relevant data for your request.
If you check out this answer it shows curl login with PHP and links to a number of useful other related answers with examples.
EDIT:
Here is a working example of using PHP and cURL to log in to Pinterest.
This code is a Pinterest PHP login example (works as of 2014-05-11]. You may ask yourself, can what I want to do be done with the API instead of this hackish code which could break at any time???
As you can see I parse the CSRF_Token out of the headers, you should probably do this for the APP-VERSION as well since it can update almost daily. Right now it's hard coded.
<?php
error_reporting(E_ALL);
ini_set('display_errors', 1);
$username = 'you#yoursite.com'; // your username
$password = 'yourpassword'; // your password
// this is the http post data for logging in - username & password are substituted in later
$login_post = array(
'source_url' => '/login/',
'data' => '{"options":{"username_or_email":"%s","password":"%s"},"context":{}}',
'module_path' => 'App()>LoginPage()>Login()>Button(class_name=primary, text=Log In, type=submit, size=large',
);
$pinterest_url = 'https://www.pinterest.com/'; // pinterest home url
$login_url = $pinterest_url . 'login/'; // pinterest login page url
$login_post_url = $pinterest_url . 'resource/UserSessionResource/create/'; // pinterest login post url
// http headers to send with requests
$httpheaders = array(
'Connection: keep-alive',
'Pragma: no-cache',
'Cache-Control: no-cache',
'Accept-Language: en-US,en;q=0.5',
);
// http headers to send when logging in
$login_header = array(
'X-NEW-APP: 1',
'X-APP-VERSION: d2bb370', // THIS WILL UPDATE FREQUENTLY, CHANGE IT!!!
'X-Requested-With: XMLHttpRequest',
'Accept: application/json, text/javascript, */*; q=0.01');
// ----------------------------------------------------------------------------
// request home page to establish cookies and a session, set curl options
$ch = curl_init($pinterest_url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, 1);
curl_setopt($ch, CURLOPT_AUTOREFERER, 1);
curl_setopt($ch, CURLOPT_ENCODING, 'gzip,deflate');
curl_setopt($ch, CURLOPT_USERAGENT, 'Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Iron/31.0.1700.0 Chrome/31.0.1700.0');
curl_setopt($ch, CURLOPT_COOKIEFILE, 'cookie.txt');
curl_setopt($ch, CURLOPT_COOKIEJAR, 'cookie.txt');
curl_setopt($ch, CURLOPT_VERBOSE, 1);
curl_setopt($ch, CURLOPT_STDERR, fopen('/tmp/debug.txt', 'w+'));
curl_setopt($ch, CURLOPT_HEADER, 1);
curl_setopt($ch, CURLOPT_HTTPHEADER, $httpheaders);
$data = curl_exec($ch);
// ----------------------------------------------------------------------------
// parse the csrf token out of the cookies to set later when logging in
list($headers, $body) = explode("\r\n\r\n", $data, 2);
preg_match('/csrftoken=(.*?)[\b;\s]/i', $headers, $csrf_token);
// next request the login page
curl_setopt($ch, CURLOPT_URL, $login_url);
$data = curl_exec($ch);
// ----------------------------------------------------------------------------
// perform login post
$login_header[] = 'X-CSRFToken: ' . $csrf_token[1];
$login_post['data'] = sprintf($login_post['data'], $username, $password);
$post = http_build_query($login_post);
curl_setopt($ch, CURLOPT_URL, $login_post_url);
curl_setopt($ch, CURLOPT_POST, 1);
curl_setopt($ch, CURLOPT_POSTFIELDS, $post);
curl_setopt($ch, CURLOPT_HTTPHEADER, array_merge($httpheaders, $login_header));
curl_setopt($ch, CURLOPT_REFERER, $login_url);
curl_setopt($ch, CURLOPT_HEADER, 0);
$data = curl_exec($ch);
// check response and output status
if (curl_getinfo($ch, CURLINFO_HTTP_CODE) != 200) {
echo "Error logging in.<br />";
var_dump(curl_getinfo($ch));
} else {
$response = json_decode($data, true);
if ($response === null) {
echo "Failed to decode JSON response.<br /><br />";
var_dump($response);
} else if ($response['resource_response']['error'] === null) {
echo "Login successful, " . $response['resource_response']['data']['username'] . "<br /><br />";
echo "You have {$response['resource_response']['data']['follower_count']} followers, are following {$response['resource_response']['data']['following_count']} users. You have liked {$response['resource_response']['data']['like_count']} pins.";
}
}
My output:
Login successful, drew010
You have 0 followers, are following 0 users. You have liked 0 pins.
FYI, Pinterest has login rate limit so don't run this before every request.
Here is my Ruby implementation of the Pinterest login/session mechanism.
Run this once a day to save the headers (including csrftoken). Then use the saved headers to do requests that are not (yet) supported by the api (like ads reports).
class PinterestHeadersScheduler
include Sidekiq::Worker
sidekiq_options queue: :recurring, retry: 0
HOMEPAGE = 'https://ads.pinterest.com/'
LOGIN_URL = "#{HOMEPAGE}login/"
SESSION_URL = "#{HOMEPAGE}resource/UserSessionResource/create/"
LOGIN_DATA = {
source_url: '/login/',
data: { options: { username_or_email: ENV['PI_USERNAME'], password: ENV['PI_PASSWORD'] }, context: {} }.to_json
}
HEADERS = {
'Accept': 'application/json,text/html,image/webp,image/apng,*/*;q=0.8',
'Origin': 'https://ads.pinterest.com',
'Referer': 'https://ads.pinterest.com/',
'User-Agent': 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_13_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/79.0.3945.88 Safari/537.36',
'Connection': 'keep-alive',
'Cache-Control': 'no-cache',
'Accept-Charset': 'utf-8;ISO-8859-1q=0.7,*;q=0.7',
'Accept-Encoding': 'gzip, deflate',
'Accept-Language': 'en-US,en;q=0.8'
}
SESSION_HEADERS = HEADERS.merge({
'Accept': 'application/json',
'Content-Type': 'application/x-www-form-urlencoded; charset=UTF-8',
'X-Requested-With': 'XMLHttpRequest'
})
def perform
login = HTTParty.get(LOGIN_URL, { headers: HEADERS })
cjar = login.get_fields('Set-Cookie').each_with_object(HTTParty::CookieHash.new) { |cookie, jar| jar.add_cookies(cookie) }
headers = SESSION_HEADERS.merge({ 'Cookie': cjar.to_cookie_string, 'X-CSRFToken': cjar[:csrftoken] })
res = HTTParty.post(SESSION_URL, { headers: headers, body: LOGIN_DATA.to_param })
session = JSON.parse(ActiveSupport::Gzip.decompress(res.body))
raise "login error #{session['resource_response']['error']}" if session['resource_response']['error']
cjar = res.headers.get_fields('Set-Cookie').each_with_object(HTTParty::CookieHash.new) { |cookie, jar| jar.add_cookies(cookie) }
save_session_headers(HEADERS.merge({ 'Cookie' => cjar.to_cookie_string }))
end
def save_session_headers(headers)
# replace this with your cache/db
Utils::RedisUtil.set(:pinterest_session_headers, headers.to_json)
end
end

Categories