Support informational headers in middlewares redefining the response writer.

Co-authored-by: LandryBe <lbenguigui@gmail.com>
This commit is contained in:
Romain 2023-06-14 17:42:44 +02:00 committed by GitHub
parent 68ed875966
commit 6885e410f0
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
10 changed files with 471 additions and 7 deletions

View file

@ -193,11 +193,25 @@ func (cc *codeCatcher) Write(buf []byte) (int, error) {
return cc.responseWriter.Write(buf)
}
// WriteHeader is, in the specific case of 1xx status codes, a direct call to the wrapped ResponseWriter, without marking headers as sent,
// allowing so further calls.
func (cc *codeCatcher) WriteHeader(code int) {
if cc.headersSent || cc.caughtFilteredCode {
return
}
// Handling informational headers.
if code >= 100 && code <= 199 {
// Multiple informational status codes can be used,
// so here the copy is not appending the values to not repeat them.
for k, v := range cc.Header() {
cc.responseWriter.Header()[k] = v
}
cc.responseWriter.WriteHeader(code)
return
}
cc.code = code
for _, block := range cc.httpCodeRanges {
if cc.code >= block[0] && cc.code <= block[1] {
@ -208,7 +222,11 @@ func (cc *codeCatcher) WriteHeader(code int) {
}
}
utils.CopyHeaders(cc.responseWriter.Header(), cc.Header())
// The copy is not appending the values,
// to not repeat them in case any informational status code has been written.
for k, v := range cc.Header() {
cc.responseWriter.Header()[k] = v
}
cc.responseWriter.WriteHeader(cc.code)
cc.headersSent = true
}
@ -303,12 +321,28 @@ func (r *codeModifierWithoutCloseNotify) Write(buf []byte) (int, error) {
// WriteHeader sends the headers, with the enforced code (the code in argument is always ignored),
// if it hasn't already been done.
func (r *codeModifierWithoutCloseNotify) WriteHeader(_ int) {
// WriteHeader is, in the specific case of 1xx status codes, a direct call to the wrapped ResponseWriter, without marking headers as sent,
// allowing so further calls.
func (r *codeModifierWithoutCloseNotify) WriteHeader(code int) {
if r.headerSent {
return
}
utils.CopyHeaders(r.responseWriter.Header(), r.Header())
// Handling informational headers.
if code >= 100 && code <= 199 {
// Multiple informational status codes can be used,
// so here the copy is not appending the values to not repeat them.
for k, v := range r.headerMap {
r.responseWriter.Header()[k] = v
}
r.responseWriter.WriteHeader(code)
return
}
for k, v := range r.headerMap {
r.responseWriter.Header()[k] = v
}
r.responseWriter.WriteHeader(r.code)
r.headerSent = true
}