integration tests for supervisor oidc, ldap, activedirectory IDP

Signed-off-by: Ashish Amarnath <ashish.amarnath@broadcom.com>
This commit is contained in:
Ashish Amarnath
2024-07-09 14:24:39 -07:00
committed by Ryan Richard
parent 6a610a9d51
commit 8eb15a924f
4 changed files with 73 additions and 14 deletions

View File

@@ -144,12 +144,12 @@ func New(
controllerlib.Config{
Name: controllerName,
Syncer: &jwtCacheFillerController{
namespace: namespace,
cache: cache,
client: client,
jwtAuthenticators: jwtAuthenticators,
secretInformer: secretInformer,
configMapInformer: configMapInformer,
namespace: namespace,
clock: clock,
log: log.WithName(controllerName),
},
@@ -163,12 +163,12 @@ func New(
}
type jwtCacheFillerController struct {
namespace string
cache *authncache.Cache
jwtAuthenticators authinformers.JWTAuthenticatorInformer
secretInformer corev1informers.SecretInformer
configMapInformer corev1informers.ConfigMapInformer
client conciergeclientset.Interface
namespace string
clock clock.Clock
log plog.Logger
}

View File

@@ -115,11 +115,11 @@ func TestE2EFullIntegration_Browser(t *testing.T) {
// Create a JWTAuthenticator that will validate the tokens from the downstream issuer.
// If the FederationDomain is not Ready, the JWTAuthenticator cannot be ready, either.
clusterAudience := "test-cluster-" + testlib.RandHex(t, 8)
authenticator := testlib.CreateTestJWTAuthenticator(topSetupCtx, t, authenticationv1alpha1.JWTAuthenticatorSpec{
defaultJWTAuthenticatorSpec := authenticationv1alpha1.JWTAuthenticatorSpec{
Issuer: federationDomain.Spec.Issuer,
Audience: clusterAudience,
TLS: &authenticationv1alpha1.TLSSpec{CertificateAuthorityData: testCABundleBase64},
}, authenticationv1alpha1.JWTAuthenticatorPhaseError)
}
// Add an OIDC upstream IDP and try using it to authenticate during kubectl commands.
t.Run("with Supervisor OIDC upstream IDP and browser flow with with form_post automatic authcode delivery to CLI", func(t *testing.T) {
@@ -146,6 +146,7 @@ func TestE2EFullIntegration_Browser(t *testing.T) {
Resource: "namespaces",
})
authenticator := testlib.CreateTestJWTAuthenticator(topSetupCtx, t, defaultJWTAuthenticatorSpec, authenticationv1alpha1.JWTAuthenticatorPhaseError)
// Create upstream OIDC provider and wait for it to become ready.
createdProvider := testlib.CreateTestOIDCIdentityProvider(t, idpv1alpha1.OIDCIdentityProviderSpec{
Issuer: env.SupervisorUpstreamOIDC.Issuer,
@@ -232,6 +233,21 @@ func TestE2EFullIntegration_Browser(t *testing.T) {
Resource: "namespaces",
})
// in this test, use a secret of type TLS to source ca bundle for the JWT authenticator
caSecret := testlib.CreateTestSecret(t, env.ConciergeNamespace, "ca-cert", corev1.SecretTypeTLS,
map[string]string{
"ca.crt": string(testCABundlePEM),
"tls.crt": "",
"tls.key": "",
})
jwtAuthnSpec := defaultJWTAuthenticatorSpec.DeepCopy()
jwtAuthnSpec.TLS.CertificateAuthorityData = ""
jwtAuthnSpec.TLS.CertificateAuthorityDataSource = &authenticationv1alpha1.CABundleSource{
Kind: "Secret",
Name: caSecret.Name,
Key: "ca.crt",
}
authenticator := testlib.CreateTestJWTAuthenticator(topSetupCtx, t, *jwtAuthnSpec, authenticationv1alpha1.JWTAuthenticatorPhaseError)
// Create upstream OIDC provider and wait for it to become ready.
createdProvider := testlib.CreateTestOIDCIdentityProvider(t, idpv1alpha1.OIDCIdentityProviderSpec{
Issuer: env.SupervisorUpstreamOIDC.Issuer,
@@ -320,6 +336,22 @@ func TestE2EFullIntegration_Browser(t *testing.T) {
Resource: "namespaces",
})
// in this test, use a secret of type opaque to source ca bundle for the JWT authenticator
caSecret := testlib.CreateTestSecret(t, env.ConciergeNamespace, "ca-cert", corev1.SecretTypeOpaque,
map[string]string{
"ca.crt": string(testCABundlePEM),
})
t.Logf("created secret %s/%s", caSecret.Namespace, caSecret.Name)
jwtAuthnSpec := defaultJWTAuthenticatorSpec.DeepCopy()
jwtAuthnSpec.TLS.CertificateAuthorityData = ""
jwtAuthnSpec.TLS.CertificateAuthorityDataSource = &authenticationv1alpha1.CABundleSource{
Kind: "Secret",
Name: caSecret.Name,
Key: "ca.crt",
}
authenticator := testlib.CreateTestJWTAuthenticator(topSetupCtx, t, *jwtAuthnSpec, authenticationv1alpha1.JWTAuthenticatorPhaseError)
t.Logf("authenticator: %s/%s; concierge ns: %s", authenticator.Namespace, authenticator.Name, env.ConciergeNamespace)
// Create upstream OIDC provider and wait for it to become ready.
createdProvider := testlib.CreateTestOIDCIdentityProvider(t, idpv1alpha1.OIDCIdentityProviderSpec{
Issuer: env.SupervisorUpstreamOIDC.Issuer,
@@ -444,6 +476,20 @@ func TestE2EFullIntegration_Browser(t *testing.T) {
}
}
// in this test, use a configmap to source ca bundle for the JWT authenticator
caConfigMap := testlib.CreateTestConfigMap(t, env.ConciergeNamespace, "ca-cert",
map[string]string{
"ca.crt": string(testCABundlePEM),
})
jwtAuthnSpec := defaultJWTAuthenticatorSpec.DeepCopy()
jwtAuthnSpec.TLS.CertificateAuthorityData = ""
jwtAuthnSpec.TLS.CertificateAuthorityDataSource = &authenticationv1alpha1.CABundleSource{
Kind: "ConfigMap",
Name: caConfigMap.Name,
Key: "ca.crt",
}
authenticator := testlib.CreateTestJWTAuthenticator(topSetupCtx, t, defaultJWTAuthenticatorSpec, authenticationv1alpha1.JWTAuthenticatorPhaseError)
// Create upstream OIDC provider and wait for it to become ready.
createdProvider := testlib.CreateTestOIDCIdentityProvider(t, idpv1alpha1.OIDCIdentityProviderSpec{
Issuer: env.SupervisorUpstreamOIDC.Issuer,
@@ -574,6 +620,7 @@ func TestE2EFullIntegration_Browser(t *testing.T) {
Resource: "namespaces",
})
authenticator := testlib.CreateTestJWTAuthenticator(topSetupCtx, t, defaultJWTAuthenticatorSpec, authenticationv1alpha1.JWTAuthenticatorPhaseError)
// Create upstream OIDC provider and wait for it to become ready.
createdProvider := testlib.CreateTestOIDCIdentityProvider(t, idpv1alpha1.OIDCIdentityProviderSpec{
Issuer: env.SupervisorUpstreamOIDC.Issuer,
@@ -647,6 +694,7 @@ func TestE2EFullIntegration_Browser(t *testing.T) {
tempDir := t.TempDir() // per-test tmp dir to avoid sharing files between tests
authenticator := testlib.CreateTestJWTAuthenticator(topSetupCtx, t, defaultJWTAuthenticatorSpec, authenticationv1alpha1.JWTAuthenticatorPhaseError)
// Create upstream OIDC provider and wait for it to become ready.
oidcIdentityProvider := testlib.CreateTestOIDCIdentityProvider(t, idpv1alpha1.OIDCIdentityProviderSpec{
Issuer: env.SupervisorUpstreamOIDC.Issuer,
@@ -728,6 +776,7 @@ func TestE2EFullIntegration_Browser(t *testing.T) {
expectedUsername := env.SupervisorUpstreamLDAP.TestUserMailAttributeValue
expectedGroups := env.SupervisorUpstreamLDAP.TestUserDirectGroupsDNs
authenticator := testlib.CreateTestJWTAuthenticator(topSetupCtx, t, defaultJWTAuthenticatorSpec, authenticationv1alpha1.JWTAuthenticatorPhaseError)
createdProvider := setupClusterForEndToEndLDAPTest(t, expectedUsername, env)
testlib.WaitForFederationDomainStatusPhase(testCtx, t, federationDomain.Name, supervisorconfigv1alpha1.FederationDomainPhaseReady)
testlib.WaitForJWTAuthenticatorStatusPhase(testCtx, t, authenticator.Name, authenticationv1alpha1.JWTAuthenticatorPhaseReady)
@@ -787,6 +836,7 @@ func TestE2EFullIntegration_Browser(t *testing.T) {
expectedUsername := env.SupervisorUpstreamLDAP.TestUserMailAttributeValue
expectedGroups := env.SupervisorUpstreamLDAP.TestUserDirectGroupsDNs
authenticator := testlib.CreateTestJWTAuthenticator(topSetupCtx, t, defaultJWTAuthenticatorSpec, authenticationv1alpha1.JWTAuthenticatorPhaseError)
createdProvider := setupClusterForEndToEndLDAPTest(t, expectedUsername, env)
testlib.WaitForFederationDomainStatusPhase(testCtx, t, federationDomain.Name, supervisorconfigv1alpha1.FederationDomainPhaseReady)
testlib.WaitForJWTAuthenticatorStatusPhase(testCtx, t, authenticator.Name, authenticationv1alpha1.JWTAuthenticatorPhaseReady)
@@ -850,6 +900,7 @@ func TestE2EFullIntegration_Browser(t *testing.T) {
expectedUsername := env.SupervisorUpstreamLDAP.TestUserMailAttributeValue
expectedGroups := env.SupervisorUpstreamLDAP.TestUserDirectGroupsDNs
authenticator := testlib.CreateTestJWTAuthenticator(topSetupCtx, t, defaultJWTAuthenticatorSpec, authenticationv1alpha1.JWTAuthenticatorPhaseError)
createdProvider := setupClusterForEndToEndLDAPTest(t, expectedUsername, env)
testlib.WaitForFederationDomainStatusPhase(testCtx, t, federationDomain.Name, supervisorconfigv1alpha1.FederationDomainPhaseReady)
testlib.WaitForJWTAuthenticatorStatusPhase(testCtx, t, authenticator.Name, authenticationv1alpha1.JWTAuthenticatorPhaseReady)
@@ -921,6 +972,7 @@ func TestE2EFullIntegration_Browser(t *testing.T) {
expectedUsername := env.SupervisorUpstreamActiveDirectory.TestUserPrincipalNameValue
expectedGroups := env.SupervisorUpstreamActiveDirectory.TestUserIndirectGroupsSAMAccountPlusDomainNames
authenticator := testlib.CreateTestJWTAuthenticator(topSetupCtx, t, defaultJWTAuthenticatorSpec, authenticationv1alpha1.JWTAuthenticatorPhaseError)
createdProvider := setupClusterForEndToEndActiveDirectoryTest(t, expectedUsername, env)
testlib.WaitForFederationDomainStatusPhase(testCtx, t, federationDomain.Name, supervisorconfigv1alpha1.FederationDomainPhaseReady)
testlib.WaitForJWTAuthenticatorStatusPhase(testCtx, t, authenticator.Name, authenticationv1alpha1.JWTAuthenticatorPhaseReady)
@@ -980,6 +1032,7 @@ func TestE2EFullIntegration_Browser(t *testing.T) {
expectedUsername := env.SupervisorUpstreamActiveDirectory.TestUserPrincipalNameValue
expectedGroups := env.SupervisorUpstreamActiveDirectory.TestUserIndirectGroupsSAMAccountPlusDomainNames
authenticator := testlib.CreateTestJWTAuthenticator(topSetupCtx, t, defaultJWTAuthenticatorSpec, authenticationv1alpha1.JWTAuthenticatorPhaseError)
createdProvider := setupClusterForEndToEndActiveDirectoryTest(t, expectedUsername, env)
testlib.WaitForFederationDomainStatusPhase(testCtx, t, federationDomain.Name, supervisorconfigv1alpha1.FederationDomainPhaseReady)
testlib.WaitForJWTAuthenticatorStatusPhase(testCtx, t, authenticator.Name, authenticationv1alpha1.JWTAuthenticatorPhaseReady)
@@ -1053,6 +1106,7 @@ func TestE2EFullIntegration_Browser(t *testing.T) {
expectedUsername := env.SupervisorUpstreamLDAP.TestUserMailAttributeValue
expectedGroups := env.SupervisorUpstreamLDAP.TestUserDirectGroupsDNs
authenticator := testlib.CreateTestJWTAuthenticator(topSetupCtx, t, defaultJWTAuthenticatorSpec, authenticationv1alpha1.JWTAuthenticatorPhaseError)
createdProvider := setupClusterForEndToEndLDAPTest(t, expectedUsername, env)
testlib.WaitForFederationDomainStatusPhase(testCtx, t, federationDomain.Name, supervisorconfigv1alpha1.FederationDomainPhaseReady)
testlib.WaitForJWTAuthenticatorStatusPhase(testCtx, t, authenticator.Name, authenticationv1alpha1.JWTAuthenticatorPhaseReady)
@@ -1108,6 +1162,7 @@ func TestE2EFullIntegration_Browser(t *testing.T) {
expectedUsername := env.SupervisorUpstreamActiveDirectory.TestUserPrincipalNameValue
expectedGroups := env.SupervisorUpstreamActiveDirectory.TestUserIndirectGroupsSAMAccountPlusDomainNames
authenticator := testlib.CreateTestJWTAuthenticator(topSetupCtx, t, defaultJWTAuthenticatorSpec, authenticationv1alpha1.JWTAuthenticatorPhaseError)
createdProvider := setupClusterForEndToEndActiveDirectoryTest(t, expectedUsername, env)
testlib.WaitForFederationDomainStatusPhase(testCtx, t, federationDomain.Name, supervisorconfigv1alpha1.FederationDomainPhaseReady)
testlib.WaitForJWTAuthenticatorStatusPhase(testCtx, t, authenticator.Name, authenticationv1alpha1.JWTAuthenticatorPhaseReady)
@@ -1163,6 +1218,7 @@ func TestE2EFullIntegration_Browser(t *testing.T) {
expectedUsername := env.SupervisorUpstreamLDAP.TestUserMailAttributeValue
expectedGroups := env.SupervisorUpstreamLDAP.TestUserDirectGroupsDNs
authenticator := testlib.CreateTestJWTAuthenticator(topSetupCtx, t, defaultJWTAuthenticatorSpec, authenticationv1alpha1.JWTAuthenticatorPhaseError)
createdProvider := setupClusterForEndToEndLDAPTest(t, expectedUsername, env)
testlib.WaitForFederationDomainStatusPhase(testCtx, t, federationDomain.Name, supervisorconfigv1alpha1.FederationDomainPhaseReady)
testlib.WaitForJWTAuthenticatorStatusPhase(testCtx, t, authenticator.Name, authenticationv1alpha1.JWTAuthenticatorPhaseReady)
@@ -1253,6 +1309,7 @@ func TestE2EFullIntegration_Browser(t *testing.T) {
).Name,
},
}, idpv1alpha1.GitHubPhaseReady)
authenticator := testlib.CreateTestJWTAuthenticator(topSetupCtx, t, defaultJWTAuthenticatorSpec, authenticationv1alpha1.JWTAuthenticatorPhaseError)
testlib.WaitForFederationDomainStatusPhase(testCtx, t, federationDomain.Name, supervisorconfigv1alpha1.FederationDomainPhaseReady)
testlib.WaitForJWTAuthenticatorStatusPhase(testCtx, t, authenticator.Name, authenticationv1alpha1.JWTAuthenticatorPhaseReady)
@@ -1327,6 +1384,7 @@ func TestE2EFullIntegration_Browser(t *testing.T) {
createdLDAPProvider := setupClusterForEndToEndLDAPTest(t, expectedDownstreamLDAPUsername, env)
authenticator := testlib.CreateTestJWTAuthenticator(topSetupCtx, t, defaultJWTAuthenticatorSpec, authenticationv1alpha1.JWTAuthenticatorPhaseError)
// Having one IDP should put the FederationDomain into a ready state.
testlib.WaitForFederationDomainStatusPhase(testCtx, t, federationDomain.Name, supervisorconfigv1alpha1.FederationDomainPhaseReady)
testlib.WaitForJWTAuthenticatorStatusPhase(testCtx, t, authenticator.Name, authenticationv1alpha1.JWTAuthenticatorPhaseReady)
@@ -1647,6 +1705,7 @@ func TestE2EFullIntegration_Browser(t *testing.T) {
createdLDAPProvider := setupClusterForEndToEndLDAPTest(t, expectedDownstreamLDAPUsername, env)
authenticator := testlib.CreateTestJWTAuthenticator(topSetupCtx, t, defaultJWTAuthenticatorSpec, authenticationv1alpha1.JWTAuthenticatorPhaseError)
// Having one IDP should put the FederationDomain into a ready state.
testlib.WaitForFederationDomainStatusPhase(testCtx, t, federationDomain.Name, supervisorconfigv1alpha1.FederationDomainPhaseReady)
testlib.WaitForJWTAuthenticatorStatusPhase(testCtx, t, authenticator.Name, authenticationv1alpha1.JWTAuthenticatorPhaseReady)

View File

@@ -322,7 +322,6 @@ func TestSupervisorLogin_Browser(t *testing.T) {
regexp.QuoteMeta("&sub=") + ".+" +
"$"
// TODO: update this test table to add 2 tests per IDP each to source ca bundle from secret and cm
tests := []*supervisorLoginTestcase{
{
name: "oidc with default username and groups claim settings",
@@ -344,7 +343,8 @@ func TestSupervisorLogin_Browser(t *testing.T) {
maybeSkip: skipNever,
createIDP: func(t *testing.T) string {
idpSpec := basicOIDCIdentityProviderSpec()
caData, _ := base64.StdEncoding.DecodeString(idpSpec.TLS.CertificateAuthorityData)
caData, err := base64.StdEncoding.DecodeString(idpSpec.TLS.CertificateAuthorityData)
require.NoError(t, err)
caSecret := testlib.CreateTestSecret(t, env.SupervisorNamespace, "ca-cert", corev1.SecretTypeOpaque,
map[string]string{
"ca.crt": string(caData),
@@ -372,7 +372,8 @@ func TestSupervisorLogin_Browser(t *testing.T) {
maybeSkip: skipNever,
createIDP: func(t *testing.T) string {
idpSpec := basicOIDCIdentityProviderSpec()
caData, _ := base64.StdEncoding.DecodeString(idpSpec.TLS.CertificateAuthorityData)
caData, err := base64.StdEncoding.DecodeString(idpSpec.TLS.CertificateAuthorityData)
require.NoError(t, err)
caSecret := testlib.CreateTestSecret(t, env.SupervisorNamespace, "ca-cert", corev1.SecretTypeTLS,
map[string]string{
"ca.crt": string(caData),
@@ -402,7 +403,8 @@ func TestSupervisorLogin_Browser(t *testing.T) {
maybeSkip: skipNever,
createIDP: func(t *testing.T) string {
idpSpec := basicOIDCIdentityProviderSpec()
caData, _ := base64.StdEncoding.DecodeString(idpSpec.TLS.CertificateAuthorityData)
caData, err := base64.StdEncoding.DecodeString(idpSpec.TLS.CertificateAuthorityData)
require.NoError(t, err)
caConfigMap := testlib.CreateTestConfigMap(t, env.SupervisorNamespace, "ca-cert", map[string]string{
"ca.crt": string(caData),
})
@@ -430,7 +432,8 @@ func TestSupervisorLogin_Browser(t *testing.T) {
maybeSkip: skipNever,
createIDP: func(t *testing.T) string {
idpSpec := basicOIDCIdentityProviderSpec()
caData, _ := base64.StdEncoding.DecodeString(idpSpec.TLS.CertificateAuthorityData)
caData, err := base64.StdEncoding.DecodeString(idpSpec.TLS.CertificateAuthorityData)
require.NoError(t, err)
caSecret := testlib.CreateTestSecret(t, env.SupervisorNamespace, "ca-cert", corev1.SecretTypeOpaque,
map[string]string{
"ca.crt": string(caData),
@@ -654,7 +657,6 @@ func TestSupervisorLogin_Browser(t *testing.T) {
name: "ldap IDP using secrets of type opaque to source ca bundle and with email as username and groups names as DNs and using an LDAP provider which supports TLS",
maybeSkip: skipLDAPTests,
createIDP: func(t *testing.T) string {
idp, _ := createLDAPIdentityProvider(t, func(spec *idpv1alpha1.LDAPIdentityProviderSpec) {
caSecret := testlib.CreateTestSecret(t, env.SupervisorNamespace, "ca-cert", corev1.SecretTypeOpaque,
map[string]string{
@@ -705,7 +707,6 @@ func TestSupervisorLogin_Browser(t *testing.T) {
name: "ldap IDP using secrets of type TLS to source ca bundle and with email as username and groups names as DNs and using an LDAP provider which supports TLS",
maybeSkip: skipLDAPTests,
createIDP: func(t *testing.T) string {
idp, _ := createLDAPIdentityProvider(t, func(spec *idpv1alpha1.LDAPIdentityProviderSpec) {
caSecret := testlib.CreateTestSecret(t, env.SupervisorNamespace, "ca-cert", corev1.SecretTypeTLS,
map[string]string{
@@ -758,7 +759,6 @@ func TestSupervisorLogin_Browser(t *testing.T) {
name: "ldap IDP using configmaps to source ca bundle and with email as username and groups names as DNs and using an LDAP provider which supports TLS",
maybeSkip: skipLDAPTests,
createIDP: func(t *testing.T) string {
idp, _ := createLDAPIdentityProvider(t, func(spec *idpv1alpha1.LDAPIdentityProviderSpec) {
caConfigMap := testlib.CreateTestConfigMap(t, env.SupervisorNamespace, "ca-cert",

View File

@@ -470,7 +470,7 @@ func CreateTestConfigMap(t *testing.T, namespace string, baseName string, string
err := client.CoreV1().ConfigMaps(namespace).Delete(context.Background(), created.Name, metav1.DeleteOptions{})
require.NoError(t, err)
})
t.Logf("created test ConfigMap %s", created.Name)
t.Logf("created test ConfigMap %s/%s", created.Namespace, created.Name)
return created
}
@@ -492,7 +492,7 @@ func CreateTestSecret(t *testing.T, namespace string, baseName string, secretTyp
err := client.CoreV1().Secrets(namespace).Delete(context.Background(), created.Name, metav1.DeleteOptions{})
require.NoError(t, err)
})
t.Logf("created test Secret %s", created.Name)
t.Logf("created test Secret %s/%s", created.Namespace, created.Name)
return created
}