diff --git a/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/web/reactive/function/client/ReactorClientHttpConnectorFactory.java b/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/web/reactive/function/client/ReactorClientHttpConnectorFactory.java index 472614ee999a..256a91d3e5da 100644 --- a/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/web/reactive/function/client/ReactorClientHttpConnectorFactory.java +++ b/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/web/reactive/function/client/ReactorClientHttpConnectorFactory.java @@ -55,14 +55,14 @@ class ReactorClientHttpConnectorFactory implements ClientHttpConnectorFactory (client) -> after.configure(before.configure(client))) - .orElse((client) -> client); - if (sslBundle != null) { - mapper = new SslConfigurer(sslBundle)::configure; - } - return new ReactorClientHttpConnector(this.reactorResourceFactory, mapper::configure); + final ReactorNettyHttpClientMapper mapper = + Stream.concat( + this.mappers.get(), + Stream.ofNullable(sslBundle != null ? (ReactorNettyHttpClientMapper) new SslConfigurer(sslBundle)::configure : null)) + .reduce((before, after) -> (client) -> after.configure(before.configure(client))) + .orElse((client) -> client); + return new ReactorClientHttpConnector(this.reactorResourceFactory, mapper::configure); } /** diff --git a/spring-boot-project/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/web/reactive/function/client/ClientHttpConnectorFactoryConfigurationTests.java b/spring-boot-project/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/web/reactive/function/client/ClientHttpConnectorFactoryConfigurationTests.java index 234b9d7df04a..4e743f637cd8 100644 --- a/spring-boot-project/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/web/reactive/function/client/ClientHttpConnectorFactoryConfigurationTests.java +++ b/spring-boot-project/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/web/reactive/function/client/ClientHttpConnectorFactoryConfigurationTests.java @@ -24,6 +24,10 @@ import org.junit.jupiter.api.Test; import org.springframework.boot.autoconfigure.AutoConfigurations; +import org.springframework.boot.ssl.SslBundle; +import org.springframework.boot.ssl.SslBundleKey; +import org.springframework.boot.ssl.jks.JksSslStoreBundle; +import org.springframework.boot.ssl.jks.JksSslStoreDetails; import org.springframework.boot.test.context.FilteredClassLoader; import org.springframework.boot.test.context.runner.ReactiveWebApplicationContextRunner; import org.springframework.context.annotation.Bean; @@ -80,11 +84,14 @@ private JettyClientHttpConnectorFactory getJettyClientHttpConnectorFactory( @Test void shouldApplyHttpClientMapper() { + JksSslStoreDetails storeDetails = JksSslStoreDetails.forLocation("classpath:test.jks"); + JksSslStoreBundle stores = new JksSslStoreBundle(storeDetails, storeDetails); + SslBundle sslBundle = SslBundle.of(stores, SslBundleKey.of("password")); new ReactiveWebApplicationContextRunner() .withConfiguration(AutoConfigurations.of(ClientHttpConnectorFactoryConfiguration.ReactorNetty.class)) .withUserConfiguration(CustomHttpClientMapper.class) .run((context) -> { - context.getBean(ReactorClientHttpConnectorFactory.class).createClientHttpConnector(); + context.getBean(ReactorClientHttpConnectorFactory.class).createClientHttpConnector(sslBundle); assertThat(CustomHttpClientMapper.called).isTrue(); }); }