info@a-coding-project.de

PHP und XML

Der XML-Standard ist mittlerweile aus Webanwendungen nicht mehr wegzudenken. Nachdem XML von immer mehr Programmen und Anwendungen auch außerhalb des Internets unterstützt und interpretiert wird, ist es sinnvoll und praktisch seine Daten in dieses Format zu exportieren oder zu verwalten. Damit ist die Weiterverarbeitung und/oder Export der Daten sehr schnell gewährleistet.
Auch PHP bietet mehrere Extensions an, mit denen XML-Dokumente erstellt bzw. ausgelesen und verändert werden können. Somit reiht sich PHP in diejenigen Programmier- und Skriptsprachen ein, mit denen XML genutzt werden kann. Alle XML-Extensions von PHP sind objektorientiert aufgebaut.
Dieser Artikel zeigt anhand der Extensions "SimpleXML", "XMLReader" und "XMLWriter", wie XML und PHP zusammenarbeiten.

Die XML-Datei

Für diesen Artikel wird die folgende XML-Datei verwendet:

<?xml version="1.0" standalone="yes"?>
<datenbank>
 <film>
  <titel>James Bond - Die Welt ist nicht genug</titel>
  <medium>DVD</medium>
  <darsteller>
   <hauptdarsteller>Pierce Brosnan</hauptdarsteller>
   <boesewicht>Sophie Marceau</boesewicht>
  </darsteller>
  <bewertung type="points">9</bewertung>
  <bewertung type="stars">4</bewertung>
 </film>
 <film>
  <titel>Stirb Langsam</titel>
  <medium>VHS</medium>
  <darsteller>
   <hauptdarsteller>Bruce Willis</hauptdarsteller>
   <boesewicht>Alan Rickman</boesewicht>
  </darsteller>
  <bewertung type="points">10</bewertung>
  <bewertung type="stars">5</bewertung>
 </film>
 <film>
  <titel>Oceans Eleven</titel>
  <medium>DVD</medium>
  <darsteller>
   <hauptdarsteller>George Clooney</hauptdarsteller>
   <boesewicht>Andy Garcia</boesewicht>
  </darsteller>
  <bewertung type="points">8</bewertung>
  <bewertung type="stars">3</bewertung>
 </film>
</datenbank>

Die SimpleXML-Extension

Diese Erweiterung ist in der 5er-Version von PHP standardmäßig enthalten und auch aktiviert. Das bedeutet, dass kein weiterer "organisatorischer" Eingriff in die PHP-Konfiguration notwendig ist, um diese Erweiterung nutzen zu können.

Einbindung von XML-Daten

Sind die XML-Daten in einer eigenen XML-Datei vorhanden, gibt es die Funktion simplexml_load_file, mit der die Informationen eingebunden werden können. Beispiel:

$xml_file = simplexml_load_file("Pfad/zu/XML/Datei");

Zugriff auf die XML-Daten

Der Inhalt der Variablen $xml_file entspricht der Objekt-Instanz, die für die Nutzung der Eigenschaften und Methoden gebraucht wird. Beispiel:

//Anzeige des Hauptdarstellers im ersten Film
echo $xml_file->film[0]->darsteller->hauptdarsteller;

//Anzeige der Titel aller Filme
foreach($xml_file->film as $film) {  echo "$film->titel<br>";  }

//Zugriff auf Attributwert eines bestimmten Tags
echo $xml_file->film[0]->bewertung['type'];

//Auslesen der Attributwerte, wenn das Attribut mehrmals 
//verwendet wurde
foreach($xml_file->film[0]->bewertung as $bewertung)
{
 echo $bewertung['type'];
}

//Verändern eines Element-Inhaltes
$xml_file->film[0]->darsteller->hauptdarsteller = "Sean Connery";

//Hinzufügen von neuen Elementen und neuen Attribute
$general = $xml_file->film[0]->addChild("allgemein");
$general->addChild("Jahr","1999");
$general->addChild("Regie","Lee Tamahori");

