Add integration test for UserAttributeForFilter group search setting

Also adds new integration test env var to support the new test:
PINNIPED_TEST_LDAP_EXPECTED_DIRECT_POSIX_GROUPS_CN
This commit is contained in:
Ryan Richard 2023-05-26 11:47:54 -07:00
parent e3b7ba3677
commit 552eceabdb
3 changed files with 41 additions and 4 deletions

View File

@ -1,6 +1,6 @@
#!/usr/bin/env bash #!/usr/bin/env bash
# Copyright 2020-2022 the Pinniped contributors. All Rights Reserved. # Copyright 2020-2023 the Pinniped contributors. All Rights Reserved.
# SPDX-License-Identifier: Apache-2.0 # SPDX-License-Identifier: Apache-2.0
# #
@ -420,6 +420,7 @@ export PINNIPED_TEST_LDAP_USER_EMAIL_ATTRIBUTE_VALUE="pinny.ldap@example.com"
export PINNIPED_TEST_LDAP_EXPECTED_DIRECT_GROUPS_DN="cn=ball-game-players,ou=beach-groups,ou=groups,dc=pinniped,dc=dev;cn=seals,ou=groups,dc=pinniped,dc=dev" export PINNIPED_TEST_LDAP_EXPECTED_DIRECT_GROUPS_DN="cn=ball-game-players,ou=beach-groups,ou=groups,dc=pinniped,dc=dev;cn=seals,ou=groups,dc=pinniped,dc=dev"
export PINNIPED_TEST_LDAP_EXPECTED_INDIRECT_GROUPS_DN="cn=pinnipeds,ou=groups,dc=pinniped,dc=dev;cn=mammals,ou=groups,dc=pinniped,dc=dev" export PINNIPED_TEST_LDAP_EXPECTED_INDIRECT_GROUPS_DN="cn=pinnipeds,ou=groups,dc=pinniped,dc=dev;cn=mammals,ou=groups,dc=pinniped,dc=dev"
export PINNIPED_TEST_LDAP_EXPECTED_DIRECT_GROUPS_CN="ball-game-players;seals" export PINNIPED_TEST_LDAP_EXPECTED_DIRECT_GROUPS_CN="ball-game-players;seals"
export PINNIPED_TEST_LDAP_EXPECTED_DIRECT_POSIX_GROUPS_CN="ball-game-players-posix;seals-posix"
export PINNIPED_TEST_LDAP_EXPECTED_INDIRECT_GROUPS_CN="pinnipeds;mammals" export PINNIPED_TEST_LDAP_EXPECTED_INDIRECT_GROUPS_CN="pinnipeds;mammals"
export PINNIPED_TEST_CLI_OIDC_ISSUER=https://dex.tools.svc.cluster.local/dex export PINNIPED_TEST_CLI_OIDC_ISSUER=https://dex.tools.svc.cluster.local/dex
export PINNIPED_TEST_CLI_OIDC_ISSUER_CA_BUNDLE="${test_ca_bundle_pem}" export PINNIPED_TEST_CLI_OIDC_ISSUER_CA_BUNDLE="${test_ca_bundle_pem}"

View File

