@@ -20,6 +20,7 @@ import (
2020 "context"
2121 "fmt"
2222 "path"
23+ "slices"
2324 "strings"
2425 "testing"
2526 "time"
@@ -477,89 +478,104 @@ func testHappyCase(
477478 _ , err := providerCoreClient .Namespaces ().Get (ctx , actualProviderNamespace , metav1.GetOptions {})
478479 require .NoError (t , err , "Actual provider side namespace object should exist" )
479480
481+ expectedVerbs := []string {"get" , "list" , "watch" , "create" , "update" , "patch" , "delete" }
482+ slices .Sort (expectedVerbs )
483+
480484 switch informerScope {
481485 case kubebindv1alpha2 .ClusterScope :
482486 t .Logf ("Verifying RBAC resources were created for secret management in cluster scope" )
483487 rbacClient := framework .KubeClient (t , providerConfig ).RbacV1 ()
484488
485- clusterRoles , err := rbacClient . ClusterRoles (). List ( ctx , metav1. ListOptions {})
486- require . NoError ( t , err )
487-
488- var foundSecretClusterRole bool
489- for _ , cr := range clusterRoles . Items {
490- if strings . Contains ( cr . Name , "kube-binder-export" ) {
491- for _ , rule := range cr . Rules {
492- for _ , resource := range rule . Resources {
493- if resource == "secrets" {
494- foundSecretClusterRole = true
495- require . Contains ( t , rule . Verbs , "*" , "ClusterRole should have * permissions for secrets" )
496- require . Contains ( t , rule .APIGroups , "" , "ClusterRole should target core API group" )
497- break
498- }
489+ require . Eventually ( t , func () bool {
490+ clusterRoles , err := rbacClient . ClusterRoles (). List ( ctx , metav1. ListOptions {} )
491+ require . NoError ( t , err )
492+ for _ , clusterRole := range clusterRoles . Items {
493+ if ! strings . HasPrefix ( clusterRole . Name , "kube-binder-claims-" ) {
494+ continue
495+ }
496+ for _ , rule := range clusterRole . Rules {
497+ if ! slices . Contains ( rule . Resources , "secrets" ) || ! slices . Contains ( rule . APIGroups , "" ) {
498+ continue
499+ }
500+ slices . Sort ( rule .Verbs )
501+ if slices . Equal ( expectedVerbs , rule . Verbs ) {
502+ return true
499503 }
500504 }
501505 }
502- }
503- require . True ( t , foundSecretClusterRole , "ClusterRole for secrets should be created " )
506+ return false
507+ }, wait . ForeverTestTimeout , time . Millisecond * 100 , "waiting for ClusterRole for claimed secrets resource to be ready on provider side " )
504508
505- t .Logf ("Verifying ClusterRoleBinding was created for pre-seeded namespace secret access" )
506- clusterRoleBindings , err := rbacClient .ClusterRoleBindings ().List (ctx , metav1.ListOptions {})
507- require .NoError (t , err )
509+ t .Logf ("Verifying ClusterRole for secrets claim has been aggregated into kube-binder-exports ClusterRole" )
508510
509- var foundSecretClusterRoleBinding bool
510- for _ , crb := range clusterRoleBindings .Items {
511- if strings .Contains (crb .Name , "kube-binder-export" ) {
512- for _ , subject := range crb .Subjects {
513- if subject .Kind == "ServiceAccount" && subject .Name == kuberesources .ServiceAccountName {
514- foundSecretClusterRoleBinding = true
515- require .Equal (t , "ClusterRole" , crb .RoleRef .Kind , "Should reference ClusterRole" )
516- break
517- }
511+ require .Eventually (t , func () bool {
512+ aggregatingClusterRole , err := rbacClient .ClusterRoles ().Get (ctx , "kube-binder-exports" , metav1.GetOptions {})
513+ require .NoError (t , err ) // kube-binder-exports must already exist: it is created before kube-binder-claims-* ClusterRole.
514+ for _ , rule := range aggregatingClusterRole .Rules {
515+ if ! slices .Contains (rule .Resources , "secrets" ) || ! slices .Contains (rule .APIGroups , "" ) {
516+ continue
517+ }
518+ slices .Sort (rule .Verbs )
519+ if slices .Equal (expectedVerbs , rule .Verbs ) {
520+ return true
518521 }
519522 }
520- }
521- require .True (t , foundSecretClusterRoleBinding , "ClusterRoleBinding for ServiceAccount should be created" )
523+ return false
524+ }, wait .ForeverTestTimeout , time .Millisecond * 100 , "waiting for ClusterRoleBinding to be ready on provider side" )
525+
526+ t .Logf ("Verifying ClusterRoleBinding for kube-binder-exports ClusterRole was created" )
527+
528+ require .Eventually (t , func () bool {
529+ aggregatingCRB , err := rbacClient .ClusterRoleBindings ().Get (ctx , "kube-binder-exports" , metav1.GetOptions {})
530+ require .NoError (t , err )
531+ for _ , subject := range aggregatingCRB .Subjects {
532+ if subject .Kind == "ServiceAccount" && subject .Name == kuberesources .ServiceAccountName {
533+ return true
534+ }
535+ }
536+ return false
537+ }, wait .ForeverTestTimeout , time .Millisecond * 100 , "waiting for ClusterRoleBinding kube-binder-exports to be ready on provider side" )
522538 case kubebindv1alpha2 .NamespacedScope :
523539 t .Logf ("Verifying RBAC resources were created for secret management in namespace scope" )
524540 rbacClient := framework .KubeClient (t , providerConfig ).RbacV1 ()
525541
526- roles , err := rbacClient .Roles (consumer .providerObjectNamespace ).List (ctx , metav1.ListOptions {})
527- require .NoError (t , err )
528-
529- var foundSecretRole bool
530- for _ , cr := range roles .Items {
531- if strings .Contains (cr .Name , "kube-binder-export" ) {
542+ require .Eventually (t , func () bool {
543+ roles , err := rbacClient .Roles (consumer .providerObjectNamespace ).List (ctx , metav1.ListOptions {})
544+ require .NoError (t , err )
545+ for _ , cr := range roles .Items {
546+ if ! strings .HasPrefix (cr .Name , "kube-binder-claims-" ) {
547+ continue
548+ }
532549 for _ , rule := range cr .Rules {
533- for _ , resource := range rule .Resources {
534- if resource == "secrets" {
535- foundSecretRole = true
536- require .Contains (t , rule .Verbs , "*" , "Role should have * permissions for secrets" )
537- require .Contains (t , rule .APIGroups , "" , "Role should target core API group" )
538- break
539- }
550+ if ! slices .Contains (rule .Resources , "secrets" ) || ! slices .Contains (rule .APIGroups , "" ) {
551+ continue
552+ }
553+ slices .Sort (rule .Verbs )
554+ if slices .Equal (expectedVerbs , rule .Verbs ) {
555+ return true
540556 }
541557 }
542558 }
543- }
544- require . True ( t , foundSecretRole , "Role for secrets should be created " )
559+ return false
560+ }, wait . ForeverTestTimeout , time . Millisecond * 100 , "waiting for RoleBinding for claimed secrets resource to be ready on provider side " )
545561
546562 t .Logf ("Verifying RoleBinding was created for pre-seeded namespace secret access" )
547- roleBindings , err := rbacClient .RoleBindings (consumer .providerObjectNamespace ).List (ctx , metav1.ListOptions {})
548- require .NoError (t , err )
549563
550- var foundSecretRoleBinding bool
551- for _ , crb := range roleBindings .Items {
552- if strings .Contains (crb .Name , "kube-binder-" ) && strings .Contains (crb .Name , "-export-" ) {
553- for _ , subject := range crb .Subjects {
564+ require .Eventually (t , func () bool {
565+ roleBindings , err := rbacClient .RoleBindings (consumer .providerObjectNamespace ).List (ctx , metav1.ListOptions {})
566+ require .NoError (t , err )
567+ for _ , rb := range roleBindings .Items {
568+ if ! strings .HasPrefix (rb .Name , "kube-binder-claims-" ) {
569+ continue
570+ }
571+ for _ , subject := range rb .Subjects {
554572 if subject .Kind == "ServiceAccount" && subject .Name == kuberesources .ServiceAccountName {
555- foundSecretRoleBinding = true
556- require .Equal (t , "Role" , crb .RoleRef .Kind , "Should reference Role" )
557- break
573+ return true
558574 }
559575 }
560576 }
561- }
562- require . True ( t , foundSecretRoleBinding , "RoleBinding for ServiceAccount should be created " )
577+ return false
578+ }, wait . ForeverTestTimeout , time . Millisecond * 100 , "waiting for RoleBinding for claimed secrets resource to be ready on provider side " )
563579 }
564580
565581 t .Logf ("Provider side namespace pre-seeding and secret management RBAC verified successfully" )
0 commit comments