«

»

Jul
12

Inside Implementing & Customizing Serialization in Java

Implementing serialization in Java is pretty straight forward just a little step task. The class you want to be serialized just have to implements a marker Interface Serializable no override nothing extra work.

The JVM will take care of serialization and deserialization process automatically. Now you can write your object to any persistent technology e.g. database, file system or even over the network.

Serialization:   The process of writing bits and bytes of a java object to physical stream.

Deserialization: The process of reading bits and bytes from physical stream to construct a java object.

Implementing serialization straight forward or lightly may cause problems in future. Let’s discuss some issues that can be faces.

If you not implement serialVersionUID, when you are saving the object JVM automatically calculate serialVersionUID depending upon the various class factors. So when deserialization reading object back it again calculate the serialVersionUID  of the persistent object and to whom class it going to referenced. If class structure changed after saving object then a ClassCastException will be thrown.

JVM takes significant time to generate serialVersionUID at runtime, so having serialVersionUID generated will also improve the performance.

So always be sure to have serialVersionUID, follow the guidelines to implement serialVersionUID.

  • Always include it as field, “private static final long serialVersionUID = 1L”, include this field even in the first version of the class, as a reminder of its important.
  • Do not alter the value of this field in future versions, unless you are knowingly making changes to the class which will result in incompatible with all old serialized objects.
  • In Windows, generate serialVersionUID using JDK’s graphical tool like so: issue the like following
    serialver –show persistentClassName/Path
  • Most of modern IDEs can generate serialVersionUID, like in My Eclipse if you are implement Serializable interface, it will show a bulb sign clicking on it will indicate to generate serialVersionUID automatically by the IDE.

Now come the second issue, you have implemented Serializable interface, serialVersionUID but what if you are using a third party API and you referenced their some class in your persistent class. But API’s those classes are not Serializable, so you can’t make any modification to mark the Serializable.

So, when you trying to persist (serialize) your class that contains some API’s not serialize classes, you will encounter exception NotSerializableException like this.

NotSerializableException 300x100 Inside Implementing & Customizing Serialization in Java

Java NotSerializableException Exception

You understand? Ok fine, so what to do to deal with situation.

Solution: Now, you have to customize the default serialization and deserialization process of JVM.

Implement the Serializable interface and override the readObject() and writeObject() in the following way.

The complete code snippet is given below with detailed information.

import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;

public class MainRunner {
	public static void main(String args[]) {
		MainRunner runner = new MainRunner();
		LoanCandidate candidate = new LoanCandidate();
		candidate.setApplicationNo(1000123L);
		candidate.setId("Faisal");
		candidate.setName("Faisal Basra");
		LoanInfo info = new LoanInfo();
		info.setAmount(500000L);
		info.setLoanPct(12L);
		info.setName("Faisal Lona");
		candidate.setLoanInfo(info);
		runner.write(candidate);
		System.out.println("completed...");
	}

	public void write(LoanCandidate candidate){
		FileOutputStream fos;
		try {
			fos = new FileOutputStream(new File("test.srz"));
			ObjectOutputStream stream = new ObjectOutputStream(fos);
			stream.writeObject(candidate);
			stream.flush();
			stream.close();
		} catch (FileNotFoundException e) {
			e.printStackTrace();
		} catch (IOException e) {
			e.printStackTrace();
		}
	}

	public LoanCandidate read(){
		try {
			FileInputStream fis = new FileInputStream(new File("test.srz"));
			ObjectInputStream ois = new ObjectInputStream(fis);
			LoanCandidate candidate = (LoanCandidate)ois.readObject();
			return candidate;
		} catch (FileNotFoundException e) {
			e.printStackTrace();
		} catch (IOException e) {
			e.printStackTrace();
		} catch (ClassNotFoundException e) {
			e.printStackTrace();
		}
		return null;
	}

}

class LoanCandidate implements Serializable {

	private static final long serialVersionUID = -7971342269203014337L;
	private String name;
	private String id;
	private Long applicationNo;
	// This is not serialized class and will throw an NotSerializableException
	//Mark it transient, then we will manually write and read its values during
	//serialization and deserialization process.
	private transient LoanInfo loanInfo;

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	public String getId() {
		return id;
	}

