Discussion:
Maintaining current serialVersionUID values
(too old to reply)
Gillmer J. Derge [TeamB]
2006-02-28 04:42:54 UTC
Permalink
Do any of you have a good technique that you like for maintaining
serialVersionUID in your classes? I usually tend to be fairly lazy
about it. I typically set it to 0L and forget about it forever, not
really keeping it up to date with changes in the class file. That works
in practice as long as you aren't saving objects in files (ex. if you
use serialization for RMI, EJB's, or something similar), but it's really
not the way it's supposed to work.

What I'd really like is something like an Ant task that would go through
my code looking for classes that implement Serializable. Whenever it
finds one, it should run serialver and update the source code with the
latest serialVersionUID value (which may or may not actually change the
source code, depending on whether the class has changed lately). I've
looked around a little, and I haven't found anything. I could maybe
write a simple shell script to do it, but like I said earlier, I tend to
be lazy about it.

The only alternatives I've come up with are:

a) remember to run update the serialVersionUID manually every time you
change the class. My memory is good but not that good.

b) Put something into your checkin or deployment procedure that reminds
you to manually update every class. That works, but as soon as you have
more than about 3 serializable classes it's kind of ridiculous.
--
Gillmer J. Derge [TeamB]
Paul Furbacher [TeamB]
2006-03-01 13:17:18 UTC
Permalink
Post by Gillmer J. Derge [TeamB]
Do any of you have a good technique that you like for maintaining
serialVersionUID in your classes? I usually tend to be fairly lazy
about it. I typically set it to 0L and forget about it forever, not
really keeping it up to date with changes in the class file. That works
in practice as long as you aren't saving objects in files (ex. if you
use serialization for RMI, EJB's, or something similar), but it's really
not the way it's supposed to work.
The Cayenne list just had a discussion of this. Here
are some references which I gathered from it:

http://www.javapractices.com/Topic45.cjp (this should be taken as a
recommendation, not a rule)
http://www.javaworld.com/javaworld/javaqa/2003-06/02-qa-0627-mythser.html
http://java.sun.com/j2se/1.5.0/docs/api/java/io/Serializable.html
Post by Gillmer J. Derge [TeamB]
What I'd really like is something like an Ant task that would go through
my code looking for classes that implement Serializable. ...
Isn't there an ANT regex task which can iterate over
a fileset replacing found text with new text? I think
I just saw an instance of this being used in which it
was looking for placeholders in config files or something.
Does the id have to be different for each class?
--
Paul Furbacher (TeamB)

Save time, search the archives:
http://info.borland.com/newsgroups/ngsearch.html

Is it in Joi Ellis's Faq-O-Matic?
http://www.visi.com/~gyles19/fom-serve/cache/1.html

Finally, please send responses to the newsgroup only.
That means, do not send email directly to me.
Thank you.
Paul Furbacher [TeamB]
2006-03-01 14:10:26 UTC
Permalink
Post by Paul Furbacher [TeamB]
http://www.javapractices.com/Topic45.cjp (this should be taken as a
recommendation, not a rule)
Just to be clear, the "this should be taken ..." part was
part of the quoted references. Not my comment.
--
Paul Furbacher (TeamB)

Save time, search the archives:
http://info.borland.com/newsgroups/ngsearch.html

Is it in Joi Ellis's Faq-O-Matic?
http://www.visi.com/~gyles19/fom-serve/cache/1.html

Finally, please send responses to the newsgroup only.
That means, do not send email directly to me.
Thank you.
Gillmer J. Derge [TeamB]
2006-03-01 14:50:53 UTC
Permalink
Post by Paul Furbacher [TeamB]
The Cayenne list just had a discussion of this. Here
Thanks. Those are mostly not new information to me, though the link to
Sun's page on compatible vs. incompatible changes was interesting.
Post by Paul Furbacher [TeamB]
Isn't there an ANT regex task which can iterate over
a fileset replacing found text with new text? I think
I just saw an instance of this being used in which it
was looking for placeholders in config files or something.
Hmm. I hadn't spotted that before. That's interesting. The regex to
match is fairly obvious (something like "serialVersionUID *= *[0-9]+L"),
but I'd have to think about how to calculate appropriate replacement text.

