<?php
/*
(c) 2000 Hans Anderson Corporation. All Rights Reserved.
You are free to use and modify this class under the same
guidelines found in the PHP License.
-----------
bugs/me:
http://www.hansanderson.com/php/
me@hansanderson.com
-----------
YOU NEED PHP4 FOR THIS -- even if you have XML support in PHP3
(sorry, I hate that, too, but I use some other PHP4 functionality)
-----------
What class.xml.php is:
A very, very easy to use XML parser class. It uses PHP's XML functions
for you, returning all the objects in the XML file in an easy to use
Tree. It also can be used as a statistics-type program, as you can
use the size() method to find out how many of each elements there are.
-----------
Sample use:
require('class.xml.php');
$file = "somexmldata.xml";
$data = implode("",file($file)) or die("could not open XML input file");
$xml = new xml($data);
for($i=0;$i<$xml_item_url->size();$i++) {
print $xml_item_url->get($i) . "\n\n";
}
(that's it! slick, huh?)
-----------
Two ways to call:
$xml = new xml($data);
- or -
$xml = new xml($data,"jellyfish");
The second argument (jellyfish) is optional. Default is 'xml'.
if you have
"<html><head><title>Title stuff</title></head></html>"
the object you get would look like this:
$xml_html_head_title (value is "Title stuff")
but if you created the object like
$xml = new xml($data,"jellyfish");
then your object would look like this:
$jellyfish_html_head_title (value is "Title stuff")
Comprende? It's only really needed if you want something else to
start off your object names. If you don't understand this, just
call it like $xml = new xml($data);
----------
Class Methods You Will Use:
where 'classname' is the name of an XML object, like xml_head_title
classname->get($idx);
- returns array item found at $idx
classname->size();
- returns the size of the storage array
-----------
Explanation:
This class takes valid XML data as an argument and
returns all the information in a concise little
tree of objects.
Here's how it works:
Data:
<html>
<head>
<title>Hans Anderson's XML Class</title>
</head>
<body>
</body>
</html>
Run the data through my class, then access the title like this:
$xml_html_head_title->get(0);
That is an object, but you don't have to worry about
contructing it. The data is stored in an array in the
object, so the ->get(0) is a way to get the data out. If
there were more than one item, you'd do a loop just like
any array:
for($i=0;$i<$xml_html_head_title->size();$i++) {
print $xml_html_head_title->get($i) . "\n";
}
Yes, the variable names *are* long, but it's the best
way to create the tree, IMO.
-----------
Errors:
if you get the error "Fatal error: Call to a member function on a non-object",
you have misspelled the name of the XML tags, or you have the case wrong.
*/
class stor {
var $a; // holds data
function add($data) {
$this->a[] = $data;
}
function get($idx) {
return $this->a[$idx];
}
function size() {
return sizeof($this->a);
}
} // end class stor;
class xml {
// initialize some variables
var $identifier='xml';
var $current_tag='';
var $separator='_x_';
var $delimiter='_';
var $xml_parser;
/* Here are the XML functions needed by expat */
function startElement($parser, $name, $attrs) {
// global current tag, separator, tagdata?
$this->current_tag .= $this->separator . $name;
if(count($attrs)>0) $this->tagdata = $attrs;
}
function endElement($parser, $name) {
//global $current_tag, $tagdata, $separator ?
$curtag = $this->identifier . str_replace($this->separator,$this->delimiter,$this->current_tag);
if(!is_array($this->tagdata)) $this->tagdata = trim($this->tagdata);
if($this->tagdata) {
if(is_object($GLOBALS["$curtag"])) {
$GLOBALS["$curtag"]->add($this->tagdata);
} else {
$GLOBALS["$curtag"] = new stor;
$GLOBALS["$curtag"]->add($this->tagdata);
}
} else {
// if there is no cdata, we still stor something
// in the array, so we can count the levels later
if(is_object($GLOBALS["$curtag"])) {
$GLOBALS["$curtag"]->add(FALSE);
} else {
$GLOBALS["$curtag"] = new stor;
$GLOBALS["$curtag"]->add(FALSE);
}
}
// overwrite curtag, no longer needing the old one
$curtag = strrev($this->current_tag);
$curtag = substr($curtag,strpos($curtag,$this->separator)+strlen($this->separator));
$curtag = strrev($curtag);
$this->current_tag = $curtag;
$this->tagdata = '';
return TRUE;
}
function characterData($parser, $cdata) {
$this->tagdata .= $cdata;
}
// this is automatically called when the class is initialized
function xml($data,$identifier='xml') {
$this->identifier = $identifier;
// are we using php4 or better?
//print phpversion();
// create parser object
$this->xml_parser = xml_parser_create();
// set up some options and handlers
xml_set_object($this->xml_parser,$this);
xml_parser_set_option($this->xml_parser,XML_OPTION_CASE_FOLDING,0);
xml_set_element_handler($this->xml_parser, "startElement", "endElement");
xml_set_character_data_handler($this->xml_parser, "characterData");
if (!xml_parse($this->xml_parser, $data, TRUE)) {
die(sprintf("XML error: %s at line %d",
xml_error_string(xml_get_error_code($this->xml_parser)),
xml_get_current_line_number($this->xml_parser)));
}
// we are done with the parser, so let's free it
xml_parser_free($this->xml_parser);
}
} // thus, we end our class xml
?>
|