@ -134,11 +134,13 @@ func TestSupervisorLogin_Browser(t *testing.T) {
}, },
}, },
GroupSearch: idpv1alpha1.LDAPIdentityProviderGroupSearch{ GroupSearch: idpv1alpha1.LDAPIdentityProviderGroupSearch{
Base: env.SupervisorUpstreamLDAP.GroupSearchBase, Base: env.SupervisorUpstreamLDAP.GroupSearchBase,
Filter: "", Filter: "",
UserAttributeForFilter: "",
Attributes: idpv1alpha1.LDAPIdentityProviderGroupSearchAttributes{ Attributes: idpv1alpha1.LDAPIdentityProviderGroupSearchAttributes{
GroupName: "dn", GroupName: "dn",
}, },
SkipGroupRefresh: false,
}, },
} }
@ -471,6 +473,38 @@ func TestSupervisorLogin_Browser(t *testing.T) {
}, },
wantDownstreamIDTokenGroups: env.SupervisorUpstreamLDAP.TestUserDirectGroupsDNs, wantDownstreamIDTokenGroups: env.SupervisorUpstreamLDAP.TestUserDirectGroupsDNs,
}, },
{
name: "ldap using posix groups by using the UserAttributeForFilter option to adjust the group search filter behavior",
maybeSkip: skipLDAPTests,
createIDP: func(t *testing.T) string {
idp, _ := createLDAPIdentityProvider(t, func(spec *idpv1alpha1.LDAPIdentityProviderSpec) {
spec.GroupSearch.Filter = "&(objectClass=posixGroup)(memberUid={})"
spec.GroupSearch.UserAttributeForFilter = "uid"
spec.GroupSearch.Attributes.GroupName = "cn"
})
return idp.Name
},
requestAuthorization: func(t *testing.T, _, downstreamAuthorizeURL, _, _, _ string, httpClient *http.Client) {
requestAuthorizationUsingCLIPasswordFlow(t,
downstreamAuthorizeURL,
env.SupervisorUpstreamLDAP.TestUserMailAttributeValue, // username to present to server during login
env.SupervisorUpstreamLDAP.TestUserPassword, // password to present to server during login
httpClient,
false,
)
},
// the ID token Subject should be the Host URL plus the value pulled from the requested UserSearch.Attributes.UID attribute
wantDownstreamIDTokenSubjectToMatch: "^" + regexp.QuoteMeta(
"ldaps://"+env.SupervisorUpstreamLDAP.Host+
"?base="+url.QueryEscape(env.SupervisorUpstreamLDAP.UserSearchBase)+
"&sub="+base64.RawURLEncoding.EncodeToString([]byte(env.SupervisorUpstreamLDAP.TestUserUniqueIDAttributeValue)),
) + "$",
// the ID token Username should have been pulled from the requested UserSearch.Attributes.Username attribute
wantDownstreamIDTokenUsernameToMatch: func(_ string) string {
return "^" + regexp.QuoteMeta(env.SupervisorUpstreamLDAP.TestUserMailAttributeValue) + "$"
},
wantDownstreamIDTokenGroups: env.SupervisorUpstreamLDAP.TestUserDirectPosixGroupsCNs,
},
{ {
name: "ldap without requesting username and groups scope gets them anyway for pinniped-cli for backwards compatibility with old CLIs", name: "ldap without requesting username and groups scope gets them anyway for pinniped-cli for backwards compatibility with old CLIs",
maybeSkip: skipLDAPTests, maybeSkip: skipLDAPTests,

View File

@ -1,4 +1,4 @@
// Copyright 2020-2022 the Pinniped contributors. All Rights Reserved. // Copyright 2020-2023 the Pinniped contributors. All Rights Reserved.
// SPDX-License-Identifier: Apache-2.0 // SPDX-License-Identifier: Apache-2.0
package testlib package testlib
@ -98,6 +98,7 @@ type TestLDAPUpstream struct {
TestUserUniqueIDAttributeName string `json:"testUserUniqueIDAttributeName"` TestUserUniqueIDAttributeName string `json:"testUserUniqueIDAttributeName"`
TestUserUniqueIDAttributeValue string `json:"testUserUniqueIDAttributeValue"` TestUserUniqueIDAttributeValue string `json:"testUserUniqueIDAttributeValue"`
TestUserDirectGroupsCNs []string `json:"testUserDirectGroupsCNs"` TestUserDirectGroupsCNs []string `json:"testUserDirectGroupsCNs"`
TestUserDirectPosixGroupsCNs []string `json:"testUserDirectPosixGroupsCNs"`
TestUserDirectGroupsDNs []string `json:"testUserDirectGroupsDNs"` //nolint:revive // this is "distinguished names", not "DNS" TestUserDirectGroupsDNs []string `json:"testUserDirectGroupsDNs"` //nolint:revive // this is "distinguished names", not "DNS"
TestUserSAMAccountNameValue string `json:"testUserSAMAccountNameValue"` TestUserSAMAccountNameValue string `json:"testUserSAMAccountNameValue"`
TestUserPrincipalNameValue string `json:"testUserPrincipalNameValue"` TestUserPrincipalNameValue string `json:"testUserPrincipalNameValue"`
@ -267,6 +268,7 @@ func loadEnvVars(t *testing.T, result *TestEnv) {
TestUserMailAttributeName: needEnv(t, "PINNIPED_TEST_LDAP_USER_EMAIL_ATTRIBUTE_NAME"), TestUserMailAttributeName: needEnv(t, "PINNIPED_TEST_LDAP_USER_EMAIL_ATTRIBUTE_NAME"),
TestUserMailAttributeValue: needEnv(t, "PINNIPED_TEST_LDAP_USER_EMAIL_ATTRIBUTE_VALUE"), TestUserMailAttributeValue: needEnv(t, "PINNIPED_TEST_LDAP_USER_EMAIL_ATTRIBUTE_VALUE"),
TestUserDirectGroupsCNs: filterEmpty(strings.Split(needEnv(t, "PINNIPED_TEST_LDAP_EXPECTED_DIRECT_GROUPS_CN"), ";")), TestUserDirectGroupsCNs: filterEmpty(strings.Split(needEnv(t, "PINNIPED_TEST_LDAP_EXPECTED_DIRECT_GROUPS_CN"), ";")),
TestUserDirectPosixGroupsCNs: filterEmpty(strings.Split(needEnv(t, "PINNIPED_TEST_LDAP_EXPECTED_DIRECT_POSIX_GROUPS_CN"), ";")),
TestUserDirectGroupsDNs: filterEmpty(strings.Split(needEnv(t, "PINNIPED_TEST_LDAP_EXPECTED_DIRECT_GROUPS_DN"), ";")), TestUserDirectGroupsDNs: filterEmpty(strings.Split(needEnv(t, "PINNIPED_TEST_LDAP_EXPECTED_DIRECT_GROUPS_DN"), ";")),
TestUserPassword: needEnv(t, "PINNIPED_TEST_LDAP_USER_PASSWORD"), TestUserPassword: needEnv(t, "PINNIPED_TEST_LDAP_USER_PASSWORD"),
} }