Skip to content

Commit 16c52bc

Browse files
committed
Introduce WebTestClientBuilderCustomizer callback
Closes gh-11579
1 parent 9b9931e commit 16c52bc

File tree

3 files changed

+139
-32
lines changed

3 files changed

+139
-32
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,81 @@
1+
/*
2+
* Copyright 2012-2018 the original author or authors.
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
package org.springframework.boot.test.autoconfigure.web.reactive;
18+
19+
import java.time.Duration;
20+
import java.util.Collection;
21+
import java.util.function.Consumer;
22+
23+
import org.springframework.boot.web.codec.CodecCustomizer;
24+
import org.springframework.http.codec.ClientCodecConfigurer;
25+
import org.springframework.test.web.reactive.server.WebTestClient;
26+
import org.springframework.test.web.reactive.server.WebTestClient.Builder;
27+
import org.springframework.util.CollectionUtils;
28+
import org.springframework.web.reactive.function.client.ExchangeStrategies;
29+
30+
/**
31+
* {@link WebTestClientBuilderCustomizer} for a typical Spring Boot application. Usually
32+
* applied automatically via
33+
* {@link AutoConfigureWebTestClient @AutoConfigureWebTestClient}, but may also be used
34+
* directly.
35+
*
36+
* @author Andy Wilkinson
37+
* @since 2.0.0
38+
*/
39+
public class SpringBootWebTestClientBuilderCustomizer
40+
implements WebTestClientBuilderCustomizer {
41+
42+
private final Collection<CodecCustomizer> codecCustomizers;
43+
44+
private Duration timeout;
45+
46+
/**
47+
* Create a new {@code SpringBootWebTestClientBuilderCustomizer} that will configure
48+
* the builder's codecs using the given {@code codecCustomizers}.
49+
* @param codecCustomizers the codec customizers
50+
*/
51+
public SpringBootWebTestClientBuilderCustomizer(
52+
Collection<CodecCustomizer> codecCustomizers) {
53+
this.codecCustomizers = codecCustomizers;
54+
}
55+
56+
public void setTimeout(Duration timeout) {
57+
this.timeout = timeout;
58+
}
59+
60+
@Override
61+
public void customize(Builder builder) {
62+
if (this.timeout != null) {
63+
builder.responseTimeout(this.timeout);
64+
}
65+
customizeWebTestClientCodecs(builder);
66+
}
67+
68+
private void customizeWebTestClientCodecs(WebTestClient.Builder builder) {
69+
if (!CollectionUtils.isEmpty(this.codecCustomizers)) {
70+
builder.exchangeStrategies(ExchangeStrategies.builder()
71+
.codecs(applyCustomizers(this.codecCustomizers)).build());
72+
}
73+
}
74+
75+
private Consumer<ClientCodecConfigurer> applyCustomizers(
76+
Collection<CodecCustomizer> customizers) {
77+
return (codecs) -> customizers
78+
.forEach((customizer) -> customizer.customize(codecs));
79+
}
80+
81+
}
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2012-2017 the original author or authors.
2+
* Copyright 2012-2018 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.
@@ -16,68 +16,55 @@
1616

1717
package org.springframework.boot.test.autoconfigure.web.reactive;
1818

19-
import java.time.Duration;
2019
import java.util.Collection;
21-
import java.util.function.Consumer;
20+
import java.util.Collections;
21+
import java.util.List;
2222

23+
import org.springframework.beans.factory.ObjectProvider;
2324
import org.springframework.boot.autoconfigure.AutoConfigureAfter;
2425
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
2526
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
2627
import org.springframework.boot.autoconfigure.http.codec.CodecsAutoConfiguration;
27-
import org.springframework.boot.context.properties.bind.Binder;
28+
import org.springframework.boot.context.properties.ConfigurationProperties;
29+
import org.springframework.boot.context.properties.EnableConfigurationProperties;
2830
import org.springframework.boot.web.codec.CodecCustomizer;
2931
import org.springframework.context.ApplicationContext;
3032
import org.springframework.context.annotation.Bean;
3133
import org.springframework.context.annotation.Configuration;
32-
import org.springframework.http.codec.ClientCodecConfigurer;
3334
import org.springframework.test.web.reactive.server.WebTestClient;
34-
import org.springframework.test.web.reactive.server.WebTestClient.Builder;
35-
import org.springframework.util.CollectionUtils;
36-
import org.springframework.web.reactive.function.client.ExchangeStrategies;
3735
import org.springframework.web.reactive.function.client.WebClient;
3836

