Skip to content

Commit c28e251

Browse files
committed
Fix ControlBusTests for DefaultHeaderChannelReg
We cannot use a `DFA` to set value to the `record` property: it is marked as `trustedFinal` and cannot be modified via reflection. Therefore, rework `ControlBusTests` to do other logic than reflection. The reflection in the unit test is not a justification to stay away from the `record` structure
1 parent 8e7a0a0 commit c28e251

File tree

3 files changed

+25
-33
lines changed

3 files changed

+25
-33
lines changed

spring-integration-core/src/main/java/org/springframework/integration/channel/DefaultHeaderChannelRegistry.java

Lines changed: 7 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -186,11 +186,12 @@ public MessageChannel channelNameToChannel(@Nullable String name) {
186186
else {
187187
messageChannelWrapper = this.channels.get(name);
188188
}
189+
189190
if (messageChannelWrapper != null) {
190-
logger.debug(() -> "Retrieved " + messageChannelWrapper.getChannel() + " with " + name);
191+
MessageChannel channel = messageChannelWrapper.channel();
192+
logger.debug(() -> "Retrieved " + channel + " with " + name);
193+
return channel;
191194
}
192-
193-
return messageChannelWrapper == null ? null : messageChannelWrapper.getChannel();
194195
}
195196
return null;
196197
}
@@ -215,8 +216,8 @@ public synchronized void run() {
215216
long now = System.currentTimeMillis();
216217
while (iterator.hasNext()) {
217218
Entry<String, MessageChannelWrapper> entry = iterator.next();
218-
if (entry.getValue().getExpireAt() < now) {
219-
logger.debug(() -> "Expiring " + entry.getKey() + " (" + entry.getValue().getChannel() + ")");
219+
if (entry.getValue().expireAt() < now) {
220+
logger.debug(() -> "Expiring " + entry.getKey() + " (" + entry.getValue().channel() + ")");
220221
iterator.remove();
221222
}
222223
}
@@ -228,15 +229,7 @@ public synchronized void run() {
228229
}
229230

230231

231-
protected record MessageChannelWrapper(MessageChannel channel, long expireAt) {
232-
233-
public long getExpireAt() {
234-
return this.expireAt;
235-
}
236-
237-
public MessageChannel getChannel() {
238-
return this.channel;
239-
}
232+
protected static final record MessageChannelWrapper(MessageChannel channel, long expireAt) {
240233

241234
}
242235

spring-integration-core/src/test/java/org/springframework/integration/config/xml/ControlBusTests-context.xml

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,16 @@
11
<?xml version="1.0" encoding="UTF-8"?>
22
<beans:beans xmlns="http://www.springframework.org/schema/integration" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
3-
xmlns:beans="http://www.springframework.org/schema/beans" xmlns:groovy="http://www.springframework.org/schema/integration/groovy"
3+
xmlns:beans="http://www.springframework.org/schema/beans"
44
xsi:schemaLocation="http://www.springframework.org/schema/integration
55
https://www.springframework.org/schema/integration/spring-integration.xsd
66
http://www.springframework.org/schema/beans
77
https://www.springframework.org/schema/beans/spring-beans.xsd">
88

9+
<beans:bean id="integrationHeaderChannelRegistry"
10+
class="org.springframework.integration.channel.DefaultHeaderChannelRegistry">
11+
<beans:constructor-arg value="1000"/>
12+
</beans:bean>
13+
914
<channel id="output">
1015
<queue/>
1116
</channel>

spring-integration-core/src/test/java/org/springframework/integration/config/xml/ControlBusTests.java

Lines changed: 12 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2002-2019 the original author or authors.
2+
* Copyright 2002-2022 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -23,26 +23,22 @@
2323
import java.util.concurrent.CountDownLatch;
2424
import java.util.concurrent.TimeUnit;
2525

26-
import org.junit.Test;
27-
import org.junit.runner.RunWith;
26+
import org.junit.jupiter.api.Test;
2827

29-
import org.springframework.beans.DirectFieldAccessor;
3028
import org.springframework.beans.factory.annotation.Autowired;
3129
import org.springframework.context.ConfigurableApplicationContext;
3230
import org.springframework.context.support.ClassPathXmlApplicationContext;
3331
import org.springframework.integration.channel.DefaultHeaderChannelRegistry;
3432
import org.springframework.integration.channel.DirectChannel;
3533
import org.springframework.integration.core.MessagingTemplate;
3634
import org.springframework.integration.support.MessageBuilder;
37-
import org.springframework.integration.test.util.TestUtils;
3835
import org.springframework.jmx.export.annotation.ManagedOperation;
3936
import org.springframework.messaging.Message;
4037
import org.springframework.messaging.MessageChannel;
4138
import org.springframework.messaging.PollableChannel;
4239
import org.springframework.messaging.support.GenericMessage;
4340
import org.springframework.test.annotation.DirtiesContext;
44-
import org.springframework.test.context.ContextConfiguration;
45-
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
41+
import org.springframework.test.context.junit.jupiter.SpringJUnitConfig;
4642

4743
/**
4844
* @author Dave Syer
@@ -52,8 +48,7 @@
5248
*
5349
* @since 2.0
5450
*/
55-
@ContextConfiguration
56-
@RunWith(SpringJUnit4ClassRunner.class)
51+
@SpringJUnitConfig
5752
@DirtiesContext
5853
public class ControlBusTests {
5954

@@ -71,7 +66,10 @@ public class ControlBusTests {
7166

7267
@Test
7368
public void testDefaultEvaluationContext() {
74-
Message<?> message = MessageBuilder.withPayload("@service.convert('aardvark')+headers.foo").setHeader("foo", "bar").build();
69+
Message<?> message =
70+
MessageBuilder.withPayload("@service.convert('aardvark')+headers.foo")
71+
.setHeader("foo", "bar")
72+
.build();
7573
this.input.send(message);
7674
assertThat(output.receive(0).getPayload()).isEqualTo("catbar");
7775
assertThat(output.receive(0)).isNull();
@@ -106,17 +104,12 @@ public void testControlHeaderChannelReaper() throws InterruptedException {
106104
// No channels in the registry
107105
assertThat(result.getPayload()).isEqualTo(0);
108106
this.registry.channelToChannelName(new DirectChannel());
109-
// Sleep a bit to be sure that we aren't reaped by registry TTL as 60000
110-
Thread.sleep(10);
111107
messagingTemplate.convertAndSend(input, "@integrationHeaderChannelRegistry.size()");
112108
result = this.output.receive(0);
113109
assertThat(result).isNotNull();
114110
assertThat(result.getPayload()).isEqualTo(1);
115-
// Some DirectFieldAccessor magic to modify 'expireAt' to the past to avoid timing issues on high-loaded build
116-
Object messageChannelWrapper =
117-
TestUtils.getPropertyValue(this.registry, "channels", Map.class).values().iterator().next();
118-
DirectFieldAccessor dfa = new DirectFieldAccessor(messageChannelWrapper);
119-
dfa.setPropertyValue("expireAt", System.currentTimeMillis() - 60000);
111+
// Let the registry to reap old channels
112+
Thread.sleep(1000);
120113
messagingTemplate.convertAndSend(input, "@integrationHeaderChannelRegistry.runReaper()");
121114
messagingTemplate.convertAndSend(input, "@integrationHeaderChannelRegistry.size()");
122115
result = this.output.receive(0);
@@ -161,8 +154,9 @@ public void voidOp(String input) {
161154
}
162155

163156
public static class AdapterService {
157+
164158
public Message<String> receive() {
165-
return new GenericMessage<String>(new Date().toString());
159+
return new GenericMessage<>(new Date().toString());
166160
}
167161

168162
}

0 commit comments

Comments
 (0)