Skip to content

Commit

Permalink
Limit manager to given namespace
Browse files Browse the repository at this point in the history
This should improve security; controller will only be able to check secrets in it's own namespace.
It also has the potential to lower resource usage drastically on bigger clusters with many objects.
  • Loading branch information
bastjan committed Nov 2, 2023
1 parent 0462c4c commit 5d943ce
Show file tree
Hide file tree
Showing 6 changed files with 53 additions and 12 deletions.
1 change: 1 addition & 0 deletions config/manager/manager.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,7 @@ spec:
containers:
- args:
- --leader-elect
- --namespace=$(POD_NAMESPACE)
env:
- name: POD_NAMESPACE
valueFrom:
Expand Down
19 changes: 13 additions & 6 deletions config/rbac/role.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,19 @@ kind: ClusterRole
metadata:
name: manager-role
rules:
- apiGroups:
- authentication.k8s.io
resources:
- tokenreviews
verbs:
- create
---
apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
name: manager-role
namespace: system
rules:
- apiGroups:
- ""
resources:
Expand Down Expand Up @@ -33,12 +46,6 @@ rules:
- serviceaccounts/token
verbs:
- create
- apiGroups:
- authentication.k8s.io
resources:
- tokenreviews
verbs:
- create
- apiGroups:
- cluster.appuio.io
resources:
Expand Down
20 changes: 20 additions & 0 deletions config/rbac/role_binding.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -17,3 +17,23 @@ subjects:
- kind: ServiceAccount
name: controller-manager
namespace: system
---
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
labels:
app.kubernetes.io/name: rolebinding
app.kubernetes.io/instance: manager-rolebinding
app.kubernetes.io/component: rbac
app.kubernetes.io/created-by: emergency-credentials-controller
app.kubernetes.io/part-of: emergency-credentials-controller
app.kubernetes.io/managed-by: kustomize
name: manager-rolebinding
namespace: system
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: Role
name: manager-role
subjects:
- kind: ServiceAccount
name: controller-manager
10 changes: 5 additions & 5 deletions controllers/emergencyaccount_controller.go
Original file line number Diff line number Diff line change
Expand Up @@ -35,12 +35,12 @@ type EmergencyAccountReconciler struct {
Clock Clock
}

//+kubebuilder:rbac:groups=cluster.appuio.io,resources=emergencyaccounts,verbs=get;list;watch;create;update;patch;delete
//+kubebuilder:rbac:groups=cluster.appuio.io,resources=emergencyaccounts/status,verbs=get;update;patch
//+kubebuilder:rbac:groups=cluster.appuio.io,resources=emergencyaccounts/finalizers,verbs=update
//+kubebuilder:rbac:groups=cluster.appuio.io,resources=emergencyaccounts,verbs=get;list;watch;create;update;patch;delete,namespace="system"
//+kubebuilder:rbac:groups=cluster.appuio.io,resources=emergencyaccounts/status,verbs=get;update;patch,namespace="system"
//+kubebuilder:rbac:groups=cluster.appuio.io,resources=emergencyaccounts/finalizers,verbs=update,namespace="system"

//+kubebuilder:rbac:groups="",resources=serviceaccounts,verbs=get;list;watch;create;update;patch;delete
//+kubebuilder:rbac:groups="",resources=serviceaccounts/token,verbs=create
//+kubebuilder:rbac:groups="",resources=serviceaccounts,verbs=get;list;watch;create;update;patch;delete,namespace="system"
//+kubebuilder:rbac:groups="",resources=serviceaccounts/token,verbs=create,namespace="system"

//+kubebuilder:rbac:groups=authentication.k8s.io,resources=tokenreviews,verbs=create

Expand Down
2 changes: 1 addition & 1 deletion controllers/stores/secret_store.go
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ import (
"sigs.k8s.io/controller-runtime/pkg/log"
)

//+kubebuilder:rbac:groups="",resources=secrets,verbs=get;list;watch;create;update;patch
//+kubebuilder:rbac:groups="",resources=secrets,verbs=get;list;watch;create;update;patch,namespace="system"

type SecretStore struct {
SecretStoreSpec emcv1beta1.SecretStoreSpec
Expand Down
13 changes: 13 additions & 0 deletions main.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,12 +8,14 @@ import (
// Import all Kubernetes client auth plugins (e.g. Azure, GCP, OIDC, etc.)
// to ensure that exec-entrypoint and run can make use of them.
_ "k8s.io/client-go/plugin/pkg/client/auth"
"k8s.io/client-go/rest"

authenticationv1 "k8s.io/api/authentication/v1"
"k8s.io/apimachinery/pkg/runtime"
utilruntime "k8s.io/apimachinery/pkg/util/runtime"
clientgoscheme "k8s.io/client-go/kubernetes/scheme"
ctrl "sigs.k8s.io/controller-runtime"
"sigs.k8s.io/controller-runtime/pkg/cache"
"sigs.k8s.io/controller-runtime/pkg/healthz"
"sigs.k8s.io/controller-runtime/pkg/log/zap"
"sigs.k8s.io/controller-runtime/pkg/metrics/server"
Expand All @@ -40,11 +42,13 @@ func main() {
var metricsAddr string
var enableLeaderElection bool
var probeAddr string
var namespace string
flag.StringVar(&metricsAddr, "metrics-bind-address", ":8080", "The address the metric endpoint binds to.")
flag.StringVar(&probeAddr, "health-probe-bind-address", ":8081", "The address the probe endpoint binds to.")
flag.BoolVar(&enableLeaderElection, "leader-elect", false,
"Enable leader election for controller manager. "+
"Enabling this will ensure there is only one active controller manager.")
flag.StringVar(&namespace, "namespace", "default", "The namespace to watch for EmergencyAccount resources.")
opts := zap.Options{
Development: true,
}
Expand All @@ -53,6 +57,7 @@ func main() {

ctrl.SetLogger(zap.New(zap.UseFlagOptions(&opts)))

setupLog.Info("limiting manager and cache to namespace", "namespace", namespace)
mgr, err := ctrl.NewManager(ctrl.GetConfigOrDie(), ctrl.Options{
Scheme: scheme,
Metrics: server.Options{
Expand All @@ -72,6 +77,14 @@ func main() {
// if you are doing or is intended to do any operation such as perform cleanups
// after the manager stops then its usage might be unsafe.
// LeaderElectionReleaseOnCancel: true,

// Limit the manager to only watch the namespace the controller is running in.
NewCache: func(config *rest.Config, opts cache.Options) (cache.Cache, error) {
opts.DefaultNamespaces = map[string]cache.Config{
namespace: {},
}
return cache.New(config, opts)
},
})
if err != nil {
setupLog.Error(err, "unable to start manager")
Expand Down

0 comments on commit 5d943ce

Please sign in to comment.