Implement waygate authorization grant flow

This commit is contained in:
Anders Pitman
2022-03-03 14:01:39 -07:00
parent f232e1db24
commit ec4e24d913
4 changed files with 62 additions and 12 deletions

View File

@@ -14,14 +14,15 @@ import (
var DBFolderPath string
type Database struct {
AdminDomain string `json:"admin_domain"`
Tokens map[string]TokenData `json:"tokens"`
Tunnels map[string]Tunnel `json:"tunnels"`
Users map[string]User `json:"users"`
dnsRequests map[string]namedrop.DNSRequest `json:"dns_requests"`
WaygateTunnels map[string]waygate.WaygateTunnel `json:"waygate_tunnels"`
WaygateTalismans map[string]waygate.WaygateTalisman `json:"waygate_talismans"`
mutex *sync.Mutex
AdminDomain string `json:"admin_domain"`
Tokens map[string]TokenData `json:"tokens"`
Tunnels map[string]Tunnel `json:"tunnels"`
Users map[string]User `json:"users"`
dnsRequests map[string]namedrop.DNSRequest `json:"dns_requests"`
WaygateTunnels map[string]waygate.WaygateTunnel `json:"waygate_tunnels"`
WaygateTalismans map[string]waygate.WaygateTalisman `json:"waygate_talismans"`
WaygatePendingTokens map[string]string `json:"waygate_pending_tokens"`
mutex *sync.Mutex
}
type TokenData struct {
@@ -105,6 +106,9 @@ func NewDatabase(path string) (*Database, error) {
if db.WaygateTalismans == nil {
db.WaygateTalismans = make(map[string]waygate.WaygateTalisman)
}
if db.WaygatePendingTokens == nil {
db.WaygatePendingTokens = make(map[string]string)
}
db.mutex = &sync.Mutex{}
@@ -413,6 +417,33 @@ func (d *Database) GetWaygateTalisman(id string) (waygate.WaygateTalisman, error
return talisman, nil
}
func (d *Database) SetTokenCode(token, code string) error {
d.mutex.Lock()
defer d.mutex.Unlock()
_, exists := d.WaygateTalismans[token]
if !exists {
return errors.New("No such token")
}
d.WaygatePendingTokens[code] = token
d.persist()
return nil
}
func (d *Database) GetTokenByCode(code string) (string, error) {
d.mutex.Lock()
defer d.mutex.Unlock()
token, exists := d.WaygatePendingTokens[code]
if !exists {
return "", errors.New("No such code")
}
return token, nil
}
func (d *Database) persist() {
saveJson(d, DBFolderPath+"boringproxy_db.json")
}

3
go.mod
View File

@@ -20,12 +20,13 @@ require (
github.com/libdns/libdns v0.2.1 // indirect
github.com/mholt/acmez v1.0.1 // indirect
github.com/miekg/dns v1.1.43 // indirect
github.com/pkg/browser v0.0.0-20210911075715-681adbf594b8 // indirect
go.uber.org/atomic v1.7.0 // indirect
go.uber.org/multierr v1.6.0 // indirect
go.uber.org/zap v1.17.0 // indirect
golang.org/x/net v0.0.0-20210525063256-abc453219eb5 // indirect
golang.org/x/oauth2 v0.0.0-20211104180415-d3ed0bb246c8 // indirect
golang.org/x/sys v0.0.0-20210423082822-04245dca01da // indirect
golang.org/x/sys v0.0.0-20210616045830-e2b7044e8c71 // indirect
golang.org/x/text v0.3.6 // indirect
google.golang.org/appengine v1.6.6 // indirect
google.golang.org/protobuf v1.25.0 // indirect

4
go.sum
View File

@@ -122,6 +122,8 @@ github.com/mholt/acmez v1.0.1 h1:J7uquHOKEmo71UDnVApy1sSLA0oF/r+NtVrNzMKKA9I=
github.com/mholt/acmez v1.0.1/go.mod h1:8qnn8QA/Ewx8E3ZSsmscqsIjhhpxuy9vqdgbX2ceceM=
github.com/miekg/dns v1.1.43 h1:JKfpVSCB84vrAmHzyrsxB5NAr5kLoMXZArPSw7Qlgyg=
github.com/miekg/dns v1.1.43/go.mod h1:+evo5L0630/F6ca/Z9+GAqzhjGyn8/c+TBaOyfEl0V4=
github.com/pkg/browser v0.0.0-20210911075715-681adbf594b8 h1:KoWmjvw+nsYOo29YJK9vDA65RGE3NrOnUtO7a+RF9HU=
github.com/pkg/browser v0.0.0-20210911075715-681adbf594b8/go.mod h1:HKlIX3XHQyzLZPlr7++PzdhaXEj94dEiJgZDTsxEqUI=
github.com/pkg/errors v0.8.1 h1:iURUrRGxPUNPdy5/HRSm+Yj6okJ6UtLINN0Q9M4+h3I=
github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM=
@@ -268,6 +270,8 @@ golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7w
golang.org/x/sys v0.0.0-20210303074136-134d130e1a04/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20210423082822-04245dca01da h1:b3NXsE2LusjYGGjL5bxEVZZORm/YEFFrWFjR8eFrw/c=
golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20210616045830-e2b7044e8c71 h1:X/2sJAybVknnUnV7AD2HdT6rm2p5BP6eH2j+igduWgk=
golang.org/x/sys v0.0.0-20210616045830-e2b7044e8c71/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1 h1:v+OssWQX+hTHEmOBgwxdZxK4zHq3yOs8F9J7mk0PY8E=
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
golang.org/x/text v0.0.0-20170915032832-14c0d48ead0c/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=

View File

@@ -146,11 +146,25 @@ func (h *WebUiHandler) handleWebUiRequest(w http.ResponseWriter, r *http.Request
if authReq.RedirectUri == "urn:ietf:wg:oauth:2.0:oob" {
fmt.Fprintf(w, talisman)
} else {
w.WriteHeader(500)
h.alertDialog(w, r, "Unsupported auth", "/")
return
code, err := genRandomCode(32)
if err != nil {
w.WriteHeader(500)
h.alertDialog(w, r, err.Error(), "/")
return
}
err = h.db.SetTokenCode(talisman, code)
if err != nil {
w.WriteHeader(500)
h.alertDialog(w, r, err.Error(), "/")
return
}
url := fmt.Sprintf("http://%s?code=%s&state=%s", authReq.RedirectUri, code, authReq.State)
http.Redirect(w, r, url, 303)
}
return
case "/waygate/authorize":
if r.Method != "GET" {
w.WriteHeader(405)