Lehrer Nussbaumer - JAVA (eine kleine Einführung ;)

Grundlagen

GUI

Eingabe

Ausgabe

Applikationen

Applets

Servlets

Beispiele

  1. Ein- und Ausgabe
  2. Textdateien
  3. Kryptographie
  4. MySQL
  5. DOM
  6. SAX
  7. JDOM

Spiele

IDEs

Skriptum

JAVA-DOCS


-----------------
letzte Änderung:
09 December 2021
-----------------
Lehrer Nussbaumers Seite

... in Arbeit ...

JDOM

JDOM (Java Document Object Model) ist eine Schnittstelle, mit der es möglich ist, XML-Dokumente komfortabel unter JAVA zu bearbeiten. Wie DOM und SAX können bestehende XML-Dokumente gelesen und verändert werden. JDOM kann unter der Adresse http://www.jdom.org mit den folgenden Packages bezogen werden:

  • org.jdom - Grundlegende Interfaces und Klassen
  • org.jdom.adapters - verschiedene Adapter-Klassen für verschiedene XML-Parser
  • org.jdom.filter - Klassen, die die Sichtbarkeit bestimmter XML-Elemente regeln
  • org.jdom.input - Klassen für das Einlesen von XML-Daten
  • org.jdom.output - Klassen für die Ausgabe von XML-Daten
  • org.jdom.transform - Klassen für XSLT (XML Stylesheet Language Transformations)
  • org.jdom.xpath - Klasse mit Methoden zu XPath-Ausdrücken

Das *tgz-File wird in ein eigenes Verzeichnis entpackt und anschließend das Skript "build.sh" (Linux) bzw. "build.bat" (Windows) ausgeführt. Die dabei erhaltene Datei "jdom.jar" ist dem Pfad hinzuzufügen:

nus@ice:/usr/lib/java/jre/lib/ext> dir
insgesamt 1921
-rw-r--r--    1 root     root         8893 2003-09-23 18:46 dnsns.jar
-rw-r--r--    1 root     root       135152 2004-04-02 22:46 jdom.jar
-rw-r--r--    1 root     root        53244 2003-09-23 18:46 ldapsec.jar
-rw-r--r--    1 root     root       769332 2003-09-23 18:46 localedata.jar
-rw-r--r--    1 root     root       226061 2003-12-30 21:34 mysql-connector-java-3.0.9-stable-bin.jar
-rw-r--r--    1 root     root         1615 2004-04-05 10:53 saxon-fop.jar
-rw-r--r--    1 root     root       625687 2004-04-05 10:53 saxon.jar
-rw-r--r--    1 root     root        16522 2004-04-05 10:53 saxon-jdom.jar
-r--r--r--    1 root     root       111374 2003-09-23 18:46 sunjce_provider.jar

Für die folgenden Beispiele verwenden wir folgende XML-Datei "weblinks.xml":

<?xml version="1.0" standalone="no"?>
 <!DOCTYPE weblinks SYSTEM "weblinks.dtd">
 <weblinks>
        <eintrag id="0">
                <kategorie>edv</kategorie>
                <url>http://www.w3.org</url>
                <notiz>W3-Konsortium</notiz>
                <notiz>Technische Referenz</notiz>
        </eintrag>
        <eintrag id="1">
                <kategorie>phy</kategorie>
                <url>http://www.cern.ch</url>
                <notiz>Europaeisches Kernforschungszentrum</notiz>
                <notiz>Aktuelles zur Hochenergiephysik</notiz>
                <notiz>Materialien zur Elementarteilchenphysik</notiz>
        </eintrag>
        <eintrag id="2">
		...

Diese XML-Datei wird gegen die folgende DTD "weblinks.dtd" validiert:

