Presentation is loading. Please wait.

Presentation is loading. Please wait.

Advanced XML and Web Services September 12, 2006 Robert Richards

Similar presentations


Presentation on theme: "Advanced XML and Web Services September 12, 2006 Robert Richards"— Presentation transcript:

1 Advanced XML and Web Services September 12, 2006 Robert Richards

2 Agenda Introduction to Terms and Concepts Introduction to Terms and Concepts Libxml Libxml DOM DOM SimpleXML SimpleXML SAX (ext/xml) SAX (ext/xml) XMLReader XMLReader XSL XSL XMLWriter XMLWriter SOAP (ext/soap) SOAP (ext/soap)

3 XML Namespaces An XML Namespace is a collection of names identified by a URI. An XML Namespace is a collection of names identified by a URI. They are applicable to elements and attributes. They are applicable to elements and attributes. Namespaces may or may not be associated with a prefix. Namespaces may or may not be associated with a prefix. xmlns:rob="urn:rob" xmlns:rob="urn:rob" xmlns=http://www.example.com/rob xmlns=http://www.example.com/robhttp://www.example.com/rob Attributes never reside within a default namespace. Attributes never reside within a default namespace. It is illegal to have two attributes with the same localname and same namespace on the same element. It is illegal to have two attributes with the same localname and same namespace on the same element.

4 XML Namespace Example John Smith 123 Here Jane Doe 456 Somewhere else

5 XML Namespace Example John Smith 123 Here Jane Doe 456 Somewhere else

6 Illegal Namespace Usage xmlns:ship="urn:order"> John Smith order:type="legal">John Smith

7 Illegal Namespace Usage xmlns:ship="urn:order"> John Smith order:type="legal">John Smith

8 Reserved Namespaces and Prefixes The prefix xml is bound to The prefix xml is bound to The prefix xmlns is bound to The prefix xmlns is bound to Prefixes should also not begin with the characters xml. Prefixes should also not begin with the characters xml.

9 Schemas and Validation Validation insures an XML document conforms to a set of defined rules. Validation insures an XML document conforms to a set of defined rules. Multiple mechanisms exist to write document rule sets: Multiple mechanisms exist to write document rule sets: Document Type Definition (DTD) Document Type Definition (DTD) XML Schema XML Schema RelaxNG RelaxNG

10 Document Type Definition (DTD) validation/courses-dtd.xml Basic Languages Introduction to Languages T11:13:01...

11 DTD and IDs validation/course-id.xml Basic Languages Introduction to Languages French I Introduction to French French II Intermediate French

12 XML Schema validation/course.xsd

13 RelaxNG validation/course.rng

14 XPath Language to locate and retrieve information from an XML document Language to locate and retrieve information from an XML document A foundation for XSLT A foundation for XSLT An XML document is a tree containing nodes An XML document is a tree containing nodes The XML document is the root node The XML document is the root node Locations are addressable similar to the syntax for a filesystem Locations are addressable similar to the syntax for a filesystem

15 XPath Reference Document xpath/courses.xml Basic Languages Introduction to Languages French I Introduction to French French II Intermediate French content

16 XPath Location Example xpath/location.php /courses/course/description //description /courses/*/description //description[ancestor::course] Expression: Resulting Nodset: Introduction to Languages Introduction to French Intermediate French

17 XPath Function Example xpath/function.php French II French II Intermediate French Intermediate French content content

18 XPath and Namespaces xpath/namespaces.php //title Empty NodeSet //t:title Basic Languages French I French II //defns Empty NodeSet //*[local-name()="defns"] content

