Merge pull request #2846 from Infisical/misc/operator-namespace-installation

feat: k8 operator namespace installation
This commit is contained in:
Maidul Islam
2024-12-13 14:10:45 -05:00
committed by GitHub
6 changed files with 75 additions and 19 deletions
@@ -41,6 +41,30 @@ The operator can be install via [Helm](https://helm.sh) or [kubectl](https://git
helm install --generate-name infisical-helm-charts/secrets-operator --version=0.1.4 --set controllerManager.manager.image.tag=v0.2.0 helm install --generate-name infisical-helm-charts/secrets-operator --version=0.1.4 --set controllerManager.manager.image.tag=v0.2.0
``` ```
**Namespace-scoped Installation**
The operator can be configured to watch and manage secrets in a specific namespace instead of having cluster-wide access.
```bash
helm install operator infisical-helm-charts/secrets-operator \
--namespace your-namespace \
--set scopedNamespace=your-namespace \
--set scopedRBAC=true
```
When scoped to a namespace, the operator will:
- Only watch InfisicalSecrets in the specified namespace
- Only create/update Kubernetes secrets in that namespace
- Only access deployments in that namespace
The default configuration gives cluster-wide access:
```yaml
scopedNamespace: "" # Empty for cluster-wide access
scopedRBAC: false # Cluster-wide permissions
```
</Tab> </Tab>
<Tab title="Kubectl"> <Tab title="Kubectl">
For production deployments, it is highly recommended to set the version of the Kubernetes operator manually instead of pointing to the latest version. For production deployments, it is highly recommended to set the version of the Kubernetes operator manually instead of pointing to the latest version.
+2 -2
View File
@@ -13,9 +13,9 @@ type: application
# This is the chart version. This version number should be incremented each time you make changes # This is the chart version. This version number should be incremented each time you make changes
# to the chart and its templates, including the app version. # to the chart and its templates, including the app version.
# Versions are expected to follow Semantic Versioning (https://semver.org/) # Versions are expected to follow Semantic Versioning (https://semver.org/)
version: v0.7.5 version: v0.7.6
# This is the version number of the application being deployed. This version number should be # This is the version number of the application being deployed. This version number should be
# incremented each time you make changes to the application. Versions are not expected to # incremented each time you make changes to the application. Versions are not expected to
# follow Semantic Versioning. They should reflect the version the application is using. # follow Semantic Versioning. They should reflect the version the application is using.
# It is recommended to use it with quotes. # It is recommended to use it with quotes.
appVersion: "v0.7.5" appVersion: "v0.7.6"
@@ -54,7 +54,11 @@ spec:
10 }} 10 }}
securityContext: {{- toYaml .Values.controllerManager.kubeRbacProxy.containerSecurityContext securityContext: {{- toYaml .Values.controllerManager.kubeRbacProxy.containerSecurityContext
| nindent 10 }} | nindent 10 }}
- args: {{- toYaml .Values.controllerManager.manager.args | nindent 8 }} - args:
{{- toYaml .Values.controllerManager.manager.args | nindent 8 }}
{{- if and .Values.scopedNamespace .Values.scopedRBAC }}
- --namespace={{ .Values.scopedNamespace }}
{{- end }}
command: command:
- /manager - /manager
env: env:
@@ -1,7 +1,14 @@
apiVersion: rbac.authorization.k8s.io/v1 apiVersion: rbac.authorization.k8s.io/v1
{{- if and .Values.scopedNamespace .Values.scopedRBAC }}
kind: Role
{{- else }}
kind: ClusterRole kind: ClusterRole
{{- end }}
metadata: metadata:
name: {{ include "secrets-operator.fullname" . }}-manager-role name: {{ include "secrets-operator.fullname" . }}-manager-role
{{- if and .Values.scopedNamespace .Values.scopedRBAC }}
namespace: {{ .Values.scopedNamespace | quote }}
{{- end }}
labels: labels:
{{- include "secrets-operator.labels" . | nindent 4 }} {{- include "secrets-operator.labels" . | nindent 4 }}
rules: rules:
@@ -72,9 +79,16 @@ rules:
- update - update
--- ---
apiVersion: rbac.authorization.k8s.io/v1 apiVersion: rbac.authorization.k8s.io/v1
{{- if and .Values.scopedNamespace .Values.scopedRBAC }}
kind: RoleBinding
{{- else }}
kind: ClusterRoleBinding kind: ClusterRoleBinding
{{- end }}
metadata: metadata:
name: {{ include "secrets-operator.fullname" . }}-manager-rolebinding name: {{ include "secrets-operator.fullname" . }}-manager-rolebinding
{{- if and .Values.scopedNamespace .Values.scopedRBAC }}
namespace: {{ .Values.scopedNamespace | quote }}
{{- end }}
labels: labels:
app.kubernetes.io/component: rbac app.kubernetes.io/component: rbac
app.kubernetes.io/created-by: k8-operator app.kubernetes.io/created-by: k8-operator
@@ -82,7 +96,11 @@ metadata:
{{- include "secrets-operator.labels" . | nindent 4 }} {{- include "secrets-operator.labels" . | nindent 4 }}
roleRef: roleRef:
apiGroup: rbac.authorization.k8s.io apiGroup: rbac.authorization.k8s.io
{{- if and .Values.scopedNamespace .Values.scopedRBAC }}
kind: Role
{{- else }}
kind: ClusterRole kind: ClusterRole
{{- end }}
name: '{{ include "secrets-operator.fullname" . }}-manager-role' name: '{{ include "secrets-operator.fullname" . }}-manager-role'
subjects: subjects:
- kind: ServiceAccount - kind: ServiceAccount
+16 -14
View File
@@ -1,15 +1,15 @@
controllerManager: controllerManager:
kubeRbacProxy: kubeRbacProxy:
args: args:
- --secure-listen-address=0.0.0.0:8443 - --secure-listen-address=0.0.0.0:8443
- --upstream=http://127.0.0.1:8080/ - --upstream=http://127.0.0.1:8080/
- --logtostderr=true - --logtostderr=true
- --v=0 - --v=0
containerSecurityContext: containerSecurityContext:
allowPrivilegeEscalation: false allowPrivilegeEscalation: false
capabilities: capabilities:
drop: drop:
- ALL - ALL
image: image:
repository: gcr.io/kubebuilder/kube-rbac-proxy repository: gcr.io/kubebuilder/kube-rbac-proxy
tag: v0.15.0 tag: v0.15.0
@@ -22,17 +22,17 @@ controllerManager:
memory: 64Mi memory: 64Mi
manager: manager:
args: args:
- --health-probe-bind-address=:8081 - --health-probe-bind-address=:8081
- --metrics-bind-address=127.0.0.1:8080 - --metrics-bind-address=127.0.0.1:8080
- --leader-elect - --leader-elect
containerSecurityContext: containerSecurityContext:
allowPrivilegeEscalation: false allowPrivilegeEscalation: false
capabilities: capabilities:
drop: drop:
- ALL - ALL
image: image:
repository: infisical/kubernetes-operator repository: infisical/kubernetes-operator
tag: v0.7.5 tag: v0.7.6
resources: resources:
limits: limits:
cpu: 500m cpu: 500m
@@ -46,10 +46,12 @@ controllerManager:
nodeSelector: {} nodeSelector: {}
tolerations: [] tolerations: []
kubernetesClusterDomain: cluster.local kubernetesClusterDomain: cluster.local
scopedNamespace: ""
scopedRBAC: false
metricsService: metricsService:
ports: ports:
- name: https - name: https
port: 8443 port: 8443
protocol: TCP protocol: TCP
targetPort: https targetPort: https
type: ClusterIP type: ClusterIP
+10 -2
View File
@@ -36,8 +36,10 @@ func main() {
var metricsAddr string var metricsAddr string
var enableLeaderElection bool var enableLeaderElection bool
var probeAddr string var probeAddr string
var namespace string
flag.StringVar(&metricsAddr, "metrics-bind-address", ":8080", "The address the metric endpoint binds to.") 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.StringVar(&probeAddr, "health-probe-bind-address", ":8081", "The address the probe endpoint binds to.")
flag.StringVar(&namespace, "namespace", "", "Watch InfisicalSecrets scoped in the provided namespace only")
flag.BoolVar(&enableLeaderElection, "leader-elect", false, flag.BoolVar(&enableLeaderElection, "leader-elect", false,
"Enable leader election for controller manager. "+ "Enable leader election for controller manager. "+
"Enabling this will ensure there is only one active controller manager.") "Enabling this will ensure there is only one active controller manager.")
@@ -49,7 +51,7 @@ func main() {
ctrl.SetLogger(zap.New(zap.UseFlagOptions(&opts))) ctrl.SetLogger(zap.New(zap.UseFlagOptions(&opts)))
mgr, err := ctrl.NewManager(ctrl.GetConfigOrDie(), ctrl.Options{ ctrlOpts := ctrl.Options{
Scheme: scheme, Scheme: scheme,
MetricsBindAddress: metricsAddr, MetricsBindAddress: metricsAddr,
Port: 9443, Port: 9443,
@@ -67,7 +69,13 @@ func main() {
// if you are doing or is intended to do any operation such as perform cleanups // 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. // after the manager stops then its usage might be unsafe.
// LeaderElectionReleaseOnCancel: true, // LeaderElectionReleaseOnCancel: true,
}) }
if namespace != "" {
ctrlOpts.Namespace = namespace
}
mgr, err := ctrl.NewManager(ctrl.GetConfigOrDie(), ctrlOpts)
if err != nil { if err != nil {
setupLog.Error(err, "unable to start manager") setupLog.Error(err, "unable to start manager")
os.Exit(1) os.Exit(1)