-
Notifications
You must be signed in to change notification settings - Fork 96
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Support finding unused roles and SA fix (#12)
* add support for finding unused roles * find serviceaccounts used in rolebinding and clusterrolebinding * update documentation with role command and SA fix --------- Co-authored-by: Yonah Dissen <ydissen@vmware.com>
- Loading branch information
Showing
5 changed files
with
199 additions
and
10 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,21 @@ | ||
package kor | ||
|
||
import ( | ||
"github.com/spf13/cobra" | ||
"github.com/yonahd/kor/pkg/kor" | ||
) | ||
|
||
var roleCmd = &cobra.Command{ | ||
Use: "role", | ||
Short: "Gets unused roles", | ||
Args: cobra.NoArgs, | ||
Run: func(cmd *cobra.Command, args []string) { | ||
kor.GetUnusedRoles(namespace) | ||
|
||
}, | ||
} | ||
|
||
func init() { | ||
roleCmd.PersistentFlags().StringVarP(&namespace, "namespace", "n", "", "Namespace to run on") | ||
rootCmd.AddCommand(roleCmd) | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,103 @@ | ||
package kor | ||
|
||
import ( | ||
"context" | ||
"fmt" | ||
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" | ||
"k8s.io/client-go/kubernetes" | ||
_ "k8s.io/client-go/plugin/pkg/client/auth/oidc" | ||
"os" | ||
) | ||
|
||
func retrieveUsedRoles(clientset *kubernetes.Clientset, namespace string) ([]string, error) { | ||
// Get a list of all role bindings in the specified namespace | ||
roleBindings, err := clientset.RbacV1().RoleBindings(namespace).List(context.TODO(), metav1.ListOptions{}) | ||
if err != nil { | ||
return nil, fmt.Errorf("failed to list role bindings in namespace %s: %v", namespace, err) | ||
} | ||
|
||
// Create a map to store role binding names | ||
usedRoles := make(map[string]bool) | ||
|
||
// Populate the map with role binding names | ||
for _, rb := range roleBindings.Items { | ||
usedRoles[rb.RoleRef.Name] = true | ||
} | ||
|
||
// Create a slice to store used role names | ||
var usedRoleNames []string | ||
|
||
// Extract used role names from the map | ||
for role := range usedRoles { | ||
usedRoleNames = append(usedRoleNames, role) | ||
} | ||
|
||
return usedRoleNames, nil | ||
} | ||
|
||
func retrieveRoleNames(kubeClient *kubernetes.Clientset, namespace string) ([]string, error) { | ||
roles, err := kubeClient.RbacV1().Roles(namespace).List(context.TODO(), metav1.ListOptions{}) | ||
if err != nil { | ||
return nil, err | ||
} | ||
names := make([]string, 0, len(roles.Items)) | ||
for _, role := range roles.Items { | ||
names = append(names, role.Name) | ||
} | ||
return names, nil | ||
} | ||
|
||
func calculateRoleDifference(usedRoles []string, roleNames []string) []string { | ||
difference := []string{} | ||
for _, name := range roleNames { | ||
found := false | ||
for _, usedName := range usedRoles { | ||
if name == usedName { | ||
found = true | ||
break | ||
} | ||
} | ||
if !found { | ||
difference = append(difference, name) | ||
} | ||
} | ||
return difference | ||
} | ||
|
||
func processNamespaceRoles(kubeClient *kubernetes.Clientset, namespace string) ([]string, error) { | ||
usedRoles, err := retrieveUsedRoles(kubeClient, namespace) | ||
if err != nil { | ||
return nil, err | ||
} | ||
|
||
usedRoles = RemoveDuplicatesAndSort(usedRoles) | ||
|
||
roleNames, err := retrieveRoleNames(kubeClient, namespace) | ||
if err != nil { | ||
return nil, err | ||
} | ||
|
||
diff := calculateRoleDifference(usedRoles, roleNames) | ||
return diff, nil | ||
|
||
} | ||
|
||
func GetUnusedRoles(namespace string) { | ||
var kubeClient *kubernetes.Clientset | ||
var namespaces []string | ||
|
||
kubeClient = GetKubeClient() | ||
|
||
namespaces = SetNamespaceList(namespace, kubeClient) | ||
|
||
for _, namespace := range namespaces { | ||
diff, err := processNamespaceRoles(kubeClient, namespace) | ||
if err != nil { | ||
fmt.Fprintf(os.Stderr, "Failed to process namespace %s: %v\n", namespace, err) | ||
continue | ||
} | ||
output := FormatOutput(namespace, diff, "Roles") | ||
fmt.Println(output) | ||
fmt.Println() | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters