0

Maybe I just need to get some sleep, but I cannot figure this one out :( ... My problem is that the json output I have changes when it contains a single order vs multiple orders.

Here is an example json output of a single order:

{"Ack":"Success","OrderArray":{"Order":{"OrderID":"165921181012"}},"OrdersPerPage":"10","PageNumber":"1","ReturnedOrderCountActual":"1"}

Here is an example json output of multiple orders:

{"Ack":"Success","OrderArray":{"Order":[{"OrderID":"165921181012","OrderStatus":"Completed"},{"OrderID":"151330738592-1109250612005","OrderStatus":"Completed"},{"OrderID":"380931137567-501668037025","OrderStatus":"Completed"}]},"OrdersPerPage":"10","PageNumber":"1","ReturnedOrderCountActual":"3"}

The difference being the [ ]

Right now my code is as follows:

$json_o = json_decode($json);
foreach ($json_o->OrderArray->Order as $orderkey=>$o) { echo $o->OrderID; }

My first thought was to write an if statement to handle single orders Edit**, I can detect the difference between the single orders vs multiple orders using is_array / is_object. But, is there a way to add the [ ] (force a single element array) around json "OrderID" so that the foreach loop would run even if only one order exists?

imos
  • 165
  • 1
  • 8
  • if you control how the json is generated, make both cases the same – charlietfl Jul 06 '14 at 13:05
  • `Order` _is_ an array in your second case, so `is_array` should detect that. You neglected to show us how exactly you used it, so we can’t tell you what you did wrong. – CBroe Jul 06 '14 at 13:10
  • So I dumped what was going on and I saw that I am actually able to use is_array to detect if its an array or not. But, I am still wondering if there is a way I can somehow force a single element array so that the foreach loop does not bug out. – imos Jul 07 '14 at 01:49

2 Answers2

0

If you are also generating the JSON yourself, normalise the format at that point. 'Order' should always be an array of orders, even if it only contains a single element. That, or set some other flag which signifies whether it contains only a single order or multiple orders.

If you're only consuming the JSON and have no choice:

if (!isset($json_o->OrderArray[0])) {
    $json_o->OrderArray = array($json_o->OrderArray);
}

foreach ($json_O->OrderArray as $order) ...
deceze
  • 510,633
  • 85
  • 743
  • 889
  • oddly enough $json_o->OrderArray = array($json_o->OrderArray); does not allow the foreach loop to run through if there is only one object. – imos Jul 07 '14 at 01:46
0

So I found another question that dealt with a similar issue. php-convert-xml-to-json-group-when-there-is-one-child With this you can customize the json encode and add brackets where it is needed. The example below adds the array around the "status" element.

    <?php
/**
 * PHP convert XML to JSON group when there is one child
 * @link https://stackoverflow.com/q/16935560/367456
 */
$bufferXml = <<<STRING
<?xml version="1.0" encoding="UTF-8"?>
<searchResult>
    <status>
        <userName1>johndoe</userName1>
    </status>
    <users>
        <user>
            <userName>johndoe</userName>
        </user>
        <user>
            <userName>johndoe1</userName>
            <fullName>John Doe</fullName>
        </user>
        <user>
            <userName>johndoe2</userName>
        </user>
        <user>
            <userName>johndoe3</userName>
            <fullName>John Doe Mother</fullName>
        </user>
        <user>
            <userName>johndoe4</userName>
        </user>
    </users>
</searchResult>
STRING;
class XML2JsonSearchResult extends SimpleXMLElement implements JsonSerializable
{
    public function jsonSerialize()
    {
        $name = $this->getName();
        if ($name == 'status') {
            $value = (array)$this;
            return [$value];
        }
        return $this;
    }
}
$converter = new XML2JsonSearchResult($bufferXml);
echo "<pre>";
echo json_encode($converter, JSON_PRETTY_PRINT);
echo "</pre>";
Community
  • 1
  • 1
imos
  • 165
  • 1
  • 8