curl response cannot be handled after saved in a variable PHP - php

$ch = curl_init("http://acrs.bboxpr.com/getAddress.php?lat=35.545112&lng=-90.657635");
curl_setopt($ch, CURLOPT_RETURNTRANSFER, TRUE);
$address = curl_exec($ch);
curl_close($ch);
//prints the address
echo $address;
//$token = strtok($address, ",");
//$phaddress=array();
//while ($token != null)
//{
//array_push($phaddress,$token);
//$token = strtok(",");
//}
//print_r($phaddress); //blank
In the line echo $address; will print in the content in the page, but if I uncomment the code below(the one that starts with: $token=strtok),$address will look empty. I added more code that uses the results with $address (but I did not include that in here) and sometimes appears the source-code of the site that is invoked in the curl initialization. So I think maybe curl is taking a little bit longer, but I tried to put a sleep before srtok, but didn't work.

In your while loop, you have to replace $token = strtok(","); with $token = strtok($address, ",");

Since you are tying to get MAP information from google i think you are using the wrong approch my using javascript because that might be more difficult to parse
Why don't you try using PHP directly
$ch = curl_init("http://maps.google.com/maps/api/geocode/json?latlng=35.545112,-90.657635&sensor=false");
curl_setopt($ch, CURLOPT_RETURNTRANSFER, TRUE);
$return = curl_exec($ch);
curl_close($ch);
$geoOutput = json_decode($return,true);
echo "<pre>" ;
foreach($geoOutput as $key => $data)
{
if(is_array($data))
{
foreach($data as $cKey => $cData)
{
var_dump($cData['formatted_address']);
}
}
}
Output
string(43) "6724-6916 Bay Ln, Harrisburg, AR 72432, USA"
string(16) "Bolivar, AR, USA"
string(25) "Harrisburg, AR 72432, USA"
string(17) "Poinsett, AR, USA"
string(13) "Arkansas, USA"

Change your while loop to this: while ($token !== false)

Related

How to extract and access data from JSON with PHP when some data changes?

I am trying to bring in some API data to a directory in wordpress.
The data I am trying to get is just crypto coin price, none of the other information but because its format is sort of nested (?) it doesnt seem to work.
{
"bitcoin": {
"usd": 16808.82
}
}
This is my code so far:
<?php
$handle = curl_init();
$url = get_post_meta($entity-\>post()-\>ID, '\_drts_field_004', true);
// Set the url
curl_setopt($handle, CURLOPT_URL, $url);
// Set the result output to be a string.
curl_setopt($handle, CURLOPT_RETURNTRANSFER, true);
curl_setopt($handle, CURLOPT_SSL_VERIFYPEER, false);
$output = curl_exec($handle);
curl_close($handle);
$data = json_decode($output);
echo $output;
var_dump($data);
The results are:
{
"bitcoin":{
"usd":16833.02
}
}
object(stdClass)#10399 (1) {
["bitcoin"]=> object(stdClass)#10492 (1) {
["usd"]=> float(16833.02)
}
}
In this example I am only after the 16833.02
I am trying to do this for lots of different coins, the "usd" will always be the same but the "bitcoin" will change when other coins.
How can I echo only the number?
I have tried lots of variations of echo but cannot get it? Is it possible to do something like:
echo $data['bitcoin']['usd'];
but rather than bitcoin use * ?
As in anything can be there?
You can access the usd value by decoding the JSON to an array instead of an object like this
$data = json_decode($output, true);
$usd = current($data)['usd'];

PHP: Assign array to variable