While writing a longer reply to your message, I think I just figured out
how to do this. I'll work on it and post back later. Basically it
involves using a doclet to go through your code. You'll only get
warnings about potential problems. You'll need to actually fix them
yourself, but that's fine by me. In fact, it's probably better.
Post by Paul Furbacher [TeamB]
Does the id have to be different for each class?
You would think so, given the UID in the variable name, but it doesn't.
It's just a number. It's really serialVersionNumber.
--
Gillmer J. Derge [TeamB]
Paul Furbacher [TeamB]
2006-03-01 15:30:57 UTC
Permalink
Post by Gillmer J. Derge [TeamB]
Post by Paul Furbacher [TeamB]
The Cayenne list just had a discussion of this. Here
Thanks. Those are mostly not new information to me, though the link to
Sun's page on compatible vs. incompatible changes was interesting.
But don't they suggest that you really don't need to futz
with the value? That is, it's one of those Sun/Java ideas
that seemed useful but really isn't?!
Post by Gillmer J. Derge [TeamB]
Post by Paul Furbacher [TeamB]
Isn't there an ANT regex task [...]
Hmm. I hadn't spotted that before. That's interesting. The regex to
match is fairly obvious (something like "serialVersionUID *= *[0-9]+L"),
but I'd have to think about how to calculate appropriate replacement text.
While writing a longer reply to your message, I think I just figured out
how to do this. ...
Post by Paul Furbacher [TeamB]
Does the id have to be different for each class?
You would think so, given the UID in the variable name, but it doesn't.
It's just a number. It's really serialVersionNumber.
If that's so, why not use a properties file which has just one thing
in it, the new value.

And given that it's not really a UID, just a number, seems to point
to the fact that it's pretty much a waste of time to be managing
it, no?
--
Paul Furbacher (TeamB)

Save time, search the archives:
http://info.borland.com/newsgroups/ngsearch.html

Is it in Joi Ellis's Faq-O-Matic?
http://www.visi.com/~gyles19/fom-serve/cache/1.html

Finally, please send responses to the newsgroup only.
That means, do not send email directly to me.
Thank you.
Gillmer J. Derge [TeamB]
2006-03-01 15:57:47 UTC
Permalink
Post by Paul Furbacher [TeamB]
But don't they suggest that you really don't need to futz
with the value?
That wasn't my take on it. For example, here are some quotes.

"Do not change the value of this field in future versions, unless you
are knowingly making changes to the class which will render it
incompatible with old serialized objects."

"It is strongly recommended that all serializable classes explicitly
declare serialVersionUID values, since the default serialVersionUID
computation is highly sensitive to class details that may vary depending
on compiler implementations."

The second article said not to do it in order to improve performance,
but I wouldn't do it in order to make pigs fly either. The point of
setting the value is to improve portability, not to improve performance.
Post by Paul Furbacher [TeamB]
If that's so, why not use a properties file which has just one thing
in it, the new value.
And given that it's not really a UID, just a number, seems to point
to the fact that it's pretty much a waste of time to be managing
it, no?
Not really. You're supposed to change it whenever there's an
incompatible change to the class. Now, like I said in my original
message, that doesn't really come into play in practice. I mean, unless
you change one end of your RMI without changing the other, they're
always going to be in synch anyway. But my anal retentiveness doesn't
allow me the luxury of ignoring the theoretical problems (remember, this
all originates from turning on all warnings and insisting on warning
free code; I could simply turn off the serialVersionUID warning and be
done with the whole thing).

The properties file is an option I considered when you pointed out the
Ant regex task. The only thing I don't like about that is you wind up
changing the value all the time, not just when you need to.

My doclet might not work anyway. It was really easy to write a simple
version 0.1, but it looks like it might be hard to get at the calculated
serialVersionUID if you've already set one explicitly. Since the whole
point is to issue a warning when the explicitly set value looks like it
might be out of date compared to the default one, that presents a
problem. I might keep fiddling with it though.
--
Gillmer J. Derge [TeamB]
Lori M Olson [TeamB]
2006-03-01 18:21:02 UTC
Permalink
Post by Gillmer J. Derge [TeamB]
Post by Paul Furbacher [TeamB]
But don't they suggest that you really don't need to futz
with the value?
That wasn't my take on it. For example, here are some quotes.
"Do not change the value of this field in future versions, unless you
are knowingly making changes to the class which will render it
incompatible with old serialized objects."
The last time I dealt with this was very long ago, but the idea was if
you ADD to the class, you are good without a change to the
serialVersionUID. Adding methods, adding privates, adding public or
protected members.

BUT if you CHANGE an existing method signature, or CHANGE the type of a
public or protected member, or something along those lines, you get a
breaking change, and you have to update the serialVersionUID.

I don't know how you would automate that. I'm sure that it can be done,
but I'm also sure that I don't want to be the one figuring it out ;-)
--
Regards,

Lori Olson [TeamB]

------------

Save yourself, and everyone else, some time and search the
newsgroups and the FAQ-O-Matic before posting your next
question.

