|
@@ -5,6 +5,7 @@ import (
|
|
"io/ioutil"
|
|
"io/ioutil"
|
|
"log"
|
|
"log"
|
|
"net/http"
|
|
"net/http"
|
|
|
|
+ "strconv"
|
|
"time"
|
|
"time"
|
|
|
|
|
|
"golang.org/x/oauth2"
|
|
"golang.org/x/oauth2"
|
|
@@ -12,6 +13,7 @@ import (
|
|
auth "imuslab.com/arozos/mod/auth"
|
|
auth "imuslab.com/arozos/mod/auth"
|
|
syncdb "imuslab.com/arozos/mod/auth/oauth2/syncdb"
|
|
syncdb "imuslab.com/arozos/mod/auth/oauth2/syncdb"
|
|
reg "imuslab.com/arozos/mod/auth/register"
|
|
reg "imuslab.com/arozos/mod/auth/register"
|
|
|
|
+ db "imuslab.com/arozos/mod/database"
|
|
)
|
|
)
|
|
|
|
|
|
type OauthHandler struct {
|
|
type OauthHandler struct {
|
|
@@ -21,6 +23,8 @@ type OauthHandler struct {
|
|
DefaultUserGroup string
|
|
DefaultUserGroup string
|
|
ag *auth.AuthAgent
|
|
ag *auth.AuthAgent
|
|
reg *reg.RegisterHandler
|
|
reg *reg.RegisterHandler
|
|
|
|
+ coredb *db.Database
|
|
|
|
+ config *Config
|
|
}
|
|
}
|
|
|
|
|
|
type GoogleField struct {
|
|
type GoogleField struct {
|
|
@@ -34,22 +38,37 @@ type GoogleField struct {
|
|
Locale string `json:"locale"`
|
|
Locale string `json:"locale"`
|
|
}
|
|
}
|
|
|
|
|
|
|
|
+type Config struct {
|
|
|
|
+ Enabled bool `json:"enabled"`
|
|
|
|
+ IDP string `json:"idp"`
|
|
|
|
+ RedirectURL string `json:"redirect_url"`
|
|
|
|
+ ClientID string `json:"client_id"`
|
|
|
|
+ ClientSecret string `json:"client_secret"`
|
|
|
|
+ DefaultUserGroup string `json:"default_user_group"`
|
|
|
|
+}
|
|
|
|
+
|
|
//NewOauthHandler xxx
|
|
//NewOauthHandler xxx
|
|
-func NewOauthHandler(authAgent *auth.AuthAgent, register *reg.RegisterHandler) *OauthHandler {
|
|
|
|
|
|
+func NewOauthHandler(authAgent *auth.AuthAgent, register *reg.RegisterHandler, coreDb *db.Database) *OauthHandler {
|
|
|
|
+ err := coreDb.NewTable("oauth")
|
|
|
|
+ if err != nil {
|
|
|
|
+ log.Println("Failed to create oauth database. Terminating.")
|
|
|
|
+ panic(err)
|
|
|
|
+ }
|
|
|
|
+
|
|
NewlyCreatedOauthHandler := OauthHandler{
|
|
NewlyCreatedOauthHandler := OauthHandler{
|
|
googleOauthConfig: &oauth2.Config{
|
|
googleOauthConfig: &oauth2.Config{
|
|
- RedirectURL: "http://localhost:8080/system/auth/oauth/authorize",
|
|
|
|
- ClientID: "682431817920-nkmfn7m6uq0qbdo00hr2944m6r3hj8ua.apps.googleusercontent.com",
|
|
|
|
- ClientSecret: "Obdlr2S5n8rj_qwsPLhToD3h",
|
|
|
|
|
|
+ RedirectURL: readSingleConfig("redirecturl", coreDb) + "/system/auth/oauth/authorize",
|
|
|
|
+ ClientID: readSingleConfig("clientid", coreDb),
|
|
|
|
+ ClientSecret: readSingleConfig("clientsecret", coreDb),
|
|
Scopes: []string{"https://www.googleapis.com/auth/userinfo.profile",
|
|
Scopes: []string{"https://www.googleapis.com/auth/userinfo.profile",
|
|
"https://www.googleapis.com/auth/userinfo.email"},
|
|
"https://www.googleapis.com/auth/userinfo.email"},
|
|
Endpoint: google.Endpoint,
|
|
Endpoint: google.Endpoint,
|
|
},
|
|
},
|
|
- // Some random string, random for each request
|
|
|
|
- DefaultUserGroup: "default",
|
|
|
|
|
|
+ DefaultUserGroup: readSingleConfig("defaultusergroup", coreDb),
|
|
ag: authAgent,
|
|
ag: authAgent,
|
|
syncDb: syncdb.NewSyncDB(),
|
|
syncDb: syncdb.NewSyncDB(),
|
|
reg: register,
|
|
reg: register,
|
|
|
|
+ coredb: coreDb,
|
|
}
|
|
}
|
|
|
|
|
|
return &NewlyCreatedOauthHandler
|
|
return &NewlyCreatedOauthHandler
|
|
@@ -76,22 +95,19 @@ func (oh *OauthHandler) HandleAuthorize(w http.ResponseWriter, r *http.Request)
|
|
//read the uuid(aka the state parameter)
|
|
//read the uuid(aka the state parameter)
|
|
uuid, err := r.Cookie("uuid_login")
|
|
uuid, err := r.Cookie("uuid_login")
|
|
if err != nil {
|
|
if err != nil {
|
|
- w.Header().Set("Content-Type", "text/html; charset=UTF-8")
|
|
|
|
- w.Write([]byte("Invalid redirect URI."))
|
|
|
|
|
|
+ sendTextResponse(w, "Invalid redirect URI.")
|
|
}
|
|
}
|
|
|
|
|
|
state := r.FormValue("state")
|
|
state := r.FormValue("state")
|
|
if state != uuid.Value {
|
|
if state != uuid.Value {
|
|
- w.Header().Set("Content-Type", "text/html; charset=UTF-8")
|
|
|
|
- w.Write([]byte("Invalid oauth state."))
|
|
|
|
|
|
+ sendTextResponse(w, "Invalid oauth state.")
|
|
return
|
|
return
|
|
}
|
|
}
|
|
|
|
|
|
code := r.FormValue("code")
|
|
code := r.FormValue("code")
|
|
token, err := oh.googleOauthConfig.Exchange(oauth2.NoContext, code)
|
|
token, err := oh.googleOauthConfig.Exchange(oauth2.NoContext, code)
|
|
if err != nil {
|
|
if err != nil {
|
|
- w.Header().Set("Content-Type", "text/html; charset=UTF-8")
|
|
|
|
- w.Write([]byte("Code exchange failed."))
|
|
|
|
|
|
+ sendTextResponse(w, "Code exchange failed.")
|
|
return
|
|
return
|
|
}
|
|
}
|
|
|
|
|
|
@@ -108,8 +124,7 @@ func (oh *OauthHandler) HandleAuthorize(w http.ResponseWriter, r *http.Request)
|
|
if oh.reg.AllowRegistry {
|
|
if oh.reg.AllowRegistry {
|
|
http.Redirect(w, r, "/public/register/register.system?user="+data.Email, 302)
|
|
http.Redirect(w, r, "/public/register/register.system?user="+data.Email, 302)
|
|
} else {
|
|
} else {
|
|
- w.Header().Set("Content-Type", "text/html; charset=UTF-8")
|
|
|
|
- w.Write([]byte("You are not allowed to register in this system. <a href=\"/\">Back</a>"))
|
|
|
|
|
|
+ sendTextResponse(w, "You are not allowed to register in this system. <a href=\"/\">Back</a>")
|
|
}
|
|
}
|
|
} else {
|
|
} else {
|
|
log.Println(data.Email + " logged in via OAuth.")
|
|
log.Println(data.Email + " logged in via OAuth.")
|
|
@@ -125,7 +140,11 @@ func (oh *OauthHandler) HandleAuthorize(w http.ResponseWriter, r *http.Request)
|
|
}
|
|
}
|
|
|
|
|
|
func (oh *OauthHandler) CheckOAuth(w http.ResponseWriter, r *http.Request) {
|
|
func (oh *OauthHandler) CheckOAuth(w http.ResponseWriter, r *http.Request) {
|
|
- sendJSONResponse(w, "true")
|
|
|
|
|
|
+ enabled := oh.readSingleConfig("enabled")
|
|
|
|
+ if enabled == "" {
|
|
|
|
+ enabled = "false"
|
|
|
|
+ }
|
|
|
|
+ sendJSONResponse(w, enabled)
|
|
}
|
|
}
|
|
|
|
|
|
//https://golangcode.com/add-a-http-cookie/
|
|
//https://golangcode.com/add-a-http-cookie/
|
|
@@ -138,3 +157,90 @@ func (oh *OauthHandler) addCookie(w http.ResponseWriter, name, value string, ttl
|
|
}
|
|
}
|
|
http.SetCookie(w, &cookie)
|
|
http.SetCookie(w, &cookie)
|
|
}
|
|
}
|
|
|
|
+
|
|
|
|
+func (oh *OauthHandler) ReadConfig(w http.ResponseWriter, r *http.Request) {
|
|
|
|
+ enabled, _ := strconv.ParseBool(oh.readSingleConfig("enabled"))
|
|
|
|
+ idp := oh.readSingleConfig("idp")
|
|
|
|
+ redirecturl := oh.readSingleConfig("redirecturl")
|
|
|
|
+ clientid := oh.readSingleConfig("clientid")
|
|
|
|
+ clientsecret := oh.readSingleConfig("clientsecret")
|
|
|
|
+ defaultusergroup := oh.readSingleConfig("defaultusergroup")
|
|
|
|
+
|
|
|
|
+ config, err := json.Marshal(Config{
|
|
|
|
+ Enabled: enabled,
|
|
|
|
+ IDP: idp,
|
|
|
|
+ RedirectURL: redirecturl,
|
|
|
|
+ ClientID: clientid,
|
|
|
|
+ ClientSecret: clientsecret,
|
|
|
|
+ DefaultUserGroup: defaultusergroup,
|
|
|
|
+ })
|
|
|
|
+ if err != nil {
|
|
|
|
+ empty, _ := json.Marshal(Config{})
|
|
|
|
+ sendJSONResponse(w, string(empty))
|
|
|
|
+ }
|
|
|
|
+ sendJSONResponse(w, string(config))
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+func (oh *OauthHandler) WriteConfig(w http.ResponseWriter, r *http.Request) {
|
|
|
|
+ enabled, err := mv(r, "enabled", true)
|
|
|
|
+ if err != nil {
|
|
|
|
+ sendTextResponse(w, "enabled field can't be empty'")
|
|
|
|
+ }
|
|
|
|
+ idp, err := mv(r, "idp", true)
|
|
|
|
+ if err != nil {
|
|
|
|
+ sendTextResponse(w, "idp field can't be empty'")
|
|
|
|
+ }
|
|
|
|
+ redirecturl, err := mv(r, "redirecturl", true)
|
|
|
|
+ if err != nil {
|
|
|
|
+ sendTextResponse(w, "redirecturl field can't be empty'")
|
|
|
|
+ }
|
|
|
|
+ clientid, err := mv(r, "clientid", true)
|
|
|
|
+ if err != nil {
|
|
|
|
+ sendTextResponse(w, "clientid field can't be empty'")
|
|
|
|
+ }
|
|
|
|
+ clientsecret, err := mv(r, "clientsecret", true)
|
|
|
|
+ if err != nil {
|
|
|
|
+ sendTextResponse(w, "clientsecret field can't be empty'")
|
|
|
|
+ }
|
|
|
|
+ defaultusergroup, err := mv(r, "defaultusergroup", true)
|
|
|
|
+ if err != nil {
|
|
|
|
+ sendTextResponse(w, "defaultusergroup field can't be empty'")
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ oh.coredb.Write("oauth", "enabled", enabled)
|
|
|
|
+ oh.coredb.Write("oauth", "idp", idp)
|
|
|
|
+ oh.coredb.Write("oauth", "redirecturl", redirecturl)
|
|
|
|
+ oh.coredb.Write("oauth", "clientid", clientid)
|
|
|
|
+ oh.coredb.Write("oauth", "clientsecret", clientsecret)
|
|
|
|
+ oh.coredb.Write("oauth", "defaultusergroup", defaultusergroup)
|
|
|
|
+
|
|
|
|
+ //update the information inside the oauth class
|
|
|
|
+ oh.googleOauthConfig = &oauth2.Config{
|
|
|
|
+ RedirectURL: oh.readSingleConfig("redirecturl") + "/system/auth/oauth/authorize",
|
|
|
|
+ ClientID: oh.readSingleConfig("clientid"),
|
|
|
|
+ ClientSecret: oh.readSingleConfig("clientsecret"),
|
|
|
|
+ Scopes: []string{"https://www.googleapis.com/auth/userinfo.profile",
|
|
|
|
+ "https://www.googleapis.com/auth/userinfo.email"},
|
|
|
|
+ Endpoint: google.Endpoint,
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ sendOK(w)
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+func (oh *OauthHandler) readSingleConfig(key string) string {
|
|
|
|
+ var value string
|
|
|
|
+ err := oh.coredb.Read("oauth", key, &value)
|
|
|
|
+ if err != nil {
|
|
|
|
+ value = ""
|
|
|
|
+ }
|
|
|
|
+ return value
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+func readSingleConfig(key string, coredb *db.Database) string {
|
|
|
|
+ var value string
|
|
|
|
+ err := coredb.Read("oauth", key, &value)
|
|
|
|
+ if err != nil {
|
|
|
|
+ value = ""
|
|
|
|
+ }
|
|
|
|
+ return value
|
|
|
|
+}
|