When using the @EventListener functionality with Spring Data's repositories the behavior is different than when calling the same code procedural.

My persistent objects publish events using the following base class:

  public abstract class Aggregate  {

      private transient final Set<Object> events = new LinkedHashSet<>();

      protected <T> T registerEvent(T event) {
          return event;

      Collection<Object> events() {
          return Collections.unmodifiableSet(events);

      void clearEvents() {

My event listening class is implemented as follows:

  class Service {

      public void listener(SomeEvent event) {

When the listener is triggered and someOtherRepository's save(…) method fails a rollback will be issued. But someOtherCode() is executed regardless of the rollback.

But when I remove all @EventListening functionality and call the listener(…) method directly after the point where the originating repository is responsible for firing the event. Then I get a different behavior. Then someOtherCode() is never executed and the someOtherRepository.save(…) method fails immediately.

The original service responsible for publishing the event looks like this

public OriginatingService {
    public void someMethod() {

Why is this happening and is there a way to force the same behavior onto my event listening implementation?

1 Answers

Alan Hay On Best Solutions

Because writes to the database may be delayed until transaction commit i.e. when the transactional method returns.

Update as below to explicitly trigger an immediate flush:

  public void listener(SomeEvent event) {