<!ELEMENT weblinks (eintrag*)>
        <!ELEMENT eintrag (kategorie, url, notiz, datum)>
        <!ATTLIST eintrag id CDATA #REQUIRED>
                <!ELEMENT kategorie (#PCDATA)>
                <!ELEMENT url (#PCDATA)>
                <!ELEMENT notiz (#PCDATA)>
                <!ELEMENT datum (#PCDATA)>

XML-Dokumente ausgeben

Alle Elemente der XML-Datei "weblinks.xml" sollen (auf der Konsole) ausgegeben werden. Dazu werden aus dem Package "org.jdom" die Klassen "Document" und "JDOMException" geladen. Zum Einlesen der Daten benötigen wir die Klasse "SAXBuilder" aus dem Package "org.jdom.input"; und zur Ausgabe die Klasse "XMLOutputter" aus dem Package "org.jdom.output":

import org.jdom.Document;
import org.jdom.JDOMException;
import org.jdom.input.SAXBuilder;
import org.jdom.output.XMLOutputter;

public class jdom1 {
  public static void main (String args[]) {
    try {
      SAXBuilder builder = new SAXBuilder();
      Document document = builder.build("weblinks.xml");
      XMLOutputter ausgabe = new XMLOutputter();
      ausgabe.output(document, System.out);
    }
    catch (JDOMException je) {
      System.out.println("JDOM-Fehler: " + je.getMessage());
    }
    catch (Exception ie) {
      System.out.println(ie.getMessage());
    }
  }
}

Zu beachten ist, dass die Ausgabe der XML-Datei durch lediglich 4 Programmzeilen bestimmt wird!!!

Ein einfaches XML-Dokument erzeugen

Ein einfaches XML-Dokument ist mit Hilfe von JDOM-Klassen und -Methoden zu erstellen. Dazu sind nur wenige Klassen notwendig:

import org.jdom.Document;
import org.jdom.Element;
import org.jdom.output.XMLOutputter;
import java.io.IOException;

public class jdom4 {
    public static void main (String args[]) {
	Document dokument = new Document(new Element("wurzel")
					 .addContent(new Element("kind1").addContent("sohn ohne Nachkommen"))
					 .addContent(new Element("kind2")
						     .addContent(new Element("enkel1").addContent("enkel"))
						     .addContent(new Element("enkel2").addContent("enkelin")))
					 .addContent(new Element("kind3").addContent("tochter ohne Nachkommen")));
	XMLOutputter ausgabe = new XMLOutputter();
	try {
	    ausgabe.output(dokument,System.out);
	}
	catch (IOException e) {
	    System.out.println(e);
	}
    }
}

Besonders zu beachten ist die Schachtelung der Element-Methode "addContent()": Mit "new Element("elementname")" wird ein neues Element mit dem angegebenen Namen erzeugt und mit der Element-Methode "addContent(..)" als Kindelement eingetragen.

Mit der XMLOutputter-Methode "output()" kann der erzeugte XML-Dokumentenbaum ausgegeben werden; im Beispiel geschieht diese Ausgabe auf der Konsole:

<?xml version="1.0" encoding="UTF-8"?>
<wurzel><kind1>sohn ohne Nachkommen</kind1><kind2><enkel1>enkel</enkel1><enkel2>enkelin</enkel2></kind2>
<kind3>tochter ohne Nachkommen</kind3></wurzel>

Die verschachtelte Schreibweise im letzten Beispiel ist schwer zu lesen. Aus diesem Grund ist es im Allgemeinen günstiger, einen XML-Dokumentenbaum in Teilschritten wie folgt zu erzeugen:

import org.jdom.Document;
import org.jdom.Element;
import org.jdom.output.XMLOutputter;
import java.io.IOException;

public class jdom10 {
    public static void main (String args[]) {
        Element kind1 = new Element("kind");
        kind1.setAttribute("person","kind1");
        kind1.setAttribute("alter","31");
        Element name1 = new Element("name");
        name1.addContent("Gernot");
        kind1.addContent(name1);

        Element enkel1 = new Element("enkel");
        enkel1.setAttribute("person","enkel1");
        enkel1.setAttribute("alter","4");
        Element name2 = new Element("name");
        name2.addContent("Franz");
        enkel1.addContent(name2);

        Element enkel2 = new Element("enkel");
        enkel2.setAttribute("person", "enkel2");
        enkel2.setAttribute("alter","2");
        Element name3 = new Element("name");
        name3.addContent("Maria");
        enkel2.addContent(name3);

        Element kind2 = new Element("kind");
        kind2.setAttribute("person","kind2");
        kind2.setAttribute("alter","29");
        Element name4 = new Element("name");
        name4.addContent("Gerlinde");
        kind2.addContent(name4);
        kind2.addContent(enkel1);
        kind2.addContent(enkel2);

        Element wurzel = new Element("wurzel");
        wurzel.addContent(kind1);
        wurzel.addContent(kind2);

        Document dokument = new Document(wurzel);

        XMLOutputter ausgabe = new XMLOutputter();
        try {
            ausgabe.output(dokument,System.out);
        }
        catch (IOException e) {
            System.out.println(e);
        }
    }
}

Führen wir diese JAVA-Applikation aus, so erhalten wir die folgende unstrukturierte Ausgabe auf der Konsole:

nus@ice:~/java/xml/jdom> java jdom10
<?xml version="1.0" encoding="UTF-8"?>
<wurzel><kind person="kind1" alter="31"><name>Gernot</name></kind>
<kind person="kind2" alter="29"><name>Gerlinde</name><enkel person="enkel1" alter="4"><name>Franz</name></enkel>
<enkel person="enkel2" alter="2"><name>Maria</name></enkel></kind></wurzel>

Eine einfache Transformation ausführen

JDOM unterstützt in besonderer Weise das Ausführen von XSL-Transformationen. Wir verwenden dazu das folgende Stylesheet "weblinks.xsl":

<?xml version="1.0" encoding="iso-8859-1"?>
 <xsl:stylesheet version="1.0" xmlns:xsl = "http://www.w3.org/1999/XSL/Transform">
   <xsl:output method="html" />
   <xsl:template match="/">
     <html>
       <head>
         <title>WebLinks</title>
       </head>
       <body>
         <h1>WebLinks</h1>
         <xsl:apply-templates select="weblinks/eintrag">
          <xsl:sort select="kategorie" />
         </xsl:apply-templates>
       </body>
     </html>
   </xsl:template>

   <xsl:template match="weblinks/eintrag">
     <h2><xsl:value-of select="kategorie" /></h2>
     <p>
       <xsl:apply-templates select="url" />
     </p>
   </xsl:template>

   <xsl:template match="url">
     <strong><xsl:value-of select="../url" /></strong>
     <xsl:apply-templates select="../notiz" />
   </xsl:template>

   <xsl:template match="notiz">
     <dd>
       <xsl:value-of select="." />
     </dd>
   </xsl:template>
 </xsl:stylesheet>

In dieser (wohlgeformten) XML-Datei kommen nach der XML-Deklaration HTML-Elemente und XSL-Elemente vor. Um eine Verwechslung auszuschließen, werden so genannte Namensräume verwendet: Der Namensraum für die XSL-Elemente wird durch das Präfix xsl angegeben.

Wie XSL-Transformationen ablaufen ist gewöhnungsbedürftig: Grundsätzlich bestimmten Templates (Schablonen, Vorlagen), welche Elemente für die Ausgabe gewählt werden und welche Elemente neu generiert werden. Mit Hilfe der angegebenen Muster (patterns) wird festgelegt, auf welche Elemente des Eingabedokumentes ein Template angewendet werden soll. Was mit diesem Element geschehen soll wird in den so genannten Vorlagenregeln (template rules) festgelegt, die zwischen dem Starttag und Endetag des <xsl:template>-Elementes stehen.

Das erste Template im Beispiel wird anhand des Musters "/" auf das Wurzelelement der XML-Datei "weblinks.xml" angewendet. Konkret werden einige HTML-Elemente ausgegeben und ein Template ausgeführt (<xsl:apply-templates>,das alle <eintrag>-Elemente anhand des Inhaltes des <kategorie>-Elementes alphabetisch sortiert (<xsl:sort>). Weiters legt das select-Attribut des <xsl:apply-templates> fest, welche weiteren Templates ausgeführt werden sollen: Hier soll das Template, das auf das Muster "weblinks/eintrag" passt ausgeführt werden.

Das zweite Template bezieht sich genau auf dieses Muster: Hier soll zunächst das HTML-Element <h2> ausgegeben werden, dessen Inhalt aus dem Textwert des <kategorie>-Elementes besteht. An dieser Stelle ist es wichtig, dass das <kategorie>-Element ein direktes Kindelement von <eintrag> ist, welches auf Grund des Musters "weblinks/eintrag" ausgewählt wurde. Der Textwert wird mit Hilfe des XSL-Elementes <xsl:value-of> ausgegeben. Im folgenden HTML-Absatz (<p>) soll das Template für das Muster "url" ausgewählt werden.

Im vorletzten Template für das Muster "url" wird der Textwert des <url>-Elementes innerhalb des HTML-Elementes <strong> ausgegeben. Anschließend wird das letzte Template aufgerufen, das auf das Muster "notiz" passt. Da der Pfad für das Muster korrekt angegeben werden muss, ist es innerhalb des "url"-Templates notwendig, mit dem Muster ".." eine Elementebene höher zu steigen.

Das letzte Template passt auf die <notiz>-Elemente: Der Textwert jedes <notiz>-Elementes wird zwischen <dd>-Tags ausgegeben. Alle Notizelemente werden mit Hilfe des Musters "." gewählt.

Führen wir die Transformation mit Hilfe eines XSLT-Prozessors aus, so erhalten wir die folgende HTML-Datei:

<html>
    <head>
       <meta http-equiv="Content-Type" content="text/html; charset=utf-8">

       <title>WebLinks</title>
    </head>
    <body>
       <h1>WebLinks</h1>
       <h2>ast</h2>
       <p><strong>http://www.nasa.gov</strong><dd>Amerikanische Weltraumfahrtbehoerde</dd>
          <dd>Aktuelle Raumfahrtprojekte</dd>
          <dd>Historische Daten</dd>
       </p>
       <h2>ast</h2>
       <p><strong>http://www.heavens-above.com</strong><dd>Der abendliche Sternhimmel ...</dd>
          <dd>Beobachtung von Satelliten</dd>
          <dd>Iridium Flares</dd>
          <dd>Mond- und Sonnenbahn</dd>
       </p>
       <h2>edv</h2>
       <p><strong>http://www.w3.org</strong><dd>W3-Konsortium</dd>
          <dd>Technische Referenz</dd>
       </p>
       <h2>edv</h2>
       <p><strong>http://www.suse.de</strong><dd>phy</dd>
          <dd>SuSE, Linux</dd>
          <dd>Treiber-Datenbank</dd>
       </p>
       <h2>edv</h2>
       <p><strong>http://www.microsoft.com</strong><dd>Microsoft, Windows</dd>
          <dd>phy</dd>
          <dd>Sicherheits-Updates</dd>
          <dd>OS-Patches</dd>
       </p>
       <h2>med</h2>
       <p><strong>http://www.medizin.at</strong><dd>Die InternetSeite zur Gesundheit</dd>
       </p>
       <h2>phy</h2>
       <p><strong>http://www.cern.ch</strong><dd>Europaeisches Kernforschungszentrum</dd>
          <dd>Aktuelles zur Hochenergiephysik</dd>
          <dd>Materialien zur Elementarteilchenphysik</dd>
       </p>
    </body>
 </html>

Die Transformation mit JDOM durchführen

Die oben dargestellte Transformation eines XML-Baumes soll nun mit Hilfe von JDOM-Objekten durchgeführt werden:

import org.jdom.Document;
import org.jdom.JDOMException;
import org.jdom.input.SAXBuilder;
import org.jdom.output.XMLOutputter;
import org.jdom.transform.JDOMSource;
import org.jdom.transform.JDOMResult;

import java.util.List;
import javax.xml.transform.*;
import javax.xml.transform.stream.*;

public class jdom2 {

  static List ergebnis;

  public static void main (String args[]) throws Exception {
    SAXBuilder builder = new SAXBuilder();
    Document document = builder.build("weblinks.xml");
    ergebnis = transform(document, "weblinks.xsl");
    XMLOutputter xmlausgabe = new XMLOutputter();
    xmlausgabe.output(ergebnis, System.out);
  }

  public static List transform(Document in, String stylesheet) throws JDOMException {
    try {
      Transformer transformer = TransformerFactory.newInstance().newTransformer(new StreamSource(stylesheet));
      JDOMResult ausgabe = new JDOMResult();
      transformer.transform(new JDOMSource(in), ausgabe);
      return ausgabe.getResult();
    }
    catch (TransformerException e) {
      throw new JDOMException(e);
    }
  }
}

Die Transformation geschieht innerhalb der Methode transform(): Das ursprüngliche XML-Dokument wird als Document-Variable übergeben; die Stylesheet-Datei wird über ihren Dateinamen referenziert. transform() gibt das Ergebnis der Transformation als Liste zurück. Sie wird im Beispiel mit Hilfe der XMLOutputter-Methode output() auf der Konsole ausgegeben.

Das Ausgabedokument in einer Textdatei speichern

Im letzten Beispiel soll der transformierte XML-Datenbaum in einer Textdatei dauerhaft gespeichert werden. Dazu importieren wir zunächst das Package java.io und erzeugen das File-Objekt ausgabedatei:

import org.jdom.Document;
import org.jdom.JDOMException;
import org.jdom.input.SAXBuilder;
import org.jdom.output.XMLOutputter;
import org.jdom.transform.JDOMSource;
import org.jdom.transform.JDOMResult;

import java.util.List;
import javax.xml.transform.*;
import javax.xml.transform.stream.*;
import java.io.*;

public class jdom3 {

  static List ergebnis;
  static File ausgabedatei = new File("weblinks_out.html");

  public static void main (String args[]) throws Exception {
    SAXBuilder builder = new SAXBuilder();
    Document document = builder.build("weblinks.xml");
    ergebnis = transform(document, "weblinks.xsl");
    XMLOutputter xmlausgabe = new XMLOutputter();
    try {
      FileOutputStream ausgabestrom = new FileOutputStream(ausgabedatei);
      DataOutputStream datei = new DataOutputStream(ausgabestrom);
      xmlausgabe.output(ergebnis, datei);
    }
    catch (IOException e) {
      System.out.println(e);
    }
  }

  public static List transform(Document in, String stylesheet) throws JDOMException {
    try {
      Transformer transformer = TransformerFactory.newInstance().newTransformer(new StreamSource(stylesheet));
      JDOMResult ausgabe = new JDOMResult();
      transformer.transform(new JDOMSource(in), ausgabe);
      return ausgabe.getResult();
    }
    catch (TransformerException e) {
      throw new JDOMException(e);
    }
  }
}

Hat man die Textdatei für die Ausgabe vorbereitet, so schreibt man mit Hilfe der XMLOutputter-Methode "output()" den XML-Ergebnisdatenbaum in diese Datei.


© Alfred Nussbaumer, Weblog "MiniNuss"