My question is, how can I access the prod array?
You can't. Because there is no array. But it's okay you ask, it's just print_r has been fooling you a little. SimpleXMLElement is an object and it can change what will be shown when it gets print_r'ed and it fakes you some arrays there.
Some basics to the rescue:
$data represents the document element of the XML you have. In case you're in doubt what's in the XML, instead of print_r look into $data->asXML() (if you look through your browser view source or hint the output as plain-text otherwise the browser will hide all tags).
$data['prod'] gives you the attribute named prod on that document element. As there is none, it returns null:
var_dump($data['prod']); --- NULL
And the count of NULL is 0:
var_dump(count(NULL)); --- int(0)
You neither want to look into the document element nor do you want to look-up attributes. You're interested in the child-elements named prod inside the merchant element.
So first obtain the first merchant element:
$merchant = $data->merchant;
You obtain elements with object access, that is with the object operator ->.
And the get the count of the number of child elements named prod:
var_dump(count($merchant->prod)); --- int(3)
As this shows, I've got three (3) children named prod inside the merchant element represented by $merchant.
So you don't need any array here, the SimpleXMLElement allows you access to all the XML-elements inside the XML document.
As written earlier, the array brackets are used for array-access. So it looks like an array, but it is actually an object. It has been used to access the attributes. But this is only true, if the key is not a number. If it's a number, it will access the n-th named element:
var_dump($merchant->prod[0]->asXML());
Will give the XML of the first prod element of the merchant element:
string(94) "<prod id="690579815" lang="en" pre_order="no" web_offer="yes" in_stock="yes">product #1</prod>"
As it is the first element, you can obtain it's id attribute as well:
var_dump($merchant->prod[0]['id']->asXML());
Which returns exactly that attribute:
string(15) " id="690579815""
But it does not stop here. Each of these SimpleXMLElement objects of XML elements and attributes can be cased to string:
var_dump((string)$merchant->prod[0]); --- string(10) "product #1"
var_dump((string)$merchant->prod[0]['id']); --- string(9) "690579815"
Which is most often the actual information you're looking for. When you use echo or similar, this string-casting is done automatically btw.
echo $merchant->prod[0]; // prints: "product #1"
Similar to arrays (and object), you can also iterate over each SimpleXMLElement. For example the $merchant element:
foreach ($merchant as $children)
{
echo $children->asXML(), "\n";
}
Gives:
<merchant id="1" name="companyname">
<prod id="690579815" lang="en" pre_order="no" web_offer="yes" in_stock="yes">product #1</prod>
<prod id="250544605" lang="en" pre_order="no" web_offer="yes" in_stock="yes">product #2</prod>
<prod id="360355798" lang="en" pre_order="no" web_offer="yes" in_stock="yes">product #3</prod>
</merchant>
Which is a single element. So more interesting this is with named child-elements:
foreach ($merchant->prod as $prod)
{
echo $prod->asXML(), "\n";
}
This now gives all children named prod one after the other:
<prod id="690579815" lang="en" pre_order="no" web_offer="yes" in_stock="yes">product #1</prod>
<prod id="250544605" lang="en" pre_order="no" web_offer="yes" in_stock="yes">product #2</prod>
<prod id="360355798" lang="en" pre_order="no" web_offer="yes" in_stock="yes">product #3</prod>
You find this as well explained in Basic SimpleXML usage in the PHP manual. Consult it as another source.
Just take these rules:
print_r and var_dump cheat on you when used with SimpleXMLElement
- You don't need an array when you've got a SimpleXMLElement already
- In case SimpleXMLElement is too simple in data-access, it's sister DOM library can be used easily as you can switch over to it.
See the full example.
$datais not an array, it's an instance ofSimpleXMLElement, use it accordingly:$data->merchant->prod[0];