	public void setId(String id) {
		this.id = id;
	}

	public Long getApplicationNo() {
		return applicationNo;
	}

	public void setApplicationNo(Long applicationNo) {
		this.applicationNo = applicationNo;
	}

	public LoanInfo getLoanInfo() {
		return loanInfo;
	}

	public void setLoanInfo(LoanInfo loanInfo) {
		this.loanInfo = loanInfo;
	}

	public void readOjbect(ObjectInputStream ois) throws IOException,ClassNotFoundException {
		ois.defaultReadObject();
		LoanInfo calc = new LoanInfo();
		// Read the object in which sequence you write them.
		calc.setName(ois.readUTF());
		calc.setAmount(ois.readLong());
		calc.setLoanPct(ois.readLong());
		this.setLoanInfo(calc);
	}

	private void writeObject(ObjectOutputStream oos) throws IOException {
		oos.defaultWriteObject();
		// Now write all the transient field's data manually in sequence.
		oos.writeUTF(getLoanInfo().getName());
		oos.writeLong(getLoanInfo().getAmount());
		oos.writeLong(getLoanInfo().getLoanPct());
	}
}

/*
 * Suppose this is third party API class, you do not have rights to modify it
 * and you have to persist this class's information within your class.
 */
class LoanInfo {
	private long amount;
	private long loanPct;
	private String name;

	public long getLoan(long amount) {
		long loanAmount = amount * loanPct;
		return loanAmount;
	}

	public long getAmount() {
		return amount;
	}

	public void setAmount(long amount) {
		this.amount = amount;
	}

	public long getLoanPct() {
		return loanPct;
	}

	public void setLoanPct(long loanPct) {
		this.loanPct = loanPct;
	}

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

}
VN:F [1.9.13_1145]
Rating: 10.0/10 (3 votes cast)
VN:F [1.9.13_1145]
Rating: +2 (from 2 votes)
Inside Implementing & Customizing Serialization in Java, 10.0 out of 10 based on 3 ratings

About the author

Faisal Basra

Faisal Basra is an independent consultant, software developer, writer, blogger, speaker, architect and technology leader in Lahore, Pakistan. He has been a professional software developer since 2008, has been writing code since 2006. Having hands on experience of popular Java EE frameworks & technologies like JSF, Spring, Hibernate, Enverse, JPA, Richfaces, Primefaces, JSP/Servlet. I have taken many initiatives while working with teams. Some of includes Automated Build & Release Management system via Hudson, Maven, Archiva & SVN. Blogging is my hobby and I also initiated blog at corporate level from setting up complete blog for company, content generation strategy and visibility over the Internet by Internet Marketing. Framworks & Technologies: JSF, Richfaces, Primefaces, Openfaces, Struts, Hibernate, Spring, ORMLite Tools & Servers: jUnit, Log4j, Maven, Eclipse, MyEclipse, NetBeans, Tomcat, Jboss, WebLogic Mobile Development: Google Android Marketing: Internet Marketing, Mobile App Marketing

Permanent link to this article: http://www.javaplex.com/blog/inside-implementing-customizing-serialization-in-java/

2 comments

  1. James (http://www NULL.javaplex NULL.com) says:

    Thanks buddy for such a detailed article for serialization process. I have been searching to customize the default serialization process of JVM provided by Sun.

    But, it is very headache process when your non persistent classes are nested and big enough, suppose you marked a class “A” transient due to some reasons, then class “A” have class “B” and “C” and so on, assume up to 15 classes and they all have several properties. Then what we will do in this scenario ???

    Waiting for an expert answer.

    VA:F [1.9.13_1145]
    Rating: 0.0/5 (0 votes cast)
    VA:F [1.9.13_1145]
    Rating: 0 (from 0 votes)
  2. Myron Liebig (http://www NULL.kegitetuliouyter NULL.org) says:

    Hey how are you. I found your blog through Google and I just wanted to say that I think your writing is simply stunning! Thanks again for providing this content for free.

    VA:F [1.9.13_1145]
    Rating: 0.0/5 (0 votes cast)
    VA:F [1.9.13_1145]
    Rating: 0 (from 0 votes)

Leave a Reply

Your email address will not be published.

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>