progress
ci / build (push) Failing after 1s Details

This commit is contained in:
CJ_Clippy 2024-08-13 13:18:01 -08:00
parent 331e27138f
commit 7793e38878
184 changed files with 38429 additions and 244 deletions

View File

@ -21,3 +21,5 @@ S3 for media storage
Domain Driven Development
Test Driven Development
12 Factor App

46
MANTRAS.md Normal file
View File

@ -0,0 +1,46 @@
# Development Mantras
### Move fast and break things
Get through the [OODA loop](https://en.wikipedia.org/wiki/OODA_loop) as many times as possible.
### Alligator energy (move slow and preserve things)
### Make it work, make it right, make it fast (in that order)
### Done is better than perfect
### If it looks like a duck and quacks like a duck, it is a duck.
> "It's ugly, but it works!"
> -- R. Fisher
### If the way is long, the way is wrong
### [Project Management Triangle](https://en.wikipedia.org/wiki/Project_management_triangle)
> Good, Fast, Cheap. Pick two but not all three.
### Organizations are fractals
### Focus on what moves the needle
### Code is run more than it is read
### [ONE SHOT. ONE LIFE](https://www.youtube.com/watch?v=Rh-ohspuCmE)
### The computer doesn't care
> "There are 2 hard problems in computer science: cache invalidation, naming things, and off-by-1 errors."
> Leon Bambrick
In other words, pick something for a name and roll with the punches.
### Elon's 5 Step Design Process
1. Make the requirements less dumb
2. Try and delete part of the process
3. Simplify or optimize
4. Accelerate Cycle Time
5. Automate

View File

@ -13,10 +13,13 @@ secrets:
flux:
./scripts/flux-bootstrap.sh
cluster: echoenv kind namespaces secrets velero flux metrics
chisel:
./scripts/k8s-chisel.sh
cluster: echoenv kind namespaces secrets velero flux metrics chisel
metrics:
kubectl apply -f https://github.com/kubernetes-sigs/metrics-server/releases/latest/download/components.yaml
./scripts/k8s-metrics.sh
echoenv:
echo "[echoenv] Using ${ENV} environment. If this is not what you want, export ENV=development|staging|production"

View File

@ -37,28 +37,3 @@ Keeping track of metrics we want to scrape using Prometheus
https://uppy.fp.sbtp.xyz/metrics
## Development Mantras
### Move fast and break things
### Make it work, make it right, make it fast (in that order)
### Done is better than perfect
### If it looks like a duck and quacks like a duck, it is a duck.
### If the way is long, the way is wrong
### Good, Fast, Cheap. Pick two but not all three.
### Organizations are fractals
### Focus on what moves the needle
### Alligator energy (move slow and preserve things)
### Code is run more than it is read
### The computer doesn't care
### [ONE SHOT. ONE LIFE](https://www.youtube.com/watch?v=Rh-ohspuCmE)

View File

@ -108,12 +108,50 @@ k8s_yaml(helm(
]
))
k8s_yaml(helm(
'./charts/traefik/traefik',
namespace='futureporn',
values=[
'./charts/traefik/values-overrides.yaml'
]
))
## redis is for uppy
## before you think of switching to valkey, dragonfly, or one of the other redis alternatives, STOP. Uppy is picky.
## I tested dragonfly, valkey, and KeyDB. Uppy's ioredis client was unable to connect. "ECONNREFUSED" ...
## Uppy was only happy connecting to official redis.
k8s_yaml(helm(
'./charts/redis/redis',
namespace='futureporn',
values=[
'./charts/redis/values-overrides.yaml'
]
))
k8s_yaml(helm(
'./charts/cert-manager/cert-manager',
namespace='cert-manager',
values=['./charts/cert-manager/values-overrides.yaml']
))
## chisel-operator helm chart is not ready for general use. It has an invalid DNS name, "v1.1" that prevents successful deployment
## instead, we use kustomize to deploy
## @see ./Makefile
# k8s_yaml(helm(
# './charts/chisel-operator/chisel-operator',
# namespace='futureporn',
# values=['./charts/chisel-operator/values-overrides.yaml']
# ))
## ngrok
# k8s_yaml(helm(
# './charts/kubernetes-ingress-controller/kubernetes-ingress-controller',
# namespace='futureporn',
# values=['./charts/kubernetes-ingress-controller/values-overrides.yaml']
# ))
# docker_build('fp/link2cid', './packages/link2cid')
docker_build(
@ -130,8 +168,7 @@ docker_build(
'./packages/types',
],
live_update=[
sync('./services/strapi', '/app'),
run('cd /app && pnpm i', trigger=['./services/strapi/package.json', './services/strapi/pnpm-lock.yaml'])
sync('./services/strapi', '/usr/src/app')
],
pull=False,
)
@ -213,12 +250,12 @@ docker_build(
'fp/next',
'.',
dockerfile='dockerfiles/next.dockerfile',
target='next',
target='dev',
build_args={
'NEXT_PUBLIC_STRAPI_URL': 'https://strapi.fp.sbtp.xyz'
'NEXT_PUBLIC_STRAPI_URL': 'https://strapi.fp.sbtp.xyz',
},
live_update=[
sync('./services/next', '/app')
sync('./services/next', '/app/services/next')
],
pull=False,
)
@ -343,14 +380,14 @@ docker_build(
# )
# k8s_resource(
# workload='uppy',
# links=[
# link('https://uppy.fp.sbtp.xyz'),
# ],
# resource_deps=['redis-master'],
# labels=['backend'],
# )
k8s_resource(
workload='uppy',
links=[
link('https://uppy.fp.sbtp.xyz'),
],
resource_deps=['redis-master'],
labels=['backend'],
)
k8s_resource(
workload='next',
port_forwards=['3000'],
@ -371,6 +408,14 @@ k8s_resource(
labels=['backend'],
)
k8s_resource(
workload='game-2048',
port_forwards=['8088:80'],
labels=['frontend'],
links=[
link('https://game-2048.fp.sbtp.xyz/')
]
)
k8s_resource(
workload='postgresql-primary',
port_forwards=['5432'],
@ -418,21 +463,6 @@ k8s_resource(
# )
## redis is only here for uppy's usage.
## If we can engineer a way to delete redis, let's do it
# helm_remote(
# 'redis',
# repo_name='redis',
# repo_url='https://charts.bitnami.com/bitnami',
# namespace='futureporn',
# version='19.6.1',
# set=[
# 'auth.existingSecret=redis',
# 'auth.existingSecretPasswordKey=password',
# 'replica.persistence.enabled=false',
# 'architecture=standalone'
# ]
# )
k8s_resource(
workload='external-dns',
@ -444,12 +474,16 @@ k8s_resource(
labels=['networking'],
)
# k8s_resource(
# workload='redis-master',
# labels=['backend']
# workload='ngrok-manager',
# labels=['networking'],
# )
k8s_resource(
workload='redis-master',
labels=['cache']
)
k8s_resource(
workload='bot',

View File

@ -21,4 +21,28 @@ We override default values in the parent folder.
### cert-manager
helm repo add jetstack https://charts.jetstack.io --force-update
helm pull jetstack/cert-manager --untar --destination ./charts/cert-manager
helm pull jetstack/cert-manager --untar --destination ./charts/cert-manager
### valkey
helm repo add bitnami https://charts.bitnami.com/bitnami
helm pull bitnami/valkey --untar --destination ./charts/valkey
### redis
helm repo add bitnami https://charts.bitnami.com/bitnami
helm pull bitnami/redis --version 20.0.1 --untar --destination ./charts/redis
### chisel-operator
pnpx tiged 'https://github.com/FyraLabs/chisel-operator/charts/chisel-operator#v0.3.4' ./charts/chisel-operator/chisel-operator
### ngrok
helm repo add ngrok https://ngrok.github.io/kubernetes-ingress-controller
helm pull ngrok/kubernetes-ingress-controller --version 0.14.0 --untar --destination ./charts/kubernetes-ingress-controller
### traefik
helm repo add traefik https://traefik.github.io/charts
helm pull traefik/traefik --version 30.0.2 --untar --destination ./charts/traefik

View File

@ -1,2 +1,3 @@
fullnameOverride: cert-manager
installCRDs: true
crds:
enabled: true

View File

@ -0,0 +1 @@
fullnameOverride: "chisel-operator"

View File

@ -1,20 +1,3 @@
---
apiVersion: v1
kind: Service
metadata:
name: redis
namespace: futureporn
spec:
type: ClusterIP
selector:
app: redis
ports:
- name: web
port: {{ .Values.redis.port }}
targetPort: http
protocol: TCP
---
apiVersion: apps/v1
kind: Deployment
@ -22,6 +5,7 @@ metadata:
name: redis
namespace: futureporn
labels:
app.kubernetes.io/name: redis
app: redis
spec:
replicas: {{ .Values.redis.replicas }}
@ -37,13 +21,28 @@ spec:
- name: redis
image: "{{ .Values.redis.image }}"
ports:
- name: http
containerPort: {{ .Values.redis.port }}
env:
- name: PGRST_DB_ANON_ROLE
value: anonymous
- name: PGRST_JWT_SECRET
valueFrom:
secretKeyRef:
name: redis
key: jwtSecret
- name: web
containerPort: 6379
resources:
limits:
cpu: 150m
memory: 128Mi
restartPolicy: Always
---
apiVersion: v1
kind: Service
metadata:
name: redis
namespace: futureporn
spec:
type: ClusterIP
selector:
app.kubernetes.io/name: redis
ports:
- name: web
port: 6379
targetPort: web
protocol: TCP

View File

@ -1,3 +1,7 @@
---
apiVersion: v1
kind: Service
@ -113,4 +117,4 @@ spec:
limits:
cpu: 100m
memory: 256Mi
restartPolicy: Always
restartPolicy: Always

View File

@ -0,0 +1,23 @@
{{ if ne .Values.environment "production" }}
## chisel-operator acts on all Services of type LoadBalancer, randomly assigning them to an available ExitNode.
## Thus, we need to create lots of ExitNodes to ensure that
## each services gets an ExitNode
{{- $exitNodeCount := 9 }} # Define the number of ExitNodes you need
{{- range $i := until $exitNodeCount }}
---
apiVersion: chisel-operator.io/v1
kind: ExitNode
metadata:
name: exit-node-{{ $i }}
namespace: futureporn
spec:
host: "155.138.254.201"
port: 9090
auth: chisel
{{- end }}
{{ end }}

View File

@ -0,0 +1,102 @@
# ---
# apiVersion: networking.k8s.io/v1
# kind: Ingress
# metadata:
# name: game-2048
# namespace: futureporn
# spec:
# ingressClassName: ngrok
# rules:
# - host: "{{ .Values.ngrok.hostname }}"
# http:
# paths:
# - path: /
# pathType: Prefix
# backend:
# service:
# name: game-2048
# port:
# number: 80
---
apiVersion: traefik.io/v1alpha1
kind: IngressRoute
metadata:
name: game-2048-http
namespace: futureporn
spec:
entryPoints:
- web
routes:
- match: Host(`game-2048.fp.sbtp.xyz`)
kind: Rule
middlewares:
- name: redirect
namespace: futureporn
services:
- name: game-2048
port: 80
---
apiVersion: traefik.io/v1alpha1
kind: IngressRoute
metadata:
name: game-2048-https
namespace: futureporn
annotations:
cert-manager.io/cluster-issuer: "{{ .Values.certManager.issuer }}"
spec:
entryPoints:
- websecure
routes:
- match: Host(`game-2048.fp.sbtp.xyz`)
kind: Rule
services:
- name: game-2048
namespace: futureporn
port: 80
tls:
secretName: game-2048-tls
---
apiVersion: v1
kind: Service
metadata:
name: game-2048
namespace: futureporn
annotations:
external-dns.alpha.kubernetes.io/hostname: "{{ .Values.game2048.hostname }}"
spec:
type: LoadBalancer
selector:
app: game-2048
ports:
- name: http
port: 80
targetPort: 80
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: game-2048
namespace: futureporn
spec:
replicas: 1
selector:
matchLabels:
app: game-2048
template:
metadata:
labels:
app: game-2048
spec:
containers:
- name: game-2048
image: alexwhen/docker-2048
ports:
- name: http
containerPort: 80

View File

@ -1,3 +1,45 @@
---
apiVersion: traefik.io/v1alpha1
kind: IngressRoute
metadata:
name: next-http
namespace: futureporn
spec:
entryPoints:
- web
routes:
- match: Host(`next.fp.sbtp.xyz`)
kind: Rule
middlewares:
- name: redirect
namespace: futureporn
services:
- name: next
port: web
---
apiVersion: traefik.io/v1alpha1
kind: IngressRoute
metadata:
name: next-https
namespace: futureporn
annotations:
cert-manager.io/cluster-issuer: "{{ .Values.certManager.issuer }}"
spec:
entryPoints:
- websecure
routes:
- match: Host(`next.fp.sbtp.xyz`)
kind: Rule
services:
- name: next
namespace: futureporn
port: web
tls:
secretName: next-tls
---
apiVersion: v1
kind: Pod
@ -15,8 +57,6 @@ spec:
value: 0.0.0.0
- name: NEXT_PUBLIC_UPPY_COMPANION_URL
value: "{{ .Values.uppy.url }}"
- name: NODE_EXTRA_CA_CERTS
value: "{{ .Values.next.nodeExtraCaCerts }}"
ports:
- name: web
containerPort: 3000
@ -43,65 +83,6 @@ spec:
protocol: TCP
# {{ if eq .Values.environment "production" }}
# ---
# apiVersion: networking.k8s.io/v1
# kind: Ingress
# metadata:
# name: next
# namespace: futureporn
# annotations:
# cert-manager.io/cluster-issuer: "{{ .Values.certManager.issuer }}"
# kubernetes.io/ingress.class: nginx
# external-dns.alpha.kubernetes.io/hostname: "{{ .Values.next.hostname }}"
# spec:
# ingressClassName: nginx
# backend:
# serviceName: next
# servicePort: 3000
# tls:
# - secretName: next-tls
# hosts:
# - "{{ .Values.next.hostname }}"
# rules:
# - host: "{{ .Values.next.hostname }}"
# http:
# paths:
# - path: /
# pathType: Prefix
# backend:
# service:
# name: next
# port:
# number: 3000
# {{ end }}
# ---
# apiVersion: networking.k8s.io/v1
# kind: Ingress
# metadata:
# name: next
# namespace: futureporn
# annotations:
# spec:
# rules:
# - host: next.fp.sbtp.xyz
# http:
# paths:
# - path: /
# pathType: Prefix
# backend:
# service:
# name: next
# port:
# number: 3000
# tls:
# - hosts:
# - "{{ .Values.next.hostname }}"
# secretName: next-cert
---
apiVersion: cert-manager.io/v1
kind: Certificate

View File

@ -1,3 +1,44 @@
---
apiVersion: traefik.io/v1alpha1
kind: IngressRoute
metadata:
name: strapi-http
namespace: futureporn
spec:
entryPoints:
- web
routes:
- match: Host(`strapi.fp.sbtp.xyz`)
kind: Rule
middlewares:
- name: redirect
namespace: futureporn
services:
- name: strapi
port: http
---
apiVersion: traefik.io/v1alpha1
kind: IngressRoute
metadata:
name: strapi-https
namespace: futureporn
annotations:
cert-manager.io/cluster-issuer: "{{ .Values.certManager.issuer }}"
spec:
entryPoints:
- websecure
routes:
- match: Host(`strapi.fp.sbtp.xyz`)
kind: Rule
services:
- name: strapi
namespace: futureporn
port: http
tls:
secretName: strapi-tls
---
apiVersion: v1
kind: Service
@ -9,12 +50,11 @@ metadata:
spec:
type: LoadBalancer
selector:
app.kubernetes.io/name: strapi
app: strapi
ports:
- name: http
port: 1339
targetPort: http
protocol: TCP
---
apiVersion: apps/v1
@ -36,11 +76,19 @@ spec:
spec:
containers:
- name: strapi
readinessProbe:
httpGet:
path: /
port: http
initialDelaySeconds: 5
periodSeconds: 5
image: "{{ .Values.strapi.imageName }}"
ports:
- name: http
containerPort: 1339
env:
- name: NODE_EXTRA_CA_CERTS
value: "{{ .Values.strapi.nodeExtraCaCerts }}"
- name: ADMIN_JWT_SECRET
valueFrom:
secretKeyRef:

View File

@ -0,0 +1,11 @@
---
apiVersion: traefik.io/v1alpha1
kind: Middleware
metadata:
name: redirect
namespace: futureporn
spec:
redirectScheme:
scheme: https
permanent: true

View File

@ -4,7 +4,7 @@ metadata:
name: uppy
namespace: futureporn
spec:
replicas: 2
replicas: {{ .Values.uppy.replicas }}
minReadySeconds: 5
strategy:
type: RollingUpdate
@ -40,10 +40,7 @@ spec:
- name: COMPANION_PROTOCOL
value: https
- name: COMPANION_REDIS_URL
valueFrom:
secretKeyRef:
name: uppy
key: redisUrl
value: "{{ .Values.uppy.redisUrl }}"
- name: COMPANION_SECRET
valueFrom:
secretKeyRef:

View File

@ -0,0 +1,86 @@
# an http service for testing purposes
{{ if ne .Values.environment "production" }}
---
apiVersion: traefik.io/v1alpha1
kind: IngressRoute
metadata:
name: whoami-http
namespace: futureporn
spec:
entryPoints:
- web
routes:
- match: Host(`whoami.fp.sbtp.xyz`)
kind: Rule
middlewares:
- name: redirect
namespace: futureporn
services:
- name: whoami
port: 80
---
apiVersion: traefik.io/v1alpha1
kind: IngressRoute
metadata:
name: whoami-https
namespace: futureporn
annotations:
cert-manager.io/cluster-issuer: "{{ .Values.certManager.issuer }}"
spec:
entryPoints:
- websecure
routes:
- match: Host(`whoami.fp.sbtp.xyz`)
kind: Rule
services:
- name: whoami
namespace: futureporn
port: 80
tls:
secretName: whoami-tls
---
apiVersion: v1
kind: Service
metadata:
name: whoami
namespace: futureporn
annotations:
external-dns.alpha.kubernetes.io/hostname: "{{ .Values.whoami.hostname }}"
spec:
type: LoadBalancer
selector:
app: whoami
ports:
- port: 80
targetPort: 80
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: whoami
namespace: futureporn
spec:
replicas: 1
selector:
matchLabels:
app: whoami
template:
metadata:
labels:
app: whoami
spec:
containers:
- name: whoami
image: containous/whoami
ports:
- containerPort: 80
{{ end }}

View File

@ -18,11 +18,11 @@ next:
imageName: fp/next
hostname: next.fp.sbtp.xyz
ingressClassName: nginx
nodeExtraCaCerts: /app/letsencrypt-stg-root-x1.pem
nodeExtraCaCerts: /app/certs/letsencrypt-stg-root-x1.pem
capture:
imageName: fp/capture
worker:
replicas: 3
replicas: 1
api:
port: 5003
replicas: 1
@ -43,16 +43,19 @@ strapi:
hostname: strapi.fp.sbtp.xyz
# hostname: strapi.futureporn.svc.cluster.local ## https://gitea.futureporn.net/futureporn/pm/issues/126
ingressClassName: nginx
nodeExtraCaCerts: /usr/src/app/certs/letsencrypt-stg-root-x1.pem
ngrok:
hostname: grateful-engaging-cicada.ngrok-free.app
hostname: mint-star-crappie.ngrok-free.app
realtime:
imageName: fp/realtime
adminEmail: cj@futureporn.net
echo:
hostname: echo.fp.sbtp.xyz
uppy:
replicas: 3
hostname: uppy.fp.sbtp.xyz
imageName: fp/uppy
redisUrl: redis-master.futureporn.svc.cluster.local
s3:
endpoint: https://s3.us-west-000.backblazeb2.com
bucket: fp-usc-dev
@ -80,3 +83,11 @@ postgrest:
# replicas: 1
# user: futureporn
# port: 5432
chisel:
exitNode:
host: "155.138.254.201"
port: 9090
game2048:
hostname: game-2048.fp.sbtp.xyz
whoami:
hostname: whoami.fp.sbtp.xyz

View File

@ -0,0 +1,25 @@
# Source: https://github.com/helm/helm/blob/main/pkg/repo/repotest/testdata/examplechart/.helmignore
# 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
*~
# Various IDEs
.project
.idea/
*.tmproj
# helmtest plugin tests
tests

View File

@ -0,0 +1,156 @@
# Changelog
All notable changes to this project will be documented in this file.
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
## 0.14.0
**Full Changelog**: https://github.com/ngrok/kubernetes-ingress-controller/compare/helm-chart-0.13.0...helm-chart-0.14.0
### Added
- feat: Auto-provision domain for TLS Edges [#386]( https://github.com/ngrok/kubernetes-ingress-controller/pull/386)
- feat: Support for Load Balancer services [#387](https://github.com/ngrok/kubernetes-ingress-controller/pull/387)
- feat: Support TLS termination in modulesets for Load Balancer Services [388](https://github.com/ngrok/kubernetes-ingress-controller/pull/388)
## 0.13.0
**Full Changelog**: https://github.com/ngrok/kubernetes-ingress-controller/compare/helm-chart-0.12.4...helm-chart-0.13.0
**Important**: If you are upgrading from a previous version and are using `helm install` or `helm upgrade`, you will need to manually apply the changes to the CRDs. This is because the CRDs are not [updated automatically when the chart is updated](https://helm.sh/docs/chart_best_practices/custom_resource_definitions/#some-caveats-and-explanations). To do this, apply the contents of the `crds` directory in the chart to your cluster.
Ex (from the root of the repository):
```shell
kubectl apply -f ./helm/ingress-controller/templates/crds/
```
### Added
- root-cas setting [#371](https://github.com/ngrok/kubernetes-ingress-controller/pull/371)
Takes an install option for `--set rootCAs=host` and plumb the isHostCA check into the caCerts for it to just get the host certs.
- feat: Add support for mutualTLS [#373](https://github.com/ngrok/kubernetes-ingress-controller/pull/373)
### Changed
- Update nix flake, go version, and Makefile dep versions [#379](https://github.com/ngrok/kubernetes-ingress-controller/pull/379)
## 0.12.4
- Add the `apiURL` value.
This sets the ngrok API endpoint used by the controller.
It corresponds to the `--api-url` argument to the manager binary.
- Update to version 0.10.4 of the ingress controller.
See its changes [here](../../CHANGELOG.md#0104).
## 0.12.1
- Update to version 0.10.1 of the ingress controller, which includes:
- IPPolicy controller wasn't applying the attached rules, leaving the IP policy in its current state [#315](https://github.com/ngrok/kubernetes-ingress-controller/pull/315)
## 0.12.0
- Update to version 0.10.0 of the ingress controller, this includes:
- TLSEdge support - see the [TCP and TLS Edges Guide](https://github.com/ngrok/kubernetes-ingress-controller/blob/main/docs/user-guide/tcp-tls-edges.md) for more details.
- A fix for renegotiating TLS backends
## 0.11.0
** Important ** This version of the controller changes the ownership model for https edge and tunnel CRs. To ease out the transition to the new ownership, make sure to run `migrate-edges.sh` and `migrate-tunnels.sh` scripts before installing the new version.
### Changed
- Specify IPPolicyRule action as an enum of (allow,deny) as part of [#260](https://github.com/ngrok/kubernetes-ingress-controller/pull/260)
- Handle special case for changing auth types that causes an error during state transition [#259](https://github.com/ngrok/kubernetes-ingress-controller/pull/259)
- Better handling when changing pathType between 'Exact' and 'Prefix' [#262](https://github.com/ngrok/kubernetes-ingress-controller/pull/262)
- Update ngrok-go to 1.4.0 [#298](https://github.com/ngrok/kubernetes-ingress-controller/pull/298)
- Tunnels are now unique in their respective namespace, not across the cluster [#281](https://github.com/ngrok/kubernetes-ingress-controller/pull/281)
- The CRs that ingress controller creates are uniquely marked and managed by it. Other CRs created manually are no longer deleted when the ingress controller is not using them [#267](https://github.com/ngrok/kubernetes-ingress-controller/issues/267); fixed for tunnel in [#285](https://github.com/ngrok/kubernetes-ingress-controller/pull/285) and for https edges in [#286](https://github.com/ngrok/kubernetes-ingress-controller/pull/286)
- Better error handling and retry, specifically for the case where we try to create an https edge for a domain which is not created yet [#283](https://github.com/ngrok/kubernetes-ingress-controller/issues/283); fixed in [#288](https://github.com/ngrok/kubernetes-ingress-controller/pull/288)
- Watch and apply ngrok module set CR changes [#287](https://github.com/ngrok/kubernetes-ingress-controller/issues/287); fixed in [#290](https://github.com/ngrok/kubernetes-ingress-controller/pull/290)
- Label https edges and tunnels with service UID to make them more unique within ngrok [#291](https://github.com/ngrok/kubernetes-ingress-controller/issues/291); fixed in [#293](https://github.com/ngrok/kubernetes-ingress-controller/pull/293) and [#302](https://github.com/ngrok/kubernetes-ingress-controller/pull/302)
### Added
- Add support for configuring pod affinities, pod disruption budget, and priorityClassName [#258](https://github.com/ngrok/kubernetes-ingress-controller/pull/258)
- The controller stopping at the first resource create [#270](https://github.com/ngrok/kubernetes-ingress-controller/pull/270)
- Using `make deploy` now requires `NGROK_AUTHTOKEN` and `NGROK_API_KEY` to be set [#292](https://github.com/ngrok/kubernetes-ingress-controller/pull/292)
## 0.10.0
### Added
- Support HTTPS backends via service annotation [#238](https://github.com/ngrok/kubernetes-ingress-controller/pull/238)
### Changed
- Normalize all ngrok `.io` TLD to `.app` TLD [#240](https://github.com/ngrok/kubernetes-ingress-controller/pull/240)
- Chart Icon
### Fixed
- Add namespace to secret [#244](https://github.com/ngrok/kubernetes-ingress-controller/pull/244). Thank you for the contribution, @vincetse!
## 0.9.0
### Added
- Add a 'podLabels' option to the helm chart [#212](https://github.com/ngrok/kubernetes-ingress-controller/pull/212).
- Permission to `get`,`list`, and `watch` `services` [#222](https://github.com/ngrok-kubernetes-ingress-controller/pull/222).
## 0.8.0
### Changed
- Log Level configuration to helm chart [#199](https://github.com/ngrok/kubernetes-ingress-controller/pull/199).
- Bump default controller image to use `0.6.0` release [#204](https://github.com/ngrok/kubernetes-ingress-controller/pull/204).
### Fixed
- update default-container annotation so logs work correctly [#197](https://github.com/ngrok/kubernetes-ingress-controller/pull/197)
## 0.7.0
### Added
- Update `NgrokModuleSet` and `HTTPSEdge` CRD to support SAML and OAuth
### Changed
- Update appVersion to `0.5.0` to match the latest release of the controller.
## 0.6.1
### Fixed
- Default the image tag to the chart's `appVersion` for predictable installs. Previously, the helm chart would default to the `latest` image tag which can have breaking changes, notably with CRDs.
## 0.6.0
### Changed
- Ingress Class has Default set to false [#109](https://github.com/ngrok/kubernetes-ingress-controller/pull/109)
### Added
- Allow controller name to be configured to support multiple ngrok ingress classes [#159](https://github.com/ngrok/kubernetes-ingress-controller/pull/159)
- Allow the controller to be configured to only watch a single namespace [#157](https://github.com/ngrok/kubernetes-ingress-controller/pull/157)
- Pass key/value pairs to helm that get added as json string metadata in ngrok api resources [#156](https://github.com/ngrok/kubernetes-ingress-controller/pull/156)
- Add IP Policy CRD and IP Policy Route Module [#120](https://github.com/ngrok/kubernetes-ingress-controller/pull/120)
- Load certs from the directory `"/etc/ssl/certs/ngrok/"` for ngrok-go if present [#111](https://github.com/ngrok/kubernetes-ingress-controller/pull/111)
## 0.5.0
### Changed
- Renamed chart from `ngrok-ingress-controller` to `kubernetes-ingress-controller`.
- Added CRDs for `domains`, `tcpedges`, and `httpsedges`.
## 0.4.0
### Added
- `serverAddr` flag to override the ngrok tunnel server address
- `extraVolumes` to add an arbitrary set of volumes to the controller pod
- `extraVolumeMounts` to add an arbitrary set of volume mounts to the controller container
## 0.3.1
### Fixed
- Fixes rendering of `NOTES.txt` when installing via helm
## 0.3.0
### Changed
- Moved from calling ngrok-agent sidecar to using the ngrok-go library in the controller process.
- Moved `apiKey` and `authtoken` to `credentials.apiKey` and `credentials.authtoken` respectively.
- `credentialSecrets.name` is now `credentials.secret.name`
- Changed replicas to 1 by default to work better for default/demo setup.
## 0.2.0
### Added
- Support for different values commonly found in helm charts
# 0.1.0
TODO

View File

@ -0,0 +1,6 @@
dependencies:
- name: common
repository: https://charts.bitnami.com/bitnami
version: 2.19.3
digest: sha256:b0c5b947a6622accb48678c6034a1180e1fb58d0d8c8d2fa44cb7e9c3b1a4255
generated: "2024-05-21T13:06:30.412702362-05:00"

View File

@ -0,0 +1,21 @@
apiVersion: v2
appVersion: 0.12.0
dependencies:
- name: common
repository: https://charts.bitnami.com/bitnami
tags:
- bitnami-common
version: 2.x.x
description: A Kubernetes ingress controller built using ngrok.
home: https://ngrok.com
icon: https://ngrok.github.io/kubernetes-ingress-controller/ngrok-favicon.svg
keywords:
- ngrok
- networking
- ingress
- edge
- api gateway
name: kubernetes-ingress-controller
sources:
- https://github.com/ngrok/kubernetes-ingress-controller
version: 0.14.0

View File

@ -0,0 +1,93 @@
# ngrok Ingress Controller
This is the helm chart to install the ngrok ingress controller
# Usage
## Prerequisites
The cluster Must be setup with a secret named `ngrok-ingress-controller-credentials` with the following keys:
* AUTHTOKEN
* API\_KEY
## Install the controller with helm
[Helm](https://helm.sh) must be installed to use the charts. Please refer to
Helm's [documentation](https://helm.sh/docs) to get started.
Once Helm has been set up correctly, add the repo as follows:
`helm repo add ngrok https://ngrok.github.io/kubernetes-ingress-controller`
If you had already added this repo earlier, run `helm repo update` to retrieve
the latest versions of the packages. You can then run `helm search repo ngrok` to see the charts.
To install the ngrok-ingress-controller chart:
`helm install my-ngrok-ingress-controller ngrok/kubernetes-ingress-controller`
To uninstall the chart:
`helm delete my-ngrok-ingress-controller`
<!-- Parameters are auto generated via @bitnami/readme-generator-for-helm -->
## Parameters
### Common parameters
| Name | Description | Value |
| ------------------- | ----------------------------------------------------- | ----- |
| `nameOverride` | String to partially override generated resource names | `""` |
| `fullnameOverride` | String to fully override generated resource names | `""` |
| `commonLabels` | Labels to add to all deployed objects | `{}` |
| `commonAnnotations` | Annotations to add to all deployed objects | `{}` |
### Controller parameters
| Name | Description | Value |
| ------------------------------------ | --------------------------------------------------------------------------------------------------------------------- | ------------------------------------- |
| `podAnnotations` | Used to apply custom annotations to the ingress pods. | `{}` |
| `podLabels` | Used to apply custom labels to the ingress pods. | `{}` |
| `replicaCount` | The number of controllers to run. | `1` |
| `image.registry` | The ngrok ingress controller image registry. | `docker.io` |
| `image.repository` | The ngrok ingress controller image repository. | `ngrok/kubernetes-ingress-controller` |
| `image.tag` | The ngrok ingress controller image tag. Defaults to the chart's appVersion if not specified | `""` |
| `image.pullPolicy` | The ngrok ingress controller image pull policy. | `IfNotPresent` |
| `image.pullSecrets` | An array of imagePullSecrets to be used when pulling the image. | `[]` |
| `ingressClass.name` | The name of the ingress class to use. | `ngrok` |
| `ingressClass.create` | Whether to create the ingress class. | `true` |
| `ingressClass.default` | Whether to set the ingress class as default. | `false` |
| `controllerName` | The name of the controller to look for matching ingress classes | `k8s.ngrok.com/ingress-controller` |
| `watchNamespace` | The namespace to watch for ingress resources. Defaults to all | `""` |
| `credentials.secret.name` | The name of the secret the credentials are in. If not provided, one will be generated using the helm release name. | `""` |
| `credentials.apiKey` | Your ngrok API key. If provided, it will be will be written to the secret and the authtoken must be provided as well. | `""` |
| `credentials.authtoken` | Your ngrok authtoken. If provided, it will be will be written to the secret and the apiKey must be provided as well. | `""` |
| `region` | ngrok region to create tunnels in. Defaults to connect to the closest geographical region. | `""` |
| `rootCAs` | Set to "trusted" for the ngrok agent CA or "host" to trust the host's CA. Defaults to "trusted". | `""` |
| `serverAddr` | This is the address of the ngrok server to connect to. You should set this if you are using a custom ingress address. | `""` |
| `apiURL` | This is the URL of the ngrok API. You should set this if you are using a custom API URL. | `""` |
| `metaData` | This is a map of key/value pairs that will be added as meta data to all ngrok api resources created | `{}` |
| `affinity` | Affinity for the controller pod assignment | `{}` |
| `podAffinityPreset` | Pod affinity preset. Ignored if `affinity` is set. Allowed values: `soft` or `hard` | `""` |
| `podAntiAffinityPreset` | Pod anti-affinity preset. Ignored if `affinity` is set. Allowed values: `soft` or `hard` | `soft` |
| `nodeAffinityPreset.type` | Node affinity preset type. Ignored if `affinity` is set. Allowed values: `soft` or `hard` | `""` |
| `nodeAffinityPreset.key` | Node label key to match. Ignored if `affinity` is set. | `""` |
| `nodeAffinityPreset.values` | Node label values to match. Ignored if `affinity` is set. | `[]` |
| `priorityClassName` | Priority class for pod scheduling | `""` |
| `podDisruptionBudget.create` | Enable a Pod Disruption Budget creation | `false` |
| `podDisruptionBudget.minAvailable` | Minimum number/percentage of pods that should remain scheduled | `""` |
| `podDisruptionBudget.maxUnavailable` | Maximum number/percentage of pods that may be made unavailable | `1` |
| `resources.limits` | The resources limits for the container | `{}` |
| `resources.requests` | The requested resources for the container | `{}` |
| `extraVolumes` | An array of extra volumes to add to the controller. | `[]` |
| `extraVolumeMounts` | An array of extra volume mounts to add to the controller. | `[]` |
| `extraEnv` | an object of extra environment variables to add to the controller. | `{}` |
| `serviceAccount.create` | Specifies whether a ServiceAccount should be created | `true` |
| `serviceAccount.name` | The name of the ServiceAccount to use. | `""` |
| `serviceAccount.annotations` | Additional annotations to add to the ServiceAccount | `{}` |
| `log.level` | The level to log at. One of 'debug', 'info', or 'error'. | `info` |
| `log.stacktraceLevel` | The level to report stacktrace logs one of 'info' or 'error'. | `error` |
| `log.format` | The log format to use. One of console, json. | `json` |
| `lifecycle` | an object containing lifecycle configuration | `{}` |

View File

@ -0,0 +1,53 @@
================================================================================
The ngrok Ingress controller has been deployed as a Deployment type to your
cluster.
If you haven't yet, create some Ingress resources in your cluster and they will
be automatically configured on the internet using ngrok.
{{- $found := false }}
{{- range $svcIndex, $service := (lookup "v1" "Service" "" "").items }}
{{- if not $found }}
{{- range $portMapIdx, $portMap := $service.spec.ports }}
{{- if eq $portMap.port 80 443 }}
{{- if ne $service.metadata.name "kubernetes" }}
{{- $found = true -}}
{{- $randomStr := randAlphaNum 8 | lower }}
One example, taken from your cluster, is the Service:
{{ $service.metadata.name | quote }}
You can make this accessible via ngrok with the following manifest:
--------------------------------------------------------------------------------
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: {{ $service.metadata.name }}
namespace: {{ $service.metadata.namespace }}
spec:
ingressClassName: ngrok
rules:
- host: {{ $service.metadata.name -}}-{{- $randomStr -}}.ngrok.app
http:
paths:
- path: /
pathType: Prefix
backend:
service:
name: {{ $service.metadata.name }}
port:
number: {{ $portMap.port }}
--------------------------------------------------------------------------------
Applying this manifest will make the service {{ $service.metadata.name | quote }}
available on the public internet at "https://{{ $service.metadata.name -}}-{{- $randomStr -}}.ngrok.app/".
{{- end }}
{{- end }}
{{- end }}
{{- end}}
{{- end }}
Once done, view your edges in the Dashboard https://dashboard.ngrok.com/cloud-edge/edges
Find the tunnels running in your cluster here https://dashboard.ngrok.com/tunnels/agents
If you have any questions or feedback, please join us in https://ngrok.com/slack and let us know!

View File

@ -0,0 +1,87 @@
{{/* vim: set filetype=mustache: */}}
{{/*
Expand the name of the chart.
*/}}
{{- define "kubernetes-ingress-controller.name" -}}
{{- default .Chart.Name .Values.nameOverride | trunc 63 | trimSuffix "-" -}}
{{- end -}}
{{/*
Create chart name and version as used by the chart label.
*/}}
{{- define "kubernetes-ingress-controller.chart" -}}
{{- printf "%s-%s" .Chart.Name .Chart.Version | replace "+" "_" | 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).
*/}}
{{- define "kubernetes-ingress-controller.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 a default name for the credentials secret name using the helm release
*/}}
{{- define "kubernetes-ingress-controller.credentialsSecretName" -}}
{{- if .Values.credentials.secret.name -}}
{{- .Values.credentials.secret.name -}}
{{- else -}}
{{- printf "%s-credentials" (include "kubernetes-ingress-controller.fullname" .) -}}
{{- end -}}
{{- end -}}
{{/*
Common labels
*/}}
{{- define "kubernetes-ingress-controller.labels" -}}
helm.sh/chart: {{ include "kubernetes-ingress-controller.chart" . }}
{{ include "kubernetes-ingress-controller.selectorLabels" . }}
{{- if .Chart.AppVersion }}
app.kubernetes.io/version: {{ .Chart.AppVersion | quote }}
{{- end }}
app.kubernetes.io/part-of: {{ template "kubernetes-ingress-controller.name" . }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
{{- if .Values.commonLabels}}
{{ toYaml .Values.commonLabels }}
{{- end }}
{{- end -}}
{{/*
Selector labels
*/}}
{{- define "kubernetes-ingress-controller.selectorLabels" -}}
app.kubernetes.io/name: {{ include "kubernetes-ingress-controller.name" . }}
app.kubernetes.io/instance: {{ .Release.Name }}
{{- end -}}
{{/*
Create the name of the controller service account to use
*/}}
{{- define "kubernetes-ingress-controller.serviceAccountName" -}}
{{- if .Values.serviceAccount.create -}}
{{ default (include "kubernetes-ingress-controller.fullname" .) .Values.serviceAccount.name }}
{{- else -}}
{{ default "default" .Values.serviceAccount.name }}
{{- end -}}
{{- end -}}
{{/*
Return the ngrok/ingress-controller image name
*/}}
{{- define "kubernetes-ingress-controller.image" -}}
{{- $registryName := .Values.image.registry -}}
{{- $repositoryName := .Values.image.repository -}}
{{- $tag := .Values.image.tag | default .Chart.AppVersion | toString -}}
{{- printf "%s/%s:%s" $registryName $repositoryName $tag -}}
{{- end -}}

View File

@ -0,0 +1,16 @@
apiVersion: v1
kind: ConfigMap
metadata:
name: {{ include "kubernetes-ingress-controller.fullname" . }}-manager-config
namespace: {{ .Release.Namespace }}
data:
controller_manager_config.yaml: |
apiVersion: controller-runtime.sigs.k8s.io/v1alpha1
kind: ControllerManagerConfig
health:
healthProbeBindAddress: :8081
metrics:
bindAddress: 127.0.0.1:8080
leaderElection:
leaderElect: true
resourceName: {{ include "kubernetes-ingress-controller.fullname" . }}-leader

View File

@ -0,0 +1,143 @@
{{- $component := "controller" }}
apiVersion: apps/v1
kind: Deployment
metadata:
labels:
{{- include "kubernetes-ingress-controller.labels" . | nindent 4 }}
app.kubernetes.io/component: {{ $component }}
name: {{ include "kubernetes-ingress-controller.fullname" . }}-manager
namespace: {{ .Release.Namespace }}
annotations:
checksum/controller-role: {{ include (print $.Template.BasePath "/rbac/role.yaml") . | sha256sum }}
checksum/rbac: {{ include (print $.Template.BasePath "/controller-rbac.yaml") . | sha256sum }}
spec:
replicas: {{.Values.replicaCount}}
selector:
matchLabels:
{{- include "kubernetes-ingress-controller.selectorLabels" . | nindent 6 }}
{{- if .Values.podLabels }}
{{- toYaml .Values.podLabels | nindent 6 }}
{{- end }}
app.kubernetes.io/component: {{ $component }}
template:
metadata:
annotations:
{{- if .Values.podAnnotations }}
{{- toYaml .Values.podAnnotations | nindent 8 }}
{{- end }}
prometheus.io/path: /metrics
prometheus.io/port: '8080'
prometheus.io/scrape: 'true'
checksum/controller-role: {{ include (print $.Template.BasePath "/rbac/role.yaml") . | sha256sum }}
checksum/rbac: {{ include (print $.Template.BasePath "/controller-rbac.yaml") . | sha256sum }}
checksum/secret: {{ include (print $.Template.BasePath "/credentials-secret.yaml") . | sha256sum }}
labels:
{{- include "kubernetes-ingress-controller.selectorLabels" . | nindent 8 }}
{{- if .Values.podLabels }}
{{- toYaml .Values.podLabels | nindent 8 }}
{{- end }}
app.kubernetes.io/component: {{ $component }}
spec:
{{- if .Values.priorityClassName }}
priorityClassName: {{ .Values.priorityClassName | quote }}
{{- end }}
{{- if .Values.affinity }}
affinity: {{- include "common.tplvalues.render" (dict "value" .Values.affinity "context" $) | nindent 8 }}
{{- else }}
affinity:
podAffinity: {{- include "common.affinities.pods" (dict "type" .Values.podAffinityPreset "component" $component "context" $) | nindent 10 }}
podAntiAffinity: {{- include "common.affinities.pods" (dict "type" .Values.podAntiAffinityPreset "component" $component "context" $) | nindent 10 }}
nodeAffinity: {{- include "common.affinities.nodes" (dict "type" .Values.nodeAffinityPreset.type "key" .Values.nodeAffinityPreset.key "values" .Values.nodeAffinityPreset.values) | nindent 10 }}
{{- end }}
serviceAccountName: {{ template "kubernetes-ingress-controller.serviceAccountName" . }}
{{- if .Values.image.pullSecrets }}
imagePullSecrets:
{{- toYaml .Values.image.pullSecrets | nindent 8 }}
{{- end }}
containers:
- name: ngrok-ingress-controller
image: {{ include "kubernetes-ingress-controller.image" . }}
imagePullPolicy: {{ .Values.image.pullPolicy }}
command:
- /manager
args:
{{- if .Values.region }}
- --region={{ .Values.region}}
{{- end }}
{{- if .Values.apiURL }}
- --api-url={{ .Values.apiURL}}
{{- end }}
{{- if .Values.rootCAs }}
- --root-cas={{ .Values.rootCAs}}
{{- end }}
{{- if .Values.serverAddr }}
- --server-addr={{ .Values.serverAddr}}
{{- end }}
{{- if .Values.metaData }}
- --metadata={{- $metadataArgs := list -}}
{{- range $key, $value := .Values.metaData }}
{{- $metadataArgs = append $metadataArgs (printf "%s=%s" $key $value) -}}
{{- end }}
{{- $metadataArgs | join "," }}
{{- end }}
- --controller-name={{ .Values.controllerName }}
{{- if .Values.watchNamespace }}
- --watch-namespace={{ .Values.watchNamespace}}
{{- end }}
{{- if .Values.useExperimentalGatewayApi }}
- --use-experimental-gateway-api={{ .Values.useExperimentalGatewayApi }}
{{- end }}
- --zap-log-level={{ .Values.log.level }}
- --zap-stacktrace-level={{ .Values.log.stacktraceLevel }}
- --zap-encoder={{ .Values.log.format }}
- --health-probe-bind-address=:8081
- --metrics-bind-address=:8080
- --election-id={{ include "kubernetes-ingress-controller.fullname" . }}-leader
- --manager-name={{ include "kubernetes-ingress-controller.fullname" . }}-manager
securityContext:
allowPrivilegeEscalation: false
env:
- name: NGROK_API_KEY
valueFrom:
secretKeyRef:
key: API_KEY
name: {{ include "kubernetes-ingress-controller.credentialsSecretName" . }}
- name: NGROK_AUTHTOKEN
valueFrom:
secretKeyRef:
key: AUTHTOKEN
name: {{ include "kubernetes-ingress-controller.credentialsSecretName" . }}
- name: POD_NAMESPACE
valueFrom:
fieldRef:
fieldPath: metadata.namespace
{{- range $key, $value := .Values.extraEnv }}
- name: {{ $key }}
value: {{- toYaml $value | nindent 12 }}
{{- end }}
{{- if .Values.extraVolumeMounts }}
volumeMounts:
{{ toYaml .Values.extraVolumeMounts | nindent 10 }}
{{- end }}
{{- if .Values.lifecycle }}
lifecycle:
{{ toYaml .Values.lifecycle | nindent 10 }}
{{- end }}
livenessProbe:
httpGet:
path: /healthz
port: 8081
initialDelaySeconds: 15
periodSeconds: 20
readinessProbe:
httpGet:
path: /readyz
port: 8081
initialDelaySeconds: 5
periodSeconds: 10
resources:
{{- toYaml .Values.resources | nindent 10 }}
{{- if .Values.extraVolumes }}
volumes:
{{ toYaml .Values.extraVolumes | nindent 6 }}
{{- end }}

View File

@ -0,0 +1,26 @@
{{- if .Values.podDisruptionBudget.create }}
{{ $component := "controller"}}
---
apiVersion: policy/v1
kind: PodDisruptionBudget
metadata:
name: {{ include "kubernetes-ingress-controller.fullname" . }}-controller-pdb
namespace: {{ .Release.Namespace | quote }}
labels:
{{- include "kubernetes-ingress-controller.labels" . | nindent 4 }}
app.kubernetes.io/component: {{ $component }}
spec:
{{- if .Values.podDisruptionBudget.minAvailable }}
minAvailable: {{ .Values.podDisruptionBudget.minAvailable }}
{{- end }}
{{- if .Values.podDisruptionBudget.maxUnavailable }}
maxUnavailable: {{ .Values.podDisruptionBudget.maxUnavailable }}
{{- end }}
selector:
matchLabels:
{{- include "kubernetes-ingress-controller.selectorLabels" . | nindent 6 }}
{{- if .Values.podLabels }}
{{- toYaml .Values.podLabels | nindent 6 }}
{{- end }}
app.kubernetes.io/component: {{ $component }}
{{- end }}

View File

@ -0,0 +1,96 @@
---
apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
name: ngrok-ingress-controller-leader-election-role
namespace: {{ .Release.Namespace }}
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: ClusterRole
metadata:
name: ngrok-ingress-controller-proxy-role
rules:
- apiGroups:
- authentication.k8s.io
resources:
- tokenreviews
verbs:
- create
- apiGroups:
- authorization.k8s.io
resources:
- subjectaccessreviews
verbs:
- create
---
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
name: ngrok-ingress-controller-leader-election-rolebinding
namespace: {{ .Release.Namespace }}
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: Role
name: ngrok-ingress-controller-leader-election-role
subjects:
- kind: ServiceAccount
name: {{ template "kubernetes-ingress-controller.serviceAccountName" . }}
namespace: {{ .Release.Namespace }}
---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
name: ngrok-ingress-controller-manager-rolebinding
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: ngrok-ingress-controller-manager-role
subjects:
- kind: ServiceAccount
name: {{ template "kubernetes-ingress-controller.serviceAccountName" . }}
namespace: {{ .Release.Namespace }}
---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
name: ngrok-ingress-controller-proxy-rolebinding
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: ngrok-ingress-controller-proxy-role
subjects:
- kind: ServiceAccount
name: {{ template "kubernetes-ingress-controller.serviceAccountName" . }}
namespace: {{ .Release.Namespace }}

View File

@ -0,0 +1,15 @@
{{- if .Values.serviceAccount.create -}}
---
apiVersion: v1
kind: ServiceAccount
metadata:
name: {{ template "kubernetes-ingress-controller.serviceAccountName" . }}
namespace: {{ .Release.Namespace }}
labels:
{{- include "kubernetes-ingress-controller.labels" . | nindent 4 }}
app.kubernetes.io/component: controller
{{- if .Values.serviceAccount.annotations }}
annotations:
{{- toYaml .Values.serviceAccount.annotations | nindent 4 }}
{{- end }}
{{- end }}

View File

@ -0,0 +1,105 @@
---
apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
metadata:
annotations:
controller-gen.kubebuilder.io/version: v0.14.0
name: domains.ingress.k8s.ngrok.com
spec:
group: ingress.k8s.ngrok.com
names:
kind: Domain
listKind: DomainList
plural: domains
singular: domain
scope: Namespaced
versions:
- additionalPrinterColumns:
- description: Domain ID
jsonPath: .status.id
name: ID
type: string
- description: Region
jsonPath: .status.region
name: Region
type: string
- description: Domain
jsonPath: .status.domain
name: Domain
type: string
- description: CNAME Target
jsonPath: .status.cnameTarget
name: CNAME Target
type: string
- description: Age
jsonPath: .metadata.creationTimestamp
name: Age
type: date
name: v1alpha1
schema:
openAPIV3Schema:
description: Domain is the Schema for the domains 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: DomainSpec defines the desired state of Domain
properties:
description:
default: Created by kubernetes-ingress-controller
description: Description is a human-readable description of the object
in the ngrok API/Dashboard
type: string
domain:
description: Domain is the domain name to reserve
type: string
metadata:
default: '{"owned-by":"kubernetes-ingress-controller"}'
description: Metadata is a string of arbitrary data associated with
the object in the ngrok API/Dashboard
type: string
region:
description: Region is the region in which to reserve the domain
type: string
required:
- domain
type: object
status:
description: DomainStatus defines the observed state of Domain
properties:
cnameTarget:
description: CNAMETarget is the CNAME target for the domain
type: string
domain:
description: Domain is the domain that was reserved
type: string
id:
description: ID is the unique identifier of the domain
type: string
region:
description: Region is the region in which the domain was created
type: string
uri:
description: URI of the reserved domain API resource
type: string
type: object
type: object
served: true
storage: true
subresources:
status: {}

View File

@ -0,0 +1,109 @@
---
apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
metadata:
annotations:
controller-gen.kubebuilder.io/version: v0.14.0
name: ippolicies.ingress.k8s.ngrok.com
spec:
group: ingress.k8s.ngrok.com
names:
kind: IPPolicy
listKind: IPPolicyList
plural: ippolicies
singular: ippolicy
scope: Namespaced
versions:
- additionalPrinterColumns:
- description: IPPolicy ID
jsonPath: .status.id
name: ID
type: string
- description: Age
jsonPath: .metadata.creationTimestamp
name: Age
type: date
name: v1alpha1
schema:
openAPIV3Schema:
description: IPPolicy is the Schema for the ippolicies 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: IPPolicySpec defines the desired state of IPPolicy
properties:
description:
default: Created by kubernetes-ingress-controller
description: Description is a human-readable description of the object
in the ngrok API/Dashboard
type: string
metadata:
default: '{"owned-by":"kubernetes-ingress-controller"}'
description: Metadata is a string of arbitrary data associated with
the object in the ngrok API/Dashboard
type: string
rules:
description: Rules is a list of rules that belong to the policy
items:
properties:
action:
enum:
- allow
- deny
type: string
cidr:
type: string
description:
default: Created by kubernetes-ingress-controller
description: Description is a human-readable description of
the object in the ngrok API/Dashboard
type: string
metadata:
default: '{"owned-by":"kubernetes-ingress-controller"}'
description: Metadata is a string of arbitrary data associated
with the object in the ngrok API/Dashboard
type: string
type: object
type: array
type: object
status:
description: IPPolicyStatus defines the observed state of IPPolicy
properties:
id:
description: |-
INSERT ADDITIONAL STATUS FIELD - define observed state of cluster
Important: Run "make" to regenerate code after modifying this file
type: string
rules:
items:
properties:
action:
type: string
cidr:
type: string
id:
type: string
type: object
type: array
type: object
type: object
served: true
storage: true
subresources:
status: {}

View File

@ -0,0 +1,132 @@
---
apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
metadata:
annotations:
controller-gen.kubebuilder.io/version: v0.14.0
name: tcpedges.ingress.k8s.ngrok.com
spec:
group: ingress.k8s.ngrok.com
names:
kind: TCPEdge
listKind: TCPEdgeList
plural: tcpedges
singular: tcpedge
scope: Namespaced
versions:
- additionalPrinterColumns:
- description: Domain ID
jsonPath: .status.id
name: ID
type: string
- description: Hostports
jsonPath: .status.hostports
name: Hostports
type: string
- description: Tunnel Group Backend ID
jsonPath: .status.backend.id
name: Backend ID
type: string
- description: Age
jsonPath: .metadata.creationTimestamp
name: Age
type: date
name: v1alpha1
schema:
openAPIV3Schema:
description: TCPEdge is the Schema for the tcpedges 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: TCPEdgeSpec defines the desired state of TCPEdge
properties:
backend:
description: |-
Backend is the definition for the tunnel group backend
that serves traffic for this edge
properties:
description:
default: Created by kubernetes-ingress-controller
description: Description is a human-readable description of the
object in the ngrok API/Dashboard
type: string
labels:
additionalProperties:
type: string
description: Labels to watch for tunnels on this backend
type: object
metadata:
default: '{"owned-by":"kubernetes-ingress-controller"}'
description: Metadata is a string of arbitrary data associated
with the object in the ngrok API/Dashboard
type: string
type: object
description:
default: Created by kubernetes-ingress-controller
description: Description is a human-readable description of the object
in the ngrok API/Dashboard
type: string
ipRestriction:
description: IPRestriction is an IPRestriction to apply to this edge
properties:
policies:
items:
type: string
type: array
type: object
metadata:
default: '{"owned-by":"kubernetes-ingress-controller"}'
description: Metadata is a string of arbitrary data associated with
the object in the ngrok API/Dashboard
type: string
policy:
description: raw json policy string that was applied to the ngrok
API
type: object
x-kubernetes-preserve-unknown-fields: true
type: object
status:
description: TCPEdgeStatus defines the observed state of TCPEdge
properties:
backend:
description: |-
Backend stores the status of the tunnel group backend,
mainly the ID of the backend
properties:
id:
description: ID is the unique identifier for this backend
type: string
type: object
hostports:
description: Hostports served by this edge
items:
type: string
type: array
id:
description: ID is the unique identifier for this edge
type: string
uri:
description: URI is the URI of the edge
type: string
type: object
type: object
served: true
storage: true
subresources:
status: {}

View File

@ -0,0 +1,166 @@
---
apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
metadata:
annotations:
controller-gen.kubebuilder.io/version: v0.14.0
name: tlsedges.ingress.k8s.ngrok.com
spec:
group: ingress.k8s.ngrok.com
names:
kind: TLSEdge
listKind: TLSEdgeList
plural: tlsedges
singular: tlsedge
scope: Namespaced
versions:
- additionalPrinterColumns:
- description: Domain ID
jsonPath: .status.id
name: ID
type: string
- description: Hostports
jsonPath: .status.hostports
name: Hostports
type: string
- description: Tunnel Group Backend ID
jsonPath: .status.backend.id
name: Backend ID
type: string
- description: Age
jsonPath: .metadata.creationTimestamp
name: Age
type: date
name: v1alpha1
schema:
openAPIV3Schema:
description: TLSEdge is the Schema for the tlsedges 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: TLSEdgeSpec defines the desired state of TLSEdge
properties:
backend:
description: |-
Backend is the definition for the tunnel group backend
that serves traffic for this edge
properties:
description:
default: Created by kubernetes-ingress-controller
description: Description is a human-readable description of the
object in the ngrok API/Dashboard
type: string
labels:
additionalProperties:
type: string
description: Labels to watch for tunnels on this backend
type: object
metadata:
default: '{"owned-by":"kubernetes-ingress-controller"}'
description: Metadata is a string of arbitrary data associated
with the object in the ngrok API/Dashboard
type: string
type: object
description:
default: Created by kubernetes-ingress-controller
description: Description is a human-readable description of the object
in the ngrok API/Dashboard
type: string
hostports:
description: Hostports is a list of hostports served by this edge
items:
type: string
type: array
ipRestriction:
description: IPRestriction is an IPRestriction to apply to this edge
properties:
policies:
items:
type: string
type: array
type: object
metadata:
default: '{"owned-by":"kubernetes-ingress-controller"}'
description: Metadata is a string of arbitrary data associated with
the object in the ngrok API/Dashboard
type: string
mutualTls:
properties:
certificateAuthorities:
description: |-
List of CA IDs that will be used to validate incoming connections to the
edge.
items:
type: string
type: array
type: object
policy:
description: raw json policy string that was applied to the ngrok
API
type: object
x-kubernetes-preserve-unknown-fields: true
tlsTermination:
properties:
minVersion:
description: MinVersion is the minimum TLS version to allow for
connections to the edge
type: string
terminateAt:
description: |-
TerminateAt determines where the TLS connection should be terminated.
"edge" if the ngrok edge should terminate TLS traffic, "upstream" if TLS
traffic should be passed through to the upstream ngrok agent /
application server for termination.
type: string
type: object
type: object
status:
description: TLSEdgeStatus defines the observed state of TLSEdge
properties:
backend:
description: |-
Backend stores the status of the tunnel group backend,
mainly the ID of the backend
properties:
id:
description: ID is the unique identifier for this backend
type: string
type: object
cnameTargets:
additionalProperties:
type: string
description: Map of hostports to the ngrok assigned CNAME targets
type: object
hostports:
description: Hostports served by this edge
items:
type: string
type: array
id:
description: ID is the unique identifier for this edge
type: string
uri:
description: URI is the URI of the edge
type: string
type: object
type: object
served: true
storage: true
subresources:
status: {}

View File

@ -0,0 +1,78 @@
---
apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
metadata:
annotations:
controller-gen.kubebuilder.io/version: v0.14.0
name: tunnels.ingress.k8s.ngrok.com
spec:
group: ingress.k8s.ngrok.com
names:
kind: Tunnel
listKind: TunnelList
plural: tunnels
singular: tunnel
scope: Namespaced
versions:
- additionalPrinterColumns:
- description: Service/port to forward to
jsonPath: .spec.forwardsTo
name: ForwardsTo
type: string
- description: Age
jsonPath: .metadata.creationTimestamp
name: Age
type: date
name: v1alpha1
schema:
openAPIV3Schema:
description: Tunnel is the Schema for the tunnels 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: TunnelSpec defines the desired state of Tunnel
properties:
appProtocol:
description: The appProtocol for the backend. Currently only supports
`http2`
type: string
backend:
description: The configuration for backend connections to services
properties:
protocol:
type: string
type: object
forwardsTo:
description: ForwardsTo is the name and port of the service to forward
traffic to
type: string
labels:
additionalProperties:
type: string
description: Labels are key/value pairs that are attached to the tunnel
type: object
type: object
status:
description: TunnelStatus defines the observed state of Tunnel
type: object
type: object
served: true
storage: true
subresources:
status: {}

View File

@ -0,0 +1,62 @@
---
apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
metadata:
annotations:
controller-gen.kubebuilder.io/version: v0.14.0
name: ngroktrafficpolicies.ngrok.k8s.ngrok.com
spec:
group: ngrok.k8s.ngrok.com
names:
kind: NgrokTrafficPolicy
listKind: NgrokTrafficPolicyList
plural: ngroktrafficpolicies
singular: ngroktrafficpolicy
scope: Namespaced
versions:
- name: v1alpha1
schema:
openAPIV3Schema:
description: NgrokTrafficPolicy is the Schema for the ngroktrafficpolicies
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: NgrokTrafficPolicySpec defines the desired state of NgrokTrafficPolicy
properties:
policy:
description: The raw json encoded policy that was applied to the ngrok
API
type: object
x-kubernetes-preserve-unknown-fields: true
type: object
status:
description: NgrokTrafficPolicyStatus defines the observed state of NgrokTrafficPolicy
properties:
policy:
description: The raw json encoded policy that was applied to the ngrok
API
type: object
x-kubernetes-preserve-unknown-fields: true
type: object
type: object
served: true
storage: true
subresources:
status: {}

View File

@ -0,0 +1,11 @@
{{- if or (not (empty .Values.credentials.apiKey)) (not (empty .Values.credentials.authtoken)) }}
apiVersion: v1
kind: Secret
metadata:
name: {{ include "kubernetes-ingress-controller.credentialsSecretName" .}}
namespace: {{ .Release.Namespace }}
type: Opaque
data:
API_KEY: {{ required "An ngrok API key is required" .Values.credentials.apiKey | b64enc }}
AUTHTOKEN: {{ required "An ngrok Authtoken is required" .Values.credentials.authtoken | b64enc }}
{{ end }}

View File

@ -0,0 +1,15 @@
{{- if .Values.ingressClass.create -}}
apiVersion: networking.k8s.io/v1
kind: IngressClass
metadata:
labels:
{{- include "kubernetes-ingress-controller.labels" . | nindent 4 }}
app.kubernetes.io/component: controller
name: {{ .Values.ingressClass.name }}
{{- if .Values.ingressClass.default }}
annotations:
ingressclass.kubernetes.io/is-default-class: "true"
{{- end }}
spec:
controller: {{ .Values.controllerName }}
{{- end}}

View File

@ -0,0 +1,27 @@
# permissions for end users to edit domains.
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
labels:
{{- include "kubernetes-ingress-controller.labels" . | nindent 4 }}
app.kubernetes.io/component: rbac
name: {{ include "kubernetes-ingress-controller.fullname" . }}-domain-editor-role
rules:
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- domains
verbs:
- create
- delete
- get
- list
- patch
- update
- watch
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- domains/status
verbs:
- get

View File

@ -0,0 +1,23 @@
# permissions for end users to view domains.
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
labels:
{{- include "kubernetes-ingress-controller.labels" . | nindent 4 }}
app.kubernetes.io/component: rbac
name: {{ include "kubernetes-ingress-controller.fullname" . }}-domain-viewer-role
rules:
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- domains
verbs:
- get
- list
- watch
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- domains/status
verbs:
- get

View File

@ -0,0 +1,31 @@
# permissions for end users to edit httpsedges.
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
labels:
app.kubernetes.io/name: clusterrole
app.kubernetes.io/instance: httpsedge-editor-role
app.kubernetes.io/component: rbac
app.kubernetes.io/created-by: ngrok-ingress-controller
app.kubernetes.io/part-of: ngrok-ingress-controller
app.kubernetes.io/managed-by: kustomize
name: httpsedge-editor-role
rules:
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- httpsedges
verbs:
- create
- delete
- get
- list
- patch
- update
- watch
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- httpsedges/status
verbs:
- get

View File

@ -0,0 +1,27 @@
# permissions for end users to view httpsedges.
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
labels:
app.kubernetes.io/name: clusterrole
app.kubernetes.io/instance: httpsedge-viewer-role
app.kubernetes.io/component: rbac
app.kubernetes.io/created-by: ngrok-ingress-controller
app.kubernetes.io/part-of: ngrok-ingress-controller
app.kubernetes.io/managed-by: kustomize
name: httpsedge-viewer-role
rules:
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- httpsedges
verbs:
- get
- list
- watch
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- httpsedges/status
verbs:
- get

View File

@ -0,0 +1,31 @@
# permissions for end users to edit ippolicies.
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
labels:
app.kubernetes.io/name: clusterrole
app.kubernetes.io/instance: ippolicy-editor-role
app.kubernetes.io/component: rbac
app.kubernetes.io/created-by: ngrok-ingress-controller
app.kubernetes.io/part-of: ngrok-ingress-controller
app.kubernetes.io/managed-by: kustomize
name: ippolicy-editor-role
rules:
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- ippolicies
verbs:
- create
- delete
- get
- list
- patch
- update
- watch
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- ippolicies/status
verbs:
- get

View File

@ -0,0 +1,27 @@
# permissions for end users to view ippolicies.
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
labels:
app.kubernetes.io/name: clusterrole
app.kubernetes.io/instance: ippolicy-viewer-role
app.kubernetes.io/component: rbac
app.kubernetes.io/created-by: ngrok-ingress-controller
app.kubernetes.io/part-of: ngrok-ingress-controller
app.kubernetes.io/managed-by: kustomize
name: ippolicy-viewer-role
rules:
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- ippolicies
verbs:
- get
- list
- watch
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- ippolicies/status
verbs:
- get

View File

@ -0,0 +1,31 @@
# permissions for end users to edit ngrokmodulesets.
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
labels:
app.kubernetes.io/name: clusterrole
app.kubernetes.io/instance: ngrokmoduleset-editor-role
app.kubernetes.io/component: rbac
app.kubernetes.io/created-by: kubernetes-ingress-controller
app.kubernetes.io/part-of: kubernetes-ingress-controller
app.kubernetes.io/managed-by: kustomize
name: ngrokmoduleset-editor-role
rules:
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- ngrokmodulesets
verbs:
- create
- delete
- get
- list
- patch
- update
- watch
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- ngrokmodulesets/status
verbs:
- get

View File

@ -0,0 +1,27 @@
# permissions for end users to view ngrokmodulesets.
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
labels:
app.kubernetes.io/name: clusterrole
app.kubernetes.io/instance: ngrokmoduleset-viewer-role
app.kubernetes.io/component: rbac
app.kubernetes.io/created-by: kubernetes-ingress-controller
app.kubernetes.io/part-of: kubernetes-ingress-controller
app.kubernetes.io/managed-by: kustomize
name: ngrokmoduleset-viewer-role
rules:
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- ngrokmodulesets
verbs:
- get
- list
- watch
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- ngrokmodulesets/status
verbs:
- get

View File

@ -0,0 +1,330 @@
---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
name: ngrok-ingress-controller-manager-role
rules:
- apiGroups:
- ""
resources:
- configmaps
verbs:
- create
- delete
- get
- list
- update
- watch
- apiGroups:
- ""
resources:
- events
verbs:
- create
- patch
- apiGroups:
- ""
resources:
- namespaces
verbs:
- get
- list
- update
- watch
- apiGroups:
- ""
resources:
- secrets
verbs:
- get
- list
- watch
- apiGroups:
- ""
resources:
- services
verbs:
- get
- list
- update
- watch
- apiGroups:
- ""
resources:
- services/status
verbs:
- get
- list
- patch
- update
- watch
- apiGroups:
- gateway.networking.k8s.io
resources:
- gatewayclasses
verbs:
- get
- list
- update
- watch
- apiGroups:
- gateway.networking.k8s.io
resources:
- gatewayclasses/status
verbs:
- get
- list
- update
- watch
- apiGroups:
- gateway.networking.k8s.io
resources:
- gateways
verbs:
- get
- list
- update
- watch
- apiGroups:
- gateway.networking.k8s.io
resources:
- gateways/status
verbs:
- get
- list
- update
- watch
- apiGroups:
- gateway.networking.k8s.io
resources:
- httproutes
verbs:
- get
- list
- update
- watch
- apiGroups:
- gateway.networking.k8s.io
resources:
- httproutes/status
verbs:
- get
- list
- update
- watch
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- domains
verbs:
- create
- delete
- get
- list
- patch
- update
- watch
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- domains/finalizers
verbs:
- update
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- domains/status
verbs:
- get
- patch
- update
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- httpsedges
verbs:
- create
- delete
- get
- list
- patch
- update
- watch
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- httpsedges/finalizers
verbs:
- update
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- httpsedges/status
verbs:
- get
- patch
- update
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- ippolicies
verbs:
- create
- delete
- get
- list
- patch
- update
- watch
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- ippolicies/finalizers
verbs:
- update
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- ippolicies/status
verbs:
- get
- patch
- update
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- ngrokmodulesets
verbs:
- get
- list
- watch
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- tcpedges
verbs:
- create
- delete
- get
- list
- patch
- update
- watch
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- tcpedges/finalizers
verbs:
- update
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- tcpedges/status
verbs:
- get
- patch
- update
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- tlsedges
verbs:
- create
- delete
- get
- list
- patch
- update
- watch
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- tlsedges/finalizers
verbs:
- update
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- tlsedges/status
verbs:
- get
- patch
- update
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- tunnels
verbs:
- create
- delete
- get
- list
- patch
- update
- watch
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- tunnels/finalizers
verbs:
- update
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- tunnels/status
verbs:
- get
- patch
- update
- apiGroups:
- networking.k8s.io
resources:
- ingressclasses
verbs:
- get
- list
- watch
- apiGroups:
- networking.k8s.io
resources:
- ingresses
verbs:
- get
- list
- update
- watch
- apiGroups:
- networking.k8s.io
resources:
- ingresses/status
verbs:
- get
- list
- update
- watch
- apiGroups:
- ngrok.k8s.ngrok.com
resources:
- ngroktrafficpolicies
verbs:
- create
- delete
- get
- list
- patch
- update
- watch
- apiGroups:
- ngrok.k8s.ngrok.com
resources:
- ngroktrafficpolicies/finalizers
verbs:
- update
- apiGroups:
- ngrok.k8s.ngrok.com
resources:
- ngroktrafficpolicies/status
verbs:
- get
- patch
- update

View File

@ -0,0 +1,31 @@
# permissions for end users to edit tcpedges.
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
labels:
app.kubernetes.io/name: clusterrole
app.kubernetes.io/instance: tcpedge-editor-role
app.kubernetes.io/component: rbac
app.kubernetes.io/created-by: ngrok-ingress-controller
app.kubernetes.io/part-of: ngrok-ingress-controller
app.kubernetes.io/managed-by: kustomize
name: tcpedge-editor-role
rules:
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- tcpedges
verbs:
- create
- delete
- get
- list
- patch
- update
- watch
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- tcpedges/status
verbs:
- get

View File

@ -0,0 +1,27 @@
# permissions for end users to view tcpedges.
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
labels:
app.kubernetes.io/name: clusterrole
app.kubernetes.io/instance: tcpedge-viewer-role
app.kubernetes.io/component: rbac
app.kubernetes.io/created-by: ngrok-ingress-controller
app.kubernetes.io/part-of: ngrok-ingress-controller
app.kubernetes.io/managed-by: kustomize
name: tcpedge-viewer-role
rules:
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- tcpedges
verbs:
- get
- list
- watch
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- tcpedges/status
verbs:
- get

View File

@ -0,0 +1,31 @@
# permissions for end users to edit tlsedges.
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
labels:
app.kubernetes.io/name: clusterrole
app.kubernetes.io/instance: tlsedge-editor-role
app.kubernetes.io/component: rbac
app.kubernetes.io/created-by: ngrok-ingress-controller
app.kubernetes.io/part-of: ngrok-ingress-controller
app.kubernetes.io/managed-by: kustomize
name: tlsedge-editor-role
rules:
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- tlsedges
verbs:
- create
- delete
- get
- list
- patch
- update
- watch
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- tlsedges/status
verbs:
- get

View File

@ -0,0 +1,27 @@
# permissions for end users to view tlsedges.
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
labels:
app.kubernetes.io/name: clusterrole
app.kubernetes.io/instance: tlsedge-viewer-role
app.kubernetes.io/component: rbac
app.kubernetes.io/created-by: ngrok-ingress-controller
app.kubernetes.io/part-of: ngrok-ingress-controller
app.kubernetes.io/managed-by: kustomize
name: tlsedge-viewer-role
rules:
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- tlsedges
verbs:
- get
- list
- watch
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- tlsedges/status
verbs:
- get

View File

@ -0,0 +1,27 @@
# permissions for end users to edit tunnels.
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
labels:
{{- include "kubernetes-ingress-controller.labels" . | nindent 4 }}
app.kubernetes.io/component: rbac
name: {{ include "kubernetes-ingress-controller.fullname" . }}-tunnel-editor-role
rules:
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- tunnels
verbs:
- create
- delete
- get
- list
- patch
- update
- watch
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- tunnels/status
verbs:
- get

View File

@ -0,0 +1,23 @@
# permissions for end users to view tunnels.
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
labels:
{{- include "kubernetes-ingress-controller.labels" . | nindent 4 }}
app.kubernetes.io/component: rbac
name: {{ include "kubernetes-ingress-controller.fullname" . }}-tunnel-viewer-role
rules:
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- tunnels
verbs:
- get
- list
- watch
- apiGroups:
- ingress.k8s.ngrok.com
resources:
- tunnels/status
verbs:
- get

View File

@ -0,0 +1,202 @@
## @section Common parameters
##
## @param nameOverride String to partially override generated resource names
## @param fullnameOverride String to fully override generated resource names
## @param commonLabels Labels to add to all deployed objects
## @param commonAnnotations Annotations to add to all deployed objects
##
nameOverride: ""
fullnameOverride: ""
commonLabels: {}
commonAnnotations: {}
## @section Controller parameters
##
## @param podAnnotations Used to apply custom annotations to the ingress pods.
## @param podLabels Used to apply custom labels to the ingress pods.
##
podAnnotations: {}
podLabels: {}
## @param replicaCount The number of controllers to run.
## A minimum of 2 is recommended in production for HA.
##
replicaCount: 1
## @param image.registry The ngrok ingress controller image registry.
## @param image.repository The ngrok ingress controller image repository.
## @param image.tag The ngrok ingress controller image tag. Defaults to the chart's appVersion if not specified
## @param image.pullPolicy The ngrok ingress controller image pull policy.
## @param image.pullSecrets An array of imagePullSecrets to be used when pulling the image.
image:
registry: docker.io
repository: ngrok/kubernetes-ingress-controller
tag: ""
pullPolicy: IfNotPresent
## Example
## pullSecrets:
## - name: my-imagepull-secret
##
pullSecrets: []
## @param ingressClass.name The name of the ingress class to use.
## @param ingressClass.create Whether to create the ingress class.
## @param ingressClass.default Whether to set the ingress class as default.
ingressClass:
name: ngrok
create: true
default: false
## @param controllerName The name of the controller to look for matching ingress classes
controllerName: "k8s.ngrok.com/ingress-controller"
## @param watchNamespace The namespace to watch for ingress resources. Defaults to all
watchNamespace: ""
## @param credentials.secret.name The name of the secret the credentials are in. If not provided, one will be generated using the helm release name.
## @param credentials.apiKey Your ngrok API key. If provided, it will be will be written to the secret and the authtoken must be provided as well.
## @param credentials.authtoken Your ngrok authtoken. If provided, it will be will be written to the secret and the apiKey must be provided as well.
credentials:
secret:
name: ""
apiKey: ""
authtoken: ""
## @param region ngrok region to create tunnels in. Defaults to connect to the closest geographical region.
region: ""
## @param rootCAs Set to "trusted" for the ngrok agent CA or "host" to trust the host's CA. Defaults to "trusted".
rootCAs: ""
## @param serverAddr This is the address of the ngrok server to connect to. You should set this if you are using a custom ingress address.
serverAddr: ""
## @param apiURL This is the URL of the ngrok API. You should set this if you are using a custom API URL.
apiURL: ""
## @param metaData This is a map of key/value pairs that will be added as meta data to all ngrok api resources created
metaData: {}
## @param affinity Affinity for the controller pod assignment
## ref: https://kubernetes.io/docs/concepts/configuration/assign-pod-node/#affinity-and-anti-affinity
## Note: podAffinityPreset, podAntiAffinityPreset, and nodeAffinityPreset will be ignored when it's set
##
affinity: {}
## @param podAffinityPreset Pod affinity preset. Ignored if `affinity` is set. Allowed values: `soft` or `hard`
## ref: https://kubernetes.io/docs/concepts/scheduling-eviction/assign-pod-node/#inter-pod-affinity-and-anti-affinity
##
podAffinityPreset: ""
## @param podAntiAffinityPreset Pod anti-affinity preset. Ignored if `affinity` is set. Allowed values: `soft` or `hard`
## Ref: https://kubernetes.io/docs/concepts/scheduling-eviction/assign-pod-node/#inter-pod-affinity-and-anti-affinity
##
podAntiAffinityPreset: soft
## Node affinity preset
## Ref: https://kubernetes.io/docs/concepts/scheduling-eviction/assign-pod-node/#node-affinity
##
nodeAffinityPreset:
## @param nodeAffinityPreset.type Node affinity preset type. Ignored if `affinity` is set. Allowed values: `soft` or `hard`
##
type: ""
## @param nodeAffinityPreset.key Node label key to match. Ignored if `affinity` is set.
## E.g.
## key: "kubernetes.io/e2e-az-name"
##
key: ""
## @param nodeAffinityPreset.values Node label values to match. Ignored if `affinity` is set.
## E.g.
## values:
## - e2e-az1
## - e2e-az2
##
values: []
## @param priorityClassName Priority class for pod scheduling
## ref: https://kubernetes.io/docs/concepts/configuration/pod-priority-preemption/#priorityclass
priorityClassName: ""
## Pod Disruption Budget configuration
## ref: https://kubernetes.io/docs/tasks/run-application/configure-pdb/
## @param podDisruptionBudget.create Enable a Pod Disruption Budget creation
## @param podDisruptionBudget.minAvailable Minimum number/percentage of pods that should remain scheduled
## @param podDisruptionBudget.maxUnavailable Maximum number/percentage of pods that may be made unavailable
##
podDisruptionBudget:
create: false
minAvailable: ""
maxUnavailable: 1
## Controller container resource requests and limits
## ref: https://kubernetes.io/docs/user-guide/compute-resources/
## We usually recommend not to specify default resources and to leave this as a conscious
## choice for the user. This also increases chances charts run on environments with little
## resources, such as Minikube. If you do want to specify resources, uncomment the following
## lines, adjust them as necessary, and remove the curly braces after 'resources:'.
## @param resources.limits The resources limits for the container
## @param resources.requests The requested resources for the container
##
resources:
## Example:
## limits:
## cpu: 100m
## memory: 128Mi
##
limits: {}
## Examples:
## requests:
## cpu: 100m
## memory: 128Mi
##
requests: {}
## @param extraVolumes An array of extra volumes to add to the controller.
extraVolumes: []
## @param extraVolumeMounts An array of extra volume mounts to add to the controller.
extraVolumeMounts: []
##
## Example:
##
## extraVolumes:
## - name: test-volume
## emptyDir: {}
## extraVolumeMounts:
## - name: test-volume
## mountPath: /test-volume
## @param extraEnv an object of extra environment variables to add to the controller.
extraEnv: {}
## Example:
## MY_VAR: test
## MY_SECRET_VAR:
## secretKeyRef:
## key: test-key
## value: test-value
## Controller Service Account Settings
## @param serviceAccount.create Specifies whether a ServiceAccount should be created
## @param serviceAccount.name The name of the ServiceAccount to use.
## If not set and create is true, a name is generated using the fullname template
## @param serviceAccount.annotations Additional annotations to add to the ServiceAccount
##
serviceAccount:
create: true
name: ""
annotations: {}
## Logging configuration
## @param log.level The level to log at. One of 'debug', 'info', or 'error'.
## @param log.stacktraceLevel The level to report stacktrace logs one of 'info' or 'error'.
## @param log.format The log format to use. One of console, json.
log:
format: json
level: info
stacktraceLevel: error
## @param lifecycle an object containing lifecycle configuration
## ref: https://kubernetes.io/docs/concepts/containers/container-lifecycle-hooks/
##
lifecycle: {}

View File

@ -0,0 +1,7 @@
fullnameOverride: ngrok
credentials:
secret:
name: ngrok
serviceAccount:
create: true
name: ngrok

View File

@ -0,0 +1,25 @@
# 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
*~
# Various IDEs
.project
.idea/
*.tmproj
# img folder
img/
# Changelog
CHANGELOG.md

View File

@ -0,0 +1,6 @@
dependencies:
- name: common
repository: oci://registry-1.docker.io/bitnamicharts
version: 2.22.0
digest: sha256:a8fb2fc887ead658a89598a48acde5324196fbc0509503a3eaed50a710fbfe74
generated: "2024-08-09T13:57:12.563276536Z"

View File

@ -0,0 +1,38 @@
annotations:
category: Database
images: |
- name: kubectl
image: docker.io/bitnami/kubectl:1.30.3-debian-12-r5
- name: os-shell
image: docker.io/bitnami/os-shell:12-debian-12-r27
- name: redis
image: docker.io/bitnami/redis:7.4.0-debian-12-r0
- name: redis-exporter
image: docker.io/bitnami/redis-exporter:1.62.0-debian-12-r3
- name: redis-sentinel
image: docker.io/bitnami/redis-sentinel:7.4.0-debian-12-r0
licenses: Apache-2.0
apiVersion: v2
appVersion: 7.4.0
dependencies:
- name: common
repository: oci://registry-1.docker.io/bitnamicharts
tags:
- bitnami-common
version: 2.x.x
description: Redis(R) is an open source, advanced key-value store. It is often referred
to as a data structure server since keys can contain strings, hashes, lists, sets
and sorted sets.
home: https://bitnami.com
icon: https://bitnami.com/assets/stacks/redis/img/redis-stack-220x234.png
keywords:
- redis
- keyvalue
- database
maintainers:
- name: Broadcom, Inc. All Rights Reserved.
url: https://github.com/bitnami/charts
name: redis
sources:
- https://github.com/bitnami/charts/tree/main/bitnami/redis
version: 20.0.1

1280
charts/redis/redis/README.md Normal file

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,213 @@
CHART NAME: {{ .Chart.Name }}
CHART VERSION: {{ .Chart.Version }}
APP VERSION: {{ .Chart.AppVersion }}
** Please be patient while the chart is being deployed **
{{- if .Values.diagnosticMode.enabled }}
The chart has been deployed in diagnostic mode. All probes have been disabled and the command has been overwritten with:
command: {{- include "common.tplvalues.render" (dict "value" .Values.diagnosticMode.command "context" $) | nindent 4 }}
args: {{- include "common.tplvalues.render" (dict "value" .Values.diagnosticMode.args "context" $) | nindent 4 }}
Get the list of pods by executing:
kubectl get pods --namespace {{ include "common.names.namespace" . }} -l app.kubernetes.io/instance={{ .Release.Name }}
Access the pod you want to debug by executing
kubectl exec --namespace {{ include "common.names.namespace" . }} -ti <NAME OF THE POD> -- bash
In order to replicate the container startup scripts execute this command:
For Redis:
/opt/bitnami/scripts/redis/entrypoint.sh /opt/bitnami/scripts/redis/run.sh
{{- if .Values.sentinel.enabled }}
For Redis Sentinel:
/opt/bitnami/scripts/redis-sentinel/entrypoint.sh /opt/bitnami/scripts/redis-sentinel/run.sh
{{- end }}
{{- else }}
{{- if contains .Values.master.service.type "LoadBalancer" }}
{{- if not .Values.auth.enabled }}
{{ if and (not .Values.networkPolicy.enabled) (.Values.networkPolicy.allowExternal) }}
-------------------------------------------------------------------------------
WARNING
By specifying "master.service.type=LoadBalancer" and "auth.enabled=false" you have
most likely exposed the Redis&reg; service externally without any authentication
mechanism.
For security reasons, we strongly suggest that you switch to "ClusterIP" or
"NodePort". As alternative, you can also switch to "auth.enabled=true"
providing a valid password on "password" parameter.
-------------------------------------------------------------------------------
{{- end }}
{{- end }}
{{- end }}
{{- if and .Values.auth.usePasswordFiles (not .Values.auth.usePasswordFileFromSecret) (or (empty .Values.master.initContainers) (empty .Values.replica.initContainers)) }}
-------------------------------------------------------------------------------
WARNING
By specifying ".Values.auth.usePasswordFiles=true" and ".Values.auth.usePasswordFileFromSecret=false"
Redis is expecting that the password is mounted as a file in each pod
(by default in /opt/bitnami/redis/secrets/redis-password)
Ensure that you specify the respective initContainers in
both .Values.master.initContainers and .Values.replica.initContainers
in order to populate the contents of this file.
-------------------------------------------------------------------------------
{{- end }}
{{- if eq .Values.architecture "replication" }}
{{- if .Values.sentinel.enabled }}
Redis&reg; can be accessed via port {{ .Values.sentinel.service.ports.redis }} on the following DNS name from within your cluster:
{{ template "common.names.fullname" . }}.{{ include "common.names.namespace" . }}.svc.{{ .Values.clusterDomain }} for read only operations
For read/write operations, first access the Redis&reg; Sentinel cluster, which is available in port {{ .Values.sentinel.service.ports.sentinel }} using the same domain name above.
{{- else }}
Redis&reg; can be accessed on the following DNS names from within your cluster:
{{ printf "%s-master.%s.svc.%s" (include "common.names.fullname" .) (include "common.names.namespace" . ) .Values.clusterDomain }} for read/write operations (port {{ .Values.master.service.ports.redis }})
{{ printf "%s-replicas.%s.svc.%s" (include "common.names.fullname" .) (include "common.names.namespace" . ) .Values.clusterDomain }} for read-only operations (port {{ .Values.replica.service.ports.redis }})
{{- end }}
{{- else }}
Redis&reg; can be accessed via port {{ .Values.master.service.ports.redis }} on the following DNS name from within your cluster:
{{ template "common.names.fullname" . }}-master.{{ include "common.names.namespace" . }}.svc.{{ .Values.clusterDomain }}
{{- end }}
{{ if .Values.auth.enabled }}
To get your password run:
export REDIS_PASSWORD=$(kubectl get secret --namespace {{ include "common.names.namespace" . }} {{ template "redis.secretName" . }} -o jsonpath="{.data.redis-password}" | base64 -d)
{{- end }}
To connect to your Redis&reg; server:
1. Run a Redis&reg; pod that you can use as a client:
kubectl run --namespace {{ include "common.names.namespace" . }} redis-client --restart='Never' {{ if .Values.auth.enabled }} --env REDIS_PASSWORD=$REDIS_PASSWORD {{ end }} --image {{ template "redis.image" . }} --command -- sleep infinity
{{- if .Values.tls.enabled }}
Copy your TLS certificates to the pod:
kubectl cp --namespace {{ include "common.names.namespace" . }} /path/to/client.cert redis-client:/tmp/client.cert
kubectl cp --namespace {{ include "common.names.namespace" . }} /path/to/client.key redis-client:/tmp/client.key
kubectl cp --namespace {{ include "common.names.namespace" . }} /path/to/CA.cert redis-client:/tmp/CA.cert
{{- end }}
Use the following command to attach to the pod:
kubectl exec --tty -i redis-client \
{{- if and (.Values.networkPolicy.enabled) (not .Values.networkPolicy.allowExternal) }}--labels="{{ template "common.names.fullname" . }}-client=true" \{{- end }}
--namespace {{ include "common.names.namespace" . }} -- bash
2. Connect using the Redis&reg; CLI:
{{- if eq .Values.architecture "replication" }}
{{- if .Values.sentinel.enabled }}
{{ if .Values.auth.enabled }}REDISCLI_AUTH="$REDIS_PASSWORD" {{ end }}redis-cli -h {{ template "common.names.fullname" . }} -p {{ .Values.sentinel.service.ports.redis }}{{ if .Values.tls.enabled }} --tls --cert /tmp/client.cert --key /tmp/client.key --cacert /tmp/CA.cert{{ end }} # Read only operations
{{ if .Values.auth.enabled }}REDISCLI_AUTH="$REDIS_PASSWORD" {{ end }}redis-cli -h {{ template "common.names.fullname" . }} -p {{ .Values.sentinel.service.ports.sentinel }}{{ if .Values.tls.enabled }} --tls --cert /tmp/client.cert --key /tmp/client.key --cacert /tmp/CA.cert{{ end }} # Sentinel access
{{- else }}
{{ if .Values.auth.enabled }}REDISCLI_AUTH="$REDIS_PASSWORD" {{ end }}redis-cli -h {{ printf "%s-master" (include "common.names.fullname" .) }}{{ if .Values.tls.enabled }} --tls --cert /tmp/client.cert --key /tmp/client.key --cacert /tmp/CA.cert{{ end }}
{{ if .Values.auth.enabled }}REDISCLI_AUTH="$REDIS_PASSWORD" {{ end }}redis-cli -h {{ printf "%s-replicas" (include "common.names.fullname" .) }}{{ if .Values.tls.enabled }} --tls --cert /tmp/client.cert --key /tmp/client.key --cacert /tmp/CA.cert{{ end }}
{{- end }}
{{- else }}
{{ if .Values.auth.enabled }}REDISCLI_AUTH="$REDIS_PASSWORD" {{ end }}redis-cli -h {{ template "common.names.fullname" . }}-master{{ if .Values.tls.enabled }} --tls --cert /tmp/client.cert --key /tmp/client.key --cacert /tmp/CA.cert{{ end }}
{{- end }}
{{- if and (.Values.networkPolicy.enabled) (not .Values.networkPolicy.allowExternal) }}
Note: Since NetworkPolicy is enabled, only pods with label {{ template "common.names.fullname" . }}-client=true" will be able to connect to redis.
{{- else }}
To connect to your database from outside the cluster execute the following commands:
{{- if and (eq .Values.architecture "replication") .Values.sentinel.enabled }}
{{- if contains "NodePort" .Values.sentinel.service.type }}
export NODE_IP=$(kubectl get nodes --namespace {{ include "common.names.namespace" . }} -o jsonpath="{.items[0].status.addresses[0].address}")
export NODE_PORT=$(kubectl get --namespace {{ include "common.names.namespace" . }} -o jsonpath="{.spec.ports[0].nodePort}" services {{ template "common.names.fullname" . }})
{{ if .Values.auth.enabled }}REDISCLI_AUTH="$REDIS_PASSWORD" {{ end }}redis-cli -h $NODE_IP -p $NODE_PORT {{- if .Values.tls.enabled }} --tls --cert /tmp/client.cert --key /tmp/client.key --cacert /tmp/CA.cert{{ end }}
{{- else if contains "LoadBalancer" .Values.sentinel.service.type }}
NOTE: It may take a few minutes for the LoadBalancer IP to be available.
Watch the status with: 'kubectl get svc --namespace {{ include "common.names.namespace" . }} -w {{ template "common.names.fullname" . }}'
export SERVICE_IP=$(kubectl get svc --namespace {{ include "common.names.namespace" . }} {{ template "common.names.fullname" . }} --template "{{ "{{ range (index .status.loadBalancer.ingress 0) }}{{ . }}{{ end }}" }}")
{{ if .Values.auth.enabled }}REDISCLI_AUTH="$REDIS_PASSWORD" {{ end }}redis-cli -h $SERVICE_IP -p {{ .Values.sentinel.service.ports.redis }} {{- if .Values.tls.enabled }} --tls --cert /tmp/client.cert --key /tmp/client.key --cacert /tmp/CA.cert{{ end }}
{{- else if contains "ClusterIP" .Values.sentinel.service.type }}
kubectl port-forward --namespace {{ include "common.names.namespace" . }} svc/{{ template "common.names.fullname" . }} {{ .Values.sentinel.service.ports.redis }}:{{ .Values.sentinel.service.ports.redis }} &
{{ if .Values.auth.enabled }}REDISCLI_AUTH="$REDIS_PASSWORD" {{ end }}redis-cli -h 127.0.0.1 -p {{ .Values.sentinel.service.ports.redis }} {{- if .Values.tls.enabled }} --tls --cert /tmp/client.cert --key /tmp/client.key --cacert /tmp/CA.cert{{ end }}
{{- end }}
{{- else }}
{{- if contains "NodePort" .Values.master.service.type }}
export NODE_IP=$(kubectl get nodes --namespace {{ include "common.names.namespace" . }} -o jsonpath="{.items[0].status.addresses[0].address}")
export NODE_PORT=$(kubectl get --namespace {{ include "common.names.namespace" . }} -o jsonpath="{.spec.ports[0].nodePort}" services {{ printf "%s-master" (include "common.names.fullname" .) }})
{{ if .Values.auth.enabled }}REDISCLI_AUTH="$REDIS_PASSWORD" {{ end }}redis-cli -h $NODE_IP -p $NODE_PORT {{- if .Values.tls.enabled }} --tls --cert /tmp/client.cert --key /tmp/client.key --cacert /tmp/CA.cert{{ end }}
{{- else if contains "LoadBalancer" .Values.master.service.type }}
NOTE: It may take a few minutes for the LoadBalancer IP to be available.
Watch the status with: 'kubectl get svc --namespace {{ include "common.names.namespace" . }} -w {{ template "common.names.fullname" . }}'
export SERVICE_IP=$(kubectl get svc --namespace {{ include "common.names.namespace" . }} {{ printf "%s-master" (include "common.names.fullname" .) }} --template "{{ "{{ range (index .status.loadBalancer.ingress 0) }}{{ . }}{{ end }}" }}")
{{ if .Values.auth.enabled }}REDISCLI_AUTH="$REDIS_PASSWORD" {{ end }}redis-cli -h $SERVICE_IP -p {{ .Values.master.service.ports.redis }} {{- if .Values.tls.enabled }} --tls --cert /tmp/client.cert --key /tmp/client.key --cacert /tmp/CA.cert{{ end }}
{{- else if contains "ClusterIP" .Values.master.service.type }}
kubectl port-forward --namespace {{ include "common.names.namespace" . }} svc/{{ printf "%s-master" (include "common.names.fullname" .) }} {{ .Values.master.service.ports.redis }}:{{ .Values.master.service.ports.redis }} &
{{ if .Values.auth.enabled }}REDISCLI_AUTH="$REDIS_PASSWORD" {{ end }}redis-cli -h 127.0.0.1 -p {{ .Values.master.service.ports.redis }} {{- if .Values.tls.enabled }} --tls --cert /tmp/client.cert --key /tmp/client.key --cacert /tmp/CA.cert{{ end }}
{{- end }}
{{- end }}
{{- end }}
{{- end }}
{{- include "redis.checkRollingTags" . }}
{{- include "common.warnings.rollingTag" .Values.volumePermissions.image }}
{{- include "common.warnings.rollingTag" .Values.sysctl.image }}
{{- include "redis.validateValues" . }}
{{- if and (eq .Values.architecture "replication") .Values.sentinel.enabled (eq .Values.sentinel.service.type "NodePort") (not .Release.IsUpgrade ) }}
{{- if $.Values.sentinel.service.nodePorts.sentinel }}
No need to upgrade, ports and nodeports have been set from values
{{- else }}
#!#!#!#!#!#!#!# IMPORTANT #!#!#!#!#!#!#!#
YOU NEED TO PERFORM AN UPGRADE FOR THE SERVICES AND WORKLOAD TO BE CREATED
{{- end }}
{{- end }}
{{- $resourceSections := list "metrics" "replica" "sentinel" "sysctl" "volumePermissions" }}
{{- if not (and (eq .Values.architecture "replication") .Values.sentinel.enabled) }}
{{- $resourceSections = append $resourceSections "master" -}}
{{- end }}
{{- include "common.warnings.resources" (dict "sections" $resourceSections "context" $) }}
{{- include "common.warnings.modifiedImages" (dict "images" (list .Values.image .Values.sentinel.image .Values.metrics.image .Values.volumePermissions.image .Values.kubectl.image .Values.sysctl.image) "context" $) }}

View File

@ -0,0 +1,346 @@
{{/*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{/* vim: set filetype=mustache: */}}
{{/*
Return the proper Redis image name
*/}}
{{- define "redis.image" -}}
{{ include "common.images.image" (dict "imageRoot" .Values.image "global" .Values.global) }}
{{- end -}}
{{/*
Return the proper Redis Sentinel image name
*/}}
{{- define "redis.sentinel.image" -}}
{{ include "common.images.image" (dict "imageRoot" .Values.sentinel.image "global" .Values.global) }}
{{- end -}}
{{/*
Return the proper image name (for the metrics image)
*/}}
{{- define "redis.metrics.image" -}}
{{ include "common.images.image" (dict "imageRoot" .Values.metrics.image "global" .Values.global) }}
{{- end -}}
{{/*
Return the proper image name (for the init container volume-permissions image)
*/}}
{{- define "redis.volumePermissions.image" -}}
{{ include "common.images.image" (dict "imageRoot" .Values.volumePermissions.image "global" .Values.global) }}
{{- end -}}
{{/*
Return kubectl image
*/}}
{{- define "redis.kubectl.image" -}}
{{ include "common.images.image" (dict "imageRoot" .Values.kubectl.image "global" .Values.global) }}
{{- end -}}
{{/*
Return sysctl image
*/}}
{{- define "redis.sysctl.image" -}}
{{ include "common.images.image" (dict "imageRoot" .Values.sysctl.image "global" .Values.global) }}
{{- end -}}
{{/*
Return the proper Docker Image Registry Secret Names
*/}}
{{- define "redis.imagePullSecrets" -}}
{{- include "common.images.renderPullSecrets" (dict "images" (list .Values.image .Values.sentinel.image .Values.metrics.image .Values.volumePermissions.image .Values.sysctl.image) "context" $) -}}
{{- end -}}
{{/*
Return the appropriate apiVersion for networkpolicy.
*/}}
{{- define "networkPolicy.apiVersion" -}}
{{- if semverCompare ">=1.4-0, <1.7-0" .Capabilities.KubeVersion.GitVersion -}}
{{- print "extensions/v1beta1" -}}
{{- else -}}
{{- print "networking.k8s.io/v1" -}}
{{- end -}}
{{- end -}}
{{/*
Return the appropriate apiGroup for PodSecurityPolicy.
*/}}
{{- define "podSecurityPolicy.apiGroup" -}}
{{- if semverCompare ">=1.14-0" .Capabilities.KubeVersion.GitVersion -}}
{{- print "policy" -}}
{{- else -}}
{{- print "extensions" -}}
{{- end -}}
{{- end -}}
{{/*
Return true if a TLS secret object should be created
*/}}
{{- define "redis.createTlsSecret" -}}
{{- if and .Values.tls.enabled .Values.tls.autoGenerated (and (not .Values.tls.existingSecret) (not .Values.tls.certificatesSecret)) }}
{{- true -}}
{{- end -}}
{{- end -}}
{{/*
Return the secret containing Redis TLS certificates
*/}}
{{- define "redis.tlsSecretName" -}}
{{- $secretName := coalesce .Values.tls.existingSecret .Values.tls.certificatesSecret -}}
{{- if $secretName -}}
{{- printf "%s" (tpl $secretName $) -}}
{{- else -}}
{{- printf "%s-crt" (include "common.names.fullname" .) -}}
{{- end -}}
{{- end -}}
{{/*
Return the path to the cert file.
*/}}
{{- define "redis.tlsCert" -}}
{{- if (include "redis.createTlsSecret" . ) -}}
{{- printf "/opt/bitnami/redis/certs/%s" "tls.crt" -}}
{{- else -}}
{{- required "Certificate filename is required when TLS in enabled" .Values.tls.certFilename | printf "/opt/bitnami/redis/certs/%s" -}}
{{- end -}}
{{- end -}}
{{/*
Return the path to the cert key file.
*/}}
{{- define "redis.tlsCertKey" -}}
{{- if (include "redis.createTlsSecret" . ) -}}
{{- printf "/opt/bitnami/redis/certs/%s" "tls.key" -}}
{{- else -}}
{{- required "Certificate Key filename is required when TLS in enabled" .Values.tls.certKeyFilename | printf "/opt/bitnami/redis/certs/%s" -}}
{{- end -}}
{{- end -}}
{{/*
Return the path to the CA cert file.
*/}}
{{- define "redis.tlsCACert" -}}
{{- if (include "redis.createTlsSecret" . ) -}}
{{- printf "/opt/bitnami/redis/certs/%s" "ca.crt" -}}
{{- else -}}
{{- required "Certificate CA filename is required when TLS in enabled" .Values.tls.certCAFilename | printf "/opt/bitnami/redis/certs/%s" -}}
{{- end -}}
{{- end -}}
{{/*
Return the path to the DH params file.
*/}}
{{- define "redis.tlsDHParams" -}}
{{- if .Values.tls.dhParamsFilename -}}
{{- printf "/opt/bitnami/redis/certs/%s" .Values.tls.dhParamsFilename -}}
{{- end -}}
{{- end -}}
{{/*
Create the name of the shared service account to use
*/}}
{{- define "redis.serviceAccountName" -}}
{{- if .Values.serviceAccount.create -}}
{{ default (include "common.names.fullname" .) .Values.serviceAccount.name }}
{{- else -}}
{{ default "default" .Values.serviceAccount.name }}
{{- end -}}
{{- end -}}
{{/*
Create the name of the master service account to use
*/}}
{{- define "redis.masterServiceAccountName" -}}
{{- if .Values.master.serviceAccount.create -}}
{{ default (printf "%s-master" (include "common.names.fullname" .)) .Values.master.serviceAccount.name }}
{{- else -}}
{{- if .Values.serviceAccount.create -}}
{{ template "redis.serviceAccountName" . }}
{{- else -}}
{{ default "default" .Values.master.serviceAccount.name }}
{{- end -}}
{{- end -}}
{{- end -}}
{{/*
Create the name of the replicas service account to use
*/}}
{{- define "redis.replicaServiceAccountName" -}}
{{- if .Values.replica.serviceAccount.create -}}
{{ default (printf "%s-replica" (include "common.names.fullname" .)) .Values.replica.serviceAccount.name }}
{{- else -}}
{{- if .Values.serviceAccount.create -}}
{{ template "redis.serviceAccountName" . }}
{{- else -}}
{{ default "default" .Values.replica.serviceAccount.name }}
{{- end -}}
{{- end -}}
{{- end -}}
{{/*
Return the configuration configmap name
*/}}
{{- define "redis.configmapName" -}}
{{- if .Values.existingConfigmap -}}
{{- printf "%s" (tpl .Values.existingConfigmap $) -}}
{{- else -}}
{{- printf "%s-configuration" (include "common.names.fullname" .) -}}
{{- end -}}
{{- end -}}
{{/*
Return true if a configmap object should be created
*/}}
{{- define "redis.createConfigmap" -}}
{{- if empty .Values.existingConfigmap }}
{{- true -}}
{{- end -}}
{{- end -}}
{{/*
Get the password secret.
*/}}
{{- define "redis.secretName" -}}
{{- if .Values.auth.existingSecret -}}
{{- printf "%s" (tpl .Values.auth.existingSecret $) -}}
{{- else -}}
{{- printf "%s" (include "common.names.fullname" .) -}}
{{- end -}}
{{- end -}}
{{/*
Get the password key to be retrieved from Redis&reg; secret.
*/}}
{{- define "redis.secretPasswordKey" -}}
{{- if and .Values.auth.existingSecret .Values.auth.existingSecretPasswordKey -}}
{{- printf "%s" (tpl .Values.auth.existingSecretPasswordKey $) -}}
{{- else -}}
{{- printf "redis-password" -}}
{{- end -}}
{{- end -}}
{{/*
Returns the available value for certain key in an existing secret (if it exists),
otherwise it generates a random value.
*/}}
{{- define "getValueFromSecret" }}
{{- $len := (default 16 .Length) | int -}}
{{- $obj := (lookup "v1" "Secret" .Namespace .Name).data -}}
{{- if $obj }}
{{- index $obj .Key | b64dec -}}
{{- else -}}
{{- randAlphaNum $len -}}
{{- end -}}
{{- end }}
{{/*
Return Redis&reg; password
*/}}
{{- define "redis.password" -}}
{{- if or .Values.auth.enabled .Values.global.redis.password }}
{{- if not (empty .Values.global.redis.password) }}
{{- .Values.global.redis.password -}}
{{- else if not (empty .Values.auth.password) -}}
{{- .Values.auth.password -}}
{{- else -}}
{{- include "getValueFromSecret" (dict "Namespace" (include "common.names.namespace" .) "Name" (include "redis.secretName" .) "Length" 10 "Key" (include "redis.secretPasswordKey" .)) -}}
{{- end -}}
{{- end -}}
{{- end }}
{{/* Check if there are rolling tags in the images */}}
{{- define "redis.checkRollingTags" -}}
{{- include "common.warnings.rollingTag" .Values.image }}
{{- include "common.warnings.rollingTag" .Values.sentinel.image }}
{{- include "common.warnings.rollingTag" .Values.metrics.image }}
{{- end -}}
{{/*
Compile all warnings into a single message, and call fail.
*/}}
{{- define "redis.validateValues" -}}
{{- $messages := list -}}
{{- $messages := append $messages (include "redis.validateValues.topologySpreadConstraints" .) -}}
{{- $messages := append $messages (include "redis.validateValues.architecture" .) -}}
{{- $messages := append $messages (include "redis.validateValues.podSecurityPolicy.create" .) -}}
{{- $messages := append $messages (include "redis.validateValues.tls" .) -}}
{{- $messages := append $messages (include "redis.validateValues.createMaster" .) -}}
{{- $messages := without $messages "" -}}
{{- $message := join "\n" $messages -}}
{{- if $message -}}
{{- printf "\nVALUES VALIDATION:\n%s" $message | fail -}}
{{- end -}}
{{- end -}}
{{/* Validate values of Redis&reg; - spreadConstrainsts K8s version */}}
{{- define "redis.validateValues.topologySpreadConstraints" -}}
{{- if and (semverCompare "<1.16-0" .Capabilities.KubeVersion.GitVersion) .Values.replica.topologySpreadConstraints -}}
redis: topologySpreadConstraints
Pod Topology Spread Constraints are only available on K8s >= 1.16
Find more information at https://kubernetes.io/docs/concepts/workloads/pods/pod-topology-spread-constraints/
{{- end -}}
{{- end -}}
{{/* Validate values of Redis&reg; - must provide a valid architecture */}}
{{- define "redis.validateValues.architecture" -}}
{{- if and (ne .Values.architecture "standalone") (ne .Values.architecture "replication") -}}
redis: architecture
Invalid architecture selected. Valid values are "standalone" and
"replication". Please set a valid architecture (--set architecture="xxxx")
{{- end -}}
{{- if and .Values.sentinel.enabled (not (eq .Values.architecture "replication")) }}
redis: architecture
Using redis sentinel on standalone mode is not supported.
To deploy redis sentinel, please select the "replication" mode
(--set "architecture=replication,sentinel.enabled=true")
{{- end -}}
{{- end -}}
{{/* Validate values of Redis&reg; - PodSecurityPolicy create */}}
{{- define "redis.validateValues.podSecurityPolicy.create" -}}
{{- if and .Values.podSecurityPolicy.create (not .Values.podSecurityPolicy.enabled) }}
redis: podSecurityPolicy.create
In order to create PodSecurityPolicy, you also need to enable
podSecurityPolicy.enabled field
{{- end -}}
{{- end -}}
{{/* Validate values of Redis&reg; - TLS enabled */}}
{{- define "redis.validateValues.tls" -}}
{{- if and .Values.tls.enabled (not .Values.tls.autoGenerated) (not .Values.tls.existingSecret) (not .Values.tls.certificatesSecret) }}
redis: tls.enabled
In order to enable TLS, you also need to provide
an existing secret containing the TLS certificates or
enable auto-generated certificates.
{{- end -}}
{{- end -}}
{{/* Validate values of Redis&reg; - master service enabled */}}
{{- define "redis.validateValues.createMaster" -}}
{{- if and (or .Values.sentinel.masterService.enabled .Values.sentinel.service.createMaster) (or (not .Values.rbac.create) (not .Values.replica.automountServiceAccountToken) (not .Values.serviceAccount.create)) }}
redis: sentinel.masterService.enabled
In order to redirect requests only to the master pod via the service, you also need to
create rbac and serviceAccount. In addition, you need to enable
replica.automountServiceAccountToken.
{{- end -}}
{{- end -}}
{{/* Define the suffix utilized for external-dns */}}
{{- define "redis.externalDNS.suffix" -}}
{{ printf "%s.%s" (include "common.names.fullname" .) .Values.useExternalDNS.suffix }}
{{- end -}}
{{/* Compile all annotations utilized for external-dns */}}
{{- define "redis.externalDNS.annotations" -}}
{{- if and .Values.useExternalDNS.enabled .Values.useExternalDNS.annotationKey }}
{{ .Values.useExternalDNS.annotationKey }}hostname: {{ include "redis.externalDNS.suffix" . }}
{{- range $key, $val := .Values.useExternalDNS.additionalAnnotations }}
{{ $.Values.useExternalDNS.annotationKey }}{{ $key }}: {{ $val | quote }}
{{- end }}
{{- end }}
{{- end }}

View File

@ -0,0 +1,64 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if (include "redis.createConfigmap" .) }}
apiVersion: v1
kind: ConfigMap
metadata:
name: {{ printf "%s-configuration" (include "common.names.fullname" .) }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- if .Values.commonAnnotations }}
annotations: {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
data:
redis.conf: |-
# User-supplied common configuration:
{{- if .Values.commonConfiguration }}
{{- include "common.tplvalues.render" ( dict "value" .Values.commonConfiguration "context" $ ) | nindent 4 }}
{{- end }}
# End of common configuration
master.conf: |-
dir {{ .Values.master.persistence.path }}
# User-supplied master configuration:
{{- if .Values.master.configuration }}
{{- include "common.tplvalues.render" ( dict "value" .Values.master.configuration "context" $ ) | nindent 4 }}
{{- end }}
{{- if .Values.master.disableCommands }}
{{- range .Values.master.disableCommands }}
rename-command {{ . }} ""
{{- end }}
{{- end }}
# End of master configuration
replica.conf: |-
dir {{ .Values.replica.persistence.path }}
# User-supplied replica configuration:
{{- if .Values.replica.configuration }}
{{- include "common.tplvalues.render" ( dict "value" .Values.replica.configuration "context" $ ) | nindent 4 }}
{{- end }}
{{- if .Values.replica.disableCommands }}
{{- range .Values.replica.disableCommands }}
rename-command {{ . }} ""
{{- end }}
{{- end }}
# End of replica configuration
{{- if .Values.sentinel.enabled }}
sentinel.conf: |-
dir "/tmp"
port {{ .Values.sentinel.containerPorts.sentinel }}
sentinel monitor {{ .Values.sentinel.masterSet }} {{ template "common.names.fullname" . }}-node-0.{{ template "common.names.fullname" . }}-headless.{{ include "common.names.namespace" . }}.svc.{{ .Values.clusterDomain }} {{ .Values.sentinel.service.ports.redis }} {{ .Values.sentinel.quorum }}
sentinel down-after-milliseconds {{ .Values.sentinel.masterSet }} {{ .Values.sentinel.downAfterMilliseconds }}
sentinel failover-timeout {{ .Values.sentinel.masterSet }} {{ .Values.sentinel.failoverTimeout }}
sentinel parallel-syncs {{ .Values.sentinel.masterSet }} {{ .Values.sentinel.parallelSyncs }}
{{- if or .Values.sentinel.masterService.enabled .Values.sentinel.service.createMaster }}
sentinel client-reconfig-script {{ .Values.sentinel.masterSet }} /opt/bitnami/scripts/start-scripts/push-master-label.sh
{{- end }}
# User-supplied sentinel configuration:
{{- if .Values.sentinel.configuration }}
{{- include "common.tplvalues.render" ( dict "value" .Values.sentinel.configuration "context" $ ) | nindent 4 }}
{{- end }}
# End of sentinel configuration
{{- end }}
{{- end }}

View File

@ -0,0 +1,9 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- range .Values.extraDeploy }}
---
{{ include "common.tplvalues.render" (dict "value" . "context" $) }}
{{- end }}

View File

@ -0,0 +1,35 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
apiVersion: v1
kind: Service
metadata:
name: {{ printf "%s-headless" (include "common.names.fullname" .) }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- if or .Values.sentinel.service.headless.annotations .Values.commonAnnotations (include "redis.externalDNS.annotations" .) }}
annotations:
{{- if or .Values.sentinel.service.headless.annotations .Values.commonAnnotations }}
{{- $annotations := include "common.tplvalues.merge" ( dict "values" ( list .Values.sentinel.service.headless.annotations .Values.commonAnnotations ) "context" . ) }}
{{- include "common.tplvalues.render" ( dict "value" $annotations "context" $) | nindent 4 }}
{{- end }}
{{- include "redis.externalDNS.annotations" . | nindent 4 }}
{{- end }}
spec:
type: ClusterIP
clusterIP: None
{{- if .Values.sentinel.enabled }}
publishNotReadyAddresses: true
{{- end }}
ports:
- name: tcp-redis
port: {{ if .Values.sentinel.enabled }}{{ .Values.sentinel.service.ports.redis }}{{ else }}{{ .Values.master.service.ports.redis }}{{ end }}
targetPort: redis
{{- if .Values.sentinel.enabled }}
- name: tcp-sentinel
port: {{ .Values.sentinel.service.ports.sentinel }}
targetPort: redis-sentinel
{{- end }}
selector: {{- include "common.labels.matchLabels" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}

View File

@ -0,0 +1,194 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
apiVersion: v1
kind: ConfigMap
metadata:
name: {{ printf "%s-health" (include "common.names.fullname" .) }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- if .Values.commonAnnotations }}
annotations: {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
data:
ping_readiness_local.sh: |-
#!/bin/bash
[[ -f $REDIS_PASSWORD_FILE ]] && export REDIS_PASSWORD="$(< "${REDIS_PASSWORD_FILE}")"
[[ -n "$REDIS_PASSWORD" ]] && export REDISCLI_AUTH="$REDIS_PASSWORD"
response=$(
timeout -s 15 $1 \
redis-cli \
-h localhost \
{{- if .Values.tls.enabled }}
-p $REDIS_TLS_PORT \
--tls \
--cacert {{ template "redis.tlsCACert" . }} \
{{- if .Values.tls.authClients }}
--cert {{ template "redis.tlsCert" . }} \
--key {{ template "redis.tlsCertKey" . }} \
{{- end }}
{{- else }}
-p $REDIS_PORT \
{{- end }}
ping
)
if [ "$?" -eq "124" ]; then
echo "Timed out"
exit 1
fi
if [ "$response" != "PONG" ]; then
echo "$response"
exit 1
fi
ping_liveness_local.sh: |-
#!/bin/bash
[[ -f $REDIS_PASSWORD_FILE ]] && export REDIS_PASSWORD="$(< "${REDIS_PASSWORD_FILE}")"
[[ -n "$REDIS_PASSWORD" ]] && export REDISCLI_AUTH="$REDIS_PASSWORD"
response=$(
timeout -s 15 $1 \
redis-cli \
-h localhost \
{{- if .Values.tls.enabled }}
-p $REDIS_TLS_PORT \
--tls \
--cacert {{ template "redis.tlsCACert" . }} \
{{- if .Values.tls.authClients }}
--cert {{ template "redis.tlsCert" . }} \
--key {{ template "redis.tlsCertKey" . }} \
{{- end }}
{{- else }}
-p $REDIS_PORT \
{{- end }}
ping
)
if [ "$?" -eq "124" ]; then
echo "Timed out"
exit 1
fi
responseFirstWord=$(echo $response | head -n1 | awk '{print $1;}')
if [ "$response" != "PONG" ] && [ "$responseFirstWord" != "LOADING" ] && [ "$responseFirstWord" != "MASTERDOWN" ]; then
echo "$response"
exit 1
fi
{{- if .Values.sentinel.enabled }}
ping_sentinel.sh: |-
#!/bin/bash
{{- if .Values.auth.sentinel }}
[[ -f $REDIS_PASSWORD_FILE ]] && export REDIS_PASSWORD="$(< "${REDIS_PASSWORD_FILE}")"
[[ -n "$REDIS_PASSWORD" ]] && export REDISCLI_AUTH="$REDIS_PASSWORD"
{{- end }}
response=$(
timeout -s 15 $1 \
redis-cli \
-h localhost \
{{- if .Values.tls.enabled }}
-p $REDIS_SENTINEL_TLS_PORT_NUMBER \
--tls \
--cacert "$REDIS_SENTINEL_TLS_CA_FILE" \
{{- if .Values.tls.authClients }}
--cert "$REDIS_SENTINEL_TLS_CERT_FILE" \
--key "$REDIS_SENTINEL_TLS_KEY_FILE" \
{{- end }}
{{- else }}
-p $REDIS_SENTINEL_PORT \
{{- end }}
ping
)
if [ "$?" -eq "124" ]; then
echo "Timed out"
exit 1
fi
if [ "$response" != "PONG" ]; then
echo "$response"
exit 1
fi
parse_sentinels.awk: |-
/ip/ {FOUND_IP=1}
/port/ {FOUND_PORT=1}
/runid/ {FOUND_RUNID=1}
!/ip|port|runid/ {
if (FOUND_IP==1) {
IP=$1; FOUND_IP=0;
}
else if (FOUND_PORT==1) {
PORT=$1;
FOUND_PORT=0;
} else if (FOUND_RUNID==1) {
printf "\nsentinel known-sentinel {{ .Values.sentinel.masterSet }} %s %s %s", IP, PORT, $0; FOUND_RUNID=0;
}
}
{{- end }}
ping_readiness_master.sh: |-
#!/bin/bash
[[ -f $REDIS_MASTER_PASSWORD_FILE ]] && export REDIS_MASTER_PASSWORD="$(< "${REDIS_MASTER_PASSWORD_FILE}")"
[[ -n "$REDIS_MASTER_PASSWORD" ]] && export REDISCLI_AUTH="$REDIS_MASTER_PASSWORD"
response=$(
timeout -s 15 $1 \
redis-cli \
-h $REDIS_MASTER_HOST \
-p $REDIS_MASTER_PORT_NUMBER \
{{- if .Values.tls.enabled }}
--tls \
--cacert {{ template "redis.tlsCACert" . }} \
{{- if .Values.tls.authClients }}
--cert {{ template "redis.tlsCert" . }} \
--key {{ template "redis.tlsCertKey" . }} \
{{- end }}
{{- end }}
ping
)
if [ "$?" -eq "124" ]; then
echo "Timed out"
exit 1
fi
if [ "$response" != "PONG" ]; then
echo "$response"
exit 1
fi
ping_liveness_master.sh: |-
#!/bin/bash
[[ -f $REDIS_MASTER_PASSWORD_FILE ]] && export REDIS_MASTER_PASSWORD="$(< "${REDIS_MASTER_PASSWORD_FILE}")"
[[ -n "$REDIS_MASTER_PASSWORD" ]] && export REDISCLI_AUTH="$REDIS_MASTER_PASSWORD"
response=$(
timeout -s 15 $1 \
redis-cli \
-h $REDIS_MASTER_HOST \
-p $REDIS_MASTER_PORT_NUMBER \
{{- if .Values.tls.enabled }}
--tls \
--cacert {{ template "redis.tlsCACert" . }} \
{{- if .Values.tls.authClients }}
--cert {{ template "redis.tlsCert" . }} \
--key {{ template "redis.tlsCertKey" . }} \
{{- end }}
{{- end }}
ping
)
if [ "$?" -eq "124" ]; then
echo "Timed out"
exit 1
fi
responseFirstWord=$(echo $response | head -n1 | awk '{print $1;}')
if [ "$response" != "PONG" ] && [ "$responseFirstWord" != "LOADING" ]; then
echo "$response"
exit 1
fi
ping_readiness_local_and_master.sh: |-
script_dir="$(dirname "$0")"
exit_status=0
"$script_dir/ping_readiness_local.sh" $1 || exit_status=$?
"$script_dir/ping_readiness_master.sh" $1 || exit_status=$?
exit $exit_status
ping_liveness_local_and_master.sh: |-
script_dir="$(dirname "$0")"
exit_status=0
"$script_dir/ping_liveness_local.sh" $1 || exit_status=$?
"$script_dir/ping_liveness_master.sh" $1 || exit_status=$?
exit $exit_status

View File

@ -0,0 +1,546 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if gt (int64 .Values.master.count) 0 -}}
{{- if or (not (eq .Values.architecture "replication")) (not .Values.sentinel.enabled) }}
apiVersion: {{ include "common.capabilities.statefulset.apiVersion" . }}
kind: {{ .Values.master.kind }}
metadata:
name: {{ printf "%s-master" (include "common.names.fullname" .) }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
app.kubernetes.io/component: master
{{- if .Values.commonAnnotations }}
annotations: {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
spec:
{{- if not (eq .Values.master.kind "DaemonSet") }}
replicas: {{ .Values.master.count }}
{{- end }}
revisionHistoryLimit: {{ .Values.master.revisionHistoryLimit }}
{{- $podLabels := include "common.tplvalues.merge" ( dict "values" ( list .Values.master.podLabels .Values.commonLabels ) "context" . ) }}
selector:
matchLabels: {{- include "common.labels.matchLabels" ( dict "customLabels" $podLabels "context" $ ) | nindent 6 }}
app.kubernetes.io/component: master
{{- if (eq .Values.master.kind "StatefulSet") }}
serviceName: {{ printf "%s-headless" (include "common.names.fullname" .) }}
{{- end }}
{{- if .Values.master.updateStrategy }}
{{- if (eq .Values.master.kind "Deployment") }}
strategy: {{- toYaml .Values.master.updateStrategy | nindent 4 }}
{{- else }}
updateStrategy: {{- toYaml .Values.master.updateStrategy | nindent 4 }}
{{- end }}
{{- if and .Values.master.minReadySeconds (semverCompare ">= 1.23-0" (include "common.capabilities.kubeVersion" .)) }}
minReadySeconds: {{ .Values.master.minReadySeconds }}
{{- end }}
{{- end }}
template:
metadata:
labels: {{- include "common.labels.standard" ( dict "customLabels" $podLabels "context" $ ) | nindent 8 }}
app.kubernetes.io/component: master
{{- if and .Values.metrics.enabled .Values.metrics.podLabels }}
{{- include "common.tplvalues.render" ( dict "value" .Values.metrics.podLabels "context" $ ) | nindent 8 }}
{{- end }}
annotations:
{{- if (include "redis.createConfigmap" .) }}
checksum/configmap: {{ pick ( include (print $.Template.BasePath "/configmap.yaml") . | fromYaml ) "data" | toYaml | sha256sum }}
{{- end }}
checksum/health: {{ pick ( include (print $.Template.BasePath "/health-configmap.yaml") . | fromYaml ) "data" | toYaml | sha256sum }}
checksum/scripts: {{ pick ( include (print $.Template.BasePath "/scripts-configmap.yaml") . | fromYaml ) "data" | toYaml | sha256sum }}
checksum/secret: {{ pick ( include (print $.Template.BasePath "/secret.yaml") . | fromYaml ) "data" | toYaml | sha256sum }}
{{- if .Values.master.podAnnotations }}
{{- include "common.tplvalues.render" ( dict "value" .Values.master.podAnnotations "context" $ ) | nindent 8 }}
{{- end }}
{{- if and .Values.metrics.enabled .Values.metrics.podAnnotations }}
{{- include "common.tplvalues.render" ( dict "value" .Values.metrics.podAnnotations "context" $ ) | nindent 8 }}
{{- end }}
spec:
{{- include "redis.imagePullSecrets" . | nindent 6 }}
{{- if .Values.master.hostAliases }}
hostAliases: {{- include "common.tplvalues.render" (dict "value" .Values.master.hostAliases "context" $) | nindent 8 }}
{{- end }}
{{- if .Values.master.podSecurityContext.enabled }}
securityContext: {{- include "common.compatibility.renderSecurityContext" (dict "secContext" .Values.master.podSecurityContext "context" $) | nindent 8 }}
{{- end }}
serviceAccountName: {{ template "redis.masterServiceAccountName" . }}
automountServiceAccountToken: {{ .Values.master.automountServiceAccountToken }}
{{- if .Values.master.priorityClassName }}
priorityClassName: {{ .Values.master.priorityClassName | quote }}
{{- end }}
{{- if .Values.master.affinity }}
affinity: {{- include "common.tplvalues.render" (dict "value" .Values.master.affinity "context" $) | nindent 8 }}
{{- else }}
affinity:
podAffinity: {{- include "common.affinities.pods" (dict "type" .Values.master.podAffinityPreset "component" "master" "customLabels" $podLabels "context" $) | nindent 10 }}
podAntiAffinity: {{- include "common.affinities.pods" (dict "type" .Values.master.podAntiAffinityPreset "component" "master" "customLabels" $podLabels "context" $) | nindent 10 }}
nodeAffinity: {{- include "common.affinities.nodes" (dict "type" .Values.master.nodeAffinityPreset.type "key" .Values.master.nodeAffinityPreset.key "values" .Values.master.nodeAffinityPreset.values) | nindent 10 }}
{{- end }}
{{- if .Values.master.nodeSelector }}
nodeSelector: {{- include "common.tplvalues.render" (dict "value" .Values.master.nodeSelector "context" $) | nindent 8 }}
{{- end }}
{{- if .Values.master.tolerations }}
tolerations: {{- include "common.tplvalues.render" (dict "value" .Values.master.tolerations "context" $) | nindent 8 }}
{{- end }}
{{- if .Values.master.topologySpreadConstraints }}
topologySpreadConstraints: {{- include "common.tplvalues.render" (dict "value" .Values.master.topologySpreadConstraints "context" $) | nindent 8 }}
{{- end }}
{{- if .Values.master.shareProcessNamespace }}
shareProcessNamespace: {{ .Values.master.shareProcessNamespace }}
{{- end }}
{{- if .Values.master.schedulerName }}
schedulerName: {{ .Values.master.schedulerName | quote }}
{{- end }}
{{- if .Values.master.dnsPolicy }}
dnsPolicy: {{ .Values.master.dnsPolicy }}
{{- end }}
{{- if .Values.master.dnsConfig }}
dnsConfig: {{- include "common.tplvalues.render" (dict "value" .Values.master.dnsConfig "context" $) | nindent 8 }}
{{- end }}
enableServiceLinks: {{ .Values.master.enableServiceLinks }}
terminationGracePeriodSeconds: {{ .Values.master.terminationGracePeriodSeconds }}
containers:
- name: redis
image: {{ template "redis.image" . }}
imagePullPolicy: {{ .Values.image.pullPolicy | quote }}
{{- if .Values.master.lifecycleHooks }}
lifecycle: {{- include "common.tplvalues.render" (dict "value" .Values.master.lifecycleHooks "context" $) | nindent 12 }}
{{- end }}
{{- if .Values.master.containerSecurityContext.enabled }}
securityContext: {{- include "common.compatibility.renderSecurityContext" (dict "secContext" .Values.master.containerSecurityContext "context" $) | nindent 12 }}
{{- end }}
{{- if .Values.diagnosticMode.enabled }}
command: {{- include "common.tplvalues.render" (dict "value" .Values.diagnosticMode.command "context" $) | nindent 12 }}
{{- else if .Values.master.command }}
command: {{- include "common.tplvalues.render" (dict "value" .Values.master.command "context" $) | nindent 12 }}
{{- else }}
command:
- /bin/bash
{{- end }}
{{- if .Values.diagnosticMode.enabled }}
args: {{- include "common.tplvalues.render" (dict "value" .Values.diagnosticMode.args "context" $) | nindent 12 }}
{{- else if .Values.master.args }}
args: {{- include "common.tplvalues.render" (dict "value" .Values.master.args "context" $) | nindent 12 }}
{{- else }}
args:
- -c
- /opt/bitnami/scripts/start-scripts/start-master.sh
{{- end }}
env:
- name: BITNAMI_DEBUG
value: {{ ternary "true" "false" (or .Values.image.debug .Values.diagnosticMode.enabled) | quote }}
- name: REDIS_REPLICATION_MODE
value: master
- name: ALLOW_EMPTY_PASSWORD
value: {{ ternary "no" "yes" .Values.auth.enabled | quote }}
{{- if .Values.auth.enabled }}
{{- if .Values.auth.usePasswordFiles }}
- name: REDIS_PASSWORD_FILE
value: "/opt/bitnami/redis/secrets/redis-password"
{{- else }}
- name: REDIS_PASSWORD
valueFrom:
secretKeyRef:
name: {{ template "redis.secretName" . }}
key: {{ template "redis.secretPasswordKey" . }}
{{- end }}
{{- end }}
- name: REDIS_TLS_ENABLED
value: {{ ternary "yes" "no" .Values.tls.enabled | quote }}
{{- if .Values.tls.enabled }}
- name: REDIS_TLS_PORT
value: {{ .Values.master.containerPorts.redis | quote }}
- name: REDIS_TLS_AUTH_CLIENTS
value: {{ ternary "yes" "no" .Values.tls.authClients | quote }}
- name: REDIS_TLS_CERT_FILE
value: {{ template "redis.tlsCert" . }}
- name: REDIS_TLS_KEY_FILE
value: {{ template "redis.tlsCertKey" . }}
- name: REDIS_TLS_CA_FILE
value: {{ template "redis.tlsCACert" . }}
{{- if .Values.tls.dhParamsFilename }}
- name: REDIS_TLS_DH_PARAMS_FILE
value: {{ template "redis.tlsDHParams" . }}
{{- end }}
{{- else }}
- name: REDIS_PORT
value: {{ .Values.master.containerPorts.redis | quote }}
{{- end }}
{{- if .Values.master.extraEnvVars }}
{{- include "common.tplvalues.render" (dict "value" .Values.master.extraEnvVars "context" $) | nindent 12 }}
{{- end }}
{{- if or .Values.master.extraEnvVarsCM .Values.master.extraEnvVarsSecret }}
envFrom:
{{- if .Values.master.extraEnvVarsCM }}
- configMapRef:
name: {{ .Values.master.extraEnvVarsCM }}
{{- end }}
{{- if .Values.master.extraEnvVarsSecret }}
- secretRef:
name: {{ .Values.master.extraEnvVarsSecret }}
{{- end }}
{{- end }}
ports:
- name: redis
containerPort: {{ .Values.master.containerPorts.redis }}
{{- if not .Values.diagnosticMode.enabled }}
{{- if .Values.master.customStartupProbe }}
startupProbe: {{- include "common.tplvalues.render" (dict "value" .Values.master.customStartupProbe "context" $) | nindent 12 }}
{{- else if .Values.master.startupProbe.enabled }}
startupProbe: {{- include "common.tplvalues.render" (dict "value" (omit .Values.master.startupProbe "enabled") "context" $) | nindent 12 }}
tcpSocket:
port: redis
{{- end }}
{{- if .Values.master.customLivenessProbe }}
livenessProbe: {{- include "common.tplvalues.render" (dict "value" .Values.master.customLivenessProbe "context" $) | nindent 12 }}
{{- else if .Values.master.livenessProbe.enabled }}
livenessProbe:
initialDelaySeconds: {{ .Values.master.livenessProbe.initialDelaySeconds }}
periodSeconds: {{ .Values.master.livenessProbe.periodSeconds }}
# One second longer than command timeout should prevent generation of zombie processes.
timeoutSeconds: {{ add1 .Values.master.livenessProbe.timeoutSeconds }}
successThreshold: {{ .Values.master.livenessProbe.successThreshold }}
failureThreshold: {{ .Values.master.livenessProbe.failureThreshold }}
exec:
command:
- sh
- -c
- /health/ping_liveness_local.sh {{ .Values.master.livenessProbe.timeoutSeconds }}
{{- end }}
{{- if .Values.master.customReadinessProbe }}
readinessProbe: {{- include "common.tplvalues.render" (dict "value" .Values.master.customReadinessProbe "context" $) | nindent 12 }}
{{- else if .Values.master.readinessProbe.enabled }}
readinessProbe:
initialDelaySeconds: {{ .Values.master.readinessProbe.initialDelaySeconds }}
periodSeconds: {{ .Values.master.readinessProbe.periodSeconds }}
timeoutSeconds: {{ add1 .Values.master.readinessProbe.timeoutSeconds }}
successThreshold: {{ .Values.master.readinessProbe.successThreshold }}
failureThreshold: {{ .Values.master.readinessProbe.failureThreshold }}
exec:
command:
- sh
- -c
- /health/ping_readiness_local.sh {{ .Values.master.readinessProbe.timeoutSeconds }}
{{- end }}
{{- end }}
{{- if .Values.master.resources }}
resources: {{- toYaml .Values.master.resources | nindent 12 }}
{{- else if ne .Values.master.resourcesPreset "none" }}
resources: {{- include "common.resources.preset" (dict "type" .Values.master.resourcesPreset) | nindent 12 }}
{{- end }}
volumeMounts:
- name: start-scripts
mountPath: /opt/bitnami/scripts/start-scripts
- name: health
mountPath: /health
{{- if .Values.auth.usePasswordFiles }}
- name: redis-password
mountPath: /opt/bitnami/redis/secrets/
{{- end }}
- name: redis-data
mountPath: {{ .Values.master.persistence.path }}
{{- if .Values.master.persistence.subPath }}
subPath: {{ .Values.master.persistence.subPath }}
{{- else if .Values.master.persistence.subPathExpr }}
subPathExpr: {{ .Values.master.persistence.subPathExpr }}
{{- end }}
- name: config
mountPath: /opt/bitnami/redis/mounted-etc
- name: empty-dir
mountPath: /opt/bitnami/redis/etc/
subPath: app-conf-dir
- name: empty-dir
mountPath: /tmp
subPath: tmp-dir
{{- if .Values.tls.enabled }}
- name: redis-certificates
mountPath: /opt/bitnami/redis/certs
readOnly: true
{{- end }}
{{- if .Values.master.extraVolumeMounts }}
{{- include "common.tplvalues.render" ( dict "value" .Values.master.extraVolumeMounts "context" $ ) | nindent 12 }}
{{- end }}
{{- if .Values.metrics.enabled }}
- name: metrics
image: {{ include "redis.metrics.image" . }}
imagePullPolicy: {{ .Values.metrics.image.pullPolicy | quote }}
{{- if .Values.metrics.containerSecurityContext.enabled }}
securityContext: {{- include "common.compatibility.renderSecurityContext" (dict "secContext" .Values.metrics.containerSecurityContext "context" $) | nindent 12 }}
{{- end }}
{{- if .Values.diagnosticMode.enabled }}
command: {{- include "common.tplvalues.render" (dict "value" .Values.diagnosticMode.command "context" $) | nindent 12 }}
{{- else if .Values.metrics.command }}
command: {{- include "common.tplvalues.render" (dict "value" .Values.metrics.command "context" $) | nindent 12 }}
{{- else }}
command:
- /bin/bash
- -c
- |
if [[ -f '/secrets/redis-password' ]]; then
export REDIS_PASSWORD=$(cat /secrets/redis-password)
fi
redis_exporter{{- range $key, $value := .Values.metrics.extraArgs }} --{{ $key }}={{ $value }}{{- end }}
{{- end }}
{{- if .Values.diagnosticMode.enabled }}
args: {{- include "common.tplvalues.render" (dict "value" .Values.diagnosticMode.args "context" $) | nindent 12 }}
{{- end }}
env:
- name: REDIS_ALIAS
value: {{ template "common.names.fullname" . }}
- name: REDIS_EXPORTER_WEB_LISTEN_ADDRESS
value: {{ printf ":%v" .Values.metrics.containerPorts.http }}
{{- if .Values.auth.enabled }}
- name: REDIS_USER
value: default
{{- if (not .Values.auth.usePasswordFiles) }}
- name: REDIS_PASSWORD
valueFrom:
secretKeyRef:
name: {{ template "redis.secretName" . }}
key: {{ template "redis.secretPasswordKey" . }}
{{- end }}
{{- end }}
{{- if .Values.tls.enabled }}
- name: REDIS_ADDR
value: rediss://{{ .Values.metrics.redisTargetHost }}:{{ .Values.master.containerPorts.redis }}
{{- if .Values.tls.authClients }}
- name: REDIS_EXPORTER_TLS_CLIENT_KEY_FILE
value: {{ template "redis.tlsCertKey" . }}
- name: REDIS_EXPORTER_TLS_CLIENT_CERT_FILE
value: {{ template "redis.tlsCert" . }}
{{- end }}
- name: REDIS_EXPORTER_TLS_CA_CERT_FILE
value: {{ template "redis.tlsCACert" . }}
{{- end }}
{{- if .Values.metrics.extraEnvVars }}
{{- include "common.tplvalues.render" (dict "value" .Values.metrics.extraEnvVars "context" $) | nindent 12 }}
{{- end }}
ports:
- name: metrics
containerPort: {{ .Values.metrics.containerPorts.http }}
{{- if not .Values.diagnosticMode.enabled }}
{{- if .Values.metrics.customStartupProbe }}
startupProbe: {{- include "common.tplvalues.render" (dict "value" .Values.metrics.customStartupProbe "context" $) | nindent 12 }}
{{- else if .Values.metrics.startupProbe.enabled }}
startupProbe: {{- include "common.tplvalues.render" (dict "value" (omit .Values.metrics.startupProbe "enabled") "context" $) | nindent 12 }}
tcpSocket:
port: metrics
{{- end }}
{{- if .Values.metrics.customLivenessProbe }}
livenessProbe: {{- include "common.tplvalues.render" (dict "value" .Values.metrics.customLivenessProbe "context" $) | nindent 12 }}
{{- else if .Values.metrics.livenessProbe.enabled }}
livenessProbe: {{- include "common.tplvalues.render" (dict "value" (omit .Values.metrics.livenessProbe "enabled") "context" $) | nindent 12 }}
tcpSocket:
port: metrics
{{- end }}
{{- if .Values.metrics.customReadinessProbe }}
readinessProbe: {{- include "common.tplvalues.render" (dict "value" .Values.metrics.customReadinessProbe "context" $) | nindent 12 }}
{{- else if .Values.metrics.readinessProbe.enabled }}
readinessProbe: {{- include "common.tplvalues.render" (dict "value" (omit .Values.metrics.readinessProbe "enabled") "context" $) | nindent 12 }}
httpGet:
path: /
port: metrics
{{- end }}
{{- end }}
{{- if .Values.metrics.resources }}
resources: {{- toYaml .Values.metrics.resources | nindent 12 }}
{{- else if ne .Values.metrics.resourcesPreset "none" }}
resources: {{- include "common.resources.preset" (dict "type" .Values.metrics.resourcesPreset) | nindent 12 }}
{{- end }}
volumeMounts:
- name: empty-dir
mountPath: /tmp
subPath: app-tmp-dir
{{- if .Values.auth.usePasswordFiles }}
- name: redis-password
mountPath: /secrets/
{{- end }}
{{- if .Values.tls.enabled }}
- name: redis-certificates
mountPath: /opt/bitnami/redis/certs
readOnly: true
{{- end }}
{{- if .Values.metrics.extraVolumeMounts }}
{{- include "common.tplvalues.render" ( dict "value" .Values.metrics.extraVolumeMounts "context" $ ) | nindent 12 }}
{{- end }}
{{- end }}
{{- if .Values.master.sidecars }}
{{- include "common.tplvalues.render" (dict "value" .Values.master.sidecars "context" $) | nindent 8 }}
{{- end }}
{{- $needsVolumePermissions := and .Values.volumePermissions.enabled .Values.master.persistence.enabled .Values.master.podSecurityContext.enabled .Values.master.containerSecurityContext.enabled }}
{{- if or .Values.master.initContainers $needsVolumePermissions .Values.sysctl.enabled }}
initContainers:
{{- if .Values.master.initContainers }}
{{- include "common.tplvalues.render" (dict "value" .Values.master.initContainers "context" $) | nindent 8 }}
{{- end }}
{{- if $needsVolumePermissions }}
- name: volume-permissions
image: {{ include "redis.volumePermissions.image" . }}
imagePullPolicy: {{ .Values.volumePermissions.image.pullPolicy | quote }}
command:
- /bin/bash
- -ec
- |
{{- if eq ( toString ( .Values.volumePermissions.containerSecurityContext.runAsUser )) "auto" }}
chown -R `id -u`:`id -G | cut -d " " -f2` {{ .Values.master.persistence.path }}
{{- else }}
chown -R {{ .Values.master.containerSecurityContext.runAsUser }}:{{ .Values.master.podSecurityContext.fsGroup }} {{ .Values.master.persistence.path }}
{{- end }}
{{- if eq ( toString ( .Values.volumePermissions.containerSecurityContext.runAsUser )) "auto" }}
securityContext: {{- omit .Values.volumePermissions.containerSecurityContext "runAsUser" | toYaml | nindent 12 }}
{{- else }}
securityContext: {{- .Values.volumePermissions.containerSecurityContext | toYaml | nindent 12 }}
{{- end }}
{{- if .Values.volumePermissions.resources }}
resources: {{- toYaml .Values.volumePermissions.resources | nindent 12 }}
{{- else if ne .Values.volumePermissions.resourcesPreset "none" }}
resources: {{- include "common.resources.preset" (dict "type" .Values.volumePermissions.resourcesPreset) | nindent 12 }}
{{- end }}
volumeMounts:
- name: empty-dir
mountPath: /tmp
subPath: tmp-dir
- name: redis-data
mountPath: {{ .Values.master.persistence.path }}
{{- if .Values.master.persistence.subPath }}
subPath: {{ .Values.master.persistence.subPath }}
{{- else if .Values.master.persistence.subPathExpr }}
subPathExpr: {{ .Values.master.persistence.subPathExpr }}
{{- end }}
{{- end }}
{{- if .Values.sysctl.enabled }}
- name: init-sysctl
image: {{ include "redis.sysctl.image" . }}
imagePullPolicy: {{ default "" .Values.sysctl.image.pullPolicy | quote }}
securityContext:
privileged: true
runAsUser: 0
{{- if .Values.sysctl.command }}
command: {{- include "common.tplvalues.render" (dict "value" .Values.sysctl.command "context" $) | nindent 12 }}
{{- end }}
{{- if .Values.sysctl.resources }}
resources: {{- toYaml .Values.sysctl.resources | nindent 12 }}
{{- else if ne .Values.sysctl.resourcesPreset "none" }}
resources: {{- include "common.resources.preset" (dict "type" .Values.sysctl.resourcesPreset) | nindent 12 }}
{{- end }}
{{- if .Values.sysctl.mountHostSys }}
volumeMounts:
- name: empty-dir
mountPath: /tmp
subPath: tmp-dir
- name: host-sys
mountPath: /host-sys
{{- end }}
{{- end }}
{{- end }}
volumes:
- name: start-scripts
configMap:
name: {{ printf "%s-scripts" (include "common.names.fullname" .) }}
defaultMode: 0755
- name: health
configMap:
name: {{ printf "%s-health" (include "common.names.fullname" .) }}
defaultMode: 0755
{{- if .Values.auth.usePasswordFiles }}
- name: redis-password
{{ if .Values.auth.usePasswordFileFromSecret }}
secret:
secretName: {{ template "redis.secretName" . }}
items:
- key: {{ template "redis.secretPasswordKey" . }}
path: redis-password
{{- else }}
emptyDir: {}
{{- end }}
{{- end }}
- name: config
configMap:
name: {{ include "redis.configmapName" . }}
{{- if .Values.sysctl.mountHostSys }}
- name: host-sys
hostPath:
path: /sys
{{- end }}
- name: empty-dir
{{- if or .Values.master.persistence.medium .Values.master.persistence.sizeLimit }}
emptyDir:
{{- if .Values.master.persistence.medium }}
medium: {{ .Values.master.persistence.medium | quote }}
{{- end }}
{{- if .Values.master.persistence.sizeLimit }}
sizeLimit: {{ .Values.master.persistence.sizeLimit | quote }}
{{- end }}
{{- else }}
emptyDir: {}
{{- end }}
{{- if .Values.tls.enabled }}
- name: redis-certificates
secret:
secretName: {{ include "redis.tlsSecretName" . }}
defaultMode: 256
{{- end }}
{{- if .Values.master.extraVolumes }}
{{- include "common.tplvalues.render" ( dict "value" .Values.master.extraVolumes "context" $ ) | nindent 8 }}
{{- end }}
{{- if .Values.metrics.extraVolumes }}
{{- include "common.tplvalues.render" ( dict "value" .Values.metrics.extraVolumes "context" $ ) | nindent 8 }}
{{- end }}
{{- if or (not .Values.master.persistence.enabled) (eq .Values.master.kind "DaemonSet") }}
- name: redis-data
{{- if or .Values.master.persistence.medium .Values.master.persistence.sizeLimit }}
emptyDir:
{{- if .Values.master.persistence.medium }}
medium: {{ .Values.master.persistence.medium | quote }}
{{- end }}
{{- if .Values.master.persistence.sizeLimit }}
sizeLimit: {{ .Values.master.persistence.sizeLimit | quote }}
{{- end }}
{{- else }}
emptyDir: {}
{{- end }}
{{- else if .Values.master.persistence.existingClaim }}
- name: redis-data
persistentVolumeClaim:
claimName: {{ printf "%s" (tpl .Values.master.persistence.existingClaim .) }}
{{- else if (eq .Values.master.kind "Deployment") }}
- name: redis-data
persistentVolumeClaim:
claimName: {{ printf "redis-data-%s-master" (include "common.names.fullname" .) }}
{{- else }}
{{- if .Values.master.persistentVolumeClaimRetentionPolicy.enabled }}
persistentVolumeClaimRetentionPolicy:
whenDeleted: {{ .Values.master.persistentVolumeClaimRetentionPolicy.whenDeleted }}
whenScaled: {{ .Values.master.persistentVolumeClaimRetentionPolicy.whenScaled }}
{{- end }}
volumeClaimTemplates:
- apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: redis-data
{{- $claimLabels := include "common.tplvalues.merge" ( dict "values" ( list .Values.master.persistence.labels .Values.commonLabels ) "context" . ) }}
labels: {{- include "common.labels.matchLabels" ( dict "customLabels" $claimLabels "context" $ ) | nindent 10 }}
app.kubernetes.io/component: master
{{- if .Values.master.persistence.annotations }}
annotations: {{- toYaml .Values.master.persistence.annotations | nindent 10 }}
{{- end }}
spec:
accessModes:
{{- range .Values.master.persistence.accessModes }}
- {{ . | quote }}
{{- end }}
resources:
requests:
storage: {{ .Values.master.persistence.size | quote }}
{{- if .Values.master.persistence.selector }}
selector: {{- include "common.tplvalues.render" (dict "value" .Values.master.persistence.selector "context" $) | nindent 10 }}
{{- end }}
{{- if .Values.master.persistence.dataSource }}
dataSource: {{- include "common.tplvalues.render" (dict "value" .Values.master.persistence.dataSource "context" $) | nindent 10 }}
{{- end }}
{{- include "common.storage.class" (dict "persistence" .Values.master.persistence "global" .Values.global) | nindent 8 }}
{{- end }}
{{- end }}
{{- end }}

View File

@ -0,0 +1,27 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- $pdb := coalesce .Values.pdb .Values.master.pdb }}
{{- if and $pdb.create (gt (int64 .Values.master.count) 0) (or (not (eq .Values.architecture "replication")) (not .Values.sentinel.enabled)) }}
apiVersion: {{ include "common.capabilities.policy.apiVersion" . }}
kind: PodDisruptionBudget
metadata:
name: {{ printf "%s-master" (include "common.names.fullname" .) }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
app.kubernetes.io/component: master
{{- if .Values.commonAnnotations }}
annotations: {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
spec:
{{- if $pdb.minAvailable }}
minAvailable: {{ $pdb.minAvailable }}
{{- end }}
{{- if or $pdb.maxUnavailable (not $pdb.minAvailable)}}
maxUnavailable: {{ $pdb.maxUnavailable | default 1 }}
{{- end }}
selector:
matchLabels: {{- include "common.labels.matchLabels" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 6 }}
app.kubernetes.io/component: master
{{- end }}

View File

@ -0,0 +1,47 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if and (include "common.capabilities.psp.supported" .) .Values.podSecurityPolicy.create }}
apiVersion: policy/v1beta1
kind: PodSecurityPolicy
metadata:
name: {{ printf "%s-master" (include "common.names.fullname" .) }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- if .Values.commonAnnotations }}
annotations: {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
spec:
allowPrivilegeEscalation: false
fsGroup:
rule: 'MustRunAs'
ranges:
- min: {{ .Values.master.podSecurityContext.fsGroup }}
max: {{ .Values.master.podSecurityContext.fsGroup }}
hostIPC: false
hostNetwork: false
hostPID: false
privileged: false
readOnlyRootFilesystem: false
requiredDropCapabilities:
- ALL
runAsUser:
rule: 'MustRunAs'
ranges:
- min: {{ .Values.master.containerSecurityContext.runAsUser }}
max: {{ .Values.master.containerSecurityContext.runAsUser }}
seLinux:
rule: 'RunAsAny'
supplementalGroups:
rule: 'MustRunAs'
ranges:
- min: {{ .Values.master.containerSecurityContext.runAsUser }}
max: {{ .Values.master.containerSecurityContext.runAsUser }}
volumes:
- 'configMap'
- 'secret'
- 'emptyDir'
- 'persistentVolumeClaim'
{{- end }}

View File

@ -0,0 +1,33 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if and (eq .Values.architecture "standalone") (eq .Values.master.kind "Deployment") (.Values.master.persistence.enabled) (not .Values.master.persistence.existingClaim) }}
kind: PersistentVolumeClaim
apiVersion: v1
metadata:
name: {{ printf "redis-data-%s-master" (include "common.names.fullname" .) }}
namespace: {{ include "common.names.namespace" . | quote }}
{{- $labels := include "common.tplvalues.merge" ( dict "values" ( list .Values.master.persistence.labels .Values.commonLabels ) "context" . ) }}
labels: {{- include "common.labels.standard" ( dict "customLabels" $labels "context" $ ) | nindent 4 }}
app.kubernetes.io/component: master
{{- if .Values.master.persistence.annotations }}
annotations: {{- toYaml .Values.master.persistence.annotations | nindent 4 }}
{{- end }}
spec:
accessModes:
{{- range .Values.master.persistence.accessModes }}
- {{ . | quote }}
{{- end }}
resources:
requests:
storage: {{ .Values.master.persistence.size | quote }}
{{- if .Values.master.persistence.selector }}
selector: {{- include "common.tplvalues.render" (dict "value" .Values.master.persistence.selector "context" $) | nindent 4 }}
{{- end }}
{{- if .Values.master.persistence.dataSource }}
dataSource: {{- include "common.tplvalues.render" (dict "value" .Values.master.persistence.dataSource "context" $) | nindent 4 }}
{{- end }}
{{- include "common.storage.class" (dict "persistence" .Values.master.persistence "global" .Values.global) | nindent 2 }}
{{- end }}

View File

@ -0,0 +1,62 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if and (not .Values.sentinel.enabled) (gt (int64 .Values.master.count) 0) }}
apiVersion: v1
kind: Service
metadata:
name: {{ printf "%s-master" (include "common.names.fullname" .) }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
app.kubernetes.io/component: master
{{- if or .Values.master.service.annotations .Values.commonAnnotations }}
{{- $annotations := include "common.tplvalues.merge" ( dict "values" ( list .Values.master.service.annotations .Values.commonAnnotations ) "context" . ) }}
annotations: {{- include "common.tplvalues.render" ( dict "value" $annotations "context" $) | nindent 4 }}
{{- end }}
spec:
type: {{ .Values.master.service.type }}
{{- if or (eq .Values.master.service.type "LoadBalancer") (eq .Values.master.service.type "NodePort") }}
externalTrafficPolicy: {{ .Values.master.service.externalTrafficPolicy | quote }}
{{- end }}
{{- if (semverCompare ">=1.22-0" (include "common.capabilities.kubeVersion" .)) }}
internalTrafficPolicy: {{ .Values.master.service.internalTrafficPolicy }}
{{- end }}
{{- if and (eq .Values.master.service.type "LoadBalancer") (not (empty .Values.master.service.loadBalancerIP)) }}
loadBalancerIP: {{ .Values.master.service.loadBalancerIP }}
{{- end }}
{{- if and (eq .Values.master.service.type "LoadBalancer") .Values.master.service.loadBalancerClass }}
loadBalancerClass: {{ .Values.master.service.loadBalancerClass }}
{{- end }}
{{- if and (eq .Values.master.service.type "LoadBalancer") (not (empty .Values.master.service.loadBalancerSourceRanges)) }}
loadBalancerSourceRanges: {{ toYaml .Values.master.service.loadBalancerSourceRanges | nindent 4 }}
{{- end }}
{{- if and .Values.master.service.clusterIP (eq .Values.master.service.type "ClusterIP") }}
clusterIP: {{ .Values.master.service.clusterIP }}
{{- end }}
{{- if .Values.master.service.sessionAffinity }}
sessionAffinity: {{ .Values.master.service.sessionAffinity }}
{{- end }}
{{- if .Values.master.service.sessionAffinityConfig }}
sessionAffinityConfig: {{- include "common.tplvalues.render" (dict "value" .Values.master.service.sessionAffinityConfig "context" $) | nindent 4 }}
{{- end }}
{{- if .Values.master.service.externalIPs }}
externalIPs: {{- include "common.tplvalues.render" (dict "value" .Values.master.service.externalIPs "context" $) | nindent 4 }}
{{- end }}
ports:
- name: {{ .Values.master.service.portNames.redis }}
port: {{ .Values.master.service.ports.redis }}
targetPort: redis
{{- if and (or (eq .Values.master.service.type "NodePort") (eq .Values.master.service.type "LoadBalancer")) .Values.master.service.nodePorts.redis}}
nodePort: {{ .Values.master.service.nodePorts.redis}}
{{- else if eq .Values.master.service.type "ClusterIP" }}
nodePort: null
{{- end }}
{{- if .Values.master.service.extraPorts }}
{{- include "common.tplvalues.render" (dict "value" .Values.master.service.extraPorts "context" $) | nindent 4 }}
{{- end }}
{{- $podLabels := include "common.tplvalues.merge" ( dict "values" ( list .Values.master.podLabels .Values.commonLabels ) "context" . ) }}
selector: {{- include "common.labels.matchLabels" ( dict "customLabels" $podLabels "context" $ ) | nindent 4 }}
app.kubernetes.io/component: master
{{- end }}

View File

@ -0,0 +1,18 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if and .Values.master.serviceAccount.create (or (not (eq .Values.architecture "replication")) (not .Values.sentinel.enabled)) }}
apiVersion: v1
kind: ServiceAccount
automountServiceAccountToken: {{ .Values.master.serviceAccount.automountServiceAccountToken }}
metadata:
name: {{ template "redis.masterServiceAccountName" . }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- if or .Values.master.serviceAccount.annotations .Values.commonAnnotations }}
{{- $annotations := include "common.tplvalues.merge" ( dict "values" ( list .Values.master.serviceAccount.annotations .Values.commonAnnotations ) "context" . ) }}
annotations: {{- include "common.tplvalues.render" ( dict "value" $annotations "context" $) | nindent 4 }}
{{- end }}
{{- end }}

View File

@ -0,0 +1,44 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if and .Values.metrics.enabled .Values.metrics.service.enabled }}
apiVersion: v1
kind: Service
metadata:
name: {{ printf "%s-metrics" (include "common.names.fullname" .) }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
app.kubernetes.io/component: metrics
{{- if or .Values.metrics.service.annotations .Values.commonAnnotations }}
{{- $annotations := include "common.tplvalues.merge" ( dict "values" ( list .Values.metrics.service.annotations .Values.commonAnnotations ) "context" . ) }}
annotations: {{- include "common.tplvalues.render" ( dict "value" $annotations "context" $) | nindent 4 }}
{{- end }}
spec:
type: {{ .Values.metrics.service.type }}
{{- if and .Values.metrics.service.clusterIP (eq .Values.metrics.service.type "ClusterIP") }}
clusterIP: {{ .Values.metrics.service.clusterIP }}
{{- end }}
{{- if eq .Values.metrics.service.type "LoadBalancer" }}
externalTrafficPolicy: {{ .Values.metrics.service.externalTrafficPolicy }}
{{- end }}
{{- if and (eq .Values.metrics.service.type "LoadBalancer") .Values.metrics.service.loadBalancerIP }}
loadBalancerIP: {{ .Values.metrics.service.loadBalancerIP }}
{{- end }}
{{- if and (eq .Values.metrics.service.type "LoadBalancer") .Values.metrics.service.loadBalancerClass }}
loadBalancerClass: {{ .Values.metrics.service.loadBalancerClass }}
{{- end }}
{{- if and (eq .Values.metrics.service.type "LoadBalancer") .Values.metrics.service.loadBalancerSourceRanges }}
loadBalancerSourceRanges: {{- toYaml .Values.metrics.service.loadBalancerSourceRanges | nindent 4 }}
{{- end }}
ports:
- name: http-metrics
port: {{ coalesce .Values.metrics.service.ports.http .Values.metrics.service.port }}
protocol: TCP
targetPort: metrics
{{- if .Values.metrics.service.extraPorts }}
{{- include "common.tplvalues.render" (dict "value" .Values.metrics.service.extraPorts "context" $) | nindent 4 }}
{{- end }}
selector: {{- include "common.labels.matchLabels" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- end }}

View File

@ -0,0 +1,108 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if .Values.networkPolicy.enabled }}
kind: NetworkPolicy
apiVersion: {{ template "networkPolicy.apiVersion" . }}
metadata:
name: {{ template "common.names.fullname" . }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- if .Values.commonAnnotations }}
annotations: {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
spec:
podSelector:
matchLabels: {{- include "common.labels.matchLabels" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 6 }}
policyTypes:
- Ingress
- Egress
{{- if .Values.networkPolicy.allowExternalEgress }}
egress:
- {}
{{- else }}
egress:
{{- if eq .Values.architecture "replication" }}
# Allow dns resolution
- ports:
- port: 53
protocol: UDP
# Allow outbound connections to other cluster pods
- ports:
- port: {{ .Values.master.containerPorts.redis }}
{{- if .Values.sentinel.enabled }}
- port: {{ .Values.sentinel.containerPorts.sentinel }}
{{- end }}
to:
- podSelector:
matchLabels: {{- include "common.labels.matchLabels" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 14 }}
{{- end }}
{{- if .Values.networkPolicy.extraEgress }}
{{- include "common.tplvalues.render" ( dict "value" .Values.networkPolicy.extraEgress "context" $ ) | nindent 4 }}
{{- end }}
{{- end }}
ingress:
# Allow inbound connections
- ports:
- port: {{ .Values.master.containerPorts.redis }}
{{- if .Values.sentinel.enabled }}
- port: {{ .Values.sentinel.containerPorts.sentinel }}
{{- end }}
{{- if not .Values.networkPolicy.allowExternal }}
from:
- podSelector:
matchLabels:
{{ template "common.names.fullname" . }}-client: "true"
- podSelector:
matchLabels: {{- include "common.labels.matchLabels" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 14 }}
{{- if or .Values.networkPolicy.ingressNSMatchLabels .Values.networkPolicy.ingressNSPodMatchLabels }}
- namespaceSelector:
matchLabels:
{{- if .Values.networkPolicy.ingressNSMatchLabels }}
{{- range $key, $value := .Values.networkPolicy.ingressNSMatchLabels }}
{{ $key | quote }}: {{ $value | quote }}
{{- end }}
{{ else }}
{}
{{- end }}
{{- if .Values.networkPolicy.ingressNSPodMatchLabels }}
podSelector:
matchLabels:
{{- range $key, $value := .Values.networkPolicy.ingressNSPodMatchLabels }}
{{ $key | quote }}: {{ $value | quote }}
{{- end }}
{{- end }}
{{- end }}
{{- end }}
{{- if .Values.metrics.enabled }}
# Allow prometheus scrapes for metrics
- ports:
- port: {{ .Values.metrics.containerPorts.http }}
{{- if not .Values.networkPolicy.metrics.allowExternal }}
from:
{{- if or .Values.networkPolicy.metrics.ingressNSMatchLabels .Values.networkPolicy.metrics.ingressNSPodMatchLabels }}
- namespaceSelector:
matchLabels:
{{- if .Values.networkPolicy.metrics.ingressNSMatchLabels }}
{{- range $key, $value := .Values.networkPolicy.metrics.ingressNSMatchLabels }}
{{ $key | quote }}: {{ $value | quote }}
{{- end }}
{{ else }}
{}
{{- end }}
{{- if .Values.networkPolicy.metrics.ingressNSPodMatchLabels }}
podSelector:
matchLabels:
{{- range $key, $value := .Values.networkPolicy.metrics.ingressNSPodMatchLabels }}
{{ $key | quote }}: {{ $value | quote }}
{{- end }}
{{- end }}
{{- end }}
{{- end }}
{{- end }}
{{- if .Values.networkPolicy.extraIngress }}
{{- include "common.tplvalues.render" ( dict "value" .Values.networkPolicy.extraIngress "context" $ ) | nindent 4 }}
{{- end }}
{{- end }}

View File

@ -0,0 +1,81 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if and .Values.metrics.enabled .Values.metrics.podMonitor.enabled }}
apiVersion: monitoring.coreos.com/v1
kind: PodMonitor
metadata:
name: {{ template "common.names.fullname" . }}
namespace: {{ default (include "common.names.namespace" .) .Values.metrics.podMonitor.namespace | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- if .Values.metrics.podMonitor.additionalLabels }}
{{- include "common.tplvalues.render" (dict "value" .Values.metrics.podMonitor.additionalLabels "context" $) | nindent 4 }}
{{- end }}
{{- if .Values.commonAnnotations }}
annotations: {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
spec:
podMetricsEndpoints:
- port: {{ .Values.metrics.podMonitor.port }}
{{- if .Values.metrics.podMonitor.interval }}
interval: {{ .Values.metrics.podMonitor.interval }}
{{- end }}
{{- if .Values.metrics.podMonitor.scrapeTimeout }}
scrapeTimeout: {{ .Values.metrics.podMonitor.scrapeTimeout }}
{{- end }}
{{- if .Values.metrics.podMonitor.honorLabels }}
honorLabels: {{ .Values.metrics.podMonitor.honorLabels }}
{{- end }}
{{- with concat .Values.metrics.podMonitor.relabelings .Values.metrics.podMonitor.relabellings }}
relabelings: {{- toYaml . | nindent 6 }}
{{- end }}
{{- if .Values.metrics.podMonitor.metricRelabelings }}
metricRelabelings: {{- toYaml .Values.metrics.podMonitor.metricRelabelings | nindent 6 }}
{{- end }}
{{- range .Values.metrics.podMonitor.additionalEndpoints }}
- port: {{ .port }}
{{- if .interval }}
interval: {{ .interval }}
{{- end }}
{{- if .path }}
path: {{ .path }}
{{- end }}
{{- if .honorLabels }}
honorLabels: {{ .honorLabels }}
{{- end }}
{{- with concat .relabelings .relabellings }}
relabelings: {{- toYaml . | nindent 6 }}
{{- end }}
{{- if .metricRelabelings }}
metricRelabelings: {{- toYaml .metricRelabelings | nindent 6 }}
{{- end }}
{{- if .scrapeTimeout }}
scrapeTimeout: {{ .scrapeTimeout }}
{{- end }}
{{- if .params }}
params:
{{- range $key, $value := .params }}
{{ $key }}:
{{- range $value }}
- {{ . | quote }}
{{- end }}
{{- end }}
{{- end }}
{{- end }}
{{- if .Values.metrics.serviceMonitor.podTargetLabels }}
podTargetLabels: {{- toYaml .Values.metrics.podMonitor.podTargetLabels | nindent 4 }}
{{- end }}
{{- with .Values.metrics.podMonitor.sampleLimit -}}
sampleLimit: {{ . }}
{{- end }}
{{- with .Values.metrics.podMonitor.targetLimit -}}
targetLimit: {{ . }}
{{- end }}
namespaceSelector:
matchNames:
- {{ include "common.names.namespace" . | quote }}
selector:
matchLabels: {{- include "common.labels.matchLabels" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 6 }}
{{- end }}

View File

@ -0,0 +1,23 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if and .Values.metrics.enabled .Values.metrics.prometheusRule.enabled }}
apiVersion: monitoring.coreos.com/v1
kind: PrometheusRule
metadata:
name: {{ template "common.names.fullname" . }}
namespace: {{ default (include "common.names.namespace" .) .Values.metrics.prometheusRule.namespace | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- if .Values.metrics.prometheusRule.additionalLabels }}
{{- include "common.tplvalues.render" (dict "value" .Values.metrics.prometheusRule.additionalLabels "context" $) | nindent 4 }}
{{- end }}
{{- if .Values.commonAnnotations }}
annotations: {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
spec:
groups:
- name: {{ include "common.names.fullname" . }}
rules: {{- include "common.tplvalues.render" ( dict "value" .Values.metrics.prometheusRule.rules "context" $ ) | nindent 8 }}
{{- end }}

View File

@ -0,0 +1,561 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if and (eq .Values.architecture "replication") (not .Values.sentinel.enabled) }}
apiVersion: {{ include "common.capabilities.statefulset.apiVersion" . }}
kind: {{ .Values.replica.kind }}
metadata:
name: {{ printf "%s-replicas" (include "common.names.fullname" .) }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
app.kubernetes.io/component: replica
{{- if .Values.commonAnnotations }}
annotations: {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
spec:
{{- if and (not (eq .Values.replica.kind "DaemonSet")) (not .Values.replica.autoscaling.enabled) }}
replicas: {{ .Values.replica.replicaCount }}
{{- end }}
revisionHistoryLimit: {{ .Values.replica.revisionHistoryLimit }}
{{- $podLabels := include "common.tplvalues.merge" ( dict "values" ( list .Values.replica.podLabels .Values.commonLabels ) "context" . ) }}
selector:
matchLabels: {{- include "common.labels.matchLabels" ( dict "customLabels" $podLabels "context" $ ) | nindent 6 }}
app.kubernetes.io/component: replica
{{- if (eq .Values.replica.kind "StatefulSet") }}
serviceName: {{ printf "%s-headless" (include "common.names.fullname" .) }}
{{- end }}
{{- if .Values.replica.updateStrategy }}
updateStrategy: {{- toYaml .Values.replica.updateStrategy | nindent 4 }}
{{- end }}
{{- if and .Values.replica.minReadySeconds (semverCompare ">= 1.23-0" (include "common.capabilities.kubeVersion" .)) }}
minReadySeconds: {{ .Values.replica.minReadySeconds }}
{{- end }}
{{- if .Values.replica.podManagementPolicy }}
podManagementPolicy: {{ .Values.replica.podManagementPolicy | quote }}
{{- end }}
template:
metadata:
labels: {{- include "common.labels.standard" ( dict "customLabels" $podLabels "context" $ ) | nindent 8 }}
app.kubernetes.io/component: replica
{{- if and .Values.metrics.enabled .Values.metrics.podLabels }}
{{- include "common.tplvalues.render" ( dict "value" .Values.metrics.podLabels "context" $ ) | nindent 8 }}
{{- end }}
annotations:
{{- if (include "redis.createConfigmap" .) }}
checksum/configmap: {{ pick ( include (print $.Template.BasePath "/configmap.yaml") . | fromYaml ) "data" | toYaml | sha256sum }}
{{- end }}
checksum/health: {{ pick ( include (print $.Template.BasePath "/health-configmap.yaml") . | fromYaml ) "data" | toYaml | sha256sum }}
checksum/scripts: {{ pick ( include (print $.Template.BasePath "/scripts-configmap.yaml") . | fromYaml ) "data" | toYaml | sha256sum }}
checksum/secret: {{ pick ( include (print $.Template.BasePath "/secret.yaml") . | fromYaml ) "data" | toYaml | sha256sum }}
{{- if .Values.replica.podAnnotations }}
{{- include "common.tplvalues.render" ( dict "value" .Values.replica.podAnnotations "context" $ ) | nindent 8 }}
{{- end }}
{{- if and .Values.metrics.enabled .Values.metrics.podAnnotations }}
{{- include "common.tplvalues.render" ( dict "value" .Values.metrics.podAnnotations "context" $ ) | nindent 8 }}
{{- end }}
spec:
{{- include "redis.imagePullSecrets" . | nindent 6 }}
{{- if .Values.replica.hostAliases }}
hostAliases: {{- include "common.tplvalues.render" (dict "value" .Values.replica.hostAliases "context" $) | nindent 8 }}
{{- end }}
{{- if .Values.replica.podSecurityContext.enabled }}
securityContext: {{- include "common.compatibility.renderSecurityContext" (dict "secContext" .Values.replica.podSecurityContext "context" $) | nindent 8 }}
{{- end }}
serviceAccountName: {{ template "redis.replicaServiceAccountName" . }}
automountServiceAccountToken: {{ .Values.replica.automountServiceAccountToken }}
{{- if .Values.replica.priorityClassName }}
priorityClassName: {{ .Values.replica.priorityClassName | quote }}
{{- end }}
{{- if .Values.replica.affinity }}
affinity: {{- include "common.tplvalues.render" (dict "value" .Values.replica.affinity "context" $) | nindent 8 }}
{{- else }}
affinity:
podAffinity: {{- include "common.affinities.pods" (dict "type" .Values.replica.podAffinityPreset "component" "replica" "customLabels" $podLabels "context" $) | nindent 10 }}
podAntiAffinity: {{- include "common.affinities.pods" (dict "type" .Values.replica.podAntiAffinityPreset "component" "replica" "customLabels" $podLabels "context" $) | nindent 10 }}
nodeAffinity: {{- include "common.affinities.nodes" (dict "type" .Values.replica.nodeAffinityPreset.type "key" .Values.replica.nodeAffinityPreset.key "values" .Values.replica.nodeAffinityPreset.values) | nindent 10 }}
{{- end }}
{{- if .Values.replica.nodeSelector }}
nodeSelector: {{- include "common.tplvalues.render" (dict "value" .Values.replica.nodeSelector "context" $) | nindent 8 }}
{{- end }}
{{- if .Values.replica.tolerations }}
tolerations: {{- include "common.tplvalues.render" (dict "value" .Values.replica.tolerations "context" $) | nindent 8 }}
{{- end }}
{{- if .Values.replica.topologySpreadConstraints }}
topologySpreadConstraints: {{- include "common.tplvalues.render" (dict "value" .Values.replica.topologySpreadConstraints "context" $) | nindent 8 }}
{{- end }}
{{- if .Values.replica.shareProcessNamespace }}
shareProcessNamespace: {{ .Values.replica.shareProcessNamespace }}
{{- end }}
{{- if .Values.replica.schedulerName }}
schedulerName: {{ .Values.replica.schedulerName | quote }}
{{- end }}
{{- if .Values.replica.dnsPolicy }}
dnsPolicy: {{ .Values.replica.dnsPolicy }}
{{- end }}
{{- if .Values.replica.dnsConfig }}
dnsConfig: {{- include "common.tplvalues.render" (dict "value" .Values.replica.dnsConfig "context" $) | nindent 8 }}
{{- end }}
enableServiceLinks: {{ .Values.replica.enableServiceLinks }}
terminationGracePeriodSeconds: {{ .Values.replica.terminationGracePeriodSeconds }}
containers:
- name: redis
image: {{ template "redis.image" . }}
imagePullPolicy: {{ .Values.image.pullPolicy | quote }}
{{- if not .Values.diagnosticMode.enabled }}
{{- if .Values.replica.lifecycleHooks }}
lifecycle: {{- include "common.tplvalues.render" (dict "value" .Values.replica.lifecycleHooks "context" $) | nindent 12 }}
{{- end }}
{{- end }}
{{- if .Values.replica.containerSecurityContext.enabled }}
securityContext: {{- include "common.compatibility.renderSecurityContext" (dict "secContext" .Values.replica.containerSecurityContext "context" $) | nindent 12 }}
{{- end }}
{{- if .Values.diagnosticMode.enabled }}
command: {{- include "common.tplvalues.render" (dict "value" .Values.diagnosticMode.command "context" $) | nindent 12 }}
{{- else if .Values.replica.command }}
command: {{- include "common.tplvalues.render" (dict "value" .Values.replica.command "context" $) | nindent 12 }}
{{- else }}
command:
- /bin/bash
{{- end }}
{{- if .Values.diagnosticMode.enabled }}
args: {{- include "common.tplvalues.render" (dict "value" .Values.diagnosticMode.args "context" $) | nindent 12 }}
{{- else if .Values.replica.args }}
args: {{- include "common.tplvalues.render" (dict "value" .Values.replica.args "context" $) | nindent 12 }}
{{- else }}
args:
- -c
- /opt/bitnami/scripts/start-scripts/start-replica.sh
{{- end }}
env:
- name: BITNAMI_DEBUG
value: {{ ternary "true" "false" (or .Values.image.debug .Values.diagnosticMode.enabled) | quote }}
- name: REDIS_REPLICATION_MODE
value: replica
- name: REDIS_MASTER_HOST
{{- if .Values.replica.externalMaster.enabled }}
value: {{ .Values.replica.externalMaster.host | quote }}
{{- else if and (eq (int64 .Values.master.count) 1) (eq .Values.master.kind "StatefulSet") }}
value: {{ template "common.names.fullname" . }}-master-0.{{ template "common.names.fullname" . }}-headless.{{ include "common.names.namespace" . }}.svc.{{ .Values.clusterDomain }}
{{- else }}
value: {{ template "common.names.fullname" . }}-master.{{ include "common.names.namespace" . }}.svc.{{ .Values.clusterDomain }}
{{- end }}
- name: REDIS_MASTER_PORT_NUMBER
{{- if .Values.replica.externalMaster.enabled }}
value: {{ .Values.replica.externalMaster.port | quote }}
{{- else }}
value: {{ .Values.master.containerPorts.redis | quote }}
{{- end }}
- name: ALLOW_EMPTY_PASSWORD
value: {{ ternary "no" "yes" .Values.auth.enabled | quote }}
{{- if .Values.auth.enabled }}
{{- if .Values.auth.usePasswordFiles }}
- name: REDIS_PASSWORD_FILE
value: "/opt/bitnami/redis/secrets/redis-password"
- name: REDIS_MASTER_PASSWORD_FILE
value: "/opt/bitnami/redis/secrets/redis-password"
{{- else }}
- name: REDIS_PASSWORD
valueFrom:
secretKeyRef:
name: {{ template "redis.secretName" . }}
key: {{ template "redis.secretPasswordKey" . }}
- name: REDIS_MASTER_PASSWORD
valueFrom:
secretKeyRef:
name: {{ template "redis.secretName" . }}
key: {{ template "redis.secretPasswordKey" . }}
{{- end }}
{{- end }}
- name: REDIS_TLS_ENABLED
value: {{ ternary "yes" "no" .Values.tls.enabled | quote }}
{{- if .Values.tls.enabled }}
- name: REDIS_TLS_PORT
value: {{ .Values.replica.containerPorts.redis | quote }}
- name: REDIS_TLS_AUTH_CLIENTS
value: {{ ternary "yes" "no" .Values.tls.authClients | quote }}
- name: REDIS_TLS_CERT_FILE
value: {{ template "redis.tlsCert" . }}
- name: REDIS_TLS_KEY_FILE
value: {{ template "redis.tlsCertKey" . }}
- name: REDIS_TLS_CA_FILE
value: {{ template "redis.tlsCACert" . }}
{{- if .Values.tls.dhParamsFilename }}
- name: REDIS_TLS_DH_PARAMS_FILE
value: {{ template "redis.tlsDHParams" . }}
{{- end }}
{{- else }}
- name: REDIS_PORT
value: {{ .Values.replica.containerPorts.redis | quote }}
{{- end }}
{{- if .Values.replica.extraEnvVars }}
{{- include "common.tplvalues.render" (dict "value" .Values.replica.extraEnvVars "context" $) | nindent 12 }}
{{- end }}
{{- if or .Values.replica.extraEnvVarsCM .Values.replica.extraEnvVarsSecret }}
envFrom:
{{- if .Values.replica.extraEnvVarsCM }}
- configMapRef:
name: {{ .Values.replica.extraEnvVarsCM }}
{{- end }}
{{- if .Values.replica.extraEnvVarsSecret }}
- secretRef:
name: {{ .Values.replica.extraEnvVarsSecret }}
{{- end }}
{{- end }}
ports:
- name: redis
containerPort: {{ .Values.replica.containerPorts.redis }}
{{- if not .Values.diagnosticMode.enabled }}
{{- if .Values.replica.customStartupProbe }}
startupProbe: {{- include "common.tplvalues.render" (dict "value" .Values.replica.customStartupProbe "context" $) | nindent 12 }}
{{- else if .Values.replica.startupProbe.enabled }}
startupProbe: {{- include "common.tplvalues.render" (dict "value" (omit .Values.replica.startupProbe "enabled") "context" $) | nindent 12 }}
tcpSocket:
port: redis
{{- end }}
{{- if .Values.replica.customLivenessProbe }}
livenessProbe: {{- include "common.tplvalues.render" (dict "value" .Values.replica.customLivenessProbe "context" $) | nindent 12 }}
{{- else if .Values.replica.livenessProbe.enabled }}
livenessProbe:
initialDelaySeconds: {{ .Values.replica.livenessProbe.initialDelaySeconds }}
periodSeconds: {{ .Values.replica.livenessProbe.periodSeconds }}
timeoutSeconds: {{ add1 .Values.replica.livenessProbe.timeoutSeconds }}
successThreshold: {{ .Values.replica.livenessProbe.successThreshold }}
failureThreshold: {{ .Values.replica.livenessProbe.failureThreshold }}
exec:
command:
- sh
- -c
- /health/ping_liveness_local_and_master.sh {{ .Values.replica.livenessProbe.timeoutSeconds }}
{{- end }}
{{- if .Values.replica.customReadinessProbe }}
readinessProbe: {{- include "common.tplvalues.render" (dict "value" .Values.replica.customReadinessProbe "context" $) | nindent 12 }}
{{- else if .Values.replica.readinessProbe.enabled }}
readinessProbe:
initialDelaySeconds: {{ .Values.replica.readinessProbe.initialDelaySeconds }}
periodSeconds: {{ .Values.replica.readinessProbe.periodSeconds }}
timeoutSeconds: {{ add1 .Values.replica.readinessProbe.timeoutSeconds }}
successThreshold: {{ .Values.replica.readinessProbe.successThreshold }}
failureThreshold: {{ .Values.replica.readinessProbe.failureThreshold }}
exec:
command:
- sh
- -c
- /health/ping_readiness_local_and_master.sh {{ .Values.replica.readinessProbe.timeoutSeconds }}
{{- end }}
{{- end }}
{{- if .Values.replica.resources }}
resources: {{- toYaml .Values.replica.resources | nindent 12 }}
{{- else if ne .Values.replica.resourcesPreset "none" }}
resources: {{- include "common.resources.preset" (dict "type" .Values.replica.resourcesPreset) | nindent 12 }}
{{- end }}
volumeMounts:
- name: start-scripts
mountPath: /opt/bitnami/scripts/start-scripts
- name: health
mountPath: /health
{{- if .Values.auth.usePasswordFiles }}
- name: redis-password
mountPath: /opt/bitnami/redis/secrets/
{{- end }}
- name: redis-data
mountPath: /data
{{- if .Values.replica.persistence.subPath }}
subPath: {{ .Values.replica.persistence.subPath }}
{{- else if .Values.replica.persistence.subPathExpr }}
subPathExpr: {{ .Values.replica.persistence.subPathExpr }}
{{- end }}
- name: config
mountPath: /opt/bitnami/redis/mounted-etc
- name: empty-dir
mountPath: /opt/bitnami/redis/etc
subPath: app-conf-dir
- name: empty-dir
mountPath: /tmp
subPath: tmp-dir
{{- if .Values.tls.enabled }}
- name: redis-certificates
mountPath: /opt/bitnami/redis/certs
readOnly: true
{{- end }}
{{- if .Values.replica.extraVolumeMounts }}
{{- include "common.tplvalues.render" ( dict "value" .Values.replica.extraVolumeMounts "context" $ ) | nindent 12 }}
{{- end }}
{{- if .Values.metrics.enabled }}
- name: metrics
image: {{ include "redis.metrics.image" . }}
imagePullPolicy: {{ .Values.metrics.image.pullPolicy | quote }}
{{- if .Values.metrics.containerSecurityContext.enabled }}
securityContext: {{- include "common.compatibility.renderSecurityContext" (dict "secContext" .Values.metrics.containerSecurityContext "context" $) | nindent 12 }}
{{- end }}
{{- if .Values.diagnosticMode.enabled }}
command: {{- include "common.tplvalues.render" (dict "value" .Values.diagnosticMode.command "context" $) | nindent 12 }}
{{- else if .Values.metrics.command }}
command: {{- include "common.tplvalues.render" (dict "value" .Values.metrics.command "context" $) | nindent 12 }}
{{- else }}
command:
- /bin/bash
- -c
- |
if [[ -f '/secrets/redis-password' ]]; then
export REDIS_PASSWORD=$(cat /secrets/redis-password)
fi
redis_exporter{{- range $key, $value := .Values.metrics.extraArgs }} --{{ $key }}={{ $value }}{{- end }}
{{- end }}
{{- if .Values.diagnosticMode.enabled }}
args: {{- include "common.tplvalues.render" (dict "value" .Values.diagnosticMode.args "context" $) | nindent 12 }}
{{- end }}
env:
- name: REDIS_ALIAS
value: {{ template "common.names.fullname" . }}
- name: REDIS_EXPORTER_WEB_LISTEN_ADDRESS
value: {{ printf ":%v" .Values.metrics.containerPorts.http }}
{{- if .Values.auth.enabled }}
- name: REDIS_USER
value: default
{{- if (not .Values.auth.usePasswordFiles) }}
- name: REDIS_PASSWORD
valueFrom:
secretKeyRef:
name: {{ template "redis.secretName" . }}
key: {{ template "redis.secretPasswordKey" . }}
{{- end }}
{{- end }}
{{- if .Values.tls.enabled }}
- name: REDIS_ADDR
value: rediss://{{ .Values.metrics.redisTargetHost }}:{{ .Values.replica.containerPorts.redis }}
{{- if .Values.tls.authClients }}
- name: REDIS_EXPORTER_TLS_CLIENT_KEY_FILE
value: {{ template "redis.tlsCertKey" . }}
- name: REDIS_EXPORTER_TLS_CLIENT_CERT_FILE
value: {{ template "redis.tlsCert" . }}
{{- end }}
- name: REDIS_EXPORTER_TLS_CA_CERT_FILE
value: {{ template "redis.tlsCACert" . }}
{{- end }}
{{- if .Values.metrics.extraEnvVars }}
{{- include "common.tplvalues.render" (dict "value" .Values.metrics.extraEnvVars "context" $) | nindent 12 }}
{{- end }}
ports:
- name: metrics
containerPort: {{ .Values.metrics.containerPorts.http }}
{{- if not .Values.diagnosticMode.enabled }}
{{- if .Values.metrics.customStartupProbe }}
startupProbe: {{- include "common.tplvalues.render" (dict "value" .Values.metrics.customStartupProbe "context" $) | nindent 12 }}
{{- else if .Values.metrics.startupProbe.enabled }}
startupProbe: {{- include "common.tplvalues.render" (dict "value" (omit .Values.metrics.startupProbe "enabled") "context" $) | nindent 12 }}
tcpSocket:
port: metrics
{{- end }}
{{- if .Values.metrics.customLivenessProbe }}
livenessProbe: {{- include "common.tplvalues.render" (dict "value" .Values.metrics.customLivenessProbe "context" $) | nindent 12 }}
{{- else if .Values.metrics.livenessProbe.enabled }}
livenessProbe: {{- include "common.tplvalues.render" (dict "value" (omit .Values.metrics.livenessProbe "enabled") "context" $) | nindent 12 }}
tcpSocket:
port: metrics
{{- end }}
{{- if .Values.metrics.customReadinessProbe }}
readinessProbe: {{- include "common.tplvalues.render" (dict "value" .Values.metrics.customReadinessProbe "context" $) | nindent 12 }}
{{- else if .Values.metrics.readinessProbe.enabled }}
readinessProbe: {{- include "common.tplvalues.render" (dict "value" (omit .Values.metrics.readinessProbe "enabled") "context" $) | nindent 12 }}
httpGet:
path: /
port: metrics
{{- end }}
{{- end }}
{{- if .Values.metrics.resources }}
resources: {{- toYaml .Values.metrics.resources | nindent 12 }}
{{- else if ne .Values.metrics.resourcesPreset "none" }}
resources: {{- include "common.resources.preset" (dict "type" .Values.metrics.resourcesPreset) | nindent 12 }}
{{- end }}
volumeMounts:
- name: empty-dir
mountPath: /tmp
subPath: tmp-dir
{{- if .Values.auth.usePasswordFiles }}
- name: redis-password
mountPath: /secrets/
{{- end }}
{{- if .Values.tls.enabled }}
- name: redis-certificates
mountPath: /opt/bitnami/redis/certs
readOnly: true
{{- end }}
{{- if .Values.metrics.extraVolumeMounts }}
{{- include "common.tplvalues.render" ( dict "value" .Values.metrics.extraVolumeMounts "context" $ ) | nindent 12 }}
{{- end }}
{{- end }}
{{- if .Values.replica.sidecars }}
{{- include "common.tplvalues.render" (dict "value" .Values.replica.sidecars "context" $) | nindent 8 }}
{{- end }}
{{- $needsVolumePermissions := and .Values.volumePermissions.enabled .Values.replica.persistence.enabled .Values.replica.podSecurityContext.enabled .Values.replica.containerSecurityContext.enabled }}
{{- if or .Values.replica.initContainers $needsVolumePermissions .Values.sysctl.enabled }}
initContainers:
{{- if .Values.replica.initContainers }}
{{- include "common.tplvalues.render" (dict "value" .Values.replica.initContainers "context" $) | nindent 8 }}
{{- end }}
{{- if $needsVolumePermissions }}
- name: volume-permissions
image: {{ include "redis.volumePermissions.image" . }}
imagePullPolicy: {{ .Values.volumePermissions.image.pullPolicy | quote }}
command:
- /bin/bash
- -ec
- |
{{- if eq ( toString ( .Values.volumePermissions.containerSecurityContext.runAsUser )) "auto" }}
chown -R `id -u`:`id -G | cut -d " " -f2` {{ .Values.replica.persistence.path }}
{{- else }}
chown -R {{ .Values.replica.containerSecurityContext.runAsUser }}:{{ .Values.replica.podSecurityContext.fsGroup }} {{ .Values.replica.persistence.path }}
{{- end }}
{{- if eq ( toString ( .Values.volumePermissions.containerSecurityContext.runAsUser )) "auto" }}
securityContext: {{- omit .Values.volumePermissions.containerSecurityContext "runAsUser" | toYaml | nindent 12 }}
{{- else }}
securityContext: {{- .Values.volumePermissions.containerSecurityContext | toYaml | nindent 12 }}
{{- end }}
{{- if .Values.volumePermissions.resources }}
resources: {{- toYaml .Values.volumePermissions.resources | nindent 12 }}
{{- else if ne .Values.volumePermissions.resourcesPreset "none" }}
resources: {{- include "common.resources.preset" (dict "type" .Values.volumePermissions.resourcesPreset) | nindent 12 }}
{{- end }}
volumeMounts:
- name: empty-dir
mountPath: /tmp
subPath: tmp-dir
- name: redis-data
mountPath: {{ .Values.replica.persistence.path }}
{{- if .Values.replica.persistence.subPath }}
subPath: {{ .Values.replica.persistence.subPath }}
{{- else if .Values.replica.persistence.subPathExpr }}
subPathExpr: {{ .Values.replica.persistence.subPathExpr }}
{{- end }}
{{- end }}
{{- if .Values.sysctl.enabled }}
- name: init-sysctl
image: {{ include "redis.sysctl.image" . }}
imagePullPolicy: {{ default "" .Values.sysctl.image.pullPolicy | quote }}
securityContext:
privileged: true
runAsUser: 0
{{- if .Values.sysctl.command }}
command: {{- include "common.tplvalues.render" (dict "value" .Values.sysctl.command "context" $) | nindent 12 }}
{{- end }}
{{- if .Values.sysctl.resources }}
resources: {{- toYaml .Values.sysctl.resources | nindent 12 }}
{{- else if ne .Values.sysctl.resourcesPreset "none" }}
resources: {{- include "common.resources.preset" (dict "type" .Values.sysctl.resourcesPreset) | nindent 12 }}
{{- end }}
{{- if .Values.sysctl.mountHostSys }}
volumeMounts:
- name: empty-dir
mountPath: /tmp
subPath: tmp-dir
- name: host-sys
mountPath: /host-sys
{{- end }}
{{- end }}
{{- end }}
volumes:
- name: start-scripts
configMap:
name: {{ printf "%s-scripts" (include "common.names.fullname" .) }}
defaultMode: 0755
- name: health
configMap:
name: {{ printf "%s-health" (include "common.names.fullname" .) }}
defaultMode: 0755
{{- if .Values.auth.usePasswordFiles }}
- name: redis-password
{{ if .Values.auth.usePasswordFileFromSecret }}
secret:
secretName: {{ template "redis.secretName" . }}
items:
- key: {{ template "redis.secretPasswordKey" . }}
path: redis-password
{{- else }}
emptyDir: {}
{{- end }}
{{- end }}
- name: config
configMap:
name: {{ include "redis.configmapName" . }}
{{- if .Values.sysctl.mountHostSys }}
- name: host-sys
hostPath:
path: /sys
{{- end }}
- name: empty-dir
{{- if or .Values.replica.persistence.medium .Values.replica.persistence.sizeLimit }}
emptyDir:
{{- if .Values.replica.persistence.medium }}
medium: {{ .Values.replica.persistence.medium | quote }}
{{- end }}
{{- if .Values.replica.persistence.sizeLimit }}
sizeLimit: {{ .Values.replica.persistence.sizeLimit | quote }}
{{- end }}
{{- else }}
emptyDir: {}
{{- end }}
{{- if .Values.tls.enabled }}
- name: redis-certificates
secret:
secretName: {{ include "redis.tlsSecretName" . }}
defaultMode: 256
{{- end }}
{{- if .Values.replica.extraVolumes }}
{{- include "common.tplvalues.render" ( dict "value" .Values.replica.extraVolumes "context" $ ) | nindent 8 }}
{{- end }}
{{- if .Values.metrics.extraVolumes }}
{{- include "common.tplvalues.render" ( dict "value" .Values.metrics.extraVolumes "context" $ ) | nindent 8 }}
{{- end }}
{{- if or (not .Values.replica.persistence.enabled) (not (eq .Values.replica.kind "StatefulSet")) }}
- name: redis-data
{{- if or .Values.replica.persistence.medium .Values.replica.persistence.sizeLimit }}
emptyDir:
{{- if .Values.replica.persistence.medium }}
medium: {{ .Values.replica.persistence.medium | quote }}
{{- end }}
{{- if .Values.replica.persistence.sizeLimit }}
sizeLimit: {{ .Values.replica.persistence.sizeLimit | quote }}
{{- end }}
{{- else }}
emptyDir: {}
{{- end }}
{{- else if .Values.replica.persistence.existingClaim }}
- name: redis-data
persistentVolumeClaim:
claimName: {{ printf "%s" (tpl .Values.replica.persistence.existingClaim .) }}
{{- else }}
{{- if .Values.replica.persistentVolumeClaimRetentionPolicy.enabled }}
persistentVolumeClaimRetentionPolicy:
whenDeleted: {{ .Values.replica.persistentVolumeClaimRetentionPolicy.whenDeleted }}
whenScaled: {{ .Values.replica.persistentVolumeClaimRetentionPolicy.whenScaled }}
{{- end }}
volumeClaimTemplates:
- apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: redis-data
{{- $claimLabels := include "common.tplvalues.merge" ( dict "values" ( list .Values.master.persistence.labels .Values.commonLabels ) "context" . ) }}
labels: {{- include "common.labels.matchLabels" ( dict "customLabels" $claimLabels "context" $ ) | nindent 10 }}
app.kubernetes.io/component: replica
{{- if .Values.replica.persistence.annotations }}
annotations: {{- toYaml .Values.replica.persistence.annotations | nindent 10 }}
{{- end }}
spec:
accessModes:
{{- range .Values.replica.persistence.accessModes }}
- {{ . | quote }}
{{- end }}
resources:
requests:
storage: {{ .Values.replica.persistence.size | quote }}
{{- if .Values.replica.persistence.selector }}
selector: {{- include "common.tplvalues.render" (dict "value" .Values.replica.persistence.selector "context" $) | nindent 10 }}
{{- end }}
{{- if .Values.replica.persistence.dataSource }}
dataSource: {{- include "common.tplvalues.render" (dict "value" .Values.replica.persistence.dataSource "context" $) | nindent 10 }}
{{- end }}
{{- include "common.storage.class" (dict "persistence" .Values.replica.persistence "global" .Values.global) | nindent 8 }}
{{- end }}
{{- end }}

View File

@ -0,0 +1,49 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if and .Values.replica.autoscaling.enabled (not .Values.sentinel.enabled) }}
apiVersion: {{ include "common.capabilities.hpa.apiVersion" ( dict "context" $ ) }}
kind: HorizontalPodAutoscaler
metadata:
name: {{ printf "%s-replicas" (include "common.names.fullname" .) }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
app.kubernetes.io/component: replica
{{- if .Values.commonAnnotations }}
annotations: {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
spec:
scaleTargetRef:
apiVersion: {{ include "common.capabilities.deployment.apiVersion" . }}
kind: StatefulSet
name: {{ printf "%s-replicas" (include "common.names.fullname" .) }}
minReplicas: {{ .Values.replica.autoscaling.minReplicas }}
maxReplicas: {{ .Values.replica.autoscaling.maxReplicas }}
metrics:
{{- if .Values.replica.autoscaling.targetCPU }}
- type: Resource
resource:
name: cpu
{{- if semverCompare "<1.23-0" (include "common.capabilities.kubeVersion" .) }}
targetAverageUtilization: {{ .Values.replica.autoscaling.targetCPU }}
{{- else }}
target:
type: Utilization
averageUtilization: {{ .Values.replica.autoscaling.targetCPU }}
{{- end }}
{{- end }}
{{- if .Values.replica.autoscaling.targetMemory }}
- type: Resource
resource:
name: memory
{{- if semverCompare "<1.23-0" (include "common.capabilities.kubeVersion" .) }}
targetAverageUtilization: {{ .Values.replica.autoscaling.targetMemory }}
{{- else }}
target:
type: Utilization
averageUtilization: {{ .Values.replica.autoscaling.targetMemory }}
{{- end }}
{{- end }}
{{- end }}

View File

@ -0,0 +1,28 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- $pdb := coalesce .Values.pdb .Values.replica.pdb }}
{{- if and (eq .Values.architecture "replication") (not .Values.sentinel.enabled) $pdb.create }}
apiVersion: {{ include "common.capabilities.policy.apiVersion" . }}
kind: PodDisruptionBudget
metadata:
name: {{ printf "%s-replicas" (include "common.names.fullname" .) }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
app.kubernetes.io/component: replica
{{- if .Values.commonAnnotations }}
annotations: {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
spec:
{{- if $pdb.minAvailable }}
minAvailable: {{ $pdb.minAvailable }}
{{- end }}
{{- if or $pdb.maxUnavailable (not $pdb.minAvailable) }}
maxUnavailable: {{ $pdb.maxUnavailable | default 1 }}
{{- end }}
selector:
matchLabels: {{- include "common.labels.matchLabels" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 6 }}
app.kubernetes.io/component: replica
{{- end }}

View File

@ -0,0 +1,59 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if and (eq .Values.architecture "replication") (not .Values.sentinel.enabled) }}
apiVersion: v1
kind: Service
metadata:
name: {{ printf "%s-replicas" (include "common.names.fullname" .) }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
app.kubernetes.io/component: replica
{{- if or .Values.replica.service.annotations .Values.commonAnnotations }}
{{- $annotations := include "common.tplvalues.merge" ( dict "values" ( list .Values.replica.service.annotations .Values.commonAnnotations ) "context" . ) }}
annotations: {{- include "common.tplvalues.render" ( dict "value" $annotations "context" $) | nindent 4 }}
{{- end }}
spec:
type: {{ .Values.replica.service.type }}
{{- if or (eq .Values.replica.service.type "LoadBalancer") (eq .Values.replica.service.type "NodePort") }}
externalTrafficPolicy: {{ .Values.replica.service.externalTrafficPolicy | quote }}
{{- end }}
{{- if (semverCompare ">=1.22-0" (include "common.capabilities.kubeVersion" .)) }}
internalTrafficPolicy: {{ .Values.replica.service.internalTrafficPolicy }}
{{- end }}
{{- if and (eq .Values.replica.service.type "LoadBalancer") (not (empty .Values.replica.service.loadBalancerIP)) }}
loadBalancerIP: {{ .Values.replica.service.loadBalancerIP }}
{{- end }}
{{- if and (eq .Values.replica.service.type "LoadBalancer") .Values.replica.service.loadBalancerClass }}
loadBalancerClass: {{ .Values.replica.service.loadBalancerClass }}
{{- end }}
{{- if and (eq .Values.replica.service.type "LoadBalancer") (not (empty .Values.replica.service.loadBalancerSourceRanges)) }}
loadBalancerSourceRanges: {{ toYaml .Values.replica.service.loadBalancerSourceRanges | nindent 4 }}
{{- end }}
{{- if and .Values.replica.service.clusterIP (eq .Values.replica.service.type "ClusterIP") }}
clusterIP: {{ .Values.replica.service.clusterIP }}
{{- end }}
{{- if .Values.replica.service.sessionAffinity }}
sessionAffinity: {{ .Values.replica.service.sessionAffinity }}
{{- end }}
{{- if .Values.replica.service.sessionAffinityConfig }}
sessionAffinityConfig: {{- include "common.tplvalues.render" (dict "value" .Values.replica.service.sessionAffinityConfig "context" $) | nindent 4 }}
{{- end }}
ports:
- name: tcp-redis
port: {{ .Values.replica.service.ports.redis }}
targetPort: redis
{{- if and (or (eq .Values.replica.service.type "NodePort") (eq .Values.replica.service.type "LoadBalancer")) .Values.replica.service.nodePorts.redis}}
nodePort: {{ .Values.replica.service.nodePorts.redis}}
{{- else if eq .Values.replica.service.type "ClusterIP" }}
nodePort: null
{{- end }}
{{- if .Values.replica.service.extraPorts }}
{{- include "common.tplvalues.render" (dict "value" .Values.replica.service.extraPorts "context" $) | nindent 4 }}
{{- end }}
{{- $podLabels := include "common.tplvalues.merge" ( dict "values" ( list .Values.replica.podLabels .Values.commonLabels ) "context" . ) }}
selector: {{- include "common.labels.matchLabels" ( dict "customLabels" $podLabels "context" $ ) | nindent 4 }}
app.kubernetes.io/component: replica
{{- end }}

View File

@ -0,0 +1,18 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if and .Values.replica.serviceAccount.create (eq .Values.architecture "replication") (not .Values.sentinel.enabled) }}
apiVersion: v1
kind: ServiceAccount
automountServiceAccountToken: {{ .Values.replica.serviceAccount.automountServiceAccountToken }}
metadata:
name: {{ template "redis.replicaServiceAccountName" . }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- if or .Values.replica.serviceAccount.annotations .Values.commonAnnotations }}
{{- $annotations := include "common.tplvalues.merge" ( dict "values" ( list .Values.replica.serviceAccount.annotations .Values.commonAnnotations ) "context" . ) }}
annotations: {{- include "common.tplvalues.render" ( dict "value" $annotations "context" $) | nindent 4 }}
{{- end }}
{{- end }}

View File

@ -0,0 +1,34 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if .Values.rbac.create }}
apiVersion: {{ include "common.capabilities.rbac.apiVersion" . }}
kind: Role
metadata:
name: {{ template "common.names.fullname" . }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- if .Values.commonAnnotations }}
annotations: {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
rules:
{{- if and (include "common.capabilities.psp.supported" .) .Values.podSecurityPolicy.enabled }}
- apiGroups:
- '{{ template "podSecurityPolicy.apiGroup" . }}'
resources:
- 'podsecuritypolicies'
verbs:
- 'use'
resourceNames: [{{ printf "%s-master" (include "common.names.fullname" .) }}]
{{- end }}
{{- if and .Values.sentinel.enabled (or .Values.sentinel.masterService.enabled .Values.sentinel.service.createMaster) }}
- apiGroups: [""]
resources: ["pods"]
verbs: ["list", "patch"]
{{- end -}}
{{- if .Values.rbac.rules }}
{{- include "common.tplvalues.render" ( dict "value" .Values.rbac.rules "context" $ ) | nindent 2 }}
{{- end }}
{{- end }}

View File

@ -0,0 +1,23 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if .Values.rbac.create }}
apiVersion: {{ include "common.capabilities.rbac.apiVersion" . }}
kind: RoleBinding
metadata:
name: {{ template "common.names.fullname" . }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- if .Values.commonAnnotations }}
annotations: {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: Role
name: {{ template "common.names.fullname" . }}
subjects:
- kind: ServiceAccount
name: {{ template "redis.serviceAccountName" . }}
{{- end }}

View File

@ -0,0 +1,791 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
apiVersion: v1
kind: ConfigMap
metadata:
name: {{ printf "%s-scripts" (include "common.names.fullname" .) }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- if .Values.commonAnnotations }}
annotations: {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
data:
{{- if and (eq .Values.architecture "replication") .Values.sentinel.enabled }}
start-node.sh: |
#!/bin/bash
. /opt/bitnami/scripts/libos.sh
. /opt/bitnami/scripts/liblog.sh
. /opt/bitnami/scripts/libvalidations.sh
get_port() {
hostname="$1"
type="$2"
port_var=$(echo "${hostname^^}_SERVICE_PORT_$type" | sed "s/-/_/g")
port=${!port_var}
if [ -z "$port" ]; then
case $type in
"SENTINEL")
echo {{ .Values.sentinel.containerPorts.sentinel }}
;;
"REDIS")
echo {{ .Values.master.containerPorts.redis }}
;;
esac
else
echo $port
fi
}
get_full_hostname() {
hostname="$1"
{{- if .Values.useExternalDNS.enabled }}
full_hostname="${hostname}.{{- include "redis.externalDNS.suffix" . }}"
{{- else if eq .Values.sentinel.service.type "NodePort" }}
full_hostname="${hostname}.{{- include "common.names.namespace" . }}"
{{- else }}
full_hostname="${hostname}.${HEADLESS_SERVICE}"
{{- end }}
{{- if .Values.useHostnames }}
echo "${full_hostname}"
{{- else }}
retry_count=0
until getent hosts "${full_hostname}" | awk '{ print $1; exit }' | grep .; do
if [[ $retry_count -lt {{ .Values.nameResolutionThreshold }} ]]; then
sleep {{ .Values.nameResolutionTimeout }}
else
error "IP address for ${full_hostname} not found"
exit 1
fi
((retry_count++))
done
{{- end }}
}
REDISPORT=$(get_port "$HOSTNAME" "REDIS")
HEADLESS_SERVICE="{{ template "common.names.fullname" . }}-headless.{{ include "common.names.namespace" . }}.svc.{{ .Values.clusterDomain }}"
if [ -n "$REDIS_EXTERNAL_MASTER_HOST" ]; then
REDIS_SERVICE="$REDIS_EXTERNAL_MASTER_HOST"
else
REDIS_SERVICE="{{ template "common.names.fullname" . }}.{{ include "common.names.namespace" . }}.svc.{{ .Values.clusterDomain }}"
fi
SENTINEL_SERVICE_PORT=$(get_port "{{ include "common.names.fullname" . }}" "SENTINEL")
validate_quorum() {
if is_boolean_yes "$REDIS_TLS_ENABLED"; then
quorum_info_command="{{- if and .Values.auth.enabled .Values.auth.sentinel }}REDISCLI_AUTH="\$REDIS_PASSWORD" {{ end }}redis-cli -h $REDIS_SERVICE -p $SENTINEL_SERVICE_PORT --tls --cert ${REDIS_TLS_CERT_FILE} --key ${REDIS_TLS_KEY_FILE} --cacert ${REDIS_TLS_CA_FILE} sentinel master {{ .Values.sentinel.masterSet }}"
else
quorum_info_command="{{- if and .Values.auth.enabled .Values.auth.sentinel }}REDISCLI_AUTH="\$REDIS_PASSWORD" {{ end }}redis-cli -h $REDIS_SERVICE -p $SENTINEL_SERVICE_PORT sentinel master {{ .Values.sentinel.masterSet }}"
fi
info "about to run the command: $quorum_info_command"
eval $quorum_info_command | grep -Fq "s_down"
}
trigger_manual_failover() {
if is_boolean_yes "$REDIS_TLS_ENABLED"; then
failover_command="{{- if and .Values.auth.enabled .Values.auth.sentinel }}REDISCLI_AUTH="\$REDIS_PASSWORD" {{ end }}redis-cli -h $REDIS_SERVICE -p $SENTINEL_SERVICE_PORT --tls --cert ${REDIS_TLS_CERT_FILE} --key ${REDIS_TLS_KEY_FILE} --cacert ${REDIS_TLS_CA_FILE} sentinel failover {{ .Values.sentinel.masterSet }}"
else
failover_command="{{- if and .Values.auth.enabled .Values.auth.sentinel }}REDISCLI_AUTH="\$REDIS_PASSWORD" {{ end }}redis-cli -h $REDIS_SERVICE -p $SENTINEL_SERVICE_PORT sentinel failover {{ .Values.sentinel.masterSet }}"
fi
info "about to run the command: $failover_command"
eval $failover_command
}
get_sentinel_master_info() {
if is_boolean_yes "$REDIS_TLS_ENABLED"; then
sentinel_info_command="{{- if and .Values.auth.enabled .Values.auth.sentinel }}REDISCLI_AUTH="\$REDIS_PASSWORD" {{ end }}timeout {{ .Values.sentinel.getMasterTimeout }} redis-cli -h $REDIS_SERVICE -p $SENTINEL_SERVICE_PORT --tls --cert ${REDIS_TLS_CERT_FILE} --key ${REDIS_TLS_KEY_FILE} --cacert ${REDIS_TLS_CA_FILE} sentinel get-master-addr-by-name {{ .Values.sentinel.masterSet }}"
else
sentinel_info_command="{{- if and .Values.auth.enabled .Values.auth.sentinel }}REDISCLI_AUTH="\$REDIS_PASSWORD" {{ end }}timeout {{ .Values.sentinel.getMasterTimeout }} redis-cli -h $REDIS_SERVICE -p $SENTINEL_SERVICE_PORT sentinel get-master-addr-by-name {{ .Values.sentinel.masterSet }}"
fi
info "about to run the command: $sentinel_info_command"
retry_while "eval $sentinel_info_command" 2 5
}
{{- if and .Values.replica.containerSecurityContext.runAsUser (eq (.Values.replica.containerSecurityContext.runAsUser | int) 0) }}
useradd redis
chown -R redis {{ .Values.replica.persistence.path }}
{{- end }}
[[ -f $REDIS_PASSWORD_FILE ]] && export REDIS_PASSWORD="$(< "${REDIS_PASSWORD_FILE}")"
[[ -f $REDIS_MASTER_PASSWORD_FILE ]] && export REDIS_MASTER_PASSWORD="$(< "${REDIS_MASTER_PASSWORD_FILE}")"
# check if there is a master
master_in_persisted_conf="$(get_full_hostname "$HOSTNAME")"
master_port_in_persisted_conf="$REDIS_MASTER_PORT_NUMBER"
master_in_sentinel="$(get_sentinel_master_info)"
redisRetVal=$?
if [[ -f /opt/bitnami/redis-sentinel/etc/sentinel.conf ]]; then
master_in_persisted_conf="$(awk '/monitor/ {print $4}' /opt/bitnami/redis-sentinel/etc/sentinel.conf)"
master_port_in_persisted_conf="$(awk '/monitor/ {print $5}' /opt/bitnami/redis-sentinel/etc/sentinel.conf)"
info "Found previous master ${master_in_persisted_conf}:${master_port_in_persisted_conf} in /opt/bitnami/redis-sentinel/etc/sentinel.conf"
debug "$(cat /opt/bitnami/redis-sentinel/etc/sentinel.conf | grep monitor)"
fi
if [[ $redisRetVal -ne 0 ]]; then
if [[ "$master_in_persisted_conf" == "$(get_full_hostname "$HOSTNAME")" ]]; then
# Case 1: No active sentinel and in previous sentinel.conf we were the master --> MASTER
info "Configuring the node as master"
export REDIS_REPLICATION_MODE="master"
else
# Case 2: No active sentinel and in previous sentinel.conf we were not master --> REPLICA
info "Configuring the node as replica"
export REDIS_REPLICATION_MODE="replica"
REDIS_MASTER_HOST=${master_in_persisted_conf}
REDIS_MASTER_PORT_NUMBER=${master_port_in_persisted_conf}
fi
else
# Fetches current master's host and port
REDIS_SENTINEL_INFO=($(get_sentinel_master_info))
info "Current master: REDIS_SENTINEL_INFO=(${REDIS_SENTINEL_INFO[0]},${REDIS_SENTINEL_INFO[1]})"
REDIS_MASTER_HOST=${REDIS_SENTINEL_INFO[0]}
REDIS_MASTER_PORT_NUMBER=${REDIS_SENTINEL_INFO[1]}
if [[ "$REDIS_MASTER_HOST" == "$(get_full_hostname "$HOSTNAME")" ]]; then
# Case 3: Active sentinel and master it is this node --> MASTER
info "Configuring the node as master"
export REDIS_REPLICATION_MODE="master"
else
# Case 4: Active sentinel and master is not this node --> REPLICA
info "Configuring the node as replica"
export REDIS_REPLICATION_MODE="replica"
{{- if and .Values.sentinel.automateClusterRecovery (le (int .Values.sentinel.downAfterMilliseconds) 2000) }}
retry_count=1
while validate_quorum
do
info "sleeping, waiting for Redis master to come up"
sleep 1s
if ! ((retry_count % 11)); then
info "Trying to manually failover"
failover_result=$(trigger_manual_failover)
debug "Failover result: $failover_result"
fi
((retry_count+=1))
done
info "Redis master is up now"
{{- end }}
fi
fi
if [[ -n "$REDIS_EXTERNAL_MASTER_HOST" ]]; then
REDIS_MASTER_HOST="$REDIS_EXTERNAL_MASTER_HOST"
REDIS_MASTER_PORT_NUMBER="${REDIS_EXTERNAL_MASTER_PORT}"
fi
if [[ -f /opt/bitnami/redis/mounted-etc/replica.conf ]];then
cp /opt/bitnami/redis/mounted-etc/replica.conf /opt/bitnami/redis/etc/replica.conf
fi
if [[ -f /opt/bitnami/redis/mounted-etc/redis.conf ]];then
cp /opt/bitnami/redis/mounted-etc/redis.conf /opt/bitnami/redis/etc/redis.conf
fi
echo "" >> /opt/bitnami/redis/etc/replica.conf
echo "replica-announce-port $REDISPORT" >> /opt/bitnami/redis/etc/replica.conf
echo "replica-announce-ip $(get_full_hostname "$HOSTNAME")" >> /opt/bitnami/redis/etc/replica.conf
{{- if .Values.tls.enabled }}
ARGS=("--port" "0")
ARGS+=("--tls-port" "${REDIS_TLS_PORT}")
ARGS+=("--tls-cert-file" "${REDIS_TLS_CERT_FILE}")
ARGS+=("--tls-key-file" "${REDIS_TLS_KEY_FILE}")
ARGS+=("--tls-ca-cert-file" "${REDIS_TLS_CA_FILE}")
ARGS+=("--tls-auth-clients" "${REDIS_TLS_AUTH_CLIENTS}")
ARGS+=("--tls-replication" "yes")
{{- if .Values.tls.dhParamsFilename }}
ARGS+=("--tls-dh-params-file" "${REDIS_TLS_DH_PARAMS_FILE}")
{{- end }}
{{- else }}
ARGS=("--port" "${REDIS_PORT}")
{{- end }}
if [[ "$REDIS_REPLICATION_MODE" = "slave" ]] || [[ "$REDIS_REPLICATION_MODE" = "replica" ]]; then
ARGS+=("--replicaof" "${REDIS_MASTER_HOST}" "${REDIS_MASTER_PORT_NUMBER}")
fi
{{- if .Values.auth.enabled }}
ARGS+=("--requirepass" "${REDIS_PASSWORD}")
ARGS+=("--masterauth" "${REDIS_MASTER_PASSWORD}")
{{- else }}
ARGS+=("--protected-mode" "no")
{{- end }}
ARGS+=("--include" "/opt/bitnami/redis/etc/replica.conf")
ARGS+=("--include" "/opt/bitnami/redis/etc/redis.conf")
{{- if .Values.replica.extraFlags }}
{{- range .Values.replica.extraFlags }}
ARGS+=({{ . | quote }})
{{- end }}
{{- end }}
{{- if .Values.replica.preExecCmds }}
{{- .Values.replica.preExecCmds | nindent 4 }}
{{- end }}
{{- if .Values.replica.command }}
exec {{ .Values.replica.command }} "${ARGS[@]}"
{{- else }}
exec redis-server "${ARGS[@]}"
{{- end }}
start-sentinel.sh: |
#!/bin/bash
. /opt/bitnami/scripts/libos.sh
. /opt/bitnami/scripts/libvalidations.sh
. /opt/bitnami/scripts/libfile.sh
HEADLESS_SERVICE="{{ template "common.names.fullname" . }}-headless.{{ include "common.names.namespace" . }}.svc.{{ .Values.clusterDomain }}"
REDIS_SERVICE="{{ template "common.names.fullname" . }}.{{ include "common.names.namespace" . }}.svc.{{ .Values.clusterDomain }}"
get_port() {
hostname="$1"
type="$2"
port_var=$(echo "${hostname^^}_SERVICE_PORT_$type" | sed "s/-/_/g")
port=${!port_var}
if [ -z "$port" ]; then
case $type in
"SENTINEL")
echo {{ .Values.sentinel.containerPorts.sentinel }}
;;
"REDIS")
echo {{ .Values.master.containerPorts.redis }}
;;
esac
else
echo $port
fi
}
get_full_hostname() {
hostname="$1"
{{- if .Values.useExternalDNS.enabled }}
full_hostname="${hostname}.{{- include "redis.externalDNS.suffix" . }}"
{{- else if eq .Values.sentinel.service.type "NodePort" }}
full_hostname="${hostname}.{{- include "common.names.namespace" . }}"
{{- else }}
full_hostname="${hostname}.${HEADLESS_SERVICE}"
{{- end }}
{{- if .Values.useHostnames }}
echo "${full_hostname}"
{{- else }}
retry_count=0
until getent hosts "${full_hostname}" | awk '{ print $1; exit }' | grep .; do
if [[ $retry_count -lt {{ .Values.nameResolutionThreshold }} ]]; then
sleep {{ .Values.nameResolutionTimeout }}
else
error "IP address for ${full_hostname} not found"
exit 1
fi
((retry_count++))
done
{{- end }}
}
SERVPORT=$(get_port "$HOSTNAME" "SENTINEL")
REDISPORT=$(get_port "$HOSTNAME" "REDIS")
SENTINEL_SERVICE_PORT=$(get_port "{{ include "common.names.fullname" . }}" "SENTINEL")
sentinel_conf_set() {
local -r key="${1:?missing key}"
local value="${2:-}"
# Sanitize inputs
value="${value//\\/\\\\}"
value="${value//&/\\&}"
value="${value//\?/\\?}"
[[ "$value" = "" ]] && value="\"$value\""
replace_in_file "/opt/bitnami/redis-sentinel/etc/prepare-sentinel.conf" "^#*\s*${key} .*" "${key} ${value}" false
}
sentinel_conf_add() {
echo $'\n'"$@" >> "/opt/bitnami/redis-sentinel/etc/prepare-sentinel.conf"
}
host_id() {
echo "$1" | openssl sha1 | awk '{print $2}'
}
get_sentinel_master_info() {
if is_boolean_yes "$REDIS_SENTINEL_TLS_ENABLED"; then
sentinel_info_command="{{- if and .Values.auth.enabled .Values.auth.sentinel }}REDISCLI_AUTH="\$REDIS_PASSWORD" {{ end }}timeout {{ .Values.sentinel.getMasterTimeout }} redis-cli -h $REDIS_SERVICE -p $SENTINEL_SERVICE_PORT --tls --cert ${REDIS_SENTINEL_TLS_CERT_FILE} --key ${REDIS_SENTINEL_TLS_KEY_FILE} --cacert ${REDIS_SENTINEL_TLS_CA_FILE} sentinel get-master-addr-by-name {{ .Values.sentinel.masterSet }}"
else
sentinel_info_command="{{- if and .Values.auth.enabled .Values.auth.sentinel }}REDISCLI_AUTH="\$REDIS_PASSWORD" {{ end }}timeout {{ .Values.sentinel.getMasterTimeout }} redis-cli -h $REDIS_SERVICE -p $SENTINEL_SERVICE_PORT sentinel get-master-addr-by-name {{ .Values.sentinel.masterSet }}"
fi
info "about to run the command: $sentinel_info_command"
retry_while "eval $sentinel_info_command" 2 5
}
[[ -f $REDIS_PASSWORD_FILE ]] && export REDIS_PASSWORD="$(< "${REDIS_PASSWORD_FILE}")"
master_in_persisted_conf="$(get_full_hostname "$HOSTNAME")"
if [[ -f /opt/bitnami/redis-sentinel/etc/sentinel.conf ]]; then
master_in_persisted_conf="$(awk '/monitor/ {print $4}' /opt/bitnami/redis-sentinel/etc/sentinel.conf)"
info "Found previous master $master_in_persisted_conf in /opt/bitnami/redis-sentinel/etc/sentinel.conf"
debug "$(cat /opt/bitnami/redis-sentinel/etc/sentinel.conf | grep monitor)"
fi
REDIS_SENTINEL_INFO=($(get_sentinel_master_info))
if [ "$?" -eq "0" ]; then
# current master's host and port obtained from other Sentinel
info "printing REDIS_SENTINEL_INFO=(${REDIS_SENTINEL_INFO[0]},${REDIS_SENTINEL_INFO[1]})"
REDIS_MASTER_HOST=${REDIS_SENTINEL_INFO[0]}
REDIS_MASTER_PORT_NUMBER=${REDIS_SENTINEL_INFO[1]}
else
REDIS_MASTER_HOST="$master_in_persisted_conf"
REDIS_MASTER_PORT_NUMBER="$REDISPORT"
fi
if [[ "$REDIS_MASTER_HOST" == "$(get_full_hostname "$HOSTNAME")" ]]; then
export REDIS_REPLICATION_MODE="master"
else
export REDIS_REPLICATION_MODE="replica"
fi
{{- if or .Values.sentinel.masterService.enabled .Values.sentinel.service.createMaster }}
if [[ "${REDIS_REPLICATION_MODE}" == "master" ]]; then
# Add isMaster label to master node for master service
echo "${REDIS_MASTER_HOST/.*}" > /etc/shared/current
fi
{{- end }}
if [[ -n "$REDIS_EXTERNAL_MASTER_HOST" ]]; then
REDIS_MASTER_HOST="$REDIS_EXTERNAL_MASTER_HOST"
REDIS_MASTER_PORT_NUMBER="${REDIS_EXTERNAL_MASTER_PORT}"
fi
# To prevent incomplete configuration and as the redis container accesses /opt/bitnami/redis-sentinel/etc/sentinel.conf
# as well, prepare the new config in `prepare-sentinel.conf` and move it atomically to the ultimate destination when it is complete.
cp /opt/bitnami/redis-sentinel/mounted-etc/sentinel.conf /opt/bitnami/redis-sentinel/etc/prepare-sentinel.conf
{{- if .Values.auth.enabled }}
printf "\nsentinel auth-pass %s %s" "{{ .Values.sentinel.masterSet }}" "$REDIS_PASSWORD" >> /opt/bitnami/redis-sentinel/etc/prepare-sentinel.conf
{{- if and .Values.auth.enabled .Values.auth.sentinel }}
printf "\nrequirepass %s" "$REDIS_PASSWORD" >> /opt/bitnami/redis-sentinel/etc/prepare-sentinel.conf
{{- end }}
{{- end }}
printf "\nsentinel myid %s" "$(host_id "$HOSTNAME")" >> /opt/bitnami/redis-sentinel/etc/prepare-sentinel.conf
if [[ -z "$REDIS_MASTER_HOST" ]] || [[ -z "$REDIS_MASTER_PORT_NUMBER" ]]
then
# Prevent incorrect configuration to be written to sentinel.conf
error "Redis master host is configured incorrectly (host: $REDIS_MASTER_HOST, port: $REDIS_MASTER_PORT_NUMBER)"
exit 1
fi
sentinel_conf_set "sentinel monitor" "{{ .Values.sentinel.masterSet }} "$REDIS_MASTER_HOST" "$REDIS_MASTER_PORT_NUMBER" {{ .Values.sentinel.quorum }}"
add_known_sentinel() {
hostname="$1"
ip="$2"
if [[ -n "$hostname" && -n "$ip" && "$hostname" != "$HOSTNAME" ]]; then
sentinel_conf_add "sentinel known-sentinel {{ .Values.sentinel.masterSet }} $(get_full_hostname "$hostname") $(get_port "$hostname" "SENTINEL") $(host_id "$hostname")"
fi
}
add_known_replica() {
hostname="$1"
ip="$2"
if [[ -n "$ip" && "$(get_full_hostname "$hostname")" != "$REDIS_MASTER_HOST" ]]; then
sentinel_conf_add "sentinel known-replica {{ .Values.sentinel.masterSet }} $(get_full_hostname "$hostname") $(get_port "$hostname" "REDIS")"
fi
}
# Add available hosts on the network as known replicas & sentinels
for node in $(seq 0 $(({{ .Values.replica.replicaCount }}-1))); do
hostname="{{ template "common.names.fullname" . }}-node-$node"
ip="$(getent hosts "$hostname.$HEADLESS_SERVICE" | awk '{ print $1 }')"
add_known_sentinel "$hostname" "$ip"
add_known_replica "$hostname" "$ip"
done
echo "" >> /opt/bitnami/redis-sentinel/etc/prepare-sentinel.conf
{{- if not (contains "sentinel announce-hostnames" .Values.sentinel.configuration) }}
echo "sentinel announce-hostnames yes" >> /opt/bitnami/redis-sentinel/etc/prepare-sentinel.conf
{{- end }}
{{- if not (contains "sentinel resolve-hostnames" .Values.sentinel.configuration) }}
echo "sentinel resolve-hostnames yes" >> /opt/bitnami/redis-sentinel/etc/prepare-sentinel.conf
{{- end }}
{{- if not (contains "sentinel announce-port" .Values.sentinel.configuration) }}
echo "sentinel announce-port $SERVPORT" >> /opt/bitnami/redis-sentinel/etc/prepare-sentinel.conf
{{- end }}
{{- if not (contains "sentinel announce-ip" .Values.sentinel.configuration) }}
echo "sentinel announce-ip $(get_full_hostname "$HOSTNAME")" >> /opt/bitnami/redis-sentinel/etc/prepare-sentinel.conf
{{- end }}
{{- if .Values.tls.enabled }}
ARGS=("--port" "0")
ARGS+=("--tls-port" "${REDIS_SENTINEL_TLS_PORT_NUMBER}")
ARGS+=("--tls-cert-file" "${REDIS_SENTINEL_TLS_CERT_FILE}")
ARGS+=("--tls-key-file" "${REDIS_SENTINEL_TLS_KEY_FILE}")
ARGS+=("--tls-ca-cert-file" "${REDIS_SENTINEL_TLS_CA_FILE}")
ARGS+=("--tls-replication" "yes")
ARGS+=("--tls-auth-clients" "${REDIS_SENTINEL_TLS_AUTH_CLIENTS}")
{{- if .Values.tls.dhParamsFilename }}
ARGS+=("--tls-dh-params-file" "${REDIS_SENTINEL_TLS_DH_PARAMS_FILE}")
{{- end }}
{{- end }}
{{- if .Values.sentinel.preExecCmds }}
{{ .Values.sentinel.preExecCmds | nindent 4 }}
{{- end }}
mv /opt/bitnami/redis-sentinel/etc/prepare-sentinel.conf /opt/bitnami/redis-sentinel/etc/sentinel.conf
exec redis-server /opt/bitnami/redis-sentinel/etc/sentinel.conf {{- if .Values.tls.enabled }} "${ARGS[@]}" {{- end }} --sentinel
prestop-sentinel.sh: |
#!/bin/bash
. /opt/bitnami/scripts/libvalidations.sh
. /opt/bitnami/scripts/libos.sh
HEADLESS_SERVICE="{{ template "common.names.fullname" . }}-headless.{{ include "common.names.namespace" . }}.svc.{{ .Values.clusterDomain }}"
get_full_hostname() {
hostname="$1"
{{- if .Values.useExternalDNS.enabled }}
full_hostname="${hostname}.{{- include "redis.externalDNS.suffix" . }}"
{{- else if eq .Values.sentinel.service.type "NodePort" }}
full_hostname="${hostname}.{{- include "common.names.namespace" . }}"
{{- else }}
full_hostname="${hostname}.${HEADLESS_SERVICE}"
{{- end }}
{{- if .Values.useHostnames }}
echo "${full_hostname}"
{{- else }}
retry_count=0
until getent hosts "${full_hostname}" | awk '{ print $1; exit }' | grep .; do
if [[ $retry_count -lt {{ .Values.nameResolutionThreshold }} ]]; then
sleep {{ .Values.nameResolutionTimeout }}
else
error "IP address for ${full_hostname} not found"
exit 1
fi
((retry_count++))
done
{{- end }}
}
run_sentinel_command() {
if is_boolean_yes "$REDIS_SENTINEL_TLS_ENABLED"; then
redis-cli -h "$REDIS_SERVICE" -p "$REDIS_SENTINEL_TLS_PORT_NUMBER" --tls --cert "$REDIS_SENTINEL_TLS_CERT_FILE" --key "$REDIS_SENTINEL_TLS_KEY_FILE" --cacert "$REDIS_SENTINEL_TLS_CA_FILE" sentinel "$@"
else
redis-cli -h "$REDIS_SERVICE" -p "$REDIS_SENTINEL_PORT" sentinel "$@"
fi
}
sentinel_failover_finished() {
REDIS_SENTINEL_INFO=($(run_sentinel_command get-master-addr-by-name "{{ .Values.sentinel.masterSet }}"))
REDIS_MASTER_HOST="${REDIS_SENTINEL_INFO[0]}"
[[ "$REDIS_MASTER_HOST" != "$(get_full_hostname $HOSTNAME)" ]]
}
REDIS_SERVICE="{{ include "common.names.fullname" . }}.{{ include "common.names.namespace" . }}.svc.{{ .Values.clusterDomain }}"
{{ if .Values.auth.sentinel -}}
# redis-cli automatically consumes credentials from the REDISCLI_AUTH variable
[[ -n "$REDIS_PASSWORD" ]] && export REDISCLI_AUTH="$REDIS_PASSWORD"
[[ -f "$REDIS_PASSWORD_FILE" ]] && export REDISCLI_AUTH="$(< "${REDIS_PASSWORD_FILE}")"
{{- end }}
if ! sentinel_failover_finished; then
echo "I am the master pod and you are stopping me. Starting sentinel failover"
if retry_while "sentinel_failover_finished" "{{ sub .Values.sentinel.terminationGracePeriodSeconds 10 }}" 1; then
echo "Master has been successfuly failed over to a different pod."
exit 0
else
echo "Master failover failed"
exit 1
fi
else
exit 0
fi
prestop-redis.sh: |
#!/bin/bash
. /opt/bitnami/scripts/libvalidations.sh
. /opt/bitnami/scripts/libos.sh
run_redis_command() {
if is_boolean_yes "$REDIS_TLS_ENABLED"; then
redis-cli -h 127.0.0.1 -p "$REDIS_TLS_PORT" --tls --cert "$REDIS_TLS_CERT_FILE" --key "$REDIS_TLS_KEY_FILE" --cacert "$REDIS_TLS_CA_FILE" "$@"
else
redis-cli -h 127.0.0.1 -p "$REDIS_PORT" "$@"
fi
}
is_master() {
REDIS_ROLE=$(run_redis_command role | head -1)
[[ "$REDIS_ROLE" == "master" ]]
}
HEADLESS_SERVICE="{{ template "common.names.fullname" . }}-headless.{{- include "common.names.namespace" . }}.svc.{{ .Values.clusterDomain }}"
get_full_hostname() {
hostname="$1"
{{- if .Values.useExternalDNS.enabled }}
full_hostname="${hostname}.{{- include "redis.externalDNS.suffix" . }}"
{{- else if eq .Values.sentinel.service.type "NodePort" }}
full_hostname="${hostname}.{{- include "common.names.namespace" . }}"
{{- else }}
full_hostname="${hostname}.${HEADLESS_SERVICE}"
{{- end }}
{{- if .Values.useHostnames }}
echo "${full_hostname}"
{{- else }}
retry_count=0
until getent hosts "${full_hostname}" | awk '{ print $1; exit }' | grep .; do
if [[ $retry_count -lt {{ .Values.nameResolutionThreshold }} ]]; then
sleep {{ .Values.nameResolutionTimeout }}
else
error "IP address for ${full_hostname} not found"
exit 1
fi
((retry_count++))
done
{{- end }}
}
run_sentinel_command() {
if is_boolean_yes "$REDIS_SENTINEL_TLS_ENABLED"; then
{{ .Values.auth.sentinel | ternary "" "env -u REDISCLI_AUTH " -}} redis-cli -h "$REDIS_SERVICE" -p "$REDIS_SENTINEL_TLS_PORT_NUMBER" --tls --cert "$REDIS_SENTINEL_TLS_CERT_FILE" --key "$REDIS_SENTINEL_TLS_KEY_FILE" --cacert "$REDIS_SENTINEL_TLS_CA_FILE" sentinel "$@"
else
{{ .Values.auth.sentinel | ternary "" "env -u REDISCLI_AUTH " -}} redis-cli -h "$REDIS_SERVICE" -p "$REDIS_SENTINEL_PORT" sentinel "$@"
fi
}
sentinel_failover_finished() {
REDIS_SENTINEL_INFO=($(run_sentinel_command get-master-addr-by-name "{{ .Values.sentinel.masterSet }}"))
REDIS_MASTER_HOST="${REDIS_SENTINEL_INFO[0]}"
[[ "$REDIS_MASTER_HOST" != "$(get_full_hostname $HOSTNAME)" ]]
}
REDIS_SERVICE="{{ include "common.names.fullname" . }}.{{ include "common.names.namespace" . }}.svc.{{ .Values.clusterDomain }}"
# redis-cli automatically consumes credentials from the REDISCLI_AUTH variable
[[ -n "$REDIS_PASSWORD" ]] && export REDISCLI_AUTH="$REDIS_PASSWORD"
[[ -f "$REDIS_PASSWORD_FILE" ]] && export REDISCLI_AUTH="$(< "${REDIS_PASSWORD_FILE}")"
if is_master && ! sentinel_failover_finished; then
echo "I am the master pod and you are stopping me. Pausing client connections."
# Pausing client write connections to avoid data loss
run_redis_command CLIENT PAUSE "{{ mul (add 2 (sub .Values.sentinel.terminationGracePeriodSeconds 10)) 1000 }}" WRITE
echo "Issuing failover"
# if I am the master, issue a command to failover once
run_sentinel_command failover "{{ .Values.sentinel.masterSet }}"
{{- if .Values.sentinel.redisShutdownWaitFailover }}
echo "Waiting for sentinel to complete failover for up to {{ sub .Values.sentinel.terminationGracePeriodSeconds 10 }}s"
retry_while "sentinel_failover_finished" "{{ sub .Values.sentinel.terminationGracePeriodSeconds 10 }}" 1
{{- end }}
else
exit 0
fi
{{- if or .Values.sentinel.masterService.enabled .Values.sentinel.service.createMaster }}
push-master-label.sh: |
#!/bin/bash
# https://download.redis.io/redis-stable/sentinel.conf
echo "${6/.*}" > /etc/shared/current
echo "${4/.*}" > /etc/shared/previous
{{- end }}
{{- else }}
start-master.sh: |
#!/bin/bash
[[ -f $REDIS_PASSWORD_FILE ]] && export REDIS_PASSWORD="$(< "${REDIS_PASSWORD_FILE}")"
{{- if and .Values.master.containerSecurityContext.runAsUser (eq (.Values.master.containerSecurityContext.runAsUser | int) 0) }}
useradd redis
chown -R redis {{ .Values.master.persistence.path }}
{{- end }}
if [[ -f /opt/bitnami/redis/mounted-etc/master.conf ]];then
cp /opt/bitnami/redis/mounted-etc/master.conf /opt/bitnami/redis/etc/master.conf
fi
if [[ -f /opt/bitnami/redis/mounted-etc/redis.conf ]];then
cp /opt/bitnami/redis/mounted-etc/redis.conf /opt/bitnami/redis/etc/redis.conf
fi
{{- if .Values.tls.enabled }}
ARGS=("--port" "0")
ARGS+=("--tls-port" "${REDIS_TLS_PORT}")
ARGS+=("--tls-cert-file" "${REDIS_TLS_CERT_FILE}")
ARGS+=("--tls-key-file" "${REDIS_TLS_KEY_FILE}")
ARGS+=("--tls-ca-cert-file" "${REDIS_TLS_CA_FILE}")
ARGS+=("--tls-auth-clients" "${REDIS_TLS_AUTH_CLIENTS}")
{{- if .Values.tls.dhParamsFilename }}
ARGS+=("--tls-dh-params-file" "${REDIS_TLS_DH_PARAMS_FILE}")
{{- end }}
{{- else }}
ARGS=("--port" "${REDIS_PORT}")
{{- end }}
{{- if .Values.auth.enabled }}
ARGS+=("--requirepass" "${REDIS_PASSWORD}")
ARGS+=("--masterauth" "${REDIS_PASSWORD}")
{{- else }}
ARGS+=("--protected-mode" "no")
{{- end }}
ARGS+=("--include" "/opt/bitnami/redis/etc/redis.conf")
ARGS+=("--include" "/opt/bitnami/redis/etc/master.conf")
{{- if .Values.master.extraFlags }}
{{- range .Values.master.extraFlags }}
ARGS+=({{ . | quote }})
{{- end }}
{{- end }}
{{- if .Values.master.preExecCmds }}
{{ .Values.master.preExecCmds | nindent 4 }}
{{- end }}
{{- if .Values.master.command }}
exec {{ .Values.master.command }} "${ARGS[@]}"
{{- else }}
exec redis-server "${ARGS[@]}"
{{- end }}
{{- if eq .Values.architecture "replication" }}
start-replica.sh: |
#!/bin/bash
get_port() {
hostname="$1"
type="$2"
port_var=$(echo "${hostname^^}_SERVICE_PORT_$type" | sed "s/-/_/g")
port=${!port_var}
if [ -z "$port" ]; then
case $type in
"SENTINEL")
echo {{ .Values.sentinel.containerPorts.sentinel }}
;;
"REDIS")
echo {{ .Values.master.containerPorts.redis }}
;;
esac
else
echo $port
fi
}
get_full_hostname() {
hostname="$1"
{{- if .Values.useExternalDNS.enabled }}
full_hostname="${hostname}.{{- include "redis.externalDNS.suffix" . }}"
{{- else if eq .Values.sentinel.service.type "NodePort" }}
full_hostname="${hostname}.{{- include "common.names.namespace" . }}"
{{- else }}
full_hostname="${hostname}.${HEADLESS_SERVICE}"
{{- end }}
{{- if .Values.useHostnames }}
echo "${full_hostname}"
{{- else }}
retry_count=0
until getent hosts "${full_hostname}" | awk '{ print $1; exit }' | grep .; do
if [[ $retry_count -lt {{ .Values.nameResolutionThreshold }} ]]; then
sleep {{ .Values.nameResolutionTimeout }}
else
error "IP address for ${full_hostname} not found"
exit 1
fi
((retry_count++))
done
{{- end }}
}
REDISPORT=$(get_port "$HOSTNAME" "REDIS")
HEADLESS_SERVICE="{{ template "common.names.fullname" . }}-headless.{{ include "common.names.namespace" . }}.svc.{{ .Values.clusterDomain }}"
[[ -f $REDIS_PASSWORD_FILE ]] && export REDIS_PASSWORD="$(< "${REDIS_PASSWORD_FILE}")"
[[ -f $REDIS_MASTER_PASSWORD_FILE ]] && export REDIS_MASTER_PASSWORD="$(< "${REDIS_MASTER_PASSWORD_FILE}")"
{{- if and .Values.replica.containerSecurityContext.runAsUser (eq (.Values.replica.containerSecurityContext.runAsUser | int) 0) }}
useradd redis
chown -R redis {{ .Values.replica.persistence.path }}
{{- end }}
if [[ -f /opt/bitnami/redis/mounted-etc/replica.conf ]];then
cp /opt/bitnami/redis/mounted-etc/replica.conf /opt/bitnami/redis/etc/replica.conf
fi
if [[ -f /opt/bitnami/redis/mounted-etc/redis.conf ]];then
cp /opt/bitnami/redis/mounted-etc/redis.conf /opt/bitnami/redis/etc/redis.conf
fi
echo "" >> /opt/bitnami/redis/etc/replica.conf
echo "replica-announce-port $REDISPORT" >> /opt/bitnami/redis/etc/replica.conf
echo "replica-announce-ip $(get_full_hostname "$HOSTNAME")" >> /opt/bitnami/redis/etc/replica.conf
{{- if .Values.tls.enabled }}
ARGS=("--port" "0")
ARGS+=("--tls-port" "${REDIS_TLS_PORT}")
ARGS+=("--tls-cert-file" "${REDIS_TLS_CERT_FILE}")
ARGS+=("--tls-key-file" "${REDIS_TLS_KEY_FILE}")
ARGS+=("--tls-ca-cert-file" "${REDIS_TLS_CA_FILE}")
ARGS+=("--tls-auth-clients" "${REDIS_TLS_AUTH_CLIENTS}")
ARGS+=("--tls-replication" "yes")
{{- if .Values.tls.dhParamsFilename }}
ARGS+=("--tls-dh-params-file" "${REDIS_TLS_DH_PARAMS_FILE}")
{{- end }}
{{- else }}
ARGS=("--port" "${REDIS_PORT}")
{{- end }}
ARGS+=("--replicaof" "${REDIS_MASTER_HOST}" "${REDIS_MASTER_PORT_NUMBER}")
{{- if .Values.auth.enabled }}
ARGS+=("--requirepass" "${REDIS_PASSWORD}")
ARGS+=("--masterauth" "${REDIS_MASTER_PASSWORD}")
{{- else }}
ARGS+=("--protected-mode" "no")
{{- end }}
ARGS+=("--include" "/opt/bitnami/redis/etc/redis.conf")
ARGS+=("--include" "/opt/bitnami/redis/etc/replica.conf")
{{- if .Values.replica.extraFlags }}
{{- range .Values.replica.extraFlags }}
ARGS+=({{ . | quote }})
{{- end }}
{{- end }}
{{- if .Values.replica.preExecCmds }}
{{ .Values.replica.preExecCmds | nindent 4 }}
{{- end }}
{{- if .Values.replica.command }}
exec {{ .Values.replica.command }} "${ARGS[@]}"
{{- else }}
exec redis-server "${ARGS[@]}"
{{- end }}
{{- end }}
{{- end }}
---
{{- if or .Values.sentinel.masterService.enabled .Values.sentinel.service.createMaster }}
apiVersion: v1
kind: ConfigMap
metadata:
name: {{ printf "%s-kubectl-scripts" (include "common.names.fullname" .) }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- if .Values.commonAnnotations }}
annotations: {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
data:
update-master-label.sh: |
#!/bin/bash
while true; do
while [ ! -f "/etc/shared/current" ]; do
sleep 1
done
echo "new master elected, updating label(s)..."
kubectl label pod --field-selector metadata.name="$(< "/etc/shared/current")" isMaster="true" --overwrite
if [ -f /etc/shared/previous ]; then
kubectl label pod --field-selector metadata.name="$(< "/etc/shared/previous")" isMaster="false" --overwrite
fi
rm "/etc/shared/current" "/etc/shared/previous"
done
{{- end }}

View File

@ -0,0 +1,37 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if .Values.serviceBindings.enabled }}
{{- $host := include "common.names.fullname" . }}
{{- if not .Values.sentinel.enabled }}
{{- $host = printf "%s-master" (include "common.names.fullname" .) }}
{{- end }}
{{- $port := print .Values.master.service.ports.redis }}
{{- if .Values.sentinel.enabled }}
{{- $port = print .Values.sentinel.service.ports.redis }}
{{- end }}
{{- $password := include "redis.password" . }}
apiVersion: v1
kind: Secret
metadata:
name: {{ include "common.names.fullname" . }}-svcbind
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- if .Values.commonAnnotations }}
annotations: {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
type: servicebinding.io/redis
data:
provider: {{ print "bitnami" | b64enc | quote }}
type: {{ print "redis" | b64enc | quote }}
host: {{ print $host | b64enc | quote }}
port: {{ print $port | b64enc | quote }}
password: {{ print $password | b64enc | quote }}
{{- if $password }}
uri: {{ printf "redis://:%s@%s:%s" $password $host $port | b64enc | quote }}
{{- else }}
uri: {{ printf "redis://%s:%s" $host $port | b64enc | quote }}
{{- end }}
{{- end }}

View File

@ -0,0 +1,25 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if and .Values.auth.enabled (not .Values.auth.existingSecret) (or .Values.auth.usePasswordFileFromSecret (not .Values.auth.usePasswordFiles)) -}}
apiVersion: v1
kind: Secret
metadata:
name: {{ template "common.names.fullname" . }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- if or .Values.secretAnnotations .Values.commonAnnotations }}
annotations:
{{- if .Values.secretAnnotations }}
{{- include "common.tplvalues.render" ( dict "value" .Values.secretAnnotations "context" $ ) | nindent 4 }}
{{- end }}
{{- if .Values.commonAnnotations }}
{{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
{{- end }}
type: Opaque
data:
redis-password: {{ include "redis.password" . | b64enc | quote }}
{{- end -}}

View File

@ -0,0 +1,49 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if and .Values.replica.autoscaling.enabled .Values.sentinel.enabled }}
apiVersion: {{ include "common.capabilities.hpa.apiVersion" ( dict "context" $ ) }}
kind: HorizontalPodAutoscaler
metadata:
name: {{ printf "%s-node" (include "common.names.fullname" .) }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
app.kubernetes.io/component: replica
{{- if .Values.commonAnnotations }}
annotations: {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
spec:
scaleTargetRef:
apiVersion: {{ include "common.capabilities.deployment.apiVersion" . }}
kind: StatefulSet
name: {{ printf "%s-node" (include "common.names.fullname" .) }}
minReplicas: {{ .Values.replica.autoscaling.minReplicas }}
maxReplicas: {{ .Values.replica.autoscaling.maxReplicas }}
metrics:
{{- if .Values.replica.autoscaling.targetMemory }}
- type: Resource
resource:
name: memory
{{- if semverCompare "<1.23-0" (include "common.capabilities.kubeVersion" .) }}
targetAverageUtilization: {{ .Values.replica.autoscaling.targetMemory }}
{{- else }}
target:
type: Utilization
averageUtilization: {{ .Values.replica.autoscaling.targetMemory }}
{{- end }}
{{- end }}
{{- if .Values.replica.autoscaling.targetCPU }}
- type: Resource
resource:
name: cpu
{{- if semverCompare "<1.23-0" (include "common.capabilities.kubeVersion" .) }}
targetAverageUtilization: {{ .Values.replica.autoscaling.targetCPU }}
{{- else }}
target:
type: Utilization
averageUtilization: {{ .Values.replica.autoscaling.targetCPU }}
{{- end }}
{{- end }}
{{- end }}

View File

@ -0,0 +1,67 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if and (eq .Values.architecture "replication") .Values.sentinel.enabled (eq .Values.sentinel.service.type "NodePort") (or .Release.IsUpgrade .Values.sentinel.service.nodePorts.redis ) }}
{{- range $i := until (int .Values.replica.replicaCount) }}
{{ $portsmap := (lookup "v1" "ConfigMap" (include "common.names.namespace" $) (printf "%s-%s" ( include "common.names.fullname" $ ) "ports-configmap")).data }}
{{ $sentinelport := 0}}
{{ $redisport := 0}}
{{- if $portsmap }}
{{ $sentinelport = index $portsmap (printf "%s-node-%s-%s" (include "common.names.fullname" $) (toString $i) "sentinel") }}
{{ $redisport = index $portsmap (printf "%s-node-%s-%s" (include "common.names.fullname" $) (toString $i) "redis") }}
{{- else }}
{{- end }}
apiVersion: v1
kind: Service
metadata:
name: {{ template "common.names.fullname" $ }}-node-{{ $i }}
namespace: {{ include "common.names.namespace" $ | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" $.Values.commonLabels "context" $ ) | nindent 4 }}
app.kubernetes.io/component: node
{{- if or $.Values.commonAnnotations $.Values.sentinel.service.annotations }}
{{- $annotations := include "common.tplvalues.merge" ( dict "values" ( list $.Values.sentinel.service.annotations $.Values.commonAnnotations ) "context" $ ) }}
annotations: {{- include "common.tplvalues.render" ( dict "value" $annotations "context" $) | nindent 4 }}
{{- end }}
spec:
type: NodePort
ports:
- name: sentinel
{{- if $.Values.sentinel.service.nodePorts.sentinel }}
nodePort: {{ (add $.Values.sentinel.service.nodePorts.sentinel $i 1) }}
port: {{ (add $.Values.sentinel.service.nodePorts.sentinel $i 1) }}
{{- else }}
nodePort: {{ $sentinelport }}
port: {{ $sentinelport }}
{{- end }}
protocol: TCP
targetPort: {{ $.Values.sentinel.containerPorts.sentinel }}
- name: redis
{{- if $.Values.sentinel.service.nodePorts.redis }}
nodePort: {{ (add $.Values.sentinel.service.nodePorts.redis $i 1) }}
port: {{ (add $.Values.sentinel.service.nodePorts.redis $i 1) }}
{{- else }}
nodePort: {{ $redisport }}
port: {{ $redisport }}
{{- end }}
protocol: TCP
targetPort: {{ $.Values.replica.containerPorts.redis }}
- name: sentinel-internal
nodePort: null
port: {{ $.Values.sentinel.containerPorts.sentinel }}
protocol: TCP
targetPort: {{ $.Values.sentinel.containerPorts.sentinel }}
- name: redis-internal
nodePort: null
port: {{ $.Values.replica.containerPorts.redis }}
protocol: TCP
targetPort: {{ $.Values.replica.containerPorts.redis }}
selector:
statefulset.kubernetes.io/pod-name: {{ template "common.names.fullname" $ }}-node-{{ $i }}
---
{{- end }}
{{- end }}

View File

@ -0,0 +1,27 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- $pdb := coalesce .Values.pdb .Values.replica.pdb }}
{{- if and (eq .Values.architecture "replication") .Values.sentinel.enabled $pdb.create }}
apiVersion: {{ include "common.capabilities.policy.apiVersion" . }}
kind: PodDisruptionBudget
metadata:
name: {{ printf "%s-node" (include "common.names.fullname" .) }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
app.kubernetes.io/component: node
{{- if .Values.commonAnnotations }}
annotations: {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
spec:
{{- if $pdb.minAvailable }}
minAvailable: {{ $pdb.minAvailable }}
{{- end }}
{{- if or $pdb.maxUnavailable (not $pdb.minAvailable) }}
maxUnavailable: {{ $pdb.maxUnavailable | default 1 }}
{{- end }}
selector:
matchLabels: {{- include "common.labels.matchLabels" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 6 }}
app.kubernetes.io/component: node
{{- end }}

View File

@ -0,0 +1,102 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if and (eq .Values.architecture "replication") .Values.sentinel.enabled (eq .Values.sentinel.service.type "NodePort") (not .Values.sentinel.service.nodePorts.redis ) }}
{{- /* create a list to keep track of ports we choose to use */}}
{{ $chosenports := (list ) }}
{{- /* Get list of all used nodeports */}}
{{ $usedports := (list ) }}
{{- range $index, $service := (lookup "v1" "Service" "" "").items }}
{{- range.spec.ports }}
{{- if .nodePort }}
{{- $usedports = (append $usedports .nodePort) }}
{{- end }}
{{- end }}
{{- end }}
{{- /*
comments that start with # are rendered in the output when you debug, so you can less and search for them
Vars in the comment will be rendered out, so you can check their value this way.
https://helm.sh/docs/chart_best_practices/templates/#comments-yaml-comments-vs-template-comments
remove the template comments and leave the yaml comments to help debug
*/}}
{{- /* Sort the list */}}
{{ $usedports = $usedports | sortAlpha }}
#usedports {{ $usedports }}
{{- /* How many nodeports per service do we want to create, except for the main service which is always two */}}
{{ $numberofPortsPerNodeService := 2 }}
{{- /* for every nodeport we want, loop though the used ports to get an unused port */}}
{{- range $j := until (int (add (mul (int .Values.replica.replicaCount) $numberofPortsPerNodeService) 2)) }}
{{- /* #j={{ $j }} */}}
{{- $nodeport := (add $j 30000) }}
{{- $nodeportfound := false }}
{{- range $i := $usedports }}
{{- /* #i={{ $i }}
#nodeport={{ $nodeport }}
#usedports={{ $usedports }} */}}
{{- if and (has (toString $nodeport) $usedports) (eq $nodeportfound false) }}
{{- /* nodeport conflicts with in use */}}
{{- $nodeport = (add $nodeport 1) }}
{{- else if and ( has $nodeport $chosenports) (eq $nodeportfound false) }}
{{- /* nodeport already chosen, try another */}}
{{- $nodeport = (add $nodeport 1) }}
{{- else if (eq $nodeportfound false) }}
{{- /* nodeport free to use: not already claimed and not in use */}}
{{- /* select nodeport, and place into usedports */}}
{{- $chosenports = (append $chosenports $nodeport) }}
{{- $nodeportfound = true }}
{{- else }}
{{- /* nodeport has already been chosen and locked in, just work through the rest of the list to get to the next nodeport selection */}}
{{- end }}
{{- end }}
{{- if (eq $nodeportfound false) }}
{{- $chosenports = (append $chosenports $nodeport) }}
{{- end }}
{{- end }}
{{- /* print the usedports and chosenports for debugging */}}
#usedports {{ $usedports }}
#chosenports {{ $chosenports }}}}
---
apiVersion: v1
kind: ConfigMap
metadata:
name: {{ template "common.names.fullname" . }}-ports-configmap
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- if .Values.commonAnnotations }}
annotations:
{{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
data:
{{ $portsmap := (lookup "v1" "ConfigMap" (include "common.names.namespace" .) (printf "%s-%s" ( include "common.names.fullname" . ) "ports-configmap")).data }}
{{- if $portsmap }}
{{- /* configmap already exists, do not install again */ -}}
{{- range $name, $value := $portsmap }}
"{{ $name }}": "{{ $value }}"
{{- end }}
{{- else }}
{{- /* configmap being set for first time */ -}}
{{- range $index, $port := $chosenports }}
{{- $nodenumber := (floor (div $index 2)) }}
{{- if (eq $index 0) }}
"{{ template "common.names.fullname" $ }}-sentinel": "{{ $port }}"
{{- else if (eq $index 1) }}
"{{ template "common.names.fullname" $ }}-redis": "{{ $port }}"
{{- else if (eq (mod $index 2) 0) }}
"{{ template "common.names.fullname" $ }}-node-{{ (sub $nodenumber 1) }}-sentinel": "{{ $port }}"
{{- else if (eq (mod $index 2) 1) }}
"{{ template "common.names.fullname" $ }}-node-{{ (sub $nodenumber 1) }}-redis": "{{ $port }}"
{{- end }}
{{- end }}
{{- end }}
{{- end }}

View File

@ -0,0 +1,160 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if or .Release.IsUpgrade (ne .Values.sentinel.service.type "NodePort") .Values.sentinel.service.nodePorts.redis -}}
{{- if and (eq .Values.architecture "replication") .Values.sentinel.enabled }}
{{ $portsmap := (lookup "v1" "ConfigMap" (include "common.names.namespace" .) (printf "%s-%s" ( include "common.names.fullname" . ) "ports-configmap")).data }}
{{ $sentinelport := 0}}
{{ $redisport := 0}}
{{- if $portsmap }}
{{ $sentinelport = index $portsmap (printf "%s-%s" (include "common.names.fullname" $) "sentinel") }}
{{ $redisport = index $portsmap (printf "%s-%s" (include "common.names.fullname" $) "redis") }}
{{- else }}
{{- end }}
apiVersion: v1
kind: Service
metadata:
name: {{ template "common.names.fullname" . }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
app.kubernetes.io/component: node
{{- if or .Values.sentinel.service.annotations .Values.commonAnnotations }}
{{- $annotations := include "common.tplvalues.merge" ( dict "values" ( list .Values.sentinel.service.annotations .Values.commonAnnotations ) "context" . ) }}
annotations: {{- include "common.tplvalues.render" ( dict "value" $annotations "context" $) | nindent 4 }}
{{- end }}
spec:
type: {{ .Values.sentinel.service.type }}
{{- if or (eq .Values.sentinel.service.type "LoadBalancer") (eq .Values.sentinel.service.type "NodePort") }}
externalTrafficPolicy: {{ .Values.sentinel.service.externalTrafficPolicy | quote }}
{{- end }}
{{- if and (eq .Values.sentinel.service.type "LoadBalancer") (not (empty .Values.sentinel.service.loadBalancerIP)) }}
loadBalancerIP: {{ .Values.sentinel.service.loadBalancerIP }}
{{- end }}
{{- if and (eq .Values.sentinel.service.type "LoadBalancer") .Values.sentinel.service.loadBalancerClass }}
loadBalancerClass: {{ .Values.sentinel.service.loadBalancerClass }}
{{- end }}
{{- if and (eq .Values.sentinel.service.type "LoadBalancer") (not (empty .Values.sentinel.service.loadBalancerSourceRanges)) }}
loadBalancerSourceRanges: {{ toYaml .Values.sentinel.service.loadBalancerSourceRanges | nindent 4 }}
{{- end }}
{{- if and .Values.sentinel.service.clusterIP (eq .Values.sentinel.service.type "ClusterIP") }}
clusterIP: {{ .Values.sentinel.service.clusterIP }}
{{- end }}
{{- if .Values.sentinel.service.sessionAffinity }}
sessionAffinity: {{ .Values.sentinel.service.sessionAffinity }}
{{- end }}
{{- if .Values.sentinel.service.sessionAffinityConfig }}
sessionAffinityConfig: {{- include "common.tplvalues.render" (dict "value" .Values.sentinel.service.sessionAffinityConfig "context" $) | nindent 4 }}
{{- end }}
ports:
- name: tcp-redis
{{- if and (or (eq .Values.sentinel.service.type "NodePort") (eq .Values.sentinel.service.type "LoadBalancer")) .Values.sentinel.service.nodePorts.redis }}
port: {{ .Values.sentinel.service.nodePorts.redis }}
{{- else if eq .Values.sentinel.service.type "NodePort" }}
port: {{ $redisport }}
{{- else}}
port: {{ .Values.sentinel.service.ports.redis }}
{{- end }}
targetPort: {{ .Values.replica.containerPorts.redis }}
{{- if and (or (eq .Values.sentinel.service.type "NodePort") (eq .Values.sentinel.service.type "LoadBalancer")) .Values.sentinel.service.nodePorts.redis }}
nodePort: {{ .Values.sentinel.service.nodePorts.redis }}
{{- else if eq .Values.sentinel.service.type "ClusterIP" }}
nodePort: null
{{- else if eq .Values.sentinel.service.type "NodePort" }}
nodePort: {{ $redisport }}
{{- end }}
- name: tcp-sentinel
{{- if and (or (eq .Values.sentinel.service.type "NodePort") (eq .Values.sentinel.service.type "LoadBalancer")) .Values.sentinel.service.nodePorts.sentinel }}
port: {{ .Values.sentinel.service.nodePorts.sentinel }}
{{- else if eq .Values.sentinel.service.type "NodePort" }}
port: {{ $sentinelport }}
{{- else }}
port: {{ .Values.sentinel.service.ports.sentinel }}
{{- end }}
targetPort: {{ .Values.sentinel.containerPorts.sentinel }}
{{- if and (or (eq .Values.sentinel.service.type "NodePort") (eq .Values.sentinel.service.type "LoadBalancer")) .Values.sentinel.service.nodePorts.sentinel }}
nodePort: {{ .Values.sentinel.service.nodePorts.sentinel }}
{{- else if eq .Values.sentinel.service.type "ClusterIP" }}
nodePort: null
{{- else if eq .Values.sentinel.service.type "NodePort" }}
nodePort: {{ $sentinelport }}
{{- end }}
{{- if eq .Values.sentinel.service.type "NodePort" }}
- name: sentinel-internal
nodePort: null
port: {{ .Values.sentinel.containerPorts.sentinel }}
protocol: TCP
targetPort: {{ .Values.sentinel.containerPorts.sentinel }}
- name: redis-internal
nodePort: null
port: {{ .Values.replica.containerPorts.redis }}
protocol: TCP
targetPort: {{ .Values.replica.containerPorts.redis }}
{{- end }}
{{- if .Values.sentinel.service.extraPorts }}
{{- include "common.tplvalues.render" (dict "value" .Values.sentinel.service.extraPorts "context" $) | nindent 4 }}
{{- end }}
{{- $podLabels := include "common.tplvalues.merge" ( dict "values" ( list .Values.replica.podLabels .Values.commonLabels ) "context" . ) }}
selector: {{- include "common.labels.matchLabels" ( dict "customLabels" $podLabels "context" $ ) | nindent 4 }}
app.kubernetes.io/component: node
{{- $masterServiceConfig := ternary .Values.sentinel.masterService .Values.sentinel.service .Values.sentinel.masterService.enabled -}}
{{- if and .Values.sentinel.enabled (or .Values.sentinel.masterService.enabled .Values.sentinel.service.createMaster) }}
---
apiVersion: v1
kind: Service
metadata:
name: "{{ template "common.names.fullname" . }}-master"
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
app.kubernetes.io/component: node
{{- if or $masterServiceConfig.annotations .Values.commonAnnotations }}
{{- $annotations := include "common.tplvalues.merge" ( dict "values" ( list ($masterServiceConfig.annotations) .Values.commonAnnotations ) "context" . ) }}
annotations: {{- include "common.tplvalues.render" ( dict "value" $annotations "context" $) | nindent 4 }}
{{- end }}
spec:
type: {{ $masterServiceConfig.type }}
{{- if or (eq $masterServiceConfig.type "LoadBalancer") (eq $masterServiceConfig.type "NodePort") }}
externalTrafficPolicy: {{ $masterServiceConfig.externalTrafficPolicy | quote }}
{{- end }}
{{- if and (eq $masterServiceConfig.type "LoadBalancer") (not (empty ($masterServiceConfig.loadBalancerIP))) }}
loadBalancerIP: {{ $masterServiceConfig.loadBalancerIP }}
{{- end }}
{{- if and (eq $masterServiceConfig.type "LoadBalancer") (not (empty ($masterServiceConfig.loadBalancerClass))) }}
loadBalancerClass: {{ $masterServiceConfig.loadBalancerClass }}
{{- end }}
{{- if and (eq $masterServiceConfig.type "LoadBalancer") (not (empty ($masterServiceConfig.loadBalancerSourceRanges))) }}
loadBalancerSourceRanges: {{ toYaml ($masterServiceConfig.loadBalancerSourceRanges) | nindent 4 }}
{{- end }}
{{- if and (eq $masterServiceConfig.type "ClusterIP") (not (empty ($masterServiceConfig.clusterIP))) }}
clusterIP: {{ $masterServiceConfig.clusterIP }}
{{- end }}
sessionAffinity: {{ $masterServiceConfig.sessionAffinity }}
{{- if $masterServiceConfig.sessionAffinityConfig }}
sessionAffinityConfig: {{- include "common.tplvalues.render" (dict "value" ($masterServiceConfig.sessionAffinityConfig) "context" $) | nindent 4 }}
{{- end }}
ports:
- name: tcp-redis
{{- if and (or (eq $masterServiceConfig.type "NodePort") (eq $masterServiceConfig.type "LoadBalancer")) ($masterServiceConfig.nodePorts.redis) }}
port: {{ $masterServiceConfig.nodePorts.redis }}
{{- else if eq $masterServiceConfig.type "NodePort" }}
port: {{ $redisport }}
{{- else }}
port: {{ $masterServiceConfig.ports.redis }}
{{- end }}
targetPort: {{ .Values.replica.containerPorts.redis }}
{{- if and (or (eq $masterServiceConfig.type "NodePort") (eq $masterServiceConfig.type "LoadBalancer")) ($masterServiceConfig.nodePorts.redis) }}
nodePort: {{ $masterServiceConfig.nodePorts.redis }}
{{- else if eq $masterServiceConfig.type "ClusterIP" }}
nodePort: null
{{- else if eq $masterServiceConfig.type "NodePort" }}
nodePort: {{ $redisport }}
{{- end }}
selector: {{- include "common.labels.matchLabels" ( dict "customLabels" $podLabels "context" $ ) | nindent 4 }}
isMaster: "true"
{{- end }}
{{- end }}
{{- end }}

View File

@ -0,0 +1,831 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if or .Release.IsUpgrade (ne .Values.sentinel.service.type "NodePort") .Values.sentinel.service.nodePorts.redis -}}
{{- if and (eq .Values.architecture "replication") .Values.sentinel.enabled }}
apiVersion: {{ include "common.capabilities.statefulset.apiVersion" . }}
kind: StatefulSet
metadata:
name: {{ printf "%s-node" (include "common.names.fullname" .) }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
app.kubernetes.io/component: node
{{- if or .Values.commonAnnotations .Values.sentinel.annotations }}
{{- $annotations := include "common.tplvalues.merge" ( dict "values" ( list .Values.sentinel.annotations .Values.commonAnnotations ) "context" . ) }}
annotations: {{- include "common.tplvalues.render" ( dict "value" $annotations "context" $) | nindent 4 }}
{{- end }}
spec:
replicas: {{ .Values.replica.replicaCount }}
revisionHistoryLimit: {{ .Values.replica.revisionHistoryLimit }}
{{- $podLabels := include "common.tplvalues.merge" ( dict "values" ( list .Values.replica.podLabels .Values.commonLabels ) "context" . ) }}
selector:
matchLabels: {{- include "common.labels.matchLabels" ( dict "customLabels" $podLabels "context" $ ) | nindent 6 }}
app.kubernetes.io/component: node
serviceName: {{ printf "%s-headless" (include "common.names.fullname" .) }}
{{- if .Values.replica.updateStrategy }}
updateStrategy: {{- toYaml .Values.replica.updateStrategy | nindent 4 }}
{{- end }}
{{- if and .Values.replica.minReadySeconds (semverCompare ">= 1.23-0" (include "common.capabilities.kubeVersion" .)) }}
minReadySeconds: {{ .Values.replica.minReadySeconds }}
{{- end }}
{{- if .Values.replica.podManagementPolicy }}
podManagementPolicy: {{ .Values.replica.podManagementPolicy | quote }}
{{- end }}
template:
metadata:
labels: {{- include "common.labels.standard" ( dict "customLabels" $podLabels "context" $ ) | nindent 8 }}
app.kubernetes.io/component: node
{{- if and .Values.metrics.enabled .Values.metrics.podLabels }}
{{- include "common.tplvalues.render" ( dict "value" .Values.metrics.podLabels "context" $ ) | nindent 8 }}
{{- end }}
annotations:
{{- if (include "redis.createConfigmap" .) }}
checksum/configmap: {{ pick ( include (print $.Template.BasePath "/configmap.yaml") . | fromYaml ) "data" | toYaml | sha256sum }}
{{- end }}
checksum/health: {{ pick ( include (print $.Template.BasePath "/health-configmap.yaml") . | fromYaml ) "data" | toYaml | sha256sum }}
checksum/scripts: {{ pick ( include (print $.Template.BasePath "/scripts-configmap.yaml") . | fromYaml ) "data" | toYaml | sha256sum }}
checksum/secret: {{ pick ( include (print $.Template.BasePath "/secret.yaml") . | fromYaml ) "data" | toYaml | sha256sum }}
{{- if .Values.replica.podAnnotations }}
{{- include "common.tplvalues.render" ( dict "value" .Values.replica.podAnnotations "context" $ ) | nindent 8 }}
{{- end }}
{{- if and .Values.metrics.enabled .Values.metrics.podAnnotations }}
{{- include "common.tplvalues.render" ( dict "value" .Values.metrics.podAnnotations "context" $ ) | nindent 8 }}
{{- end }}
spec:
{{- include "redis.imagePullSecrets" . | nindent 6 }}
automountServiceAccountToken: {{ .Values.replica.automountServiceAccountToken }}
{{- if .Values.replica.hostAliases }}
hostAliases: {{- include "common.tplvalues.render" (dict "value" .Values.replica.hostAliases "context" $) | nindent 8 }}
{{- end }}
{{- if .Values.replica.podSecurityContext.enabled }}
securityContext: {{- include "common.compatibility.renderSecurityContext" (dict "secContext" .Values.replica.podSecurityContext "context" $) | nindent 8 }}
{{- end }}
serviceAccountName: {{ template "redis.serviceAccountName" . }}
{{- if .Values.replica.priorityClassName }}
priorityClassName: {{ .Values.replica.priorityClassName | quote }}
{{- end }}
{{- if .Values.replica.affinity }}
affinity: {{- include "common.tplvalues.render" (dict "value" .Values.replica.affinity "context" $) | nindent 8 }}
{{- else }}
affinity:
podAffinity: {{- include "common.affinities.pods" (dict "type" .Values.replica.podAffinityPreset "component" "node" "customLabels" $podLabels "context" $) | nindent 10 }}
podAntiAffinity: {{- include "common.affinities.pods" (dict "type" .Values.replica.podAntiAffinityPreset "component" "node" "customLabels" $podLabels "context" $) | nindent 10 }}
nodeAffinity: {{- include "common.affinities.nodes" (dict "type" .Values.replica.nodeAffinityPreset.type "key" .Values.replica.nodeAffinityPreset.key "values" .Values.replica.nodeAffinityPreset.values) | nindent 10 }}
{{- end }}
{{- if .Values.replica.nodeSelector }}
nodeSelector: {{- include "common.tplvalues.render" (dict "value" .Values.replica.nodeSelector "context" $) | nindent 8 }}
{{- end }}
{{- if .Values.replica.tolerations }}
tolerations: {{- include "common.tplvalues.render" (dict "value" .Values.replica.tolerations "context" $) | nindent 8 }}
{{- end }}
{{- if .Values.replica.topologySpreadConstraints }}
topologySpreadConstraints: {{- include "common.tplvalues.render" (dict "value" .Values.replica.topologySpreadConstraints "context" $) | nindent 8 }}
{{- end }}
{{- if .Values.replica.shareProcessNamespace }}
shareProcessNamespace: {{ .Values.replica.shareProcessNamespace }}
{{- end }}
{{- if .Values.replica.schedulerName }}
schedulerName: {{ .Values.replica.schedulerName | quote }}
{{- end }}
{{- if .Values.replica.dnsPolicy }}
dnsPolicy: {{ .Values.replica.dnsPolicy }}
{{- end }}
{{- if .Values.replica.dnsConfig }}
dnsConfig: {{- include "common.tplvalues.render" (dict "value" .Values.replica.dnsConfig "context" $) | nindent 8 }}
{{- end }}
enableServiceLinks: {{ .Values.sentinel.enableServiceLinks }}
terminationGracePeriodSeconds: {{ .Values.sentinel.terminationGracePeriodSeconds }}
containers:
- name: redis
image: {{ template "redis.image" . }}
imagePullPolicy: {{ .Values.image.pullPolicy | quote }}
{{- if not .Values.diagnosticMode.enabled }}
{{- if .Values.replica.lifecycleHooks }}
lifecycle: {{- include "common.tplvalues.render" (dict "value" .Values.replica.lifecycleHooks "context" $) | nindent 12 }}
{{- else }}
lifecycle:
preStop:
exec:
command:
- /bin/bash
- -c
- /opt/bitnami/scripts/start-scripts/prestop-redis.sh
{{- end }}
{{- end }}
{{- if .Values.replica.containerSecurityContext.enabled }}
securityContext: {{- include "common.compatibility.renderSecurityContext" (dict "secContext" .Values.replica.containerSecurityContext "context" $) | nindent 12 }}
{{- end }}
{{- if .Values.diagnosticMode.enabled }}
command: {{- include "common.tplvalues.render" (dict "value" .Values.diagnosticMode.command "context" $) | nindent 12 }}
{{- else if .Values.replica.command }}
command: {{- include "common.tplvalues.render" (dict "value" .Values.replica.command "context" $) | nindent 12 }}
{{- else }}
command:
- /bin/bash
{{- end }}
{{- if .Values.diagnosticMode.enabled }}
args: {{- include "common.tplvalues.render" (dict "value" .Values.diagnosticMode.args "context" $) | nindent 12 }}
{{- else if .Values.replica.args }}
args: {{- include "common.tplvalues.render" (dict "value" .Values.replica.args "context" $) | nindent 12 }}
{{- else }}
args:
- -c
- /opt/bitnami/scripts/start-scripts/start-node.sh
{{- end }}
env:
- name: BITNAMI_DEBUG
value: {{ ternary "true" "false" (or .Values.image.debug .Values.diagnosticMode.enabled) | quote }}
- name: REDIS_MASTER_PORT_NUMBER
value: {{ .Values.replica.containerPorts.redis | quote }}
- name: ALLOW_EMPTY_PASSWORD
value: {{ ternary "no" "yes" .Values.auth.enabled | quote }}
{{- if .Values.auth.enabled }}
{{- if .Values.auth.usePasswordFiles }}
- name: REDIS_PASSWORD_FILE
value: "/opt/bitnami/redis/secrets/redis-password"
- name: REDIS_MASTER_PASSWORD_FILE
value: "/opt/bitnami/redis/secrets/redis-password"
{{- else }}
- name: REDIS_PASSWORD
valueFrom:
secretKeyRef:
name: {{ template "redis.secretName" . }}
key: {{ template "redis.secretPasswordKey" . }}
- name: REDIS_MASTER_PASSWORD
valueFrom:
secretKeyRef:
name: {{ template "redis.secretName" . }}
key: {{ template "redis.secretPasswordKey" . }}
{{- end }}
{{- end }}
- name: REDIS_TLS_ENABLED
value: {{ ternary "yes" "no" .Values.tls.enabled | quote }}
{{- if .Values.tls.enabled }}
- name: REDIS_TLS_PORT
value: {{ .Values.replica.containerPorts.redis | quote }}
- name: REDIS_TLS_AUTH_CLIENTS
value: {{ ternary "yes" "no" .Values.tls.authClients | quote }}
- name: REDIS_TLS_CERT_FILE
value: {{ template "redis.tlsCert" . }}
- name: REDIS_TLS_KEY_FILE
value: {{ template "redis.tlsCertKey" . }}
- name: REDIS_TLS_CA_FILE
value: {{ template "redis.tlsCACert" . }}
{{- if .Values.tls.dhParamsFilename }}
- name: REDIS_TLS_DH_PARAMS_FILE
value: {{ template "redis.tlsDHParams" . }}
{{- end }}
{{- else }}
- name: REDIS_PORT
value: {{ .Values.replica.containerPorts.redis | quote }}
{{- end }}
- name: REDIS_SENTINEL_TLS_ENABLED
value: {{ ternary "yes" "no" .Values.tls.enabled | quote }}
{{- if .Values.tls.enabled }}
- name: REDIS_SENTINEL_TLS_PORT_NUMBER
value: {{ .Values.sentinel.containerPorts.sentinel | quote }}
- name: REDIS_SENTINEL_TLS_AUTH_CLIENTS
value: {{ ternary "yes" "no" .Values.tls.authClients | quote }}
- name: REDIS_SENTINEL_TLS_CERT_FILE
value: {{ template "redis.tlsCert" . }}
- name: REDIS_SENTINEL_TLS_KEY_FILE
value: {{ template "redis.tlsCertKey" . }}
- name: REDIS_SENTINEL_TLS_CA_FILE
value: {{ template "redis.tlsCACert" . }}
{{- if .Values.tls.dhParamsFilename }}
- name: REDIS_SENTINEL_TLS_DH_PARAMS_FILE
value: {{ template "redis.tlsDHParams" . }}
{{- end }}
{{- else }}
- name: REDIS_SENTINEL_PORT
value: {{ .Values.sentinel.containerPorts.sentinel | quote }}
{{- end }}
- name: REDIS_DATA_DIR
value: {{ .Values.replica.persistence.path }}
{{- if .Values.replica.externalMaster.enabled }}
- name: REDIS_EXTERNAL_MASTER_HOST
value: {{ .Values.replica.externalMaster.host | quote }}
- name: REDIS_EXTERNAL_MASTER_PORT
value: {{ .Values.replica.externalMaster.port | quote }}
{{- end }}
{{- if .Values.replica.extraEnvVars }}
{{- include "common.tplvalues.render" ( dict "value" .Values.replica.extraEnvVars "context" $ ) | nindent 12 }}
{{- end }}
{{- if or .Values.replica.extraEnvVarsCM .Values.replica.extraEnvVarsSecret }}
envFrom:
{{- if .Values.replica.extraEnvVarsCM }}
- configMapRef:
name: {{ .Values.replica.extraEnvVarsCM }}
{{- end }}
{{- if .Values.replica.extraEnvVarsSecret }}
- secretRef:
name: {{ .Values.replica.extraEnvVarsSecret }}
{{- end }}
{{- end }}
ports:
- name: redis
containerPort: {{ .Values.replica.containerPorts.redis }}
{{- if not .Values.diagnosticMode.enabled }}
{{- if .Values.replica.customStartupProbe }}
startupProbe: {{- include "common.tplvalues.render" (dict "value" .Values.replica.customStartupProbe "context" $) | nindent 12 }}
{{- else if .Values.replica.startupProbe.enabled }}
startupProbe: {{- include "common.tplvalues.render" (dict "value" (omit .Values.replica.startupProbe "enabled") "context" $) | nindent 12 }}
exec:
command:
- sh
- -c
- /health/ping_liveness_local.sh {{ .Values.replica.livenessProbe.timeoutSeconds }}
{{- end }}
{{- if .Values.replica.customLivenessProbe }}
livenessProbe: {{- include "common.tplvalues.render" (dict "value" .Values.replica.customLivenessProbe "context" $) | nindent 12 }}
{{- else if .Values.replica.livenessProbe.enabled }}
livenessProbe:
initialDelaySeconds: {{ .Values.replica.livenessProbe.initialDelaySeconds }}
periodSeconds: {{ .Values.replica.livenessProbe.periodSeconds }}
timeoutSeconds: {{ .Values.replica.livenessProbe.timeoutSeconds }}
successThreshold: {{ .Values.replica.livenessProbe.successThreshold }}
failureThreshold: {{ .Values.replica.livenessProbe.failureThreshold }}
exec:
command:
- sh
- -c
- /health/ping_liveness_local.sh {{ .Values.replica.livenessProbe.timeoutSeconds }}
{{- end }}
{{- if .Values.replica.customReadinessProbe }}
readinessProbe: {{- include "common.tplvalues.render" (dict "value" .Values.replica.customReadinessProbe "context" $) | nindent 12 }}
{{- else if .Values.replica.readinessProbe.enabled }}
readinessProbe:
initialDelaySeconds: {{ .Values.replica.readinessProbe.initialDelaySeconds }}
periodSeconds: {{ .Values.replica.readinessProbe.periodSeconds }}
timeoutSeconds: {{ .Values.replica.readinessProbe.timeoutSeconds }}
successThreshold: {{ .Values.replica.readinessProbe.successThreshold }}
failureThreshold: {{ .Values.replica.readinessProbe.failureThreshold }}
exec:
command:
- sh
- -c
- /health/ping_readiness_local.sh {{ .Values.replica.readinessProbe.timeoutSeconds }}
{{- end }}
{{- end }}
{{- if .Values.replica.resources }}
resources: {{- toYaml .Values.replica.resources | nindent 12 }}
{{- else if ne .Values.replica.resourcesPreset "none" }}
resources: {{- include "common.resources.preset" (dict "type" .Values.replica.resourcesPreset) | nindent 12 }}
{{- end }}
volumeMounts:
- name: start-scripts
mountPath: /opt/bitnami/scripts/start-scripts
- name: health
mountPath: /health
- name: sentinel-data
mountPath: /opt/bitnami/redis-sentinel/etc
{{- if .Values.auth.usePasswordFiles }}
- name: redis-password
mountPath: /opt/bitnami/redis/secrets/
{{- end }}
- name: redis-data
mountPath: {{ .Values.replica.persistence.path }}
{{- if .Values.replica.persistence.subPath }}
subPath: {{ .Values.replica.persistence.subPath }}
{{- else if .Values.replica.persistence.subPathExpr }}
subPathExpr: {{ .Values.replica.persistence.subPathExpr }}
{{- end }}
- name: config
mountPath: /opt/bitnami/redis/mounted-etc
- name: empty-dir
mountPath: /opt/bitnami/redis/etc
subPath: app-conf-dir
- name: empty-dir
mountPath: /tmp
subPath: tmp-dir
{{- if .Values.tls.enabled }}
- name: redis-certificates
mountPath: /opt/bitnami/redis/certs
readOnly: true
{{- end }}
{{- if .Values.replica.extraVolumeMounts }}
{{- include "common.tplvalues.render" ( dict "value" .Values.replica.extraVolumeMounts "context" $ ) | nindent 12 }}
{{- end }}
- name: sentinel
image: {{ template "redis.sentinel.image" . }}
imagePullPolicy: {{ .Values.sentinel.image.pullPolicy | quote }}
{{- if not .Values.diagnosticMode.enabled }}
{{- if .Values.sentinel.lifecycleHooks }}
lifecycle: {{- include "common.tplvalues.render" (dict "value" .Values.sentinel.lifecycleHooks "context" $) | nindent 12 }}
{{- else }}
lifecycle:
preStop:
exec:
command:
- /bin/bash
- -c
- /opt/bitnami/scripts/start-scripts/prestop-sentinel.sh
{{- end }}
{{- end }}
{{- if .Values.sentinel.containerSecurityContext.enabled }}
securityContext: {{- include "common.compatibility.renderSecurityContext" (dict "secContext" .Values.sentinel.containerSecurityContext "context" $) | nindent 12 }}
{{- end }}
{{- if .Values.diagnosticMode.enabled }}
command: {{- include "common.tplvalues.render" (dict "value" .Values.diagnosticMode.command "context" $) | nindent 12 }}
{{- else if .Values.sentinel.command }}
command: {{- include "common.tplvalues.render" (dict "value" .Values.sentinel.command "context" $) | nindent 12 }}
{{- else }}
command:
- /bin/bash
{{- end }}
{{- if .Values.diagnosticMode.enabled }}
args: {{- include "common.tplvalues.render" (dict "value" .Values.diagnosticMode.args "context" $) | nindent 12 }}
{{- else if .Values.sentinel.args }}
args: {{- include "common.tplvalues.render" (dict "value" .Values.sentinel.args "context" $) | nindent 12 }}
{{- else }}
args:
- -c
- /opt/bitnami/scripts/start-scripts/start-sentinel.sh
{{- end }}
env:
- name: BITNAMI_DEBUG
value: {{ ternary "true" "false" (or .Values.sentinel.image.debug .Values.diagnosticMode.enabled) | quote }}
{{- if .Values.auth.enabled }}
{{- if .Values.auth.usePasswordFiles }}
- name: REDIS_PASSWORD_FILE
value: "/opt/bitnami/redis/secrets/redis-password"
{{- else }}
- name: REDIS_PASSWORD
valueFrom:
secretKeyRef:
name: {{ template "redis.secretName" . }}
key: {{ template "redis.secretPasswordKey" . }}
{{- end }}
{{- else }}
- name: ALLOW_EMPTY_PASSWORD
value: "yes"
{{- end }}
- name: REDIS_SENTINEL_TLS_ENABLED
value: {{ ternary "yes" "no" .Values.tls.enabled | quote }}
{{- if .Values.tls.enabled }}
- name: REDIS_SENTINEL_TLS_PORT_NUMBER
value: {{ .Values.sentinel.containerPorts.sentinel | quote }}
- name: REDIS_SENTINEL_TLS_AUTH_CLIENTS
value: {{ ternary "yes" "no" .Values.tls.authClients | quote }}
- name: REDIS_SENTINEL_TLS_CERT_FILE
value: {{ template "redis.tlsCert" . }}
- name: REDIS_SENTINEL_TLS_KEY_FILE
value: {{ template "redis.tlsCertKey" . }}
- name: REDIS_SENTINEL_TLS_CA_FILE
value: {{ template "redis.tlsCACert" . }}
{{- if .Values.tls.dhParamsFilename }}
- name: REDIS_SENTINEL_TLS_DH_PARAMS_FILE
value: {{ template "redis.tlsDHParams" . }}
{{- end }}
{{- else }}
- name: REDIS_SENTINEL_PORT
value: {{ .Values.sentinel.containerPorts.sentinel | quote }}
{{- end }}
{{- if .Values.sentinel.externalMaster.enabled }}
- name: REDIS_EXTERNAL_MASTER_HOST
value: {{ .Values.sentinel.externalMaster.host | quote }}
- name: REDIS_EXTERNAL_MASTER_PORT
value: {{ .Values.sentinel.externalMaster.port | quote }}
{{- end }}
{{- if .Values.sentinel.extraEnvVars }}
{{- include "common.tplvalues.render" ( dict "value" .Values.sentinel.extraEnvVars "context" $ ) | nindent 12 }}
{{- end }}
{{- if or .Values.sentinel.extraEnvVarsCM .Values.sentinel.extraEnvVarsSecret }}
envFrom:
{{- if .Values.sentinel.extraEnvVarsCM }}
- configMapRef:
name: {{ .Values.sentinel.extraEnvVarsCM }}
{{- end }}
{{- if .Values.sentinel.extraEnvVarsSecret }}
- secretRef:
name: {{ .Values.sentinel.extraEnvVarsSecret }}
{{- end }}
{{- end }}
ports:
- name: redis-sentinel
containerPort: {{ .Values.sentinel.containerPorts.sentinel }}
{{- if not .Values.diagnosticMode.enabled }}
{{- if .Values.sentinel.customStartupProbe }}
startupProbe: {{- include "common.tplvalues.render" (dict "value" .Values.sentinel.customStartupProbe "context" $) | nindent 12 }}
{{- else if .Values.sentinel.startupProbe.enabled }}
startupProbe: {{- include "common.tplvalues.render" (dict "value" (omit .Values.sentinel.startupProbe "enabled") "context" $) | nindent 12 }}
exec:
command:
- sh
- -c
- /health/ping_sentinel.sh {{ .Values.sentinel.livenessProbe.timeoutSeconds }}
{{- end }}
{{- if .Values.sentinel.customLivenessProbe }}
livenessProbe: {{- include "common.tplvalues.render" (dict "value" .Values.sentinel.customLivenessProbe "context" $) | nindent 12 }}
{{- else if .Values.sentinel.livenessProbe.enabled }}
livenessProbe:
initialDelaySeconds: {{ .Values.sentinel.livenessProbe.initialDelaySeconds }}
periodSeconds: {{ .Values.sentinel.livenessProbe.periodSeconds }}
timeoutSeconds: {{ .Values.sentinel.livenessProbe.timeoutSeconds }}
successThreshold: {{ .Values.sentinel.livenessProbe.successThreshold }}
failureThreshold: {{ .Values.sentinel.livenessProbe.failureThreshold }}
exec:
command:
- sh
- -c
- /health/ping_sentinel.sh {{ .Values.sentinel.livenessProbe.timeoutSeconds }}
{{- end }}
{{- end }}
{{- if not .Values.diagnosticMode.enabled }}
{{- if .Values.sentinel.customReadinessProbe }}
readinessProbe: {{- include "common.tplvalues.render" (dict "value" .Values.sentinel.customReadinessProbe "context" $) | nindent 12 }}
{{- else if .Values.sentinel.readinessProbe.enabled }}
readinessProbe:
initialDelaySeconds: {{ .Values.sentinel.readinessProbe.initialDelaySeconds }}
periodSeconds: {{ .Values.sentinel.readinessProbe.periodSeconds }}
timeoutSeconds: {{ .Values.sentinel.readinessProbe.timeoutSeconds }}
successThreshold: {{ .Values.sentinel.readinessProbe.successThreshold }}
failureThreshold: {{ .Values.sentinel.readinessProbe.failureThreshold }}
exec:
command:
- sh
- -c
- /health/ping_sentinel.sh {{ .Values.sentinel.readinessProbe.timeoutSeconds }}
{{- end }}
{{- end }}
{{- if .Values.sentinel.resources }}
resources: {{- toYaml .Values.sentinel.resources | nindent 12 }}
{{- else if ne .Values.sentinel.resourcesPreset "none" }}
resources: {{- include "common.resources.preset" (dict "type" .Values.sentinel.resourcesPreset) | nindent 12 }}
{{- end }}
volumeMounts:
- name: empty-dir
mountPath: /tmp
subPath: tmp-dir
- name: start-scripts
mountPath: /opt/bitnami/scripts/start-scripts
- name: health
mountPath: /health
{{- if or .Values.sentinel.masterService.enabled .Values.sentinel.service.createMaster}}
- name: kubectl-shared
mountPath: /etc/shared
{{- end }}
- name: sentinel-data
mountPath: /opt/bitnami/redis-sentinel/etc
{{- if .Values.auth.usePasswordFiles }}
- name: redis-password
mountPath: /opt/bitnami/redis/secrets/
{{- end }}
- name: redis-data
mountPath: {{ .Values.replica.persistence.path }}
{{- if .Values.replica.persistence.subPath }}
subPath: {{ .Values.replica.persistence.subPath }}
{{- else if .Values.replica.persistence.subPathExpr }}
subPathExpr: {{ .Values.replica.persistence.subPathExpr }}
{{- end }}
- name: config
mountPath: /opt/bitnami/redis-sentinel/mounted-etc
{{- if .Values.tls.enabled }}
- name: redis-certificates
mountPath: /opt/bitnami/redis/certs
readOnly: true
{{- end }}
{{- if .Values.sentinel.extraVolumeMounts }}
{{- include "common.tplvalues.render" ( dict "value" .Values.sentinel.extraVolumeMounts "context" $ ) | nindent 12 }}
{{- end }}
{{- if .Values.metrics.enabled }}
- name: metrics
image: {{ template "redis.metrics.image" . }}
imagePullPolicy: {{ .Values.metrics.image.pullPolicy | quote }}
{{- if .Values.metrics.containerSecurityContext.enabled }}
securityContext: {{- include "common.compatibility.renderSecurityContext" (dict "secContext" .Values.metrics.containerSecurityContext "context" $) | nindent 12 }}
{{- end }}
{{- if .Values.diagnosticMode.enabled }}
command: {{- include "common.tplvalues.render" (dict "value" .Values.diagnosticMode.command "context" $) | nindent 12 }}
{{- else }}
command:
- /bin/bash
- -c
- |
if [[ -f '/secrets/redis-password' ]]; then
export REDIS_PASSWORD=$(cat /secrets/redis-password)
fi
redis_exporter{{- range $key, $value := .Values.metrics.extraArgs }} --{{ $key }}={{ $value }}{{- end }}
{{- end }}
{{- if .Values.diagnosticMode.enabled }}
args: {{- include "common.tplvalues.render" (dict "value" .Values.diagnosticMode.args "context" $) | nindent 12 }}
{{- end }}
env:
- name: REDIS_ALIAS
value: {{ template "common.names.fullname" . }}
- name: REDIS_EXPORTER_WEB_LISTEN_ADDRESS
value: {{ printf ":%v" .Values.metrics.containerPorts.http }}
{{- if .Values.auth.enabled }}
- name: REDIS_USER
value: default
{{- if (not .Values.auth.usePasswordFiles) }}
- name: REDIS_PASSWORD
valueFrom:
secretKeyRef:
name: {{ template "redis.secretName" . }}
key: {{ template "redis.secretPasswordKey" . }}
{{- end }}
{{- end }}
{{- if .Values.tls.enabled }}
- name: REDIS_ADDR
value: rediss://{{ .Values.metrics.redisTargetHost }}:{{ .Values.replica.containerPorts.redis }}
{{- if .Values.tls.authClients }}
- name: REDIS_EXPORTER_TLS_CLIENT_KEY_FILE
value: {{ template "redis.tlsCertKey" . }}
- name: REDIS_EXPORTER_TLS_CLIENT_CERT_FILE
value: {{ template "redis.tlsCert" . }}
{{- end }}
- name: REDIS_EXPORTER_TLS_CA_CERT_FILE
value: {{ template "redis.tlsCACert" . }}
{{- end }}
{{- if .Values.metrics.extraEnvVars }}
{{- include "common.tplvalues.render" (dict "value" .Values.metrics.extraEnvVars "context" $) | nindent 12 }}
{{- end }}
ports:
- name: metrics
containerPort: {{ .Values.metrics.containerPorts.http }}
{{- if not .Values.diagnosticMode.enabled }}
{{- if .Values.metrics.customStartupProbe }}
startupProbe: {{- include "common.tplvalues.render" (dict "value" .Values.metrics.customStartupProbe "context" $) | nindent 12 }}
{{- else if .Values.metrics.startupProbe.enabled }}
startupProbe: {{- include "common.tplvalues.render" (dict "value" (omit .Values.metrics.startupProbe "enabled") "context" $) | nindent 12 }}
tcpSocket:
port: metrics
{{- end }}
{{- if .Values.metrics.customLivenessProbe }}
livenessProbe: {{- include "common.tplvalues.render" (dict "value" .Values.metrics.customLivenessProbe "context" $) | nindent 12 }}
{{- else if .Values.metrics.livenessProbe.enabled }}
livenessProbe: {{- include "common.tplvalues.render" (dict "value" (omit .Values.metrics.livenessProbe "enabled") "context" $) | nindent 12 }}
tcpSocket:
port: metrics
{{- end }}
{{- if .Values.metrics.customReadinessProbe }}
readinessProbe: {{- include "common.tplvalues.render" (dict "value" .Values.metrics.customReadinessProbe "context" $) | nindent 12 }}
{{- else if .Values.metrics.readinessProbe.enabled }}
readinessProbe: {{- include "common.tplvalues.render" (dict "value" (omit .Values.metrics.readinessProbe "enabled") "context" $) | nindent 12 }}
httpGet:
path: /
port: metrics
{{- end }}
{{- end }}
{{- if .Values.metrics.resources }}
resources: {{- toYaml .Values.metrics.resources | nindent 12 }}
{{- else if ne .Values.metrics.resourcesPreset "none" }}
resources: {{- include "common.resources.preset" (dict "type" .Values.metrics.resourcesPreset) | nindent 12 }}
{{- end }}
volumeMounts:
- name: empty-dir
mountPath: /tmp
subPath: tmp-dir
{{- if .Values.auth.usePasswordFiles }}
- name: redis-password
mountPath: /secrets/
{{- end }}
{{- if .Values.tls.enabled }}
- name: redis-certificates
mountPath: /opt/bitnami/redis/certs
readOnly: true
{{- end }}
{{- if .Values.metrics.extraVolumeMounts }}
{{- include "common.tplvalues.render" ( dict "value" .Values.metrics.extraVolumeMounts "context" $ ) | nindent 12 }}
{{- end }}
{{- end }}
{{- if or .Values.sentinel.masterService.enabled .Values.sentinel.service.createMaster }}
- name: kubectl-shared
image: {{ template "redis.kubectl.image" . }}
imagePullPolicy: {{ .Values.kubectl.image.pullPolicy | quote }}
command: {{- toYaml .Values.kubectl.command | nindent 12 }}
{{- if .Values.kubectl.containerSecurityContext.enabled }}
securityContext: {{- include "common.compatibility.renderSecurityContext" (dict "secContext" .Values.kubectl.containerSecurityContext "context" $) | nindent 12 }}
{{- end }}
volumeMounts:
- name: kubectl-shared
mountPath: /etc/shared
- name: kubectl-scripts
mountPath: /opt/bitnami/scripts/kubectl-scripts
{{- if .Values.kubectl.resources }}
resources: {{- toYaml .Values.kubectl.resources | nindent 12 }}
{{- end }}
{{- end }}
{{- if .Values.replica.sidecars }}
{{- include "common.tplvalues.render" (dict "value" .Values.replica.sidecars "context" $) | nindent 8 }}
{{- end }}
{{- $needsVolumePermissions := and .Values.volumePermissions.enabled .Values.replica.persistence.enabled .Values.replica.podSecurityContext.enabled .Values.replica.containerSecurityContext.enabled }}
{{- if or .Values.replica.initContainers $needsVolumePermissions .Values.sysctl.enabled }}
initContainers:
{{- if .Values.replica.initContainers }}
{{- include "common.tplvalues.render" (dict "value" .Values.replica.initContainers "context" $) | nindent 8 }}
{{- end }}
{{- if $needsVolumePermissions }}
- name: volume-permissions
image: {{ include "redis.volumePermissions.image" . }}
imagePullPolicy: {{ .Values.volumePermissions.image.pullPolicy | quote }}
command:
- /bin/bash
- -ec
- |
{{- if eq ( toString ( .Values.volumePermissions.containerSecurityContext.runAsUser )) "auto" }}
chown -R `id -u`:`id -G | cut -d " " -f2` {{ .Values.replica.persistence.path }}
{{- else }}
chown -R {{ .Values.replica.containerSecurityContext.runAsUser }}:{{ .Values.replica.podSecurityContext.fsGroup }} {{ .Values.replica.persistence.path }}
{{- end }}
{{- if eq ( toString ( .Values.volumePermissions.containerSecurityContext.runAsUser )) "auto" }}
securityContext: {{- omit .Values.volumePermissions.containerSecurityContext "runAsUser" | toYaml | nindent 12 }}
{{- else }}
securityContext: {{- .Values.volumePermissions.containerSecurityContext | toYaml | nindent 12 }}
{{- end }}
{{- if .Values.volumePermissions.resources }}
resources: {{- toYaml .Values.volumePermissions.resources | nindent 12 }}
{{- else if ne .Values.volumePermissions.resourcesPreset "none" }}
resources: {{- include "common.resources.preset" (dict "type" .Values.volumePermissions.resourcesPreset) | nindent 12 }}
{{- end }}
volumeMounts:
- name: empty-dir
mountPath: /tmp
subPath: tmp-dir
- name: redis-data
mountPath: {{ .Values.replica.persistence.path }}
{{- if .Values.replica.persistence.subPath }}
subPath: {{ .Values.replica.persistence.subPath }}
{{- else if .Values.replica.persistence.subPathExpr }}
subPathExpr: {{ .Values.replica.persistence.subPathExpr }}
{{- end }}
{{- end }}
{{- if .Values.sysctl.enabled }}
- name: init-sysctl
image: {{ include "redis.sysctl.image" . }}
imagePullPolicy: {{ default "" .Values.sysctl.image.pullPolicy | quote }}
securityContext:
privileged: true
runAsUser: 0
{{- if .Values.sysctl.command }}
command: {{- include "common.tplvalues.render" (dict "value" .Values.sysctl.command "context" $) | nindent 12 }}
{{- end }}
{{- if .Values.sysctl.resources }}
resources: {{- toYaml .Values.sysctl.resources | nindent 12 }}
{{- else if ne .Values.sysctl.resourcesPreset "none" }}
resources: {{- include "common.resources.preset" (dict "type" .Values.sysctl.resourcesPreset) | nindent 12 }}
{{- end }}
{{- if .Values.sysctl.mountHostSys }}
volumeMounts:
- name: empty-dir
mountPath: /tmp
subPath: tmp-dir
- name: host-sys
mountPath: /host-sys
{{- end }}
{{- end }}
{{- end }}
volumes:
- name: start-scripts
configMap:
name: {{ printf "%s-scripts" (include "common.names.fullname" .) }}
defaultMode: 0755
- name: health
configMap:
name: {{ printf "%s-health" (include "common.names.fullname" .) }}
defaultMode: 0755
{{- if or .Values.sentinel.masterService.enabled .Values.sentinel.service.createMaster}}
- name: kubectl-shared
emptyDir: {}
- name: kubectl-scripts
configMap:
name: {{ printf "%s-kubectl-scripts" (include "common.names.fullname" .) }}
defaultMode: 0755
{{- end }}
{{- if .Values.auth.usePasswordFiles }}
- name: redis-password
{{ if .Values.auth.usePasswordFileFromSecret }}
secret:
secretName: {{ template "redis.secretName" . }}
items:
- key: {{ template "redis.secretPasswordKey" . }}
path: redis-password
{{- else }}
emptyDir: {}
{{- end }}
{{- end }}
- name: config
configMap:
name: {{ include "redis.configmapName" . }}
{{- if .Values.sysctl.mountHostSys }}
- name: host-sys
hostPath:
path: /sys
{{- end }}
{{- if not .Values.sentinel.persistence.enabled }}
- name: sentinel-data
{{- if or .Values.sentinel.persistence.medium .Values.sentinel.persistence.sizeLimit }}
emptyDir:
{{- if .Values.sentinel.persistence.medium }}
medium: {{ .Values.sentinel.persistence.medium | quote }}
{{- end }}
{{- if .Values.sentinel.persistence.sizeLimit }}
sizeLimit: {{ .Values.sentinel.persistence.sizeLimit | quote }}
{{- end }}
{{- else }}
emptyDir: {}
{{- end }}
{{- end }}
- name: empty-dir
{{- if or .Values.sentinel.persistence.medium .Values.sentinel.persistence.sizeLimit }}
emptyDir:
{{- if .Values.sentinel.persistence.medium }}
medium: {{ .Values.sentinel.persistence.medium | quote }}
{{- end }}
{{- if .Values.sentinel.persistence.sizeLimit }}
sizeLimit: {{ .Values.sentinel.persistence.sizeLimit | quote }}
{{- end }}
{{- else }}
emptyDir: {}
{{- end }}
{{- if .Values.replica.extraVolumes }}
{{- include "common.tplvalues.render" ( dict "value" .Values.replica.extraVolumes "context" $ ) | nindent 8 }}
{{- end }}
{{- if .Values.metrics.extraVolumes }}
{{- include "common.tplvalues.render" ( dict "value" .Values.metrics.extraVolumes "context" $ ) | nindent 8 }}
{{- end }}
{{- if .Values.sentinel.extraVolumes }}
{{- include "common.tplvalues.render" ( dict "value" .Values.sentinel.extraVolumes "context" $ ) | nindent 8 }}
{{- end }}
{{- if .Values.tls.enabled }}
- name: redis-certificates
secret:
secretName: {{ include "redis.tlsSecretName" . }}
defaultMode: 256
{{- end }}
{{- if not .Values.replica.persistence.enabled }}
- name: redis-data
{{- if or .Values.replica.persistence.medium .Values.replica.persistence.sizeLimit }}
emptyDir:
{{- if .Values.replica.persistence.medium }}
medium: {{ .Values.replica.persistence.medium | quote }}
{{- end }}
{{- if .Values.replica.persistence.sizeLimit }}
sizeLimit: {{ .Values.replica.persistence.sizeLimit | quote }}
{{- end }}
{{- else }}
emptyDir: {}
{{- end }}
{{- else if .Values.replica.persistence.existingClaim }}
- name: redis-data
persistentVolumeClaim:
claimName: {{ printf "%s" (tpl .Values.replica.persistence.existingClaim .) }}
{{- else }}
{{- if .Values.sentinel.persistentVolumeClaimRetentionPolicy.enabled }}
persistentVolumeClaimRetentionPolicy:
whenDeleted: {{ .Values.sentinel.persistentVolumeClaimRetentionPolicy.whenDeleted }}
whenScaled: {{ .Values.sentinel.persistentVolumeClaimRetentionPolicy.whenScaled }}
{{- end }}
volumeClaimTemplates:
- apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: redis-data
labels: {{- include "common.labels.matchLabels" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 10 }}
app.kubernetes.io/component: node
{{- if .Values.replica.persistence.annotations }}
annotations: {{- toYaml .Values.replica.persistence.annotations | nindent 10 }}
{{- end }}
spec:
accessModes:
{{- range .Values.replica.persistence.accessModes }}
- {{ . | quote }}
{{- end }}
resources:
requests:
storage: {{ .Values.replica.persistence.size | quote }}
{{- if .Values.replica.persistence.selector }}
selector: {{- include "common.tplvalues.render" ( dict "value" .Values.replica.persistence.selector "context" $) | nindent 10 }}
{{- end }}
{{- include "common.storage.class" (dict "persistence" .Values.replica.persistence "global" .Values.global) | nindent 8 }}
{{- if .Values.sentinel.persistence.enabled }}
- metadata:
name: sentinel-data
{{- $claimLabels := include "common.tplvalues.merge" ( dict "values" ( list .Values.sentinel.persistence.labels .Values.commonLabels ) "context" . ) }}
labels: {{- include "common.labels.matchLabels" ( dict "customLabels" $claimLabels "context" $ ) | nindent 10 }}
app.kubernetes.io/component: node
{{- if .Values.sentinel.persistence.annotations }}
annotations: {{- toYaml .Values.sentinel.persistence.annotations | nindent 10 }}
{{- end }}
spec:
accessModes:
{{- range .Values.sentinel.persistence.accessModes }}
- {{ . | quote }}
{{- end }}
resources:
requests:
storage: {{ .Values.sentinel.persistence.size | quote }}
{{- if .Values.sentinel.persistence.selector }}
selector: {{- include "common.tplvalues.render" ( dict "value" .Values.sentinel.persistence.selector "context" $) | nindent 10 }}
{{- end }}
{{- if .Values.sentinel.persistence.dataSource }}
dataSource: {{- include "common.tplvalues.render" (dict "value" .Values.sentinel.persistence.dataSource "context" $) | nindent 10 }}
{{- end }}
{{- include "common.storage.class" (dict "persistence" .Values.sentinel.persistence "global" .Values.global) | nindent 8 }}
{{- end }}
{{- end }}
{{- end }}
{{- end }}

View File

@ -0,0 +1,18 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if and .Values.serviceAccount.create .Values.sentinel.enabled }}
apiVersion: v1
kind: ServiceAccount
automountServiceAccountToken: {{ .Values.serviceAccount.automountServiceAccountToken }}
metadata:
name: {{ template "redis.serviceAccountName" . }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- if or .Values.commonAnnotations .Values.serviceAccount.annotations }}
{{- $annotations := include "common.tplvalues.merge" ( dict "values" ( list .Values.serviceAccount.annotations .Values.commonAnnotations ) "context" . ) }}
annotations: {{- include "common.tplvalues.render" ( dict "value" $annotations "context" $) | nindent 4 }}
{{- end }}
{{- end }}

