mirror of
https://github.com/golang/go
synced 2024-11-23 19:30:05 -07:00
net/http: update bundled http2
Updates http2 to x/net git rev 0e6d34ef942 for https://golang.org/cl/18472 which means we'll get to delete a ton of grpc-go code and just use the standard library's HTTP client instead. Also, the comments in this CL aren't entirely accurate it turns out. RFC 2616 says: "The Trailer header field can be used to indicate which header fields are included in a trailer (see section 14.40)." And 14.40: " An HTTP/1.1 message SHOULD include a Trailer header field in a message using chunked transfer-coding with a non-empty trailer. Doing so allows the recipient to know which header fields to expect in the trailer. If no Trailer header field is present, the trailer SHOULD NOT include any header fields. See section 3.6.1 for restrictions on the use of trailer fields in a "chunked" transfer-coding." So it's really a SHOULD more than a MUST. And gRPC (at least Google's server) doesn't predeclare "grpc-status" ahead of time in a Trailer Header, so we'll be lenient. We were too strict anyway. It's also not a concern for the Go client we have a different place to populate the Trailers, and it won't confuse clients which aren't looking for them. The ResponseWriter server side is more complicated (and strict), though, since we don't want to widen the ResponseWriter interface. So the Go server still requires that you predeclare Trailers. Change-Id: Ia2defc11a2469fb8570ecfabb8453537121084eb Reviewed-on: https://go-review.googlesource.com/18473 Run-TryBot: Brad Fitzpatrick <bradfitz@golang.org> Reviewed-by: Brad Fitzpatrick <bradfitz@golang.org>
This commit is contained in:
parent
2747ca351e
commit
9ee72f424c
@ -24,6 +24,7 @@ import (
|
||||
"encoding/binary"
|
||||
"errors"
|
||||
"fmt"
|
||||
"golang.org/x/net/http2/hpack"
|
||||
"io"
|
||||
"io/ioutil"
|
||||
"log"
|
||||
@ -37,8 +38,6 @@ import (
|
||||
"strings"
|
||||
"sync"
|
||||
"time"
|
||||
|
||||
"golang.org/x/net/http2/hpack"
|
||||
)
|
||||
|
||||
// ClientConnPool manages a pool of HTTP/2 client connections.
|
||||
@ -4348,8 +4347,8 @@ type http2clientStream struct {
|
||||
pastHeaders bool // got HEADERS w/ END_HEADERS
|
||||
pastTrailers bool // got second HEADERS frame w/ END_HEADERS
|
||||
|
||||
trailer Header // accumulated trailers
|
||||
resTrailer Header // client's Response.Trailer
|
||||
trailer Header // accumulated trailers
|
||||
resTrailer *Header // client's Response.Trailer
|
||||
}
|
||||
|
||||
// awaitRequestCancel runs in its own goroutine and waits for the user
|
||||
@ -5255,7 +5254,7 @@ func (rl *http2clientConnReadLoop) processHeaderBlockFragment(frag []byte, strea
|
||||
}
|
||||
}
|
||||
|
||||
cs.resTrailer = res.Trailer
|
||||
cs.resTrailer = &res.Trailer
|
||||
rl.activeRes[cs.ID] = cs
|
||||
cs.resc <- http2resAndError{res: res}
|
||||
rl.nextRes = nil
|
||||
@ -5383,7 +5382,11 @@ func (rl *http2clientConnReadLoop) endStream(cs *http2clientStream) {
|
||||
|
||||
func (cs *http2clientStream) copyTrailers() {
|
||||
for k, vv := range cs.trailer {
|
||||
cs.resTrailer[k] = vv
|
||||
t := cs.resTrailer
|
||||
if *t == nil {
|
||||
*t = make(Header)
|
||||
}
|
||||
(*t)[k] = vv
|
||||
}
|
||||
}
|
||||
|
||||
@ -5583,7 +5586,12 @@ func (rl *http2clientConnReadLoop) onNewTrailerField(cs *http2clientStream, f hp
|
||||
}
|
||||
|
||||
key := CanonicalHeaderKey(f.Name)
|
||||
if _, ok := cs.resTrailer[key]; ok {
|
||||
|
||||
// The spec says one must predeclare their trailers but in practice
|
||||
// popular users (which is to say the only user we found) do not so we
|
||||
// violate the spec and accept all of them.
|
||||
const acceptAllTrailers = true
|
||||
if _, ok := (*cs.resTrailer)[key]; ok || acceptAllTrailers {
|
||||
if cs.trailer == nil {
|
||||
cs.trailer = make(Header)
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user