I'm performing a POST request to a REST Service that requires an OAuth 2.0 authorization.
In Postman everything works perfectly fine since enabling the "Follow Authorization header" option so the auth header will be retained after a redirection.
However I dont know the equivalent to that attribute for a CURL request in PHP. So therefore I still get the following error: "Session expired or invalid".
Does anyone know how to successfully keep the auth header after a redirection in PHP cURL?
This is my php code:
$token = $this->getToken();
$url = "XXX";
$curl = curl_init();
curl_setopt_array($curl, array(
CURLOPT_URL => $url,
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => '',
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 0,
CURLOPT_FOLLOWLOCATION => true,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => 'POST',
CURLOPT_POSTFIELDS => json_encode($data),
CURLOPT_HTTPHEADER => array(
'Authorization: Bearer ' . $token,
'Content-Type: application/json'
,
curl_setopt($curl, CURLOPT_POSTFIELDS, array(
'client_id' => 'XXX',
'client_secret' => 'XXX',
'username' => 'XXX',
'password' => 'XXX',
'grant_type' => 'password',
'redirect_uri' => 'XXX'
)))
));
$response = curl_exec($curl);
var_dump('TOKEN: ' . $token);
var_dump($url);
var_dump(curl_getinfo($curl));
if (curl_errno($curl)) {
var_dump('Error:' . curl_error($curl));
} else {
var_dump("SUCCESS! ");
var_dump($response);
}
You cannot do this:
curl_setopt($curl, CURLOPT_POSTFIELDS, array(
'client_id' => 'XXX',
'client_secret' => 'XXX',
'username' => 'XXX',
'password' => 'XXX',
'grant_type' => 'password',
'redirect_uri' => 'XXX'
You already did this: URLOPT_POSTFIELDS => json_encode($data),
And you cannot use an array if you want to keep the Content-Type: application/json.
When you use an array for POSTFIELDS, curl will override the content type with Content-Type: application/x-www-form-urlencoded
I sometimes use file_get_content() with a context.
This is an easy way (without SSL) to get the headers and post data right.
Keeping mind that file_get_content() has some of the same idiosyncrasies as curl. The context has file_get_content() which populates the Body.
<?php
header("Content-Type: text/plain,UTF-8");
$jsn = file_get_contents('json.jsn');
$postdata = http_build_query(
array(
'json' => $jsn,
)
);
$opts = array('http' =>
array(
'method' => 'PUT',
'header' => 'Content-type: application/json',
'content' => $jsn //useing JSON rather than $postdata
)
);
$context = stream_context_create($opts);
$result = file_get_contents($url, false, $context);
echo $result;
Related
I'm running a cURL post request that is appearing to hit the url and return a response. However, I'm led to believe that I'm not handling the request output properly and it's throwing an error that I don't understand. I'm extremely new to cURL and if anyone could point me in the right direction, I'd appreciate it.
$curl = curl_init();
$headers = array(
'Content-Type: application/json',
'X-Requested-With: XMLHttpRequest',
);
curl_setopt_array($curl, [
CURLOPT_RETURNTRANSFER => 1,
CURLOPT_URL => 'XXX',
CURLOPT_POST => 1,
CURLOPT_POSTFIELDS => [
client_id => 'XXX',
client_secret => 'XXX',
member_id => 'XXX'
],
CURLOPT_HTTPHEADER => $headers,
CURLOPT_HTTPAUTH => CURLAUTH_BASIC
]);
$resp = curl_exec($curl);
curl_close($curl);
var_dump(json_decode($resp, true));
This results in the errors that follows:
{"errors":{"":["Input string '--------------------------cec6101ba64bcb7f' is not a valid number. Path '', line 1, position 42."]},"title":"One or more validation errors occurred.","status":400,"traceId":"80031695-0002-ef00-b63f-84710c7967bb"}
$curl = curl_init();
$headers = array(
'Content-Type: application/json',
'X-Requested-With: XMLHttpRequest',
);
//////
Adding this and using json_encode allowed for the request to be properly sent with the required id's and secret tokens.
//////
$data = array(
"ClientId" => "$api_clientId" ,
"ClientSecret" => "$api_clientSecret",
"MemberId" => "$api_memberId"
);
$data_string = json_encode($data);
curl_setopt_array($curl, [
CURLOPT_RETURNTRANSFER => 1,
CURLOPT_URL => 'https://cors-anywhere.herokuapp.com/https://staging.micromerchantsystems.com/authenticationservice/api/GateKeeper/createtoken',
CURLOPT_POST => 1,
CURLOPT_POSTFIELDS => $data_string,
CURLOPT_HTTPHEADER => $headers,
CURLOPT_HTTPAUTH => CURLAUTH_BASIC
]);
$resp = curl_exec($curl);
curl_close($curl);
var_dump(json_decode($resp, true));
I'm trying to make a POST request and send some values in the body of an API call. In the documentation of the API it says I need to make a POST request, using startUrls as an array with key and value.
<?php
$url = 'https://api.apify.com/v1/USERID/crawlers/CRAWLERID/execute?token=TOKENID';
$postData = array(
'startUrls' => array(array('key'=>'START', 'value'=>'https://instagram.com/instagram'))
);
$context = stream_context_create(array(
'http' => array(
'method' => 'POST',
'header' => 'Content-type: application/json',
'body' => json_encode($postData)
)
));
$resp = file_get_contents($url, FALSE, $context);
print_r($resp);
?>
The JSON seems to be how it should, but the script is not sending the body properly to the website.
According to the documentation, there is no body option for the HTTP context. Try content instead:
<?php
$url = "https://api.apify.com/v1/USERID/crawlers/CRAWLERID/execute?token=TOKENID";
$postData = [
"startUrls" => [
["key"=>"START", "value" => "https://instagram.com/instagram"]
]
];
$context = stream_context_create([
"http" => [
"method" => "POST",
"header" => "Content-type: application/json",
"content" => json_encode($postData)
]
]);
$resp = file_get_contents($url, FALSE, $context);
print_r($resp);
The following code will work. I have set the headers and specified the content type.
$request = new HttpRequest();
$request->setUrl('$url = 'https://api.apify.com/v1/USERID/crawlers/CRAWLERID/execute?token=TOKENID');
$request->setMethod(HTTP_METH_POST);
$request->setHeaders(array(
'cache-control' => 'no-cache',
'content-type' => 'application/x-www-form-urlencoded'
));
$request->setContentType('application/x-www-form-urlencoded');
$request->setPostFields(array('key'=>'START', 'value'=>'https://instagram.com/instagram')
));
try {
$response = $request->send();
echo $response->getBody();
} catch (HttpException $ex) {
echo $ex;
}
If you want to try with cUrl the following code snippet will work.
$curl = curl_init();
$postData = array(
'startUrls' => array(array('key'=>'START', 'value'=>'https://instagram.com/instagram'))
);
curl_setopt_array($curl, array(
CURLOPT_URL => "https://api.apify.com/v1/USERID/crawlers/CRAWLERID/execute?token=TOKENID",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "POST",
CURLOPT_POSTFIELDS => $postData,
CURLOPT_HTTPHEADER => array(
"Cache-Control: no-cache",
"content-type: multipart/form-data;"
),
));
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
When trying to revoke the oauth access_token for Box, I get the error : Client id was not found in the headers or body
This is the curl-command (which works fine) :
curl https://api.box.com/oauth2/revoke -d 'client_id=CLIENT_ID&client_secret=CLIENT_SECRET&token=access_token' -X POST
When trying the same with php curl, I get the error.
<?php
$revokeurl="https://api.box.com/oauth2/revoke";
$dataq = array(
'client_id' => $client_id,
'client_secret' => $client_secret,
'token' => $access_token
);
$dataqjson= json_encode($dataq);
$headers=array(
"Content-Type: application/json"
);
$curl = curl_init();
curl_setopt_array($curl, array(
CURLOPT_URL => $revokeurl,
CURLOPT_CUSTOMREQUEST => "POST",
CURLOPT_POSTFIELDS => $dataqjson,
CURLOPT_HTTPHEADER => $headers,
CURLOPT_RETURNTRANSFER => 1,
CURLOPT_SSL_VERIFYPEER => FALSE,
CURLOPT_SSL_VERIFYHOST => FALSE
));
$response = curl_exec($curl);
$json_response = json_decode( $response, TRUE );
curl_close($curl);
?>
Why is my POST with json body not correct ?
Data should be set as application/x-www-form-urlencoded rather than JSON-encoded. Example:
<?php
$revokeurl = "https://api.box.com/oauth2/revoke";
$dataq = array(
'client_id' => 'client_id',
'client_secret' => 'client_secret',
'token' => 'access_token',
);
$curl = curl_init();
curl_setopt_array(
$curl,
array(
CURLOPT_URL => $revokeurl,
CURLOPT_CUSTOMREQUEST => "POST",
CURLOPT_POSTFIELDS => http_build_query($dataq),
CURLOPT_RETURNTRANSFER => 1,
CURLOPT_SSL_VERIFYPEER => false,
CURLOPT_SSL_VERIFYHOST => false
)
);
$response = curl_exec($curl);
$json_response = json_decode($response, false);
print_r($json_response);
curl_close($curl);
I'm trying to access a third-party API with PHP.
Their command reference is like so:
curl "https://api.example.com/api/" \
-H "Authorization: BEARER-TOKEN" \
-F 'data={"language":"EN","latitude":12.345,"longitude":12.345}'
I've tried:
$url = 'https://api.example.com/api/';
$header = array(
'Content-type: application/json',
'Authorization: ' . $bearertoken
);
$fields = 'data={"language":"EN","latitude":"'.$latitude.'","longitude":"'.$longitude.'"}';
// I've tried this too:
$fields = array('data' => '{"language":"EN","latitude":"'.$latitude.'","longitude":"'.$longitude.'"}');
$ch = curl_init();
$options = array(
CURLOPT_URL => $url,
CURLOPT_POST => true,
CURLOPT_POSTFIELDS => $fields,
CURLOPT_HTTPHEADER => $header,
CURLOPT_RETURNTRANSFER => true,
CURLOPT_HEADER => false,
CURLOPT_FOLLOWLOCATION => true,
CURLOPT_MAXREDIRS => 10,
CURLOPT_ENCODING => "",
CURLOPT_AUTOREFERER => true,
CURLOPT_CONNECTTIMEOUT => 120,
CURLOPT_TIMEOUT => 120
);
curl_setopt_array($ch, $options);
$result = curl_exec($ch);`
But the server responds with a message telling me it didn't get the parameters I'm sending. When I send the same -F "data={}" from a terminal I get the correct response.
You shouldn't use Content-type: application/json. The value of the data parameter is JSON, but the parameters as a whole are sent in application/x-www-form-urlencoded format.
You also need to URL-encode the value of the data parameter.
The best solution is to use json_encode to create the JSON value, then use an array of post fields, then curl will encode the fields properly.
$header = array(
'Authorization: ' . $bearertoken
);
$fields = array('data' =>
json_encode(array('language' => 'EN',
'longitude' => $longitude,
'latitude' => $latitude)));
curl -F submits the form using Content-Type: multipart/form-data, following RFC 2388. You're specifically contravening that when you set the application/json content type.
$data = array('language' => 'EN', 'longitude' => $longitude, 'latitude' => $latitude);
$headers = array (
"Content-Type: multipart/form-data",
"Authorization: $bearertoken",
);
$postfields = array ("data" => json_encode($data));
$ch = curl_init();
$options = array(
CURLOPT_URL => $url,
CURLOPT_HEADER => true,
CURLOPT_HTTPHEADER => $headers,
CURLOPT_POST => true,
CURLOPT_POSTFIELDS => $postfields,
CURLOPT_RETURNTRANSFER => true
);
curl_setopt_array($ch, $options);
curl_exec($ch);
Also, if that's the actual documentation, it may be wrong. The format for Authorization header is Authorization: Bearer <token>.
I am currently trying to work with the Buffer API but I cannot even get CURL to return a error message.
I tried print_r on $resp but still just a blank page.
P.S I have checked with phpinfo that I do in fact currently have curl enabled which it is and it is version 7.30.0
if(isset($_GET['code'])){
$code = "REMOVED";
$curl = curl_init();
curl_setopt_array($curl, array(
CURLOPT_RETURNTRANSFER => 1,
CURLOPT_URL => 'http://api.bufferapp.com/1/oauth2/token.json',
CURLOPT_POST => 1,
CURLOPT_POSTFIELDS => array(
'client_id' => 'REMOVED',
'client_secret' => 'REMOVED',
'redirect_uri' => 'http://localhost/example',
'code' => 'REMOVED',
'grant_type' => 'authorization_code'
)
));
$resp = curl_exec($curl);
curl_close($curl);
}
Edit:
I added the following lines of code before closing the curl
echo curl_errno($curl);
echo curl_error($curl);
And this was returned
60SSL certificate problem: unable to get local issuer certificate
As you are directly passing an array to the CURLOPT_POSTFIELDS, its assume this as multipart form posting request. Use the function http_build_query over your array.
CURLOPT_POSTFIELDS => http_build_query( array(
'client_id' => 'REMOVED',
'client_secret' => 'REMOVED',
'redirect_uri' => 'http://localhost/example',
'code' => 'REMOVED',
'grant_type' => 'authorization_code'
))