Add initial version with help and admission controller (#1)

- It adds a helm chart that will be hosted in the Github pages URL of this repository
- an admission controller operator 
- Basic documentation for installing the operator, configuring CRDs and example pod configuration
This commit is contained in:
M. Essam
2025-01-29 22:44:09 +01:00
committed by GitHub
parent 50aa9ada37
commit 64091a6439
45 changed files with 4638 additions and 9 deletions
+23
View File
@@ -0,0 +1,23 @@
# Patterns to ignore when building packages.
# This supports shell glob matching, relative path matching, and
# negation (prefixed with !). Only one pattern per line.
.DS_Store
# Common VCS dirs
.git/
.gitignore
.bzr/
.bzrignore
.hg/
.hgignore
.svn/
# Common backup files
*.swp
*.bak
*.tmp
*.orig
*~
# Various IDEs
.project
.idea/
*.tmproj
.vscode/
+6
View File
@@ -0,0 +1,6 @@
apiVersion: v2
name: netbird-operator
description: A Helm chart for Kubernetes
type: application
version: 0.1.0
appVersion: "v0.1.0"
@@ -0,0 +1,116 @@
---
apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
metadata:
annotations:
controller-gen.kubebuilder.io/version: v0.17.1
name: nbsetupkeys.netbird.io
spec:
group: netbird.io
names:
kind: NBSetupKey
listKind: NBSetupKeyList
plural: nbsetupkeys
singular: nbsetupkey
scope: Namespaced
versions:
- name: v1
schema:
openAPIV3Schema:
description: NBSetupKey is the Schema for the nbsetupkeys API.
properties:
apiVersion:
description: |-
APIVersion defines the versioned schema of this representation of an object.
Servers should convert recognized schemas to the latest internal value, and
may reject unrecognized values.
More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources
type: string
kind:
description: |-
Kind is a string value representing the REST resource this object represents.
Servers may infer this from the endpoint the client submits requests to.
Cannot be updated.
In CamelCase.
More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds
type: string
metadata:
type: object
spec:
description: NBSetupKeySpec defines the desired state of NBSetupKey.
properties:
managementURL:
description: ManagementURL optional, override operator management
URL
type: string
secretKeyRef:
description: SecretKeyRef is a reference to the secret containing
the setup key
properties:
key:
description: The key of the secret to select from. Must be a
valid secret key.
type: string
name:
default: ""
description: |-
Name of the referent.
This field is effectively required, but due to backwards compatibility is
allowed to be empty. Instances of this type with an empty value here are
almost certainly wrong.
More info: https://kubernetes.io/docs/concepts/overview/working-with-objects/names/#names
type: string
optional:
description: Specify whether the Secret or its key must be defined
type: boolean
required:
- key
type: object
x-kubernetes-map-type: atomic
required:
- secretKeyRef
type: object
status:
description: NBSetupKeyStatus defines the observed state of NBSetupKey.
properties:
conditions:
items:
description: NBSetupKeyCondition defines a condition in NBSetupKey
status.
properties:
lastProbeTime:
description: Last time we probed the condition.
format: date-time
type: string
lastTransitionTime:
description: Last time the condition transitioned from one status
to another.
format: date-time
type: string
message:
description: Human-readable message indicating details about
last transition.
type: string
reason:
description: Unique, one-word, CamelCase reason for the condition's
last transition.
type: string
status:
description: |-
Status is the status of the condition.
Can be True, False, Unknown.
type: string
type:
description: Type is the type of the condition.
type: string
required:
- status
- type
type: object
type: array
type: object
type: object
served: true
storage: true
subresources:
status: {}
@@ -0,0 +1,102 @@
{{/*
Expand the name of the chart.
*/}}
{{- define "netbird-operator.name" -}}
{{- default .Chart.Name .Values.nameOverride | trunc 63 | trimSuffix "-" }}
{{- end }}
{{/*
Create a default fully qualified app name.
We truncate at 63 chars because some Kubernetes name fields are limited to this (by the DNS naming spec).
If release name contains chart name it will be used as a full name.
*/}}
{{- define "netbird-operator.fullname" -}}
{{- if .Values.fullnameOverride }}
{{- .Values.fullnameOverride | trunc 63 | trimSuffix "-" }}
{{- else }}
{{- $name := default .Chart.Name .Values.nameOverride }}
{{- if contains $name .Release.Name }}
{{- .Release.Name | trunc 63 | trimSuffix "-" }}
{{- else }}
{{- printf "%s-%s" .Release.Name $name | trunc 63 | trimSuffix "-" }}
{{- end }}
{{- end }}
{{- end }}
{{/*
Create chart name and version as used by the chart label.
*/}}
{{- define "netbird-operator.chart" -}}
{{- printf "%s-%s" .Chart.Name .Chart.Version | replace "+" "_" | trunc 63 | trimSuffix "-" }}
{{- end }}
{{/*
Common labels
*/}}
{{- define "netbird-operator.labels" -}}
helm.sh/chart: {{ include "netbird-operator.chart" . }}
{{ include "netbird-operator.selectorLabels" . }}
{{- if .Chart.AppVersion }}
app.kubernetes.io/version: {{ .Chart.AppVersion | quote }}
{{- end }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
{{- end }}
{{/*
Selector labels
*/}}
{{- define "netbird-operator.selectorLabels" -}}
app.kubernetes.io/name: {{ include "netbird-operator.name" . }}
app.kubernetes.io/instance: {{ .Release.Name }}
{{- end }}
{{/*
Create the name of the service account to use
*/}}
{{- define "netbird-operator.serviceAccountName" -}}
{{- if .Values.operator.serviceAccount.create }}
{{- default (include "netbird-operator.fullname" .) .Values.operator.serviceAccount.name }}
{{- else }}
{{- default "default" .Values.operator.serviceAccount.name }}
{{- end }}
{{- end }}
{{/*
Create the name of the webhook service
*/}}
{{- define "netbird-operator.webhookService" -}}
{{- printf "%s-webhook-service" (include "netbird-operator.fullname" .) -}}
{{- end -}}
{{/*
Create the name of the webhook cert secret
*/}}
{{- define "netbird-operator.webhookCertSecret" -}}
{{- printf "%s-tls" (include "netbird-operator.fullname" .) -}}
{{- end -}}
{{/*
Generate certificates for webhook
*/}}
{{- define "netbird-operator.webhookCerts" -}}
{{- $serviceName := (include "netbird-operator.webhookService" .) -}}
{{- $secretName := (include "netbird-operator.webhookCertSecret" .) -}}
{{- $secret := lookup "v1" "Secret" .Release.Namespace $secretName -}}
{{- if (and .Values.webhook.tls.caCert .Values.webhook.tls.cert .Values.webhook.tls.key) -}}
caCert: {{ .Values.webhook.tls.caCert | b64enc }}
clientCert: {{ .Values.webhook.tls.cert | b64enc }}
clientKey: {{ .Values.webhook.tls.key | b64enc }}
{{- else if and .Values.keepTLSSecret $secret -}}
caCert: {{ index $secret.data "ca.crt" }}
clientCert: {{ index $secret.data "tls.crt" }}
clientKey: {{ index $secret.data "tls.key" }}
{{- else -}}
{{- $altNames := list (printf "%s.%s" $serviceName .Release.Namespace) (printf "%s.%s.svc" $serviceName .Release.Namespace) (printf "%s.%s.svc.%s" $serviceName .Release.Namespace .Values.webhook.cluster.dnsDomain) -}}
{{- $ca := genCA "netbird-operator-ca" 3650 -}}
{{- $cert := genSignedCert (include "netbird-operator.fullname" .) nil $altNames 3650 $ca -}}
caCert: {{ $ca.Cert | b64enc }}
clientCert: {{ $cert.Cert | b64enc }}
clientKey: {{ $cert.Key | b64enc }}
{{- end -}}
{{- end -}}
@@ -0,0 +1,103 @@
apiVersion: apps/v1
kind: Deployment
metadata:
name: {{ include "netbird-operator.fullname" . }}
labels:
app.kubernetes.io/component: operator
{{- include "netbird-operator.labels" . | nindent 4 }}
spec:
replicas: {{ .Values.operator.replicaCount }}
selector:
matchLabels:
{{- include "netbird-operator.selectorLabels" . | nindent 6 }}
template:
metadata:
{{- with .Values.operator.podAnnotations }}
annotations:
{{- toYaml . | nindent 8 }}
{{- end }}
labels:
app.kubernetes.io/component: operator
{{- include "netbird-operator.labels" . | nindent 8 }}
{{- with .Values.operator.podLabels }}
{{- toYaml . | nindent 8 }}
{{- end }}
spec:
{{- with .Values.operator.imagePullSecrets }}
imagePullSecrets:
{{- toYaml . | nindent 8 }}
{{- end }}
serviceAccountName: {{ include "netbird-operator.serviceAccountName" . }}
securityContext:
{{- toYaml .Values.operator.podSecurityContext | nindent 8 }}
containers:
- name: {{ .Chart.Name }}
securityContext:
{{- toYaml .Values.operator.securityContext | nindent 12 }}
image: "{{ .Values.operator.image.registry }}/{{ .Values.operator.image.repository }}:{{ .Values.operator.image.tag | default .Chart.AppVersion }}"
imagePullPolicy: {{ .Values.operator.image.pullPolicy }}
command:
- /manager
args:
{{- if .Values.operator.metrics.enabled }}
- --metrics-bind-address=:{{ .Values.operator.metrics.port}}
{{- end }}
- --leader-elect
- --health-probe-bind-address=:{{ .Values.operator.livenessProbe.port }}
- --webhook-cert-path=/tmp/k8s-webhook-server/serving-certs
{{- if .Values.managementURL }}
- --netbird-management-url={{.Values.managementURL}}
{{- end }}
ports:
- name: webhook-server
containerPort: {{ .Values.webhook.service.port }}
protocol: TCP
livenessProbe:
failureThreshold: 3
httpGet:
path: /healthz
port: {{ .Values.operator.livenessProbe.port }}
scheme: HTTP
initialDelaySeconds: {{ .Values.operator.livenessProbe.initialDelaySeconds }}
periodSeconds: {{ .Values.operator.livenessProbe.periodSeconds }}
successThreshold: {{ .Values.operator.livenessProbe.successThreshold }}
timeoutSeconds: {{ .Values.operator.livenessProbe.timeoutSeconds }}
readinessProbe:
failureThreshold: 3
httpGet:
path: /readyz
port: {{ .Values.operator.readinessProbe.port }}
scheme: HTTP
initialDelaySeconds: {{ .Values.operator.readinessProbe.initialDelaySeconds }}
periodSeconds: {{ .Values.operator.readinessProbe.periodSeconds }}
successThreshold: {{ .Values.operator.readinessProbe.successThreshold }}
timeoutSeconds: {{ .Values.operator.readinessProbe.timeoutSeconds }}
resources:
{{- toYaml .Values.operator.resources | nindent 12 }}
volumeMounts:
- mountPath: /tmp/k8s-webhook-server/serving-certs
name: webhook-certs
readOnly: true
{{- with .Values.operator.volumeMounts }}
{{- toYaml . | nindent 12 }}
{{- end }}
volumes:
- name: webhook-certs
secret:
defaultMode: 420
secretName: {{ template "netbird-operator.webhookCertSecret" . }}
{{- with .Values.operator.volumes }}
{{- toYaml . | nindent 8 }}
{{- end }}
{{- with .Values.operator.nodeSelector }}
nodeSelector:
{{- toYaml . | nindent 8 }}
{{- end }}
{{- with .Values.operator.affinity }}
affinity:
{{- toYaml . | nindent 8 }}
{{- end }}
{{- with .Values.operator.tolerations }}
tolerations:
{{- toYaml . | nindent 8 }}
{{- end }}
+116
View File
@@ -0,0 +1,116 @@
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
name: {{ include "netbird-operator.fullname" . }}
labels:
{{- include "netbird-operator.labels" . | nindent 4 }}
rules:
- apiGroups:
- netbird.io
resources:
- nbsetupkeys
verbs:
- get
- list
- watch
- apiGroups:
- netbird.io
resources:
- nbsetupkeys/finalizers
verbs:
- update
- apiGroups:
- netbird.io
resources:
- nbsetupkeys/status
verbs:
- get
- patch
- update
- apiGroups:
- ""
resources:
- pods
verbs:
- get
- list
- watch
{{- if .Values.clusterSecretsPermissions.allowAllSecrets }}
- apiGroups:
- ""
resources:
- secrets
verbs:
- get
- list
- watch
{{- end }}
---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
name: {{ include "netbird-operator.fullname" . }}
labels:
{{- include "netbird-operator.labels" . | nindent 4 }}
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: {{ include "netbird-operator.fullname" . }}
subjects:
- kind: ServiceAccount
name: {{ include "netbird-operator.serviceAccountName" . }}
namespace: {{ .Release.Namespace }}
---
apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
name: {{ include "netbird-operator.fullname" . }}
labels:
{{- include "netbird-operator.labels" . | nindent 4 }}
rules:
- apiGroups:
- ""
resources:
- configmaps
verbs:
- get
- list
- watch
- create
- update
- patch
- delete
- apiGroups:
- coordination.k8s.io
resources:
- leases
verbs:
- get
- list
- watch
- create
- update
- patch
- delete
- apiGroups:
- ""
resources:
- events
verbs:
- create
- patch
---
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
name: {{ include "netbird-operator.fullname" . }}
labels:
{{- include "netbird-operator.labels" . | nindent 4 }}
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: Role
name: {{ include "netbird-operator.fullname" . }}
subjects:
- kind: ServiceAccount
name: {{ include "netbird-operator.serviceAccountName" . }}
namespace: {{ .Release.Namespace }}
@@ -0,0 +1,33 @@
{{- if .Values.operator.metrics.enabled }}
apiVersion: v1
kind: Service
metadata:
name: {{ include "netbird-operator.fullname" . }}-metrics
labels:
{{- include "netbird-operator.labels" . | nindent 4 }}
spec:
type: {{ .Values.operator.metrics.type }}
ports:
- name: http
port: {{ .Values.operator.metrics.port }}
protocol: TCP
targetPort: {{ .Values.operator.metrics.port }}
selector:
{{- include "netbird-operator.selectorLabels" . | nindent 4 }}
{{- end }}
---
apiVersion: v1
kind: Service
metadata:
name: {{ include "netbird-operator.webhookService" . }}
labels:
{{- include "netbird-operator.labels" . | nindent 4 }}
spec:
type: {{ .Values.webhook.service.type }}
ports:
- name: https
port: {{ .Values.webhook.service.port }}
protocol: TCP
targetPort: {{ .Values.webhook.service.targetPort }}
selector:
{{- include "netbird-operator.selectorLabels" . | nindent 4 }}
@@ -0,0 +1,13 @@
{{- if .Values.operator.serviceAccount.create -}}
apiVersion: v1
kind: ServiceAccount
metadata:
name: {{ include "netbird-operator.serviceAccountName" . }}
labels:
{{- include "netbird-operator.labels" . | nindent 4 }}
{{- with .Values.operator.serviceAccount.annotations }}
annotations:
{{- toYaml . | nindent 4 }}
{{- end }}
automountServiceAccountToken: {{ .Values.operator.serviceAccount.automount }}
{{- end }}
@@ -0,0 +1,134 @@
{{ $tls := fromYaml ( include "netbird-operator.webhookCerts" . ) }}
---
apiVersion: admissionregistration.k8s.io/v1
kind: MutatingWebhookConfiguration
metadata:
{{- if $.Values.webhook.enableCertManager }}
annotations:
cert-manager.io/inject-ca-from: {{ .Release.Namespace }}/{{ template "netbird-operator.fullname" . }}-serving-cert
{{- end }}
name: {{ include "netbird-operator.fullname" . }}-mpod-webhook
labels:
{{- include "netbird-operator.labels" . | nindent 4 }}
webhooks:
- clientConfig:
{{- if not $.Values.webhook.enableCertManager -}}
caBundle: {{ $tls.caCert }}
{{ end }}
service:
name: {{ template "netbird-operator.webhookService" . }}
namespace: {{ $.Release.Namespace }}
path: /mutate--v1-pod
failurePolicy: Fail
name: mpod-v1.netbird.io
admissionReviewVersions:
- v1
{{- if .Values.webhook.namespaceSelectors }}
namespaceSelector:
matchExpressions:
{{ toYaml .Values.webhook.namespaceSelectors | nindent 4 }}
{{ end }}
objectSelector:
matchExpressions:
- key: app.kubernetes.io/name
operator: NotIn
values:
- {{ include "netbird-operator.name" . }}
{{- if .Values.webhook.objectSelector.matchExpressions }}
{{- toYaml .Values.webhook.objectSelector.matchExpressions | nindent 4 }}
{{- end }}
{{- if .Values.webhook.objectSelector.matchLabels }}
matchLabels:
{{- toYaml .Values.webhook.objectSelector.matchLabels | nindent 6 }}
{{- end }}
rules:
- apiGroups:
- ""
apiVersions:
- v1
operations:
- CREATE
resources:
- pods
sideEffects: None
---
apiVersion: admissionregistration.k8s.io/v1
kind: ValidatingWebhookConfiguration
metadata:
{{- if $.Values.webhook.enableCertManager }}
annotations:
cert-manager.io/inject-ca-from: {{ .Release.Namespace }}/{{ template "netbird-operator.fullname" . }}-serving-cert
{{- end }}
name: {{ include "netbird-operator.fullname" . }}-vnbsetupkey-webhook
labels:
{{- include "netbird-operator.labels" . | nindent 4 }}
webhooks:
- clientConfig:
{{- if not $.Values.webhook.enableCertManager -}}
caBundle: {{ $tls.caCert }}
{{ end }}
service:
name: {{ template "netbird-operator.webhookService" . }}
namespace: {{ $.Release.Namespace }}
path: /validate-netbird-io-v1-nbsetupkey
failurePolicy: Fail
name: vnbsetupkey-v1.netbird.io
admissionReviewVersions:
- v1
{{- if .Values.webhook.namespaceSelectors }}
namespaceSelector:
matchExpressions:
{{ toYaml .Values.webhook.namespaceSelectors | nindent 4 }}
{{ end }}
rules:
- apiGroups:
- netbird.io
apiVersions:
- v1
operations:
- CREATE
- UPDATE
resources:
- "*/*"
sideEffects: None
---
{{- if not $.Values.webhook.enableCertManager }}
apiVersion: v1
kind: Secret
metadata:
name: {{ template "netbird-operator.webhookCertSecret" . }}
namespace: {{ .Release.Namespace }}
labels:
{{ include "netbird-operator.labels" . | indent 4 }}
type: kubernetes.io/tls
data:
ca.crt: {{ $tls.caCert }}
tls.crt: {{ $tls.clientCert }}
tls.key: {{ $tls.clientKey }}
{{- else }}
apiVersion: cert-manager.io/v1
kind: Certificate
metadata:
name: {{ template "netbird-operator.fullname" . }}-serving-cert
namespace: {{ .Release.Namespace }}
labels:
{{ include "netbird-operator.labels" . | indent 4 }}
spec:
dnsNames:
- {{ template "netbird-operator.webhookService" . }}.{{ .Release.Namespace }}.svc
- {{ template "netbird-operator.webhookService" . }}.{{ .Release.Namespace }}.svc.{{ .Values.webhook.cluster.dnsDomain }}
issuerRef:
kind: Issuer
name: {{ template "netbird-operator.fullname" . }}-selfsigned-issuer
secretName: {{ template "netbird-operator.webhookCertSecret" . }}
---
apiVersion: cert-manager.io/v1
kind: Issuer
metadata:
name: {{ template "netbird-operator.fullname" . }}-selfsigned-issuer
namespace: {{ .Release.Namespace }}
labels:
{{ include "netbird-operator.labels" . | indent 4 }}
spec:
selfSigned: {}
{{- end }}
+130
View File
@@ -0,0 +1,130 @@
clusterSecretsPermissions:
allowAllSecrets: true
webhook:
service:
type: ClusterIP
port: 443
targetPort: 9443
cluster:
# Cluster DNS domain (required for requesting TLS certificates)
dnsDomain: cluster.local
# TLS configuration for webhook
tls: {}
# Use cert-manager to provision webhook certificates
enableCertManager: true
namespaceSelectors: []
# - key: foo
# operator: In
# values:
# - bar
objectSelector:
matchExpressions: []
# - key: app.kubernetes.io/name
# operator: NotIn
# values:
# - foo
operator:
# This will set the replicaset count more information can be found here: https://kubernetes.io/docs/concepts/workloads/controllers/replicaset/
replicaCount: 1
# This sets the container image more information can be found here: https://kubernetes.io/docs/concepts/containers/images/
image:
# Set operator image registry
registry: docker.io
# Set operator image repository
repository: netbirdio/kubernetes-operator
# This sets the pull policy for images.
pullPolicy: IfNotPresent
# Overrides the image tag whose default is the chart appVersion.
tag: ""
metrics:
enabled: true
type: ClusterIP
port: 8080
# This is for the secretes for pulling an image from a private repository more information can be found here: https://kubernetes.io/docs/tasks/configure-pod-container/pull-image-private-registry/
imagePullSecrets: []
# This is to override the chart name.
nameOverride: ""
fullnameOverride: ""
#This section builds out the service account more information can be found here: https://kubernetes.io/docs/concepts/security/service-accounts/
serviceAccount:
# Specifies whether a service account should be created
create: true
# Automatically mount a ServiceAccount's API credentials?
automount: true
# Annotations to add to the service account
annotations: {}
# The name of the service account to use.
# If not set and create is true, a name is generated using the fullname template
name: ""
# This is for setting Kubernetes Annotations to a Pod.
# For more information checkout: https://kubernetes.io/docs/concepts/overview/working-with-objects/annotations/
podAnnotations: {}
# This is for setting Kubernetes Labels to a Pod.
# For more information checkout: https://kubernetes.io/docs/concepts/overview/working-with-objects/labels/
podLabels: {}
securityContext:
allowPrivilegeEscalation: false
capabilities:
drop:
- ALL
podSecurityContext:
runAsNonRoot: true
seccompProfile:
type: RuntimeDefault
# This is for setting up a service more information can be found here: https://kubernetes.io/docs/concepts/services-networking/service/
service:
# This sets the service type more information can be found here: https://kubernetes.io/docs/concepts/services-networking/service/#publishing-services-service-types
type: ClusterIP
# This sets the ports more information can be found here: https://kubernetes.io/docs/concepts/services-networking/service/#field-spec-ports
port: 9443
resources: {}
# limits:
# cpu: 100m
# memory: 128Mi
# requests:
# cpu: 100m
# memory: 128Mi
# This is to setup the liveness and readiness probes more information can be found here: https://kubernetes.io/docs/tasks/configure-pod-container/configure-liveness-readiness-startup-probes/
livenessProbe:
port: 8081
initialDelaySeconds: 15
periodSeconds: 20
successThreshold: 1
timeoutSeconds: 1
readinessProbe:
port: 8081
initialDelaySeconds: 5
periodSeconds: 10
successThreshold: 1
timeoutSeconds: 1
# Additional volumes on the output Deployment definition.
volumes: []
# Additional volumeMounts on the output Deployment definition.
volumeMounts: []
nodeSelector: {}
tolerations: []
affinity: {}