Skip to content

Commit

Permalink
feat(base-cluster/rbac)!: allow to use the k8s default ClusterRoles (#…
Browse files Browse the repository at this point in the history
…1230)

The most often used rbac roles are exactly the default ones, this eases
that configuration

this is breaking because one might already use these names, but they are
now forbidden
  • Loading branch information
cwrau authored Nov 11, 2024
1 parent 7d103b1 commit a3b24e4
Show file tree
Hide file tree
Showing 3 changed files with 49 additions and 32 deletions.
72 changes: 42 additions & 30 deletions charts/base-cluster/templates/rbac/_rbac.tpl
Original file line number Diff line number Diff line change
@@ -1,38 +1,50 @@
{{- define "base-cluster.rbac.roles" -}}
{{- $roles := dict -}}
{{- $definedRoles := .roles -}}
{{- $definedNamespaces := .namespaces -}}
{{- range $accountName, $account := .accounts -}}
{{- range $roleName, $namespaces := dig "roles" (dict) $account -}}
{{- if not (has $roleName $definedRoles) -}}
{{- fail (printf "Role '%s' doesn't exist, used in account '%s'" $roleName $accountName ) -}}
{{- define "base-cluster.rbac.preexistingRoles" -}}
{{- $preexistingRoles := list -}}
{{- range $role := (lookup "rbac.authorization.k8s.io/v1" "ClusterRole" "" "").items -}}
{{/* Only allow the default k8s ClusterRoles */}}
{{- if eq (dig "metadata" "labels" "kubernetes.io/bootstrapping" "" $role) "rbac-defaults" -}}
{{- $preexistingRoles = append $preexistingRoles $role.metadata.name -}}
{{- end -}}
{{- end -}}
{{- toYaml $preexistingRoles -}}
{{- end -}}

{{- $existingRole := dig $roleName (dict) $roles -}}
{{- $namespaceMapping := dig "namespaceMapping" (dict) $existingRole -}}
{{- range $roleNamespace := $namespaces -}}
{{- if not (has $roleNamespace $definedNamespaces) -}}
{{- fail (printf "Role '%s' wants to be in the undefined namespace '%s'" $roleName $roleNamespace) -}}
{{- define "base-cluster.rbac.roles" -}}
{{- $roles := dict -}}
{{- $definedRoles := .roles -}}
{{- $preexistingRoles := include "base-cluster.rbac.preexistingRoles" (dict) | fromYamlArray -}}
{{- $definedNamespaces := .namespaces -}}
{{- range $accountName, $account := .accounts -}}
{{- range $roleName, $namespaces := dig "roles" (dict) $account -}}
{{- if and (not (has $roleName $definedRoles)) (not (has $roleName $preexistingRoles)) -}}
{{- fail (printf "Role '%s' doesn't exist, used in account '%s'" $roleName $accountName ) -}}
{{- end -}}

{{- $existingNamespace := dig $roleNamespace (list) $namespaceMapping -}}
{{- $existingNamespace = append $existingNamespace $accountName -}}
{{- $namespaceMapping = set $namespaceMapping $roleNamespace $existingNamespace -}}
{{- end -}}
{{- $existingRole = set $existingRole "namespaceMapping" $namespaceMapping -}}
{{- $roles = set $roles $roleName $existingRole -}}
{{- end -}}
{{- range $roleName := dig "clusterRoles" (list) $account -}}
{{- if not (has $roleName $definedRoles) -}}
{{- fail (printf "Role '%s' doesn't exist, used in account '%s'" $roleName $accountName ) -}}
{{- $existingRole := dig $roleName (dict) $roles -}}
{{- $namespaceMapping := dig "namespaceMapping" (dict) $existingRole -}}
{{- range $roleNamespace := $namespaces -}}
{{- if not (has $roleNamespace $definedNamespaces) -}}
{{- fail (printf "Role '%s' wants to be in the undefined namespace '%s'" $roleName $roleNamespace) -}}
{{- end -}}

