2008-09-30 11 views
20

Ich frage mich, ob es sicher ist, jdk 1.5 und 1.6 (Java 6) Objekt Serialisierung (biderctional Kommunikation) zu mischen. Ich suchte nach einer expliziten Aussage von Sun zu dieser Frage, die aber nicht gelang. So suche ich neben der technischen Machbarkeit nach einer "offiziellen" Aussage zum Problem.Ist Java Objekt Serialisierung kompatibel zwischen 1.5 und 1.6

+0

ich weiß, dass dies eine alte Frage, aber für zukünftige Entwickler, ist dies etwas, das ich ausgiebig für ein Produkt mit Kunden verwendet habe, Server, die POJOs für mehrere Jahre verwenden. Die serialisierten Objekte zwischen den Versionen hat ohne Probleme funktioniert. Das einzige Mal, dass wir ein Problem hatten, war, als wir die Serialisierungsregeln durchbrochen haben. Ändern Sie beispielsweise nicht den Typ einer Variablen. –

Antwort

2

Nach dem Testen mit einem serialisierten Objekt in eine Datei geschrieben mit dem ObjectOutputStream in einem Java 1.5-Programm, dann einen Lesevorgang mit einem ObjectInputStream in einem Java-1.6-Programm kann ich sagen, das funktionierte ohne jedes Problem.

+0

Nein, du kannst nicht. Du hast es für eine Klasse getestet. Eine Schwalbe macht keinen Sommer. – EJP

16

Der Serialisierungsmechanismus selbst hat sich nicht geändert. Für einzelne Klassen hängt es von der spezifischen Klasse ab. Wenn eine Klasse ein serialVersionUID-Feld hat, sollte dies die Serialisierungskompatibilität anzeigen.

Etwas wie:

private static final long serialVersionUID = 8683452581122892189L; 

Wenn es unverändert ist, sind die serialisierten Versionen kompatibel. Für JDK-Klassen ist dies garantiert, aber natürlich ist es immer möglich zu vergessen, die serialVersionUID zu aktualisieren, nachdem eine Änderung vorgenommen wurde.

Wenn JDK-Klassen nicht garantiert kompatibel sind, wird dies normalerweise im Javadoc erwähnt.

Warnung: serialisierten Objekte dieser Klasse werden nicht mit zukünftigen Swing-Versionen

2

kompatibel wäre ich schnell hinzufügen, dass es möglich ist, die Klasse zu ändern, aber vergessen die serialVersionUID zu ändern. Es ist also falsch, dass "Wenn die Klasse eine serialVersionUID definiert und sich dies nicht ändert, ist die Klasse garantiert kompatibel." Mit der gleichen serialVersionUID ist die Art und Weise, wie eine API Abwärtskompatibilität verspricht, gegeben.

+0

Ich ging davon aus, dass die Frage über JDK-Klassen ist, und dass ihre serialVersionUIDs korrekt sind ... – Tom

+0

Fair genug: Wenn Ihr JDK-Upgrade Serializable durcheinander bringt, die Clients Ihres großen Jungen JDK (dh Sun, BEA, IBM, etc.)) sollte blutiger Mord schreien (und ich habe). Zugegebenermaßen war die Frage nicht klar, ob es sich nur um JDK-Klassen handelte. – Alan

2

Sofern nicht anders angegeben, sollte dies Teil der Binärkompatibilität sein. Swing-Klassen sind explizit nicht kompatibel zwischen den Versionen. Wenn Sie ein Problem mit anderen Klassen feststellen, melden Sie einen Fehler unter bugs.sun.com.

+0

Bei der Binärkompatibilität handelt es sich um die öffentliche und geschützte Schnittstelle, während bei der Serialisierungskompatibilität normalerweise private Felder verwendet werden. Sind Sie sicher, dass einer den anderen impliziert? – Tom

+0

Technisch ist es nicht Binärkompatibilität wie in Kapitel 13 der JLS definiert. Allerdings ist eine binäre Kompatibilität in Bezug auf die Serialisierung zwischen Java-Versionen erforderlich, sofern nicht anders angegeben. Wenn Sie ein Problem finden, melden Sie einen Fehler. –

2

Haben Sie die Java Object Serialization Specification gelesen? Es gibt ein Thema auf versioning. Es gibt auch einen Artikel für Klassenimplementierer: Discover the secrets of the Java Serialization API. Jede Java-Version wird von begleitet.

Vom Java 6 spec auf Serialisierung:


