The problem
I would like to make the event outbox completely independent of my classes, so that I can always safely rename and move classes between packages without having to create migrations for the event_publication table.
Currently, two columns within that table are dependent on class information:
listener_id is easily solvable by always declaring a custom id in @TransactionalEventListener.
Unfortunately, event_type is hardcoded as Class<T> in EventSerializer, JpaEventPublicationRepository and JpaEventPublication itself.
I could probably work around EventSerializer and JpaEventPublicationRepository via some casting shenanigans. However, Hibernate will throw an exception when it tries to retrieve a JpaEventPublication with an eventType class that is not on the class path, so there currently seems to be no path to a solution.
Use case example
I created the following annotation in my project, which I'm using along with a custom EventSerializer:
@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface OutboxEventMapper {
String id();
Class<?> domain();
Class<?> outbox();
}
It allows me to very simply declare mappers between my internal domain events and their outbox DTOs, e.g.,:
@OutboxEventMapper(
id = "FileBackupFinishedEvent",
domain = FileBackupFinishedEvent.class,
outbox = FileBackupFinishedOutboxEvent.class
)
@Mapper(unmappedSourcePolicy = ReportingPolicy.IGNORE)
public interface FileBackupFinishedOutboxEventMapper {
FileBackupFinishedOutboxEvent toOutbox(FileBackupFinishedEvent domain);
FileBackupFinishedEvent toDomain(FileBackupFinishedOutboxEvent outbox);
}
I would like to be able to use the id property to identify which domain event class to deserialize an outbox event into.
Suggested solution
I think the best solution would be to abstract away the eventType as a string and allow clients to provide their own resolvers for it.
The problem
I would like to make the event outbox completely independent of my classes, so that I can always safely rename and move classes between packages without having to create migrations for the
event_publicationtable.Currently, two columns within that table are dependent on class information:
listener_id,event_type.listener_idis easily solvable by always declaring a custom id in@TransactionalEventListener.Unfortunately,
event_typeis hardcoded asClass<T>inEventSerializer,JpaEventPublicationRepositoryandJpaEventPublicationitself.I could probably work around
EventSerializerandJpaEventPublicationRepositoryvia some casting shenanigans. However, Hibernate will throw an exception when it tries to retrieve aJpaEventPublicationwith aneventTypeclass that is not on the class path, so there currently seems to be no path to a solution.Use case example
I created the following annotation in my project, which I'm using along with a custom
EventSerializer:It allows me to very simply declare mappers between my internal domain events and their outbox DTOs, e.g.,:
I would like to be able to use the
idproperty to identify which domain event class to deserialize an outbox event into.Suggested solution
I think the best solution would be to abstract away the
eventTypeas a string and allow clients to provide their own resolvers for it.