php cURL set manual cookies - php

I have a cookie file with this
.adidas.de TRUE / FALSE 1519852113 restoreBasketUrl %2Fon%2Fdemandware.store%2FSites-adidas-DE-Site%2Fde_DE%2FCart-UpdateItems%3Fpid_0%3DBB2092_610%26qty_0%3D1
.adidas.de TRUE / FALSE 1550524169 utag_main v_id:015fe2df50a60014c3cedb252f0d04073001906b01978$_sn:7$_ss:0$_st:1518989969891$_prevpage:ACCOUNT%7COVERVIEW%3Bexp-1518991769885$_pn:3%3Bexp-session$ses_id:1518987220846%3Bexp-session$ab__doubleclick:TEST%3Bexp-1521580164884
I know I can read it out from file in cURL like
curl_setopt ($ch, CURLOPT_COOKIEFILE, $cookiefile);
But how can I set these cookies manual without a file? Because I need to modify them a bit before sending

You can use curl_setopt function with option CURLOPT_HTTPHEADER.
curl_setopt($ch, CURLOPT_HTTPHEADER, ["Cookie: mycookie=value;mycookie2=value2"]);
[Edit]
From this guide The Unofficial Cookie FAQ.
The layout of Netscape's cookies.txt file is such that each line contains one name-value pair. An example cookies.txt file may have an entry that looks like this:
.netscape.com TRUE / FALSE 946684799 NETSCAPE_ID 100103
Each line represents a single piece of stored information. A tab is inserted between each of the fields.
From left-to-right, here is what each field represents:
domain - The domain that created AND that can read the variable.
flag - A TRUE/FALSE value indicating if all machines within a given domain can access the variable. This value is set automatically by the browser, depending on the value you set for domain.
path - The path within the domain that the variable is valid for.
secure - A TRUE/FALSE value indicating if a secure connection with the domain is needed to access the variable.
expiration - The UNIX time that the variable will expire on. UNIX time is defined as the number of seconds since Jan 1, 1970 00:00:00 GMT.
name - The name of the variable.
value - The value of the variable.
For answer your question
1) To modify a bit before sending do this:
$file = file('cookie.txt');
$cookies = [];
/*
* From the guidelines that I linked and posted above each line must contain 7 "fields" separated by tab only (The text you posted in the question is not well formatted but with some tricks we can do this)
*/
foreach ($file as $fileLine) {
$fileLine = preg_replace("/\s+/", "\t", trim($fileLine));
$fields = explode("\t", $fileLine);
if (count($fields) === 7) {
$cookies[] = [
'domain' => $fields[0],
'flag' => $fields[1],
'path' => $fields[2],
'secure' => $fields[3],
'expiration' => $fields[4],
'name' => $fields[5],
'value' => $fields[6],
];
}
}
var_dump($cookies); // Here you have all lines from your cookie file and can modify the fields such name, value or something
2) For override the cookie.txt with your modify cookies array do this:
// Preserve Netscape format
$cookies = implode(PHP_EOL, array_map(function($data){
return implode("\t", $data);
}, $cookies));
file_put_contents('cookie.txt', $cookies);
3) For send your new cookies from file do this (must be in Netscape format):
curl_setopt ($ch, CURLOPT_COOKIEFILE, 'cookie.txt');

Related

PHP: Check if a loaded TLS certificate is trusted