View File

@ -0,0 +1,82 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if and .Values.metrics.enabled .Values.metrics.serviceMonitor.enabled }}
apiVersion: monitoring.coreos.com/v1
kind: ServiceMonitor
metadata:
name: {{ template "common.names.fullname" . }}
namespace: {{ default (include "common.names.namespace" .) .Values.metrics.serviceMonitor.namespace | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- if .Values.metrics.serviceMonitor.additionalLabels }}
{{- include "common.tplvalues.render" (dict "value" .Values.metrics.serviceMonitor.additionalLabels "context" $) | nindent 4 }}
{{- end }}
{{- if .Values.commonAnnotations }}
annotations: {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
spec:
endpoints:
- port: {{ .Values.metrics.serviceMonitor.port }}
{{- if .Values.metrics.serviceMonitor.interval }}
interval: {{ .Values.metrics.serviceMonitor.interval }}
{{- end }}
{{- if .Values.metrics.serviceMonitor.scrapeTimeout }}
scrapeTimeout: {{ .Values.metrics.serviceMonitor.scrapeTimeout }}
{{- end }}
{{- if .Values.metrics.serviceMonitor.honorLabels }}
honorLabels: {{ .Values.metrics.serviceMonitor.honorLabels }}
{{- end }}
{{- with concat .Values.metrics.serviceMonitor.relabelings .Values.metrics.serviceMonitor.relabellings }}
relabelings: {{- toYaml . | nindent 6 }}
{{- end }}
{{- if .Values.metrics.serviceMonitor.metricRelabelings }}
metricRelabelings: {{- toYaml .Values.metrics.serviceMonitor.metricRelabelings | nindent 6 }}
{{- end }}
{{- range .Values.metrics.serviceMonitor.additionalEndpoints }}
- port: {{ .port }}
{{- if .interval }}
interval: {{ .interval }}
{{- end }}
{{- if .scrapeTimeout }}
scrapeTimeout: {{ .scrapeTimeout }}
{{- end }}
{{- if .honorLabels }}
honorLabels: {{ .honorLabels }}
{{- end }}
{{- with concat .Values.metrics.serviceMonitor.relabelings .Values.metrics.serviceMonitor.relabellings }}
relabelings: {{- toYaml . | nindent 6 }}
{{- end }}
{{- if .metricRelabelings }}
metricRelabelings: {{- toYaml .metricRelabelings | nindent 6 }}
{{- end }}
{{- if .path }}
path: {{ .path }}
{{- end }}
{{- if .params }}
params:
{{- range $key, $value := .params }}
{{ $key }}:
{{- range $value }}
- {{ . | quote }}
{{- end }}
{{- end }}
{{- end }}
{{- end }}
{{- if .Values.metrics.serviceMonitor.podTargetLabels }}
podTargetLabels: {{- toYaml .Values.metrics.serviceMonitor.podTargetLabels | nindent 4 }}
{{- end }}
{{- with .Values.metrics.serviceMonitor.sampleLimit }}
sampleLimit: {{ . }}
{{- end }}
{{- with .Values.metrics.serviceMonitor.targetLimit }}
targetLimit: {{ . }}
{{- end }}
namespaceSelector:
matchNames:
- {{ include "common.names.namespace" . | quote }}
selector:
matchLabels: {{- include "common.labels.matchLabels" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 6 }}
app.kubernetes.io/component: metrics
{{- end }}

View File

@ -0,0 +1,31 @@
{{- /*
Copyright Broadcom, Inc. All Rights Reserved.
SPDX-License-Identifier: APACHE-2.0
*/}}
{{- if (include "redis.createTlsSecret" .) }}
{{- $secretName := printf "%s-crt" (include "common.names.fullname" .) }}
{{- $ca := genCA "redis-ca" 365 }}
{{- $releaseNamespace := (include "common.names.namespace" .) }}
{{- $clusterDomain := .Values.clusterDomain }}
{{- $fullname := include "common.names.fullname" . }}
{{- $serviceName := include "common.names.fullname" . }}
{{- $headlessServiceName := printf "%s-headless" (include "common.names.fullname" .) }}
{{- $masterServiceName := printf "%s-master" (include "common.names.fullname" .) }}
{{- $altNames := list (printf "*.%s.%s.svc.%s" $serviceName $releaseNamespace $clusterDomain) (printf "%s.%s.svc.%s" $masterServiceName $releaseNamespace $clusterDomain) (printf "*.%s.%s.svc.%s" $masterServiceName $releaseNamespace $clusterDomain) (printf "*.%s.%s.svc.%s" $headlessServiceName $releaseNamespace $clusterDomain) (printf "%s.%s.svc.%s" $headlessServiceName $releaseNamespace $clusterDomain) "127.0.0.1" "localhost" $fullname }}
{{- $cert := genSignedCert $fullname nil $altNames 365 $ca }}
apiVersion: v1
kind: Secret
metadata:
name: {{ $secretName }}
namespace: {{ include "common.names.namespace" . | quote }}
labels: {{- include "common.labels.standard" ( dict "customLabels" .Values.commonLabels "context" $ ) | nindent 4 }}
{{- if .Values.commonAnnotations }}
annotations: {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }}
{{- end }}
type: kubernetes.io/tls
data:
tls.crt: {{ include "common.secrets.lookup" (dict "secret" $secretName "key" "tls.crt" "defaultValue" $cert.Cert "context" $) }}
tls.key: {{ include "common.secrets.lookup" (dict "secret" $secretName "key" "tls.key" "defaultValue" $cert.Key "context" $) }}
ca.crt: {{ include "common.secrets.lookup" (dict "secret" $secretName "key" "ca.crt" "defaultValue" $ca.Cert "context" $) }}
{{- end }}

