Skip to content

Commit 620d578

Browse files
committed
spring-projectsGH-3869: Apply review comments.
1 parent a9a7484 commit 620d578

File tree

3 files changed

+134
-55
lines changed

3 files changed

+134
-55
lines changed

spring-integration-file/src/main/java/org/springframework/integration/file/remote/session/ContextHolderRequestHandlerAdvice.java

Lines changed: 33 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -19,15 +19,16 @@
1919
import java.util.function.Consumer;
2020
import java.util.function.Function;
2121

22+
import org.springframework.integration.handler.advice.AbstractRequestHandlerAdvice;
2223
import org.springframework.messaging.Message;
2324

2425
/**
2526
* Provides a key for the context holder.This key could for example be stored in a message header.
2627
*
2728
* @author Adel Haidar
28-
* @since 6.0
29+
* @since 6.1
2930
*/
30-
public class ContextHolderRequestHandlerAdvice {
31+
public class ContextHolderRequestHandlerAdvice extends AbstractRequestHandlerAdvice {
3132
public Function<Message<?>, Object> keyProvider;
3233

3334
public Consumer<Object> contextSetHook;
@@ -83,4 +84,34 @@ public Consumer<Object> getContextClearHook() {
8384
public void setContextClearHook(Consumer<Object> contextClearHook) {
8485
this.contextClearHook = contextClearHook;
8586
}
87+
88+
@Override
89+
protected Object doInvoke(ExecutionCallback callback, Object target, Message<?> message) {
90+
final var result = callback.execute();
91+
applyKeyProvider(message);
92+
return result;
93+
}
94+
95+
private void applyKeyProvider(Message<?> message) {
96+
if (this.keyProvider != null) {
97+
final Object key = this.keyProvider.apply(message);
98+
if (key != null) {
99+
setContext(key);
100+
clearContext(key);
101+
}
102+
}
103+
}
104+
105+
private void setContext(Object key) {
106+
if (this.contextSetHook != null) {
107+
this.contextSetHook.accept(key);
108+
}
109+
}
110+
111+
private void clearContext(Object key) {
112+
if (this.contextClearHook != null) {
113+
this.contextClearHook.accept(key);
114+
}
115+
}
116+
86117
}

spring-integration-file/src/test/java/org/springframework/integration/file/remote/session/ContextHolderRequestHandlerAdviceTests.java

Lines changed: 81 additions & 53 deletions
Original file line numberDiff line numberDiff line change
@@ -16,76 +16,104 @@
1616

1717
package org.springframework.integration.file.remote.session;
1818

19+
import java.io.IOException;
1920
import java.util.HashMap;
2021
import java.util.Map;
2122

22-
import org.junit.jupiter.api.BeforeEach;
2323
import org.junit.jupiter.api.Test;
2424

25-
import org.springframework.integration.support.MessageBuilder;
26-
27-
import static org.assertj.core.api.Assertions.assertThat;
25+
import org.springframework.beans.factory.annotation.Autowired;
26+
import org.springframework.context.annotation.Bean;
27+
import org.springframework.context.annotation.Configuration;
28+
import org.springframework.context.annotation.ImportResource;
29+
import org.springframework.integration.config.EnableIntegration;
30+
import org.springframework.messaging.MessageChannel;
31+
import org.springframework.messaging.PollableChannel;
32+
import org.springframework.messaging.support.GenericMessage;
33+
import org.springframework.test.context.junit.jupiter.SpringJUnitConfig;
34+
35+
import static org.mockito.ArgumentMatchers.anyString;
36+
import static org.mockito.BDDMockito.given;
2837
import static org.mockito.Mockito.mock;
38+
import static org.mockito.Mockito.verify;
2939

40+
/**
41+
* @author Adel Haidar
42+
*
43+
* @since 6.1
44+
*
45+
*/
46+
@SpringJUnitConfig
3047
public class ContextHolderRequestHandlerAdviceTests {
3148

32-
private ContextHolderRequestHandlerAdvice advice;
49+
@Autowired
50+
TestSessionFactory foo;
3351

34-
@BeforeEach
35-
public void setUp() {
36-
advice = new ContextHolderRequestHandlerAdvice();
37-
}
52+
@Autowired
53+
TestSessionFactory bar;
3854

39-
@Test
40-
public void shouldSetKeyProvider() {
41-
// given
42-
advice.setKeyProvider(message -> message.getHeaders().get("test-key"));
43-
final var message = MessageBuilder.withPayload("test-payload").setHeader("test-key", new TestSessionFactory()).build();
55+
@Autowired
56+
ContextHolderRequestHandlerAdvice advice;
4457

45-
// when
46-
final var sessionFactory = advice.getKeyProvider().apply(message);
58+
@Autowired
59+
MessageChannel in;
4760

48-
// then
49-
assertThat(sessionFactory).isNotNull();
50-
assertThat(sessionFactory).isInstanceOf(TestSessionFactory.class);
51-
}
61+
@Autowired
62+
PollableChannel out;
63+
64+
@Autowired
65+
DefaultSessionFactoryLocator<String> sessionFactoryLocator;
5266

5367
@Test
54-
void shouldSetContextSetHook() {
55-
// given
56-
final Map<Object, SessionFactory<String>> factories = new HashMap<>();
57-
final var testSessionFactory = new TestSessionFactory();
58-
factories.put("test-key", testSessionFactory);
59-
final var defaultFactory = new TestSessionFactory();
60-
factories.put("default", defaultFactory);
61-
62-
final DelegatingSessionFactory<String> delegatingSessionFactory = new DelegatingSessionFactory<>(factories, testSessionFactory);
63-
advice.setContextSetHook(delegatingSessionFactory::setThreadKey);
64-
65-
// when
66-
advice.getContextSetHook().accept("test-key");
67-
68-
// then
69-
assertThat(delegatingSessionFactory.getSession()).isNotEqualTo(defaultFactory.mockSession).isEqualTo(testSessionFactory.mockSession);
68+
public void testFlow() throws IOException {
69+
given(foo.mockSession.list(anyString()))
70+
.willReturn(new String[0]);
71+
final Map<String, Object> headers = Map.of("foo", "foo");
72+
this.in.send(new GenericMessage<>("foo", headers));
73+
verify(foo.mockSession).list("foo/");
7074
}
7175

72-
@Test
73-
void shouldSetContextClearHook() {
74-
// given
75-
final Map<Object, SessionFactory<String>> factories = new HashMap<>();
76-
final var testSessionFactory = new TestSessionFactory();
77-
factories.put("test-key", testSessionFactory);
78-
final var defaultFactory = new TestSessionFactory();
79-
factories.put("default", defaultFactory);
80-
81-
final DelegatingSessionFactory<String> delegatingSessionFactory = new DelegatingSessionFactory<>(factories, defaultFactory);
82-
advice.setContextClearHook(key -> delegatingSessionFactory.clearThreadKey());
83-
84-
// when
85-
advice.getContextClearHook().accept("test-key");
86-
87-
// then
88-
assertThat(delegatingSessionFactory.getSession()).isNotEqualTo(testSessionFactory.mockSession).isEqualTo(defaultFactory.mockSession);
76+
@Configuration
77+
@ImportResource(
78+
"classpath:/org/springframework/integration/file/remote/session/context-holder-request-handler-advice-context.xml")
79+
@EnableIntegration
80+
public static class Config {
81+
82+
@Bean
83+
TestSessionFactory foo() {
84+
return new TestSessionFactory();
85+
}
86+
87+
@Bean
88+
TestSessionFactory bar() {
89+
return new TestSessionFactory();
90+
}
91+
92+
@Bean
93+
ContextHolderRequestHandlerAdvice advice() {
94+
final DelegatingSessionFactory<String> dsf = dsf();
95+
final var contextHolderRequestHandlerAdvice = new ContextHolderRequestHandlerAdvice();
96+
contextHolderRequestHandlerAdvice.setKeyProvider(m -> m.getHeaders().get("foo"));
97+
contextHolderRequestHandlerAdvice.setContextSetHook(dsf::setThreadKey);
98+
contextHolderRequestHandlerAdvice.setContextClearHook(c -> dsf.clearThreadKey());
99+
return contextHolderRequestHandlerAdvice;
100+
}
101+
102+
@Bean
103+
DelegatingSessionFactory<String> dsf() {
104+
SessionFactoryLocator<String> sff = sessionFactoryLocator();
105+
return new DelegatingSessionFactory<>(sff);
106+
}
107+
108+
@Bean
109+
public SessionFactoryLocator<String> sessionFactoryLocator() {
110+
Map<Object, SessionFactory<String>> factories = new HashMap<>();
111+
factories.put("foo", foo());
112+
TestSessionFactory bar = bar();
113+
factories.put("bar", bar);
114+
return new DefaultSessionFactoryLocator<>(factories, bar);
115+
}
116+
89117
}
90118

91119
private static class TestSessionFactory implements SessionFactory<String> {
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
<?xml version="1.0" encoding="UTF-8"?>
2+
<beans xmlns="http://www.springframework.org/schema/beans"
3+
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
4+
xmlns:int="http://www.springframework.org/schema/integration"
5+
xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd
6+
http://www.springframework.org/schema/integration https://www.springframework.org/schema/integration/spring-integration.xsd">
7+
8+
<int:channel id="in" />
9+
10+
<int:service-activator input-channel="in" output-channel="out" expression="payload">
11+
<int:request-handler-advice-chain>
12+
<ref bean="advice" />
13+
</int:request-handler-advice-chain>
14+
</int:service-activator>
15+
16+
<int:channel id="out">
17+
<int:queue />
18+
</int:channel>
19+
20+
</beans>

0 commit comments

Comments
 (0)