19 PHP and XML PHP 5 introduced numerous interfaces for working with XML PHP 5 introduced numerous interfaces for working with XML The libxml2 library (http://www.xmlsoft.org/) was chosen to provide XML support The libxml2 library (http://www.xmlsoft.org/) was chosen to provide XML support The sister library libxslt provides XSLT support The sister library libxslt provides XSLT support I/O is handled via PHP streams I/O is handled via PHP streams

20 XML Entensions for PHP 5 ext/libxml ext/libxml ext/xml (SAX push parser) ext/xml (SAX push parser) ext/dom ext/dom ext/simplexml ext/simplexml ext/xmlreader (pull parser) ext/xmlreader (pull parser) ext/xmlwriter ext/xmlwriter ext/xsl ext/xsl ext/wddx ext/wddx ext/soap ext/soap

21 Libxml Contains common functionality shared across extensions. Contains common functionality shared across extensions. Defines constants to modify parse time behavior. Defines constants to modify parse time behavior. Provides access to streams context. Provides access to streams context. Allows modification of error handling behavior for XML based extensions. Allows modification of error handling behavior for XML based extensions.

22 Libxml: Parser Options LIBXML_NOENT Substitute entities with replacement content LIBXML_DTDLOAD Load subsets but do not perform validation LIBXML_DTDATTR Create defaulted attributes defined in DTD LIBXML_DTDVALID Loads subsets and perform validation LIBXML_NOERROR Suppress parsing errors from libxml2 LIBXML_NOWARNING Suppress parser warnings from libxml2 LIBXML_NOBLANKS Remove insignificant whitespace on parsing LIBXML_XINCLUDE Perform XIncludes during parsing LIBXML_NOCDATA Merge CDATA nodes in Text nodes LIBXML_NONET Disable network access when loading

23 Libxml: Error Handling bool libxml_use_internal_errors ([bool use_errors]) void libxml_clear_errors ( void ) LibXMLError libxml_get_last_error ( void ) array libxml_get_errors ( void )

24 Libxml: LibXMLError Class: LibXMLError Properties (Read-Only): (int) level (int) code (int) column (string) message (string) file (int) line LibXMLError::code Values: LIBXML_ERR_NONE LIBXML_ERR_WARNING LIBXML_ERR_ERROR LIBXML_ERR_FATAL

25 LibXMLError Example libxml/error.php loadXML(' '); /* New Error Handling */ libxml_use_internal_errors(TRUE); if (! $dom->loadXML('root')) { $arrError = libxml_get_errors(); foreach ($arrError AS $xmlError) { var_dump($xmlError); } } else { print "Document Loaded"; } ?>

26 LibXMLError Result PHP Warning: DOMDocument::loadXML(): Premature end of data in tag root line 1 in Entity, line: 1 in /home/rrichards/workshop/libxml/error.php on line 4 Warning: DOMDocument::loadXML(): Premature end of data in tag root line 1 in Entity, line: 1 in /home/rrichards/workshop/libxml/error.php on line 4 New Error Handling: object(LibXMLError)#2 (6) { ["level"]=> int(3) ["level"]=> int(3) ["code"]=> int(4) ["code"]=> int(4) ["column"]=> int(1) ["column"]=> int(1) ["message"]=> string(34) "Start tag expected, ' string(34) "Start tag expected, '<' not found" ["file"]=> string(0) "" ["file"]=> string(0) "" ["line"]=> int(1) ["line"]=> int(1)}

27 DOM Tree based parser Tree based parser Allows for creation and editing of XML documents Allows for creation and editing of XML documents W3C Specification with DOM Level 2/3 compliancy W3C Specification with DOM Level 2/3 compliancy Provides XPath support Provides XPath support Provides XInclude Support Provides XInclude Support Ability to work with HTML documents Ability to work with HTML documents Zero copy interoperability with SimpleXML Zero copy interoperability with SimpleXML Replacement for ext/domxml from PHP 4 Replacement for ext/domxml from PHP 4

28 DOMNode Classes DOMDocument DOMDocument DOMElement DOMElement DOMAttr DOMAttr DOMComment DOMComment DOMDocumentType DOMDocumentType DOMNotation DOMNotation DOMEntity DOMEntity DOMEntityReference DOMProcessingInstruction DOMNameSpaceNode DOMDocumentFragment DOMCharacterData DOMText DOMCdataSection

29 Additional DOM Classes DOMException DOMException DOMImplementation DOMImplementation DOMNodeList DOMNodeList DOMNamedNodeMap DOMNamedNodeMap DOMXPath DOMXPath

30 DOM: Sample Document Basic Languages Basic Languages Introduction to Languages Introduction to Languages T11:13: T11:13:01 French I French I Introduction to French Introduction to French T14:21: T14:21:37 French II French II Intermediate French Intermediate French T15:45: T15:45:44

31 DOM: Document Navigation dom/navigate.php /* Find first description element in subtrees */ function locateDescription($nodeset) { foreach ($nodeset AS $node) { foreach ($nodeset AS $node) { if ($node->nodeType == XML_ELEMENT_NODE && $node->nodeName == 'description') { if ($node->nodeType == XML_ELEMENT_NODE && $node->nodeName == 'description') { $GLOBALS['arNodeSet'][] = $node; $GLOBALS['arNodeSet'][] = $node; return; return; } if ($node->hasChildNodes()) { locateDescription($node->childNodes); } if ($node->hasChildNodes()) { locateDescription($node->childNodes); } }} $dom = new DOMDocument(); $dom->load('course.xml'); $root = $dom->documentElement; $arNodeSet = array(); if ($root->hasChildNodes()) { locateDescription($root->childNodes); } foreach ($arNodeSet AS $key=>$node) { print "#$key: ".$node->nodeValue."\n"; }

32 DOM: Document Navigation Results #0: Introduction to Languages #1: Introduction to French #2: Intermediate French

33 DOM:Document Navigation #2 dom/navigate-2.php load('course.xml'); $nodelist = $dom->getElementsByTagName('description'); foreach ($nodelist AS $key=>$node) { print "#$key: ".$node->nodeValue."\n"; } ?> Results: #0: Introduction to Languages #1: Introduction to French #2: Intermediate French

34 DOM: Navigation Optimized dom/navigate-optimized.php function locateDescription($node) { while($node) { while($node) { if ($node->nodeType == XML_ELEMENT_NODE && $node->nodeName == 'description') { if ($node->nodeType == XML_ELEMENT_NODE && $node->nodeName == 'description') { $GLOBALS['arNodeSet'][] = $node; $GLOBALS['arNodeSet'][] = $node; return; return; } locateDescription($node->firstChild); locateDescription($node->firstChild); $node = $node->nextSibling; $node = $node->nextSibling; }} $dom = new DOMDocument(); $dom->load('course.xml'); $root = $dom->documentElement; $arNodeSet = array(); locateDescription($root->firstChild); foreach ($arNodeSet AS $key=>$node) { print "#$key: ".$node->nodeValue."\n"; print "#$key: ".$node->nodeValue."\n";}

35 DOM: Creating a Simple Tree dom/create_simple_tree.php $doc = new DOMDocument(); $root = $doc->createElement("tree"); $doc->appendChild($root); $root->setAttribute("att1", "att1 value"); $attr2 = $doc->createAttribute("att2"); $attr2->appendChild($doc->createTextNode("att2 value")); $root->setAttributeNode($attr2); $child = $root->appendChild($doc->createElement("child")); $comment = $doc->createComment("My first Document"); $doc->insertBefore($comment, $root); $pi = $doc->createProcessingInstruction("php", 'echo "Hello World!"'); $root->appendChild($pi); $cdata = $doc->createCdataSection("special chars: & '"); $child->appendChild($cdata);

36 DOM: Simple Tree Output ']]>

37 DOM: Creating an Atom Feed dom/atom_feed_creation.php define('ATOMNS', 'http://www.w3.org/2005/Atom'); $feed_title = "Example Atom Feed"; $alt_url = "http://www.example.org/"; $feed = "http://www.example.org/atom/"; $doc = new DOMDocument("1.0", "UTF-8"); function create_append_Atom_elements($doc, $name, $value=NULL, $parent=NULL) { if ($value) if ($value) $newelem = $doc->createElementNS(ATOMNS, $name, $value); $newelem = $doc->createElementNS(ATOMNS, $name, $value);else $newelem = $doc->createElementNS(ATOMNS, $name); $newelem = $doc->createElementNS(ATOMNS, $name); if ($parent) { return $parent->appendChild($newelem); } if ($parent) { return $parent->appendChild($newelem); }} $feed = create_append_Atom_elements($doc, 'feed', NULL, $doc); create_append_Atom_elements($doc, 'title', $feed_title, $feed); create_append_Atom_elements($doc, 'subtitle', $feed_title, $feed); create_append_Atom_elements($doc, 'id', $alt_url, $feed); create_append_Atom_elements($doc, 'updated', date('c'), $feed); $doc->formatOutput = TRUE; print $doc->saveXML();

38 DOM: Creating an Atom Feed Result (initial structure) Example Atom Feed Example Atom Feed T01:39:40-05: T01:39:40-05:00

39 DOM: Creating an Atom Feed dom/atom_feed_creation.php $entry = create_append_Atom_elements($doc, 'entry', NULL, $feed); $entry = create_append_Atom_elements($doc, 'entry', NULL, $feed); $title = create_append_Atom_elements($doc, 'title', 'My first entry', $entry); $title = create_append_Atom_elements($doc, 'title', 'My first entry', $entry); $title->setAttribute('type', 'text'); $title->setAttribute('type', 'text'); $link = create_append_Atom_elements($doc, 'link', NULL, $entry); $link = create_append_Atom_elements($doc, 'link', NULL, $entry); $link->setAttribute('type', 'text/html'); $link->setAttribute('type', 'text/html'); $link->setAttribute('rel', 'alternate'); $link->setAttribute('rel', 'alternate'); $link->setAttribute('href', 'http://www.example.org/entry-url'); $link->setAttribute('href', 'http://www.example.org/entry-url'); $link->setAttribute('title', 'My first entry'); $link->setAttribute('title', 'My first entry'); $author = create_append_Atom_elements($doc, 'author', NULL, $entry); $author = create_append_Atom_elements($doc, 'author', NULL, $entry); create_append_Atom_elements($doc, 'name', 'Rob', $author); create_append_Atom_elements($doc, 'name', 'Rob', $author); create_append_Atom_elements($doc, 'id', 'http://www.example.org/entry-guid', $entry); create_append_Atom_elements($doc, 'id', 'http://www.example.org/entry-guid', $entry); create_append_Atom_elements($doc, 'updated', date('c'), $entry); create_append_Atom_elements($doc, 'updated', date('c'), $entry); create_append_Atom_elements($doc, 'published', date('c'), $entry); create_append_Atom_elements($doc, 'published', date('c'), $entry); $content = create_append_Atom_elements($doc, 'content', NULL, $entry); $content = create_append_Atom_elements($doc, 'content', NULL, $entry); $cdata = $doc->createCDATASection('This is my first Atom entry! More to follow'); $cdata = $doc->createCDATASection('This is my first Atom entry! More to follow'); $content->appendChild($cdata); $content->appendChild($cdata); $doc->formatOutput = TRUE; $doc->formatOutput = TRUE; print $doc->saveXML(); print $doc->saveXML();

40 DOM: Creating an Atom Feed Result dom/atomoutput.xml Example Atom Feed Example Atom Feed T01:53:59-05: T01:53:59-05:00 My first entry My first entry href="http://www.example.org/entry-url" title="My first entry"/> Rob Rob T01:53:59-05: T01:53:59-05:00 More to follow]]> More to follow]]>

41 DOM: Document Editing dom/editing.php $dom->load('atomoutput.xml'); $child = $dom->documentElement->firstChild; while($child && $child->nodeName != "entry") { $child = $child->nextSibling; } if ($child && ($child = $child->firstChild)) { while($child && $child->nodeName != "title") { $child = $child->nextSibling; } while($child && $child->nodeName != "title") { $child = $child->nextSibling; } if ($child) { if ($child) { $child->setAttribute('type', 'html'); $child->setAttribute('type', 'html'); $text = $child->firstChild; $text = $child->firstChild; $text->nodeValue = " My first entry "; $text->nodeValue = " My first entry "; while($child) { while($child) { if ($child->nodeName == "updated") { if ($child->nodeName == "updated") { $text = $child->firstChild; $text = $child->firstChild; $text->nodeValue = date('c'); $text->nodeValue = date('c'); break; break; } $child = $child->nextSibling; $child = $child->nextSibling; } }} print $dom->saveXML();

42 DOM: Editing dom/new_atomoutput.xml Example Atom Feed Example Atom Feed T01:53:59-05: T01:53:59-05:00 <em>My first entry</em> <em>My first entry</em> href="http://www.example.org/entry-url" title="My first entry"/> Rob Rob T02:29:22-05: T02:29:22-05: T01:53:59-05: T01:53:59-05:00 More to follow]]> More to follow]]>