i've tried a lot of things to achieve this but none of them seem to
work. Im using PHP 7.4
Let's say i have this:
$othervar = array();
$var = array(1, 2, 3);
$othervar = $var;
THIS doesn't work for me, var_dump($othervar) returns
array(1) { [0]=> string(5) "Array" }
I've tried using array_push, i DON'T WANT to use array_merge because i
need to assign two arrays to one variable. This is what i need to do:
$variable = array();
$variable["type1"] = $data; //Array 1
$variable["type2"] = $otherData; //Array 2
This doesn't work either.
Barmar showed me here that this works so i must be doing it wrong somewhere else.
I'll explan the whole code:
To login to my webpage, i send a request trough AJAX request with jQuery.
function SendData(data, btn, actionOnSuccess, shouldReplace = false, elementToReplace = "", getServerData = true, htmlData = "") {
if (!loading)
{
ToggleLoading();
data.push({name: "action", value: $(btn).data("action")});
data.push({name: "attr", value: JSON.stringify($(btn).data("attr"))});
$.post("SendRequest.php", data)
.done(function (r) {
if (!r.success)
//ajax sent and received but it has an error
else
//ajax sent and it was successfull
})
.fail(function () {
//ajax call failed
});
}
else {
//This determines if some request is already executing or not.
}
}
"action" and "attr" are encrypted values that i send to reference some actions on the system (i'll show more here):
The code goes from AJAX to SendRequest.php where it executes an action let's say, login.
The first lines of SendRequest.php are:
require "Functions.php";
$apiAction = Decrypt($_POST["action"]); //Action
$actionData = json_decode(Decrypt($_POST["attr"])); //Attr
$finalPost = $_POST;
foreach ($actionData as $key => $value) { $finalPost[$key] = $value; }
$finalPost["loggedin_ip"] = $_SERVER['REMOTE_ADDR'];
$result = APICall($apiAction, $finalPost);
Then, this is what i want to achieve to communicate with my API:
function APICall($option, $data = array())
{
session_start();
$post = array("uData" => ArrayToAPI($_SESSION), "uPost" => ArrayToAPI($data));
$ch = curl_init();
curl_setopt($ch, CURLOPT_HEADER, 0);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($ch, CURLOPT_POSTFIELDS, $post);
curl_setopt($ch, CURLOPT_URL, "https://apiurl?" . $option); //option is the ACTION to perform on API (let's say "login") it is an encrypted word on a data-attr atribute on every form/button that creates a communication with API.
$returned = curl_exec($ch);
curl_close ($ch);
$newData = json_decode($returned, true);
return $newData;
}
function ArrayToAPI($array)
{
$toApiData = array();
foreach ($array as $key=>$value) {
if (is_array($value))
$toApiData[$key] = ArrayToAPI($value);
else
$toApiData[$key] = Encrypt($value);
}
return $toApiData;
}
This is what i have on API side:
ob_start();
var_dump($_POST);
$result = ob_get_clean();
$api->EndRequest(false, array("errorDesc" => "a - " . $result));
function EndRequest(bool $task_completed, array $data = array())
{
$jsonData = array();
$jsonData['success'] = $task_completed;
$jsonData['data'] = $data;
header('Content-type: application/json; charset=utf-8');
echo json_encode($jsonData, JSON_FORCE_OBJECT);
exit;
}
This ALWAYS returns
array(2) { ["uData"]=> string(5) "Array" ["uPost"]=> string(5) "Array" }
I hope im more clear now, thanks.
The problem is with the request being sent out from your code because of this line:
curl_setopt($ch, CURLOPT_POSTFIELDS, $post);
CURLOPT_POSTFIELDS doesn't support multi-level arrays. Your array values (which the keys are pointing to) are cast to string, which ends up as Array. Use:
curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query($post));
.. instead to "properly" serialize multidimensional arrays in a post request ("properly" as there are many ways to do just that, but it matches the expected PHP format - with [] to denote arrays).

USPS API returning 80040B19 error code and Account is in Production

