From db812162407ddaff3c592b489285ffb769610745 Mon Sep 17 00:00:00 2001 From: Misi Date: Fri, 15 Dec 2023 12:09:17 +0100 Subject: [PATCH] Chore: Cleanup SocialBase + connectors and use the OAuthInfo (#79453) * Clean up SocialBase * Cleanup other connectors --- pkg/login/social/connectors/azuread_oauth.go | 10 ++-- pkg/login/social/connectors/common.go | 4 +- pkg/login/social/connectors/generic_oauth.go | 32 +++++------ .../social/connectors/generic_oauth_test.go | 12 ++-- pkg/login/social/connectors/github_oauth.go | 14 ++--- pkg/login/social/connectors/gitlab_oauth.go | 12 ++-- .../social/connectors/gitlab_oauth_test.go | 8 +-- pkg/login/social/connectors/google_oauth.go | 16 ++---- pkg/login/social/connectors/okta_oauth.go | 18 +++--- pkg/login/social/connectors/social_base.go | 57 +++++++------------ 10 files changed, 76 insertions(+), 107 deletions(-) diff --git a/pkg/login/social/connectors/azuread_oauth.go b/pkg/login/social/connectors/azuread_oauth.go index 30791bc74c2..3e8ccce19e5 100644 --- a/pkg/login/social/connectors/azuread_oauth.go +++ b/pkg/login/social/connectors/azuread_oauth.go @@ -143,11 +143,11 @@ func (s *SocialAzureAD) UserInfo(ctx context.Context, client *http.Client, token } var isGrafanaAdmin *bool = nil - if s.allowAssignGrafanaAdmin { + if s.info.AllowAssignGrafanaAdmin { isGrafanaAdmin = &grafanaAdmin } - if s.allowAssignGrafanaAdmin && s.info.SkipOrgRoleSync { + if s.info.AllowAssignGrafanaAdmin && s.info.SkipOrgRoleSync { s.log.Debug("AllowAssignGrafanaAdmin and skipOrgRoleSync are both set, Grafana Admin role will not be synced, consider setting one or the other") } @@ -246,7 +246,7 @@ func (claims *azureClaims) extractEmail() string { // extractRoleAndAdmin extracts the role from the claims and returns the role and whether the user is a Grafana admin. func (s *SocialAzureAD) extractRoleAndAdmin(claims *azureClaims) (org.RoleType, bool, error) { if len(claims.Roles) == 0 { - if s.roleAttributeStrict { + if s.info.RoleAttributeStrict { return "", false, errRoleAttributeStrictViolation.Errorf("AzureAD OAuth: unset role") } return s.defaultRole(), false, nil @@ -264,7 +264,7 @@ func (s *SocialAzureAD) extractRoleAndAdmin(claims *azureClaims) (org.RoleType, } } - if s.roleAttributeStrict { + if s.info.RoleAttributeStrict { return "", false, errRoleAttributeStrictViolation.Errorf("AzureAD OAuth: idP did not return a valid role %q", claims.Roles) } @@ -390,7 +390,7 @@ func (s *SocialAzureAD) groupsGraphAPIURL(claims *azureClaims, token *oauth2.Tok func (s *SocialAzureAD) SupportBundleContent(bf *bytes.Buffer) error { bf.WriteString("## AzureAD specific configuration\n\n") bf.WriteString("```ini\n") - bf.WriteString(fmt.Sprintf("allowed_groups = %v\n", s.allowedGroups)) + bf.WriteString(fmt.Sprintf("allowed_groups = %v\n", s.info.AllowedGroups)) bf.WriteString(fmt.Sprintf("forceUseGraphAPI = %v\n", s.forceUseGraphAPI)) bf.WriteString("```\n\n") diff --git a/pkg/login/social/connectors/common.go b/pkg/login/social/connectors/common.go index a4452080c9e..d9700dc6860 100644 --- a/pkg/login/social/connectors/common.go +++ b/pkg/login/social/connectors/common.go @@ -38,11 +38,11 @@ type httpGetResponse struct { } func (s *SocialBase) IsEmailAllowed(email string) bool { - return isEmailAllowed(email, s.allowedDomains) + return isEmailAllowed(email, s.info.AllowedDomains) } func (s *SocialBase) IsSignupAllowed() bool { - return s.allowSignup + return s.info.AllowSignup } func isEmailAllowed(email string, allowedDomains []string) bool { diff --git a/pkg/login/social/connectors/generic_oauth.go b/pkg/login/social/connectors/generic_oauth.go index 800ffabe1a6..6728c54f52a 100644 --- a/pkg/login/social/connectors/generic_oauth.go +++ b/pkg/login/social/connectors/generic_oauth.go @@ -34,7 +34,6 @@ var _ ssosettings.Reloadable = (*SocialGenericOAuth)(nil) type SocialGenericOAuth struct { *SocialBase allowedOrganizations []string - apiUrl string teamsUrl string emailAttributeName string emailAttributePath string @@ -44,14 +43,12 @@ type SocialGenericOAuth struct { idTokenAttributeName string teamIdsAttributePath string teamIds []string - allowedGroups []string } func NewGenericOAuthProvider(info *social.OAuthInfo, cfg *setting.Cfg, ssoSettings ssosettings.Service, features *featuremgmt.FeatureManager) *SocialGenericOAuth { config := createOAuthConfig(info, cfg, social.GenericOAuthProviderName) provider := &SocialGenericOAuth{ SocialBase: newSocialBase(social.GenericOAuthProviderName, config, info, cfg.AutoAssignOrgRole, *features), - apiUrl: info.ApiUrl, teamsUrl: info.TeamsUrl, emailAttributeName: info.EmailAttributeName, emailAttributePath: info.EmailAttributePath, @@ -62,7 +59,6 @@ func NewGenericOAuthProvider(info *social.OAuthInfo, cfg *setting.Cfg, ssoSettin teamIdsAttributePath: info.TeamIdsAttributePath, teamIds: util.SplitString(info.Extra[teamIdsKey]), allowedOrganizations: util.SplitString(info.Extra[allowedOrganizationsKey]), - allowedGroups: info.AllowedGroups, } if features.IsEnabledGlobally(featuremgmt.FlagSsoSettingsApi) { @@ -82,11 +78,11 @@ func (s *SocialGenericOAuth) Reload(ctx context.Context, settings ssoModels.SSOS // TODOD: remove this in the next PR and use the isGroupMember from social.go func (s *SocialGenericOAuth) IsGroupMember(groups []string) bool { - if len(s.allowedGroups) == 0 { + if len(s.info.AllowedGroups) == 0 { return true } - for _, allowedGroup := range s.allowedGroups { + for _, allowedGroup := range s.info.AllowedGroups { for _, group := range groups { if group == allowedGroup { return true @@ -198,7 +194,7 @@ func (s *SocialGenericOAuth) UserInfo(ctx context.Context, client *http.Client, s.log.Warn("Failed to extract role", "err", err) } else { userInfo.Role = role - if s.allowAssignGrafanaAdmin { + if s.info.AllowAssignGrafanaAdmin { userInfo.IsGrafanaAdmin = &grafanaAdmin } } @@ -216,13 +212,13 @@ func (s *SocialGenericOAuth) UserInfo(ctx context.Context, client *http.Client, } if userInfo.Role == "" && !s.info.SkipOrgRoleSync { - if s.roleAttributeStrict { + if s.info.RoleAttributeStrict { return nil, errRoleAttributeStrictViolation.Errorf("idP did not return a role attribute") } userInfo.Role = s.defaultRole() } - if s.allowAssignGrafanaAdmin && s.info.SkipOrgRoleSync { + if s.info.AllowAssignGrafanaAdmin && s.info.SkipOrgRoleSync { s.log.Debug("AllowAssignGrafanaAdmin and skipOrgRoleSync are both set, Grafana Admin role will not be synced, consider setting one or the other") } @@ -295,14 +291,14 @@ func (s *SocialGenericOAuth) extractFromToken(token *oauth2.Token) *UserInfoJson func (s *SocialGenericOAuth) extractFromAPI(ctx context.Context, client *http.Client) *UserInfoJson { s.log.Debug("Getting user info from API") - if s.apiUrl == "" { + if s.info.ApiUrl == "" { s.log.Debug("No api url configured") return nil } - rawUserInfoResponse, err := s.httpGet(ctx, client, s.apiUrl) + rawUserInfoResponse, err := s.httpGet(ctx, client, s.info.ApiUrl) if err != nil { - s.log.Debug("Error getting user info from API", "url", s.apiUrl, "error", err) + s.log.Debug("Error getting user info from API", "url", s.info.ApiUrl, "error", err) return nil } @@ -418,9 +414,9 @@ func (s *SocialGenericOAuth) FetchPrivateEmail(ctx context.Context, client *http IsConfirmed bool `json:"is_confirmed"` } - response, err := s.httpGet(ctx, client, fmt.Sprintf(s.apiUrl+"/emails")) + response, err := s.httpGet(ctx, client, fmt.Sprintf(s.info.ApiUrl+"/emails")) if err != nil { - s.log.Error("Error getting email address", "url", s.apiUrl+"/emails", "error", err) + s.log.Error("Error getting email address", "url", s.info.ApiUrl+"/emails", "error", err) return "", fmt.Errorf("%v: %w", "Error getting email address", err) } @@ -480,9 +476,9 @@ func (s *SocialGenericOAuth) fetchTeamMembershipsFromDeprecatedTeamsUrl(ctx cont Id int `json:"id"` } - response, err := s.httpGet(ctx, client, fmt.Sprintf(s.apiUrl+"/teams")) + response, err := s.httpGet(ctx, client, fmt.Sprintf(s.info.ApiUrl+"/teams")) if err != nil { - s.log.Error("Error getting team memberships", "url", s.apiUrl+"/teams", "error", err) + s.log.Error("Error getting team memberships", "url", s.info.ApiUrl+"/teams", "error", err) return []string{}, err } @@ -521,9 +517,9 @@ func (s *SocialGenericOAuth) FetchOrganizations(ctx context.Context, client *htt Login string `json:"login"` } - response, err := s.httpGet(ctx, client, fmt.Sprintf(s.apiUrl+"/orgs")) + response, err := s.httpGet(ctx, client, fmt.Sprintf(s.info.ApiUrl+"/orgs")) if err != nil { - s.log.Error("Error getting organizations", "url", s.apiUrl+"/orgs", "error", err) + s.log.Error("Error getting organizations", "url", s.info.ApiUrl+"/orgs", "error", err) return nil, false } diff --git a/pkg/login/social/connectors/generic_oauth_test.go b/pkg/login/social/connectors/generic_oauth_test.go index e0d3df51aad..dbb5d482c06 100644 --- a/pkg/login/social/connectors/generic_oauth_test.go +++ b/pkg/login/social/connectors/generic_oauth_test.go @@ -207,7 +207,7 @@ func TestSearchJSONForRole(t *testing.T) { } for _, test := range tests { - provider.roleAttributePath = test.RoleAttributePath + provider.info.RoleAttributePath = test.RoleAttributePath t.Run(test.Name, func(t *testing.T) { actualResult, err := provider.searchJSONForStringAttr(test.RoleAttributePath, test.UserInfoJSONResponse) if test.ExpectedError == "" { @@ -453,8 +453,8 @@ func TestUserInfoSearchesForEmailAndRole(t *testing.T) { } for _, test := range tests { - provider.roleAttributePath = test.RoleAttributePath - provider.allowAssignGrafanaAdmin = test.AllowAssignGrafanaAdmin + provider.info.RoleAttributePath = test.RoleAttributePath + provider.info.AllowAssignGrafanaAdmin = test.AllowAssignGrafanaAdmin provider.info.SkipOrgRoleSync = test.SkipOrgRoleSync t.Run(test.Name, func(t *testing.T) { @@ -466,7 +466,7 @@ func TestUserInfoSearchesForEmailAndRole(t *testing.T) { _, err = w.Write(body) require.NoError(t, err) })) - provider.apiUrl = ts.URL + provider.info.ApiUrl = ts.URL staticToken := oauth2.Token{ AccessToken: "", TokenType: "", @@ -566,7 +566,7 @@ func TestUserInfoSearchesForLogin(t *testing.T) { _, err = w.Write(body) require.NoError(t, err) })) - provider.apiUrl = ts.URL + provider.info.ApiUrl = ts.URL staticToken := oauth2.Token{ AccessToken: "", TokenType: "", @@ -663,7 +663,7 @@ func TestUserInfoSearchesForName(t *testing.T) { _, err = w.Write(body) require.NoError(t, err) })) - provider.apiUrl = ts.URL + provider.info.ApiUrl = ts.URL staticToken := oauth2.Token{ AccessToken: "", TokenType: "", diff --git a/pkg/login/social/connectors/github_oauth.go b/pkg/login/social/connectors/github_oauth.go index bd8296d1c35..7506f21348d 100644 --- a/pkg/login/social/connectors/github_oauth.go +++ b/pkg/login/social/connectors/github_oauth.go @@ -30,7 +30,6 @@ var _ ssosettings.Reloadable = (*SocialGithub)(nil) type SocialGithub struct { *SocialBase allowedOrganizations []string - apiUrl string teamIds []int } @@ -61,7 +60,6 @@ func NewGitHubProvider(info *social.OAuthInfo, cfg *setting.Cfg, ssoSettings sso config := createOAuthConfig(info, cfg, social.GitHubProviderName) provider := &SocialGithub{ SocialBase: newSocialBase(social.GitHubProviderName, config, info, cfg.AutoAssignOrgRole, *features), - apiUrl: info.ApiUrl, teamIds: teamIds, allowedOrganizations: util.SplitString(info.Extra[allowedOrganizationsKey]), } @@ -135,7 +133,7 @@ func (s *SocialGithub) FetchPrivateEmail(ctx context.Context, client *http.Clien Verified bool `json:"verified"` } - response, err := s.httpGet(ctx, client, fmt.Sprintf(s.apiUrl+"/emails")) + response, err := s.httpGet(ctx, client, fmt.Sprintf(s.info.ApiUrl+"/emails")) if err != nil { return "", fmt.Errorf("Error getting email address: %s", err) } @@ -158,7 +156,7 @@ func (s *SocialGithub) FetchPrivateEmail(ctx context.Context, client *http.Clien } func (s *SocialGithub) FetchTeamMemberships(ctx context.Context, client *http.Client) ([]GithubTeam, error) { - url := fmt.Sprintf(s.apiUrl + "/teams?per_page=100") + url := fmt.Sprintf(s.info.ApiUrl + "/teams?per_page=100") hasMore := true teams := make([]GithubTeam, 0) @@ -240,7 +238,7 @@ func (s *SocialGithub) UserInfo(ctx context.Context, client *http.Client, token Name string `json:"name"` } - response, err := s.httpGet(ctx, client, s.apiUrl) + response, err := s.httpGet(ctx, client, s.info.ApiUrl) if err != nil { return nil, fmt.Errorf("error getting user info: %s", err) } @@ -266,13 +264,13 @@ func (s *SocialGithub) UserInfo(ctx context.Context, client *http.Client, token return nil, err } - if s.allowAssignGrafanaAdmin { + if s.info.AllowAssignGrafanaAdmin { isGrafanaAdmin = &grafanaAdmin } } // we skip allowing assignment of GrafanaAdmin if skipOrgRoleSync is present - if s.allowAssignGrafanaAdmin && s.info.SkipOrgRoleSync { + if s.info.AllowAssignGrafanaAdmin && s.info.SkipOrgRoleSync { s.log.Debug("AllowAssignGrafanaAdmin and skipOrgRoleSync are both set, Grafana Admin role will not be synced, consider setting one or the other") } @@ -289,7 +287,7 @@ func (s *SocialGithub) UserInfo(ctx context.Context, client *http.Client, token userInfo.Name = data.Name } - organizationsUrl := fmt.Sprintf(s.apiUrl + "/orgs?per_page=100") + organizationsUrl := fmt.Sprintf(s.info.ApiUrl + "/orgs?per_page=100") if !s.IsTeamMember(ctx, client) { return nil, ErrMissingTeamMembership.Errorf("User is not a member of any of the allowed teams: %v", s.teamIds) diff --git a/pkg/login/social/connectors/gitlab_oauth.go b/pkg/login/social/connectors/gitlab_oauth.go index 6d09e8c7b57..2bce4283bb4 100644 --- a/pkg/login/social/connectors/gitlab_oauth.go +++ b/pkg/login/social/connectors/gitlab_oauth.go @@ -29,7 +29,6 @@ var _ ssosettings.Reloadable = (*SocialGitlab)(nil) type SocialGitlab struct { *SocialBase - apiUrl string } type apiData struct { @@ -57,7 +56,6 @@ func NewGitLabProvider(info *social.OAuthInfo, cfg *setting.Cfg, ssoSettings sso config := createOAuthConfig(info, cfg, social.GitlabProviderName) provider := &SocialGitlab{ SocialBase: newSocialBase(social.GitlabProviderName, config, info, cfg.AutoAssignOrgRole, *features), - apiUrl: info.ApiUrl, } if features.IsEnabledGlobally(featuremgmt.FlagSsoSettingsApi) { @@ -94,7 +92,7 @@ func (s *SocialGitlab) getGroupsPage(ctx context.Context, client *http.Client, n FullPath string `json:"full_path"` } - groupURL, err := url.JoinPath(s.apiUrl, "/groups") + groupURL, err := url.JoinPath(s.info.ApiUrl, "/groups") if err != nil { s.log.Error("Error joining GitLab API URL", "err", err) return nil, nil @@ -183,7 +181,7 @@ func (s *SocialGitlab) UserInfo(ctx context.Context, client *http.Client, token return nil, errMissingGroupMembership } - if s.allowAssignGrafanaAdmin && s.info.SkipOrgRoleSync { + if s.info.AllowAssignGrafanaAdmin && s.info.SkipOrgRoleSync { s.log.Debug("AllowAssignGrafanaAdmin and skipOrgRoleSync are both set, Grafana Admin role will not be synced, consider setting one or the other") } @@ -196,7 +194,7 @@ func (s *SocialGitlab) GetOAuthInfo() *social.OAuthInfo { func (s *SocialGitlab) extractFromAPI(ctx context.Context, client *http.Client, token *oauth2.Token) (*userData, error) { apiResp := &apiData{} - response, err := s.httpGet(ctx, client, s.apiUrl+"/user") + response, err := s.httpGet(ctx, client, s.info.ApiUrl+"/user") if err != nil { return nil, fmt.Errorf("Error getting user info: %w", err) } @@ -229,7 +227,7 @@ func (s *SocialGitlab) extractFromAPI(ctx context.Context, client *http.Client, return nil, err } - if s.allowAssignGrafanaAdmin { + if s.info.AllowAssignGrafanaAdmin { idData.IsGrafanaAdmin = &grafanaAdmin } @@ -285,7 +283,7 @@ func (s *SocialGitlab) extractFromToken(ctx context.Context, client *http.Client return nil, errRole } - if s.allowAssignGrafanaAdmin { + if s.info.AllowAssignGrafanaAdmin { data.IsGrafanaAdmin = &grafanaAdmin } diff --git a/pkg/login/social/connectors/gitlab_oauth_test.go b/pkg/login/social/connectors/gitlab_oauth_test.go index 14271f72cea..3c068cb01b8 100644 --- a/pkg/login/social/connectors/gitlab_oauth_test.go +++ b/pkg/login/social/connectors/gitlab_oauth_test.go @@ -161,10 +161,10 @@ func TestSocialGitlab_UserInfo(t *testing.T) { } for _, test := range tests { - provider.roleAttributePath = test.RoleAttributePath - provider.allowAssignGrafanaAdmin = test.Cfg.AllowAssignGrafanaAdmin + provider.info.RoleAttributePath = test.RoleAttributePath + provider.info.AllowAssignGrafanaAdmin = test.Cfg.AllowAssignGrafanaAdmin provider.autoAssignOrgRole = string(test.Cfg.AutoAssignOrgRole) - provider.roleAttributeStrict = test.Cfg.RoleAttributeStrict + provider.info.RoleAttributeStrict = test.Cfg.RoleAttributeStrict provider.info.SkipOrgRoleSync = test.Cfg.SkipOrgRoleSync t.Run(test.Name, func(t *testing.T) { @@ -187,7 +187,7 @@ func TestSocialGitlab_UserInfo(t *testing.T) { require.Fail(t, "unexpected request URI: "+r.RequestURI) } })) - provider.apiUrl = ts.URL + apiURI + provider.info.ApiUrl = ts.URL + apiURI actualResult, err := provider.UserInfo(context.Background(), ts.Client(), &oauth2.Token{}) if test.ExpectedError != nil { require.ErrorIs(t, err, test.ExpectedError) diff --git a/pkg/login/social/connectors/google_oauth.go b/pkg/login/social/connectors/google_oauth.go index a44eadc1073..7d3391f13d6 100644 --- a/pkg/login/social/connectors/google_oauth.go +++ b/pkg/login/social/connectors/google_oauth.go @@ -28,8 +28,6 @@ var _ ssosettings.Reloadable = (*SocialGoogle)(nil) type SocialGoogle struct { *SocialBase - hostedDomain string - apiUrl string } type googleUserData struct { @@ -43,9 +41,7 @@ type googleUserData struct { func NewGoogleProvider(info *social.OAuthInfo, cfg *setting.Cfg, ssoSettings ssosettings.Service, features *featuremgmt.FeatureManager) *SocialGoogle { config := createOAuthConfig(info, cfg, social.GoogleProviderName) provider := &SocialGoogle{ - SocialBase: newSocialBase(social.GoogleProviderName, config, info, cfg.AutoAssignOrgRole, *features), - hostedDomain: info.HostedDomain, - apiUrl: info.ApiUrl, + SocialBase: newSocialBase(social.GoogleProviderName, config, info, cfg.AutoAssignOrgRole, *features), } if strings.HasPrefix(info.ApiUrl, legacyAPIURL) { @@ -114,7 +110,7 @@ func (s *SocialGoogle) UserInfo(ctx context.Context, client *http.Client, token return nil, errRole } - if s.allowAssignGrafanaAdmin { + if s.info.AllowAssignGrafanaAdmin { userInfo.IsGrafanaAdmin = &grafanaAdmin } @@ -138,9 +134,9 @@ type googleAPIData struct { } func (s *SocialGoogle) extractFromAPI(ctx context.Context, client *http.Client) (*googleUserData, error) { - if strings.HasPrefix(s.apiUrl, legacyAPIURL) { + if strings.HasPrefix(s.info.ApiUrl, legacyAPIURL) { data := googleAPIData{} - response, err := s.httpGet(ctx, client, s.apiUrl) + response, err := s.httpGet(ctx, client, s.info.ApiUrl) if err != nil { return nil, fmt.Errorf("error retrieving legacy user info: %s", err) } @@ -159,7 +155,7 @@ func (s *SocialGoogle) extractFromAPI(ctx context.Context, client *http.Client) } data := googleUserData{} - response, err := s.httpGet(ctx, client, s.apiUrl) + response, err := s.httpGet(ctx, client, s.info.ApiUrl) if err != nil { return nil, fmt.Errorf("error getting user info: %s", err) } @@ -172,7 +168,7 @@ func (s *SocialGoogle) extractFromAPI(ctx context.Context, client *http.Client) } func (s *SocialGoogle) AuthCodeURL(state string, opts ...oauth2.AuthCodeOption) string { - if s.features.IsEnabledGlobally(featuremgmt.FlagAccessTokenExpirationCheck) && s.useRefreshToken { + if s.features.IsEnabledGlobally(featuremgmt.FlagAccessTokenExpirationCheck) && s.info.UseRefreshToken { opts = append(opts, oauth2.AccessTypeOffline, oauth2.ApprovalForce) } return s.SocialBase.AuthCodeURL(state, opts...) diff --git a/pkg/login/social/connectors/okta_oauth.go b/pkg/login/social/connectors/okta_oauth.go index 5cc5dfa9e10..ae0991add48 100644 --- a/pkg/login/social/connectors/okta_oauth.go +++ b/pkg/login/social/connectors/okta_oauth.go @@ -23,8 +23,6 @@ var _ ssosettings.Reloadable = (*SocialOkta)(nil) type SocialOkta struct { *SocialBase - apiUrl string - allowedGroups []string } type OktaUserInfoJson struct { @@ -49,9 +47,7 @@ type OktaClaims struct { func NewOktaProvider(info *social.OAuthInfo, cfg *setting.Cfg, ssoSettings ssosettings.Service, features *featuremgmt.FeatureManager) *SocialOkta { config := createOAuthConfig(info, cfg, social.OktaProviderName) provider := &SocialOkta{ - SocialBase: newSocialBase(social.OktaProviderName, config, info, cfg.AutoAssignOrgRole, *features), - apiUrl: info.ApiUrl, - allowedGroups: info.AllowedGroups, + SocialBase: newSocialBase(social.OktaProviderName, config, info, cfg.AutoAssignOrgRole, *features), } if info.UseRefreshToken && features.IsEnabledGlobally(featuremgmt.FlagAccessTokenExpirationCheck) { @@ -122,11 +118,11 @@ func (s *SocialOkta) UserInfo(ctx context.Context, client *http.Client, token *o return nil, err } - if s.allowAssignGrafanaAdmin { + if s.info.AllowAssignGrafanaAdmin { isGrafanaAdmin = &grafanaAdmin } } - if s.allowAssignGrafanaAdmin && s.info.SkipOrgRoleSync { + if s.info.AllowAssignGrafanaAdmin && s.info.SkipOrgRoleSync { s.log.Debug("AllowAssignGrafanaAdmin and skipOrgRoleSync are both set, Grafana Admin role will not be synced, consider setting one or the other") } @@ -146,9 +142,9 @@ func (s *SocialOkta) GetOAuthInfo() *social.OAuthInfo { } func (s *SocialOkta) extractAPI(ctx context.Context, data *OktaUserInfoJson, client *http.Client) error { - rawUserInfoResponse, err := s.httpGet(ctx, client, s.apiUrl) + rawUserInfoResponse, err := s.httpGet(ctx, client, s.info.ApiUrl) if err != nil { - s.log.Debug("Error getting user info response", "url", s.apiUrl, "error", err) + s.log.Debug("Error getting user info response", "url", s.info.ApiUrl, "error", err) return fmt.Errorf("error getting user info response: %w", err) } data.rawJSON = rawUserInfoResponse.Body @@ -174,11 +170,11 @@ func (s *SocialOkta) GetGroups(data *OktaUserInfoJson) []string { // TODO: remove this in a separate PR and use the isGroupMember from the social.go func (s *SocialOkta) IsGroupMember(groups []string) bool { - if len(s.allowedGroups) == 0 { + if len(s.info.AllowedGroups) == 0 { return true } - for _, allowedGroup := range s.allowedGroups { + for _, allowedGroup := range s.info.AllowedGroups { for _, group := range groups { if group == allowedGroup { return true diff --git a/pkg/login/social/connectors/social_base.go b/pkg/login/social/connectors/social_base.go index e5d67d929dc..5ee11e3be20 100644 --- a/pkg/login/social/connectors/social_base.go +++ b/pkg/login/social/connectors/social_base.go @@ -22,18 +22,10 @@ import ( type SocialBase struct { *oauth2.Config - info *social.OAuthInfo - log log.Logger - allowSignup bool - allowAssignGrafanaAdmin bool - allowedDomains []string - allowedGroups []string - - roleAttributePath string - roleAttributeStrict bool - autoAssignOrgRole string - features featuremgmt.FeatureManager - useRefreshToken bool + info *social.OAuthInfo + log log.Logger + autoAssignOrgRole string + features featuremgmt.FeatureManager } func newSocialBase(name string, @@ -45,18 +37,11 @@ func newSocialBase(name string, logger := log.New("oauth." + name) return &SocialBase{ - Config: config, - info: info, - log: logger, - allowSignup: info.AllowSignup, - allowAssignGrafanaAdmin: info.AllowAssignGrafanaAdmin, - allowedDomains: info.AllowedDomains, - allowedGroups: info.AllowedGroups, - roleAttributePath: info.RoleAttributePath, - roleAttributeStrict: info.RoleAttributeStrict, - autoAssignOrgRole: autoAssignOrgRole, - features: features, - useRefreshToken: info.UseRefreshToken, + Config: config, + info: info, + log: logger, + autoAssignOrgRole: autoAssignOrgRole, + features: features, } } @@ -67,12 +52,12 @@ type groupStruct struct { func (s *SocialBase) SupportBundleContent(bf *bytes.Buffer) error { bf.WriteString("## Client configuration\n\n") bf.WriteString("```ini\n") - bf.WriteString(fmt.Sprintf("allow_assign_grafana_admin = %v\n", s.allowAssignGrafanaAdmin)) - bf.WriteString(fmt.Sprintf("allow_sign_up = %v\n", s.allowSignup)) - bf.WriteString(fmt.Sprintf("allowed_domains = %v\n", s.allowedDomains)) + bf.WriteString(fmt.Sprintf("allow_assign_grafana_admin = %v\n", s.info.AllowAssignGrafanaAdmin)) + bf.WriteString(fmt.Sprintf("allow_sign_up = %v\n", s.info.AllowSignup)) + bf.WriteString(fmt.Sprintf("allowed_domains = %v\n", s.info.AllowedDomains)) bf.WriteString(fmt.Sprintf("auto_assign_org_role = %v\n", s.autoAssignOrgRole)) - bf.WriteString(fmt.Sprintf("role_attribute_path = %v\n", s.roleAttributePath)) - bf.WriteString(fmt.Sprintf("role_attribute_strict = %v\n", s.roleAttributeStrict)) + bf.WriteString(fmt.Sprintf("role_attribute_path = %v\n", s.info.RoleAttributePath)) + bf.WriteString(fmt.Sprintf("role_attribute_strict = %v\n", s.info.RoleAttributeStrict)) bf.WriteString(fmt.Sprintf("skip_org_role_sync = %v\n", s.info.SkipOrgRoleSync)) bf.WriteString(fmt.Sprintf("client_id = %v\n", s.Config.ClientID)) bf.WriteString(fmt.Sprintf("client_secret = %v ; issue if empty\n", strings.Repeat("*", len(s.Config.ClientSecret)))) @@ -86,8 +71,8 @@ func (s *SocialBase) SupportBundleContent(bf *bytes.Buffer) error { } func (s *SocialBase) extractRoleAndAdminOptional(rawJSON []byte, groups []string) (org.RoleType, bool, error) { - if s.roleAttributePath == "" { - if s.roleAttributeStrict { + if s.info.RoleAttributePath == "" { + if s.info.RoleAttributeStrict { return "", false, errRoleAttributePathNotSet.Errorf("role_attribute_path not set and role_attribute_strict is set") } return "", false, nil @@ -99,7 +84,7 @@ func (s *SocialBase) extractRoleAndAdminOptional(rawJSON []byte, groups []string return "", false, errInvalidRole.Errorf("invalid role: %s", role) } - if s.roleAttributeStrict { + if s.info.RoleAttributeStrict { return "", false, errRoleAttributeStrictViolation.Errorf("idP did not return a role attribute, but role_attribute_strict is set") } @@ -116,13 +101,13 @@ func (s *SocialBase) extractRoleAndAdmin(rawJSON []byte, groups []string) (org.R } func (s *SocialBase) searchRole(rawJSON []byte, groups []string) (org.RoleType, bool) { - role, err := s.searchJSONForStringAttr(s.roleAttributePath, rawJSON) + role, err := s.searchJSONForStringAttr(s.info.RoleAttributePath, rawJSON) if err == nil && role != "" { return getRoleFromSearch(role) } if groupBytes, err := json.Marshal(groupStruct{groups}); err == nil { - role, err := s.searchJSONForStringAttr(s.roleAttributePath, groupBytes) + role, err := s.searchJSONForStringAttr(s.info.RoleAttributePath, groupBytes) if err == nil && role != "" { return getRoleFromSearch(role) } @@ -144,11 +129,11 @@ func (s *SocialBase) defaultRole() org.RoleType { } func (s *SocialBase) isGroupMember(groups []string) bool { - if len(s.allowedGroups) == 0 { + if len(s.info.AllowedGroups) == 0 { return true } - for _, allowedGroup := range s.allowedGroups { + for _, allowedGroup := range s.info.AllowedGroups { for _, group := range groups { if group == allowedGroup { return true