Merge pull request #70 from jehiah/templates_dir_70

Custom Sign In Template Support
This commit is contained in:
Jehiah Czebotar 2015-03-17 23:18:00 -04:00
commit 85e025db25
6 changed files with 27 additions and 6 deletions

View File

@ -75,6 +75,7 @@ Usage of google_auth_proxy:
-pass-host-header=true: pass the request Host Header to upstream -pass-host-header=true: pass the request Host Header to upstream
-redirect-url="": the OAuth Redirect URL. ie: "https://internalapp.yourcompany.com/oauth2/callback" -redirect-url="": the OAuth Redirect URL. ie: "https://internalapp.yourcompany.com/oauth2/callback"
-skip-auth-regex=: bypass authentication for requests path's that match (may be given multiple times) -skip-auth-regex=: bypass authentication for requests path's that match (may be given multiple times)
-custom templates-dir="": path to custom html templates
-upstream=: the http url(s) of the upstream endpoint. If multiple, routing is based on path -upstream=: the http url(s) of the upstream endpoint. If multiple, routing is based on path
-version=false: print version string -version=false: print version string
``` ```

View File

@ -36,6 +36,10 @@
## enabling exposes a username/login signin form ## enabling exposes a username/login signin form
# htpasswd_file = "" # htpasswd_file = ""
## Templates
## optional directory with custom sign_in.html and error.html
# custom_templates_dir = ""
## Cookie Settings ## Cookie Settings
## Secret - the seed string for secure cookies ## Secret - the seed string for secure cookies

View File

@ -38,6 +38,7 @@ func main() {
flagSet.String("authenticated-emails-file", "", "authenticate against emails via file (one per line)") flagSet.String("authenticated-emails-file", "", "authenticate against emails via file (one per line)")
flagSet.String("htpasswd-file", "", "additionally authenticate against a htpasswd file. Entries must be created with \"htpasswd -s\" for SHA encryption") flagSet.String("htpasswd-file", "", "additionally authenticate against a htpasswd file. Entries must be created with \"htpasswd -s\" for SHA encryption")
flagSet.Bool("display-htpasswd-form", true, "display username / password login form if an htpasswd file is provided") flagSet.Bool("display-htpasswd-form", true, "display username / password login form if an htpasswd file is provided")
flagSet.String("custom-templates-dir", "", "path to custom html templates")
flagSet.String("cookie-secret", "", "the seed string for secure cookies") flagSet.String("cookie-secret", "", "the seed string for secure cookies")
flagSet.String("cookie-domain", "", "an optional cookie domain to force cookies to (ie: .yourcompany.com)*") flagSet.String("cookie-domain", "", "an optional cookie domain to force cookies to (ie: .yourcompany.com)*")

View File

@ -5,6 +5,7 @@ import (
"encoding/base64" "encoding/base64"
"errors" "errors"
"fmt" "fmt"
"html/template"
"io/ioutil" "io/ioutil"
"log" "log"
"net/http" "net/http"
@ -44,6 +45,7 @@ type OauthProxy struct {
PassBasicAuth bool PassBasicAuth bool
skipAuthRegex []string skipAuthRegex []string
compiledRegex []*regexp.Regexp compiledRegex []*regexp.Regexp
templates *template.Template
} }
func NewReverseProxy(target *url.URL) (proxy *httputil.ReverseProxy) { func NewReverseProxy(target *url.URL) (proxy *httputil.ReverseProxy) {
@ -103,6 +105,7 @@ func NewOauthProxy(opts *Options, validator func(string) bool) *OauthProxy {
skipAuthRegex: opts.SkipAuthRegex, skipAuthRegex: opts.SkipAuthRegex,
compiledRegex: opts.CompiledRegex, compiledRegex: opts.CompiledRegex,
PassBasicAuth: opts.PassBasicAuth, PassBasicAuth: opts.PassBasicAuth,
templates: loadTemplates(opts.CustomTemplatesDir),
} }
} }
@ -245,7 +248,6 @@ func (p *OauthProxy) PingPage(rw http.ResponseWriter) {
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)
templates := getTemplates()
t := struct { t := struct {
Title string Title string
Message string Message string
@ -253,13 +255,12 @@ func (p *OauthProxy) ErrorPage(rw http.ResponseWriter, code int, title string, m
Title: fmt.Sprintf("%d %s", code, title), Title: fmt.Sprintf("%d %s", code, title),
Message: message, Message: message,
} }
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)
templates := getTemplates()
t := struct { t := struct {
SignInMessage string SignInMessage string
@ -272,7 +273,7 @@ func (p *OauthProxy) SignInPage(rw http.ResponseWriter, req *http.Request, code
Redirect: req.URL.RequestURI(), Redirect: req.URL.RequestURI(),
Version: VERSION, Version: VERSION,
} }
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) {

View File

@ -19,6 +19,7 @@ type Options struct {
GoogleAppsDomains []string `flag:"google-apps-domain" cfg:"google_apps_domains"` GoogleAppsDomains []string `flag:"google-apps-domain" cfg:"google_apps_domains"`
HtpasswdFile string `flag:"htpasswd-file" cfg:"htpasswd_file"` HtpasswdFile string `flag:"htpasswd-file" cfg:"htpasswd_file"`
DisplayHtpasswdForm bool `flag:"display-htpasswd-form" cfg:"display_htpasswd_form"` DisplayHtpasswdForm bool `flag:"display-htpasswd-form" cfg:"display_htpasswd_form"`
CustomTemplatesDir string `flag:"custom-templates-dir" cfg:"custom_templates_dir"`
CookieSecret string `flag:"cookie-secret" cfg:"cookie_secret" env:"GOOGLE_AUTH_PROXY_COOKIE_SECRET"` CookieSecret string `flag:"cookie-secret" cfg:"cookie_secret" env:"GOOGLE_AUTH_PROXY_COOKIE_SECRET"`
CookieDomain string `flag:"cookie-domain" cfg:"cookie_domain" env:"GOOGLE_AUTH_PROXY_COOKIE_DOMAIN"` CookieDomain string `flag:"cookie-domain" cfg:"cookie_domain" env:"GOOGLE_AUTH_PROXY_COOKIE_DOMAIN"`

View File

@ -3,8 +3,21 @@ package main
import ( import (
"html/template" "html/template"
"log" "log"
"path"
) )
func loadTemplates(dir string) *template.Template {
if dir == "" {
return getTemplates()
}
log.Printf("using custom template directory %q", dir)
t, err := template.New("").ParseFiles(path.Join(dir, "sign_in.html"), path.Join(dir, "error.html"))
if err != nil {
log.Fatalf("failed parsing template %s", err)
}
return t
}
func getTemplates() *template.Template { func getTemplates() *template.Template {
t, err := template.New("foo").Parse(`{{define "sign_in.html"}} t, err := template.New("foo").Parse(`{{define "sign_in.html"}}
<!DOCTYPE html> <!DOCTYPE html>
@ -123,7 +136,7 @@ func getTemplates() *template.Template {
</html> </html>
{{end}}`) {{end}}`)
if err != nil { if err != nil {
log.Fatalf("failed parsing template %s", err.Error()) log.Fatalf("failed parsing template %s", err)
} }
t, err = t.Parse(`{{define "error.html"}} t, err = t.Parse(`{{define "error.html"}}
@ -141,7 +154,7 @@ func getTemplates() *template.Template {
</body> </body>
</html>{{end}}`) </html>{{end}}`)
if err != nil { if err != nil {
log.Fatalf("failed parsing template %s", err.Error()) log.Fatalf("failed parsing template %s", err)
} }
return t return t
} }