so my issue is according to the documentation (wich is pretty slim and not the greatest) the xml i have is everything that is required, but im getting this error code back
<?xml version="1.0" encoding="UTF-8"?>
<Error><Number>80040B19</Number><Description>XML Syntax Error: Please check the XML request to see if it can be parsed.</Description><Source>USPSCOM::DoAuth</Source></Error>
this doesnt make much sense to me because my account is in production mode, and as i said according to the documentation i have everything that is required, i have spent the last 2 days trying to get this to work and nothing.
the VerifyAddress function works fine, but the RateCheck function does not work.
class USPS
{
protected $Endpoint = 'http://production.shippingapis.com/ShippingAPI.dll';
protected $SecureEndpoint = 'https://secure.shippingapis.com/ShippingAPI.dll';
protected $TestEndpoint = 'http://stg-production.shippingapis.com/ShippingAPI.dll';
protected $TestSecureEndpoint = 'https://stg-secure.shippingapis.com/ShippingAPI.dll';
private $username = 'example’;
function VerifyAddress($address1, $address2, $city, $state, $zip)
{
$xml = '<AddressValidateRequest%20USERID="'.$this->username.'">
<Address>
<Address1>'.$address1.'</Address1>
<Address2>'.$address2.'</Address2>
<City>'.$city.'</City>
<State>'.$state.'</State>
<Zip5>'.$zip.'</Zip5>
<Zip4></Zip4>
</Address>
</AddressValidateRequest>';
//build the data
$data = $this->AddressVerify . $xml;
//send for the request
$verified = $this->Request($data);
//return he results
return $verified;
}
function RateCheck($packages, $zipDest, $service='PRIORITY', $zipOrigin='93274', $pounds='3', $ounces='0',
$container='RECTANGULAR', $size='LARGE', $width='13', $length='14', $height='6', $girth='38')
{
$packageIDS = array('1ST'=>1, '2ND'=>2, '3RD'=>3, '4TH'=>4, '5TH'=>5, '6TH'=>6, '7TH'=>7, '8th'=>8,'9TH'=>9,
'10th'=>10);
$packagexml = array();
for($i=1;$i<=$packages;$i++)
{
$PackageID = array_search($i, $packageIDS);
$packagexml[] = '<Package ID="'.$PackageID.'">
<Service>'.$service.'</Service>
<ZipOrigination>'.$zipOrigin.'</ZipOrigination>
<ZipDestination>'.$zipDest.'</ZipDestination>
<Pounds>'.$pounds.'/Pounds>
<Ounces>'.$ounces.'</Ounces>
<Container>'.$container.'</Container>
<Size>'.$size.'</Size>
<Width>'.$width.'</Width>
<Length>'.$length.'</Length>
<Height>'.$height.'</Height>
<Girth>'.$girth.'</Girth>
</Package>';
}
$xml2 = '';
foreach($packagexml as $package)
{
$xml2 .= $package;
}
$data = 'API=RateV4&XML=<RateV4Request USERID="'.$this->username.'"><Revision>2</Revision>'.$xml2.'</RateV4Request>';
$RateResult = $this->Request($data);
return $RateResult;
}
function Request($data)
{
$ch = curl_init();
// set the target url
curl_setopt($ch, CURLOPT_URL,$this->Endpoint);
curl_setopt($ch, CURLOPT_HEADER, 1);
curl_setopt($ch,CURLOPT_RETURNTRANSFER,1);
//curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true);
// parameters to post
curl_setopt($ch, CURLOPT_POST, 1);
// send the POST values to usps
curl_setopt($ch, CURLOPT_POSTFIELDS, $data);
//curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, 0);
$result=curl_exec ($ch);
curl_close($ch);
$Parseresult = $this->parseResult($result);
return $Parseresult;
}
function parseResult($responce)
{
$data = strstr($responce, '<?');
echo '<!-- '. $data. ' -->'; // Uncomment to show XML in comments
$xml_parser = xml_parser_create();
xml_parse_into_struct($xml_parser, $data, $vals, $index);
xml_parser_free($xml_parser);
$params = array();
$level = array();
foreach ($vals as $xml_elem) {
if ($xml_elem['type'] == 'open') {
if (array_key_exists('attributes',$xml_elem)) {
list($level[$xml_elem['level']],$extra) = array_values($xml_elem['attributes']);
} else {
$level[$xml_elem['level']] = $xml_elem['tag'];
}
}
if ($xml_elem['type'] == 'complete') {
$start_level = 1;
$php_stmt = '$params';
while($start_level < $xml_elem['level']) {
$php_stmt .= '[$level['.$start_level.']]';
$start_level++;
}
$php_stmt .= '[$xml_elem[\'tag\']] = $xml_elem[\'value\'];';
eval($php_stmt);
}
}
return $params;
}
}
The reason I was getting this was because I had unescaped ampersands in my XML that I was posting to the USPS API. Before you POST the XML, print the XML out on your screen just to see exactly what is being posted. I'm not sure how to do this in php (maybe echo?) but in python I would do print(my_xml_string).
Like I said, my generated xml had ampersand characters in it &, I fixed the problem by replacing those with &. Again, I'm not way familiar with php but python would be my_xml_string.replace('&', '&'). This is because an ampersand in XML needs to be 'closed' with a ;.
soultion form Viable works .. by adding the following code in appropriate format
'.$pounds.'
i have demonstrated at usps tracking site and its now works well
I got following error to my site usps tracking : when i manually entered field i got result . but through the form i got that error mentioned below.
80040B19XML Syntax Error: Please check the XML request to see if it can be parsed.(B)USPSCOM::DoAuth
Finally revising quote . i got solution.
DONOT defin the value in the loop or xml tag
right <Pounds>'.$pounds.'</Pounds>
wrong <Pounds>'if($_POST['unit']=="Pounds"){ ...'</Pounds> This is creating xml VALIDATION ISSUE ..

CURLOPT_POSTFIELDS array of folder content