43 DOM: Document Modification dom/modify.php /* Assume $entry refers to the first entry element within the Atom document */ while ($entry->hasChildNodes()) { $entry->removeChild($entry->firstChild); $entry->removeChild($entry->firstChild);}OR $node = $entry->lastChild; while($node) { $prev = $node->previousSibling; $prev = $node->previousSibling; $entry->removeChild($node); $entry->removeChild($node); $node = $prev; $node = $prev;} /* This Will Not Work! */ foreach($entry->childNodes AS $node) { $entry->removeChild($node); $entry->removeChild($node);} /* These will work */ $children = $entry->childNodes; $length = $children->length - 1; for ($x=$length; $x >=0; $x--) { $entry->removeChild($children->item($x)); } OR $elem = $entry->cloneNode(FALSE); $entry->parentNode->replaceChild($elem, $entry);

44 DOM and Namespaces name="ArrayOfint"> wsdl:arrayType="xsd:int[ ]"/>

45 Dom and Namepsaces dom/namespace.php define("SCHEMA_NS", "http://www.w3.org/2001/XMLSchema"); define("WSDL_NS", "http://schemas.xmlsoap.org/wsdl/"); $dom = new DOMDocument(); $root = $dom->createElementNS(SCHEMA_NS, "xsd:complexType"); $dom->appendChild($root); $root->setAttributeNS("http://www.w3.org/2000/xmlns/", "xmlns:wsdl", WSDL_NS); $root->setAttribute("name", "ArrayOfint"); $content = $root->appendChild(new DOMElement("xsd:complexContent", NULL, SCHEMA_NS)); $restriction = $content->appendChild(new DOMElement("xsd:restriction", NULL, SCHEMA_NS)); $restriction->setAttribute("base", "soapenc:Array"); $attribute = $restriction->appendChild(new DOMElement("xsd:attribute", NULL, SCHEMA_NS)); $attribute->setAttribute("ref", "soapenc:arrayType"); $attribute->setAttributeNS(WSDL_NS, "wsdl:arrayType", "xsd:int[]");

46 DOM and Xpath dom/xpath/dom-xpath.xml Cannery Row Cannery Row Grapes of Wrath Grapes of Wrath Of Mice and Men Of Mice and Men

47 DOM and Xpath dom/xpath/dom-xpath.php $doc = new DOMDocument(); $doc->load('dom-xpath.xml'); $xpath = new DOMXPath($doc); $nodelist = $xpath->query("//name"); print "Last Book Title: ".$nodelist->item($nodelist->length - 1)->textContent."\n"; $nodelist = $xpath->query("//name[ancestor::rare]"); print "Last Rare Book Title: ".$nodelist->item($nodelist->length - 1)->nodeValue."\n"; $inventory = print "Total Books: ".$inventory."\n"; $inventory = print "Total Classic Books: ".$inventory."\n"; $inventory = $xpath->evaluate("count(//book[parent::classics])"); print "Distinct Classic Book Titles: ".$inventory."\n";

48 DOM and Xpath Results /* $nodelist = $xpath->query("//name") $nodelist->item($nodelist->length - 1)->textContent */ Last Book Title: Of Mice and Men /* $xpath->query("//name[ancestor::rare]"); $nodelist->item($nodelist->length - 1)->nodeValue */ Last Rare Book Title: Cannery Row /* */ Total Books: 54 /* */ Total Classic Books: 50 /* $xpath->evaluate("count(//book[parent::classics])") */ Distinct Classic Book Titles: 2

49 DOM and Xpath w/Namespaces dom/xpath/dom-xpathns.xml Cannery Row Cannery Row Grapes of Wrath Grapes of Wrath Of Mice and Men Of Mice and Men To Kill a Mockingbird To Kill a Mockingbird

50 DOM and Xpath w/Namespaces dom/xpath/dom-xpathns.php $nodelist = $xpath->query("//name"); print "Last Book Title: ".$nodelist->item($nodelist->length - 1)->textContent."\n"; // Last Book Title: /* Why empty? */ $nodelist = $xpath->query("//bk:name"); print "Last Book Title: ".$nodelist->item($nodelist->length - 1)->textContent."\n"; // Last Book Title: Grapes of Wrath /* Why not "Of Mice and Men" */ $nodelist = $xpath->query("//bk:name[ancestor::rare]"); print "Last Rare Book Title: ".$nodelist->item($nodelist->length - 1)->nodeValue."\n"; // Last Rare Book Title: /* Why empty? */ $xpath->registerNamespace("rt", "http://www.example.com/store"); $nodelist = $xpath->query("//bk:name[ancestor::rt:rare]"); print "Last Rare Book Title: ".$nodelist->item($nodelist->length - 1)->nodeValue."\n"; // Last Rare Book Title: Cannery Row $xpath->registerNamespace("ext", "http://www.example.com/ExteralClassics"); $nodelist = $xpath->query("(//bk:name) | (//ext:name)"); print "Last Book Title: ".$nodelist->item($nodelist->length - 1)->textContent."\n"; // Last Book Title: To Kill a Mockingbird

51 DOM and Xpath w/Namespaces dom/xpath/dom-xpathns.php $xpath->registerNamespace("bk2", "http://www.example.com/classicbook"); $nodelist = $xpath->query("//bk2:name"); print "Last Book Title (bk2): " print $nodelist->item($nodelist->length - 1)->textContent."\n"; // Last Book Title (bk2): Of Mice and Men Complete Results: Last Book Title: Last Book Title: Grapes of Wrath Last Rare Book Title: Last Rare Book Title: Cannery Row Last Book Title: To Kill a Mockingbird Last Book Title (bk2): Of Mice and Men

52 Performing Validation dom/validation/validate.php $doc = new DOMDocument(); print "DTD Validation:\n"; $doc->load('courses-dtd.xml', LIBXML_DTDVALID); /* No errors means document is valid */ if ($doc->validate()) { print " Document Is Valid\n"; } print "DTD Validation FAILURE:\n"; $doc->load('course-id.xml'); if ($doc->validate()) { print " Document Is Valid\n"; } $doc->load('course.xml'); print "\nXML Schema Validation:\n"; if ($doc->schemaValidate('course.xsd')) { print " Document is valid\n"; } $doc->load('course.xml'); print "\nRelaxNG Validation:\n"; if ($doc->relaxNGValidate('course.rng')) { print " Document is valid\n"; }

53 Performing Validation Results DTD Validation: Document Is Valid Document Is Valid DTD Validation FAILURE: Warning: DOMDocument::validate(): No declaration for element courses in /home/rrichards/workshop/dom/validation/validate.php on line 11 Warning: DOMDocument::validate(): No declaration for element course in /home/rrichards/workshop/dom/validation/validate.php on line 11 Warning: DOMDocument::validate(): No declaration for element title in /home/rrichards/workshop/dom/validation/validate.php on line XML Schema Validation: Document is valid Document is valid RelaxNG Validation: Document is valid Document is valid

54 Extending DOM Classes Overriding the constructor requires the parent constructor to be called. Overriding the constructor requires the parent constructor to be called. Properties built into the DOM classes cannot be overridden. Properties built into the DOM classes cannot be overridden. Methods built into the DOM classes may can be overridden. Methods built into the DOM classes may can be overridden. The lifespan of an extended object is that of the object itself. The lifespan of an extended object is that of the object itself.

