Serialization of versions in Java

I have a simple Java class that I need to serialize to store as a value in an RDBMS or key value store. A class is simply a collection of properties of simple types (native types or Maps / lists of native types). The problem is that the class will most likely change over time (probably: adding new properties is less likely, but still possible: renaming the property, changing the type of the property, deleting the property).

I would like to be able to gracefully handle changes in the version of the class. In particular, when an attempt is made to de-serialize an instance from an older version, I would like to be able to specify some kind of handler to control the transition of the old instance to the latest version.

I do not think Java-based serialization is appropriate here. Before trying to overturn my own solution, I wonder if anyone knows about existing libraries that can help? I know a ton of alternative serialization methods for Java, but I'm specifically looking for something that will allow me to gracefully handle changes to the class definition over time.

Edit:

For what it was worth, I ended up working with the protocol buffer ( http://code.google.com/p/protobuf/ ), because it is flexible for adding and renaming fields, while on a less code snippet I have to support (in regarding Java custom serialization using readObject / writeObject).

+4
source share
5 answers

Java serialization lets you customize the serial form by providing the readObject and writeObject . Together with ObjectInputStream.readFields , ObjectOutputStrean.putFields and defining serialPersistentFields , the serialized form may not be related to the actual fields in the implementation class.

However, Java serialization creates opaque data that cannot be read and written through other methods.

+4
source

Perhaps you should map your Java class to the relational model. Dumping some serialized blob language into a database column is a terrible approach.

+2
source

It is quite simple using a read and write object.

Try setting serialversionuid to a fixed value, then define a static target field for your version. Readobject can then use the switch statement to build the fields depending on the version. We use this to store historical data in our file system. This is very fast when searching - so much so that users cannot tell the difference.

+1
source

I had a similar problem. I found out that Java serialVersionUID helps a little when you have multiple versions of objects. So I rolled out my own.

Here is what I do to save our user sessions,

  • In my database, in addition to the BLOB field for serialized objects, I added a version column.
  • Whenever we change the session object, I save the old class, for example SessionV3.
  • A session is always written to the database with the current version number.
  • When reading a session, it is deserialized into the session object directly if the version is current. Otherwise, it is deserialized to the old object and manually copied to the current session object (SessionV3 => Session).
  • From time to time, we run a DB script to remove real old versions of the session so that we can clear the old sessions from the code. If we care about old sessions, we can also transform them.

There may be an easier way to do this, but our approach gives us more flexibility.

0
source

Never tried, but you can do something with a custom loader to load the correct version of the class file at runtime for a deserialized object.

0
source

All Articles