Skip to content

Commit 0b36c94

Browse files
committed
CodecConfigurer internal refactoring
Improve how HTTP message writers are obtained for general use vs for multipart requests.
1 parent 72e7687 commit 0b36c94

File tree

5 files changed

+86
-61
lines changed

5 files changed

+86
-61
lines changed

spring-web/src/main/java/org/springframework/http/codec/multipart/MultipartHttpMessageWriter.java

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -134,6 +134,14 @@ private static List<MediaType> initMediaTypes(@Nullable HttpMessageWriter<?> for
134134
}
135135

136136

137+
/**
138+
* Return the configured part writers.
139+
* @since 5.0.7
140+
*/
141+
public List<HttpMessageWriter<?>> getPartWriters() {
142+
return Collections.unmodifiableList(partWriters);
143+
}
144+
137145
/**
138146
* Set the character set to use for part headers such as
139147
* "Content-Disposition" (and its filename parameter).

spring-web/src/main/java/org/springframework/http/codec/support/BaseCodecConfigurer.java

Lines changed: 13 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,6 @@
1818

1919
import java.util.ArrayList;
2020
import java.util.List;
21-
import java.util.function.Supplier;
2221

2322
import org.springframework.core.ResolvableType;
2423
import org.springframework.core.codec.Decoder;
@@ -28,6 +27,7 @@
2827
import org.springframework.http.codec.EncoderHttpMessageWriter;
2928
import org.springframework.http.codec.HttpMessageReader;
3029
import org.springframework.http.codec.HttpMessageWriter;
30+
import org.springframework.http.codec.multipart.MultipartHttpMessageWriter;
3131
import org.springframework.util.Assert;
3232

3333
/**
@@ -85,30 +85,29 @@ public List<HttpMessageReader<?>> getReaders() {
8585

8686
@Override
8787
public List<HttpMessageWriter<?>> getWriters() {
88+
return getWritersInternal(false);
89+
}
90+
91+
/**
92+
* Internal method that returns the configured writers.
93+
* @param forMultipart whether to returns writers for general use ("false"),
94+
* or for multipart requests only ("true"). Generally the two sets are the
95+
* same except for the multipart writer itself.
96+
*/
97+
protected List<HttpMessageWriter<?>> getWritersInternal(boolean forMultipart) {
8898
List<HttpMessageWriter<?>> result = new ArrayList<>();
8999

90-
result.addAll(this.defaultCodecs.getTypedWriters());
100+
result.addAll(this.defaultCodecs.getTypedWriters(forMultipart));
91101
result.addAll(this.customCodecs.getTypedWriters());
92102

93-
result.addAll(this.defaultCodecs.getObjectWriters());
103+
result.addAll(this.defaultCodecs.getObjectWriters(forMultipart));
94104
result.addAll(this.customCodecs.getObjectWriters());
95105

96106
result.addAll(this.defaultCodecs.getCatchAllWriters());
97107
return result;
98108
}
99109

100110

101-
// Accessors for use in sub-classes...
102-
103-
protected Supplier<List<HttpMessageWriter<?>>> getCustomTypedWriters() {
104-
return () -> this.customCodecs.typedWriters;
105-
}
106-
107-
protected Supplier<List<HttpMessageWriter<?>>> getCustomObjectWriters() {
108-
return () -> this.customCodecs.objectWriters;
109-
}
110-
111-
112111
/**
113112
* Default implementation of {@code CustomCodecs}.
114113
*/

spring-web/src/main/java/org/springframework/http/codec/support/BaseDefaultCodecs.java

Lines changed: 46 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -95,8 +95,9 @@ void registerDefaults(boolean registerDefaults) {
9595
}
9696

9797