Google Advanced Newsgroup Search
http://www.google.ca/advanced_group_search
Other Newsgroup Searches:
http://www.borland.com/newsgroups/ngsearch.html
Joi Ellis's FAQ-O-Matic:
http://www.visi.com/~gyles19/fom-serve/cache/1.html
Gillmer J. Derge [TeamB]
2006-03-01 19:03:25 UTC
Permalink
Post by Lori M Olson [TeamB]
BUT if you CHANGE an existing method signature, or CHANGE the type of a
public or protected member, or something along those lines, you get a
breaking change, and you have to update the serialVersionUID.
Method signatures shouldn't matter. Methods aren't serialized. One of
the links Paul posted earlier leads to a good list of compatible and
incompatible changes.

http://java.sun.com/j2se/1.5.0/docs/guide/serialization/spec/version.html#6678
Post by Lori M Olson [TeamB]
I don't know how you would automate that. I'm sure that it can be done,
but I'm also sure that I don't want to be the one figuring it out ;-)
My theory is that the calculated default serialVersionUID value will
change whenever there's an incompatible change to the class. It might
change even more than that -- when certain types of compatible changes
are made -- but you should at least be able to avoid false negatives
with that approach. So then if I add a way to say "this calculated
serialVersionUID is also compatible, don't warn me if you calculate this
value", then I think I should have it. Something like this:

/**
* @compatibleSerialVersionUID 12345
*/
private static final long serialVersionUID = 54321L;

Now if it calculates something other than one of those two values,
you'll get a warning that something has changed. If you look at the
class and decide the change is compatible, you update the
compatibleSerialVersionUID tag. Next time around it shouldn't warn you.

Yes, I realize this is *way* overkill and kind of nutty. Kind of a lot
nutty. At this point it's a challenge and an experiment. I may decide
I hate it, but I need to at least try it out before I decide.
--
Gillmer J. Derge [TeamB]
Paul Furbacher [TeamB]
2006-03-01 20:08:10 UTC
Permalink
Post by Gillmer J. Derge [TeamB]
Post by Paul Furbacher [TeamB]
But don't they suggest that you really don't need to futz
with the value?
That wasn't my take on it. For example, here are some quotes.
[...]
The second article said not to do it in order to improve performance,
but I wouldn't do it in order to make pigs fly either. The point of
setting the value is to improve portability, not to improve performance.
I guess I took the following as an important message from the second
article:

"If you don't do anything, the SUID is computed as a hash of
various class elements: class name, implemented interfaces, declared
nonstatic, nontransient fields, declared nonprivate methods, and so
on. But it is also possible to take control of this value by declaring
the following class field: [...]"

That to me means that you get the same thing from the VM as you
do with your own arduous hand-work. Why do the latter and make
mistakes when the VM is quite capable of doing it itself at
pretty much the same speed.

I guess I'm missing important here which is way beyond
my easily befuddled brain. Or is it just the striving
for "no warnings"? If so, is that really possible?
In 10 days or so, Sun is going deprecate something on
you, and soon, you'll be getting no sleep at all ... that
is, if you're getting any now (smileys needed?!).
--
Paul Furbacher (TeamB)

Save time, search the archives:
http://info.borland.com/newsgroups/ngsearch.html

Is it in Joi Ellis's Faq-O-Matic?
http://www.visi.com/~gyles19/fom-serve/cache/1.html

Finally, please send responses to the newsgroup only.
That means, do not send email directly to me.
Thank you.
Gillmer J. Derge [TeamB]
2006-03-01 20:38:23 UTC
Permalink
Post by Paul Furbacher [TeamB]
I guess I'm missing important here which is way beyond
my easily befuddled brain. Or is it just the striving
for "no warnings"?
It's partly just the principle of no warnings, but it's also a good
warning. The issue is that if you let the serialVersionUID be computed
automatically, it's possible that two versions of the same class
produced by different compilers might yield a different
serialVersionUID, despite being essentially the identical class.

I can't remember the details, but if you think back to older versions of
JBuilder (around 4 through 6 or 7), before they switched to javac as the
compiler, there were occasional issues related to this or something like
it. There was some slight difference with the way Borland's compiler
handled certain constructs, and that caused the serialVersionUID to be
different. I think they added or removed an extra static block or
something.

