XML-Serialisierung in Java? [geschlossen]

104

Was ist das Java-Analogon der XML-Serialisierung von .NET?

Dmitry Shechtman
quelle
6
Ah, die glorreichen alten Zeiten, in denen Einzeiler-Fragen wie diese auf SO willkommen waren. So nützlich. Ohne all das "Was haben Sie versucht?" / "Details bereitstellen" lesen die Leute heute gerne Unsinn.
GOTO 0

Antworten:

81

2008 Antwort Die "offizielle" Java-API hierfür ist jetzt JAXB - Java API für XML-Bindung. Siehe Tutorial von Oracle . Die Referenzimplementierung befindet sich unter http://jaxb.java.net/.

Update 2018 Beachten Sie, dass die Java EE- und CORBA-Module in SE in JDK9 veraltet sind und in JDK11 aus SE entfernt werden müssen . Um JAXB verwenden zu können, muss es sich entweder in Ihrer vorhandenen Enterprise-Class-Umgebung befinden, die von Ihrem z. B. App-Server gebündelt wird, oder Sie müssen es manuell einspielen.

Cheekysoft
quelle
2
Das ist richtig, JAXB ist definitiv die beste Option!
ivan_ivanovich_ivanoff
1
JAXB wurde ab Java 10 aus Standard-Java-Distributionen entfernt. Dies macht es jetzt zu einer Bibliothek, die Sie mit Ihrer Anwendung bündeln müssen, wenn Sie dies möchten, es sei denn, Sie arbeiten in einem Kontext, der es bereits für Sie bündelt.
Theodore Murdock
69

XStream ist ziemlich gut darin, Objekte ohne viel Konfiguration und Geld in XML zu serialisieren! (Es ist unter BSD-Lizenz).

Wir haben es in einem unserer Projekte verwendet, um die einfache alte Java-Serialisierung zu ersetzen, und es hat fast sofort funktioniert.

Barak Schiller
quelle
3
Sehr nützlich, es kann jedoch Probleme mit komplizierten Baumstrukturen wie JGraph mit Nicht-String-Knotenobjekten geben.
Mikek3332002
Einfacher und besser als andere Lösungen
daitangio
Ich mag XStream. Das einzige ist, dass ich nicht verstehe, warum ein Zeichen vor dem eigentlichen XML hinzugefügt wird.
James P.
17

Projekt "Einfache XML-Serialisierung"

Vielleicht möchten Sie sich das Simple XML Serialization- Projekt ansehen . Es ist das, was ich der System.Xml.Serialization in .Net am nächsten gefunden habe.

ARKBAN
quelle
Es sind jedoch Zuordnungsanmerkungen für jedes Feld erforderlich.
mP.
1
Nicht wahr, ich brauche nicht. Sie können das Standardverhalten ändern und es werden nur vorhandene Felder verwendet.
Damluar
1
Ich unterstütze von Herzen auch "Einfach" . Ich habe es bei einigen Projekten mit großem Erfolg eingesetzt. "Einfach" ist in der Tat viel einfacher als JAXB. Am besten geeignet, wenn Sie relativ einfache Anforderungen haben: Objekte, die in den Speicher geschrieben werden müssen, um später wieder als Objekte hydratisiert zu werden. JAXB bietet weitaus mehr Funktionen und Flexibilität, ist jedoch eine Art "80/20". In den meisten Projekten benötigen Sie meistens nur die einfache Teilmenge der Funktionen.
Basil Bourque
Funktioniert gut, wenn Sie nur eine 1: 1-Zuordnung wünschen. Wenn sich Ihre Klassen weiterentwickeln und Sie noch altes XML deserialisieren müssen, treten Probleme auf, da sowohl die Dokumentation als auch die Fehlermeldungen etwas vage sind. Die Diagnose des Problems ist normalerweise möglich, es kann jedoch mehrere Tage dauern, bis das Problem behoben ist.
Werkzeugschmiede
13

JAXB ist Teil der JDK Standard Edition Version 1.6+. Es gibt also FREEkeine zusätzlichen Bibliotheken zum Herunterladen und Verwalten. Ein einfaches Beispiel finden Sie hier

XStream scheint tot zu sein. Das letzte Update war am 6. Dezember 2008. Es Simplescheint so einfach und einfacher zu sein wie JAXB, aber ich konnte keine Lizenzinformationen finden, um es für den Unternehmensgebrauch auszuwerten.

so_mv
quelle
4
XStream ist nicht tot, es ist nur ausgereift und stabil - was bedeutet, dass der Kernfunktionalität nicht viel hinzugefügt werden muss. Gleiches gilt für die JAXB-Referenzimplementierung, die in den letzten Jahren kaum aktiv war.
StaxMan
9

Erwähnenswert ist, dass Java seit Version 1.4 die Klassen java.beans.XMLEncoder und java.beans.XMLDecoder hatte. Diese Klassen führen eine XML-Codierung durch, die zumindest sehr gut mit der XML-Serialisierung vergleichbar ist und unter bestimmten Umständen den Trick für Sie erledigt.

