XML über das Netz

chironex

Erfahrenes Mitglied
Hallo Leute, ich habe ein wenig Troubles beim Schreiben eines Netzwerktools:

Anfangs habe ich versucht, Nachrichten als Texte über das Netzwerk zu schicken. Dazu habe ich einen Thread abgeleitet, welcher in einer Endlosschleife die readline Methode des Buffered Readers aufruft und blockiert, bis eine neue Zeile gekommen ist. Sind neue Daten eingelangt, wird ein anderes Objekt asynchron davon benachrichtigt.

while (ok)
{
try
{
String s = m_reader.readLine();
m_owner.dataReceived(s);
}
catch (IOException ioex)
{
ok = false;
m_owner.ConnectionBroken();
}
}


Soweit so gut.

Mit steigender Komplexität fand ich es aber besser, die Daten im XML-Format zu senden und zu empfangen.

Und damit bin ich auch schon beim Problem :)

Die Daten kann ich den XML-Klassen nur als Stream oder in Form von Files übergeben.

Jede Nachricht als File zu speichern, einzulesen und zu löschen wäre ein Schildbürgerstreich ...

Wenn ich jedoch die Daten mit einem Stream übergebe, kann der Documentbuilder ja nicht wissen, wann alle Daten angekommen und diese zu parsen sind.

DocumentBuilderFactory fabrik = DocumentBuilderFactory.newInstance();
DocumentBuilder aufbau = fabrik.newDocumentBuilder();
Document xmlbaum = aufbau.parse(is);

Mir ist schon klar, dass diese Vorgehensweise bei Files spitze funktioniert, aber mir ist schleierhaft, wie das über das Netzwerk funktionieren soll. Weiss jemand von Euch Rat bzw. hat jemand dazu Code Snippets, oä?
 
Hallo!

Suchst du vielleicht sowas?

XMLServer:
Code:
/*
 * Created on 16.01.2005@23:55:36
 *
 * TODO Licence info
 */
package de.tutorials.xmlmessenger;

import java.io.BufferedReader;
import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.ServerSocket;
import java.net.Socket;

import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.ParserConfigurationException;
import javax.xml.xpath.XPath;
import javax.xml.xpath.XPathExpressionException;
import javax.xml.xpath.XPathFactory;

import org.w3c.dom.Document;
import org.w3c.dom.Node;
import org.xml.sax.SAXException;

/**
 * @author Administrator
 *
 * TODO Explain me
 */
public class XMLServer {

    public static void main(String[] args) {
        try {
            ServerSocket serverSocket = new ServerSocket(2017);

            System.out.println("XML Server ready!");

            Socket socket = serverSocket.accept();

//In "richtigen" Applikationen sollte man hier jedoch auf einem BufferedInputStream operieren, dann wär's ein wenig flotter.
            BufferedReader br = new BufferedReader(new InputStreamReader(socket
                    .getInputStream()));

            String line;

            DocumentBuilderFactory factory = DocumentBuilderFactory
                    .newInstance();
            DocumentBuilder builder = factory.newDocumentBuilder();

            //Ab Java 5.0
            XPathFactory xPathFactory = XPathFactory.newInstance();
            XPath xPath = xPathFactory.newXPath();
            //.

            while ((line = br.readLine()) != null) {
                Document doc = builder.parse(new ByteArrayInputStream(line
                        .getBytes()));
                //Entweder so ... 
                Node msgNode = doc.getFirstChild();
                Node contentNode = msgNode.getFirstChild();
                System.out.println(contentNode.getTextContent());

                //oder per XPath unter Java 5.0
                System.out.println(xPath.evaluate("//msg/content/text()", doc));
            }

        } catch (IOException e) {
            e.printStackTrace();
        } catch (ParserConfigurationException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (SAXException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (XPathExpressionException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }

    }
}

XMLClient:
Code:
/*
 * Created on 16.01.2005@23:58:49
 *
 * TODO Licence info
 */
package de.tutorials.xmlmessenger;

import java.io.BufferedWriter;
import java.io.IOException;
import java.io.OutputStreamWriter;
import java.net.Socket;
import java.net.UnknownHostException;

/**
 * @author Administrator
 *
 * TODO Explain me
 */
public class XMLClient {

    public final static String XML_MESSAGE_TEMPLATE = "<?xml version=\"1.0\" ?><msg><content>#</content></msg>";

    public static void main(String[] args) {
        try {
            Socket s = new Socket("localhost", 2017);

            BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(s
                    .getOutputStream()));

            String helloMsg = XML_MESSAGE_TEMPLATE.replaceFirst("\\#",
                    "Hallo, Welt!");
            String exitMsg = XML_MESSAGE_TEMPLATE.replaceFirst("\\#", "EXIT");

            bw.write(helloMsg);
            bw.newLine();
            bw.flush();
            bw.write(exitMsg);
            bw.newLine();
            bw.flush();

            s.close();

        } catch (UnknownHostException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }

    }
}

HTH,
Gruß Tom
 
Hallo Thomas,

vielen Dank, Du hast mir echt weitergeholfen.

Eigentlich hätte mir die folgende Zeile Deines Servers schon gereicht:

Document doc = builder.parse(new ByteArrayInputStream(line.getBytes()));

Ich bin bei den Streams und Readern nicht so sattelfest, da ich aus Microsofts .Net Ecke komme und mir die Eigenheiten der Java Implementierung noch nicht so geheuer sind.

Den Rest hatte ich schon geschrieben als ich mit nichtXML-Nachrichten gearbeitet habe. Ich bin mir aber sicher, dass Dein Code ein gutes Beispiel für eine einfache Client/Server Verbindung ist.

mfg und nochmals Danke für Deine nächtliche Hilfe, Karl
 
Zurück