I need to get very specific values from a feed such as this:
http://gdata.youtube.com/feeds/api/videos/iIp7OnHXBlo
Some of the nodes I have to read from these bizarrely-formatted XML feed are:
<title type="text">Uploading YouTube Videos with the PHP Client Library</title>
<media:content url="http://www.youtube.com/v/iIp7OnHXBlo?version=3&f=videos&app=youtube_gdata" type="application/x-shockwave-flash" medium="video" isDefault="true" expression="full" duration="466" yt:format="5"/>
<media:content url="rtsp://v3.cache7.c.youtube.com/CiILENy73wIaGQlaBtdxOnuKiBMYDSANFEgGUgZ2aWRlb3MM/0/0/0/video.3gp" type="video/3gpp" medium="video" expression="full" duration="466" yt:format="1"/>
<media:description type="plain">Jochen Hartmann demonstrates the basics of how to use the PHP Client Library with the YouTube Data API. [...]</media:description>
<media:thumbnail url="http://i.ytimg.com/vi/iIp7OnHXBlo/0.jpg" height="360" width="480" time="00:03:53"/>
<media:thumbnail url="http://i.ytimg.com/vi/iIp7OnHXBlo/1.jpg" height="90" width="120" time="00:01:56.500"/>
<media:thumbnail url="http://i.ytimg.com/vi/iIp7OnHXBlo/2.jpg" height="90" width="120" time="00:03:53"/>
<media:thumbnail url="http://i.ytimg.com/vi/iIp7OnHXBlo/3.jpg" height="90" width="120" time="00:05:49.500"/>
<yt:duration seconds="466"/>
Of course that using the Zend Framework API for GData is absolutely out of the question (1225 files and 49 MB just to parse an XML file? Yeah, sure... My Lord.
I need to use the lastRSS parser or any built-in XML functions from PHP, as any person in his right mind would. Thanks in advance for any tips.
Another solution is to use this excellent xml2Array class: it will basically transform the xml into an associative array that's super easy to use.
For example the youtube xml you posted becomes:
Array
(
[ENTRY] => Array
(
[XMLNS] => http://www.w3.org/2005/Atom
[XMLNS:MEDIA] => http://search.yahoo.com/mrss/
[XMLNS:GD] => http://schemas.google.com/g/2005
[XMLNS:YT] => http://gdata.youtube.com/schemas/2007
[ID] => Array
(
Etc.
class xml2Array
{
var $stack=array();
var $stack_ref;
var $arrOutput = array();
var $resParser;
var $strXmlData;
function push_pos(&$pos)
{
$this->stack[count($this->stack)]=&$pos;
$this->stack_ref=&$pos;
}
function pop_pos()
{
unset($this->stack[count($this->stack)-1]);
$this->stack_ref=&$this->stack[count($this->stack)-1];
}
function parse($strInputXML)
{
$this->resParser = xml_parser_create ();
xml_set_object($this->resParser,$this);
xml_set_element_handler($this->resParser, "tagOpen", "tagClosed");
xml_set_character_data_handler($this->resParser, "tagData");
$this->push_pos($this->arrOutput);
$this->strXmlData = xml_parse($this->resParser,$strInputXML );
if(!$this->strXmlData)
{
die(sprintf("XML error: %s at line %d",
xml_error_string(xml_get_error_code($this->resParser)),
xml_get_current_line_number($this->resParser)));
}
xml_parser_free($this->resParser);
return $this->arrOutput;
}
function tagOpen($parser, $name, $attrs)
{
if (isset($this->stack_ref[$name]))
{
if (!isset($this->stack_ref[$name][0]))
{
$tmp=$this->stack_ref[$name];
unset($this->stack_ref[$name]);
$this->stack_ref[$name][0]=$tmp;
}
$cnt=count($this->stack_ref[$name]);
$this->stack_ref[$name][$cnt]=array();
if (isset($attrs))
$this->stack_ref[$name][$cnt]=$attrs;
$this->push_pos($this->stack_ref[$name][$cnt]);
}
else
{
$this->stack_ref[$name]=array();
if (isset($attrs))
$this->stack_ref[$name]=$attrs;
$this->push_pos($this->stack_ref[$name]);
}
}
function tagData($parser, $tagData)
{
if(trim($tagData))
{
if(isset($this->stack_ref['DATA']))
$this->stack_ref['DATA'] .= $tagData;
else
$this->stack_ref['DATA'] = $tagData;
}
}
function tagClosed($parser, $name)
{
$this->pop_pos();
}
}