Skip to content

Commit 417fad3

Browse files
sis-yoshidayodrotbohm
authored andcommitted
DATACMNS-1067 - Fix not to call @AfterDomainEventPublication method from collection of entities.
We now make sure the event cleanup method is called on the aggregate root, not on the parameter object directly (as the latter might be a collection. Original pull request: #216.
1 parent 2eb830d commit 417fad3

File tree

2 files changed

+51
-4
lines changed

2 files changed

+51
-4
lines changed

src/main/java/org/springframework/data/repository/core/support/EventPublishingRepositoryProxyPostProcessor.java

+6-4
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,7 @@
4444
*
4545
* @author Oliver Gierke
4646
* @author Christoph Strobl
47+
* @author Yuki Yoshida
4748
* @since 1.13
4849
* @soundtrack Henrik Freischlader Trio - Master Plan (Openness)
4950
*/
@@ -164,13 +165,14 @@ public void publishEventsFrom(Object object, ApplicationEventPublisher publisher
164165
}
165166

166167
for (Object aggregateRoot : asCollection(object)) {
167-
for (Object event : asCollection(ReflectionUtils.invokeMethod(publishingMethod, aggregateRoot))) {
168+
Collection<Object> events = asCollection(ReflectionUtils.invokeMethod(publishingMethod, aggregateRoot));
169+
for (Object event : events) {
168170
publisher.publishEvent(event);
169171
}
170-
}
171172

172-
if (clearingMethod != null) {
173-
ReflectionUtils.invokeMethod(clearingMethod, object);
173+
if (clearingMethod != null && !events.isEmpty()) {
174+
ReflectionUtils.invokeMethod(clearingMethod, aggregateRoot);
175+
}
174176
}
175177
}
176178

src/test/java/org/springframework/data/repository/core/support/EventPublishingRepositoryProxyPostProcessorUnitTests.java

+45
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@
2020
import static org.mockito.Mockito.*;
2121

2222
import lombok.Getter;
23+
import lombok.RequiredArgsConstructor;
2324
import lombok.Value;
2425

2526
import java.lang.reflect.Method;
@@ -36,6 +37,7 @@
3637
import org.mockito.junit.MockitoJUnitRunner;
3738
import org.springframework.aop.framework.ProxyFactory;
3839
import org.springframework.context.ApplicationEventPublisher;
40+
import org.springframework.data.domain.AfterDomainEventPublication;
3941
import org.springframework.data.domain.DomainEvents;
4042
import org.springframework.data.repository.CrudRepository;
4143
import org.springframework.data.repository.core.RepositoryInformation;
@@ -47,6 +49,7 @@
4749
*
4850
* @author Oliver Gierke
4951
* @author Mark Paluch
52+
* @author Yuki Yoshida
5053
* @soundtrack Henrik Freischlader Trio - Nobody Else To Blame (Openness)
5154
*/
5255
@RunWith(MockitoJUnitRunner.class)
@@ -99,6 +102,40 @@ public void doesNotExposeNullEvent() {
99102
verify(publisher, times(0)).publishEvent(any());
100103
}
101104

105+
@Test // DATACMNS-1067
106+
public void clearEventsDoesNotExposedByEntity() {
107+
108+
EventsWithClearing entity = spy(EventsWithClearing.of(Collections.emptyList()));
109+
110+
EventPublishingMethod.of(EventsWithClearing.class).publishEventsFrom(entity, publisher);
111+
112+
verify(entity, times(0)).clearDomainEvents();
113+
}
114+
115+
@Test // DATACMNS-1067
116+
public void clearEventsExposedByEntity() {
117+
118+
EventsWithClearing entity = spy(EventsWithClearing.of(Collections.singletonList(new SomeEvent())));
119+
120+
EventPublishingMethod.of(EventsWithClearing.class).publishEventsFrom(entity, publisher);
121+
122+
verify(entity, times(1)).clearDomainEvents();
123+
}
124+
125+
@Test // DATACMNS-1067
126+
public void clearEventsExposedByEntities() {
127+
128+
EventsWithClearing firstEntity = spy(EventsWithClearing.of(Collections.emptyList()));
129+
EventsWithClearing secondEntity = spy(EventsWithClearing.of(Collections.singletonList(new SomeEvent())));
130+
131+
Collection<EventsWithClearing> entities = Arrays.asList(firstEntity, secondEntity);
132+
133+
EventPublishingMethod.of(EventsWithClearing.class).publishEventsFrom(entities, publisher);
134+
135+
verify(firstEntity, times(0)).clearDomainEvents();
136+
verify(secondEntity, times(1)).clearDomainEvents();
137+
}
138+
102139
@Test // DATACMNS-928
103140
public void doesNotCreatePublishingMethodIfNoAnnotationDetected() {
104141
assertThat(EventPublishingMethod.of(Object.class)).isNull();
@@ -210,6 +247,14 @@ static class MultipleEvents {
210247
@Getter(onMethod = @__(@DomainEvents)) Collection<? extends Object> events;
211248
}
212249

250+
@RequiredArgsConstructor(staticName = "of")
251+
static class EventsWithClearing {
252+
@Getter(onMethod = @__(@DomainEvents)) final Collection<? extends Object> events;
253+
254+
@AfterDomainEventPublication
255+
void clearDomainEvents() {}
256+
}
257+
213258
@Value(staticConstructor = "of")
214259
static class OneEvent {
215260
@Getter(onMethod = @__(@DomainEvents)) Object event;

0 commit comments

Comments
 (0)