Looping through Facebook JSON object - php

I am currently getting the output I desire, although It seems that the only way I can get this to work is with these nasty nested foreach loops. I know that there must be a better way to loop this this JSON object.
$json = 'https://graph.facebook.com/218894654822767_609825405729688?fields=id,likes&key=value&access_token=245675758812857%7Ca2b43c96b8f2db07561ac8f6054b2632';
$fbObject = file_get_contents($json);
$array = json_decode($fbObject, true);
$count = 0;
if(is_array($array))
{
foreach ($array as $key => $object) {
if(is_array($object))
{
foreach ($object as $likes){
if(is_array($likes))
{
foreach ( $likes as $data ){
if(is_array($data))
{
foreach ( $data as $id ){
if (is_numeric($id))
{
echo "$id".'<br />';
}
}
}
}
}
}
}
}
}
?>

Simplifying:
$json_url = 'https://graph.facebook.com/218894654822767_609825405729688?fields=id,likes&key=value&access_token=245675758812857%7Ca2b43c96b8f2db07561ac8f6054b2632';
$json = json_decode(file_get_contents($json_url));
$user_ids = array();
foreach ($json->likes->data as $user) {
$user_ids[] = $user->id;
}
print implode('<br />', $user_ids);
Simplifying even more:
$json_url = 'https://graph.facebook.com/218894654822767_609825405729688?fields=id,likes&key=value&access_token=245675758812857%7Ca2b43c96b8f2db07561ac8f6054b2632';
$json = json_decode(file_get_contents($json_url));
print implode('<br />', array_map(function ($user) {
return $user->id;
}, (array) $json->likes->data));
That's all! :)

Related

How to decode a json from api in php (multidimensional array)

I want to decode json code with php in wordpress.
this is my code. but did not work.
function decode_func(){
$json = file_get_contents('https://api.pray.zone/v2/times/today.json?city=jakarta');
$decoded_json = json_decode($json,true);
$results = $decoded_json['results'];
foreach($results as $result) {
$datetime = $result['datetime'];
foreach($datetime as $datetim) {
$times = $datetim['times'];
foreach($times as $time) {
echo $time['Sunrise'];
}
}
}
}
add_shortcode('decode','decode_func');
I tested your code and what I found out is that your property targeting is incorrect.
In order to get the Sunrise property by foreach loops alone and not directly targeting that property you need to do the following.
$json = file_get_contents('https://api.pray.zone/v2/times/today.json?city=jakarta');
$decoded_json = json_decode($json,true);
$results = $decoded_json['results'];
foreach ($results as $key => $result) {
if ($key !== 'datetime') continue;
foreach($result as $datetime) {
foreach ($datetime as $time) {
if (!empty($time['Sunrise'])) echo $time['Sunrise'];
}
}
}
EDIT
In order to get the city as well I created a new if condition with a elseif.
The code is almost the same, because location is not a multi dimentional array its less foreachs to get the city value
$json = file_get_contents('https://api.pray.zone/v2/times/today.json?city=jakarta');
$decoded_json = json_decode($json,true);
$results = $decoded_json['results'];
foreach ($results as $key => $result) {
if ($key === 'datetime') {
foreach($result as $datetime) {
foreach ($datetime as $time) {
if (!empty($time['Sunrise'])) echo $time['Sunrise'];
}
}
} else if ($key === 'location') {
if (!empty($result['city'])) echo $result['city'];
}
}

Removing JSON children by key in PHP

My goal is to have a function that can remove a specified json child, which could also be nested inside deeper.
My function looks like this:
private function removeJsonChild(String $jsonKey, String $jsonString)
{
$json = json_decode($jsonString, true);
$arr_index = array();
foreach ($json as $key => $value) {
if (is_array($value)) {
$json[$key] = $this->removeJsonChild($jsonKey, json_encode($value));
}
if ($key == $jsonKey) {
$arr_index[] = $key;
}
}
foreach ($arr_index as $i) {
unset($json[$i]);
}
return json_encode($json);
}
The function would work if i wouldn't check if a $value is an array and then call the function again recursively. But there is the problem i think. In the statement where i assign the return value of the function to $json[$key]. What am i doing wrong?
EDIT: definitely forgot a json_decode. New code looks like this:
private function removeJsonChild(String $jsonKey, String $jsonString)
{
$json = json_decode($jsonString, true);
$arr_index = array();
foreach ($json as $key => $value) {
if (is_array($value)) {
$json[$key] = json_decode($this->removeJsonChild($jsonKey, json_encode($value)));
}
if ($key == $jsonKey) {
$arr_index[] = $key;
}
}
foreach ($arr_index as $i) {
unset($json[$i]);
}
return json_encode($json);
}
EDIT2:
The function works now, however it slightly changes the json schema.
An JSON like this:
[
{
"id": 1,
"name": "oyzadsaigny647"
}
]
now becomes this:
{
"1": {
"id": 1,
"name": "oyzadsaigny647"
}
}
private function removeJsonChild(String $jsonKey, String $jsonString) {
$data = json_decode($jsonString, true);
$data = $this->removeKeyFromArray($key, $data);
return json_encode($data);
}
private function removeKeyFromArray(String $deleteKey, array $data) {
unset($data[$deleteKey]); // No need to check if it exists, it just does nothing in that case
foreach($data as $key => value) {
if(is_array($value)) {
$data[$key] = $this->removeKeyFromArray($deleteKey, $value);
}
}
return $data;
}
NOTE: this will work in case of dictionaries, i.e. array with actual keys. If you have a plain array such as [1, 10, 23, 15] the unset behaviour is wrong, as pointed out by #decezeā™¦

