Skip to content

Commit 43b45f1

Browse files
committed
feat(common): add statefulset recreate job
including this automatically adds a `pre-upgrade` hook that deletes the referenced statefulset.
1 parent 104f986 commit 43b45f1

2 files changed

Lines changed: 161 additions & 0 deletions

File tree

Lines changed: 156 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,156 @@
1+
{{- define "common.statefulset.recreateOnSizeChangeHook" -}}
2+
{{- $_ := mustMerge . (pick .context "Values" "Capabilities" "Release") -}}
3+
{{- $renderedStatefulSets := list -}}
4+
{{- range $renderedStatefulSet := include (print .context.Template.BasePath .pathToStatefulsetTemplate) .context | splitList "---" -}}
5+
{{- with $renderedStatefulSet | fromYaml -}}
6+
{{- $renderedStatefulSets = append $renderedStatefulSets . -}}
7+
{{- end }}
8+
{{- end -}}
9+
{{- if $renderedStatefulSets }}
10+
{{- range $newStatefulSet := $renderedStatefulSets -}}
11+
{{- if $newStatefulSet.spec.volumeClaimTemplates }}
12+
{{- $resourceNamespace := default $.Release.Namespace $newStatefulSet.metadata.namespace -}}
13+
{{- $currentStatefulset := lookup $newStatefulSet.apiVersion $newStatefulSet.kind $resourceNamespace $newStatefulSet.metadata.name -}}
14+
{{- $needsRecreation := false -}}
15+
{{- $templates := dict -}}
16+
{{- if $currentStatefulset -}}
17+
{{- if ne (len $newStatefulSet.spec.volumeClaimTemplates) (len $currentStatefulset.spec.volumeClaimTemplates) -}}
18+
{{- $needsRecreation = true -}}
19+
{{- end -}}
20+
{{- range $index, $newVolumeClaimTemplate := $newStatefulSet.spec.volumeClaimTemplates -}}
21+
{{- $currentVolumeClaimTemplateSpec := dict -}}
22+
{{- range $oldVolumeClaimTemplate := $currentStatefulset.spec.volumeClaimTemplates -}}
23+
{{- if eq $oldVolumeClaimTemplate.metadata.name $newVolumeClaimTemplate.metadata.name -}}
24+
{{- $currentVolumeClaimTemplateSpec = $oldVolumeClaimTemplate.spec -}}
25+
{{- end -}}
26+
{{- end }}
27+
{{- $newVolumeClaimTemplateStorageSize := $newVolumeClaimTemplate.spec.resources.requests.storage -}}
28+
{{- if not $currentVolumeClaimTemplateSpec -}}
29+
{{- $needsRecreation = true -}}
30+
{{- else -}}
31+
{{- if ne $newVolumeClaimTemplateStorageSize $currentVolumeClaimTemplateSpec.resources.requests.storage -}}
32+
{{- $needsRecreation = true -}}
33+
{{- $templates = set $templates $newVolumeClaimTemplate.metadata.name $newVolumeClaimTemplateStorageSize -}}
34+
{{- end -}}
35+
{{- end -}}
36+
{{- end -}}
37+
{{- end -}}
38+
{{- if $needsRecreation }}
39+
apiVersion: batch/v1
40+
kind: Job
41+
metadata:
42+
name: {{ $newStatefulSet.metadata.name }}-recreate
43+
namespace: {{ $resourceNamespace }}
44+
labels:
45+
{{- $newStatefulSet.metadata.labels | toYaml | nindent 4 }}
46+
app.kubernetes.io/component: statefulset-recreate-job
47+
annotations:
48+
"helm.sh/hook": pre-upgrade
49+
"helm.sh/hook-weight": "-5"
50+
"helm.sh/hook-delete-policy": before-hook-creation,hook-succeeded
51+
spec:
52+
ttlSecondsAfterFinished: 300
53+
template:
54+
metadata:
55+
name: {{ $newStatefulSet.metadata.name }}-recreate
56+
labels:
57+
{{- $newStatefulSet.metadata.labels | toYaml | nindent 8 }}
58+
spec:
59+
serviceAccountName: {{ $newStatefulSet.metadata.name }}-recreate
60+
restartPolicy: OnFailure
61+
containers:
62+
- name: recreate
63+
image: {{ include "common.images.image" (dict "imageRoot" (mustMerge (dict "tag" $.Capabilities.KubeVersion.Version) $.Values.global.kubectl.image) "global" $.Values.global) -}}
64+
command:
65+
- kubectl
66+
- delete
67+
- statefulset
68+
- --cascade=orphan
69+
- {{ $newStatefulSet.metadata.name }}
70+
{{- range $index := until (int $newStatefulSet.spec.replicas) }}
71+
{{- range $template, $size := $templates }}
72+
- name: patch-pvc-{{ $template }}-{{ $index }}
73+
image: {{ include "loki.baseImage" (dict "service" (dict "registry" "docker.io" "repository" "rancher/kubectl" "tag" ($.Capabilities.KubeVersion.Version | default "v1.33.0")) "global" $.Values.global.image) }}
74+
command:
75+
- kubectl
76+
- patch
77+
- pvc
78+
- {{ printf "%s-%s-%d" $template $newStatefulSet.metadata.name $index }}
79+
- --type='json'
80+
- '-p=[{"op": "replace", "path": "/spec/resources/requests/storage", "value": "{{ $size }}"}]'
81+
{{- end }}
82+
{{- end }}
83+
---
84+
apiVersion: v1
85+
kind: ServiceAccount
86+
metadata:
87+
name: {{ $newStatefulSet.metadata.name }}-recreate
88+
namespace: {{ $resourceNamespace }}
89+
labels:
90+
{{- $newStatefulSet.metadata.labels | toYaml | nindent 4 }}
91+
app.kubernetes.io/component: statefulset-recreate-job
92+
annotations:
93+
"helm.sh/hook": pre-upgrade
94+
"helm.sh/hook-weight": "-10"
95+
"helm.sh/hook-delete-policy": before-hook-creation,hook-succeeded
96+
---
97+
apiVersion: rbac.authorization.k8s.io/v1
98+
kind: Role
99+
metadata:
100+
name: {{ $newStatefulSet.metadata.name }}-recreate
101+
namespace: {{ $resourceNamespace }}
102+
labels:
103+
{{- $newStatefulSet.metadata.labels | toYaml | nindent 4 }}
104+
app.kubernetes.io/component: statefulset-recreate-job
105+
annotations:
106+
"helm.sh/hook": pre-upgrade
107+
"helm.sh/hook-weight": "-10"
108+
"helm.sh/hook-delete-policy": before-hook-creation,hook-succeeded
109+
rules:
110+
- apiGroups:
111+
- apps
112+
resources:
113+
- statefulsets
114+
resourceNames:
115+
- {{ $newStatefulSet.metadata.name }}
116+
verbs:
117+
- delete
118+
- apiGroups:
119+
- v1
120+
resources:
121+
- persistentvolumeclaims
122+
resourceNames:
123+
{{- range $index := until (int $newStatefulSet.spec.replicas) }}
124+
{{- range $template := $templates | keys }}
125+
- {{ printf "%s-%s-%d" $template $newStatefulSet.metadata.name $index }}
126+
{{- end }}
127+
{{- end }}
128+
verbs:
129+
- patch
130+
---
131+
apiVersion: rbac.authorization.k8s.io/v1
132+
kind: RoleBinding
133+
metadata:
134+
name: {{ $newStatefulSet.metadata.name }}-recreate
135+
namespace: {{ $resourceNamespace }}
136+
labels:
137+
{{- $newStatefulSet.metadata.labels | toYaml | nindent 4 }}
138+
app.kubernetes.io/component: statefulset-recreate-job
139+
annotations:
140+
"helm.sh/hook": pre-upgrade
141+
"helm.sh/hook-weight": "-10"
142+
"helm.sh/hook-delete-policy": before-hook-creation,hook-succeeded
143+
subjects:
144+
- kind: ServiceAccount
145+
name: {{ $newStatefulSet.metadata.name }}-recreate
146+
namespace: {{ $resourceNamespace }}
147+
roleRef:
148+
kind: Role
149+
name: {{ $newStatefulSet.metadata.name }}-recreate
150+
apiGroup: rbac.authorization.k8s.io
151+
---
152+
{{- end }}
153+
{{ end }}
154+
{{ end }}
155+
{{ end }}
156+
{{- end -}}

charts/common/values.yaml

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,9 @@
11
global:
2+
kubectl:
3+
image:
4+
registry: registry.k8s.io
5+
repository: kubectl
6+
tag: 1.33.4@sha256:261a9ed843eb68e3d50da132245e2221d75ca19504130e47bd32788c0ff339a0
27
telemetry:
38
otlp:
49
endpoint: auto

0 commit comments

Comments
 (0)