i'm making a curl post to Google text to speech. I have a set of .flac files, that i want to send to Google Text to Speech service, in order to have the content wrote in a txt file.
This is the code i wrote to do this and it works:
$url = 'https://www.google.com/speech-api/v2/recognize?output=json&lang=it-IT&key=xxx';
$cont2 = array(
'flac/1.flac',
'flac/2.flac',
'flac/3.flac'
);
$ch = curl_init();
curl_setopt($ch, CURLOPT_HTTPHEADER, array('Content-Type: audio/x-flac; rate=44100'));
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
foreach ($cont2 as $fn) {
curl_setopt($ch, CURLOPT_POSTFIELDS, file_get_contents($fn));
$result = curl_exec($ch);
$info = curl_getinfo($ch);
//var_dump($info);
if ($result === false) {
die(curl_error());
}else{
echo "<br />".$fn." upload ok"."<br />";
file_put_contents("pum.txt", $result, FILE_APPEND);
}
}
It works like a charm, in the "pum.txt" i have all the file content wrote and it's ok.
My problem is that i don't want to add to the the array "cont2", each time, the new name o the files i need to pass to, that there are in the "flac folder".
To avoid that, i use "scandir" method, remove "." and ".." string from the array and give that array to the CURL_OPT_POSTFIELD, but the call to GTT return a empty content.
This is the code i wrote to do that (instead $cont2 array)
$directory = 'flac/';
$cont = array_diff(scandir($directory), array('..', '.', '.DS_Store'));
Print_r of that is the same as $cont2 array:
array(3) {
[3]=>
string(6) "1.flac"
[4]=>
string(6) "2.flac"
[5]=>
string(6) "3.flac"
}
But Google TTS return empty result.
Does anyone please tell me where i'm making mistake?
Kind Regards
Brus
EDIT: use "$cont = glob("$directory/*.flac");" solved the issue. Hope help some others.
scandir() won't include full path information - it'll only return filenames. SO when you're building your array of filenames to loop on and send to google, you'll have to include that directories yourself.
e.g.
$dir = 'flac';
$files = scandir($dir);
foreach($files as $key => $file);
$files[$key] = $dir . '/' . $file;
}
e.g. scan dir will return file1.flac, but you need to have flac/file1.flac. Since you're not including the path information, you're trying to do file_get_contents() on a filename which doesn't exist, and are sending a boolean false (file_get failed) over to google.
As Marc B states you need the directory to the files which is missing. I would just use glob as it will return exactly what you need:
$cont = glob("$directory/*.flac");

PHP: Get value from array

I am using the bukkit JSONAPI and php JSONAPI.php to get the list of players on my minecraft server to my website. To get the count, I do this:
require('JSONAPI.php'); // get this file at: https://github.com/alecgorge/jsonapi/raw/master/sdk/php/JSONAPI.php
$api = new JSONAPI("localhost", 20059, "user", "pass", "salt");
$limit = $api->call("getPlayerLimit");
$count = $api->call("getPlayerCount");
$c = curl_init($url);
curl_setopt($c, CURLOPT_PORT, 20059);
curl_setopt($c, CURLOPT_HEADER, false);
curl_setopt($c, CURLOPT_RETURNTRANSFER, true);
curl_setopt($c, CURLOPT_TIMEOUT, 10);
$result = curl_exec($c);
curl_close($c);
echo "<h5>Players online:</h5>";
$num= '' . $count['success'] . '/' . $limit['success'];
echo $num;
This returns: 1/40
Then, I try to get the player list:
$list = $api->call('getPlayerNames');
echo $list;
This just returns: Array
However, when I do
var_dump($api->call('getPlayerNames'));
I get:
array(3) { ["result"]=> string(7) "success" ["source"]=> string(14) "getPlayerNames" ["success"]=> array(1) { [0]=> string(8) "gauso001" } }
However, what I want is simply a list of the players without all of the extra stuff. Sorry if this is a noob question, I only know pretty basic PHP.
Stuff that might help:
method docs: http://alecgorge.com/minecraft/jsonapi/apidocs/#package-JSONAPI%20standard
tell me what else..
THANK YOU in advance, I hope I'll be as good as you in PHP one day :D
Looks like player names, oddly enough, are contained as an array in the success key.
To access the player names, you could:
$list = $api->call('getPlayerNames');
// debug
print_r($list['success']);
// direct access
echo $list['success'][0];
// loop
foreach($list['success'] as $player) {
echo $player;
}
Format to your needs. But that should get you started.
Note: I'd also encourage you to learn about Arrays in PHP.
$api->call('getPlayerNames') returns a named array, one key of which (success) is another array containing the player names. Iterate over the success key to get the player list.
$players = $api->call('getPlayerNames');
foreach($players['success'] as $player) {
echo $player;
}

Categories