The program fetches a TLS certificate chain from a server and does several checks. It should check if the last part of the chain points to a trusted certificate. Here is an excerpt show the relevant part:
$g = stream_context_create(array("ssl" => array(
"capture_peer_cert" => true,
"capture_peer_cert_chain" => true,
"peer_name" => $domain,
"verify_peer" => false,
"verify_peer_name" => false,
"SNI_enabled" => true,
)));
$r = #stream_socket_client($url, $errno, $errstr, 5, STREAM_CLIENT_CONNECT, $g);
$cont = stream_context_get_params($r);
$certchain = &$cont["options"]["ssl"]["peer_certificate_chain"];
$ChainAuthorityIds = array();
Snip: Now, there follows some longer code that fills up the array ChainAuthorityIds like that: 0-indexed each index contains an array of two fields: subject containing the key Id of the subject field, and authority, containing the key Id of the authority field. This is done by using openssl_x509_parse().
Afterwards, we can check for correct order like this:
$correctorder = true;
$previous_authority = null;
foreach ($ChainAuthorityIds as $num => &$details) {
if ($previous_authority !== null) {
if ($details['subject'] != $previous_authority) $correctorder = false;
}
$previous_authority = $details['authority'];
}
unset($details);
So, in $ChainAuthorityIds[count($ChainAuthorityIds) - 1]['authority'] must be the key Id of a certificate that is stored in OpenSSL's directory of trusted roots. How can I check if this key is part of this truststore? Also, I want to explicitly load this certificate (possibly with something like openssl_x509_parse()) into memory to check its validity period.
PS: If the chain is over-complete, and the last certificate is the root, then it contains an empty string as authority Id key. This case is properly handled in my program, but for sake of simplicity not shown in this question.
Suprisingly, the answer is quite simple. OpenSSL holds its truststore in a directory containing each root certificate as PEM file - one certificate per file. So, all that needs to be done is finding out which directory this is. This can be done by using the PHP command openssl_get_cert_locations(). It returns an array, of which the index default_cert_dir holds the said directory name.
$locations = opnenssl_get_cert_locations();
$pemfiles = glob($locations['default_cert_dir'] . '/*.pem');
foreach ($permfiles as $pemfile) {
$rootcert = openssl_x509_parse(openssl_x509_read($pemfile));
// do something with $rootcert
}

curl_exec() argument removing last 2 digit of integer

I'm using softtouch API with WordPress, and posting data to API via curl.
But in response I am not able to send the big integer value in function. I'm not getting is that data type range issue or curl.
Below is my code:
//create reservation
$prod_items = array();
$single_item = array('product_uid'=>11449701010101);
$prod_items[] = $single_item;
$res_params = array(
'customer_id' => 1111,
'payment_type' => '',
'invoice_address_id' => 123,
'delivery_address_id' => 142,
'giftlist_id' => '',
'store_id' => '',
'items' => $prod_items
);
$res_url = $base_url . 'reservations';
$res_content = json_encode($res_params);
$res_curl = curl_init();
curl_setopt($res_curl, CURLOPT_HTTPHEADER, array('Authorization: ' . $authToken, 'Content-Type: application/json'));
curl_setopt($res_curl, CURLOPT_POST, true);
curl_setopt($res_curl, CURLOPT_POSTFIELDS, $res_content);
curl_setopt($res_curl, CURLOPT_URL, $res_url);
curl_setopt($res_curl, CURLOPT_RETURNTRANSFER, true);
$res_response = curl_exec($res_curl);
if ($res_response === FALSE)
die(curl_error($res_curl));
curl_close($res_curl);
$res_array = json_decode($res_response);
While sending data to the curl_exec() function it removes the last two digits of the product_uid, as I passed it 11449701010101 it send it as 114497010101.
Is that any integer range issue or something curl function issue?
tl:dr There would seem to be something else (in the script that processes the CURL request) that is truncating the product_uid. (?)
array('product_uid'=>11449701010101)
If you are on a 32 bit system (PHP compiled as 32 bit) then 11449701010101 does exceed the 32 bit integer range. However, in such cases, PHP silently converts the number to a float and nothing is "lost" in this instance.
json_encode($res_params);
The PHP function json_encode() converts the passed array into a string respresentation (JSON string). Nothing is lost. The 11449701010101 value is preserved.
While sending data to the curl_exec() function it removes the last two digits
The (POST) data being transmitted is an ordinary string, so nothing can be lost to the individual properties at this stage.
If the receiving script then decodes the transmitted JSON string, encodes it again and sends it back, the data is returned intact. The product_uid is a float, not an integer (as it is in the original data).
If you specifically force 11449701010101 to an integer (eg. (int)11449701010101) then you get -681801035 - the last 2 digits are not simply truncated. For the last 2 digits to be truncated there would seem to be some kind of string manipulation going on?
So, there would seem to be something else (not shown here) during the processing of this data that is perhaps truncating the value. (?)

Need assistance with doing redirect with variables without query string