$rating = $xml_file->film[0]->addChild("bewertung","5");
$rating->addAttribute("typ","cinema");

//Auslesen der Attribute eines Elementes
foreach($xml_file->film[0]->bewertung[0]->attributes() as $attribute => $wert)
{
 echo $attribute. "=" . $wert . "<br>";
}

//Auslesen der Kindelemente eines Knotens
foreach($xml_file->children() as $elements)
{
 foreach($elements as $child_object)
 {
  echo gettype($child_object) . "<br>";
 }
}

//Ermitteln von Namen eines XML-Elementes
echo $xml_file->getName();
foreach($xml_file->children() as $child)
{
 echo $child->getName() . "<br>";
 //Zeit Elementnamen der ersten Ebene an
}

//Namensraum der XML-Datei (falls definiert)
$namespace = $xml_file->getNamespaces(true);
var_dump($namespace);

//Suche im XML-Dokument per XPath
$result = $xml_file->xpath("film/titel");
while(list( , $wert) = each($result)) 
{  
 echo "Ergebnis: " . $wert . "<br>"; 
}

Die XMLReader-Extension

Diese Erweiterung steht für PHP5 im PECL-Respository (http://pecl.php.net) zum Download zur Verfügung. Ab der PHP-Version 5.1.0 ist die Erweiterung jedoch standardmäßig in PHP enthalten und auch aktiviert.

Einbindung von XML-Daten

Zuerst muss eine Objektinstanz erstellt werden, damit die Methoden der Extension überhaupt verwendet werden können.
Deshalb ist die Zeile $xml_file = new XMLReader(); am Anfang eines Skriptes zwingend notwendig. Auch hier wird zwischen einem XML-String und einer XML-Datei unterschieden.

XML-String

Dafür steht die Methode XML zur Verfügung. Als Parameter wird die Variable angegeben, der der XML-String zugewiesen ist.

Beispiel:

$xml_file->XML($string);

XML-Datei

Die dazugehörige Methode heißt open und als Parameter gibt man den Namen der xml-Datei an.

Beispiel:

$xml_file->open("test.xml");

Zugriff auf die XML-Daten

Zur Analyse der einzelnen Elemente der XML-Daten stehen verschiedene Eigenschaften und Konstanten zur Verfügung.

Beispiel-Analyse des Wurzelementes <datenbank> anhand der wichtigsten Parameter:

$xml_file->read();

$p1 = $xml_file->name;
$p2 = $xml_file->nodeType;
$p3 = $xml_file->hasAttributes;
$p4 = $xml_file->attributeCount;
$p5 = $xml_file->hasValue;

echo "Knotenname: ". $p1 . "<br>";
echo "Knotentyp: ". $p2 . "<br>";
echo "Attribute vorhanden: ". $p3 . "<br>";
echo "Anzahl der Attribute: ". $p4 . "<br>";
echo "Knotenwert vorhanden: ". $p5 . "<br><br>";

... ergibt in der Ausgabe:

Knotenname: datenbank
Knotentyp: 1
Attribute vorhanden: 
Anzahl der Attribute: 0
Knotenwert vorhanden:

Hinweis: Zeilenumbrüche und Leerzeichen im Quellcode zählen als eigenständige Textknoten. Dies sind eigene Elemente in der Baumstruktur des XML-Dokumentes.

Auslesen der gesamten XML-Datei

while($xml_file->read())
{
 switch($xml_file->nodeType)
 {
  case XMLReader::ELEMENT:
    echo $xml_file->localName."<br>";
    break;

  case XMLReader::TEXT:
    echo $xml_file->value."<br>";
    break;

  case XMLReader::END_ELEMENT:
    echo $xml_file->localName."<br>";
    break;
 }
}

Innerhalb dieser while-Schleife kann für jedes Element überprüft werden, ob es zum Beispiel Attribute hat und in Abhängigkeit davon können die Attribute und die Werte ausgelesen werden. Zwischen den einzelnen Attributen kann auch hin- und hergewechselt und das dazugehörige Element ermittelt werden.

Die XMLWrite-Extension

Diese Erweiterung ist in PHP5 standardmäßig bereits enthalten und aktiviert.

Wichtig: Die Erweiterung arbeitet nicht objektorientiert, sondern prozedural.

In den folgenden Beispielen soll die XML-Datei, die als Basis für diesen Artikel verwendet wurde, in verkürzter Version erstellt werden.

Folgende Schritte / Funktionen sind notwendig:

//Reservierung eines Speicherbereiches
$xml = xmlwriter_open_memory();

//Öffnen eines neuen XML-Dokumentes mit XML-Version 1.0
xmlwriter_start_document($xml,"1.0");

//"Starten" des Elementes <datenbank> (Wurzelelement)
xmlwriter_start_element($xml,"datenbank");

//Hinweis: start_element ist notwendig, da das Element noch 
//weiter verschachtelt werden soll.

//"Starten" des Elementes <film>
xmlwriter_start_element($xml,"film");

//Schreiben der Elemente <titel> und <medium> und Zuweisen 
//eines Wertes
xmlwriter_write_element($xml,"titel",
                        "James Bond - Die Welt ist nicht genug");
xmlwriter_write_element($xml,"medium","DVD");

//"Starten" des Elementes <darsteller>, da dies weiter 
//verschachtelt wird.
xmlwriter_start_element($xml,"darsteller");

//Schreiben der Elemente <hauptdarsteller> und <boesewicht> 
//und Zuweisung eines Wertes
xmlwriter_write_element($xml,"hauptdarsteller","Pierce Brosnan");
xmlwriter_write_element($xml,"boesewicht","Sophie Marceau");

//Schließen des Elementes <darsteller>
xmlwriter_end_element($xml);
//"Starten" des Elementes <bewertung>
xmlwriter_start_element($xml,"bewertung");

//Zuweisung eines Attributes und des dazugehörigen Wertes
xmlwriter_write_attribute($xml,"type","points");

//Vergabe eines Wertes für das Element <bewertung>
xmlwriter_text($xml,"9");

//Schließen des Elementes <bewertung>
xmlwriter_end_element($xml);

//"Starten" des zweiten Elementes <bewertung>
xmlwriter_start_element($xml,"bewertung");

//Zuweisung eines Attributes und des dazugehörigen Wertes für 
//das zweite <bewertung>-Element
xmlwriter_write_attribute($xml,"type","stars");

//Vergabe eines Wertes für das Element <bewertung>
xmlwriter_text($xml,"4");

//Schließen des Elementes <bewertung>
xmlwriter_end_element($xml);

//Schließen der Elemente <film> und <datenbank>
xmlwriter_end_element($xml);
xmlwriter_end_element($xml);

//Beenden des XML-Dokumentets
xmlwriter_end_document($xml);

//Auslesen des XML-Streams aus dem Speicher
$xml_data=xmlwriter_output_memory($xml);

//Speichern des XML-Streams in einer Datei
file_put_contents("test2.xml",$xml_data);

Wenn die Zeilen genau so in der obigen Reihenfolge übernommen werden, steht in der XML-Datei die folgende Struktur:

<?xml version="1.0"?>
<datenbank>
 <film>
  <titel>James Bond - Die Welt ist nicht genug</titel>
  <medium>DVD</medium>
  <darsteller>
   <hauptdarsteller>Pierce Brosnan</hauptdarsteller>
   <boesewicht>Sophie Marceau</boesewicht>
  </darsteller>
  <bewertung type="points">9</bewertung>
  <bewertung type="stars">4</bewertung>
 </film>
</datenbank>

Über uns

Stefan Wienströer

Wir entwickeln Webanwendungen mit viel Leidenschaft. Unser Wissen geben wir dabei gerne weiter. Mehr über a coding project

Auch interessant