mirror of
https://github.com/caddyserver/caddy.git
synced 2024-12-27 22:23:48 +03:00
templates: Access to proxy response (closes #4420)
Also sorted the func map just for kicks.
This commit is contained in:
parent
f259ed52bb
commit
577f8ba811
2 changed files with 45 additions and 8 deletions
|
@ -1296,6 +1296,18 @@ var bufPool = sync.Pool{
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Response returns the reverse proxy's HTTP response attached to the
|
||||||
|
// request. It can only be used inside handle_response routes.
|
||||||
|
// EXPERIMENTAL: This API is subject to change or removal.
|
||||||
|
func Response(req *http.Request) (*http.Response, error) {
|
||||||
|
hrc, ok := req.Context().Value(proxyHandleResponseContextCtxKey).(*handleResponseContext)
|
||||||
|
if !ok {
|
||||||
|
return nil, caddyhttp.Error(http.StatusInternalServerError,
|
||||||
|
fmt.Errorf("cannot access backend response outside of reverse_proxy's handle_response route"))
|
||||||
|
}
|
||||||
|
return hrc.response, nil
|
||||||
|
}
|
||||||
|
|
||||||
// handleResponseContext carries some contextual information about the
|
// handleResponseContext carries some contextual information about the
|
||||||
// the current proxy handling.
|
// the current proxy handling.
|
||||||
type handleResponseContext struct {
|
type handleResponseContext struct {
|
||||||
|
|
|
@ -32,6 +32,7 @@ import (
|
||||||
"github.com/alecthomas/chroma/formatters/html"
|
"github.com/alecthomas/chroma/formatters/html"
|
||||||
"github.com/caddyserver/caddy/v2"
|
"github.com/caddyserver/caddy/v2"
|
||||||
"github.com/caddyserver/caddy/v2/modules/caddyhttp"
|
"github.com/caddyserver/caddy/v2/modules/caddyhttp"
|
||||||
|
"github.com/caddyserver/caddy/v2/modules/caddyhttp/reverseproxy"
|
||||||
"github.com/dustin/go-humanize"
|
"github.com/dustin/go-humanize"
|
||||||
"github.com/yuin/goldmark"
|
"github.com/yuin/goldmark"
|
||||||
highlighting "github.com/yuin/goldmark-highlighting"
|
highlighting "github.com/yuin/goldmark-highlighting"
|
||||||
|
@ -72,18 +73,18 @@ func (c *TemplateContext) NewTemplate(tplName string) *template.Template {
|
||||||
|
|
||||||
// add our own library
|
// add our own library
|
||||||
c.tpl.Funcs(template.FuncMap{
|
c.tpl.Funcs(template.FuncMap{
|
||||||
"include": c.funcInclude,
|
|
||||||
"import": c.funcImport,
|
|
||||||
"httpInclude": c.funcHTTPInclude,
|
|
||||||
"stripHTML": c.funcStripHTML,
|
|
||||||
"markdown": c.funcMarkdown,
|
|
||||||
"splitFrontMatter": c.funcSplitFrontMatter,
|
|
||||||
"listFiles": c.funcListFiles,
|
|
||||||
"env": c.funcEnv,
|
"env": c.funcEnv,
|
||||||
"placeholder": c.funcPlaceholder,
|
|
||||||
"fileExists": c.funcFileExists,
|
"fileExists": c.funcFileExists,
|
||||||
"httpError": c.funcHTTPError,
|
"httpError": c.funcHTTPError,
|
||||||
|
"httpInclude": c.funcHTTPInclude,
|
||||||
"humanize": c.funcHumanize,
|
"humanize": c.funcHumanize,
|
||||||
|
"import": c.funcImport,
|
||||||
|
"include": c.funcInclude,
|
||||||
|
"listFiles": c.funcListFiles,
|
||||||
|
"markdown": c.funcMarkdown,
|
||||||
|
"placeholder": c.funcPlaceholder,
|
||||||
|
"splitFrontMatter": c.funcSplitFrontMatter,
|
||||||
|
"stripHTML": c.funcStripHTML,
|
||||||
})
|
})
|
||||||
return c.tpl
|
return c.tpl
|
||||||
}
|
}
|
||||||
|
@ -438,6 +439,30 @@ func (c TemplateContext) funcHumanize(formatType, data string) (string, error) {
|
||||||
return "", fmt.Errorf("no know function was given")
|
return "", fmt.Errorf("no know function was given")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ProxyResponse accesses the response from a reverse proxy.
|
||||||
|
// It can only be used inside a handle_response route.
|
||||||
|
// EXPERIMENTAL: This API is subject to change or removal.
|
||||||
|
func (c TemplateContext) ProxyResponse() (proxyResponse, error) {
|
||||||
|
resp, err := reverseproxy.Response(c.Req)
|
||||||
|
if err != nil {
|
||||||
|
return proxyResponse{}, err
|
||||||
|
}
|
||||||
|
return proxyResponse{
|
||||||
|
resp: resp,
|
||||||
|
Body: func(maxSize int64) (string, error) {
|
||||||
|
body, err := io.ReadAll(io.LimitReader(resp.Body, maxSize))
|
||||||
|
return string(body), err
|
||||||
|
},
|
||||||
|
Header: WrappedHeader{resp.Header},
|
||||||
|
}, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
type proxyResponse struct {
|
||||||
|
resp *http.Response
|
||||||
|
Body func(maxSize int64) (string, error)
|
||||||
|
Header WrappedHeader
|
||||||
|
}
|
||||||
|
|
||||||
// WrappedHeader wraps niladic functions so that they
|
// WrappedHeader wraps niladic functions so that they
|
||||||
// can be used in templates. (Template functions must
|
// can be used in templates. (Template functions must
|
||||||
// return a value.)
|
// return a value.)
|
||||||
|
|
Loading…
Reference in a new issue