Response.Builder responseBuilder = null; if (HttpMethod.permitsRequestBody(request.method()) && request.body() != null) { // If there's a "Expect: 100-continue" header on the request, wait for a "HTTP/1.1 100 // Continue" response before transmitting the request body. If we don't get that, return // what we did get (such as a 4xx response) without ever transmitting the request body. // 当请求头包含"Expect: 100-continue"字段, 先发送请求头, 若服务端返回code 100, 继续发送请求体. 若返回code 4xx, 关闭流. // "Expect: 100-continue": http协议里的, 表示先发送请求头, 若服务端同意, 再发送请求体 if ("100-continue".equalsIgnoreCase(request.header("Expect"))) { // 发送请求头 httpCodec.flushRequest(); realChain.eventListener().responseHeadersStart(realChain.call()); // 读取response responseBuilder = httpCodec.readResponseHeaders(true); }
// 当responseBuilder为null, 则表示没有"Expect: 100-continue"头, // 或者有"Expect: 100-continue", 但是服务端同意继续发送请求体 if (responseBuilder == null) { // Write the request body if the "Expect: 100-continue" expectation was met. // 将请求体写入流 realChain.eventListener().requestBodyStart(realChain.call()); long contentLength = request.body().contentLength(); CountingSink requestBodyOut = new CountingSink(httpCodec.createRequestBody(request, contentLength)); BufferedSink bufferedRequestBody = Okio.buffer(requestBodyOut);
request.body().writeTo(bufferedRequestBody); bufferedRequestBody.close(); realChain.eventListener() .requestBodyEnd(realChain.call(), requestBodyOut.successfulCount); } elseif (!connection.isMultiplexed()) { // If the "Expect: 100-continue" expectation wasn't met, prevent the HTTP/1 connection // from being reused. Otherwise we're still obligated to transmit the request body to // leave the connection in a consistent state.
int code = response.code(); if (code == 100) { // server sent a 100-continue even though we did not request one. // try again to read the actual response responseBuilder = httpCodec.readResponseHeaders(false);
if (forWebSocket && code == 101) { // Connection is upgrading, but we need to ensure interceptors see a non-null response body. response = response.newBuilder() .body(Util.EMPTY_RESPONSE) .build(); } else { // 构建响应体 response = response.newBuilder() .body(httpCodec.openResponseBody(response)) .build(); }
if ("close".equalsIgnoreCase(response.request().header("Connection")) || "close".equalsIgnoreCase(response.header("Connection"))) { streamAllocation.noNewStreams(); }