Pull all values and keys related to data being searched or matched to

I am probably searching wrong but I havent been able to find a topic that fully helps understand how to pull all the data out of this multidimensional array from a json file. I am trying to pull all data that is related to a certain term or piece of data and return its key and value.
So far I have tried this and its somewhat works.
JSON - https://gist.github.com/Ryahn/ac8fcc8ae77e9a6ee9138e268b592ed3
$result = file_get_contents('21st.json');
$json = json_decode($result,true);
$term = 871957;
foreach ($json as $key => $value)
{
if ($value = $term)
{
echo $value;
echo $key;
foreach ( $value as $key1 => $value2 )
{
if ($value2 = $term)
{
echo $value2;
echo $key1;
foreach ( $value2 as $key2 => $value3 )
{
echo $value3;
}
}
}
}
}
There are multiple levels and parents that may be tied to one ID. I have yet to figure out how to pull all them at once.
Thank you in advance <3
Try this, using isset to check if the user is in the users section and array_filter plus in_array to search the tag users array:
$result = file_get_contents('21st.json');
$json = json_decode($result,true);
$userId = 871957;
$user = isset($json['users'][$userId]) ? $json['users'][$userId] : null;
$tags = [];
if ($user) {
$tags = array_filter($json['tags'], function($tag) use ($userId) {
return in_array($userId, $tag['users']);
});
}
$tagIds = array_keys($tags);
Some tweaking in your code, Replaced = to ==
$result = file_get_contents('21st.json');
$json = json_decode($result,true);
$term = 871957;
foreach ($json as $key => $value)
{
if ($value == $term)
{
echo $value;
echo $key;
foreach ( $value as $key1 => $value2 )
{
if ($value2 == $term)
{
echo $value2;
echo $key1;
foreach ( $value2 as $key2 => $value3 )
{
echo $value3;
}
}
}
}
}
P.S First check this if it is ok so kindly tell me.

How to remove "#attributes" when using simplexml_load_string() to convert XML to JSON

What I need is,
but what i got is,
How can I remove "#attributes" from the result.
The below code works for me:
// Cleans up ugly JSON data by removing #attributes tag
function cleanup_json ($ugly_json) {
if (is_object($ugly_json)) {
$nice_json = new stdClass();
foreach ($ugly_json as $attr => $value) {
if ($attr == '#attributes') {
foreach ($value as $xattr => $xvalue) {
$nice_json->$xattr = $xvalue;
}
} else {
$nice_json->$attr = cleanup_json($value);
}
}
return $nice_json;
} else if (is_array($ugly_json)) {
$nice_json = array();
foreach ($ugly_json as $n => $e) {
$nice_json[$n] = cleanup_json($e);
}
return $nice_json;
} else {
return $ugly_json;
}
}
// Convert XML to JSON
function convert_to_json ($xml_string) {
$xml = simplexml_load_string($xml_string);
$ugly_json = json_decode(json_encode($xml));
$nice_json = cleanup_json($ugly_json);
return json_encode($nice_json, JSON_PRETTY_PRINT | JSON_UNESCAPED_SLASHES);
}
Try this. It may work for you.
$xml = simplexml_load_string($string);
$json = json_encode($xml, true);

Concatenate object items

I have the following function which works fine.
function ($objects, $items = array())
{
$result = array();
foreach ($objects as $object) {
$result[$object->id] = $object->first_name . ' ' . $object->last_name;
}
return $result;
}
However, I would like to pass in an array to $items, and have that exploded, so that I dont have to specify first_name and last_name manually.
If $item was only a single value (and not an array), then it would be simple:
$result[$object->id] = $object->$item;
But I have no idea how to make this work if $items contains multiple values and I want to join them with a space. Something like, the following, but I need to get the $object in there
$items = array('first_name', 'last_name');
$result[$object->id] = implode(' ', $items);
Do I get you right that you`d like to use the strings in $item as property-names of $object?
function ($objects, $items = array())
{
$result = array();
foreach ($objects as $object) {
$valuesToAssign = array();
foreach ($items as $property) {
$valuesToAssign[] = $object->$property;
}
$result[$object->id] = implode(' ', $valuesToAssign);
}
return $result;
}
I have no idea to avoid the second foreach, but that gives you the desired result.
Not sure if I got you right, but how about this:
function foo($objects, $items = array()) {
$result = array();
$keys = array_flip($items);
foreach ($objects as $object) {
// Cast object to array, then omit all the stuff that is not in $items
$values = array_intersect_key((array) $object, $keys);
// Glue the pieces together
$result[$object->id] = implode(' ', $values);
}
return $result;
}
Demo: http://codepad.viper-7.com/l8vmGr

Categories