81 lines
1.7 KiB
Go
81 lines
1.7 KiB
Go
package action
|
|
|
|
import (
|
|
"fmt"
|
|
"git.gammaspectra.live/git/go-away/lib/challenge"
|
|
"git.gammaspectra.live/git/go-away/lib/policy"
|
|
"github.com/goccy/go-yaml"
|
|
"github.com/goccy/go-yaml/ast"
|
|
"log/slog"
|
|
"net/http"
|
|
"regexp"
|
|
)
|
|
|
|
func init() {
|
|
Register[policy.RuleActionPROXY] = func(state challenge.StateInterface, ruleName, ruleHash string, settings ast.Node) (Handler, error) {
|
|
params := ProxyDefaultSettings
|
|
|
|
if settings != nil {
|
|
ymlData, err := settings.MarshalYAML()
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
err = yaml.Unmarshal(ymlData, ¶ms)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
}
|
|
|
|
if params.Match != "" {
|
|
expr, err := regexp.Compile(params.Match)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
|
|
return Proxy{
|
|
Match: expr,
|
|
Rewrite: params.Rewrite,
|
|
Backend: params.Backend,
|
|
}, nil
|
|
}
|
|
|
|
return Proxy{
|
|
Backend: params.Backend,
|
|
}, nil
|
|
}
|
|
}
|
|
|
|
var ProxyDefaultSettings = ProxySettings{}
|
|
|
|
type ProxySettings struct {
|
|
Match string `yaml:"proxy-match"`
|
|
Rewrite string `yaml:"proxy-rewrite"`
|
|
Backend string `yaml:"proxy-backend"`
|
|
}
|
|
|
|
type Proxy struct {
|
|
Match *regexp.Regexp
|
|
Rewrite string
|
|
Backend string
|
|
}
|
|
|
|
func (a Proxy) Handle(logger *slog.Logger, w http.ResponseWriter, r *http.Request, done func() (backend http.Handler)) (next bool, err error) {
|
|
data := challenge.RequestDataFromContext(r.Context())
|
|
|
|
backend := data.State.GetBackend(a.Backend)
|
|
if backend == nil {
|
|
return false, fmt.Errorf("backend for %s not found", a.Backend)
|
|
}
|
|
|
|
if a.Match != nil {
|
|
// rewrite query
|
|
r.URL.Path = a.Match.ReplaceAllString(r.URL.Path, a.Rewrite)
|
|
}
|
|
|
|
// set headers, ignore reply
|
|
_ = done()
|
|
backend.ServeHTTP(w, r)
|
|
|
|
return false, nil
|
|
}
|