3937
/**
4038
* Auto-configuration for {@link WebTestClient}.
4139
*
4240
* @author Stephane Nicoll
41+
* @author Andy Wilkinson
4342
* @since 2.0.0
4443
*/
4544
@Configuration
4645
@ConditionalOnClass({ WebClient.class, WebTestClient.class })
4746
@AutoConfigureAfter(CodecsAutoConfiguration.class)
47+
@EnableConfigurationProperties
4848
public class WebTestClientAutoConfiguration {
4949

5050
@Bean
5151
@ConditionalOnMissingBean
52-
public WebTestClient webTestClient(ApplicationContext applicationContext) {
52+
public WebTestClient webTestClient(ApplicationContext applicationContext,
53+
List<WebTestClientBuilderCustomizer> customizers) {
5354
WebTestClient.Builder builder = WebTestClient
5455
.bindToApplicationContext(applicationContext).configureClient();
55-
customizeWebTestClient(builder, applicationContext);
56-
customizeWebTestClientCodecs(builder, applicationContext);
57-
return builder.build();
58-
}
59-
60-
private void customizeWebTestClient(Builder builder,
61-
ApplicationContext applicationContext) {
62-
Binder.get(applicationContext.getEnvironment())
63-
.bind("spring.test.webtestclient.timeout", Duration.class)
64-
.ifBound(builder::responseTimeout);
65-
}
66-
67-
private void customizeWebTestClientCodecs(WebTestClient.Builder builder,
68-
ApplicationContext applicationContext) {
69-
Collection<CodecCustomizer> customizers = applicationContext
70-
.getBeansOfType(CodecCustomizer.class).values();
71-
if (!CollectionUtils.isEmpty(customizers)) {
72-
builder.exchangeStrategies(ExchangeStrategies.builder()
73-
.codecs(applyCustomizers(customizers)).build());
56+
for (WebTestClientBuilderCustomizer customizer : customizers) {
57+
customizer.customize(builder);
7458
}
59+
return builder.build();
7560
}
7661

77-
private Consumer<ClientCodecConfigurer> applyCustomizers(
78-
Collection<CodecCustomizer> customizers) {
79-
return (codecs) -> customizers
80-
.forEach((customizer) -> customizer.customize(codecs));
62+
@Bean
63+
@ConfigurationProperties(prefix = "spring.test.webtestclient")
64+
public SpringBootWebTestClientBuilderCustomizer springBootWebTestClientBuilderCustomizer(
65+
ObjectProvider<Collection<CodecCustomizer>> codecCustomizers) {
66+
return new SpringBootWebTestClientBuilderCustomizer(
67+
codecCustomizers.getIfAvailable(Collections::emptyList));
8168
}
8269

8370
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
/*
2+
* Copyright 2012-2018 the original author or authors.
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
package org.springframework.boot.test.autoconfigure.web.reactive;
18+
19+
import org.springframework.test.web.reactive.server.WebTestClient.Builder;
20+
21+
/**
22+
* A customizer for a {@link Builder}. Any {@code WebTestClientBuilderCustomizer} beans
23+
* found in the application context will be {@link #customize called} to customize the
24+
* auto-configured {@link Builder}.
25+
*
26+
* @author Andy Wilkinson
27+
* @since 2.0.0
28+
* @see WebTestClientAutoConfiguration
29+
*/
30+
@FunctionalInterface
31+
public interface WebTestClientBuilderCustomizer {
32+
33+
/**
34+
* Customize the given {@code builder}.
35+
* @param builder the builder
36+
*/
37+
void customize(Builder builder);
38+
39+
}

0 commit comments

Comments
 (0)