Ich experimentiere gerade mit einenm EJB Singleton Cache; dieser hält Objekte inkl. Metadaten.
Der EJB Singleton Cache bietet Methoden zum Abfragen und Updaten (MyObjectUpdateEvent) der Objekte.
Änderungen bzgl. der Metadaten werden mittels MetaDataUpdateEvent mittgeteilt.
Der Event MyObjectUpdateEvent wird von einer weiteren Bean MyObjectProducerController gefeuert.
Die Bean MyObjectConsumerController benötigt die Info des Caches - er hält lokal einen MyObject-Store zur eigenen Weiterverarbeitung.
Dazu werden in der PostConstruct-Methode alle MyObject-Objekte mittels getMyObjectList geholt.
Zusätzlich wird der MetaDataUpdateEvent ausgewertet, um den lokalen MyObject-Store synchron zu halten:
Wird der MetaDataUpdateEvent SYNCHRON ausgewertet, kann es beim StartUp zu einem Deadlock kommen.
Wird der MetaDataUpdateEvent ASYNCHRON (@Asynchronous) ausgewertet, funktioniert das Design,
jedoch besteht hier das Problem, dass das Ordering der MetaDataUpdateEvent-Aufrufe verlorengeht und somit die MetaDaten veraltet sein können:
Timestamp = 1, ThreadId = 1111 : MyObjectController.fire(MyObjectUpdateEvent with objType=x id=1)
Timestamp = 2, ThreadId = 1111 : MyObjectController.fire(MyObjectUpdateEvent with objType=y id=2)
Timestamp = 3, ThreadId = 1111 : MyObjectController.fire(MyObjectUpdateEvent with objType=y id=3)
Timestamp = 4, ThreadId = 2222 : MyObjectConsumerController.onMetaDataUpdate(MyObjectUpdateEvent objType=y id=3)
Timestamp = 5, ThreadId = 3333 : MyObjectConsumerController.onMetaDataUpdate(MyObjectUpdateEvent objType=x id=1)
Timestamp = 6, ThreadId = 4444 : MyObjectConsumerController.onMetaDataUpdate(MyObjectUpdateEvent objType=y id=2)
Umgehen könnte man das Problem, dass man einen eventTimestamp/sequenceNumber per objectType einführt und somit ältere Events droppen kann.
Lässt sich das Original Ordering der MetaDataUpdateEvent-Aufrufe irgendwie beibehalten, auch wenn die Observer-Methode asynchron arbeitet (zb. FIFO Queue der Threads) ?
Der EJB Singleton Cache bietet Methoden zum Abfragen und Updaten (MyObjectUpdateEvent) der Objekte.
Änderungen bzgl. der Metadaten werden mittels MetaDataUpdateEvent mittgeteilt.
Java:
public interface MyObjectController {
List<MyObject> getMyObjectList(String myObjectType);
void onMyObjectUpdate(@Observes MyObjectUpdateEvent e);
}
Der Event MyObjectUpdateEvent wird von einer weiteren Bean MyObjectProducerController gefeuert.
Die Bean MyObjectConsumerController benötigt die Info des Caches - er hält lokal einen MyObject-Store zur eigenen Weiterverarbeitung.
Dazu werden in der PostConstruct-Methode alle MyObject-Objekte mittels getMyObjectList geholt.
Zusätzlich wird der MetaDataUpdateEvent ausgewertet, um den lokalen MyObject-Store synchron zu halten:
Java:
public void onMetaDataUpdate(@Observes MetaDataUpdateEvent e);
Wird der MetaDataUpdateEvent SYNCHRON ausgewertet, kann es beim StartUp zu einem Deadlock kommen.
Wird der MetaDataUpdateEvent ASYNCHRON (@Asynchronous) ausgewertet, funktioniert das Design,
jedoch besteht hier das Problem, dass das Ordering der MetaDataUpdateEvent-Aufrufe verlorengeht und somit die MetaDaten veraltet sein können:
Timestamp = 1, ThreadId = 1111 : MyObjectController.fire(MyObjectUpdateEvent with objType=x id=1)
Timestamp = 2, ThreadId = 1111 : MyObjectController.fire(MyObjectUpdateEvent with objType=y id=2)
Timestamp = 3, ThreadId = 1111 : MyObjectController.fire(MyObjectUpdateEvent with objType=y id=3)
Timestamp = 4, ThreadId = 2222 : MyObjectConsumerController.onMetaDataUpdate(MyObjectUpdateEvent objType=y id=3)
Timestamp = 5, ThreadId = 3333 : MyObjectConsumerController.onMetaDataUpdate(MyObjectUpdateEvent objType=x id=1)
Timestamp = 6, ThreadId = 4444 : MyObjectConsumerController.onMetaDataUpdate(MyObjectUpdateEvent objType=y id=2)
Umgehen könnte man das Problem, dass man einen eventTimestamp/sequenceNumber per objectType einführt und somit ältere Events droppen kann.
Lässt sich das Original Ordering der MetaDataUpdateEvent-Aufrufe irgendwie beibehalten, auch wenn die Observer-Methode asynchron arbeitet (zb. FIFO Queue der Threads) ?
Zuletzt bearbeitet: