views:

722

answers:

5

I have a serializiable object with listeners registered. Currently the list of listeners is stored in the object as transient. When the object is serialized and then deserialized, obviously the listeners are no longer registered.

What would be the safest and best way to go about re-registering the listeners automatically once the object is deserialized? Is there a good design pattern that would help here?

+1  A: 

You could use a proxy object which acts as both a listener and a broadcaster of events and assign the real listeners to it, and then assign it as a listener of the to-be-serialized object. When you serialize it and then de-serialize it, just reassign it as a listener of the de-serialized object.

John
A: 

I would build a decoupled event framework, meaning that the event producer would be not bound directly to the event consumer. This could consist of a EventManager, an EventProducer and an EventListener working together with publish/subscribe semantics.

  1. When the system starts up (or on the first use) a EventManager is created.
  2. The EventListener registers itself to receive a specific kind of events.
  3. The EventProducer is producing events an publishes them to the EventManager
    public interface EventManager {
        public void postEvent(Event event);
        public void addListener(Class eventType, EventListener listener);
    }

    public interface EventListener {
        public void handleEvent(Event event);
    }

In this way when you serialize the producer then the EventManager still maintains the list of the subscribed listeners. when the object is deserialized then it can still post events to the EventManager.

Panagiotis Korros
A: 

In general I did not recognize any useful pattern for this. But the combination of several will be OK :). The question is how you handle deserialization? If using standard way you can introduce lookup mechanism which will be used to locate local listeners and re-bound them to the freshly deserialized instance. If you have own deserializer, the way will be more simple. Just deserialize object and register local listeners. The deserializer can act as proxy listener if possible. Introducing some decoupled model should be also helpful as Panagiotis said. The exact solution depends of your real need but don't forget to KISS it.

Rastislav Komara
A: 

Use a registry that both your publisher and subscribers register with. As was posted by Korros, it is referred to as a Whiteboard Pattern in OSGI land.

Robin
+1  A: 

If you implement readObject(), you can reconstruct transient state as part of deserialization. You should treat deserialization as object construction (because it is).

   private void readObject(ObjectInputStream in) 
       throws ClassNotFoundException, IOException {
     // do normal serialization first!
     in.defaultReadObject();

     // put code here that can somehow reconstruct your listeners
     // presumably you have someplace you can look them up
  }
Alex Miller