{{- $existingNamespace := dig $roleNamespace (list) $namespaceMapping -}}
{{- $existingNamespace = append $existingNamespace $accountName -}}
{{- $namespaceMapping = set $namespaceMapping $roleNamespace $existingNamespace -}}
{{- end -}}
{{- $existingRole = set $existingRole "namespaceMapping" $namespaceMapping -}}
{{- $roles = set $roles $roleName $existingRole -}}
{{- end -}}
{{- range $roleName := dig "clusterRoles" (list) $account -}}
{{- if not (has $roleName $definedRoles) -}}
{{- fail (printf "Role '%s' doesn't exist, used in account '%s'" $roleName $accountName ) -}}
{{- end -}}

{{- $existingRole := dig $roleName (dict) $roles -}}
{{- $clusterMapping := dig "clusterMapping" (list) $existingRole -}}
{{- $clusterMapping = append $clusterMapping $accountName -}}
{{- $existingRole = set $existingRole "clusterMapping" $clusterMapping -}}
{{- $roles = set $roles $roleName $existingRole -}}
{{- $existingRole := dig $roleName (dict) $roles -}}
{{- $clusterMapping := dig "clusterMapping" (list) $existingRole -}}
{{- $clusterMapping = append $clusterMapping $accountName -}}
{{- $existingRole = set $existingRole "clusterMapping" $clusterMapping -}}
{{- $roles = set $roles $roleName $existingRole -}}
{{- end -}}
{{- end -}}
{{- end -}}
{{- toYaml $roles -}}
{{- toYaml $roles -}}
{{- end -}}
5 changes: 3 additions & 2 deletions charts/base-cluster/templates/rbac/roleBindings.yaml
Original file line number Diff line number Diff line change
@@ -1,9 +1,10 @@
{{- $roles := include "base-cluster.rbac.roles" (dict "accounts" .Values.rbac.accounts "roles" (.Values.rbac.roles | keys) "namespaces" (include "base-cluster.enabled-namespaces" . | fromYaml | keys)) | fromYaml -}}
{{- $definedRoles := .Values.rbac.roles | keys -}}

{{- range $roleName, $roleMapping := $roles -}}
{{- $clusterMapping := dig "clusterMapping" (dict) $roleMapping -}}
{{- $namespaceMapping := dig "namespaceMapping" (dict) $roleMapping -}}
{{- $roleFullName := printf "%s-%s" (include "common.names.fullname" $) $roleName -}}
{{- $roleFullName := has $roleName $definedRoles | ternary (printf "%s-%s" (include "common.names.fullname" $) $roleName) $roleName -}}
{{- range $namespace, $accounts := $namespaceMapping }}
---
apiVersion: rbac.authorization.k8s.io/v1
Expand Down Expand Up @@ -43,4 +44,4 @@ roleRef:
kind: ClusterRole
name: {{ $roleFullName }}
{{- end }}
{{- end }}
{{- end }}
4 changes: 4 additions & 0 deletions charts/base-cluster/templates/rbac/roles.yaml
Original file line number Diff line number Diff line change
@@ -1,8 +1,12 @@
{{- $preExistingRoles := include "base-cluster.rbac.preexistingRoles" (dict) | fromYamlArray -}}
{{- $usedRoles := include "base-cluster.rbac.roles" (dict "accounts" .Values.rbac.accounts "roles" (.Values.rbac.roles | keys) "namespaces" (include "base-cluster.enabled-namespaces" . | fromYaml | keys)) | fromYaml -}}

{{- range $name, $spec := .Values.rbac.roles -}}
{{- if not (hasKey $usedRoles $name) -}}
{{- fail (printf "Role '%s' is not used by any account" $name) -}}
{{- end -}}
{{- if has $name $preExistingRoles -}}
{{- fail (printf "Role '%s' clashes with preexisting ClusterRole" $name) -}}
{{- end }}
---
apiVersion: rbac.authorization.k8s.io/v1
Expand Down

0 comments on commit a3b24e4

Please sign in to comment.