veyron/services/identity: Code cleanup
- Collapse multiple options into a single, more understandable one
- Remove some dead code
- Get rid of "--generate" and "--identity" flags from identityd
so that we don't have multiple programs that can generate identities.
Change-Id: I9e34e96708450e40bb43ea8a086523dd963ca304
diff --git a/services/identity/googleoauth/handler.go b/services/identity/googleoauth/handler.go
index 2ce6fee..6ddc455 100644
--- a/services/identity/googleoauth/handler.go
+++ b/services/identity/googleoauth/handler.go
@@ -26,14 +26,11 @@
)
type HandlerArgs struct {
- // Whether the HTTP server is using TLS or not.
- UseTLS bool
- // Fully-qualified address (host:port) that the HTTP server is
- // listening on (and where redirect requests from Google will come to).
+ // URL at which the hander is installed.
+ // e.g. http://host:port/google/
+ // This is where the handler is installed and where redirect requests
+ // from Google will come to.
Addr string
- // Address prefix (including trailing slash) on which the Google OAuth
- // based Identity generator should run.
- Prefix string
// client_id and client_secret registered with the Google Developer
// Console for API access.
ClientID, ClientSecret string
@@ -47,24 +44,19 @@
RestrictEmailDomain string
}
-func (a *HandlerArgs) redirectURL() string {
- scheme := "http"
- if a.UseTLS {
- scheme = "https"
- }
- return fmt.Sprintf("%s://%s%soauth2callback", scheme, a.Addr, a.Prefix)
-}
+func (a *HandlerArgs) redirectURL() string { return path.Join(a.Addr, "oauth2callback") }
-// URL used to verify GoogleIDTokens.
-// (From https://developers.google.com/accounts/docs/OAuth2Login#validatinganidtoken)
-const VerifyURL = "https://www.googleapis.com/oauth2/v1/tokeninfo?id_token="
+// URL used to verify google tokens.
+// (From https://developers.google.com/accounts/docs/OAuth2Login#validatinganidtoken
+// and https://developers.google.com/accounts/docs/OAuth2UserAgent#validatetoken)
+const verifyURL = "https://www.googleapis.com/oauth2/v1/tokeninfo?"
-// NewHandler returns an http.Handler that expects to be rooted at args.Prefix
+// NewHandler returns an http.Handler that expects to be rooted at args.Addr
// and can be used to use OAuth 2.0 to authenticate with Google, mint a new
// identity and bless it with the Google email address.
func NewHandler(args HandlerArgs) http.Handler {
config := NewOAuthConfig(args.ClientID, args.ClientSecret, args.redirectURL())
- return &handler{config, args.Addr, args.MinExpiryDays, util.NewCSRFCop(), args.Runtime, args.RestrictEmailDomain}
+ return &handler{config, args.MinExpiryDays, util.NewCSRFCop(), args.Runtime, args.RestrictEmailDomain}
}
// NewOAuthConfig returns the oauth.Config required for obtaining just the email address from Google using OAuth 2.0.
@@ -81,7 +73,6 @@
type handler struct {
config *oauth.Config
- issuer string
minExpiryDays int
csrfCop *util.CSRFCop
rt veyron2.Runtime
@@ -158,9 +149,9 @@
if t.Extra == nil || len(t.Extra["id_token"]) == 0 {
return "", fmt.Errorf("no GoogleIDToken found in OAuth token")
}
- tinfo, err := http.Get(VerifyURL + t.Extra["id_token"])
+ tinfo, err := http.Get(verifyURL + "id_token=" + t.Extra["id_token"])
if err != nil {
- return "", fmt.Errorf("failed to talk to GoogleIDToken verifier (%q): %v", VerifyURL, err)
+ return "", fmt.Errorf("failed to talk to GoogleIDToken verifier (%q): %v", verifyURL, err)
}
if tinfo.StatusCode != http.StatusOK {
return "", fmt.Errorf("failed to verify GoogleIDToken: %s", tinfo.Status)
diff --git a/services/identity/identityd/main.go b/services/identity/identityd/main.go
index ad17360..39d3b9d 100644
--- a/services/identity/identityd/main.go
+++ b/services/identity/identityd/main.go
@@ -15,7 +15,6 @@
"veyron/services/identity/blesser"
"veyron/services/identity/googleoauth"
"veyron/services/identity/handlers"
- "veyron/services/identity/util"
"veyron2"
"veyron2/ipc"
"veyron2/rt"
@@ -34,10 +33,7 @@
googleConfigWeb = flag.String("google_config_web", "", "Path to the JSON-encoded file containing the ClientID for web applications registered with the Google Developer Console. (Use the 'Download JSON' link on the Google APIs console).")
googleConfigInstalled = flag.String("google_config_installed", "", "Path to the JSON-encoded file containing the ClientID for installed applications registered with the Google Developer console. (Use the 'Download JSON' link on the Google APIs console).")
-
- googleDomain = flag.String("google_domain", "", "An optional domain name. When set, only email addresses from this domain are allowed to authenticate via Google OAuth")
- generate = flag.String("generate", "", "If non-empty, instead of running an HTTP server, a new identity will be created with the provided name and saved to --identity (if specified) and dumped to STDOUT in base64-encoded-vom")
- identity = flag.String("identity", "", "Path to the file where the VOM-encoded security.PrivateID created with --generate will be written.")
+ googleDomain = flag.String("google_domain", "", "An optional domain name. When set, only email addresses from this domain are allowed to authenticate via Google OAuth")
)
func main() {
@@ -46,11 +42,6 @@
r := rt.Init()
defer r.Cleanup()
- if len(*generate) > 0 {
- generateAndSaveIdentity()
- return
- }
-
// Setup handlers
http.Handle("/pubkey/", handlers.Object{r.Identity().PublicID().PublicKey()}) // public key of this identity server
if enableRandomHandler() {
@@ -68,15 +59,9 @@
defer ipcServer.Stop()
}
if enabled, clientID, clientSecret := enableGoogleOAuth(*googleConfigWeb); enabled {
- _, port, err := net.SplitHostPort(*httpaddr)
- if err != nil {
- vlog.Fatalf("Failed to parse %q: %v", *httpaddr, err)
- }
n := "/google/"
http.Handle(n, googleoauth.NewHandler(googleoauth.HandlerArgs{
- UseTLS: enableTLS(),
- Addr: fmt.Sprintf("%s:%s", *host, port),
- Prefix: n,
+ Addr: fmt.Sprintf("%s%s", httpaddress(), n),
ClientID: clientID,
ClientSecret: clientSecret,
MinExpiryDays: *minExpiryDays,
@@ -101,6 +86,7 @@
vlog.Info("Failed to render template:", err)
}
})
+ vlog.Infof("Running HTTP server at: %v", httpaddress())
go runHTTPServer(*httpaddr)
<-signals.ShutdownOnSignals()
}
@@ -144,7 +130,6 @@
func runHTTPServer(addr string) {
if !enableTLS() {
- vlog.Infof("Starting HTTP server (without TLS) at http://%v", addr)
if err := http.ListenAndServe(addr, nil); err != nil {
vlog.Fatalf("http.ListenAndServe failed: %v", err)
}
@@ -166,6 +151,10 @@
To generate TLS certificates so the HTTP server can use SSL:
go run $GOROOT/src/pkg/crypto/tls/generate_cert.go --host <IP address>
+To generate an identity for this service itself, use:
+go install veyron/tools/identity && ./bin/identity generate <name> ><filename>
+and set the VEYRON_IDENTITY environment variable when running this application.
+
To enable use of Google APIs to use Google OAuth for authorization, set --google_config,
which must point to the contents of a JSON file obtained after registering your application
with the Google Developer Console at:
@@ -186,33 +175,16 @@
return host
}
-func generateAndSaveIdentity() {
- id, err := rt.R().NewIdentity(*generate)
+func httpaddress() string {
+ _, port, err := net.SplitHostPort(*httpaddr)
if err != nil {
- vlog.Fatalf("Runtime.NewIdentity(%q) failed: %v", *generate, err)
+ vlog.Fatalf("Failed to parse %q: %v", *httpaddr, err)
}
- if len(*identity) > 0 {
- if err = saveIdentity(*identity, id); err != nil {
- vlog.Fatalf("SaveIdentity %v: %v", *identity, err)
- }
+ scheme := "http"
+ if enableTLS() {
+ scheme = "https"
}
- b64, err := util.Base64VomEncode(id)
- if err != nil {
- vlog.Fatalf("Base64VomEncode(%q) failed: %v", id, err)
- }
- fmt.Println(b64)
-}
-
-func saveIdentity(filePath string, id security.PrivateID) error {
- f, err := os.OpenFile(filePath, os.O_WRONLY, 0600)
- if err != nil {
- return err
- }
- defer f.Close()
- if err := security.SaveIdentity(f, id); err != nil {
- return err
- }
- return nil
+ return fmt.Sprintf("%s://%s:%v", scheme, *host, port)
}
var tmpl = template.Must(template.New("main").Parse(`<!doctype html>
diff --git a/tools/identity/main.go b/tools/identity/main.go
index 861d85f..bdc007f 100644
--- a/tools/identity/main.go
+++ b/tools/identity/main.go
@@ -219,7 +219,7 @@
if err != nil {
vlog.Infof("Failed to get blessing from %q: %v, will try again in %v", flagSeekBlessingFrom, err, wait)
time.Sleep(wait)
- if wait = wait + 2; wait > maxWait {
+ if wait = wait + 2*time.Second; wait > maxWait {
wait = maxWait
}
continue