WebClient writes Content-Length for Mono bodies

In SPR-16892, the `EncoderHttpMessageWriter` has been improved to write
`"Content-Length"` HTTP response headers if the response body is of type
`Mono` (i.e. the actual content length is easily accessible without
buffering a possibly large response body). That change was relying on
the fact that the server side is using a `ChannelSendOperator` to delay
the writing of the body until the first signal is received.

This strategy is not effective on the client side, since no such channel
operator is used for `WebClient`. This commit improves
`EncoderHttpMessageWriter` and delays, for `Mono` HTTP message bodies
only, the writing of the body so that we can write the
`"Content-Length"` header information once we've got the body resolved.

Issue: SPR-16949
(Cherry-picked from 4a26f93a0d)
This commit is contained in:
Brian Clozel
2018-06-19 11:31:04 +02:00
parent 60838dcd03
commit d1c9401dc2
4 changed files with 16 additions and 11 deletions

View File

@@ -340,10 +340,12 @@ public class BodyInsertersTests {
String content = new String(resultBytes, StandardCharsets.UTF_8);
assertThat(content, containsString("Content-Disposition: form-data; name=\"name\"\r\n" +
"Content-Type: text/plain;charset=UTF-8\r\n" +
"Content-Length: 6\r\n" +
"\r\n" +
"value1"));
assertThat(content, containsString("Content-Disposition: form-data; name=\"name\"\r\n" +
"Content-Type: text/plain;charset=UTF-8\r\n" +
"Content-Length: 6\r\n" +
"\r\n" +
"value2"));
})

View File

@@ -317,7 +317,7 @@ public class WebClientIntegrationTests {
expectRequest(request -> {
assertEquals("/pojo/capitalize", request.getPath());
assertEquals("{\"foo\":\"foofoo\",\"bar\":\"barbar\"}", request.getBody().readUtf8());
assertEquals("chunked", request.getHeader(HttpHeaders.TRANSFER_ENCODING));
assertEquals("31", request.getHeader(HttpHeaders.CONTENT_LENGTH));
assertEquals("application/json", request.getHeader(HttpHeaders.ACCEPT));
assertEquals("application/json", request.getHeader(HttpHeaders.CONTENT_TYPE));
});