55 Extending DOM Classes dom/extending/ extending.php class customElement extends DOMElement { } class customDoc extends DOMDocument { public $nodeName = "customDoc"; public $nodeName = "customDoc"; function __construct($rootName) { function __construct($rootName) { parent::__construct(); parent::__construct(); if (! empty($rootName)) { if (! empty($rootName)) { $element = $this->appendChild(new DOMElement($rootName)); } $element = $this->appendChild(new DOMElement($rootName)); } } function createElement($name, $value, $parent=NULL) { function createElement($name, $value, $parent=NULL) { $custom = new customElement($name, $value); $custom = new customElement($name, $value); if ($parent && ($parent instanceof DOMElement)) { if ($parent && ($parent instanceof DOMElement)) { $parent->appendChild($custom); } $parent->appendChild($custom); } return $custom; return $custom; }} $myc = new customDoc("root"); $myelement = $myc->createElement("myname", "myvalue", $myc->documentElement); if ($myelement instanceof customElement) { print "This is a customElement\n"; } print $myc->nodeName."\n"; print $myc->saveXML();

56 DOM Object Scope dom/extending/object_scope.php class customElement extends DOMElement { } function changeit($doc) { $myelement = new customElement("custom", "element2"); $myelement = new customElement("custom", "element2"); $doc->replaceChild($myelement, $doc->documentElement); print "Within changeit function: ".get_class($doc->documentElement)."\n"; } $doc = new DOMDocument(); $myelement = $doc->appendChild(new customElement("custom", "element")); print "After Append: ".get_class($myelement)."\n"; unset($myelement); print "After unset: ".get_class($doc->documentElement)."\n"; changeit($doc); print "Outside changeit(): ".get_class($doc->documentElement)."\n"; After Append: customElement After unset: DOMElement Within changeit function: customElement Outside changeit(): DOMElement

57 DOM: registerNodeClass dom/extending/register_node_class.php class customElement extends DOMElement { } function changeit($doc) { $myelement = new DOMElement("custom", "element2"); $myelement = new DOMElement("custom", "element2"); $doc->replaceChild($myelement, $doc->documentElement); print "Within changeit function: ".get_class($doc->documentElement)."\n"; } $doc = new DOMDocument(); $doc->registerNodeClass('DOMElement', 'customElement'); $myelement = $doc->appendChild($doc->createElement("custom", "element")); print "After Append: ".get_class($myelement)."\n"; unset($myelement); print "After unset: ".get_class($doc->documentElement)."\n"; changeit($doc); print "Outside changeit(): ".get_class($doc->documentElement)."\n"; After Append: customElement After unset: customElement Within changeit function: DOMElement Outside changeit(): customElement

58 DOM:Common Issues DOM Objects and Sessions DOM Objects and Sessions Removing Nodes while iterating a Nodeset skips nodes Removing Nodes while iterating a Nodeset skips nodes XML Tree contains garbled characters XML Tree contains garbled characters Extended class is not returned from property or method Extended class is not returned from property or method Elements not being returned by ID Elements not being returned by ID Entity errors are issues when loading a document Entity errors are issues when loading a document New DTD is not recognized by document New DTD is not recognized by document

59 SimpleXML Provides simple access to XML documents Provides simple access to XML documents Operates only on elements and attributes Operates only on elements and attributes Contains XPath support Contains XPath support Allows for modifications to the XML Allows for modifications to the XML Zero copy interoperability with DOM Zero copy interoperability with DOM New in PHP New in PHP Elements and attributes can be added using addChild() and addAttribute() methods. Elements and attributes can be added using addChild() and addAttribute() methods. Node names can be retrieved by calling getName(). Node names can be retrieved by calling getName().

60 SimpleXML: Consuming Yahoo WebSearch simplexml/yahoo_rest_results.xml totalResultsAvailable="374000" totalResultsReturned="5" firstResultPosition="1"> Zend Technologies - PHP 5 In Depth - XML in PHP 5 - What's New? Zend Technologies - PHP 5 In Depth - XML in PHP 5 - What's New? XML in PHP 5 - What's New? By Christian Stocker. March... XML in PHP 5 - What's New? By Christian Stocker. March text/html text/html

61 SimpleXML: Consuming Yahoo WebSearch simplexml/reading_rest.php /* URL to Web Search service */ $url = 'http://api.search.yahoo.com/WebSearchService/V1/webSearch'; /* The query is separate here as the terms must be encoded. */ $url.= '?query='.rawurlencode('php5 xml'); /* Complete the URL adding App ID, limit to 5 results and only English results */ $url.= "&appid=zzz&results=5&language=en"; $sxe = simplexml_load_file($url); /* Check for number of results returned */ if ((int)$sxe['totalResultsReturned'] > 0) { /* Loop through each result and output title, url and modification date */ /* Loop through each result and output title, url and modification date */ foreach ($sxe->Result AS $result) { foreach ($sxe->Result AS $result) { print 'Title: '.$result->Title."\n"; print 'Title: '.$result->Title."\n"; print 'Url: '.$result->Url."\n"; print 'Url: '.$result->Url."\n"; print 'Mod Date: '.date ('M d Y', (int)$result->ModificationDate)."\n\n"; print 'Mod Date: '.date ('M d Y', (int)$result->ModificationDate)."\n\n"; }}

62 SimpleXML: Consuming Yahoo WebSearch RESULTS Title: Zend Technologies - PHP 5 In Depth - XML in PHP 5 - What's New? Url: Mod Date: Sep Title: FreshPorts -- textproc/php5-xml Url: Mod Date: Aug Title: PHP5 XML support? - Dev Shed Url: Mod Date: Aug Title: ONLamp.com -- Using PHP 5's SimpleXML Url: Mod Date: Sep Title: PHP5 XML/XSL - Rendering strings? - PHP Url: Mod Date: Sep

63 Cannery Row Cannery Row Grapes of Wrath Grapes of Wrath Of Mice and Men Of Mice and Men To Kill a Mockingbird To Kill a Mockingbird

64 SimpleXML: Namespaces simplexml/simplexml-namespace.php $store = simplexml_load_file('simplexml-xpathns.xml'); $books = $store->books; foreach ($books->classics AS $classic) { if ($classic->book) if ($classic->book) print $classic->book->name."\n\n"; print $classic->book->name."\n\n";} /* Why only one result?: To Kill a Mockingbird */ $x = 0; foreach ($books->classics AS $classics) { if ($x++ == 0) { if ($x++ == 0) { $children = $classics->children("http://www.example.com/classicbook"); $children = $classics->children("http://www.example.com/classicbook"); /* Print name for the books where book element resides in a prefixed namespace */ /* Print name for the books where book element resides in a prefixed namespace */ print $classics->children("http://www.example.com/book")->book->name."\n"; print $classics->children("http://www.example.com/book")->book->name."\n"; print $children->book->name."\n"; print $children->book->name."\n"; } else } else print $classic->book->name."\n"; print $classic->book->name."\n";}

65 SimpleXML: Namespaces Results To Kill a Mockingbird Grapes of Wrath Of Mice and Men To Kill a Mockingbird

66 SimpleXML: Xpath simplexml/simplexml-xpathns.php $sxe = simplexml_load_file('simplexml-xpathns.xml'); $nodelist = $sxe->xpath("//bk:name"); print "Last Book Title: ".$nodelist[count($nodelist) - 1]."\n"; $sxe->registerXPathNamespace("rt", "http://www.example.com/store"); $nodelist = $sxe->xpath("//bk:name[ancestor::rt:rare]"); print "Last Rare Book Title: ".$nodelist[count($nodelist) - 1]."\n"; $sxe->registerXPathNamespace("ext", "http://www.example.com/ExteralClassics"); $nodelist = $sxe->xpath("(//bk:name) | (//ext:name)"); print "Last Book Title: ".$nodelist[count($nodelist) - 1]."\n"; $sxe->registerXPathNamespace("bk2", "http://www.example.com/classicbook"); $nodelist = $sxe->xpath("//bk2:name"); print "Last Book Title (bk2): ".$nodelist[count($nodelist) - 1]."\n";

67 SimpleXML: XPath Results Last Book Title: Grapes of Wrath Last Rare Book Title: Cannery Row Last Book Title: To Kill a Mockingbird Last Book Title (bk2): Of Mice and Men

68 SimpleXML: Advanced Editing simplexml/editing.php $data = array(array('title'=>'Result 1', 'descript'=>'Res1 description'), array('title'=>'Result 2', 'descript'=>'description of Res2'), array('title'=>'Result 2', 'descript'=>'description of Res2'), array('title'=>'Result 3', 'descript'=>'This is result 3')); array('title'=>'Result 3', 'descript'=>'This is result 3')); class webservice extends simpleXMLElement { public function appendElement($name, $value=NULL) { public function appendElement($name, $value=NULL) { $node = dom_import_simplexml($this); $node = dom_import_simplexml($this); $newnode = $value ? new DOMElement($name, $value) : new DOMElement($name); $newnode = $value ? new DOMElement($name, $value) : new DOMElement($name); $node->appendChild($newnode); $node->appendChild($newnode); return simplexml_import_dom($newnode, 'webservice'); return simplexml_import_dom($newnode, 'webservice'); } } $rest = simplexml_load_string(' ', 'webservice'); $rest['num'] = count($data); foreach ($data AS $result_item) { $result = $rest->appendElement('result'); $result = $rest->appendElement('result'); $result->appendElement('title', $result_item['title']); $result->appendElement('title', $result_item['title']); $result->appendElement('description'); $result->appendElement('description'); $result->description = $result_item['descript']; } $result->description = $result_item['descript']; } print $rest->asXML();

69 SimpleXML: Advanced Editing Results Result 1 Result 1 Res1 description Res1 description Result 2 Result 2 description of Res2 description of Res2 Result 3 Result 3 This is result 3 This is result 3

70 SimpleXML: Advanced Editing PHP simplexml/editing_php513.php $data = array(array('title'=>'Result 1', 'descript'=>'Res1 description'), array('title'=>'Result 2', 'descript'=>'description of Res2'), array('title'=>'Result 2', 'descript'=>'description of Res2'), array('title'=>'Result 3', 'descript'=>'This is result 3')); array('title'=>'Result 3', 'descript'=>'This is result 3')); $rest = simplexml_load_string(' '); $rest['num'] = count($data); foreach ($data AS $result_item) { $result = $rest->addChild('result'); $result = $rest->addChild('result'); $result->addChild('title', $result_item['title']); $result->addChild('title', $result_item['title']); $result->addChild('description'); $result->addChild('description'); $result->description = $result_item['descript']; $result->description = $result_item['descript'];}$rest->asXML('editing_php513.xml');

71 SimpleXML: Removing data remove_data.php result->title); /* Delete the 2nd result element - ONLY WORKS in PHP */ unset($results->result[1]); print $results->asXML(); ?>

