- Initialisierung
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import org.w3c.dom.Document;
...
DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance();
DocumentBuilder documentBuilder = documentBuilderFactory.newDocumentBuilder();
Document docSherd = documentBuilder.newDocument();
Hier wird ein org.w3c.dom.Document
erzeugt, indem zuerst eine DocumentBuilderFactory
, daraus ein DocumentBuilder
(beides sind abstrakte Klassen, deren Default-Implementierungen in der Java Runtime stecken, aber vor uns weggekapselt sind und durch reine Konfigurationsänderungen
durch andere APIs ersetzt werden könnten)
.
- Wurzelelement anlegen
- Ziel
Das Ergebnis soll so aussehen:
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<sherd name="Testdiagramm" version="0.5" width="800" height="600"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.informatik.fh-wiesbaden.de/~knauf/SWTProjekt2009/sherd http://www.informatik.fh-wiesbaden.de/~knauf/SWTProjekt2009/sherd.xsd"
xmlns="http://www.informatik.fh-wiesbaden.de/~knauf/SWTProjekt2009/sherd">
...
</sherd>
- Wurzelelement und Default-Namespace
Um es zu erzeugen, ist folgender Code nötig:
import org.w3c.dom.Element;
...
Element nodeSherd = docSherd.createElementNS("http://www.informatik.fh-wiesbaden.de/~knauf/SWTProjekt2009/sherd", "sherd");
docSherd.appendChild(nodeSherd);
Die Document
-Instanz nutzen wir, um neue Elemente oder sonstige Knotentypen zu erzeugen. Normalerweise reicht es, die Methode createElement
mit dem Element-Namen als Parameter aufzurufen. Für das Wurzelelement soll allerdings auch ein Default-Namespace eingetragen werden. Der Namespace (beliebige URI)
sieht hier aus wie eine Internet-URL.
Das Ergebnis dieses Aufrufs würde so aussehen:
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<sherd xmlns="http://www.informatik.fh-wiesbaden.de/~knauf/SWTProjekt2009/sherd">
...
</sherd>
"schemaLocation"
Jetzt wird die SchemaLocation für den Default-Namespace "http://www.informatik.fh-wiesbaden.de/~knauf/SWTProjekt2009/sherd" erzeugt.
Dieses Attribut steckt im Standard-Namespace "http://www.w3.org/2001/XMLSchema-instance", der den Präfix "xsi" haben soll
(d.h. wir müssen diesen Namespace ebenfalls einbinden).
Attribute könnte man über das Document
(Methode createAttribute
bzw. createAttributeNS
) erzeugen. Es gibt allerdings eine
Vereinfachung, um ein Attribut direkt in das Element zu packen.
nodeSherd.setAttributeNS("http://www.w3.org/2001/XMLSchema-instance",
"xsi:schemaLocation",
"http://www.informatik.fh-wiesbaden.de/~knauf/SWTProjekt2009/sherd http://www.informatik.fh-wiesbaden.de/~knauf/SWTProjekt2009/sherd.xsd");
Hier wird ein Attribut namens "xsi:schemaLocation" definiert, wobei der Namespace-Prefix "xsi" des Attributs mit dem Namespace "http://www.w3.org/2001/XMLSchema-instance" verbunden wird.
Die "schemaLocation" verbindet den "sherd"-Namespace mit der XSD im Web. Für jeden der über "setAttributeNS" definierten Namespaces wird automatisch ein "xmls=..."-Attribut erzeugt.
Quelle: http://bytes.com/groups/xml/468470-how-declare-namespace-prefix-java
- Sonstige Attribute
Jetzt fehlen noch die "sherd"-Attribute "Diagrammname" und "Version":
nodeSherd.setAttribute("name", "Testdiagramm");
nodeSherd.setAttribute("version", "0.5");
nodeSherd.setAttribute("width", "800");
nodeSherd.setAttribute("height", "600");
- Elemente "tabellen", "relations" und "comments" anlegen
Das ist einfach:
Element elementTabellen = docSherd.createElement("tabellen");
nodeSherd.appendChild(elementTabellen);
Element elementRelations = docSherd.createElement("relations");
nodeSherd.appendChild(elementRelations);
Element elementComments= docSherd.createElement("comments");
nodeSherd.appendChild(elementComments);
- Subelement "tabelle" zufügen
Dem "tabellen"-Element wird ein Unterelement "tabelle" mit allen Attributen zugefügt:
Element elementTabelle = docSherd.createElement("tabelle");
elementTabelle.setAttribute("x", ... );
elementTabelle.setAttribute("y", ... );
elementTabelle.setAttribute("width", ... );
elementTabelle.setAttribute("height", ... );
elementTabelle.setAttribute("id", ... );
elementTabelle.setAttribute("tabellenname", ... );
elementTabellen.appendChild(elementTabelle);
Die restlichen Unterelemente werden nach dem gleichen Schema erzeugt.
- Subelement "comment" mit Textinhalt zufügen
Das Element "comment" hat eine Besonderheit: es kann Textinhalt haben. Hier gibt es zwei Möglichkeiten:
Variante 1: Textinhalt
Element elementKommentar = this.docSherd.createElement("comment");
...
elementKommentar.setTextContent("Kommentar 2 mit Markup wie '<', '>', '&'");
elementComments.appendChild(elementKommentar);
Variante 2: "CDATA"-Sektion
Element elementKommentar = this.docSherd.createElement("comment");
...
CDATASection commentText = docSherd.createCDATASection("Kommentar 2 mit Markup wie '<', '>', '&'");
elementKommentar.appendChild(commentText);
elementComments.appendChild(elementKommentar);
Den größten Unterschied zwischen den beiden Varianten erkennt man, wenn man (wie in meinem Beispielprogramm geschehen) "reservierte" Zeichen wie <, > &&
in den Kommentar hängt.
In Variante 1 entsteht dieses XML:
<comment id="501" ...>Kommentar 2 mit Markup wie '<', '>', '&'</comment>
Die reservierten Zeichen werden also automatisch durch Standard-Entities ersetzt.
Variante 2 erzeugt dieses:
<comment id="501" ...><![CDATA[Kommentar 2 mit Markup wie '<', '>', '&']]></comment>
Durch die "<![CDATA[...]]>"-Klammerung müssen reservierte Zeichen nicht mehr maskiert werden. Allerdings darf der Stringinhalt nicht "]]>" enthalten,
denn das würde die Sektion beenden!