Wenn sich Ihre Klasse an die JavaBeans-Spezifikation für ihre Getter und Setter hält, ist diese Methode einfach zu verwenden und Sie benötigen kein Schema. Mit folgenden Einschränkungen:

  • Wie bei der normalen Java-Serialisierung
    • Das Codieren und Decodieren läuft über einen InputStream und einen OutputStream
    • Der Prozess verwendet die bekannten Methoden writeObject und readObject
  • Im Gegensatz zur normalen Java-Serialisierung
    • Durch die Codierung, aber auch die Decodierung werden Konstruktoren und Initialisierer aufgerufen
    • Das Codieren und Decodieren funktioniert unabhängig davon, ob Ihre Klasse Serializable implementiert oder nicht
    • transiente Modifikatoren werden nicht berücksichtigt
    • funktioniert nur für öffentliche Klassen, die öffentliche Konstruktoren haben

Nehmen Sie zum Beispiel die folgende Erklärung:

public class NPair {
  public NPair() { }
  int number1 = 0;
  int number2 = 0;
  public void setNumber1(int value) { number1 = value;}
  public int getNumber1() { return number1; }
  public void setNumber2(int value) { number2 = value; }
  public int getNumber2() {return number2;}
}

Ausführen dieses Codes:

NPair fe = new NPair();
fe.setNumber1(12);
fe.setNumber2(13);
FileOutputStream fos1 = new FileOutputStream("d:\\ser.xml");
java.beans.XMLEncoder xe1 = new java.beans.XMLEncoder(fos1);
xe1.writeObject(fe);
xe1.close();

Würde zu folgender Datei führen:

<?xml version="1.0" encoding="UTF-8"?>
<java version="1.7.0_02" class="java.beans.XMLDecoder">
 <object class="NPair">
  <void property="number1">
   <int>12</int>
  </void>
  <void property="number2">
   <int>13</int>
  </void>
 </object>
</java>
Mishax
quelle
Beachten Sie, dass die Verwendung java.beans.XMLDecodermit vom Benutzer bereitgestellten Daten zu Sicherheitslücken bei der Ausführung von Code in Ihrem Code führen kann.
Aventurin
2

XMLBeans funktioniert hervorragend, wenn Sie ein Schema für Ihr XML haben. Es erstellt Java-Objekte für das Schema und einfach zu verwendende Analysemethoden.

John Meagher
quelle
0

Wenn Sie über die automatische XML-Serialisierung von Objekten sprechen, lesen Sie Castor :

Castor ist ein Open Source-Datenbindungsframework für Java [tm]. Dies ist der kürzeste Weg zwischen Java-Objekten, XML-Dokumenten und relationalen Tabellen. Castor bietet Java-zu-XML-Bindung, Java-zu-SQL-Persistenz und mehr.

Das Ö
quelle
0

Normalerweise verwende ich jaxb oder XMLBeans, wenn ich Objekte erstellen muss, die für XML serialisierbar sind. Jetzt kann ich diesen XStream sehen sehr nützlich sein kann, da es nicht aufdringlich ist und eine wirklich einfache API hat. Ich werde bald damit spielen und es wahrscheinlich benutzen. Der einzige Nachteil, den ich bemerkt habe, ist, dass ich die Objekt-ID nicht selbst für Querverweise erstellen kann.

@ Barak Schiller
Danke, dass du den Link zu XStream gepostet hast!

Bartosz Bierkowski
quelle
Problem ist, dass jaxb und xmlbeans ein Mapping-Schema erfordern und nicht automatisch ...
mP.
0

Wenn Sie eine strukturierte Lösung (wie ORM) wünschen, ist JAXB2 eine gute Lösung.

Wenn Sie eine Serialisierung wie DOT NET wünschen, können Sie die Langzeitpersistenz von JavaBeans-Komponenten verwenden

Die Wahl hängt von der Verwendung der Serialisierung ab.

m.genova
quelle
-1
public static String genXmlTag(String tagName, String innerXml, String properties )
{
    return String.format("<%s %s>%s</%s>", tagName, properties, innerXml, tagName);
}

public static String genXmlTag(String tagName, String innerXml )
{
    return genXmlTag(tagName, innerXml, "");
}

public static <T> String serializeXML(List<T> list)
{
    String result = "";
    if (list.size() > 0)
    {
        T tmp = list.get(0);
        String clsName = tmp.getClass().getName();
        String[] splitCls = clsName.split("\\.");
        clsName = splitCls[splitCls.length - 1];
        Field[] fields = tmp.getClass().getFields();

        for (T t : list)
        {
            String row = "";
            try {
                for (Field f : fields)
                {
                    Object value = f.get(t);
                    row += genXmlTag(f.getName(), value == null ? "" : value.toString());
                }
            } catch (IllegalAccessException e) {
                e.printStackTrace();
            }
            row = genXmlTag(clsName, row);

            result += row;
        }
    }

    result = genXmlTag("root", result);
    return result;
}
user4067649
quelle
Viele Probleme: Neuerfindung der Klasse # getSimpleName *** Neuerfindung von PropertyDescriptor *** Angenommen, alle Eigenschaften sind zugängliche Felder *** Speichert keine Reflexionsergebnisse zwischen (langsam) *** Keine Möglichkeit, etwas anzupassen (z. B. müsste ich ersetzen Klassen- und Dateinamen) *** Keine Deserialisierung
Toolforger