72 SimpleXML: Removing data RESULTS Res1 description Res1 description Result 3 Result 3 This is result 3 This is result 3

73 Simple API for XML (SAX) Event based push parser Event based push parser Low memory usage Low memory usage Works using function callbacks Works using function callbacks Almost completely compatible with ext/xml from PHP 4 Almost completely compatible with ext/xml from PHP 4 Default encoding is UTF-8 rather than ISO as it was in PHP 4 Default encoding is UTF-8 rather than ISO as it was in PHP 4

74 SAX: Source Document xml/xml_simple.xml xmlns="http://www.example.com/default"> ext/xml ext/xml First Paragraph First Paragraph About this Document About this Document

75 SAX: Simple Example xml/xml_simple.php $attvalue) { foreach ($attributes as $attname => $attvalue) { print " $attname => $attvalue \n"; print " $attname => $attvalue \n"; }} function endElement($parser, $elementname) { print "* End Element: $elementname\n"; print "* End Element: $elementname\n";} function charDataHandler($parser,$data) { if (trim($data) != "") print $data."\n"; if (trim($data) != "") print $data."\n";} function PIhandler ($parser, $target, $data) { print "PI: $target -> $data\n"; print "PI: $target -> $data\n";} function DefaultHandler($parser, $data) { print "Default: $data\n"; print "Default: $data\n";}