I can't remember why this mattered to people. Were they all using
serialization? I don't think so. But there was a reason. It does
happen. It's an extremely rare thing and not likely to happen, but it's
not impossible.
Post by Paul Furbacher [TeamB]
If so, is that really possible?
In 10 days or so, Sun is going deprecate something on
you, and soon, you'll be getting no sleep at all ... that
is, if you're getting any now (smileys needed?!).
Then I'd fix the code to use the non-deprecated alternative. It's
actually easier to get warning free code with 1.5 than it ever was
before, because you can always take the cheater's way out and add
@SuppressWarnings to a method (possibly including a specific type of
warning as part of the annotation's value).

Of course, there are always exceptions. For example, I currently have 4
unchecked type cast warnings in EventCentral, because I'm using
JBuilder's JDK 1.4 compatibility mode to compile generic code but
without using JDK 1.5 to do it (so I can't use the SuppressWarnings
annotation, since the annotation doesn't exist in JDK 1.4). Still, it's
a nice ideal to strive for, and I hate to sacrifice that ideal for
something that's as easy to fix as the serialVersionUID warning (just
add a static final long).
--
Gillmer J. Derge [TeamB]
Paul Furbacher [TeamB]
2006-03-01 21:33:32 UTC
Permalink
Post by Gillmer J. Derge [TeamB]
Of course, there are always exceptions. For example, I currently have 4
unchecked type cast warnings in EventCentral, because I'm using
JBuilder's JDK 1.4 compatibility mode to compile generic code but
without using JDK 1.5 to do it (so I can't use the SuppressWarnings
annotation, since the annotation doesn't exist in JDK 1.4).
Oh, yeah.

That's going to happen forever if one uses a library which
doesn't use generics. I ran into that problem in the last
project where all I had were the compiled classes for the
data access layer. I chose to use generic types for lists,
etc., and there was no way to avoid those warnings.
--
Paul Furbacher (TeamB)

Save time, search the archives:
http://info.borland.com/newsgroups/ngsearch.html

Is it in Joi Ellis's Faq-O-Matic?
http://www.visi.com/~gyles19/fom-serve/cache/1.html

Finally, please send responses to the newsgroup only.
That means, do not send email directly to me.
Thank you.
Gillmer J. Derge [TeamB]
2006-03-01 17:45:12 UTC
Permalink
Post by Paul Furbacher [TeamB]
And given that it's not really a UID, just a number, seems to point
to the fact that it's pretty much a waste of time to be managing
it, no?
I think I can explain it better after thinking about it some more.

a) Yes, it's probably mostly a waste of time.

b) I think we can agree that hypothetically if there was some magic way
of maintaining the serialVersionUID perfectly without any effort, that
would be better than not maintaining it. In other words, the only
reason not to maintain it is that it's a pain in the neck, not because
it's useless or bad.

So that's what I'm trying to find. Some way of dealing with it that
doesn't require a whole lot of manual effort. It's not hugely
important, but it would make me feel better to know that I'm doing it
"right."
--
Gillmer J. Derge [TeamB]
Paul Furbacher [TeamB]
2006-03-04 20:37:19 UTC
Permalink
Post by Gillmer J. Derge [TeamB]
Do any of you have a good technique that you like for maintaining
serialVersionUID in your classes? [....]
[...]
I just stumbled across the java.net OpenTools project
and noticed that there is a "Serialver" OT which may
do what you want but requires you to hand-pick classes
from the source tree.

http://cc.borland.com/Item.aspx?id=18252

What about an OpenTool which uses (I'm guessing here)
the refactoring API to search the project for instances
of "implements Serializable", presents you with a list
of those it found, each list item with checkbox (default is
selected) signifying "generate new serial version id.
Press OK and you are done.
--
Paul Furbacher (TeamB)

Save time, search the archives:
http://info.borland.com/newsgroups/ngsearch.html

Is it in Joi Ellis's Faq-O-Matic?
http://www.visi.com/~gyles19/fom-serve/cache/1.html

Finally, please send responses to the newsgroup only.
That means, do not send email directly to me.
Thank you.
Gillmer J. Derge [TeamB]
2006-03-05 01:18:23 UTC
Permalink
Post by Paul Furbacher [TeamB]
What about an OpenTool which uses (I'm guessing here)
the refactoring API to search the project for instances
of "implements Serializable", presents you with a list
of those it found, each list item with checkbox (default is
selected) signifying "generate new serial version id.
Press OK and you are done.
Thanks. I'll have to take a look at this. My first impression is that
comparing this to my current doclet would reveal the following
advantages and disadvantages.

* my doclet can automatically find all the classes needing an update /
with this tool it's a manual process

* once you find the potential problems, my doclet requires a manual
update (copy/paste the suggested serialVersionUID from the message pane
into the source code) / this tool does it automatically

I might be able to combine the two so you have a nice right click quick
fix menu item when you select one of the warnings printed by my doclet.
I'm not sure how much more work I want to put into this though. The
doclet might be good enough. Copying/pasting an integer once or twice a
week shouldn't really wear me out. :-)
--
Gillmer J. Derge [TeamB]
Loading...