Die Ziele sind:

  • Unterstützung bidirektionale Kommunikation zwischen den verschiedenen Versionen einer Klasse in verschiedenen virtuellen Maschinen durch den Betrieb:
    • Definieren eines Mechanismus, mit dem JavaTM-Klassen Ströme lesen können, die von älteren Versionen derselben Klasse geschrieben wurden.
    • Definieren eines Mechanismus, mit dem JavaTM-Klassen Streams schreiben können, die von älteren Versionen derselben Klasse gelesen werden sollen.
  • Bereitstellung der Standardserialisierung für die Persistenz und für RMI.
  • Führen Sie in einfachen Fällen gut aus und erstellen Sie kompakte Datenströme, sodass RMI die Serialisierung verwenden kann.
  • Sie können Klassen identifizieren und laden, die genau der Klasse entsprechen, die zum Schreiben des Streams verwendet wurde.
  • Halten Sie den Overhead für nicht versionierte Klassen niedrig.
  • Verwenden Sie ein Stream-Format, das das Traversieren des Streams ermöglicht, ohne dass Methoden aufgerufen werden müssen, die für die im Stream gespeicherten Objekte spezifisch sind.

3

Der Serialisierungsmechanismus in 1.5 und 1.6 kompatibel ist. Daher kann der gleiche Code, der in einem 1.5- und 1.6-Kontext kompiliert wurde, serialisierte Objekte austauschen. Ob die zwei VM-Instanzen die gleiche/kompatible Version der Klasse haben (wie durch das Feld serialVersionUID angezeigt werden kann), ist eine andere Frage, die nicht mit der JDK-Version zusammenhängt.

Wenn Sie ein serialisierbares Foo.java haben und dieses in einem 1.5 und 1.6 JDK/VM verwenden, werden serialisierte Instanzen von Foo von einem V erstellt; kann vom anderen deserialisiert werden.

0

Beachten Sie, dass die Java Beans-Spezifikation eine versionsunabhängige Serialisierungsmethode beschreibt, die eine starke Abwärtskompatibilität ermöglicht. Es führt auch zu lesbaren "serialisierten" Formen. In der Tat kann ein serialisiertes Objekt ziemlich einfach mit dem Mechanismus erstellt werden.

Suchen Sie die Dokumentation zu den Klassen XMLEncoder und XMLDecoder.

Ich würde dies nicht für die Übergabe eines Objekts über den Draht unbedingt verwenden (obwohl, wenn hohe Leistung eine Voraussetzung ist, würde ich auch keine Serialisierung verwenden), aber es ist von unschätzbarem Wert für persistenten Objektspeicher.

0

Es ist nicht sicher, Java 1.5 und 1.6 zu mischen. Zum Beispiel habe ich ein Java 1.5 Objekte in eine Datei serialisiert und versucht, Öffnen in Java 1.6 aber es kam mit der folgenden Fehler

java.io.InvalidClassException: javax.swing.JComponent; lokaler Klasse unvereinbar: Strom classdesc serialVersionUID = 7917968344860800289, lokale Klasse serialVersionUID = -1030230214076481435 bei java.io.ObjectStreamClass.initNonProxy (Unknown Source) bei java.io.ObjectInputStream.readNonProxyDesc (Unknown Source) bei java.io.ObjectInputStream. readClassDesc (Unknown Source) bei java.io.ObjectInputStream.readNonProxyDesc (Unknown Source) bei java.io.ObjectInputStream.readClassDesc (Unknown Source) bei java.io.ObjectInputStream.readNonProxyDesc (Unknown Source) bei java.io. ObjectInputStream.readClassDesc (unbekannte Quelle) bei java.io.ObjectInputStream.readOrdinaryObject (unbekannte Quelle) bei java.io.ObjectInputStream.readObject0 (unbekannte Quelle) bei java.io.ObjectInputStream.readArray (Unknown Source) bei java.io.ObjectInputStream.readObject0 (Unknown Source) bei java.io.ObjectInputStream.defaultReadFields (Unknown Source) bei java.io.ObjectInputStream.readSerialData (Unbekannt Source) bei java.io.ObjectInputStream.readOrdinaryObject (Unknown Source) bei java.io.ObjectInputStream.readObject0 (Unknown Source) bei java.io.ObjectInputStream.defaultReadFields (Unknown Source) bei java.io.ObjectInputStream.readSerialData (Unbekannte Quelle) bei java.io.ObjectInputStream.readOrdinaryObject (Unbekannte Quelle) bei java.io.ObjectInputStream.readObject0 (Unbekannte Quelle) bei java.io.ObjectInputStream.readarray (Unknown Source) bei java.io.ObjectInputStream.readObject0 (Unknown Source) bei java.io.ObjectInputStream.defaultReadFields (Unknown Source) bei java.io.ObjectInputStream.readSerialData (Unknown Source) bei java.io. ObjectInputStream.readOrdinaryObject (Unknown Source) bei java.io.ObjectInputStream.readObject0 (Unknown Source) bei java.io.ObjectInputStream.readObject (Unknown Source)

+0

Es ist nicht sicher * für diese spezifische Klasse *, wie es eindeutig in seinem eigenen Javadoc angibt. Sie sind hier nicht auf ein Gesetz des Universums gestoßen. – EJP