use claim mappings when retrieving user identity
Signed-off-by: Rui Yang <ruiya@vmware.com>
This commit is contained in:
		| @@ -28,10 +28,12 @@ type oauthConnector struct { | ||||
| 	authorizationURL     string | ||||
| 	userInfoURL          string | ||||
| 	scopes               []string | ||||
| 	groupsKey            string | ||||
| 	userIDKey            string | ||||
| 	userNameKey          string | ||||
| 	preferredUsernameKey string | ||||
| 	emailKey             string | ||||
| 	emailVerifiedKey     string | ||||
| 	groupsKey            string | ||||
| 	httpClient           *http.Client | ||||
| 	logger               log.Logger | ||||
| } | ||||
| @@ -41,36 +43,43 @@ type connectorData struct { | ||||
| } | ||||
|  | ||||
| type Config struct { | ||||
| 	ClientID             string   `json:"clientID"` | ||||
| 	ClientSecret         string   `json:"clientSecret"` | ||||
| 	RedirectURI          string   `json:"redirectURI"` | ||||
| 	TokenURL             string   `json:"tokenURL"` | ||||
| 	AuthorizationURL     string   `json:"authorizationURL"` | ||||
| 	UserInfoURL          string   `json:"userInfoURL"` | ||||
| 	Scopes               []string `json:"scopes"` | ||||
| 	GroupsKey            string   `json:"groupsKey"` | ||||
| 	UserIDKey            string   `json:"userIDKey"` | ||||
| 	UserNameKey          string   `json:"userNameKey"` | ||||
| 	PreferredUsernameKey string   `json:"preferredUsernameKey"` | ||||
| 	RootCAs              []string `json:"rootCAs"` | ||||
| 	InsecureSkipVerify   bool     `json:"insecureSkipVerify"` | ||||
| 	ClientID           string   `json:"clientID"` | ||||
| 	ClientSecret       string   `json:"clientSecret"` | ||||
| 	RedirectURI        string   `json:"redirectURI"` | ||||
| 	TokenURL           string   `json:"tokenURL"` | ||||
| 	AuthorizationURL   string   `json:"authorizationURL"` | ||||
| 	UserInfoURL        string   `json:"userInfoURL"` | ||||
| 	Scopes             []string `json:"scopes"` | ||||
| 	RootCAs            []string `json:"rootCAs"` | ||||
| 	InsecureSkipVerify bool     `json:"insecureSkipVerify"` | ||||
| 	UserIDKey          string   `json:"userIDKey"` // defaults to "id" | ||||
| 	ClaimMapping       struct { | ||||
| 		UserNameKey          string `json:"userNameKey"`          // defaults to "user_name" | ||||
| 		PreferredUsernameKey string `json:"preferredUsernameKey"` // defaults to "preferred_username" | ||||
| 		GroupsKey            string `json:"groupsKey"`            // defaults to "groups" | ||||
| 		EmailKey             string `json:"emailKey"`             // defaults to "email" | ||||
| 		EmailVerifiedKey     string `json:"emailVerifiedKey"`     // defaults to "email_verified" | ||||
| 	} `json:"claimMapping"` | ||||
| } | ||||
|  | ||||
| func (c *Config) Open(id string, logger log.Logger) (connector.Connector, error) { | ||||
| 	var err error | ||||
|  | ||||
| 	oauthConn := &oauthConnector{ | ||||
| 		clientID:         c.ClientID, | ||||
| 		clientSecret:     c.ClientSecret, | ||||
| 		tokenURL:         c.TokenURL, | ||||
| 		authorizationURL: c.AuthorizationURL, | ||||
| 		userInfoURL:      c.UserInfoURL, | ||||
| 		scopes:           c.Scopes, | ||||
| 		groupsKey:        c.GroupsKey, | ||||
| 		userIDKey:        c.UserIDKey, | ||||
| 		userNameKey:      c.UserNameKey, | ||||
| 		redirectURI:      c.RedirectURI, | ||||
| 		logger:           logger, | ||||
| 		clientID:             c.ClientID, | ||||
| 		clientSecret:         c.ClientSecret, | ||||
| 		tokenURL:             c.TokenURL, | ||||
| 		authorizationURL:     c.AuthorizationURL, | ||||
| 		userInfoURL:          c.UserInfoURL, | ||||
| 		scopes:               c.Scopes, | ||||
| 		redirectURI:          c.RedirectURI, | ||||
| 		logger:               logger, | ||||
| 		userIDKey:            c.UserIDKey, | ||||
| 		userNameKey:          c.ClaimMapping.UserNameKey, | ||||
| 		preferredUsernameKey: c.ClaimMapping.PreferredUsernameKey, | ||||
| 		groupsKey:            c.ClaimMapping.GroupsKey, | ||||
| 		emailKey:             c.ClaimMapping.EmailKey, | ||||
| 		emailVerifiedKey:     c.ClaimMapping.EmailVerifiedKey, | ||||
| 	} | ||||
|  | ||||
| 	oauthConn.httpClient, err = newHTTPClient(c.RootCAs, c.InsecureSkipVerify) | ||||
| @@ -173,26 +182,39 @@ func (c *oauthConnector) HandleCallback(s connector.Scopes, r *http.Request) (id | ||||
| 	} | ||||
|  | ||||
| 	if c.userIDKey == "" { | ||||
| 		c.userIDKey = "user_id" | ||||
| 		c.userIDKey = "id" | ||||
| 	} | ||||
|  | ||||
| 	userID, found := userInfoResult[c.userIDKey].(string) | ||||
| 	if !found { | ||||
| 		return identity, fmt.Errorf("OAuth Connector: not found %v claim", c.userIDKey) | ||||
| 	} | ||||
|  | ||||
| 	identity.UserID = userID | ||||
| 	if c.userNameKey == "" { | ||||
| 		c.userNameKey = "user_name" | ||||
| 	} | ||||
|  | ||||
| 	if c.groupsKey == "" { | ||||
| 		c.groupsKey = "groups" | ||||
| 	} | ||||
|  | ||||
| 	if c.preferredUsernameKey == "" { | ||||
| 		c.preferredUsernameKey = "preferred_username" | ||||
| 	} | ||||
|  | ||||
| 	identity.UserID, _ = userInfoResult[c.userIDKey].(string) | ||||
| 	if c.groupsKey == "" { | ||||
| 		c.groupsKey = "groups" | ||||
| 	} | ||||
|  | ||||
| 	if c.emailKey == "" { | ||||
| 		c.emailKey = "email" | ||||
| 	} | ||||
|  | ||||
| 	if c.emailVerifiedKey == "" { | ||||
| 		c.emailVerifiedKey = "email_verified" | ||||
| 	} | ||||
|  | ||||
| 	identity.Username, _ = userInfoResult[c.userNameKey].(string) | ||||
| 	identity.PreferredUsername, _ = userInfoResult[c.preferredUsernameKey].(string) | ||||
| 	identity.Email, _ = userInfoResult["email"].(string) | ||||
| 	identity.EmailVerified, _ = userInfoResult["email_verified"].(bool) | ||||
| 	identity.Email, _ = userInfoResult[c.emailKey].(string) | ||||
| 	identity.EmailVerified, _ = userInfoResult[c.emailVerifiedKey].(bool) | ||||
|  | ||||
| 	if s.Groups { | ||||
| 		groups := map[string]bool{} | ||||
|   | ||||
| @@ -75,8 +75,8 @@ func TestHandleCallBackForGroupsInUserInfo(t *testing.T) { | ||||
| 		"user_id_key":        "test-user-id", | ||||
| 		"user_name_key":      "test-username", | ||||
| 		"preferred_username": "test-preferred-username", | ||||
| 		"email":              "test-email", | ||||
| 		"email_verified":     true, | ||||
| 		"mail":               "mod_mail", | ||||
| 		"has_verified_email": false, | ||||
| 		"groups_key":         []string{"admin-group", "user-group"}, | ||||
| 	} | ||||
|  | ||||
| @@ -96,8 +96,8 @@ func TestHandleCallBackForGroupsInUserInfo(t *testing.T) { | ||||
| 	assert.Equal(t, identity.UserID, "test-user-id") | ||||
| 	assert.Equal(t, identity.Username, "test-username") | ||||
| 	assert.Equal(t, identity.PreferredUsername, "test-preferred-username") | ||||
| 	assert.Equal(t, identity.Email, "test-email") | ||||
| 	assert.Equal(t, identity.EmailVerified, true) | ||||
| 	assert.Equal(t, identity.Email, "mod_mail") | ||||
| 	assert.Equal(t, identity.EmailVerified, false) | ||||
| } | ||||
|  | ||||
| func TestHandleCallBackForGroupsInToken(t *testing.T) { | ||||
| @@ -128,8 +128,8 @@ func TestHandleCallBackForGroupsInToken(t *testing.T) { | ||||
| 	assert.Equal(t, identity.PreferredUsername, "test-preferred-username") | ||||
| 	assert.Equal(t, identity.UserID, "test-user-id") | ||||
| 	assert.Equal(t, identity.Username, "test-username") | ||||
| 	assert.Equal(t, identity.Email, "test-email") | ||||
| 	assert.Equal(t, identity.EmailVerified, true) | ||||
| 	assert.Equal(t, identity.Email, "") | ||||
| 	assert.Equal(t, identity.EmailVerified, false) | ||||
| } | ||||
|  | ||||
| func testSetup(t *testing.T, tokenClaims map[string]interface{}, userInfoClaims map[string]interface{}) *httptest.Server { | ||||
| @@ -198,11 +198,14 @@ func newConnector(t *testing.T, serverURL string) *oauthConnector { | ||||
| 		AuthorizationURL: serverURL + "/authorize", | ||||
| 		UserInfoURL:      serverURL + "/userinfo", | ||||
| 		Scopes:           []string{"openid", "groups"}, | ||||
| 		GroupsKey:        "groups_key", | ||||
| 		UserIDKey:        "user_id_key", | ||||
| 		UserNameKey:      "user_name_key", | ||||
| 	} | ||||
|  | ||||
| 	testConfig.ClaimMapping.UserNameKey = "user_name_key" | ||||
| 	testConfig.ClaimMapping.GroupsKey = "groups_key" | ||||
| 	testConfig.ClaimMapping.EmailKey = "mail" | ||||
| 	testConfig.ClaimMapping.EmailVerifiedKey = "has_verified_email" | ||||
|  | ||||
| 	log := logrus.New() | ||||
|  | ||||
| 	conn, err := testConfig.Open("id", log) | ||||
|   | ||||
		Reference in New Issue
	
	Block a user