|
|
|
|
@ -16,12 +16,16 @@
@@ -16,12 +16,16 @@
|
|
|
|
|
|
|
|
|
|
package org.springframework.boot.autoconfigure.amqp; |
|
|
|
|
|
|
|
|
|
import com.rabbitmq.stream.Environment; |
|
|
|
|
import com.rabbitmq.stream.EnvironmentBuilder; |
|
|
|
|
import org.assertj.core.api.InstanceOfAssertFactories; |
|
|
|
|
import org.junit.jupiter.api.Test; |
|
|
|
|
import org.springframework.amqp.rabbit.annotation.EnableRabbit; |
|
|
|
|
|
|
|
|
|
import org.springframework.amqp.rabbit.annotation.RabbitListener; |
|
|
|
|
import org.springframework.amqp.rabbit.config.ContainerCustomizer; |
|
|
|
|
import org.springframework.amqp.rabbit.listener.MessageListenerContainer; |
|
|
|
|
import org.springframework.amqp.rabbit.listener.RabbitListenerContainerFactory; |
|
|
|
|
import org.springframework.amqp.rabbit.listener.RabbitListenerEndpointRegistry; |
|
|
|
|
import org.springframework.beans.DirectFieldAccessor; |
|
|
|
|
import org.springframework.boot.autoconfigure.AutoConfigurations; |
|
|
|
|
import org.springframework.boot.test.context.runner.ApplicationContextRunner; |
|
|
|
|
import org.springframework.context.annotation.Bean; |
|
|
|
|
@ -31,11 +35,15 @@ import org.springframework.rabbit.stream.listener.ConsumerCustomizer;
@@ -31,11 +35,15 @@ import org.springframework.rabbit.stream.listener.ConsumerCustomizer;
|
|
|
|
|
import org.springframework.rabbit.stream.listener.StreamListenerContainer; |
|
|
|
|
|
|
|
|
|
import static org.assertj.core.api.Assertions.assertThat; |
|
|
|
|
import static org.mockito.Mockito.mock; |
|
|
|
|
import static org.mockito.Mockito.verify; |
|
|
|
|
import static org.mockito.Mockito.verifyNoMoreInteractions; |
|
|
|
|
|
|
|
|
|
/** |
|
|
|
|
* Tests for {@link RabbitStreamConfiguration}. |
|
|
|
|
* |
|
|
|
|
* @author Gary Russell |
|
|
|
|
* @author Andy Wilkinson |
|
|
|
|
*/ |
|
|
|
|
class RabbitStreamConfigurationTests { |
|
|
|
|
|
|
|
|
|
@ -43,40 +51,147 @@ class RabbitStreamConfigurationTests {
@@ -43,40 +51,147 @@ class RabbitStreamConfigurationTests {
|
|
|
|
|
.withConfiguration(AutoConfigurations.of(RabbitAutoConfiguration.class)); |
|
|
|
|
|
|
|
|
|
@Test |
|
|
|
|
void testContainerType() { |
|
|
|
|
@SuppressWarnings("unchecked") |
|
|
|
|
void whenListenerTypeIsStreamThenStreamListenerContainerAndEnvironmentAreAutoConfigured() { |
|
|
|
|
this.contextRunner.withUserConfiguration(TestConfiguration.class) |
|
|
|
|
.withPropertyValues("spring.rabbitmq.listener.type:stream").run((context) -> { |
|
|
|
|
RabbitListenerEndpointRegistry registry = context.getBean(RabbitListenerEndpointRegistry.class); |
|
|
|
|
MessageListenerContainer listenerContainer = registry.getListenerContainer("test"); |
|
|
|
|
assertThat(listenerContainer).isInstanceOf(StreamListenerContainer.class); |
|
|
|
|
assertThat(listenerContainer).extracting("consumerCustomizer").isNotNull(); |
|
|
|
|
assertThat(context.getBean(StreamRabbitListenerContainerFactory.class)) |
|
|
|
|
.extracting("nativeListener", InstanceOfAssertFactories.BOOLEAN).isFalse(); |
|
|
|
|
verify(context.getBean(ContainerCustomizer.class)).configure(listenerContainer); |
|
|
|
|
assertThat(context).hasSingleBean(Environment.class); |
|
|
|
|
}); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
@Test |
|
|
|
|
void whenNativeListenerIsEnabledThenContainerFactoryIsConfiguredToUseNativeListeners() { |
|
|
|
|
this.contextRunner |
|
|
|
|
.withPropertyValues("spring.rabbitmq.listener.type:stream", |
|
|
|
|
"spring.rabbitmq.listener.stream.native-listener:true") |
|
|
|
|
.run((context) -> assertThat(context.getBean(StreamRabbitListenerContainerFactory.class)) |
|
|
|
|
.extracting("nativeListener", InstanceOfAssertFactories.BOOLEAN).isTrue()); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
@Test |
|
|
|
|
void whenCustomEnvironmenIsDefinedThenAutoConfiguredEnvironmentBacksOff() { |
|
|
|
|
this.contextRunner.withUserConfiguration(CustomEnvironmentConfiguration.class).run((context) -> { |
|
|
|
|
assertThat(context).hasSingleBean(Environment.class); |
|
|
|
|
assertThat(context.getBean(Environment.class)) |
|
|
|
|
.isSameAs(context.getBean(CustomEnvironmentConfiguration.class).environment); |
|
|
|
|
}); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
@Test |
|
|
|
|
void whenCustomMessageListenerContainerIsDefinedThenAutoConfiguredContainerBacksOff() { |
|
|
|
|
this.contextRunner.withUserConfiguration(CustomMessageListenerContainerFactoryConfiguration.class) |
|
|
|
|
.run((context) -> { |
|
|
|
|
RabbitListenerEndpointRegistry registry = context.getBean(RabbitListenerEndpointRegistry.class); |
|
|
|
|
assertThat(registry.getListenerContainer("test")).isInstanceOf(StreamListenerContainer.class); |
|
|
|
|
assertThat(new DirectFieldAccessor(registry.getListenerContainer("test")) |
|
|
|
|
.getPropertyValue("consumerCustomizer")).isNotNull(); |
|
|
|
|
assertThat(new DirectFieldAccessor(context.getBean(StreamRabbitListenerContainerFactory.class)) |
|
|
|
|
.getPropertyValue("nativeListener")).isEqualTo(Boolean.TRUE); |
|
|
|
|
assertThat(context.getBean(TestConfiguration.class).containerCustomizerCalled).isTrue(); |
|
|
|
|
assertThat(context).hasSingleBean(RabbitListenerContainerFactory.class); |
|
|
|
|
assertThat(context.getBean(RabbitListenerContainerFactory.class)).isSameAs(context.getBean( |
|
|
|
|
CustomMessageListenerContainerFactoryConfiguration.class).listenerContainerFactory); |
|
|
|
|
}); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
@Test |
|
|
|
|
void environmentUsesPropertyDefaultsByDefault() { |
|
|
|
|
EnvironmentBuilder builder = mock(EnvironmentBuilder.class); |
|
|
|
|
RabbitProperties properties = new RabbitProperties(); |
|
|
|
|
RabbitStreamConfiguration.configure(builder, properties); |
|
|
|
|
verify(builder).port(5552); |
|
|
|
|
verify(builder).host("localhost"); |
|
|
|
|
verify(builder).lazyInitialization(true); |
|
|
|
|
verify(builder).username("guest"); |
|
|
|
|
verify(builder).password("guest"); |
|
|
|
|
verifyNoMoreInteractions(builder); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
@Test |
|
|
|
|
void whenStreamPortIsSetThenEnvironmentUsesCustomPort() { |
|
|
|
|
EnvironmentBuilder builder = mock(EnvironmentBuilder.class); |
|
|
|
|
RabbitProperties properties = new RabbitProperties(); |
|
|
|
|
properties.getStream().setPort(5553); |
|
|
|
|
RabbitStreamConfiguration.configure(builder, properties); |
|
|
|
|
verify(builder).port(5553); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
@Test |
|
|
|
|
void whenStreamHostIsSetThenEnvironmentUsesCustomHost() { |
|
|
|
|
EnvironmentBuilder builder = mock(EnvironmentBuilder.class); |
|
|
|
|
RabbitProperties properties = new RabbitProperties(); |
|
|
|
|
properties.getStream().setHost("stream.rabbit.example.com"); |
|
|
|
|
RabbitStreamConfiguration.configure(builder, properties); |
|
|
|
|
verify(builder).host("stream.rabbit.example.com"); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
@Test |
|
|
|
|
void whenStreamCredentialsAreNotSetThenEnvironmentUsesRabbitCredentials() { |
|
|
|
|
EnvironmentBuilder builder = mock(EnvironmentBuilder.class); |
|
|
|
|
RabbitProperties properties = new RabbitProperties(); |
|
|
|
|
properties.setUsername("alice"); |
|
|
|
|
properties.setPassword("secret"); |
|
|
|
|
RabbitStreamConfiguration.configure(builder, properties); |
|
|
|
|
verify(builder).username("alice"); |
|
|
|
|
verify(builder).password("secret"); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
@Test |
|
|
|
|
void whenStreamCredentialsAreSetThenEnvironmentUsesStreamCredentials() { |
|
|
|
|
EnvironmentBuilder builder = mock(EnvironmentBuilder.class); |
|
|
|
|
RabbitProperties properties = new RabbitProperties(); |
|
|
|
|
properties.setUsername("alice"); |
|
|
|
|
properties.setPassword("secret"); |
|
|
|
|
properties.getStream().setUsername("bob"); |
|
|
|
|
properties.getStream().setPassword("confidential"); |
|
|
|
|
RabbitStreamConfiguration.configure(builder, properties); |
|
|
|
|
verify(builder).username("bob"); |
|
|
|
|
verify(builder).password("confidential"); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
@Configuration(proxyBeanMethods = false) |
|
|
|
|
@EnableRabbit |
|
|
|
|
static class TestConfiguration { |
|
|
|
|
|
|
|
|
|
boolean containerCustomizerCalled; |
|
|
|
|
|
|
|
|
|
@RabbitListener(id = "test", queues = "stream", autoStartup = "false") |
|
|
|
|
void listen(String in) { |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
@Bean |
|
|
|
|
ConsumerCustomizer consumerCustomizer() { |
|
|
|
|
return (id, consumer) -> { |
|
|
|
|
}; |
|
|
|
|
return mock(ConsumerCustomizer.class); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
@Bean |
|
|
|
|
@SuppressWarnings("unchecked") |
|
|
|
|
ContainerCustomizer<StreamListenerContainer> containerCustomizer() { |
|
|
|
|
return (container) -> this.containerCustomizerCalled = true; |
|
|
|
|
return mock(ContainerCustomizer.class); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
@Configuration(proxyBeanMethods = false) |
|
|
|
|
static class CustomEnvironmentConfiguration { |
|
|
|
|
|
|
|
|
|
private final Environment environment = Environment.builder().lazyInitialization(true).build(); |
|
|
|
|
|
|
|
|
|
@Bean |
|
|
|
|
Environment rabbitStreamEnvironment() { |
|
|
|
|
return this.environment; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
@Configuration(proxyBeanMethods = false) |
|
|
|
|
static class CustomMessageListenerContainerFactoryConfiguration { |
|
|
|
|
|
|
|
|
|
@SuppressWarnings("rawtypes") |
|
|
|
|
private final RabbitListenerContainerFactory listenerContainerFactory = mock( |
|
|
|
|
RabbitListenerContainerFactory.class); |
|
|
|
|
|
|
|
|
|
@Bean |
|
|
|
|
@SuppressWarnings("unchecked") |
|
|
|
|
RabbitListenerContainerFactory<MessageListenerContainer> rabbitListenerContainerFactory() { |
|
|
|
|
return this.listenerContainerFactory; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
} |
|
|
|
|
|