ᕕ( ᐛ )ᕗ Jimyag's Blog

k8s 灰度发布

基于 service 的灰度发布

# templates/_helpers.tpl
{{- define "nginx.fullname" -}}
{{- if .Values.fullnameOverride }}
{{- .Values.fullnameOverride | trunc 63 | trimSuffix "-" }}
{{- else }}
{{- .Release.Name | trunc 63 | trimSuffix "-" }}
{{- end }}
{{- end }}

{{- define "nginx.chart" -}}
{{- printf "%s-%s" .Chart.Name .Chart.Version | replace "+" "_" | trunc 63 | trimSuffix "-" }}
{{- end }}

{{- define "nginx.greenLabels" -}}
{{ include "nginx.commonLabels" . }}
app.kubernetes.io/logverse-canary-type: green
{{- end }}

{{- define "nginx.blueLabels" -}}
{{ include "nginx.commonLabels" . }}
app.kubernetes.io/logverse-canary-type: blue
{{- end }}

{{- define "nginx.greenSelectorLabels" -}}
{{ include "nginx.commonSelectorLabels" . }}
app.kubernetes.io/logverse-canary-type: green
{{- end }}

{{- define "nginx.blueSelectorLabels" -}}
{{ include "nginx.commonSelectorLabels" . }}
app.kubernetes.io/logverse-canary-type: blue
{{- end }}

