From b79285b4fbcf58f9324aa6fad325b1b846e3f79b Mon Sep 17 00:00:00 2001 From: Armin Kunaschik Date: Mon, 22 May 2023 01:11:41 +0200 Subject: [PATCH] Added Openshift example deployments --- openshift/README.md | 18 +++ .../deploy-with-oauth-proxy/deployment.yaml | 115 ++++++++++++++++++ .../kustomization.yaml | 10 ++ .../deploy-with-oauth-proxy/namespace.yaml | 7 ++ openshift/deploy-with-oauth-proxy/rbac.yaml | 36 ++++++ .../redis-deployment.yaml | 47 +++++++ .../redis-service.yaml | 16 +++ openshift/deploy-with-oauth-proxy/route.yaml | 14 +++ .../deploy-with-oauth-proxy/service.yaml | 18 +++ openshift/deploy/deployment.yaml | 58 +++++++++ openshift/deploy/kustomization.yaml | 10 ++ openshift/deploy/namespace.yaml | 7 ++ openshift/deploy/rbac.yaml | 36 ++++++ openshift/deploy/redis-deployment.yaml | 48 ++++++++ openshift/deploy/redis-service.yaml | 16 +++ openshift/deploy/route.yaml | 14 +++ openshift/deploy/service.yaml | 16 +++ 17 files changed, 486 insertions(+) create mode 100644 openshift/README.md create mode 100644 openshift/deploy-with-oauth-proxy/deployment.yaml create mode 100644 openshift/deploy-with-oauth-proxy/kustomization.yaml create mode 100644 openshift/deploy-with-oauth-proxy/namespace.yaml create mode 100644 openshift/deploy-with-oauth-proxy/rbac.yaml create mode 100644 openshift/deploy-with-oauth-proxy/redis-deployment.yaml create mode 100644 openshift/deploy-with-oauth-proxy/redis-service.yaml create mode 100644 openshift/deploy-with-oauth-proxy/route.yaml create mode 100644 openshift/deploy-with-oauth-proxy/service.yaml create mode 100644 openshift/deploy/deployment.yaml create mode 100644 openshift/deploy/kustomization.yaml create mode 100644 openshift/deploy/namespace.yaml create mode 100644 openshift/deploy/rbac.yaml create mode 100644 openshift/deploy/redis-deployment.yaml create mode 100644 openshift/deploy/redis-service.yaml create mode 100644 openshift/deploy/route.yaml create mode 100644 openshift/deploy/service.yaml diff --git a/openshift/README.md b/openshift/README.md new file mode 100644 index 0000000..a3f925b --- /dev/null +++ b/openshift/README.md @@ -0,0 +1,18 @@ +### Directory [deploy](deploy) contains a standard deployment for Openshift 4.x (3.x is also working) + +- Changes from the original + - standard namespace is ocp-ops-view instead of default + - create the namespace with an infra node selector, this is technically not necessary but nice to have + - RunAsUser and RunAsNonRoot removed from kube-ops-view and redis deployment, Openshift deployments run with a random uid, choosing a specific one is unnecessary + - added an emptydir to redis to create a directory which is writeable for the random user + - added an edge encrypt route to expose the service via TLS only + redirect from port 80 + - set requests and limits a bit higher, your mileage may vary + +### Directory [deploy-with-oauth-proxy](deploy-with-oauth-oauth-proxy) contains an additional oauth proxy to protect the application from unauthorized access + +- Change from Openshift deploy + - switched to reencrypt route to be able to use the service CA + - added Openshift oauth proxy as a sidecar + - added necessary service annotation for the Openshift oauth proxy + - added service CA certificate to the proxy service to encrypt traffic between router and proxy + - all users with permission to read the namespace are allowed to use the service by the oauth proxy diff --git a/openshift/deploy-with-oauth-proxy/deployment.yaml b/openshift/deploy-with-oauth-proxy/deployment.yaml new file mode 100644 index 0000000..7e60bae --- /dev/null +++ b/openshift/deploy-with-oauth-proxy/deployment.yaml @@ -0,0 +1,115 @@ +apiVersion: apps/v1 +kind: Deployment +metadata: + labels: + application: kube-ops-view + component: frontend + name: kube-ops-view +spec: + replicas: 1 + selector: + matchLabels: + application: kube-ops-view + component: frontend + template: + metadata: + labels: + application: kube-ops-view + component: frontend + spec: + serviceAccountName: kube-ops-view + containers: + - name: service + # see https://github.com/hjacobs/kube-ops-view/releases + image: hjacobs/kube-ops-view:23.5.0 + args: + # remove this option to use built-in memory store + - --redis-url=redis://kube-ops-view-redis:6379 + # example to add external links for nodes and pods + # - --node-link-url-template=https://kube-web-view.example.org/clusters/{cluster}/nodes/{name} + # - --pod-link-url-template=https://kube-web-view.example.org/clusters/{cluster}/namespaces/{namespace}/pods/{name} + ports: + - containerPort: 8080 + protocol: TCP + readinessProbe: + httpGet: + path: /health + port: 8080 + initialDelaySeconds: 5 + timeoutSeconds: 5 + livenessProbe: + httpGet: + path: /health + port: 8080 + initialDelaySeconds: 30 + periodSeconds: 30 + timeoutSeconds: 10 + failureThreshold: 5 + resources: + limits: + cpu: 750m + memory: 512Mi + requests: + cpu: 500m + memory: 512Mi + securityContext: + readOnlyRootFilesystem: true +# runAsNonRoot: true +# runAsUser: 1000 + - name: oauth-proxy + env: + - name: MY_POD_NAMESPACE + valueFrom: + fieldRef: + apiVersion: v1 + fieldPath: metadata.namespace + image: registry.redhat.io/openshift4/ose-oauth-proxy:latest + imagePullPolicy: IfNotPresent + ports: + - containerPort: 8443 + name: public + args: + - --https-address=:8443 + - --provider=openshift + - --openshift-service-account=kube-ops-view + - '-openshift-sar={"namespace":"$(MY_POD_NAMESPACE)","resource": "namespaces", "verb": "get"}' + - --upstream=http://localhost:8080 + - --tls-cert=/etc/tls/private/tls.crt + - --tls-key=/etc/tls/private/tls.key + - --client-secret-file=/var/run/secrets/kubernetes.io/serviceaccount/token + - --openshift-ca=/var/run/secrets/kubernetes.io/serviceaccount/ca.crt + - --openshift-ca=/etc/pki/tls/cert.pem + - --cookie-secret=dGVzdGNvb2tpZQo= + - -skip-provider-button + resources: + limits: + cpu: 200m + memory: 256Mi + requests: + cpu: 100m + memory: 256Mi + livenessProbe: + httpGet: + path: /oauth/healthz + port: 8443 + scheme: HTTPS + initialDelaySeconds: 60 + failureThreshold: 60 + periodSeconds: 10 + timeoutSeconds: 10 + readinessProbe: + httpGet: + path: /oauth/healthz + port: 8443 + scheme: HTTPS + initialDelaySeconds: 5 + failureThreshold: 20 + periodSeconds: 10 + timeoutSeconds: 5 + volumeMounts: + - mountPath: /etc/tls/private + name: proxy-tls + volumes: + - name: proxy-tls + secret: + secretName: proxy-tls diff --git a/openshift/deploy-with-oauth-proxy/kustomization.yaml b/openshift/deploy-with-oauth-proxy/kustomization.yaml new file mode 100644 index 0000000..19d1e3d --- /dev/null +++ b/openshift/deploy-with-oauth-proxy/kustomization.yaml @@ -0,0 +1,10 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - namespace.yaml + - deployment.yaml + - rbac.yaml + - service.yaml + - redis-deployment.yaml + - redis-service.yaml + - route.yaml diff --git a/openshift/deploy-with-oauth-proxy/namespace.yaml b/openshift/deploy-with-oauth-proxy/namespace.yaml new file mode 100644 index 0000000..aa20da3 --- /dev/null +++ b/openshift/deploy-with-oauth-proxy/namespace.yaml @@ -0,0 +1,7 @@ +apiVersion: v1 +kind: Namespace +metadata: + annotations: + openshift.io/node-selector: "node-role.kubernetes.io/infra=true" + name: ocp-ops-view + diff --git a/openshift/deploy-with-oauth-proxy/rbac.yaml b/openshift/deploy-with-oauth-proxy/rbac.yaml new file mode 100644 index 0000000..7de73d0 --- /dev/null +++ b/openshift/deploy-with-oauth-proxy/rbac.yaml @@ -0,0 +1,36 @@ +apiVersion: v1 +kind: ServiceAccount +metadata: + annotations: + serviceaccounts.openshift.io/oauth-redirectreference.primary: '{"kind":"OAuthRedirectReference","apiVersion":"v1","reference":{"kind":"Route","name":"proxy"}}' + name: kube-ops-view + namespace: ocp-ops-view +--- +kind: ClusterRole +apiVersion: rbac.authorization.k8s.io/v1 +metadata: + name: kube-ops-view +rules: +- apiGroups: [""] + resources: ["nodes", "pods"] + verbs: + - list +- apiGroups: ["metrics.k8s.io"] + resources: ["nodes", "pods"] + verbs: + - get + - list +--- +kind: ClusterRoleBinding +apiVersion: rbac.authorization.k8s.io/v1 +metadata: + name: kube-ops-view +roleRef: + apiGroup: rbac.authorization.k8s.io + kind: ClusterRole + name: kube-ops-view +subjects: +- kind: ServiceAccount + name: kube-ops-view + namespace: ocp-ops-view + diff --git a/openshift/deploy-with-oauth-proxy/redis-deployment.yaml b/openshift/deploy-with-oauth-proxy/redis-deployment.yaml new file mode 100644 index 0000000..ba17727 --- /dev/null +++ b/openshift/deploy-with-oauth-proxy/redis-deployment.yaml @@ -0,0 +1,47 @@ +apiVersion: apps/v1 +kind: Deployment +metadata: + labels: + application: kube-ops-view + component: redis + name: kube-ops-view-redis +spec: + replicas: 1 + selector: + matchLabels: + application: kube-ops-view + template: + metadata: + labels: + application: kube-ops-view + component: redis + spec: + containers: + - name: redis + image: redis:7-alpine + ports: + - containerPort: 6379 + protocol: TCP + readinessProbe: + tcpSocket: + port: 6379 + resources: + limits: + cpu: 200m + memory: 300Mi + requests: + cpu: 100m + memory: 300Mi + securityContext: + readOnlyRootFilesystem: true +# runAsNonRoot: true + # we need to use the "redis" uid +# runAsUser: 999 + volumeMounts: + - name: redis-data + mountPath: /data + volumes: + - name: redis-data + emptyDir: {} +# defaultMode: 0775 + diff --git a/openshift/deploy-with-oauth-proxy/redis-service.yaml b/openshift/deploy-with-oauth-proxy/redis-service.yaml new file mode 100644 index 0000000..f74d9ee --- /dev/null +++ b/openshift/deploy-with-oauth-proxy/redis-service.yaml @@ -0,0 +1,16 @@ +apiVersion: v1 +kind: Service +metadata: + labels: + application: kube-ops-view + component: redis + name: kube-ops-view-redis +spec: + selector: + application: kube-ops-view + component: redis + type: ClusterIP + ports: + - port: 6379 + protocol: TCP + targetPort: 6379 diff --git a/openshift/deploy-with-oauth-proxy/route.yaml b/openshift/deploy-with-oauth-proxy/route.yaml new file mode 100644 index 0000000..3eca54a --- /dev/null +++ b/openshift/deploy-with-oauth-proxy/route.yaml @@ -0,0 +1,14 @@ +apiVersion: route.openshift.io/v1 +kind: Route +metadata: + name: proxy +spec: + host: ocp-ops-view.apps. + port: + targetPort: proxy + to: + kind: Service + name: proxy + tls: + insecureEdgeTerminationPolicy: Redirect + termination: reencrypt diff --git a/openshift/deploy-with-oauth-proxy/service.yaml b/openshift/deploy-with-oauth-proxy/service.yaml new file mode 100644 index 0000000..7e8c5d4 --- /dev/null +++ b/openshift/deploy-with-oauth-proxy/service.yaml @@ -0,0 +1,18 @@ +apiVersion: v1 +kind: Service +metadata: + annotations: + service.alpha.openshift.io/serving-cert-secret-name: proxy-tls + labels: + application: kube-ops-view + component: frontend + name: proxy +spec: + selector: + application: kube-ops-view + component: frontend + type: ClusterIP + ports: + - name: proxy + port: 8443 + targetPort: 8443 diff --git a/openshift/deploy/deployment.yaml b/openshift/deploy/deployment.yaml new file mode 100644 index 0000000..bdc85d3 --- /dev/null +++ b/openshift/deploy/deployment.yaml @@ -0,0 +1,58 @@ +apiVersion: apps/v1 +kind: Deployment +metadata: + labels: + application: kube-ops-view + component: frontend + name: kube-ops-view +spec: + replicas: 1 + selector: + matchLabels: + application: kube-ops-view + component: frontend + template: + metadata: + labels: + application: kube-ops-view + component: frontend + spec: + serviceAccountName: kube-ops-view + containers: + - name: service + # see https://github.com/hjacobs/kube-ops-view/releases + image: hjacobs/kube-ops-view:23.5.0 + args: + # remove this option to use built-in memory store + - --redis-url=redis://kube-ops-view-redis:6379 + # example to add external links for nodes and pods + # - --node-link-url-template=https://kube-web-view.example.org/clusters/{cluster}/nodes/{name} + # - --pod-link-url-template=https://kube-web-view.example.org/clusters/{cluster}/namespaces/{namespace}/pods/{name} + ports: + - containerPort: 8080 + protocol: TCP + readinessProbe: + httpGet: + path: /health + port: 8080 + initialDelaySeconds: 5 + timeoutSeconds: 5 + livenessProbe: + httpGet: + path: /health + port: 8080 + initialDelaySeconds: 30 + periodSeconds: 30 + timeoutSeconds: 10 + failureThreshold: 5 + resources: + limits: + cpu: 750m + memory: 512Mi + requests: + cpu: 500m + memory: 512Mi + securityContext: + readOnlyRootFilesystem: true +# runAsNonRoot: true +# runAsUser: 1000 diff --git a/openshift/deploy/kustomization.yaml b/openshift/deploy/kustomization.yaml new file mode 100644 index 0000000..19d1e3d --- /dev/null +++ b/openshift/deploy/kustomization.yaml @@ -0,0 +1,10 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - namespace.yaml + - deployment.yaml + - rbac.yaml + - service.yaml + - redis-deployment.yaml + - redis-service.yaml + - route.yaml diff --git a/openshift/deploy/namespace.yaml b/openshift/deploy/namespace.yaml new file mode 100644 index 0000000..aa20da3 --- /dev/null +++ b/openshift/deploy/namespace.yaml @@ -0,0 +1,7 @@ +apiVersion: v1 +kind: Namespace +metadata: + annotations: + openshift.io/node-selector: "node-role.kubernetes.io/infra=true" + name: ocp-ops-view + diff --git a/openshift/deploy/rbac.yaml b/openshift/deploy/rbac.yaml new file mode 100644 index 0000000..7de73d0 --- /dev/null +++ b/openshift/deploy/rbac.yaml @@ -0,0 +1,36 @@ +apiVersion: v1 +kind: ServiceAccount +metadata: + annotations: + serviceaccounts.openshift.io/oauth-redirectreference.primary: '{"kind":"OAuthRedirectReference","apiVersion":"v1","reference":{"kind":"Route","name":"proxy"}}' + name: kube-ops-view + namespace: ocp-ops-view +--- +kind: ClusterRole +apiVersion: rbac.authorization.k8s.io/v1 +metadata: + name: kube-ops-view +rules: +- apiGroups: [""] + resources: ["nodes", "pods"] + verbs: + - list +- apiGroups: ["metrics.k8s.io"] + resources: ["nodes", "pods"] + verbs: + - get + - list +--- +kind: ClusterRoleBinding +apiVersion: rbac.authorization.k8s.io/v1 +metadata: + name: kube-ops-view +roleRef: + apiGroup: rbac.authorization.k8s.io + kind: ClusterRole + name: kube-ops-view +subjects: +- kind: ServiceAccount + name: kube-ops-view + namespace: ocp-ops-view + diff --git a/openshift/deploy/redis-deployment.yaml b/openshift/deploy/redis-deployment.yaml new file mode 100644 index 0000000..c77f6aa --- /dev/null +++ b/openshift/deploy/redis-deployment.yaml @@ -0,0 +1,48 @@ +apiVersion: apps/v1 +kind: Deployment +metadata: + labels: + application: kube-ops-view + component: redis + name: kube-ops-view-redis +spec: + replicas: 1 + selector: + matchLabels: + application: kube-ops-view + component: redis + template: + metadata: + labels: + application: kube-ops-view + component: redis + spec: + containers: + - name: redis + image: redis:7-alpine + ports: + - containerPort: 6379 + protocol: TCP + readinessProbe: + tcpSocket: + port: 6379 + resources: + limits: + cpu: 200m + memory: 300Mi + requests: + cpu: 100m + memory: 300Mi + securityContext: + readOnlyRootFilesystem: true +# runAsNonRoot: true + # we need to use the "redis" uid +# runAsUser: 999 + volumeMounts: + - name: redis-data + mountPath: /data + volumes: + - name: redis-data + emptyDir: {} +# defaultMode: 0775 + diff --git a/openshift/deploy/redis-service.yaml b/openshift/deploy/redis-service.yaml new file mode 100644 index 0000000..f74d9ee --- /dev/null +++ b/openshift/deploy/redis-service.yaml @@ -0,0 +1,16 @@ +apiVersion: v1 +kind: Service +metadata: + labels: + application: kube-ops-view + component: redis + name: kube-ops-view-redis +spec: + selector: + application: kube-ops-view + component: redis + type: ClusterIP + ports: + - port: 6379 + protocol: TCP + targetPort: 6379 diff --git a/openshift/deploy/route.yaml b/openshift/deploy/route.yaml new file mode 100644 index 0000000..1858199 --- /dev/null +++ b/openshift/deploy/route.yaml @@ -0,0 +1,14 @@ +apiVersion: route.openshift.io/v1 +kind: Route +metadata: + name: proxy +spec: + host: ocp-ops-view.apps. + port: + targetPort: 8080 + to: + kind: Service + name: kube-ops-view + tls: + insecureEdgeTerminationPolicy: Redirect + termination: edge diff --git a/openshift/deploy/service.yaml b/openshift/deploy/service.yaml new file mode 100644 index 0000000..5f661cc --- /dev/null +++ b/openshift/deploy/service.yaml @@ -0,0 +1,16 @@ +apiVersion: v1 +kind: Service +metadata: + labels: + application: kube-ops-view + component: frontend + name: kube-ops-view +spec: + selector: + application: kube-ops-view + component: frontend + type: ClusterIP + ports: + - port: 8080 + protocol: TCP + targetPort: 8080