98-
// Package private access to the configured readers...
99-
98+
/**
99+
* Return readers that support specific types.
100+
*/
100101
final List<HttpMessageReader<?>> getTypedReaders() {
101102
if (!this.registerDefaults) {
102103
return Collections.emptyList();
@@ -112,9 +113,15 @@ final List<HttpMessageReader<?>> getTypedReaders() {
112113
return readers;
113114
}
114115

116+
/**
117+
* Hook for client or server specific typed readers.
118+
*/
115119
protected void extendTypedReaders(List<HttpMessageReader<?>> typedReaders) {
116120
}
117121

122+
/**
123+
* Return Object readers (JSON, XML, SSE).
124+
*/
118125
final List<HttpMessageReader<?>> getObjectReaders() {
119126
if (!this.registerDefaults) {
120127
return Collections.emptyList();
@@ -133,9 +140,15 @@ final List<HttpMessageReader<?>> getObjectReaders() {
133140
return readers;
134141
}
135142

143+
/**
144+
* Hook for client or server specific Object readers.
145+
*/
136146
protected void extendObjectReaders(List<HttpMessageReader<?>> objectReaders) {
137147
}
138148

149+
/**
150+
* Return readers that need to be at the end, after all others.
151+
*/
139152
final List<HttpMessageReader<?>> getCatchAllReaders() {
140153
if (!this.registerDefaults) {
141154
return Collections.emptyList();
@@ -145,10 +158,13 @@ final List<HttpMessageReader<?>> getCatchAllReaders() {
145158
return result;
146159
}
147160

148-
149-
// Package private access to the configured writers...
150-
151-
final List<HttpMessageWriter<?>> getTypedWriters() {
161+
/**
162+
* Return writers that support specific types.
163+
* @param forMultipart whether to returns writers for general use ("false"),
164+
* or for multipart requests only ("true"). Generally the two sets are the
165+
* same except for the multipart writer itself.
166+
*/
167+
final List<HttpMessageWriter<?>> getTypedWriters(boolean forMultipart) {
152168
if (!this.registerDefaults) {
153169
return Collections.emptyList();
154170
}
@@ -158,14 +174,26 @@ final List<HttpMessageWriter<?>> getTypedWriters() {
158174
writers.add(new EncoderHttpMessageWriter<>(new DataBufferEncoder()));
159175
writers.add(new ResourceHttpMessageWriter());
160176
writers.add(new EncoderHttpMessageWriter<>(CharSequenceEncoder.textPlainOnly()));
161-
extendTypedWriters(writers);
177+
// No client or server specific multipart writers currently..
178+
if (!forMultipart) {
179+
extendTypedWriters(writers);
180+
}
162181
return writers;
163182
}
164183

184+
/**
185+
* Hook for client or server specific typed writers.
186+
*/
165187
protected void extendTypedWriters(List<HttpMessageWriter<?>> typedWriters) {
166188
}
167189

168-
final List<HttpMessageWriter<?>> getObjectWriters() {
190+
/**
191+
* Return Object writers (JSON, XML, SSE).
192+
* @param forMultipart whether to returns writers for general use ("false"),
193+
* or for multipart requests only ("true"). Generally the two sets are the
194+
* same except for the multipart writer itself.
195+
*/
196+
final List<HttpMessageWriter<?>> getObjectWriters(boolean forMultipart) {
169197
if (!this.registerDefaults) {
170198
return Collections.emptyList();
171199
}
@@ -179,13 +207,22 @@ final List<HttpMessageWriter<?>> getObjectWriters() {
179207
if (jaxb2Present) {
180208
writers.add(new EncoderHttpMessageWriter<>(new Jaxb2XmlEncoder()));
181209
}
182-
extendObjectWriters(writers);
210+
// No client or server specific multipart writers currently..
211+
if (!forMultipart) {
212+
extendObjectWriters(writers);
213+
}
183214
return writers;
184215
}
185216

217+
/**
218+
* Hook for client or server specific Object writers.
219+
*/
186220
protected void extendObjectWriters(List<HttpMessageWriter<?>> objectWriters) {
187221
}
188222

223+
/**
224+
* Return writers that need to be at the end, after all others.
225+
*/
189226
List<HttpMessageWriter<?>> getCatchAllWriters() {
190227
if (!this.registerDefaults) {
191228
return Collections.emptyList();

spring-web/src/main/java/org/springframework/http/codec/support/ClientDefaultCodecsImpl.java

Lines changed: 18 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,6 @@
2929
import org.springframework.http.codec.ServerSentEventHttpMessageReader;
3030
import org.springframework.http.codec.multipart.MultipartHttpMessageWriter;
3131
import org.springframework.lang.Nullable;
32-
import org.springframework.util.Assert;
3332

3433
/**
3534
* Default implementation of {@link ClientCodecConfigurer.ClientDefaultCodecs}.
@@ -45,18 +44,17 @@ class ClientDefaultCodecsImpl extends BaseDefaultCodecs implements ClientCodecCo
4544
private Decoder<?> sseDecoder;
4645

4746
@Nullable
48-
private Supplier<List<HttpMessageWriter<?>>> customTypedWriters;
47+
private Supplier<List<HttpMessageWriter<?>>> partWritersSupplier;
4948

50-
@Nullable
51-
private Supplier<List<HttpMessageWriter<?>>> customObjectWriters;
52-
53-
54-
void initCustomTypedWriters(Supplier<List<HttpMessageWriter<?>>> supplier) {
55-
this.customTypedWriters = supplier;
56-
}
5749

58-
void initCustomObjectWriters(Supplier<List<HttpMessageWriter<?>>> supplier) {
59-
this.customObjectWriters = supplier;
50+
/**
51+
* Set a supplier for part writers to use when
52+
* {@link #multipartCodecs()} are not explicitly configured.
53+
* That's the same set of writers as for general except for the multipart
54+
* writer itself.
55+
*/
56+
void setPartWritersSupplier(Supplier<List<HttpMessageWriter<?>>> supplier) {
57+
this.partWritersSupplier = supplier;
6058
}
6159

6260

@@ -86,36 +84,19 @@ private Decoder<?> getSseDecoder() {
8684

8785
@Override
8886
protected void extendTypedWriters(List<HttpMessageWriter<?>> typedWriters) {
89-
90-
MultipartHttpMessageWriter multipartWriter = new MultipartHttpMessageWriter(
91-
resolvePartWriters(typedWriters, getObjectWriters()), new FormHttpMessageWriter());
92-
93-
typedWriters.add(multipartWriter);
87+
typedWriters.add(new MultipartHttpMessageWriter(getPartWriters(), new FormHttpMessageWriter()));
9488
}
9589

96-
private List<HttpMessageWriter<?>> resolvePartWriters(List<HttpMessageWriter<?>> typedWriters,
97-
List<HttpMessageWriter<?>> objectWriters) {
98-
99-
List<HttpMessageWriter<?>> partWriters;
100-
if (this.multipartCodecs != null) {
101-
partWriters = this.multipartCodecs.getWriters();
102-
}
103-
else {
104-
Assert.notNull(this.customTypedWriters, "Expected custom typed writers supplier.");
105-
Assert.notNull(this.customObjectWriters, "Expected custom object writers supplier.");
106-
107-
partWriters = new ArrayList<>(typedWriters);
108-
partWriters.addAll(this.customTypedWriters.get());
109-
110-
partWriters.addAll(objectWriters);
111-
partWriters.addAll(this.customObjectWriters.get());
112-
113-
partWriters.addAll(super.getCatchAllWriters());
114-
}
115-
return partWriters;
90+
@SuppressWarnings("ConstantConditions")
91+
private List<HttpMessageWriter<?>> getPartWriters() {
92+
return this.multipartCodecs != null ?
93+
this.multipartCodecs.getWriters() : this.partWritersSupplier.get();
11694
}
11795

11896

97+
/**
98+
* Default implementation of {@link ClientCodecConfigurer.MultipartCodecs}.
99+
*/
119100
private static class DefaultMultipartCodecs implements ClientCodecConfigurer.MultipartCodecs {
120101

121102
private final List<HttpMessageWriter<?>> writers = new ArrayList<>();
@@ -137,4 +118,5 @@ List<HttpMessageWriter<?>> getWriters() {
137118
return this.writers;
138119
}
139120
}
121+
140122
}

spring-web/src/main/java/org/springframework/http/codec/support/DefaultClientCodecConfigurer.java

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -29,8 +29,7 @@ public class DefaultClientCodecConfigurer extends BaseCodecConfigurer implements
2929

3030
public DefaultClientCodecConfigurer() {
3131
super(new ClientDefaultCodecsImpl());
32-
((ClientDefaultCodecsImpl) defaultCodecs()).initCustomTypedWriters(getCustomTypedWriters());
33-
((ClientDefaultCodecsImpl) defaultCodecs()).initCustomObjectWriters(getCustomObjectWriters());
32+
((ClientDefaultCodecsImpl) defaultCodecs()).setPartWritersSupplier(() -> getWritersInternal(true));
3433
}
3534

3635

0 commit comments

Comments
 (0)