commit
e6e2dbe459
6
main.go
6
main.go
@ -66,8 +66,8 @@ func main() {
|
|||||||
flagSet.String("redeem-url", "", "Token redemption endpoint")
|
flagSet.String("redeem-url", "", "Token redemption endpoint")
|
||||||
flagSet.String("profile-url", "", "Profile access endpoint")
|
flagSet.String("profile-url", "", "Profile access endpoint")
|
||||||
flagSet.String("validate-url", "", "Access token validation endpoint")
|
flagSet.String("validate-url", "", "Access token validation endpoint")
|
||||||
flagSet.String("scope", "", "Oauth scope specification")
|
flagSet.String("scope", "", "OAuth scope specification")
|
||||||
flagSet.String("approval-prompt", "force", "Oauth approval_prompt")
|
flagSet.String("approval-prompt", "force", "OAuth approval_prompt")
|
||||||
|
|
||||||
flagSet.Parse(os.Args[1:])
|
flagSet.Parse(os.Args[1:])
|
||||||
|
|
||||||
@ -95,7 +95,7 @@ func main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
validator := NewValidator(opts.EmailDomains, opts.AuthenticatedEmailsFile)
|
validator := NewValidator(opts.EmailDomains, opts.AuthenticatedEmailsFile)
|
||||||
oauthproxy := NewOauthProxy(opts, validator)
|
oauthproxy := NewOAuthProxy(opts, validator)
|
||||||
|
|
||||||
if len(opts.EmailDomains) != 0 && opts.AuthenticatedEmailsFile == "" {
|
if len(opts.EmailDomains) != 0 && opts.AuthenticatedEmailsFile == "" {
|
||||||
if len(opts.EmailDomains) > 1 {
|
if len(opts.EmailDomains) > 1 {
|
||||||
|
@ -18,7 +18,7 @@ import (
|
|||||||
"github.com/bitly/oauth2_proxy/providers"
|
"github.com/bitly/oauth2_proxy/providers"
|
||||||
)
|
)
|
||||||
|
|
||||||
type OauthProxy struct {
|
type OAuthProxy struct {
|
||||||
CookieSeed string
|
CookieSeed string
|
||||||
CookieName string
|
CookieName string
|
||||||
CookieDomain string
|
CookieDomain string
|
||||||
@ -31,10 +31,10 @@ type OauthProxy struct {
|
|||||||
RobotsPath string
|
RobotsPath string
|
||||||
PingPath string
|
PingPath string
|
||||||
SignInPath string
|
SignInPath string
|
||||||
OauthStartPath string
|
OAuthStartPath string
|
||||||
OauthCallbackPath string
|
OAuthCallbackPath string
|
||||||
|
|
||||||
redirectUrl *url.URL // the url to receive requests at
|
redirectURL *url.URL // the url to receive requests at
|
||||||
provider providers.Provider
|
provider providers.Provider
|
||||||
ProxyPrefix string
|
ProxyPrefix string
|
||||||
SignInMessage string
|
SignInMessage string
|
||||||
@ -86,9 +86,9 @@ func NewFileServer(path string, filesystemPath string) (proxy http.Handler) {
|
|||||||
return http.StripPrefix(path, http.FileServer(http.Dir(filesystemPath)))
|
return http.StripPrefix(path, http.FileServer(http.Dir(filesystemPath)))
|
||||||
}
|
}
|
||||||
|
|
||||||
func NewOauthProxy(opts *Options, validator func(string) bool) *OauthProxy {
|
func NewOAuthProxy(opts *Options, validator func(string) bool) *OAuthProxy {
|
||||||
serveMux := http.NewServeMux()
|
serveMux := http.NewServeMux()
|
||||||
for _, u := range opts.proxyUrls {
|
for _, u := range opts.proxyURLs {
|
||||||
path := u.Path
|
path := u.Path
|
||||||
switch u.Scheme {
|
switch u.Scheme {
|
||||||
case "http", "https":
|
case "http", "https":
|
||||||
@ -116,10 +116,10 @@ func NewOauthProxy(opts *Options, validator func(string) bool) *OauthProxy {
|
|||||||
log.Printf("compiled skip-auth-regex => %q", u)
|
log.Printf("compiled skip-auth-regex => %q", u)
|
||||||
}
|
}
|
||||||
|
|
||||||
redirectUrl := opts.redirectUrl
|
redirectURL := opts.redirectURL
|
||||||
redirectUrl.Path = fmt.Sprintf("%s/callback", opts.ProxyPrefix)
|
redirectURL.Path = fmt.Sprintf("%s/callback", opts.ProxyPrefix)
|
||||||
|
|
||||||
log.Printf("OauthProxy configured for %s Client ID: %s", opts.provider.Data().ProviderName, opts.ClientID)
|
log.Printf("OAuthProxy configured for %s Client ID: %s", opts.provider.Data().ProviderName, opts.ClientID)
|
||||||
domain := opts.CookieDomain
|
domain := opts.CookieDomain
|
||||||
if domain == "" {
|
if domain == "" {
|
||||||
domain = "<default>"
|
domain = "<default>"
|
||||||
@ -141,7 +141,7 @@ func NewOauthProxy(opts *Options, validator func(string) bool) *OauthProxy {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return &OauthProxy{
|
return &OAuthProxy{
|
||||||
CookieName: opts.CookieName,
|
CookieName: opts.CookieName,
|
||||||
CookieSeed: opts.CookieSecret,
|
CookieSeed: opts.CookieSecret,
|
||||||
CookieDomain: opts.CookieDomain,
|
CookieDomain: opts.CookieDomain,
|
||||||
@ -154,13 +154,13 @@ func NewOauthProxy(opts *Options, validator func(string) bool) *OauthProxy {
|
|||||||
RobotsPath: "/robots.txt",
|
RobotsPath: "/robots.txt",
|
||||||
PingPath: "/ping",
|
PingPath: "/ping",
|
||||||
SignInPath: fmt.Sprintf("%s/sign_in", opts.ProxyPrefix),
|
SignInPath: fmt.Sprintf("%s/sign_in", opts.ProxyPrefix),
|
||||||
OauthStartPath: fmt.Sprintf("%s/start", opts.ProxyPrefix),
|
OAuthStartPath: fmt.Sprintf("%s/start", opts.ProxyPrefix),
|
||||||
OauthCallbackPath: fmt.Sprintf("%s/callback", opts.ProxyPrefix),
|
OAuthCallbackPath: fmt.Sprintf("%s/callback", opts.ProxyPrefix),
|
||||||
|
|
||||||
ProxyPrefix: opts.ProxyPrefix,
|
ProxyPrefix: opts.ProxyPrefix,
|
||||||
provider: opts.provider,
|
provider: opts.provider,
|
||||||
serveMux: serveMux,
|
serveMux: serveMux,
|
||||||
redirectUrl: redirectUrl,
|
redirectURL: redirectURL,
|
||||||
skipAuthRegex: opts.SkipAuthRegex,
|
skipAuthRegex: opts.SkipAuthRegex,
|
||||||
compiledRegex: opts.CompiledRegex,
|
compiledRegex: opts.CompiledRegex,
|
||||||
PassBasicAuth: opts.PassBasicAuth,
|
PassBasicAuth: opts.PassBasicAuth,
|
||||||
@ -171,13 +171,13 @@ func NewOauthProxy(opts *Options, validator func(string) bool) *OauthProxy {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *OauthProxy) GetRedirectURI(host string) string {
|
func (p *OAuthProxy) GetRedirectURI(host string) string {
|
||||||
// default to the request Host if not set
|
// default to the request Host if not set
|
||||||
if p.redirectUrl.Host != "" {
|
if p.redirectURL.Host != "" {
|
||||||
return p.redirectUrl.String()
|
return p.redirectURL.String()
|
||||||
}
|
}
|
||||||
var u url.URL
|
var u url.URL
|
||||||
u = *p.redirectUrl
|
u = *p.redirectURL
|
||||||
if u.Scheme == "" {
|
if u.Scheme == "" {
|
||||||
if p.CookieSecure {
|
if p.CookieSecure {
|
||||||
u.Scheme = "https"
|
u.Scheme = "https"
|
||||||
@ -189,16 +189,16 @@ func (p *OauthProxy) GetRedirectURI(host string) string {
|
|||||||
return u.String()
|
return u.String()
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *OauthProxy) displayCustomLoginForm() bool {
|
func (p *OAuthProxy) displayCustomLoginForm() bool {
|
||||||
return p.HtpasswdFile != nil && p.DisplayHtpasswdForm
|
return p.HtpasswdFile != nil && p.DisplayHtpasswdForm
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *OauthProxy) redeemCode(host, code string) (s *providers.SessionState, err error) {
|
func (p *OAuthProxy) redeemCode(host, code string) (s *providers.SessionState, err error) {
|
||||||
if code == "" {
|
if code == "" {
|
||||||
return nil, errors.New("missing code")
|
return nil, errors.New("missing code")
|
||||||
}
|
}
|
||||||
redirectUri := p.GetRedirectURI(host)
|
redirectURI := p.GetRedirectURI(host)
|
||||||
s, err = p.provider.Redeem(redirectUri, code)
|
s, err = p.provider.Redeem(redirectURI, code)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
@ -209,7 +209,7 @@ func (p *OauthProxy) redeemCode(host, code string) (s *providers.SessionState, e
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *OauthProxy) MakeCookie(req *http.Request, value string, expiration time.Duration, now time.Time) *http.Cookie {
|
func (p *OAuthProxy) MakeCookie(req *http.Request, value string, expiration time.Duration, now time.Time) *http.Cookie {
|
||||||
domain := req.Host
|
domain := req.Host
|
||||||
if h, _, err := net.SplitHostPort(domain); err == nil {
|
if h, _, err := net.SplitHostPort(domain); err == nil {
|
||||||
domain = h
|
domain = h
|
||||||
@ -235,15 +235,15 @@ func (p *OauthProxy) MakeCookie(req *http.Request, value string, expiration time
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *OauthProxy) ClearCookie(rw http.ResponseWriter, req *http.Request) {
|
func (p *OAuthProxy) ClearCookie(rw http.ResponseWriter, req *http.Request) {
|
||||||
http.SetCookie(rw, p.MakeCookie(req, "", time.Hour*-1, time.Now()))
|
http.SetCookie(rw, p.MakeCookie(req, "", time.Hour*-1, time.Now()))
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *OauthProxy) SetCookie(rw http.ResponseWriter, req *http.Request, val string) {
|
func (p *OAuthProxy) SetCookie(rw http.ResponseWriter, req *http.Request, val string) {
|
||||||
http.SetCookie(rw, p.MakeCookie(req, val, p.CookieExpire, time.Now()))
|
http.SetCookie(rw, p.MakeCookie(req, val, p.CookieExpire, time.Now()))
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *OauthProxy) LoadCookiedSession(req *http.Request) (*providers.SessionState, time.Duration, error) {
|
func (p *OAuthProxy) LoadCookiedSession(req *http.Request) (*providers.SessionState, time.Duration, error) {
|
||||||
var age time.Duration
|
var age time.Duration
|
||||||
c, err := req.Cookie(p.CookieName)
|
c, err := req.Cookie(p.CookieName)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@ -264,7 +264,7 @@ func (p *OauthProxy) LoadCookiedSession(req *http.Request) (*providers.SessionSt
|
|||||||
return session, age, nil
|
return session, age, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *OauthProxy) SaveSession(rw http.ResponseWriter, req *http.Request, s *providers.SessionState) error {
|
func (p *OAuthProxy) SaveSession(rw http.ResponseWriter, req *http.Request, s *providers.SessionState) error {
|
||||||
value, err := p.provider.CookieForSession(s, p.CookieCipher)
|
value, err := p.provider.CookieForSession(s, p.CookieCipher)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
@ -273,17 +273,17 @@ func (p *OauthProxy) SaveSession(rw http.ResponseWriter, req *http.Request, s *p
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *OauthProxy) RobotsTxt(rw http.ResponseWriter) {
|
func (p *OAuthProxy) RobotsTxt(rw http.ResponseWriter) {
|
||||||
rw.WriteHeader(http.StatusOK)
|
rw.WriteHeader(http.StatusOK)
|
||||||
fmt.Fprintf(rw, "User-agent: *\nDisallow: /")
|
fmt.Fprintf(rw, "User-agent: *\nDisallow: /")
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *OauthProxy) PingPage(rw http.ResponseWriter) {
|
func (p *OAuthProxy) PingPage(rw http.ResponseWriter) {
|
||||||
rw.WriteHeader(http.StatusOK)
|
rw.WriteHeader(http.StatusOK)
|
||||||
fmt.Fprintf(rw, "OK")
|
fmt.Fprintf(rw, "OK")
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *OauthProxy) ErrorPage(rw http.ResponseWriter, code int, title string, message string) {
|
func (p *OAuthProxy) ErrorPage(rw http.ResponseWriter, code int, title string, message string) {
|
||||||
log.Printf("ErrorPage %d %s %s", code, title, message)
|
log.Printf("ErrorPage %d %s %s", code, title, message)
|
||||||
rw.WriteHeader(code)
|
rw.WriteHeader(code)
|
||||||
t := struct {
|
t := struct {
|
||||||
@ -298,7 +298,7 @@ func (p *OauthProxy) ErrorPage(rw http.ResponseWriter, code int, title string, m
|
|||||||
p.templates.ExecuteTemplate(rw, "error.html", t)
|
p.templates.ExecuteTemplate(rw, "error.html", t)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *OauthProxy) SignInPage(rw http.ResponseWriter, req *http.Request, code int) {
|
func (p *OAuthProxy) SignInPage(rw http.ResponseWriter, req *http.Request, code int) {
|
||||||
p.ClearCookie(rw, req)
|
p.ClearCookie(rw, req)
|
||||||
rw.WriteHeader(code)
|
rw.WriteHeader(code)
|
||||||
|
|
||||||
@ -325,7 +325,7 @@ func (p *OauthProxy) SignInPage(rw http.ResponseWriter, req *http.Request, code
|
|||||||
p.templates.ExecuteTemplate(rw, "sign_in.html", t)
|
p.templates.ExecuteTemplate(rw, "sign_in.html", t)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *OauthProxy) ManualSignIn(rw http.ResponseWriter, req *http.Request) (string, bool) {
|
func (p *OAuthProxy) ManualSignIn(rw http.ResponseWriter, req *http.Request) (string, bool) {
|
||||||
if req.Method != "POST" || p.HtpasswdFile == nil {
|
if req.Method != "POST" || p.HtpasswdFile == nil {
|
||||||
return "", false
|
return "", false
|
||||||
}
|
}
|
||||||
@ -342,7 +342,7 @@ func (p *OauthProxy) ManualSignIn(rw http.ResponseWriter, req *http.Request) (st
|
|||||||
return "", false
|
return "", false
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *OauthProxy) GetRedirect(req *http.Request) (string, error) {
|
func (p *OAuthProxy) GetRedirect(req *http.Request) (string, error) {
|
||||||
err := req.ParseForm()
|
err := req.ParseForm()
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@ -358,7 +358,7 @@ func (p *OauthProxy) GetRedirect(req *http.Request) (string, error) {
|
|||||||
return redirect, err
|
return redirect, err
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *OauthProxy) IsWhitelistedPath(path string) (ok bool) {
|
func (p *OAuthProxy) IsWhitelistedPath(path string) (ok bool) {
|
||||||
for _, u := range p.compiledRegex {
|
for _, u := range p.compiledRegex {
|
||||||
ok = u.MatchString(path)
|
ok = u.MatchString(path)
|
||||||
if ok {
|
if ok {
|
||||||
@ -376,7 +376,7 @@ func getRemoteAddr(req *http.Request) (s string) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *OauthProxy) ServeHTTP(rw http.ResponseWriter, req *http.Request) {
|
func (p *OAuthProxy) ServeHTTP(rw http.ResponseWriter, req *http.Request) {
|
||||||
switch path := req.URL.Path; {
|
switch path := req.URL.Path; {
|
||||||
case path == p.RobotsPath:
|
case path == p.RobotsPath:
|
||||||
p.RobotsTxt(rw)
|
p.RobotsTxt(rw)
|
||||||
@ -386,16 +386,16 @@ func (p *OauthProxy) ServeHTTP(rw http.ResponseWriter, req *http.Request) {
|
|||||||
p.serveMux.ServeHTTP(rw, req)
|
p.serveMux.ServeHTTP(rw, req)
|
||||||
case path == p.SignInPath:
|
case path == p.SignInPath:
|
||||||
p.SignIn(rw, req)
|
p.SignIn(rw, req)
|
||||||
case path == p.OauthStartPath:
|
case path == p.OAuthStartPath:
|
||||||
p.OauthStart(rw, req)
|
p.OAuthStart(rw, req)
|
||||||
case path == p.OauthCallbackPath:
|
case path == p.OAuthCallbackPath:
|
||||||
p.OauthCallback(rw, req)
|
p.OAuthCallback(rw, req)
|
||||||
default:
|
default:
|
||||||
p.Proxy(rw, req)
|
p.Proxy(rw, req)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *OauthProxy) SignIn(rw http.ResponseWriter, req *http.Request) {
|
func (p *OAuthProxy) SignIn(rw http.ResponseWriter, req *http.Request) {
|
||||||
redirect, err := p.GetRedirect(req)
|
redirect, err := p.GetRedirect(req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
p.ErrorPage(rw, 500, "Internal Error", err.Error())
|
p.ErrorPage(rw, 500, "Internal Error", err.Error())
|
||||||
@ -412,7 +412,7 @@ func (p *OauthProxy) SignIn(rw http.ResponseWriter, req *http.Request) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *OauthProxy) OauthStart(rw http.ResponseWriter, req *http.Request) {
|
func (p *OAuthProxy) OAuthStart(rw http.ResponseWriter, req *http.Request) {
|
||||||
redirect, err := p.GetRedirect(req)
|
redirect, err := p.GetRedirect(req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
p.ErrorPage(rw, 500, "Internal Error", err.Error())
|
p.ErrorPage(rw, 500, "Internal Error", err.Error())
|
||||||
@ -422,7 +422,7 @@ func (p *OauthProxy) OauthStart(rw http.ResponseWriter, req *http.Request) {
|
|||||||
http.Redirect(rw, req, p.provider.GetLoginURL(redirectURI, redirect), 302)
|
http.Redirect(rw, req, p.provider.GetLoginURL(redirectURI, redirect), 302)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *OauthProxy) OauthCallback(rw http.ResponseWriter, req *http.Request) {
|
func (p *OAuthProxy) OAuthCallback(rw http.ResponseWriter, req *http.Request) {
|
||||||
remoteAddr := getRemoteAddr(req)
|
remoteAddr := getRemoteAddr(req)
|
||||||
|
|
||||||
// finish the oauth cycle
|
// finish the oauth cycle
|
||||||
@ -465,7 +465,7 @@ func (p *OauthProxy) OauthCallback(rw http.ResponseWriter, req *http.Request) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *OauthProxy) Proxy(rw http.ResponseWriter, req *http.Request) {
|
func (p *OAuthProxy) Proxy(rw http.ResponseWriter, req *http.Request) {
|
||||||
var saveSession, clearSession, revalidated bool
|
var saveSession, clearSession, revalidated bool
|
||||||
remoteAddr := getRemoteAddr(req)
|
remoteAddr := getRemoteAddr(req)
|
||||||
|
|
||||||
@ -555,7 +555,7 @@ func (p *OauthProxy) Proxy(rw http.ResponseWriter, req *http.Request) {
|
|||||||
p.serveMux.ServeHTTP(rw, req)
|
p.serveMux.ServeHTTP(rw, req)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *OauthProxy) CheckBasicAuth(req *http.Request) (*providers.SessionState, error) {
|
func (p *OAuthProxy) CheckBasicAuth(req *http.Request) (*providers.SessionState, error) {
|
||||||
if p.HtpasswdFile == nil {
|
if p.HtpasswdFile == nil {
|
||||||
return nil, nil
|
return nil, nil
|
||||||
}
|
}
|
||||||
|
@ -80,7 +80,7 @@ func TestRobotsTxt(t *testing.T) {
|
|||||||
opts.CookieSecret = "xyzzyplugh"
|
opts.CookieSecret = "xyzzyplugh"
|
||||||
opts.Validate()
|
opts.Validate()
|
||||||
|
|
||||||
proxy := NewOauthProxy(opts, func(string) bool { return true })
|
proxy := NewOAuthProxy(opts, func(string) bool { return true })
|
||||||
rw := httptest.NewRecorder()
|
rw := httptest.NewRecorder()
|
||||||
req, _ := http.NewRequest("GET", "/robots.txt", nil)
|
req, _ := http.NewRequest("GET", "/robots.txt", nil)
|
||||||
proxy.ServeHTTP(rw, req)
|
proxy.ServeHTTP(rw, req)
|
||||||
@ -124,17 +124,17 @@ func TestBasicAuthPassword(t *testing.T) {
|
|||||||
opts.provider = &TestProvider{
|
opts.provider = &TestProvider{
|
||||||
ProviderData: &providers.ProviderData{
|
ProviderData: &providers.ProviderData{
|
||||||
ProviderName: "Test Provider",
|
ProviderName: "Test Provider",
|
||||||
LoginUrl: &url.URL{
|
LoginURL: &url.URL{
|
||||||
Scheme: "http",
|
Scheme: "http",
|
||||||
Host: provider_url.Host,
|
Host: provider_url.Host,
|
||||||
Path: "/oauth/authorize",
|
Path: "/oauth/authorize",
|
||||||
},
|
},
|
||||||
RedeemUrl: &url.URL{
|
RedeemURL: &url.URL{
|
||||||
Scheme: "http",
|
Scheme: "http",
|
||||||
Host: provider_url.Host,
|
Host: provider_url.Host,
|
||||||
Path: "/oauth/token",
|
Path: "/oauth/token",
|
||||||
},
|
},
|
||||||
ProfileUrl: &url.URL{
|
ProfileURL: &url.URL{
|
||||||
Scheme: "http",
|
Scheme: "http",
|
||||||
Host: provider_url.Host,
|
Host: provider_url.Host,
|
||||||
Path: "/api/v1/profile",
|
Path: "/api/v1/profile",
|
||||||
@ -144,7 +144,7 @@ func TestBasicAuthPassword(t *testing.T) {
|
|||||||
EmailAddress: email_address,
|
EmailAddress: email_address,
|
||||||
}
|
}
|
||||||
|
|
||||||
proxy := NewOauthProxy(opts, func(email string) bool {
|
proxy := NewOAuthProxy(opts, func(email string) bool {
|
||||||
return email == email_address
|
return email == email_address
|
||||||
})
|
})
|
||||||
|
|
||||||
@ -199,7 +199,7 @@ func (tp *TestProvider) ValidateSessionState(session *providers.SessionState) bo
|
|||||||
|
|
||||||
type PassAccessTokenTest struct {
|
type PassAccessTokenTest struct {
|
||||||
provider_server *httptest.Server
|
provider_server *httptest.Server
|
||||||
proxy *OauthProxy
|
proxy *OAuthProxy
|
||||||
opts *Options
|
opts *Options
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -245,17 +245,17 @@ func NewPassAccessTokenTest(opts PassAccessTokenTestOptions) *PassAccessTokenTes
|
|||||||
t.opts.provider = &TestProvider{
|
t.opts.provider = &TestProvider{
|
||||||
ProviderData: &providers.ProviderData{
|
ProviderData: &providers.ProviderData{
|
||||||
ProviderName: "Test Provider",
|
ProviderName: "Test Provider",
|
||||||
LoginUrl: &url.URL{
|
LoginURL: &url.URL{
|
||||||
Scheme: "http",
|
Scheme: "http",
|
||||||
Host: provider_url.Host,
|
Host: provider_url.Host,
|
||||||
Path: "/oauth/authorize",
|
Path: "/oauth/authorize",
|
||||||
},
|
},
|
||||||
RedeemUrl: &url.URL{
|
RedeemURL: &url.URL{
|
||||||
Scheme: "http",
|
Scheme: "http",
|
||||||
Host: provider_url.Host,
|
Host: provider_url.Host,
|
||||||
Path: "/oauth/token",
|
Path: "/oauth/token",
|
||||||
},
|
},
|
||||||
ProfileUrl: &url.URL{
|
ProfileURL: &url.URL{
|
||||||
Scheme: "http",
|
Scheme: "http",
|
||||||
Host: provider_url.Host,
|
Host: provider_url.Host,
|
||||||
Path: "/api/v1/profile",
|
Path: "/api/v1/profile",
|
||||||
@ -265,7 +265,7 @@ func NewPassAccessTokenTest(opts PassAccessTokenTestOptions) *PassAccessTokenTes
|
|||||||
EmailAddress: email_address,
|
EmailAddress: email_address,
|
||||||
}
|
}
|
||||||
|
|
||||||
t.proxy = NewOauthProxy(t.opts, func(email string) bool {
|
t.proxy = NewOAuthProxy(t.opts, func(email string) bool {
|
||||||
return email == email_address
|
return email == email_address
|
||||||
})
|
})
|
||||||
return t
|
return t
|
||||||
@ -360,7 +360,7 @@ func TestDoNotForwardAccessTokenUpstream(t *testing.T) {
|
|||||||
|
|
||||||
type SignInPageTest struct {
|
type SignInPageTest struct {
|
||||||
opts *Options
|
opts *Options
|
||||||
proxy *OauthProxy
|
proxy *OAuthProxy
|
||||||
sign_in_regexp *regexp.Regexp
|
sign_in_regexp *regexp.Regexp
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -375,7 +375,7 @@ func NewSignInPageTest() *SignInPageTest {
|
|||||||
sip_test.opts.ClientSecret = "xyzzyplugh"
|
sip_test.opts.ClientSecret = "xyzzyplugh"
|
||||||
sip_test.opts.Validate()
|
sip_test.opts.Validate()
|
||||||
|
|
||||||
sip_test.proxy = NewOauthProxy(sip_test.opts, func(email string) bool {
|
sip_test.proxy = NewOAuthProxy(sip_test.opts, func(email string) bool {
|
||||||
return true
|
return true
|
||||||
})
|
})
|
||||||
sip_test.sign_in_regexp = regexp.MustCompile(signInRedirectPattern)
|
sip_test.sign_in_regexp = regexp.MustCompile(signInRedirectPattern)
|
||||||
@ -425,7 +425,7 @@ func TestSignInPageDirectAccessRedirectsToRoot(t *testing.T) {
|
|||||||
|
|
||||||
type ProcessCookieTest struct {
|
type ProcessCookieTest struct {
|
||||||
opts *Options
|
opts *Options
|
||||||
proxy *OauthProxy
|
proxy *OAuthProxy
|
||||||
rw *httptest.ResponseRecorder
|
rw *httptest.ResponseRecorder
|
||||||
req *http.Request
|
req *http.Request
|
||||||
provider TestProvider
|
provider TestProvider
|
||||||
@ -449,7 +449,7 @@ func NewProcessCookieTest(opts ProcessCookieTestOpts) *ProcessCookieTest {
|
|||||||
pc_test.opts.CookieRefresh = time.Hour
|
pc_test.opts.CookieRefresh = time.Hour
|
||||||
pc_test.opts.Validate()
|
pc_test.opts.Validate()
|
||||||
|
|
||||||
pc_test.proxy = NewOauthProxy(pc_test.opts, func(email string) bool {
|
pc_test.proxy = NewOAuthProxy(pc_test.opts, func(email string) bool {
|
||||||
return pc_test.validate_user
|
return pc_test.validate_user
|
||||||
})
|
})
|
||||||
pc_test.proxy.provider = &TestProvider{
|
pc_test.proxy.provider = &TestProvider{
|
||||||
|
36
options.go
36
options.go
@ -16,7 +16,7 @@ type Options struct {
|
|||||||
ProxyPrefix string `flag:"proxy-prefix" cfg:"proxy-prefix"`
|
ProxyPrefix string `flag:"proxy-prefix" cfg:"proxy-prefix"`
|
||||||
HttpAddress string `flag:"http-address" cfg:"http_address"`
|
HttpAddress string `flag:"http-address" cfg:"http_address"`
|
||||||
HttpsAddress string `flag:"https-address" cfg:"https_address"`
|
HttpsAddress string `flag:"https-address" cfg:"https_address"`
|
||||||
RedirectUrl string `flag:"redirect-url" cfg:"redirect_url"`
|
RedirectURL string `flag:"redirect-url" cfg:"redirect_url"`
|
||||||
ClientID string `flag:"client-id" cfg:"client_id" env:"OAUTH2_PROXY_CLIENT_ID"`
|
ClientID string `flag:"client-id" cfg:"client_id" env:"OAUTH2_PROXY_CLIENT_ID"`
|
||||||
ClientSecret string `flag:"client-secret" cfg:"client_secret" env:"OAUTH2_PROXY_CLIENT_SECRET"`
|
ClientSecret string `flag:"client-secret" cfg:"client_secret" env:"OAUTH2_PROXY_CLIENT_SECRET"`
|
||||||
TLSCertFile string `flag:"tls-cert" cfg:"tls_cert_file"`
|
TLSCertFile string `flag:"tls-cert" cfg:"tls_cert_file"`
|
||||||
@ -51,18 +51,18 @@ type Options struct {
|
|||||||
// These options allow for other providers besides Google, with
|
// These options allow for other providers besides Google, with
|
||||||
// potential overrides.
|
// potential overrides.
|
||||||
Provider string `flag:"provider" cfg:"provider"`
|
Provider string `flag:"provider" cfg:"provider"`
|
||||||
LoginUrl string `flag:"login-url" cfg:"login_url"`
|
LoginURL string `flag:"login-url" cfg:"login_url"`
|
||||||
RedeemUrl string `flag:"redeem-url" cfg:"redeem_url"`
|
RedeemURL string `flag:"redeem-url" cfg:"redeem_url"`
|
||||||
ProfileUrl string `flag:"profile-url" cfg:"profile_url"`
|
ProfileURL string `flag:"profile-url" cfg:"profile_url"`
|
||||||
ValidateUrl string `flag:"validate-url" cfg:"validate_url"`
|
ValidateURL string `flag:"validate-url" cfg:"validate_url"`
|
||||||
Scope string `flag:"scope" cfg:"scope"`
|
Scope string `flag:"scope" cfg:"scope"`
|
||||||
ApprovalPrompt string `flag:"approval-prompt" cfg:"approval_prompt"`
|
ApprovalPrompt string `flag:"approval-prompt" cfg:"approval_prompt"`
|
||||||
|
|
||||||
RequestLogging bool `flag:"request-logging" cfg:"request_logging"`
|
RequestLogging bool `flag:"request-logging" cfg:"request_logging"`
|
||||||
|
|
||||||
// internal values that are set after config validation
|
// internal values that are set after config validation
|
||||||
redirectUrl *url.URL
|
redirectURL *url.URL
|
||||||
proxyUrls []*url.URL
|
proxyURLs []*url.URL
|
||||||
CompiledRegex []*regexp.Regexp
|
CompiledRegex []*regexp.Regexp
|
||||||
provider providers.Provider
|
provider providers.Provider
|
||||||
}
|
}
|
||||||
@ -86,7 +86,7 @@ func NewOptions() *Options {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func parseUrl(to_parse string, urltype string, msgs []string) (*url.URL, []string) {
|
func parseURL(to_parse string, urltype string, msgs []string) (*url.URL, []string) {
|
||||||
parsed, err := url.Parse(to_parse)
|
parsed, err := url.Parse(to_parse)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, append(msgs, fmt.Sprintf(
|
return nil, append(msgs, fmt.Sprintf(
|
||||||
@ -113,19 +113,19 @@ func (o *Options) Validate() error {
|
|||||||
msgs = append(msgs, "missing setting for email validation: email-domain or authenticated-emails-file required.\n use email-domain=* to authorize all email addresses")
|
msgs = append(msgs, "missing setting for email validation: email-domain or authenticated-emails-file required.\n use email-domain=* to authorize all email addresses")
|
||||||
}
|
}
|
||||||
|
|
||||||
o.redirectUrl, msgs = parseUrl(o.RedirectUrl, "redirect", msgs)
|
o.redirectURL, msgs = parseURL(o.RedirectURL, "redirect", msgs)
|
||||||
|
|
||||||
for _, u := range o.Upstreams {
|
for _, u := range o.Upstreams {
|
||||||
upstreamUrl, err := url.Parse(u)
|
upstreamURL, err := url.Parse(u)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
msgs = append(msgs, fmt.Sprintf(
|
msgs = append(msgs, fmt.Sprintf(
|
||||||
"error parsing upstream=%q %s",
|
"error parsing upstream=%q %s",
|
||||||
upstreamUrl, err))
|
upstreamURL, err))
|
||||||
}
|
}
|
||||||
if upstreamUrl.Path == "" {
|
if upstreamURL.Path == "" {
|
||||||
upstreamUrl.Path = "/"
|
upstreamURL.Path = "/"
|
||||||
}
|
}
|
||||||
o.proxyUrls = append(o.proxyUrls, upstreamUrl)
|
o.proxyURLs = append(o.proxyURLs, upstreamURL)
|
||||||
}
|
}
|
||||||
|
|
||||||
for _, u := range o.SkipAuthRegex {
|
for _, u := range o.SkipAuthRegex {
|
||||||
@ -189,10 +189,10 @@ func parseProviderInfo(o *Options, msgs []string) []string {
|
|||||||
ClientSecret: o.ClientSecret,
|
ClientSecret: o.ClientSecret,
|
||||||
ApprovalPrompt: o.ApprovalPrompt,
|
ApprovalPrompt: o.ApprovalPrompt,
|
||||||
}
|
}
|
||||||
p.LoginUrl, msgs = parseUrl(o.LoginUrl, "login", msgs)
|
p.LoginURL, msgs = parseURL(o.LoginURL, "login", msgs)
|
||||||
p.RedeemUrl, msgs = parseUrl(o.RedeemUrl, "redeem", msgs)
|
p.RedeemURL, msgs = parseURL(o.RedeemURL, "redeem", msgs)
|
||||||
p.ProfileUrl, msgs = parseUrl(o.ProfileUrl, "profile", msgs)
|
p.ProfileURL, msgs = parseURL(o.ProfileURL, "profile", msgs)
|
||||||
p.ValidateUrl, msgs = parseUrl(o.ValidateUrl, "validate", msgs)
|
p.ValidateURL, msgs = parseURL(o.ValidateURL, "validate", msgs)
|
||||||
|
|
||||||
o.provider = providers.New(o.Provider, p)
|
o.provider = providers.New(o.Provider, p)
|
||||||
switch p := o.provider.(type) {
|
switch p := o.provider.(type) {
|
||||||
|
@ -73,16 +73,16 @@ func TestInitializedOptions(t *testing.T) {
|
|||||||
|
|
||||||
// Note that it's not worth testing nonparseable URLs, since url.Parse()
|
// Note that it's not worth testing nonparseable URLs, since url.Parse()
|
||||||
// seems to parse damn near anything.
|
// seems to parse damn near anything.
|
||||||
func TestRedirectUrl(t *testing.T) {
|
func TestRedirectURL(t *testing.T) {
|
||||||
o := testOptions()
|
o := testOptions()
|
||||||
o.RedirectUrl = "https://myhost.com/oauth2/callback"
|
o.RedirectURL = "https://myhost.com/oauth2/callback"
|
||||||
assert.Equal(t, nil, o.Validate())
|
assert.Equal(t, nil, o.Validate())
|
||||||
expected := &url.URL{
|
expected := &url.URL{
|
||||||
Scheme: "https", Host: "myhost.com", Path: "/oauth2/callback"}
|
Scheme: "https", Host: "myhost.com", Path: "/oauth2/callback"}
|
||||||
assert.Equal(t, expected, o.redirectUrl)
|
assert.Equal(t, expected, o.redirectURL)
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestProxyUrls(t *testing.T) {
|
func TestProxyURLs(t *testing.T) {
|
||||||
o := testOptions()
|
o := testOptions()
|
||||||
o.Upstreams = append(o.Upstreams, "http://127.0.0.1:8081")
|
o.Upstreams = append(o.Upstreams, "http://127.0.0.1:8081")
|
||||||
assert.Equal(t, nil, o.Validate())
|
assert.Equal(t, nil, o.Validate())
|
||||||
@ -91,7 +91,7 @@ func TestProxyUrls(t *testing.T) {
|
|||||||
// note the '/' was added
|
// note the '/' was added
|
||||||
&url.URL{Scheme: "http", Host: "127.0.0.1:8081", Path: "/"},
|
&url.URL{Scheme: "http", Host: "127.0.0.1:8081", Path: "/"},
|
||||||
}
|
}
|
||||||
assert.Equal(t, expected, o.proxyUrls)
|
assert.Equal(t, expected, o.proxyURLs)
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestCompiledRegex(t *testing.T) {
|
func TestCompiledRegex(t *testing.T) {
|
||||||
@ -125,10 +125,10 @@ func TestDefaultProviderApiSettings(t *testing.T) {
|
|||||||
assert.Equal(t, nil, o.Validate())
|
assert.Equal(t, nil, o.Validate())
|
||||||
p := o.provider.Data()
|
p := o.provider.Data()
|
||||||
assert.Equal(t, "https://accounts.google.com/o/oauth2/auth?access_type=offline",
|
assert.Equal(t, "https://accounts.google.com/o/oauth2/auth?access_type=offline",
|
||||||
p.LoginUrl.String())
|
p.LoginURL.String())
|
||||||
assert.Equal(t, "https://www.googleapis.com/oauth2/v3/token",
|
assert.Equal(t, "https://www.googleapis.com/oauth2/v3/token",
|
||||||
p.RedeemUrl.String())
|
p.RedeemURL.String())
|
||||||
assert.Equal(t, "", p.ProfileUrl.String())
|
assert.Equal(t, "", p.ProfileURL.String())
|
||||||
assert.Equal(t, "profile email", p.Scope)
|
assert.Equal(t, "profile email", p.Scope)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -17,22 +17,22 @@ type GitHubProvider struct {
|
|||||||
|
|
||||||
func NewGitHubProvider(p *ProviderData) *GitHubProvider {
|
func NewGitHubProvider(p *ProviderData) *GitHubProvider {
|
||||||
p.ProviderName = "GitHub"
|
p.ProviderName = "GitHub"
|
||||||
if p.LoginUrl == nil || p.LoginUrl.String() == "" {
|
if p.LoginURL == nil || p.LoginURL.String() == "" {
|
||||||
p.LoginUrl = &url.URL{
|
p.LoginURL = &url.URL{
|
||||||
Scheme: "https",
|
Scheme: "https",
|
||||||
Host: "github.com",
|
Host: "github.com",
|
||||||
Path: "/login/oauth/authorize",
|
Path: "/login/oauth/authorize",
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if p.RedeemUrl == nil || p.RedeemUrl.String() == "" {
|
if p.RedeemURL == nil || p.RedeemURL.String() == "" {
|
||||||
p.RedeemUrl = &url.URL{
|
p.RedeemURL = &url.URL{
|
||||||
Scheme: "https",
|
Scheme: "https",
|
||||||
Host: "github.com",
|
Host: "github.com",
|
||||||
Path: "/login/oauth/access_token",
|
Path: "/login/oauth/access_token",
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if p.ValidateUrl == nil || p.ValidateUrl.String() == "" {
|
if p.ValidateURL == nil || p.ValidateURL.String() == "" {
|
||||||
p.ValidateUrl = &url.URL{
|
p.ValidateURL = &url.URL{
|
||||||
Scheme: "https",
|
Scheme: "https",
|
||||||
Host: "api.github.com",
|
Host: "api.github.com",
|
||||||
Path: "/user/emails",
|
Path: "/user/emails",
|
||||||
|
@ -21,7 +21,7 @@ import (
|
|||||||
|
|
||||||
type GoogleProvider struct {
|
type GoogleProvider struct {
|
||||||
*ProviderData
|
*ProviderData
|
||||||
RedeemRefreshUrl *url.URL
|
RedeemRefreshURL *url.URL
|
||||||
// GroupValidator is a function that determines if the passed email is in
|
// GroupValidator is a function that determines if the passed email is in
|
||||||
// the configured Google group.
|
// the configured Google group.
|
||||||
GroupValidator func(string) bool
|
GroupValidator func(string) bool
|
||||||
@ -29,21 +29,21 @@ type GoogleProvider struct {
|
|||||||
|
|
||||||
func NewGoogleProvider(p *ProviderData) *GoogleProvider {
|
func NewGoogleProvider(p *ProviderData) *GoogleProvider {
|
||||||
p.ProviderName = "Google"
|
p.ProviderName = "Google"
|
||||||
if p.LoginUrl.String() == "" {
|
if p.LoginURL.String() == "" {
|
||||||
p.LoginUrl = &url.URL{Scheme: "https",
|
p.LoginURL = &url.URL{Scheme: "https",
|
||||||
Host: "accounts.google.com",
|
Host: "accounts.google.com",
|
||||||
Path: "/o/oauth2/auth",
|
Path: "/o/oauth2/auth",
|
||||||
// to get a refresh token. see https://developers.google.com/identity/protocols/OAuth2WebServer#offline
|
// to get a refresh token. see https://developers.google.com/identity/protocols/OAuth2WebServer#offline
|
||||||
RawQuery: "access_type=offline",
|
RawQuery: "access_type=offline",
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if p.RedeemUrl.String() == "" {
|
if p.RedeemURL.String() == "" {
|
||||||
p.RedeemUrl = &url.URL{Scheme: "https",
|
p.RedeemURL = &url.URL{Scheme: "https",
|
||||||
Host: "www.googleapis.com",
|
Host: "www.googleapis.com",
|
||||||
Path: "/oauth2/v3/token"}
|
Path: "/oauth2/v3/token"}
|
||||||
}
|
}
|
||||||
if p.ValidateUrl.String() == "" {
|
if p.ValidateURL.String() == "" {
|
||||||
p.ValidateUrl = &url.URL{Scheme: "https",
|
p.ValidateURL = &url.URL{Scheme: "https",
|
||||||
Host: "www.googleapis.com",
|
Host: "www.googleapis.com",
|
||||||
Path: "/oauth2/v1/tokeninfo"}
|
Path: "/oauth2/v1/tokeninfo"}
|
||||||
}
|
}
|
||||||
@ -96,20 +96,20 @@ func jwtDecodeSegment(seg string) ([]byte, error) {
|
|||||||
return base64.URLEncoding.DecodeString(seg)
|
return base64.URLEncoding.DecodeString(seg)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *GoogleProvider) Redeem(redirectUrl, code string) (s *SessionState, err error) {
|
func (p *GoogleProvider) Redeem(redirectURL, code string) (s *SessionState, err error) {
|
||||||
if code == "" {
|
if code == "" {
|
||||||
err = errors.New("missing code")
|
err = errors.New("missing code")
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
params := url.Values{}
|
params := url.Values{}
|
||||||
params.Add("redirect_uri", redirectUrl)
|
params.Add("redirect_uri", redirectURL)
|
||||||
params.Add("client_id", p.ClientID)
|
params.Add("client_id", p.ClientID)
|
||||||
params.Add("client_secret", p.ClientSecret)
|
params.Add("client_secret", p.ClientSecret)
|
||||||
params.Add("code", code)
|
params.Add("code", code)
|
||||||
params.Add("grant_type", "authorization_code")
|
params.Add("grant_type", "authorization_code")
|
||||||
var req *http.Request
|
var req *http.Request
|
||||||
req, err = http.NewRequest("POST", p.RedeemUrl.String(), bytes.NewBufferString(params.Encode()))
|
req, err = http.NewRequest("POST", p.RedeemURL.String(), bytes.NewBufferString(params.Encode()))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
@ -127,7 +127,7 @@ func (p *GoogleProvider) Redeem(redirectUrl, code string) (s *SessionState, err
|
|||||||
}
|
}
|
||||||
|
|
||||||
if resp.StatusCode != 200 {
|
if resp.StatusCode != 200 {
|
||||||
err = fmt.Errorf("got %d from %q %s", resp.StatusCode, p.RedeemUrl.String(), body)
|
err = fmt.Errorf("got %d from %q %s", resp.StatusCode, p.RedeemURL.String(), body)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -281,7 +281,7 @@ func (p *GoogleProvider) redeemRefreshToken(refreshToken string) (token string,
|
|||||||
params.Add("refresh_token", refreshToken)
|
params.Add("refresh_token", refreshToken)
|
||||||
params.Add("grant_type", "refresh_token")
|
params.Add("grant_type", "refresh_token")
|
||||||
var req *http.Request
|
var req *http.Request
|
||||||
req, err = http.NewRequest("POST", p.RedeemUrl.String(), bytes.NewBufferString(params.Encode()))
|
req, err = http.NewRequest("POST", p.RedeemURL.String(), bytes.NewBufferString(params.Encode()))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
@ -299,7 +299,7 @@ func (p *GoogleProvider) redeemRefreshToken(refreshToken string) (token string,
|
|||||||
}
|
}
|
||||||
|
|
||||||
if resp.StatusCode != 200 {
|
if resp.StatusCode != 200 {
|
||||||
err = fmt.Errorf("got %d from %q %s", resp.StatusCode, p.RedeemUrl.String(), body)
|
err = fmt.Errorf("got %d from %q %s", resp.StatusCode, p.RedeemURL.String(), body)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -23,10 +23,10 @@ func newGoogleProvider() *GoogleProvider {
|
|||||||
return NewGoogleProvider(
|
return NewGoogleProvider(
|
||||||
&ProviderData{
|
&ProviderData{
|
||||||
ProviderName: "",
|
ProviderName: "",
|
||||||
LoginUrl: &url.URL{},
|
LoginURL: &url.URL{},
|
||||||
RedeemUrl: &url.URL{},
|
RedeemURL: &url.URL{},
|
||||||
ProfileUrl: &url.URL{},
|
ProfileURL: &url.URL{},
|
||||||
ValidateUrl: &url.URL{},
|
ValidateURL: &url.URL{},
|
||||||
Scope: ""})
|
Scope: ""})
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -35,31 +35,31 @@ func TestGoogleProviderDefaults(t *testing.T) {
|
|||||||
assert.NotEqual(t, nil, p)
|
assert.NotEqual(t, nil, p)
|
||||||
assert.Equal(t, "Google", p.Data().ProviderName)
|
assert.Equal(t, "Google", p.Data().ProviderName)
|
||||||
assert.Equal(t, "https://accounts.google.com/o/oauth2/auth?access_type=offline",
|
assert.Equal(t, "https://accounts.google.com/o/oauth2/auth?access_type=offline",
|
||||||
p.Data().LoginUrl.String())
|
p.Data().LoginURL.String())
|
||||||
assert.Equal(t, "https://www.googleapis.com/oauth2/v3/token",
|
assert.Equal(t, "https://www.googleapis.com/oauth2/v3/token",
|
||||||
p.Data().RedeemUrl.String())
|
p.Data().RedeemURL.String())
|
||||||
assert.Equal(t, "https://www.googleapis.com/oauth2/v1/tokeninfo",
|
assert.Equal(t, "https://www.googleapis.com/oauth2/v1/tokeninfo",
|
||||||
p.Data().ValidateUrl.String())
|
p.Data().ValidateURL.String())
|
||||||
assert.Equal(t, "", p.Data().ProfileUrl.String())
|
assert.Equal(t, "", p.Data().ProfileURL.String())
|
||||||
assert.Equal(t, "profile email", p.Data().Scope)
|
assert.Equal(t, "profile email", p.Data().Scope)
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestGoogleProviderOverrides(t *testing.T) {
|
func TestGoogleProviderOverrides(t *testing.T) {
|
||||||
p := NewGoogleProvider(
|
p := NewGoogleProvider(
|
||||||
&ProviderData{
|
&ProviderData{
|
||||||
LoginUrl: &url.URL{
|
LoginURL: &url.URL{
|
||||||
Scheme: "https",
|
Scheme: "https",
|
||||||
Host: "example.com",
|
Host: "example.com",
|
||||||
Path: "/oauth/auth"},
|
Path: "/oauth/auth"},
|
||||||
RedeemUrl: &url.URL{
|
RedeemURL: &url.URL{
|
||||||
Scheme: "https",
|
Scheme: "https",
|
||||||
Host: "example.com",
|
Host: "example.com",
|
||||||
Path: "/oauth/token"},
|
Path: "/oauth/token"},
|
||||||
ProfileUrl: &url.URL{
|
ProfileURL: &url.URL{
|
||||||
Scheme: "https",
|
Scheme: "https",
|
||||||
Host: "example.com",
|
Host: "example.com",
|
||||||
Path: "/oauth/profile"},
|
Path: "/oauth/profile"},
|
||||||
ValidateUrl: &url.URL{
|
ValidateURL: &url.URL{
|
||||||
Scheme: "https",
|
Scheme: "https",
|
||||||
Host: "example.com",
|
Host: "example.com",
|
||||||
Path: "/oauth/tokeninfo"},
|
Path: "/oauth/tokeninfo"},
|
||||||
@ -67,13 +67,13 @@ func TestGoogleProviderOverrides(t *testing.T) {
|
|||||||
assert.NotEqual(t, nil, p)
|
assert.NotEqual(t, nil, p)
|
||||||
assert.Equal(t, "Google", p.Data().ProviderName)
|
assert.Equal(t, "Google", p.Data().ProviderName)
|
||||||
assert.Equal(t, "https://example.com/oauth/auth",
|
assert.Equal(t, "https://example.com/oauth/auth",
|
||||||
p.Data().LoginUrl.String())
|
p.Data().LoginURL.String())
|
||||||
assert.Equal(t, "https://example.com/oauth/token",
|
assert.Equal(t, "https://example.com/oauth/token",
|
||||||
p.Data().RedeemUrl.String())
|
p.Data().RedeemURL.String())
|
||||||
assert.Equal(t, "https://example.com/oauth/profile",
|
assert.Equal(t, "https://example.com/oauth/profile",
|
||||||
p.Data().ProfileUrl.String())
|
p.Data().ProfileURL.String())
|
||||||
assert.Equal(t, "https://example.com/oauth/tokeninfo",
|
assert.Equal(t, "https://example.com/oauth/tokeninfo",
|
||||||
p.Data().ValidateUrl.String())
|
p.Data().ValidateURL.String())
|
||||||
assert.Equal(t, "profile", p.Data().Scope)
|
assert.Equal(t, "profile", p.Data().Scope)
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -94,7 +94,7 @@ func TestGoogleProviderGetEmailAddress(t *testing.T) {
|
|||||||
})
|
})
|
||||||
assert.Equal(t, nil, err)
|
assert.Equal(t, nil, err)
|
||||||
var server *httptest.Server
|
var server *httptest.Server
|
||||||
p.RedeemUrl, server = newRedeemServer(body)
|
p.RedeemURL, server = newRedeemServer(body)
|
||||||
defer server.Close()
|
defer server.Close()
|
||||||
|
|
||||||
session, err := p.Redeem("http://redirect/", "code1234")
|
session, err := p.Redeem("http://redirect/", "code1234")
|
||||||
@ -131,7 +131,7 @@ func TestGoogleProviderGetEmailAddressInvalidEncoding(t *testing.T) {
|
|||||||
})
|
})
|
||||||
assert.Equal(t, nil, err)
|
assert.Equal(t, nil, err)
|
||||||
var server *httptest.Server
|
var server *httptest.Server
|
||||||
p.RedeemUrl, server = newRedeemServer(body)
|
p.RedeemURL, server = newRedeemServer(body)
|
||||||
defer server.Close()
|
defer server.Close()
|
||||||
|
|
||||||
session, err := p.Redeem("http://redirect/", "code1234")
|
session, err := p.Redeem("http://redirect/", "code1234")
|
||||||
@ -150,7 +150,7 @@ func TestGoogleProviderGetEmailAddressInvalidJson(t *testing.T) {
|
|||||||
})
|
})
|
||||||
assert.Equal(t, nil, err)
|
assert.Equal(t, nil, err)
|
||||||
var server *httptest.Server
|
var server *httptest.Server
|
||||||
p.RedeemUrl, server = newRedeemServer(body)
|
p.RedeemURL, server = newRedeemServer(body)
|
||||||
defer server.Close()
|
defer server.Close()
|
||||||
|
|
||||||
session, err := p.Redeem("http://redirect/", "code1234")
|
session, err := p.Redeem("http://redirect/", "code1234")
|
||||||
@ -169,7 +169,7 @@ func TestGoogleProviderGetEmailAddressEmailMissing(t *testing.T) {
|
|||||||
})
|
})
|
||||||
assert.Equal(t, nil, err)
|
assert.Equal(t, nil, err)
|
||||||
var server *httptest.Server
|
var server *httptest.Server
|
||||||
p.RedeemUrl, server = newRedeemServer(body)
|
p.RedeemURL, server = newRedeemServer(body)
|
||||||
defer server.Close()
|
defer server.Close()
|
||||||
|
|
||||||
session, err := p.Redeem("http://redirect/", "code1234")
|
session, err := p.Redeem("http://redirect/", "code1234")
|
||||||
|
@ -11,10 +11,10 @@ import (
|
|||||||
|
|
||||||
// validateToken returns true if token is valid
|
// validateToken returns true if token is valid
|
||||||
func validateToken(p Provider, access_token string, header http.Header) bool {
|
func validateToken(p Provider, access_token string, header http.Header) bool {
|
||||||
if access_token == "" || p.Data().ValidateUrl == nil {
|
if access_token == "" || p.Data().ValidateURL == nil {
|
||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
endpoint := p.Data().ValidateUrl.String()
|
endpoint := p.Data().ValidateURL.String()
|
||||||
if len(header) == 0 {
|
if len(header) == 0 {
|
||||||
params := url.Values{"access_token": {access_token}}
|
params := url.Values{"access_token": {access_token}}
|
||||||
endpoint = endpoint + "?" + params.Encode()
|
endpoint = endpoint + "?" + params.Encode()
|
||||||
|
@ -63,7 +63,7 @@ func NewValidateSessionStateTest() *ValidateSessionStateTest {
|
|||||||
backend_url, _ := url.Parse(vt_test.backend.URL)
|
backend_url, _ := url.Parse(vt_test.backend.URL)
|
||||||
vt_test.provider = &ValidateSessionStateTestProvider{
|
vt_test.provider = &ValidateSessionStateTestProvider{
|
||||||
ProviderData: &ProviderData{
|
ProviderData: &ProviderData{
|
||||||
ValidateUrl: &url.URL{
|
ValidateURL: &url.URL{
|
||||||
Scheme: "http",
|
Scheme: "http",
|
||||||
Host: backend_url.Host,
|
Host: backend_url.Host,
|
||||||
Path: "/oauth/tokeninfo",
|
Path: "/oauth/tokeninfo",
|
||||||
@ -99,10 +99,10 @@ func TestValidateSessionStateEmptyToken(t *testing.T) {
|
|||||||
assert.Equal(t, false, validateToken(vt_test.provider, "", nil))
|
assert.Equal(t, false, validateToken(vt_test.provider, "", nil))
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestValidateSessionStateEmptyValidateUrl(t *testing.T) {
|
func TestValidateSessionStateEmptyValidateURL(t *testing.T) {
|
||||||
vt_test := NewValidateSessionStateTest()
|
vt_test := NewValidateSessionStateTest()
|
||||||
defer vt_test.Close()
|
defer vt_test.Close()
|
||||||
vt_test.provider.Data().ValidateUrl = nil
|
vt_test.provider.Data().ValidateURL = nil
|
||||||
assert.Equal(t, false, validateToken(vt_test.provider, "foobar", nil))
|
assert.Equal(t, false, validateToken(vt_test.provider, "foobar", nil))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -15,23 +15,23 @@ type LinkedInProvider struct {
|
|||||||
|
|
||||||
func NewLinkedInProvider(p *ProviderData) *LinkedInProvider {
|
func NewLinkedInProvider(p *ProviderData) *LinkedInProvider {
|
||||||
p.ProviderName = "LinkedIn"
|
p.ProviderName = "LinkedIn"
|
||||||
if p.LoginUrl.String() == "" {
|
if p.LoginURL.String() == "" {
|
||||||
p.LoginUrl = &url.URL{Scheme: "https",
|
p.LoginURL = &url.URL{Scheme: "https",
|
||||||
Host: "www.linkedin.com",
|
Host: "www.linkedin.com",
|
||||||
Path: "/uas/oauth2/authorization"}
|
Path: "/uas/oauth2/authorization"}
|
||||||
}
|
}
|
||||||
if p.RedeemUrl.String() == "" {
|
if p.RedeemURL.String() == "" {
|
||||||
p.RedeemUrl = &url.URL{Scheme: "https",
|
p.RedeemURL = &url.URL{Scheme: "https",
|
||||||
Host: "www.linkedin.com",
|
Host: "www.linkedin.com",
|
||||||
Path: "/uas/oauth2/accessToken"}
|
Path: "/uas/oauth2/accessToken"}
|
||||||
}
|
}
|
||||||
if p.ProfileUrl.String() == "" {
|
if p.ProfileURL.String() == "" {
|
||||||
p.ProfileUrl = &url.URL{Scheme: "https",
|
p.ProfileURL = &url.URL{Scheme: "https",
|
||||||
Host: "www.linkedin.com",
|
Host: "www.linkedin.com",
|
||||||
Path: "/v1/people/~/email-address"}
|
Path: "/v1/people/~/email-address"}
|
||||||
}
|
}
|
||||||
if p.ValidateUrl.String() == "" {
|
if p.ValidateURL.String() == "" {
|
||||||
p.ValidateUrl = p.ProfileUrl
|
p.ValidateURL = p.ProfileURL
|
||||||
}
|
}
|
||||||
if p.Scope == "" {
|
if p.Scope == "" {
|
||||||
p.Scope = "r_emailaddress r_basicprofile"
|
p.Scope = "r_emailaddress r_basicprofile"
|
||||||
@ -51,7 +51,7 @@ func (p *LinkedInProvider) GetEmailAddress(s *SessionState) (string, error) {
|
|||||||
if s.AccessToken == "" {
|
if s.AccessToken == "" {
|
||||||
return "", errors.New("missing access token")
|
return "", errors.New("missing access token")
|
||||||
}
|
}
|
||||||
req, err := http.NewRequest("GET", p.ProfileUrl.String()+"?format=json", nil)
|
req, err := http.NewRequest("GET", p.ProfileURL.String()+"?format=json", nil)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return "", err
|
return "", err
|
||||||
}
|
}
|
||||||
|
@ -12,15 +12,15 @@ func testLinkedInProvider(hostname string) *LinkedInProvider {
|
|||||||
p := NewLinkedInProvider(
|
p := NewLinkedInProvider(
|
||||||
&ProviderData{
|
&ProviderData{
|
||||||
ProviderName: "",
|
ProviderName: "",
|
||||||
LoginUrl: &url.URL{},
|
LoginURL: &url.URL{},
|
||||||
RedeemUrl: &url.URL{},
|
RedeemURL: &url.URL{},
|
||||||
ProfileUrl: &url.URL{},
|
ProfileURL: &url.URL{},
|
||||||
ValidateUrl: &url.URL{},
|
ValidateURL: &url.URL{},
|
||||||
Scope: ""})
|
Scope: ""})
|
||||||
if hostname != "" {
|
if hostname != "" {
|
||||||
updateUrl(p.Data().LoginUrl, hostname)
|
updateURL(p.Data().LoginURL, hostname)
|
||||||
updateUrl(p.Data().RedeemUrl, hostname)
|
updateURL(p.Data().RedeemURL, hostname)
|
||||||
updateUrl(p.Data().ProfileUrl, hostname)
|
updateURL(p.Data().ProfileURL, hostname)
|
||||||
}
|
}
|
||||||
return p
|
return p
|
||||||
}
|
}
|
||||||
@ -47,32 +47,32 @@ func TestLinkedInProviderDefaults(t *testing.T) {
|
|||||||
assert.NotEqual(t, nil, p)
|
assert.NotEqual(t, nil, p)
|
||||||
assert.Equal(t, "LinkedIn", p.Data().ProviderName)
|
assert.Equal(t, "LinkedIn", p.Data().ProviderName)
|
||||||
assert.Equal(t, "https://www.linkedin.com/uas/oauth2/authorization",
|
assert.Equal(t, "https://www.linkedin.com/uas/oauth2/authorization",
|
||||||
p.Data().LoginUrl.String())
|
p.Data().LoginURL.String())
|
||||||
assert.Equal(t, "https://www.linkedin.com/uas/oauth2/accessToken",
|
assert.Equal(t, "https://www.linkedin.com/uas/oauth2/accessToken",
|
||||||
p.Data().RedeemUrl.String())
|
p.Data().RedeemURL.String())
|
||||||
assert.Equal(t, "https://www.linkedin.com/v1/people/~/email-address",
|
assert.Equal(t, "https://www.linkedin.com/v1/people/~/email-address",
|
||||||
p.Data().ProfileUrl.String())
|
p.Data().ProfileURL.String())
|
||||||
assert.Equal(t, "https://www.linkedin.com/v1/people/~/email-address",
|
assert.Equal(t, "https://www.linkedin.com/v1/people/~/email-address",
|
||||||
p.Data().ValidateUrl.String())
|
p.Data().ValidateURL.String())
|
||||||
assert.Equal(t, "r_emailaddress r_basicprofile", p.Data().Scope)
|
assert.Equal(t, "r_emailaddress r_basicprofile", p.Data().Scope)
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestLinkedInProviderOverrides(t *testing.T) {
|
func TestLinkedInProviderOverrides(t *testing.T) {
|
||||||
p := NewLinkedInProvider(
|
p := NewLinkedInProvider(
|
||||||
&ProviderData{
|
&ProviderData{
|
||||||
LoginUrl: &url.URL{
|
LoginURL: &url.URL{
|
||||||
Scheme: "https",
|
Scheme: "https",
|
||||||
Host: "example.com",
|
Host: "example.com",
|
||||||
Path: "/oauth/auth"},
|
Path: "/oauth/auth"},
|
||||||
RedeemUrl: &url.URL{
|
RedeemURL: &url.URL{
|
||||||
Scheme: "https",
|
Scheme: "https",
|
||||||
Host: "example.com",
|
Host: "example.com",
|
||||||
Path: "/oauth/token"},
|
Path: "/oauth/token"},
|
||||||
ProfileUrl: &url.URL{
|
ProfileURL: &url.URL{
|
||||||
Scheme: "https",
|
Scheme: "https",
|
||||||
Host: "example.com",
|
Host: "example.com",
|
||||||
Path: "/oauth/profile"},
|
Path: "/oauth/profile"},
|
||||||
ValidateUrl: &url.URL{
|
ValidateURL: &url.URL{
|
||||||
Scheme: "https",
|
Scheme: "https",
|
||||||
Host: "example.com",
|
Host: "example.com",
|
||||||
Path: "/oauth/tokeninfo"},
|
Path: "/oauth/tokeninfo"},
|
||||||
@ -80,13 +80,13 @@ func TestLinkedInProviderOverrides(t *testing.T) {
|
|||||||
assert.NotEqual(t, nil, p)
|
assert.NotEqual(t, nil, p)
|
||||||
assert.Equal(t, "LinkedIn", p.Data().ProviderName)
|
assert.Equal(t, "LinkedIn", p.Data().ProviderName)
|
||||||
assert.Equal(t, "https://example.com/oauth/auth",
|
assert.Equal(t, "https://example.com/oauth/auth",
|
||||||
p.Data().LoginUrl.String())
|
p.Data().LoginURL.String())
|
||||||
assert.Equal(t, "https://example.com/oauth/token",
|
assert.Equal(t, "https://example.com/oauth/token",
|
||||||
p.Data().RedeemUrl.String())
|
p.Data().RedeemURL.String())
|
||||||
assert.Equal(t, "https://example.com/oauth/profile",
|
assert.Equal(t, "https://example.com/oauth/profile",
|
||||||
p.Data().ProfileUrl.String())
|
p.Data().ProfileURL.String())
|
||||||
assert.Equal(t, "https://example.com/oauth/tokeninfo",
|
assert.Equal(t, "https://example.com/oauth/tokeninfo",
|
||||||
p.Data().ValidateUrl.String())
|
p.Data().ValidateURL.String())
|
||||||
assert.Equal(t, "profile", p.Data().Scope)
|
assert.Equal(t, "profile", p.Data().Scope)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -16,23 +16,23 @@ func NewMyUsaProvider(p *ProviderData) *MyUsaProvider {
|
|||||||
const myUsaHost string = "alpha.my.usa.gov"
|
const myUsaHost string = "alpha.my.usa.gov"
|
||||||
|
|
||||||
p.ProviderName = "MyUSA"
|
p.ProviderName = "MyUSA"
|
||||||
if p.LoginUrl.String() == "" {
|
if p.LoginURL.String() == "" {
|
||||||
p.LoginUrl = &url.URL{Scheme: "https",
|
p.LoginURL = &url.URL{Scheme: "https",
|
||||||
Host: myUsaHost,
|
Host: myUsaHost,
|
||||||
Path: "/oauth/authorize"}
|
Path: "/oauth/authorize"}
|
||||||
}
|
}
|
||||||
if p.RedeemUrl.String() == "" {
|
if p.RedeemURL.String() == "" {
|
||||||
p.RedeemUrl = &url.URL{Scheme: "https",
|
p.RedeemURL = &url.URL{Scheme: "https",
|
||||||
Host: myUsaHost,
|
Host: myUsaHost,
|
||||||
Path: "/oauth/token"}
|
Path: "/oauth/token"}
|
||||||
}
|
}
|
||||||
if p.ProfileUrl.String() == "" {
|
if p.ProfileURL.String() == "" {
|
||||||
p.ProfileUrl = &url.URL{Scheme: "https",
|
p.ProfileURL = &url.URL{Scheme: "https",
|
||||||
Host: myUsaHost,
|
Host: myUsaHost,
|
||||||
Path: "/api/v1/profile"}
|
Path: "/api/v1/profile"}
|
||||||
}
|
}
|
||||||
if p.ValidateUrl.String() == "" {
|
if p.ValidateURL.String() == "" {
|
||||||
p.ValidateUrl = &url.URL{Scheme: "https",
|
p.ValidateURL = &url.URL{Scheme: "https",
|
||||||
Host: myUsaHost,
|
Host: myUsaHost,
|
||||||
Path: "/api/v1/tokeninfo"}
|
Path: "/api/v1/tokeninfo"}
|
||||||
}
|
}
|
||||||
@ -44,7 +44,7 @@ func NewMyUsaProvider(p *ProviderData) *MyUsaProvider {
|
|||||||
|
|
||||||
func (p *MyUsaProvider) GetEmailAddress(s *SessionState) (string, error) {
|
func (p *MyUsaProvider) GetEmailAddress(s *SessionState) (string, error) {
|
||||||
req, err := http.NewRequest("GET",
|
req, err := http.NewRequest("GET",
|
||||||
p.ProfileUrl.String()+"?access_token="+s.AccessToken, nil)
|
p.ProfileURL.String()+"?access_token="+s.AccessToken, nil)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Printf("failed building request %s", err)
|
log.Printf("failed building request %s", err)
|
||||||
return "", err
|
return "", err
|
||||||
|
@ -9,7 +9,7 @@ import (
|
|||||||
"github.com/bmizerany/assert"
|
"github.com/bmizerany/assert"
|
||||||
)
|
)
|
||||||
|
|
||||||
func updateUrl(url *url.URL, hostname string) {
|
func updateURL(url *url.URL, hostname string) {
|
||||||
url.Scheme = "http"
|
url.Scheme = "http"
|
||||||
url.Host = hostname
|
url.Host = hostname
|
||||||
}
|
}
|
||||||
@ -18,16 +18,16 @@ func testMyUsaProvider(hostname string) *MyUsaProvider {
|
|||||||
p := NewMyUsaProvider(
|
p := NewMyUsaProvider(
|
||||||
&ProviderData{
|
&ProviderData{
|
||||||
ProviderName: "",
|
ProviderName: "",
|
||||||
LoginUrl: &url.URL{},
|
LoginURL: &url.URL{},
|
||||||
RedeemUrl: &url.URL{},
|
RedeemURL: &url.URL{},
|
||||||
ProfileUrl: &url.URL{},
|
ProfileURL: &url.URL{},
|
||||||
ValidateUrl: &url.URL{},
|
ValidateURL: &url.URL{},
|
||||||
Scope: ""})
|
Scope: ""})
|
||||||
if hostname != "" {
|
if hostname != "" {
|
||||||
updateUrl(p.Data().LoginUrl, hostname)
|
updateURL(p.Data().LoginURL, hostname)
|
||||||
updateUrl(p.Data().RedeemUrl, hostname)
|
updateURL(p.Data().RedeemURL, hostname)
|
||||||
updateUrl(p.Data().ProfileUrl, hostname)
|
updateURL(p.Data().ProfileURL, hostname)
|
||||||
updateUrl(p.Data().ValidateUrl, hostname)
|
updateURL(p.Data().ValidateURL, hostname)
|
||||||
}
|
}
|
||||||
return p
|
return p
|
||||||
}
|
}
|
||||||
@ -53,32 +53,32 @@ func TestMyUsaProviderDefaults(t *testing.T) {
|
|||||||
assert.NotEqual(t, nil, p)
|
assert.NotEqual(t, nil, p)
|
||||||
assert.Equal(t, "MyUSA", p.Data().ProviderName)
|
assert.Equal(t, "MyUSA", p.Data().ProviderName)
|
||||||
assert.Equal(t, "https://alpha.my.usa.gov/oauth/authorize",
|
assert.Equal(t, "https://alpha.my.usa.gov/oauth/authorize",
|
||||||
p.Data().LoginUrl.String())
|
p.Data().LoginURL.String())
|
||||||
assert.Equal(t, "https://alpha.my.usa.gov/oauth/token",
|
assert.Equal(t, "https://alpha.my.usa.gov/oauth/token",
|
||||||
p.Data().RedeemUrl.String())
|
p.Data().RedeemURL.String())
|
||||||
assert.Equal(t, "https://alpha.my.usa.gov/api/v1/profile",
|
assert.Equal(t, "https://alpha.my.usa.gov/api/v1/profile",
|
||||||
p.Data().ProfileUrl.String())
|
p.Data().ProfileURL.String())
|
||||||
assert.Equal(t, "https://alpha.my.usa.gov/api/v1/tokeninfo",
|
assert.Equal(t, "https://alpha.my.usa.gov/api/v1/tokeninfo",
|
||||||
p.Data().ValidateUrl.String())
|
p.Data().ValidateURL.String())
|
||||||
assert.Equal(t, "profile.email", p.Data().Scope)
|
assert.Equal(t, "profile.email", p.Data().Scope)
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestMyUsaProviderOverrides(t *testing.T) {
|
func TestMyUsaProviderOverrides(t *testing.T) {
|
||||||
p := NewMyUsaProvider(
|
p := NewMyUsaProvider(
|
||||||
&ProviderData{
|
&ProviderData{
|
||||||
LoginUrl: &url.URL{
|
LoginURL: &url.URL{
|
||||||
Scheme: "https",
|
Scheme: "https",
|
||||||
Host: "example.com",
|
Host: "example.com",
|
||||||
Path: "/oauth/auth"},
|
Path: "/oauth/auth"},
|
||||||
RedeemUrl: &url.URL{
|
RedeemURL: &url.URL{
|
||||||
Scheme: "https",
|
Scheme: "https",
|
||||||
Host: "example.com",
|
Host: "example.com",
|
||||||
Path: "/oauth/token"},
|
Path: "/oauth/token"},
|
||||||
ProfileUrl: &url.URL{
|
ProfileURL: &url.URL{
|
||||||
Scheme: "https",
|
Scheme: "https",
|
||||||
Host: "example.com",
|
Host: "example.com",
|
||||||
Path: "/oauth/profile"},
|
Path: "/oauth/profile"},
|
||||||
ValidateUrl: &url.URL{
|
ValidateURL: &url.URL{
|
||||||
Scheme: "https",
|
Scheme: "https",
|
||||||
Host: "example.com",
|
Host: "example.com",
|
||||||
Path: "/oauth/tokeninfo"},
|
Path: "/oauth/tokeninfo"},
|
||||||
@ -86,13 +86,13 @@ func TestMyUsaProviderOverrides(t *testing.T) {
|
|||||||
assert.NotEqual(t, nil, p)
|
assert.NotEqual(t, nil, p)
|
||||||
assert.Equal(t, "MyUSA", p.Data().ProviderName)
|
assert.Equal(t, "MyUSA", p.Data().ProviderName)
|
||||||
assert.Equal(t, "https://example.com/oauth/auth",
|
assert.Equal(t, "https://example.com/oauth/auth",
|
||||||
p.Data().LoginUrl.String())
|
p.Data().LoginURL.String())
|
||||||
assert.Equal(t, "https://example.com/oauth/token",
|
assert.Equal(t, "https://example.com/oauth/token",
|
||||||
p.Data().RedeemUrl.String())
|
p.Data().RedeemURL.String())
|
||||||
assert.Equal(t, "https://example.com/oauth/profile",
|
assert.Equal(t, "https://example.com/oauth/profile",
|
||||||
p.Data().ProfileUrl.String())
|
p.Data().ProfileURL.String())
|
||||||
assert.Equal(t, "https://example.com/oauth/tokeninfo",
|
assert.Equal(t, "https://example.com/oauth/tokeninfo",
|
||||||
p.Data().ValidateUrl.String())
|
p.Data().ValidateURL.String())
|
||||||
assert.Equal(t, "profile", p.Data().Scope)
|
assert.Equal(t, "profile", p.Data().Scope)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -8,10 +8,10 @@ type ProviderData struct {
|
|||||||
ProviderName string
|
ProviderName string
|
||||||
ClientID string
|
ClientID string
|
||||||
ClientSecret string
|
ClientSecret string
|
||||||
LoginUrl *url.URL
|
LoginURL *url.URL
|
||||||
RedeemUrl *url.URL
|
RedeemURL *url.URL
|
||||||
ProfileUrl *url.URL
|
ProfileURL *url.URL
|
||||||
ValidateUrl *url.URL
|
ValidateURL *url.URL
|
||||||
Scope string
|
Scope string
|
||||||
ApprovalPrompt string
|
ApprovalPrompt string
|
||||||
}
|
}
|
||||||
|
@ -13,20 +13,20 @@ import (
|
|||||||
"github.com/bitly/oauth2_proxy/cookie"
|
"github.com/bitly/oauth2_proxy/cookie"
|
||||||
)
|
)
|
||||||
|
|
||||||
func (p *ProviderData) Redeem(redirectUrl, code string) (s *SessionState, err error) {
|
func (p *ProviderData) Redeem(redirectURL, code string) (s *SessionState, err error) {
|
||||||
if code == "" {
|
if code == "" {
|
||||||
err = errors.New("missing code")
|
err = errors.New("missing code")
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
params := url.Values{}
|
params := url.Values{}
|
||||||
params.Add("redirect_uri", redirectUrl)
|
params.Add("redirect_uri", redirectURL)
|
||||||
params.Add("client_id", p.ClientID)
|
params.Add("client_id", p.ClientID)
|
||||||
params.Add("client_secret", p.ClientSecret)
|
params.Add("client_secret", p.ClientSecret)
|
||||||
params.Add("code", code)
|
params.Add("code", code)
|
||||||
params.Add("grant_type", "authorization_code")
|
params.Add("grant_type", "authorization_code")
|
||||||
var req *http.Request
|
var req *http.Request
|
||||||
req, err = http.NewRequest("POST", p.RedeemUrl.String(), bytes.NewBufferString(params.Encode()))
|
req, err = http.NewRequest("POST", p.RedeemURL.String(), bytes.NewBufferString(params.Encode()))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
@ -45,7 +45,7 @@ func (p *ProviderData) Redeem(redirectUrl, code string) (s *SessionState, err er
|
|||||||
}
|
}
|
||||||
|
|
||||||
if resp.StatusCode != 200 {
|
if resp.StatusCode != 200 {
|
||||||
err = fmt.Errorf("got %d from %q %s", resp.StatusCode, p.RedeemUrl.String(), body)
|
err = fmt.Errorf("got %d from %q %s", resp.StatusCode, p.RedeemURL.String(), body)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -77,7 +77,7 @@ func (p *ProviderData) Redeem(redirectUrl, code string) (s *SessionState, err er
|
|||||||
// GetLoginURL with typical oauth parameters
|
// GetLoginURL with typical oauth parameters
|
||||||
func (p *ProviderData) GetLoginURL(redirectURI, finalRedirect string) string {
|
func (p *ProviderData) GetLoginURL(redirectURI, finalRedirect string) string {
|
||||||
var a url.URL
|
var a url.URL
|
||||||
a = *p.LoginUrl
|
a = *p.LoginURL
|
||||||
params, _ := url.ParseQuery(a.RawQuery)
|
params, _ := url.ParseQuery(a.RawQuery)
|
||||||
params.Set("redirect_uri", redirectURI)
|
params.Set("redirect_uri", redirectURI)
|
||||||
params.Set("approval_prompt", p.ApprovalPrompt)
|
params.Set("approval_prompt", p.ApprovalPrompt)
|
||||||
|
Loading…
Reference in New Issue
Block a user