The problem is that ObjectOutputStream
writes a header to the file. When you open new output streams this header is written several times in the middle of the file.
The classic workaround would be to leave% open% (which may not be desirable). A second alternative would be to open multiple ObjectOutputStream
s according to @mgibsonbr; each of them reads a header (but as he pointed out this may have implications, I get a little uncomfortable not closing resources).
However, in an answer in SOEN the user Andreas_D pointed out a very interesting solution involving overwriting the ObjectInputStream
method with a call to writeStreamHeader()
.
public class AppendingObjectOutputStream extends ObjectOutputStream {
public AppendingObjectOutputStream(OutputStream out) throws IOException {
super(out);
}
@Override
protected void writeStreamHeader() throws IOException {
reset();
}
}
Logic of use (adaptation of original response):
Check whether the file exists or not, then instantiate the appropriate stream :
In case the file exists we are "appending" and do not want a header:
ObjectOutputStream oos = new AppendingObjectOutputStream(fos);
In case the file does not exist we need a header:
ObjectOutputStream oos = new ObjectOutputStream(fos);
You can even encapsulate this logic into a method:
// Esboço; no código real trate exceções
public ObjectOutputStream openStream(File f) throws Exception {
ObjectOutputStream oos = null;
if (f.exists()) {
FileOutputStream fos = new FileOutputStream(f, true);
oos = new AppendingObjectOutputStream(fos);
} else {
FileOutputStream fos = new FileOutputStream(f);
oos = new ObjectOutputStream(fos);
}
return oos;
}
And the use of stream becomes transparent:
File f = new File("files\Produtos.dat");
ObjectOutputStream oos = openStream(f); // Produtos.dat pode existir ou não
oos.writeObject(p);
oos.close();
oos = openStream(f); // Produtos.dat existe, apenda
oos.writeObject(p2);
oos.close();
// Versão Java 7 com try-with-resources
try (ObjectOutputStream oos = openStream(f)) {
oos.writeObject(p3);
}
PS JEP 187 is exactly searching for faults and possible improvements to the Serialization mechanisms of Java. Maybe there is something interesting about this research effort.