-------- Forwarded Message --------
From: simon <[EMAIL PROTECTED]>
To: MyFaces Development <[email protected]>
Subject: Re: [orchestra] minor issues
Date: Sat, 11 Aug 2007 14:46:08 +0200
On Sat, 2007-08-11 at 13:50 +0200, Mario Ivankovits wrote:
> Hi!
> >> AFAIK there is no way in readObject to get the serialVersionUID of the
> >> stored object, is there a way?
> >>
> >
> > I'm not sure. Why would you want to?
> >
> >
> >> I'd generate the serialVersionUID with any number and use a second local
> >> version which will be written first to the the stream.
> >> That way, we can react in readObject appropriate.
> >> A little bit more complex, but robust about changes.
> >>
> >
> > Sorry, I don't understand.
> >
> > You're thinking perhaps that the readObject method could detect the
> > version of data being read in, and set certain fields to default values
> > if the object format is old, else read them from the stream?
> Exactly. This is what I do often.
>
> > I guess
> > that is possible but I don't see why Orchestra would need to get that
> > tricky...
> >
> On the other hand, I do not understand what the serialVersionUID is
> worth implementing it when we do not gain anything additional other than
> make our IDE shut-up.
I don't know why PhaseListener is declared Serializable in JSF 1.1 spec,
but it is so presumably it does get written to disk or passed across the
network in some situations. If this never happens then the spec wouldn't
declare it Serializable.
In this case, when it is loaded back into memory it would be nice to
avoid throwing an exception if some trivial change has been made to
ConversationPhaseListener or ViewControllerPhaseListener that doesn't
actually affect the storage medium. Adding a serialVersionUID fixes
that.
So unless you object I'd like to add serialVersionUID to these
phaselistener classes as I think it's the right thing to do.
I'm confused about serializable class RequestParameterProviderManager;
I'll post a separate email about that.
> > There is one apparently tricky case, the ConversationManager. For the
> > other classes, is it ok to add serialVersionUID?
> >
> > For ConversationManager, I see that custom serialization (readObject et
> > al) has currently been implemented, with the comment
> > //we just implement it to make it work with distributed sessions
> > Does this code actually work with distributed sessions? It looks to me
> > like any access to this class on a machine other than the one it was
> > created on will cause exceptions due to things like
> > conversationContexts and conversationManager being null..
> >
> You are right, it does NOT work with distributed sessions, but it is
> required to avoid this nasty exception if you put a not-serializable
> bean into the session scope.
> As of now, using Orchestra requires you to use sticky sessions (a
> session bound to a specific tomcat instance).
> The problem is, that I do not know yet if it is possible to serialize
> all the database session state of the used ORM mapper.
> I thought about to solve this once we have to cross this bridge.
>
> For now, it is assured that, if the http session has to switch to
> another node (e.g. due to server failure) the user just has to start
> over the current conversation.
I'm not an expert on serialization, and haven't done any serialization
tests with orchestra, so all the below is just my interpretation from
reading the code..
As I understand the code, on access to another node it won't just "start
over", it will crash with NullPointerException. The http session will
replicate correctly, so there will be a (CONVERSATION_MANAGER_KEY,
conversationManagerInstance) pair in the session data. However when that
conversationManagerInstance object is deserialized the readObject method
does nothing, so the created object ends up with nulls for all members
which is not healthy. When user code retrieves the object via
getInstance and calls any method, oops..
I think what is wanted here is some way to tell http session that a
particular (key, value) pair in the session map is transient..which
means that the ConversationManager then doesn't need to be Serializable
at all. Unfortunately I know of no such feature.
Alternately, maybe readResolve() could be implemented to return null?
Then the pair (CONVERSATION_MANAGER_KEY, null) would be in the restored
http session which would force a new ConversationManager...
Or perhaps the session could instead hold a simple "handle" object:
public class TransientHandle implements Serializable {
transient Object o;
}
rather than putting ConversationManager directly into the session..
Regards,
Simon