Hello: I have some code in on file and it needs to redirect to a WP page and carry some variables with it. Now I know I can do this with a "printf" statement and add some query string variables on the end of the URL of the page. But I do not want the variables up in the URL. I know if it was a form - it could be done with GET or POST variables. And post variables are not up in the URL. But the only way I know how to do post variables is with a form. I cannot use a form for this that needs a "submit" button that needs to be pressed. It needs to be something that is automatically executed when the script is loaded like a printf statement would be. Does anyone have any ideas on how this could be done ?
Thanks, Gerard
******* update 12/13 1:32PM EST ***************
Hello Arkascha - I have attempted to do what you suggested in your comment, and created the Curl call along with the post variables. But it would not actually redirect to the page. Not sure if I just did it wrong or if it cannot do that. But i was researching and saw where people did a header redirect along with the CURL. And so i thought i would try that. What I have does do the redirect; but it does not seem to carry the post variables with it. So I am not sure if something is wrong with my CURL code, or whether or not I need a header redirect.... etc etc...
here is my code:
$buy_refi='purchase';
$to_borrow=$entry["58"];
$home_worth=$entry["57"];
$down_payment=$entry["62"];
$purchase_price=$entry["54"];
$credit=$entry["15"];
$data = array(
'buy_refi' => $buy_refi,
'to_borrow' => $to_borrow,
'home_worth' => $home_worth,
'down_payment' => $down_payment,
'purchase_price' => $purchase_price,
'credit' => $credit,
);
$data = http_build_query($data); // convert array to urlencoded string
$curl = curl_init();
curl_setopt_array($curl, array(
CURLOPT_URL => 'http://www.mydomain.dev/purchase-options/',
CURLOPT_POST => true,
));
curl_setopt($curl, CURLOPT_POSTFIELDS, $data);
curl_setopt($curl, CURLOPT_FOLLOWLOCATION, true);
$resp = curl_exec($curl);
$code = curl_getinfo($curl, CURLINFO_HTTP_CODE);
curl_close($curl);
header("Location:http://www.mydomain.dev/purchase-options/");
*********** here is the code on redirect page which will receive post variables...
$_POST['input_2']=$_POST['buy_refi'];
$_POST['input_58']=$_POST['to_borrow'];
$_POST['input_57']=$_POST['home_worth'];
$_POST['input_62']=$_POST['down_payment'];
$_POST['input_54']=$_POST['purchase_price'];
$_POST['input_15']=$_POST['credit'];
echo "post buy refi: ".$_POST['buy_refi'];
echo "<br/>";
echo "<br/>";

Cannot retrieve JSON POST via PHP: cURL

I tried implementing the following PHP code to POST JSON via PHP: cURL (SOME FORCE.COM WEBSITE is a tag that signifies the URL that I want to POST):
$url = "<SOME FORCE.COM WEBSITE>";
$data =
'application' =>
array
(
'isTest' => FALSE,
key => value,
key => value,
key => value,
...
)
$ch = curl_init($url);
$data_string = json_encode($data);
curl_setopt($ch, CURLOPT_POST, true);
//Send blindly the json-encoded string.
//The server, IMO, expects the body of the HTTP request to be in JSON
curl_setopt($ch, CURLOPT_POSTFIELDS, $data_string);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_HEADER, true);
curl_setopt($ch, CURLOPT_HTTPHEADER,
array
(
'Content-Type:application/json',
'Content-Length: ' . strlen($data_string)
)
);
$result = curl_exec($ch);
curl_close($ch);
print_r($result);
echo '<pre>';
echo $_POST;
$jsonStr = file_get_contents('php://input'); //read the HTTP body.
var_dump($jsonStr);
var_dump(json_decode($jsonStr));
echo '</pre>';
The output of the above is the following:
"Your TEST POST is correct, please set the isTest (Boolean) attribute on the application to FALSE to actually apply."
Arraystring(0) ""
NULL
OK, the above confirms that I formatted the JSON data correctly by using json_encode, and the SOME FORCE.COM WEBSITE acknowledges that the value of 'isTest' is FALSE. However, I am not getting anything from "var_dump($jsonStr)" or "var_dump(json_decode($jsonStr))". I decided to just ignore that fact and set 'isTest' to FALSE, assuming that I am not getting any JSON data because I set 'isTest' to TRUE, but chaos ensues when I set 'isTest' to FALSE:
[{"message":"System.EmailException: SendEmail failed. First exception on row 0; first error: REQUIRED_FIELD_MISSING, Missing body, need at least one of html or plainText: []\n\nClass.careers_RestWebService.sendReceiptEmail: line 165, column 1\nClass.careers_RestWebService.postApplication: line 205, column 1","errorCode":"APEX_ERROR"}]
Arraystring(0) ""
NULL
I still do not get any JSON data, and ultimately, the email was unable to be sent. I believe that the issue is resulting from an empty email body because there is nothing coming from "var_dump($jsonStr)" or "var_dump(json_decode($jsonStr))". Can you help me retrieve the JSON POST? I would really appreciate any hints, suggestions, etc. Thanks.
I solved this question on my own. I was not sure if I was doing this correctly or not, but it turns out that my code was perfect. I kept refreshing my website, from where I am POSTing to SOME FORCE.COM WEBSITE. I believe that the people managing SOME FORCE.COM WEBSITE were having issues on their end. Nothing was wrong with what I did. For some reason, I got a code 202 and some gibberish text to go along with it. I would be glad to show the output, but I do not want to POST again for the sake of the people managing SOME FORCE.COM WEBSITE that I am POSTing to. Thank you guys for your help.