76 SAX: Simple Example xml/xml_simple.php $parser = xml_parser_create(); /* Disable as case is significant in XML */ xml_parser_set_option($parser, XML_OPTION_CASE_FOLDING, false); xml_set_element_handler($parser,"startElement","endElement"); xml_set_character_data_handler($parser, "charDataHandler"); xml_set_processing_instruction_handler ($parser, "PIhandler"); xml_set_default_handler ($parser, "DefaultHandler"); if (($fp = fopen("xml_simple.xml", "r"))) { while ($data = fread($fp, 4096)) { while ($data = fread($fp, 4096)) { xml_parse($parser, $data, feof($fp)); xml_parse($parser, $data, feof($fp)); }}?>

77 SAX: Simple Example RESULTS * Start Element: chapter xmlns:a => xmlns:a => xmlns => xmlns => * Start Element: a:title ext/xml * End Element: a:title * Start Element: para First Paragraph First Paragraph * End Element: para * Start Element: a:section a:id => about a:id => about * Start Element: title About this Document * End Element: title * Start Element: para Default: Default: PI: php -> echo 'Hi! This is PHP version '. phpversion(); * End Element: para * End Element: a:section * End Element: chapter

78 SAX: Error Handling xml/xml_error.php

79 SAX: Error Handling RESULTS XML error: Invalid document end in line 1, column 7 object(LibXMLError)#1 (6) { ["level"]=> ["level"]=> int(3) int(3) ["code"]=> ["code"]=> int(5) int(5) ["column"]=> ["column"]=> int(7) int(7) ["message"]=> ["message"]=> string(41) "Extra content at the end of the document string(41) "Extra content at the end of the document" ["file"]=> ["file"]=> string(0) "" string(0) "" ["line"]=> ["line"]=> int(1) int(1)}

80 SAX: Advanced Example xml/xml_advanced.php class cSax { function startElement($parser, $elementname, $attributes) { function startElement($parser, $elementname, $attributes) { list($namespaceURI,$localName)= list($namespaceURI,$localName)= if (! $localName) { if (! $localName) { $localName = $namespaceURI; $localName = $namespaceURI; $namespaceURI = ""; $namespaceURI = ""; } print "* Start Element: $localName". print "* Start Element: $localName". ($namespaceURI ? " in $namespaceURI" : "")."\n"; ($namespaceURI ? " in $namespaceURI" : "")."\n"; foreach ($attributes as $attname => $attvalue) { foreach ($attributes as $attname => $attvalue) { print " $attname => $attvalue \n"; print " $attname => $attvalue \n"; } } function endElement($parser, $elementname) { function endElement($parser, $elementname) { list($namespaceURI,$localName)= list($namespaceURI,$localName)= if (! $localName) { if (! $localName) { $localName = $namespaceURI; $localName = $namespaceURI; $namespaceURI = ""; $namespaceURI = ""; } print "* End Element: $localName". print "* End Element: $localName". ($namespaceURI ? " in $namespaceURI" : "")."\n"; ($namespaceURI ? " in $namespaceURI" : "")."\n"; }}

81 SAX: Advanced Example xml/xml_advanced.php $objcSax = new cSax(); $parser = /* Disable as case is significant in XML */ xml_parser_set_option($parser, XML_OPTION_CASE_FOLDING, false); false); xml_set_object($parser, $objcSax); xml_set_element_handler($parser,"startElement","endElement"); if (($fp = fopen("xml_simple.xml", "r"))) { while ($data = fread($fp, 4096)) { while ($data = fread($fp, 4096)) { if (! xml_parse($parser, $data, feof($fp))) { if (! xml_parse($parser, $data, feof($fp))) { $xmlError = libxml_get_last_error(); $xmlError = libxml_get_last_error(); var_dump($xmlError); var_dump($xmlError);exit; } }}

82 SAX: Advanced Example RESULTS * Start Element: chapter in * Start Element: title in * End Element: title in * Start Element: para in * End Element: para in * Start Element: section in => about => about * Start Element: title in * End Element: title in * Start Element: para in * End Element: para in * End Element: section in * End Element: chapter in

83 XMLReader Forward moving stream based parser Forward moving stream based parser It is a Pull parser It is a Pull parser Based on the C# XmlTextReader API Based on the C# XmlTextReader API Advantages: Advantages: Low memory footprint Low memory footprint Namespace support Namespace support Simple API Simple API Validation support Validation support Advanced Feature Set Advanced Feature Set Faster Processing Faster Processing

84 XMLReader: Simple Example xmlreader/reader_simple.xml xmlns="http://www.example.com/default"> XMLReader XMLReader First Paragraph First Paragraph About this Document About this Document

85 XMLReader: Simple Example xmlreader/reader_simple.php $reader = new XMLReader(); $reader->open('reader_simple.xml');$reader->read(); print "xmlns Attribute value: ".$reader->getAttributeNo(0)."\n\n"; while ($reader->read() && $reader->name != "a:title") { } print "Local Name for Element: ".$reader->localName."\n"; print "Namespace URI for Element: ".$reader->namespaceURI."\n"; while($reader->read()) { switch ($reader->nodeType) { switch ($reader->nodeType) { case XMLReader::ELEMENT: case XMLReader::ELEMENT: print "Element: ".$reader->name."\n"; print "Element: ".$reader->name."\n"; if ($reader->hasAttributes && $reader->moveToFirstAttribute()) { if ($reader->hasAttributes && $reader->moveToFirstAttribute()) { do { do { print " ".$reader->name."=".$reader->value."\n"; print " ".$reader->name."=".$reader->value."\n"; } while($reader->moveToNextAttribute()); } while($reader->moveToNextAttribute()); } break; break; case XMLReader::PI: case XMLReader::PI: print "PI Target: ".$reader->name."\n PI Data: ".$reader->value."\n"; print "PI Target: ".$reader->name."\n PI Data: ".$reader->value."\n"; }}

86 XMLReader: Simple Example RESULTS Local Name for Element: title Namespace URI for Element: Element: para Element: a:section a:id=about a:id=about Element: title Element: para PI Target: php PI Data: echo 'Hi! This is PHP version '. phpversion(); PI Data: echo 'Hi! This is PHP version '. phpversion();

87 XMLReader: Consuming Yahoo Shopping totalResultsAvailable="8850" firstResultPosition="2" totalResultsReturned="2">

88 XMLReader: Consuming Yahoo Shopping xmlreader/rest_yahoo_shopping.php function getTextValue($reader) {... } function processCatalog($reader) {... } function processResult($reader) {... } /* URL to Product Search service */ $url = 'http://api.shopping.yahoo.com/ShoppingService/V1/productSearch'; /* The query is separate here as the terms must be encoded. */ $url.= '?query='.rawurlencode('linksys'); /* Complete the URL with App ID, limit to 1 result and start at second record */ $url.= "&appid=zzz&results=2&start=2"; $reader = new XMLReader(); if (! $reader->open($url)) { print "Cannot access Webservice\n"; exit; } while($reader->name != "Result") { $reader->read(); } do { processResult($reader); processResult($reader); } while($reader->next('Result'));

89 XMLReader: Consuming Yahoo Shopping xmlreader/rest_yahoo_shopping.php function getTextValue($reader) { if ($reader->nodeType != XMLReader::ELEMENT || $reader->isEmptyElement if ($reader->nodeType != XMLReader::ELEMENT || $reader->isEmptyElement || ($reader->read() && $reader->nodeType == XMLReader::END_ELEMENT )) || ($reader->read() && $reader->nodeType == XMLReader::END_ELEMENT )) return; return; $retVal = $reader->value; $retVal = $reader->value; $reader->read(); $reader->read(); return $retVal; return $retVal;} function processResult($reader) { $depth = $reader->depth; $depth = $reader->depth; if ($reader->isEmptyElement || ($reader->read() && if ($reader->isEmptyElement || ($reader->read() && $reader->nodeType == XMLReader::END_ELEMENT )) $reader->nodeType == XMLReader::END_ELEMENT )) return; return; while($depth depth && $reader->name != "Catalog") { $reader->read(); }; while($depth depth && $reader->name != "Catalog") { $reader->read(); };processCatalog($reader); /* Read until is encountered */ while($depth depth) { $reader->read(); } }

90 XMLReader: Consuming Yahoo Shopping xmlreader/rest_yahoo_shopping.php function processCatalog($reader) { $depth = $reader->depth; $depth = $reader->depth; print "Catalog ID".$reader->getAttribute('ID')."\n"; print "Catalog ID".$reader->getAttribute('ID')."\n"; if ($reader->isEmptyElement || ($reader->read() && if ($reader->isEmptyElement || ($reader->read() && $reader->nodeType == XMLReader::END_ELEMENT )) $reader->nodeType == XMLReader::END_ELEMENT )) return; return; while($depth depth) { while($depth depth) { switch ($reader->name) { switch ($reader->name) { case "ProductName": case "ProductName": case "PriceFrom": case "PriceFrom": case "PriceTo": case "PriceTo": case "Description": case "Description": case "Url": case "Url": print $reader->name.": ".getTextValue($reader)."\n"; print $reader->name.": ".getTextValue($reader)."\n"; } $reader->next(); $reader->next(); }}

91 XMLReader: Consuming Yahoo Shopping RESULTS (Abbreviated) Catalog ID Url: ast%20Cable%2FDSL%20Router: ProductName: Linksys Instant Broadband EtherFast Cable/DSL Router PriceFrom: PriceTo: Description: Linksys, a provider of networking hardware for the small/medium business (SMB), small office/home office (SOHO), and enterprise markets and broadband networking hardware for the home, has announced the new EtherFast Cable/DSL Router. The first in the new Instant Broadband series, this Linksys broadband router will enable home or office users to connect their computers to a cable or DSL modem and securely share Internet access and perform networking tasks such as file and printer sharing. The built-in hardware firewall gives users the security of sharing files without fear of intruders hacking into the network. Description: Linksys, a provider of networking hardware for the small/medium business (SMB), small office/home office (SOHO), and enterprise markets and broadband networking hardware for the home, has announced the new EtherFast Cable/DSL Router. The first in the new Instant Broadband series, this Linksys broadband router will enable home or office users to connect their computers to a cable or DSL modem and securely share Internet access and perform networking tasks such as file and printer sharing. The built-in hardware firewall gives users the security of sharing files without fear of intruders hacking into the network.

92 XMLReader: DTD Validation xmlreader/validation/reader.xml XMLReader XMLReader First Paragraph First Paragraph About this Document About this Document content content

93 XMLReader: DTD Validation xmlreader/validation/reader.php $objReader = XMLReader::open('reader.xml'); $objReader->setParserProperty(XMLReader::VALIDATE, TRUE); /* As of PHP 5.2 LIBXML Parser Options may be passed */ // $objReader = XMLReader::open('reader.xml', NULL, LIBXML_DTDVALID); libxml_use_internal_errors(TRUE); while ($objReader->read()) { if (! $objReader->isValid()) { if (! $objReader->isValid()) { print "NOT VALID\n"; print "NOT VALID\n"; break; break; }} $arErrors = libxml_get_errors(); foreach ($arErrors AS $xmlError) { print $xmlError->message; print $xmlError->message;}

94 XMLReader: DTD Validation RESULTS NOT VALID Element section was declared #PCDATA but contains non text nodes

95 XMLReader: Relax NG Validation xmlreader/validation/reader.rng xmlns="http://relaxng.org/ns/structure/1.0">

96 XMLReader: Relax NG Validation xmlreader/validation/reader-rng.php $objReader = XMLReader::open('reader.xml'); $objReader->setRelaxNGSchema('reader.rng');libxml_use_internal_errors(TRUE); while ($objReader->read()) { if (! $objReader->isValid()) { if (! $objReader->isValid()) { print "NOT VALID\n"; print "NOT VALID\n"; break; break; }} $arErrors = libxml_get_errors(); foreach ($arErrors AS $xmlError) { print $xmlError->message; print $xmlError->message;}

97 XMLReader: Relax NG Validation RESULTS NOT VALID Did not expect element title there

98 XSL Used to transform XML data Used to transform XML data XSLT based on XPath XSLT based on XPath Works with DOM and SimpleXML, although the DOM extension is required. Works with DOM and SimpleXML, although the DOM extension is required. Provides the capability of calling PHP functions during a transformation Provides the capability of calling PHP functions during a transformation DOM nodes may be returned from PHP functions DOM nodes may be returned from PHP functions The LIBXML_NOCDATA and LIBXML_NOENT constants are your friends. The LIBXML_NOCDATA and LIBXML_NOENT constants are your friends. libxslt is recommended to avoid problems when using xsl:key libxslt is recommended to avoid problems when using xsl:key

99 XSL: XML Input Data xsl/sites.xml PHP General PHP General PHP Pear Dev PHP Pear Dev Planet PHP Planet PHP

100 XSL: Simple Transformation xsl/simple_stylesheet.xsl :

101 XSL: Simple Transformation xsl/simple_stylesheet.php /* Load Stylesheet */ $stylesheet = new DOMDocument(); $stylesheet->load('simple_stylesheet.xsl'); /* Create XSL Processor */ $proc = new xsltprocessor(); $proc->importStylesheet($stylesheet); /* Load XML Data */ $dom = new DOMDocument(); $dom->load('sites.xml'); print $proc->transformToXML($dom);

102 XSL: Simple Transformation RESULTS PHP General : PHP Pear Dev : Planet PHP :

103 XSL: Advanced Transformation xsl/advanced_stylesheet.php function initReader($url) { $GLOBALS['reader'] = new XMLReader(); if ($GLOBALS['reader']->open($url)) { while ($GLOBALS['reader']->read() && $GLOBALS['reader']->name != 'item') { } if ($GLOBALS['reader']->name == 'item') return 1; } $GLOBALS['reader'] = NULL; return 0; } function readNextItem() { if ($GLOBALS['reader'] == NULL) return NULL; if ($GLOBALS['beingProc']) $GLOBALS['reader']->next('item'); else $GLOBALS['beingProc'] = TRUE; if ($GLOBALS['reader']->name == 'item') return $GLOBALS['reader']->expand(); return NULL; }

104 XSL: Advanced Transformation xsl/advanced_stylesheet.php $beingProc = FALSE; $reader = NULL; /* Load Stylesheet */ $stylesheet = new DOMDocument(); $stylesheet->load('advanced_stylesheet.xsl'); /* Create XSL Processor */ $proc = new xsltprocessor(); $proc->importStylesheet($stylesheet); /* Load XML Data */ $dom = new DOMDocument(); $dom->load('sites.xml'); $proc->setParameter(NULL, 'siteid', 'php-gen'); $proc->registerPHPFunctions('initReader'); $proc->registerPHPFunctions('readNextItem'); print $proc->transformToXML($dom); /* END */

105 XSL: Advanced Transformation xsl/advanced_stylesheet.xsl 0">

106 XSL: Advanced Transformation xsl/advanced_stylesheet.xsl Title: URL: Published:

107 XSL: Advanced Transformation Results viewed through a browser xsl/advanced_stylesheet.html Title: Re: Spreadsheet Writer URL: Published: Thu, 07 Sep :52:09 –0400 Title: Re: Spreadsheet Writer URL: Published: Thu, 07 Sep :52: Title: Re: Spreadsheet Writer URL: Published: Thu, 07 Sep :52:

108 XMLWriter Lightweight and forward-only API for generating well formed XML Lightweight and forward-only API for generating well formed XML Automatically escapes data Automatically escapes data Works with PHP 4.3+ available at Works with PHP 4.3+ available at Object Oriented API available for PHP 5+ Object Oriented API available for PHP 5+ Part of core PHP distribution since PHP Part of core PHP distribution since PHP 5.1.2

109 XMLWriter: Simple Example xmlwriter/simple.php openMemory(); /* Turn on indenting to make output look pretty and set string used for indenting as teh default space is too short*/ used for indenting as teh default space is too short*/$xw->setIndent(TRUE); $xw->setIndentString(' '); /* Write out the optional XML declaration only specifying version */ $xw->startDocument('1.0'); /* Create the opening document element, which is namespaced */ $xw->startElementNs(NULL, "chapter", "http://www.example.com/default"); /* Write out an xml namespace declaration that is used later in the document */ $res = $xw->writeAttribute('xmlns:a', 'http://www.example.com/namespace-a'); /* Write complete elements with text content */ $xw->writeElement('a:title', 'XMLReader'); $xw->writeElement('para', 'spec chars & " inside para element');

110 XMLWriter: Simple Example xmlwriter/simple.php /* start an element and add an attribute to it */ $xw->startElement('a:section'); $xw->writeAttribute('a:id', 'about'); /* Write out an element with special characters */ $xw->writeElement('title', 'Pro PHP XML & Webservices'); $xw->startElement('para'); /* This opens the para element */ $xw->writeComment("this is a comment"); $xw->text(" "); $xw->writePi("php", "echo 'Hi! This is PHP version '. phpversion(); "); $xw->text("\n "); $xw->endElement(); /* This will close the open para element */ $xw->endDocument(); /* Flush and clear the buffer */ echo $xw->flush(true); ?>

111 XMLWriter: Simple Example xmlwriter/simple.php /* start an element and add an attribute to it */ $xw->startElement('a:section'); $xw->writeAttribute('a:id', 'about'); /* Write out an element with special characters */ $xw->writeElement('title', 'Pro PHP XML & Webservices'); $xw->startElement('para'); /* This opens the para element */ $xw->writeComment("this is a comment"); $xw->text(" "); $xw->writePi("php", "echo 'Hi! This is PHP version '. phpversion(); "); $xw->text("\n "); $xw->endElement(); /* This will close the open para element */ $xw->endDocument(); /* Flush and clear the buffer */ echo $xw->flush(true); ?>

112 XMLWriter: Creating a Rest Service xmlwriter/rest.php (startid and maxid) ='.$min.' and id ='.$min.' and id <='.$max; $query = sqlite_query($dbhandle,$strSQL); $query = sqlite_query($dbhandle,$strSQL); return sqlite_fetch_all($query, SQLITE_ASSOC); return sqlite_fetch_all($query, SQLITE_ASSOC); } } /* closes function and saves display space */ } } /* closes function and saves display space */

114 XMLWriter: Creating a Rest Service xmlwriter/rest.php /* Process the resulting records if any */ header('Content-Type: text/xml'); $xw = new XMLWriter(); /* Send the XML document directly to output as it is written */ $xw->openUri('php://output'); $xw->startDocument('1.0', 'UTF-8'); $xw->startElement('Results'); foreach ($arResults AS $result) { $xw->startElement('Result'); $xw->startElement('Result'); foreach ($result AS $field_name => $field_value) { foreach ($result AS $field_name => $field_value) { $xw->writeElement($field_name, $field_value); $xw->writeElement($field_name, $field_value); } $xw->endElement(); $xw->endElement(); /* Progressively send the output */ /* Progressively send the output */ $xw->flush(); $xw->flush();}$xw->endDocument(); /* Flush and clear the buffer */ $xw->flush();

115 XMLWriter: Creating a Rest Service xmlwriter/rest.php /* Process the resulting records if any */ header('Content-Type: text/xml'); $xw = new XMLWriter(); /* Send the XML document directly to output as it is written */ $xw->openUri('php://output'); $xw->startDocument('1.0', 'UTF-8'); $xw->startElement('Results'); foreach ($arResults AS $result) { $xw->startElement('Result'); $xw->startElement('Result'); foreach ($result AS $field_name => $field_value) { foreach ($result AS $field_name => $field_value) { $xw->writeElement($field_name, $field_value); $xw->writeElement($field_name, $field_value); } $xw->endElement(); $xw->endElement(); /* Progressively send the output */ /* Progressively send the output */ $xw->flush(); $xw->flush();}$xw->endDocument(); /* Flush and clear the buffer */ $xw->flush();

116 Tree Parsers Pros: Pros: Full navigation and modification of the XML document Full navigation and modification of the XML document Navigating and searching are extremely fast once the tree is loaded into memory Navigating and searching are extremely fast once the tree is loaded into memory Cons: Cons: Must wait until entire tree is loaded to begin working with the XML. Must wait until entire tree is loaded to begin working with the XML. Memory intensive Memory intensive

117 Streaming Parsers Pros: Pros: Uses minimal memory Uses minimal memory Processing takes place immediately while the document is parsed Processing takes place immediately while the document is parsed Cons: Cons: Minimal to no navigation support (forward only) Minimal to no navigation support (forward only) No document editing capabilities No document editing capabilities

118 Raw Test Data Memory Usage: DOMSimpleXMLext/xmlXMLReader 85.6MB85.6MB26KB177KB DOMSimpleXMLext/xmlXMLReader Using every optimization possible the following results show the time in seconds to locate the book element having id="5000". Average Time in Seconds for Optimized Search for an Element:

119 SOAP An XML-based protocol for exchanging information between applications An XML-based protocol for exchanging information between applications It allows for remote invocation of methods in a distributed environment It allows for remote invocation of methods in a distributed environment Uses existing transport protocols such as HTTP Uses existing transport protocols such as HTTP Can operate with or without a Web Service Definition Language (WSDL) document Can operate with or without a Web Service Definition Language (WSDL) document A W3C standard and the core component to the Web Services Interoperability Organization (WS-I) Basic Profile A W3C standard and the core component to the Web Services Interoperability Organization (WS-I) Basic Profile

120 SOAP: Basic WSDL Structure

121 SOAP: Basic Message Structure

122 SOAP: The SoapClient SoapClient::__construct ( mixed wsdl [, array options] ) Some SoapClient options: location* (string) Location of Soap service uri* (string) Target namespace for the SOAP server style 1 (int) Binding style for message (SOAP_DOCUMENT or SOAP_RPC) use 1 (int) Binding type for style (SOAP_ENCODED or SOAP_LITERAL) trace (bool) Enable / disable request/response tracing (default disabled) exceptions (bool) Turn Soap exceptions on / off (default on) *Required in NON-WSDL mode 1 Only used in NON-WSDL mode

123 SOAP: The SoapClient SoapClient::__construct ( mixed wsdl [, array options] ) Connection and security options for SoapClient: login Login for HTTP authentication password Password for HTTP authenication proxy_host Host for Proxy server proxy_port Port for Proxy server proxy_login Login for Proxy server proxy_password Password for Proxy server local_cert Client certificate for HTTPS client authentication passphrase Passphrase for client certificate

124 SOAP: Function Query a WSDL soap/google/google_get_functions.php __getFunctions(); $google_funcs = $GoogleClient->__getFunctions(); foreach($google_funcs AS $function) { foreach($google_funcs AS $function) { echo $function."\n\n"; echo $function."\n\n"; } } catch (SoapFault $e) { } catch (SoapFault $e) { var_dump($e); var_dump($e); }?>

125 SOAP: Function Query a WSDL Google Function RESULTS base64Binary doGetCachedPage(string $key, string $url) string doSpellingSuggestion(string $key, string $phrase) GoogleSearchResult doGoogleSearch(string $key, string $q, int $start, int $maxResults, boolean $filter, string $restrict, boolean $safeSearch, string $lr, string $ie, string $oe) $key refers to a Google license key, which may be obatined from:

126 SOAP: Type Query a WSDL soap/google/google_get_types.php __getTypes(); $types = $GoogleClient->__getTypes(); foreach($ types AS $type) { foreach($ types AS $type) { echo $type."\n\n"; echo $type."\n\n"; } } catch (SoapFault $e) { } catch (SoapFault $e) { var_dump($e); var_dump($e); }?>

127 SOAP: Type Query a WSDL Google Type RESULTS struct GoogleSearchResult { boolean documentFiltering; boolean documentFiltering; string searchComments; string searchComments; int estimatedTotalResultsCount; int estimatedTotalResultsCount; boolean estimateIsExact; boolean estimateIsExact; ResultElementArray resultElements; ResultElementArray resultElements; string searchQuery; string searchQuery; int startIndex; int startIndex; int endIndex; int endIndex; string searchTips; string searchTips; DirectoryCategoryArray directoryCategories; DirectoryCategoryArray directoryCategories; double searchTime; double searchTime;} ResultElement ResultElementArray[ ] DirectoryCategory DirectoryCategoryArray[ ] struct ResultElement { string summary; string URL; string snippet; string title; string cachedSize; boolean relatedInformationPresent; string hostName; DirectoryCategory directoryCategory; string directoryTitle; } struct DirectoryCategory { string fullViewableName; string specialEncoding; }

128 SOAP: Retrieving from Google Cache soap/google/google_cache_client.php doGetCachedPage($key, 'http://www.google.com/'); $cached = $client->doGetCachedPage($key, 'http://www.google.com/'); /* display first 200 characters of cached page */ /* display first 200 characters of cached page */ echo substr($cached, 0, 500); echo substr($cached, 0, 500); } catch (SoapFault $e) { } catch (SoapFault $e) { var_dump($e); var_dump($e); }?>

129 SOAP: Retrieving from Google Cache RESULTS This is G o o g l e 's This is G o o g l e 's

130 SOAP: Google Search Client soap/google/google_search_client.php doGoogleSearch($key, $search_terms, $start, $maxResults, $results = $client->doGoogleSearch($key, $search_terms, $start, $maxResults, $filter, $restrict, $safeSearch, $lr, $ie, $oe)); $filter, $restrict, $safeSearch, $lr, $ie, $oe)); var_dump($results); var_dump($results);?>

131 SOAP: Google Search Client RESULTS object(stdClass)#2 (11) { ["documentFiltering"] => bool(false) ["documentFiltering"] => bool(false) ["searchComments"] => string(0) "" ["searchComments"] => string(0) "" ["estimatedTotalResultsCount"]=> int( ) ["estimatedTotalResultsCount"]=> int( ) ["estimateIsExact"] => bool(false) ["estimateIsExact"] => bool(false) ["resultElements"] => array(10) { ["resultElements"] => array(10) { [1] => object(stdClass)#5 (9) { [1] => object(stdClass)#5 (9) { ["summary"] => string(0) "" ["summary"] => string(0) "" ["URL"]=> string(60) "http://www.amazon.com/Pro-PHP-XML-Web-Services/dp/ " ["URL"]=> string(60) "http://www.amazon.com/Pro-PHP-XML-Web-Services/dp/ " ["snippet"] => string(116) "Amazon.com: Pro PHP XML and Web Services (Pro): ["snippet"] => string(116) "Amazon.com: Pro PHP XML and Web Services (Pro): Books : Robert Richards by Robert Richards." Books : Robert Richards by Robert Richards." ["title"] => string(91) "Amazon.com: Pro PHP XML and Web Services (Pro): ["title"] => string(91) "Amazon.com: Pro PHP XML and Web Services (Pro): Books : Robert Richards" Books : Robert Richards" ["cachedSize"] => string(3) "111k" ["cachedSize"] => string(3) "111k" ["relatedInformationPresent"] => bool(true) ["relatedInformationPresent"] => bool(true) ["hostName"] => string(0) "" ["hostName"] => string(0) "" ["directoryCategory"] => object(stdClass)#6 (2) { ["directoryCategory"] => object(stdClass)#6 (2) { ["fullViewableName"] => string(0) "" ["fullViewableName"] => string(0) "" ["specialEncoding"] => string(0) "" ["specialEncoding"] => string(0) "" } ["directoryTitle"] => string(0) "" ["directoryTitle"] => string(0) "" } }

132 SOAP: Client Headers soap/headers.php soapHeader::__construct ( string namespace, string name [, mixed data [, bool mustUnderstand [, mixed actor]]] ) mixed data [, bool mustUnderstand [, mixed actor]]] )username = 'MyUsername'; $auth->password = 'MyPassword'; /* You MUST encode the object */ $authVar = new SoapVar($auth, SOAP_ENC_OBJECT); $header = new SoapHeader('urn:ExampleAPI', "Authentication", $authVar, TRUE, SOAP_ACTOR_NEXT); $authVar, TRUE, SOAP_ACTOR_NEXT); /* Set the new headers to use when creating SOAP messages */ $sClient->__setSoapHeaders(array($header));?>

133 SOAP: Client Headers SOAP-ENV:actor=" "> MyUsername MyUsername MyPassword MyPassword

134 SOAP: Client Request Modification soap/google/request_modification.php require('google_key.php'); Class mySoapClient extends SoapClient { function __doRequest($request, $location, $action, $version) { function __doRequest($request, $location, $action, $version) { /* Load the request into a DOMDocument */ /* Load the request into a DOMDocument */ $dom = new DOMDocument(); $dom = new DOMDocument(); $dom->loadXML($request); $dom->loadXML($request); /* Find the url element and set url to */ /* Find the url element and set url to */ $nodeList = $dom->getElementsByTagName('url'); $nodeList = $dom->getElementsByTagName('url'); if ($nodeList->length == 1) { if ($nodeList->length == 1) { $nodeList->item(0)->firstChild->nodeValue = "http://www.php.net/"; $nodeList->item(0)->firstChild->nodeValue = "http://www.php.net/"; } /* Serialize the tree and send modified request to parent method */ /* Serialize the tree and send modified request to parent method */ $request = $dom->saveXML(); $request = $dom->saveXML(); return parent::__doRequest($request, $location, $action, $version); return parent::__doRequest($request, $location, $action, $version); }} $sClient = new mySoapClient('GoogleSearch.wsdl'); $cached = $sClient->doGetCachedPage($key, 'http://www.google.com/'); echo substr($cached, 1500, 700)."\n";

135 SOAP: Client Request Modification RESULTS (soap/google/request_modification.php) ont> Google is neither affiliated with the authors of this page nor responsible for its content. ont> Google is neither affiliated with the authors of this page nor responsible for its content.


PHP: Hypertext Preprocessor PHP: Hypertext Preprocessor
Ads by Google