httpcaddyfile: redir with "html" emits 200, no Location (fix #4940)

The intent of "html" is to redirect browser clients only, or those which can evaluate JS and/or meta tags. So return HTTP 200 and no Location header. See #4940.
This commit is contained in:
Matthew Holt 2022-08-09 11:11:52 -06:00
parent 085df25c7e
commit 91ab0e6066
No known key found for this signature in database
GPG key ID: 2A349DD577D586A5

View file

@ -540,8 +540,13 @@ func parseVars(h Helper) (caddyhttp.MiddlewareHandler, error) {
// parseRedir parses the redir directive. Syntax:
//
// redir [<matcher>] <to> [<code>]
// redir [<matcher>] <to> [<code>]
//
// <code> can be "permanent" for 301, "temporary" for 302 (default),
// a placeholder, or any number in the 3xx range or 401. The special
// code "html" can be used to redirect only browser clients (will
// respond with HTTP 200 and no Location header; redirect is performed
// with JS and a meta tag).
func parseRedir(h Helper) (caddyhttp.MiddlewareHandler, error) {
if !h.Next() {
return nil, h.ArgErr()
@ -558,6 +563,7 @@ func parseRedir(h Helper) (caddyhttp.MiddlewareHandler, error) {
}
var body string
var hdr http.Header
switch code {
case "permanent":
code = "301"
@ -578,7 +584,7 @@ func parseRedir(h Helper) (caddyhttp.MiddlewareHandler, error) {
`
safeTo := html.EscapeString(to)
body = fmt.Sprintf(metaRedir, safeTo, safeTo, safeTo, safeTo)
code = "302"
code = "200" // don't redirect non-browser clients
default:
// Allow placeholders for the code
if strings.HasPrefix(code, "{") {
@ -601,9 +607,14 @@ func parseRedir(h Helper) (caddyhttp.MiddlewareHandler, error) {
}
}
// don't redirect non-browser clients
if code != "200" {
hdr = http.Header{"Location": []string{to}}
}
return caddyhttp.StaticResponse{
StatusCode: caddyhttp.WeakString(code),
Headers: http.Header{"Location": []string{to}},
Headers: hdr,
Body: body,
}, nil
}