PHP HTTP Post to REST Service not updating database [duplicate]

This question already has answers here:
curl POST format for CURLOPT_POSTFIELDS
(10 answers)
Closed 4 years ago.
I have this curl request below, which was successfully troubleshooted in another post. Right now, my PHP seems to work through this code without any errors, moves onto the next part of the IF statement and sends the confirmation email. It just doesn't update the database as it should from the web service. I will have to email the creator of the web service if this does not work but I just want to be sure that the code is fairly solid before I do this. Any one have any ideas? Here is the code:
$url = 'http://127.0.0.1:85/AccountCreator.ashx';
$curl_post_data = array(
'companyName' =>urlencode($companyName),
'mainContact' =>urlencode($mainContact),
'telephone1' =>urlencode($telephone1),
'email' => urlencode($email),
'contact2' => urlencode($contact2),
'telephone2' => urlencode($telephone2),
'email2' => urlencode($email2),
'package' => urlencode($package)
);
foreach($curl_post_data as $key=>$value) {$fields_string .=$key. '=' .$value.'&';
}
rtrim($fields_string, '&');
//die("Test: ".$fields_string);
$ch = curl_init();
curl_setopt ($ch, CURLOPT, $url);
curl_setopt ($ch, CURLOPT_POST, count($curl_post_data));
curl_setopt ($ch, CURLOPT_POSTFIELDS, $fields_string);
$result = curl_exec($ch);
curl_close($ch);
Firstly, what is the problem? It would be easier to troubleshoot it if you explained exactly what the failure in the code was. Secondly, there are a couple of odd things you are doing in this code:
I don't see why you are doing
curl_setopt ($ch, CURLOPT_POST, count($curl_post_data));
CURLOPT_POST requires a boolean (true/false) setting. You should set it to true.
Secondly, you don't need to encode CURLOPT_POSTFIELDS manually. Make an array and let cURL deal with it internally:
$curl_post_data = array(
'companyName' =>$companyName,
'mainContact' =>$mainContact,
'telephone1' =>$telephone),
'email' => $email,
'contact2' => $contact2,
'telephone2' => $telephone2,
'email2' => $email2,
'package' => $package
);
These might not fix the problem, but they may help.
The CURLOPT_POSTFIELDS option accepts an associative array of POST-data. Probably better to use that one rather than to construct the query string yourself so you got someone else to blame when it blows up.
PHP Manual:
The full data to post in a HTTP "POST"
operation. To post a file, prepend a
filename with # and use the full path.
This can either be passed as a
urlencoded string like
'para1=val1&para2=val2&...' or as an
array with the field name as key and
field data as value. If value is an
array, the Content-Type header will be
set to multipart/form-data.

Categories