Hi,
i have a question about how PHP XML support works, in particular how
handler methods are called.
if i have element-only tag, like:
<host>
<name>foo</name>
<location>usa</location>
</host>
and i invoke xml parser on this, should my registered pcDataHandler
method be called when tag <host> is being parsed, or parser is "smart"
enough not too, becasue their is no #PCDATA in the <host> tag?
I have smth like that going on, my pcDataHandler function is beeing
called 2 times too many, and on every single tag(even the one's with no
#PCDATA in them).
I have a feeling a have a gross mistake smwhere, but i can't find it.
please help. and sorry for longwinded message.
this is the snap-shot of my XML data file:
<section publish="true" release_host_info="false"
updated="213237827347">
<section_name>General Information</section_name>
<host>
<first_name>Janine</first_name>
<middle_name>Nadia</middle_name>
<last_name>Mohammed</last_name>
<email>[EMAIL PROTECTED]</email>
</host>
...
</section>
and this is the correcponding DTD shiplet:
<!ELEMENT section (section_name, host, question*)>
<!ATTLIST section
publish (true|false) "true"
release_host_info (true|false) "false"
updated CDATA #REQUIRED
>
<!ELEMENT section_name (#PCDATA)>
<!ELEMENT host (first_name, middle_name?, last_name,
email)> <!-- defined earlier in the DTD -->
<!ELEMENT question (from, content, answer*)>
<!ATTLIST question
id ID #REQUIRED
publish_poster_info (yes|no|anonymous)
"yes"
post_date CDATA #REQUIRED
>
<!ELEMENT from (first_name, middle_name?,
last_name, email)>
<!ELEMENT content (#PCDATA)>
<!ELEMENT answer (#PCDATA)>
<!ATTLIST answer
posted CDATA #REQUIRED
>
this is the sniplet of debug output (code follows):
before assigment currentTag = section_name - after assigment currentTag
= host
pcdata = <!--MY COMMENT: should pcDataHandler called on host
tag, it doesn't have any PCDATA?! -->
pcdata =
before assigment currentTag = host - after assigment currentTag =
first_name
pcdata = Janine
end of tag = first_name
pcdata = <!--MY COMMENT: why pcDataHandler is beeing called
extra 2 times on this tag?! -->
pcdata =
before assigment currentTag = first_name - after assigment currentTag =
middle_name
pcdata = Nadia
end of tag = middle_name
pcdata =
pcdata =
before assigment currentTag = middle_name - after assigment currentTag =
last_name
pcdata = Mohammed
end of tag = last_name
pcdata =
pcdata =
before assigment currentTag = last_name - after assigment currentTag =
email
pcdata = [EMAIL PROTECTED]
end of tag = email
pcdata =
pcdata =
end of tag = host
pcdata =
pcdata =
pcdata =
...
the parser code:
<?php
class faqHandler {
var $parser; //xml parser
var $file;
var $currentTag;
var $ATTRIBS = array();
var $FAQ_HEAD = array();
function faqHandler($file="faq.xml", $fold="false") {
$this->file = $file;
$this->parser = xml_parser_create();
//xml_set_object($this->parser, &$this);
xml_parser_set_option($this->parser, XML_OPTION_CASE_FOLDING, $fold);
xml_set_element_handler($this->parser, "startTagHandler",
"endTagHandler");
xml_set_character_data_handler($this->parser, "pcDataHandler");
}
function parseNow() {
xml_set_object($this->parser, &$this);
if ( ! ($fd = fopen($this->file, "r")) ) {
die(sprintf("Could not open xml file %s", $this->file));
}
while ( ($rawxml = fread($fd, 4096)) ) {
if ( !(xml_parse($this->parser, $rawxml, feof($fd))) ) {
die(sprintf("<font color=\"#FF0000\" size=\"+3\">XML error in file
%s at line%d possition %d</font>",
$this->file,
xml_get_current_line_number($this->parser),
xml_get_current_column_number($this->parser) ));
}//eo if
}//ei while
}
function clean() {
xml_parser_free($this->parser);
}
function getTagContent($tag_name) {
}
function startTagHandler($parser, $name, $attrib) {
echo("before assigment currentTag = $this->currentTag - ");
$this->currentTag = $name;
echo("after assigment currentTag = $this->currentTag <br>");
switch(strtolower($name)) {
case "faq" : {
$this->ATTRIBS["faq_version"] = $attrib["version"];
$this->ATTRIBS["faq_revised"] = $attrib["revised"];
break;
}
case "faq_head" : {
break;
}
case "zip" : {
$this->ATTRIBS["zip_location"] = $attrib["location"];
break;
}
case "phone" : {
$this->ATTRIBS["fone_area"] = $attrib["area"];
$this->ATTRIBS["fone_ext"] = $attrib["ext"];
break;
}
case "fax" : {
$this->ATTRIBS["fax_area"] = $attrib["area"];
$this->ATTRIBS["fax_ext"] = $attrib["ext"];
break;
}
}//eo switch
}
function pcDataHandler($parser, $pcdata) {
echo("pcdata = $pcdata <br>");
//echo("inside pcDataHandler: currentTag = $this->currentTag && pcData
= $pcdata <br>");
//echo("current errorString value = " .
xml_error_string(xml_get_error_code($this->parser)) ."<br>" );
switch(strtolower($this->currentTag)) {
case "firm_name" : {
$this->FAQ_HEAD["firm_name"] = $pcdata;
//echo("pcdata = $pcdata");
break;
}
case "firm_location" : {
$this->FAQ_HEAD["firm_location"] = $pcdata;
break;
}
}//eo switch
}
function endTagHandler($parser, $name) {
echo("end of tag = $name <br>");
}
function cleanVars() {
}
function printFaqHeader() {
echo("<br>");
echo($this->FAQ_HEAD["firm_name"]); echo("did u get it?");
echo("<br>");
echo($this->ATTRIBS["faq_version"]);
echo("<br>");
echo($this->ATTRIBS["faq_revised"]);
echo("<br>");
echo($this->ATTRIBS["zip_location"]);
echo("<br>");
echo($this->ATTRIBS["fone_area"]);
echo("<br>");
echo($this->ATTRIBS["fone_ext"]);
echo("<br>");
echo($this->ATTRIBS["fax_area"]);
echo("<br>");
echo($this->ATTRIBS["fax_ext"]);
}
}//eo class faqHandler
?>
the faq.php code which intantiates the parser and calls the print
method:
<?php
require_once $FULL_PATH.$INCLUDE.$FAQ_XML_LIB;
$faq = new faqHandler("faq.xml", false);
$faq->parseNow();
// $faq->clean();
$faq->printFaqHeader();
?>
Thanks for your help,
alex
--
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php