View File

@ -0,0 +1,163 @@
{
"$schema": "http://json-schema.org/schema#",
"type": "object",
"properties": {
"architecture": {
"type": "string",
"title": "Redis architecture",
"form": true,
"description": "Allowed values: `standalone` or `replication`",
"enum": ["standalone", "replication"]
},
"auth": {
"type": "object",
"title": "Authentication configuration",
"form": true,
"properties": {
"enabled": {
"type": "boolean",
"form": true,
"title": "Use password authentication"
},
"password": {
"type": "string",
"title": "Redis password",
"form": true,
"description": "Defaults to a random 10-character alphanumeric string if not set",
"hidden": {
"value": false,
"path": "auth/enabled"
}
}
}
},
"master": {
"type": "object",
"title": "Master replicas settings",
"form": true,
"properties": {
"kind": {
"type": "string",
"title": "Workload Kind",
"form": true,
"description": "Allowed values: `Deployment`, `StatefulSet` or `DaemonSet`",
"enum": ["Deployment", "StatefulSet", "DaemonSet"]
},
"persistence": {
"type": "object",
"title": "Persistence for master replicas",
"form": true,
"properties": {
"enabled": {
"type": "boolean",
"form": true,
"title": "Enable persistence",
"description": "Enable persistence using Persistent Volume Claims"
},
"size": {
"type": "string",
"title": "Persistent Volume Size",
"form": true,
"render": "slider",
"sliderMin": 1,
"sliderMax": 100,
"sliderUnit": "Gi",
"hidden": {
"value": false,
"path": "master/persistence/enabled"
}
}
}
}
}
},
"replica": {
"type": "object",
"title": "Redis replicas settings",
"form": true,
"hidden": {
"value": "standalone",
"path": "architecture"
},
"properties": {
"kind": {
"type": "string",
"title": "Workload Kind",
"form": true,
"description": "Allowed values: `DaemonSet` or `StatefulSet`",
"enum": ["DaemonSet", "StatefulSet"]
},
"replicaCount": {
"type": "integer",
"form": true,
"title": "Number of Redis replicas"
},
"persistence": {
"type": "object",
"title": "Persistence for Redis replicas",
"form": true,
"properties": {
"enabled": {
"type": "boolean",
"form": true,
"title": "Enable persistence",
"description": "Enable persistence using Persistent Volume Claims"
},
"size": {
"type": "string",
"title": "Persistent Volume Size",
"form": true,
"render": "slider",
"sliderMin": 1,
"sliderMax": 100,
"sliderUnit": "Gi",
"hidden": {
"value": false,
"path": "replica/persistence/enabled"
}
}
}
}
}
},
"volumePermissions": {
"type": "object",
"properties": {
"enabled": {
"type": "boolean",
"form": true,
"title": "Enable Init Containers",
"description": "Use an init container to set required folder permissions on the data volume before mounting it in the final destination"
}
}
},
"metrics": {
"type": "object",
"form": true,
"title": "Prometheus metrics details",
"properties": {
"enabled": {
"type": "boolean",
"title": "Create Prometheus metrics exporter",
"description": "Create a side-car container to expose Prometheus metrics",
"form": true
},
"serviceMonitor": {
"type": "object",
"properties": {
"enabled": {
"type": "boolean",
"title": "Create Prometheus Operator ServiceMonitor",
"description": "Create a ServiceMonitor to track metrics using Prometheus Operator",
"form": true,
"hidden": {
"value": false,
"path": "metrics/enabled"
}
}
}
}
}
}
}
}

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,8 @@
architecture: standalone
auth:
enabled: false
master:
replicaCount: 1
fullnameOverride: redis
image:
debug: true

View File

@ -0,0 +1,2 @@
tests/
crds/kustomization.yaml

Some files were not shown because too many files have changed in this diff Show More