{{- define "nginx.commonLabels" -}}
helm.sh/chart: {{ include "nginx.chart" . }}
{{ include "nginx.commonSelectorLabels" . }}
{{- if .Chart.AppVersion }}
app.kubernetes.io/version: {{ .Chart.AppVersion | quote }}
{{- end }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
{{- end }}

{{- define "nginx.commonSelectorLabels" -}}
app.kubernetes.io/name: {{ .Chart.Name }}
app.kubernetes.io/instance: {{ .Release.Name }}
{{- end }}
# templates/deployment-blue.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
  namespace: {{ .Release.Namespace }}
  name: {{ include "nginx.fullname" . }}-blue
  labels:
    {{- include "nginx.blueLabels" . | nindent 4 }}
spec:
  strategy: # 更新策略
    rollingUpdate: # 滚动更新配置
      maxSurge: 1 # 一次滚动更新的最大副本数
      maxUnavailable: 0 # 进行滚动更新时,最大不可用比例更新比例,表示在所有副本数中,最多可以有多少个不更新成功
    type: RollingUpdate # 更新类型,采用滚动更新
  selector:
    matchLabels:
      {{- include "nginx.blueSelectorLabels" . | nindent 6 }}
  replicas: {{ .Values.blue.replicaCount }}
  template:
    metadata:
      annotations:
        # 配置文件改变时,自动重启
        checksum/config: {{ include (print $.Template.BasePath "/configmap-blue.yaml") . | sha256sum }}
      labels:
        {{- include "nginx.blueLabels" . | nindent 8 }}
        {{- with .Values.podLabels }}
        {{- toYaml . | nindent 8 }}
        {{- end }}
    spec:
      containers:
        - name: {{ .Chart.Name }}-blue
          image: "{{ .Values.blue.image.repository }}:{{ .Values.blue.image.tag | default .Chart.AppVersion }}"
          imagePullPolicy: IfNotPresent
          ports:
            - name: http
              containerPort: {{ .Values.service.port }}
              protocol: TCP
          resources:
            {{- toYaml .Values.resources | nindent 12 }}
          {{- with .Values.blue.volumeMounts }}
          volumeMounts:
            {{- toYaml . | nindent 12 }}
          {{- end }}
      {{- with .Values.blue.volumes }}
      volumes:
        {{- toYaml . | nindent 8 }}
      {{- end }}
      {{- with .Values.nodeSelector }}
      nodeSelector:
        {{- toYaml . | nindent 8 }}
      {{- end }}
      {{- with .Values.affinity }}
      affinity:
        {{- toYaml . | nindent 8 }}
      {{- end }}
      {{- with .Values.tolerations }}
      tolerations:
        {{- toYaml . | nindent 8 }}
      {{- end }}
# templates/deployment-green.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
  namespace: {{ .Release.Namespace }}
  name: {{ include "nginx.fullname" . }}-green
  labels:
    {{- include "nginx.greenLabels" . | nindent 4 }}
spec:
  strategy: # 更新策略
    rollingUpdate: # 滚动更新配置
      maxSurge: 1 # 一次滚动更新的最大副本数
      maxUnavailable: 0 # 进行滚动更新时,最大不可用比例更新比例,表示在所有副本数中,最多可以有多少个不更新成功
    type: RollingUpdate # 更新类型,采用滚动更新
  selector:
    matchLabels:
      {{- include "nginx.greenSelectorLabels" . | nindent 6 }}
  replicas: {{ .Values.green.replicaCount }}
  template:
    metadata:
      annotations:
        # 配置文件改变时,自动重启
        checksum/config: {{ include (print $.Template.BasePath "/configmap-green.yaml") . | sha256sum }}
      labels:
        {{- include "nginx.greenLabels" . | nindent 8 }}
        {{- with .Values.podLabels }}
        {{- toYaml . | nindent 8 }}
        {{- end }}
    spec:
      containers:
        - name: {{ .Chart.Name }}-green
          image: "{{ .Values.green.image.repository }}:{{ .Values.green.image.tag | default .Chart.AppVersion }}"
          imagePullPolicy: IfNotPresent
          ports:
            - name: http
              containerPort: {{ .Values.service.port }}
              protocol: TCP
          resources:
            {{- toYaml .Values.resources | nindent 12 }}
          {{- with .Values.green.volumeMounts }}
          volumeMounts:
            {{- toYaml . | nindent 12 }}
          {{- end }}
      {{- with .Values.green.volumes }}
      volumes:
        {{- toYaml . | nindent 8 }}
      {{- end }}
      {{- with .Values.nodeSelector }}
      nodeSelector:
        {{- toYaml . | nindent 8 }}
      {{- end }}
      {{- with .Values.affinity }}
      affinity:
        {{- toYaml . | nindent 8 }}
      {{- end }}
      {{- with .Values.tolerations }}
      tolerations:
        {{- toYaml . | nindent 8 }}
      {{- end }}
# templates/service.yaml
apiVersion: v1
kind: Service
metadata:
  namespace: {{ .Release.Namespace }}
  name: {{ include "nginx.fullname" . }}
  labels:
    {{- include "nginx.commonLabels" . | nindent 4 }}
spec:
  type: {{ .Values.service.type }}
  ports:
    - port: {{ .Values.service.port }}
      targetPort: http
      protocol: TCP
      name: http
  selector:
    {{- include "nginx.commonSelectorLabels" . | nindent 4 }}
# templates/configmap-blue.yaml
apiVersion: v1
kind: ConfigMap
metadata:
  name: {{ include "nginx.fullname" . }}-blue
  labels:
    {{- include "nginx.blueLabels" . | nindent 4 }}
  namespace: {{ .Release.Namespace }}
data:
{{- range $key, $value := .Values.blue.configmaps }}
  {{ $key }}: |-
{{ $value | indent 4 }}
{{- end -}}
# templates/configmap-green.yaml
apiVersion: v1
kind: ConfigMap
metadata:
  name: {{ include "nginx.fullname" . }}-green
  labels:
    {{- include "nginx.greenLabels" . | nindent 4 }}
  namespace: {{ .Release.Namespace }}
data:
{{- range $key, $value := .Values.green.configmaps }}
  {{ $key }}: |-
{{ $value | indent 4 }}
{{- end -}}
# Chart.yaml
apiVersion: v2
name: nginx
description: A Helm chart for Kubernetes
type: application
version: 0.1.0
appVersion: "1.16.0"
# values.yaml
green:
  image:
    repository: nginx
    tag: 1.21
  replicaCount: 5
  configmaps:
    index.html: |-
      this is 1.21 green index.html      

  volumes:
    - name: index
      configMap:
        name: test-nginx-green
        items:
          - key: index.html
            path: index.html
  volumeMounts:
    - name: index
      mountPath: /usr/share/nginx/html/index.html
      subPath: index.html
      readOnly: true

blue:
  image:
    repository: nginx
    tag: 1.21
  replicaCount: 0
  configmaps:
    index.html: |-
      this is 1.21 blue index.html      

  volumes:
    - name: index
      configMap:
        name: test-nginx-blue
        items:
          - key: index.html
            path: index.html
  volumeMounts:
    - name: index
      mountPath: /usr/share/nginx/html/index.html
      subPath: index.html
      readOnly: true

fullnameOverride: ""
podAnnotations: {}
podLabels: {}

service:
  type: ClusterIP
  port: 80

resources: {}
nodeSelector: {}
tolerations: []
affinity: {}
helm upgrade --install -f values.yaml --description "$description" --create-namespace -n dev test-nginx ./

#k8s