Add NettyServerCustomizer beans to the auto-configured factory
Closes gh-17556
This commit is contained in:
parent
ea1139755d
commit
dad7fb4f6d
@ -28,6 +28,7 @@ import org.springframework.boot.web.embedded.jetty.JettyReactiveWebServerFactory
|
||||
import org.springframework.boot.web.embedded.jetty.JettyServerCustomizer;
|
||||
import org.springframework.boot.web.embedded.netty.NettyReactiveWebServerFactory;
|
||||
import org.springframework.boot.web.embedded.netty.NettyRouteProvider;
|
||||
import org.springframework.boot.web.embedded.netty.NettyServerCustomizer;
|
||||
import org.springframework.boot.web.embedded.tomcat.TomcatConnectorCustomizer;
|
||||
import org.springframework.boot.web.embedded.tomcat.TomcatContextCustomizer;
|
||||
import org.springframework.boot.web.embedded.tomcat.TomcatProtocolHandlerCustomizer;
|
||||
@ -66,10 +67,11 @@ abstract class ReactiveWebServerFactoryConfiguration {
|
||||
|
||||
@Bean
|
||||
NettyReactiveWebServerFactory nettyReactiveWebServerFactory(ReactorResourceFactory resourceFactory,
|
||||
ObjectProvider<NettyRouteProvider> routes) {
|
||||
ObjectProvider<NettyRouteProvider> routes, ObjectProvider<NettyServerCustomizer> serverCustomizers) {
|
||||
NettyReactiveWebServerFactory serverFactory = new NettyReactiveWebServerFactory();
|
||||
serverFactory.setResourceFactory(resourceFactory);
|
||||
routes.orderedStream().forEach((route) -> serverFactory.addRouteProviders(route));
|
||||
serverFactory.getServerCustomizers().addAll(serverCustomizers.orderedStream().collect(Collectors.toList()));
|
||||
return serverFactory;
|
||||
}
|
||||
|
||||
|
@ -16,6 +16,7 @@
|
||||
|
||||
package org.springframework.boot.autoconfigure.web.reactive;
|
||||
|
||||
import io.undertow.Undertow;
|
||||
import io.undertow.Undertow.Builder;
|
||||
import org.apache.catalina.Context;
|
||||
import org.apache.catalina.connector.Connector;
|
||||
@ -25,10 +26,14 @@ import org.junit.jupiter.api.Test;
|
||||
import reactor.netty.http.server.HttpServer;
|
||||
|
||||
import org.springframework.boot.autoconfigure.AutoConfigurations;
|
||||
import org.springframework.boot.autoconfigure.logging.ConditionEvaluationReportLoggingListener;
|
||||
import org.springframework.boot.logging.LogLevel;
|
||||
import org.springframework.boot.test.context.FilteredClassLoader;
|
||||
import org.springframework.boot.test.context.runner.ReactiveWebApplicationContextRunner;
|
||||
import org.springframework.boot.web.embedded.jetty.JettyReactiveWebServerFactory;
|
||||
import org.springframework.boot.web.embedded.jetty.JettyServerCustomizer;
|
||||
import org.springframework.boot.web.embedded.netty.NettyReactiveWebServerFactory;
|
||||
import org.springframework.boot.web.embedded.netty.NettyServerCustomizer;
|
||||
import org.springframework.boot.web.embedded.tomcat.TomcatConnectorCustomizer;
|
||||
import org.springframework.boot.web.embedded.tomcat.TomcatContextCustomizer;
|
||||
import org.springframework.boot.web.embedded.tomcat.TomcatProtocolHandlerCustomizer;
|
||||
@ -49,6 +54,7 @@ import org.springframework.web.server.adapter.ForwardedHeaderTransformer;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
import static org.mockito.ArgumentMatchers.any;
|
||||
import static org.mockito.BDDMockito.given;
|
||||
import static org.mockito.Mockito.mock;
|
||||
import static org.mockito.Mockito.times;
|
||||
import static org.mockito.Mockito.verify;
|
||||
@ -279,6 +285,33 @@ class ReactiveWebServerFactoryAutoConfigurationTests {
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void nettyServerCustomizerBeanIsAddedToFactory() {
|
||||
new ReactiveWebApplicationContextRunner(AnnotationConfigReactiveWebApplicationContext::new)
|
||||
.withConfiguration(AutoConfigurations.of(ReactiveWebServerFactoryAutoConfiguration.class))
|
||||
.withClassLoader(new FilteredClassLoader(Tomcat.class, Server.class, Undertow.class))
|
||||
.withUserConfiguration(NettyServerCustomizerConfiguration.class, HttpHandlerConfiguration.class)
|
||||
.withInitializer(new ConditionEvaluationReportLoggingListener(LogLevel.INFO)).run((context) -> {
|
||||
NettyReactiveWebServerFactory factory = context.getBean(NettyReactiveWebServerFactory.class);
|
||||
assertThat(factory.getServerCustomizers()).hasSize(1);
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void nettyServerCustomizerRegisteredAsBeanAndViaFactoryIsOnlyCalledOnce() {
|
||||
new ReactiveWebApplicationContextRunner(AnnotationConfigReactiveWebServerApplicationContext::new)
|
||||
.withConfiguration(AutoConfigurations.of(ReactiveWebServerFactoryAutoConfiguration.class))
|
||||
.withClassLoader(new FilteredClassLoader(Tomcat.class, Server.class, Undertow.class))
|
||||
.withUserConfiguration(DoubleRegistrationNettyServerCustomizerConfiguration.class,
|
||||
HttpHandlerConfiguration.class)
|
||||
.withPropertyValues("server.port: 0").run((context) -> {
|
||||
NettyReactiveWebServerFactory factory = context.getBean(NettyReactiveWebServerFactory.class);
|
||||
NettyServerCustomizer customizer = context.getBean("serverCustomizer", NettyServerCustomizer.class);
|
||||
assertThat(factory.getServerCustomizers()).contains(customizer);
|
||||
verify(customizer, times(1)).apply(any(HttpServer.class));
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void forwardedHeaderTransformerShouldBeConfigured() {
|
||||
this.contextRunner.withUserConfiguration(HttpHandlerConfiguration.class)
|
||||
@ -489,6 +522,37 @@ class ReactiveWebServerFactoryAutoConfigurationTests {
|
||||
|
||||
}
|
||||
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
static class NettyServerCustomizerConfiguration {
|
||||
|
||||
@Bean
|
||||
NettyServerCustomizer serverCustomizer() {
|
||||
return (server) -> server;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
static class DoubleRegistrationNettyServerCustomizerConfiguration {
|
||||
|
||||
private final NettyServerCustomizer customizer = mock(NettyServerCustomizer.class);
|
||||
|
||||
DoubleRegistrationNettyServerCustomizerConfiguration() {
|
||||
given(this.customizer.apply(any(HttpServer.class))).willAnswer((invocation) -> invocation.getArgument(0));
|
||||
}
|
||||
|
||||
@Bean
|
||||
NettyServerCustomizer serverCustomizer() {
|
||||
return this.customizer;
|
||||
}
|
||||
|
||||
@Bean
|
||||
WebServerFactoryCustomizer<NettyReactiveWebServerFactory> nettyCustomizer() {
|
||||
return (netty) -> netty.addServerCustomizers(this.customizer);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
static class ForwardedHeaderTransformerConfiguration {
|
||||
|
||||
|
@ -21,7 +21,9 @@ import java.time.Duration;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.Collection;
|
||||
import java.util.LinkedHashSet;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
|
||||
import reactor.netty.http.HttpProtocol;
|
||||
import reactor.netty.http.server.HttpServer;
|
||||
@ -43,7 +45,7 @@ import org.springframework.util.Assert;
|
||||
*/
|
||||
public class NettyReactiveWebServerFactory extends AbstractReactiveWebServerFactory {
|
||||
|
||||
private List<NettyServerCustomizer> serverCustomizers = new ArrayList<>();
|
||||
private Set<NettyServerCustomizer> serverCustomizers = new LinkedHashSet<>();
|
||||
|
||||
private List<NettyRouteProvider> routeProviders = new ArrayList<>();
|
||||
|
||||
@ -85,7 +87,7 @@ public class NettyReactiveWebServerFactory extends AbstractReactiveWebServerFact
|
||||
*/
|
||||
public void setServerCustomizers(Collection<? extends NettyServerCustomizer> serverCustomizers) {
|
||||
Assert.notNull(serverCustomizers, "ServerCustomizers must not be null");
|
||||
this.serverCustomizers = new ArrayList<>(serverCustomizers);
|
||||
this.serverCustomizers = new LinkedHashSet<>(serverCustomizers);
|
||||
}
|
||||
|
||||
/**
|
||||
|
Loading…
x
Reference in New Issue
Block a user