initial admin-stack (#977)

diff --git a/charts/dubbo-admin/.helmignore b/charts/admin-stack/.helmignore
similarity index 100%
rename from charts/dubbo-admin/.helmignore
rename to charts/admin-stack/.helmignore
diff --git a/charts/dubbo-admin/Chart.yaml b/charts/admin-stack/Chart.yaml
similarity index 67%
copy from charts/dubbo-admin/Chart.yaml
copy to charts/admin-stack/Chart.yaml
index a7c29d4..0e35911 100644
--- a/charts/dubbo-admin/Chart.yaml
+++ b/charts/admin-stack/Chart.yaml
@@ -1,7 +1,7 @@
 apiVersion: v2
-appVersion: 0.5.0
+appVersion: ""
 name: dubbo-admin
-description: Distributed application monitoring and management platform.
+description: The ops and reference implementation for Apache Dubbo
 home: https://cn.dubbo.apache.org
 kubeVersion: '>=1.20.0-0'
 maintainers:
@@ -10,4 +10,4 @@
 sources:
   - https://github.com/apache/dubbo
 type: application
-version: 3.1.6
\ No newline at end of file
+version: 0.5.0
\ No newline at end of file
diff --git a/charts/dubbo-admin/README.md b/charts/admin-stack/README.md
similarity index 100%
rename from charts/dubbo-admin/README.md
rename to charts/admin-stack/README.md
diff --git a/charts/admin-stack/charts/dubbo-admin/.helmignore b/charts/admin-stack/charts/dubbo-admin/.helmignore
new file mode 100644
index 0000000..0e8a0eb
--- /dev/null
+++ b/charts/admin-stack/charts/dubbo-admin/.helmignore
@@ -0,0 +1,23 @@
+# Patterns to ignore when building packages.
+# This supports shell glob matching, relative path matching, and
+# negation (prefixed with !). Only one pattern per line.
+.DS_Store
+# Common VCS dirs
+.git/
+.gitignore
+.bzr/
+.bzrignore
+.hg/
+.hgignore
+.svn/
+# Common backup files
+*.swp
+*.bak
+*.tmp
+*.orig
+*~
+# Various IDEs
+.project
+.idea/
+*.tmproj
+.vscode/
diff --git a/charts/dubbo-admin/Chart.yaml b/charts/admin-stack/charts/dubbo-admin/Chart.yaml
similarity index 89%
rename from charts/dubbo-admin/Chart.yaml
rename to charts/admin-stack/charts/dubbo-admin/Chart.yaml
index a7c29d4..dff5d7f 100644
--- a/charts/dubbo-admin/Chart.yaml
+++ b/charts/admin-stack/charts/dubbo-admin/Chart.yaml
@@ -1,5 +1,5 @@
 apiVersion: v2
-appVersion: 0.5.0
+appVersion: ""
 name: dubbo-admin
 description: Distributed application monitoring and management platform.
 home: https://cn.dubbo.apache.org
@@ -10,4 +10,4 @@
 sources:
   - https://github.com/apache/dubbo
 type: application
-version: 3.1.6
\ No newline at end of file
+version: 0.5.0
\ No newline at end of file
diff --git a/charts/dubbo-admin/templates/tpl/_images.tpl b/charts/admin-stack/charts/dubbo-admin/templates/NOTES.txt
similarity index 100%
rename from charts/dubbo-admin/templates/tpl/_images.tpl
rename to charts/admin-stack/charts/dubbo-admin/templates/NOTES.txt
diff --git a/charts/admin-stack/charts/dubbo-admin/templates/_helpers.tpl b/charts/admin-stack/charts/dubbo-admin/templates/_helpers.tpl
new file mode 100644
index 0000000..b7ea4c9
--- /dev/null
+++ b/charts/admin-stack/charts/dubbo-admin/templates/_helpers.tpl
@@ -0,0 +1,87 @@
+{{/*
+Create chart name and version as used by the chart label.
+*/}}
+{{- define "dubbo-admin.chart" -}}
+{{- printf "%s-%s" .Chart.Name .Chart.Version | replace "+" "_" | trunc 63 | trimSuffix "-" }}
+{{- end }}
+
+
+{{/* vim: set filetype=mustache: */}}
+{{/*
+Expand the name of the chart.
+*/}}
+{{- define "dubbo-admin.name" -}}
+{{- default .Chart.Name .Values.nameOverride | trunc 63 | trimSuffix "-" -}}
+{{- end -}}
+
+{{/*
+Create a default fully qualified app name.
+We truncate at 63 chars because some Kubernetes name fields are limited to this (by the DNS naming spec).
+If release name contains chart name it will be used as a full name.
+*/}}
+{{- define "dubbo-admin.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 }}
+
+{{- define "dubbo-admin.labels" -}}
+app.kubernetes.io/name: {{ include "dubbo-admin.name" . }}
+helm.sh/chart: {{ include "dubbo-admin.chart" . }}
+app.kubernetes.io/instance: {{ .Release.Name }}
+app.kubernetes.io/managed-by: {{ .Release.Service }}
+{{- end -}}
+
+
+{{/*
+Allow the release namespace to be overridden for multi-namespace deployments in combined charts
+*/}}
+{{- define "dubbo-admin.namespace" -}}
+{{- if .Values.namespaceOverride }}
+{{- .Values.namespaceOverride }}
+{{- else }}
+{{- .Release.Namespace }}
+{{- end }}
+{{- end }}
+
+
+{{/*
+Labels to use on sts.spec.selector.matchLabels and svc.spec.selector
+*/}}
+{{- define "dubbo-admin.matchLabels" -}}
+app.kubernetes.io/name: {{ include "dubbo-admin.name" . }}
+{{- end -}}
+
+
+{{- define "dubbo-admin.selectorLabels" -}}
+app.kubernetes.io/name: {{ include "dubbo-admin.name" . }}
+app.kubernetes.io/instance: {{ .Release.Name }}
+{{- end }}
+
+
+{{/*
+Create the name of the service account to use
+*/}}
+{{- define "dubbo-admin.serviceAccountName" -}}
+{{- if .Values.serviceAccount.enabled }}
+{{- default (include "dubbo-admin.fullname" .) .Values.serviceAccount.name }}
+{{- else }}
+{{- default "default" .Values.serviceAccount.name }}
+{{- end }}
+{{- end }}
+
+
+{{- define "dubbo-admin.serviceAccountNameTest" -}}
+{{- if .Values.serviceAccount.enabled }}
+{{- default (print (include "dubbo-admin.fullname" .) "-test") .Values.serviceAccount.nameTest }}
+{{- else }}
+{{- default "default" .Values.serviceAccount.nameTest }}
+{{- end }}
+{{- end }}
\ No newline at end of file
diff --git a/charts/dubbo-admin/templates/admin-clusterrole.yaml b/charts/admin-stack/charts/dubbo-admin/templates/clusterrole.yaml
similarity index 79%
rename from charts/dubbo-admin/templates/admin-clusterrole.yaml
rename to charts/admin-stack/charts/dubbo-admin/templates/clusterrole.yaml
index 89fdd64..1d666a5 100644
--- a/charts/dubbo-admin/templates/admin-clusterrole.yaml
+++ b/charts/admin-stack/charts/dubbo-admin/templates/clusterrole.yaml
@@ -1,4 +1,4 @@
-{{- if and .Values.rbac.enabled (not .Values.rbac.namespaced) (not .Values.rbac.useExistingRole) }}
+{{- if and .Values.rbac.enabled }}
 apiVersion: {{ include "dubbo-admin.rbac.apiVersion" . }}
 kind: ClusterRole
 metadata:
@@ -37,6 +37,3 @@
       - list
       - watch
   {{- end }}
-  {{- with .Values.rbac.extraClusterRoleRules }}
-  {{- toYaml . | nindent 2 }}
-  {{- end }}
diff --git a/charts/dubbo-admin/templates/admin-clusterrolebinding.yaml b/charts/admin-stack/charts/dubbo-admin/templates/clusterrolebinding.yaml
similarity index 77%
rename from charts/dubbo-admin/templates/admin-clusterrolebinding.yaml
rename to charts/admin-stack/charts/dubbo-admin/templates/clusterrolebinding.yaml
index 2f73ac3..d0e99d9 100644
--- a/charts/dubbo-admin/templates/admin-clusterrolebinding.yaml
+++ b/charts/admin-stack/charts/dubbo-admin/templates/clusterrolebinding.yaml
@@ -1,4 +1,4 @@
-{{- if and .Values.rbac.enabled (not .Values.rbac.namespaced) }}
+{{- if and .Values.rbac.enabled }}
 apiVersion: {{ include "dubbo-admin.rbac.apiVersion" . }}
 kind: ClusterRoleBinding
 metadata:
@@ -15,10 +15,6 @@
     namespace: {{ include "dubbo-admin.namespace" . }}
 roleRef:
   kind: ClusterRole
-  {{- if .Values.rbac.useExistingRole }}
-  name: {{ .Values.rbac.useExistingRole }}
-  {{- else }}
   name: {{ include "dubbo-admin.fullname" . }}-clusterrole
   {{- end }}
   apiGroup: rbac.authorization.k8s.io
-{{- end }}
diff --git a/charts/dubbo-admin/templates/admin-deployment.yaml b/charts/admin-stack/charts/dubbo-admin/templates/deployment.yaml
similarity index 90%
rename from charts/dubbo-admin/templates/admin-deployment.yaml
rename to charts/admin-stack/charts/dubbo-admin/templates/deployment.yaml
index 57057be..d7f1615 100644
--- a/charts/dubbo-admin/templates/admin-deployment.yaml
+++ b/charts/admin-stack/charts/dubbo-admin/templates/deployment.yaml
@@ -6,18 +6,16 @@
   labels:
     {{- include "dubbo-admin.labels" . | nindent 4 }}
     {{- with .Values.labels }}
-        {{- toYaml . | nindent 4 }}
-        {{- end }}
-      {{- with .Values.annotations }}
+    {{- toYaml . | nindent 4 }}
+    {{- end }}
+    {{- with .Values.annotations }}
     annotations:
         {{- toYaml . | nindent 4 }}
-      {{- end }}
+    {{- end }}
 spec:
   {{- if and (not .Values.autoscaling.enabled) (.Values.replicas) }}
   replicas: {{ .Values.replicas }}
   {{- end }}
-  revisionHistoryLimit: {{ .Values.revisionHistoryLimit }}
-  minReadySeconds: {{ .Values.minReadySeconds }}
   selector:
     matchLabels:
       {{- include "dubbo-admin.selectorLabels" . | nindent 6 }}
@@ -98,9 +96,6 @@
             {{ if .Values.persistence.ClaimName }}
             claimName: {{ .Values.persistence.ClaimName }}
             {{- else -}}
-          emptyDir: {{- if .Values.persistence.emptyDir.sizeLimit }}
-              sizeLimit: {{ .Values.persistence.emptyDir.sizeLimit }}
-             {{- else }} {}
+          emptyDir: {{ .Values.persistence.emptyDir }}
               {{- end -}}
               {{- end -}}
-            {{- end -}}
diff --git a/charts/dubbo-admin/templates/admin-ingress.yaml b/charts/admin-stack/charts/dubbo-admin/templates/ingress.yaml
similarity index 100%
rename from charts/dubbo-admin/templates/admin-ingress.yaml
rename to charts/admin-stack/charts/dubbo-admin/templates/ingress.yaml
diff --git a/charts/dubbo-admin/templates/admin-networkpolicy.yaml b/charts/admin-stack/charts/dubbo-admin/templates/networkpolicy.yaml
similarity index 100%
rename from charts/dubbo-admin/templates/admin-networkpolicy.yaml
rename to charts/admin-stack/charts/dubbo-admin/templates/networkpolicy.yaml
diff --git a/charts/dubbo-admin/templates/admin-pdb.yaml b/charts/admin-stack/charts/dubbo-admin/templates/pdb.yaml
similarity index 100%
rename from charts/dubbo-admin/templates/admin-pdb.yaml
rename to charts/admin-stack/charts/dubbo-admin/templates/pdb.yaml
diff --git a/charts/dubbo-admin/templates/admin-psp.yaml b/charts/admin-stack/charts/dubbo-admin/templates/psp.yaml
similarity index 100%
rename from charts/dubbo-admin/templates/admin-psp.yaml
rename to charts/admin-stack/charts/dubbo-admin/templates/psp.yaml
diff --git a/charts/dubbo-admin/templates/admin-pvc.yaml b/charts/admin-stack/charts/dubbo-admin/templates/pvc.yaml
similarity index 64%
copy from charts/dubbo-admin/templates/admin-pvc.yaml
copy to charts/admin-stack/charts/dubbo-admin/templates/pvc.yaml
index 80a2565..2af3e1a 100644
--- a/charts/dubbo-admin/templates/admin-pvc.yaml
+++ b/charts/admin-stack/charts/dubbo-admin/templates/pvc.yaml
@@ -1,4 +1,4 @@
-{{- if and .Values.persistence.enabled (not .Values.persistence.ClaimName) (eq .Values.persistence.type "pvc")}}
+{{- if and .Values.persistence.enabled }}
 apiVersion: v1
 kind: PersistentVolumeClaim
 metadata:
@@ -6,17 +6,10 @@
   namespace: {{ include "dubbo-admin.namespace" . }}
   labels:
     {{- include "dubbo-admin.labels" . | nindent 4 }}
-    {{- with .Values.persistence.extraPvcLabels }}
-    {{- toYaml . | nindent 4 }}
-    {{- end }}
   {{- with .Values.persistence.annotations  }}
   annotations:
     {{- toYaml . | nindent 4 }}
   {{- end }}
-  {{- with .Values.persistence.finalizers  }}
-  finalizers:
-    {{- toYaml . | nindent 4 }}
-  {{- end }}
 spec:
   accessModes:
     {{- range .Values.persistence.accessModes }}
@@ -25,7 +18,7 @@
   resources:
     requests:
       storage: {{ .Values.persistence.size | quote }}
-  {{- with .Values.persistence.storageClassName }}
+  {{- with .Values.persistence.storageClass }}
   storageClassName: {{ . }}
   {{- end }}
   {{- with .Values.persistence.selectorLabels }}
diff --git a/charts/dubbo-admin/templates/admin-role.yaml b/charts/admin-stack/charts/dubbo-admin/templates/role.yaml
similarity index 64%
rename from charts/dubbo-admin/templates/admin-role.yaml
rename to charts/admin-stack/charts/dubbo-admin/templates/role.yaml
index de391e7..b096ba5 100644
--- a/charts/dubbo-admin/templates/admin-role.yaml
+++ b/charts/admin-stack/charts/dubbo-admin/templates/role.yaml
@@ -1,4 +1,4 @@
-{{- if and .Values.rbac.enabled (not .Values.rbac.useExistingRole) -}}
+{{- if and .Values.rbac.enabled -}}
 apiVersion: {{ include "dubbo-admin.rbac.apiVersion" . }}
 kind: Role
 metadata:
@@ -6,6 +6,9 @@
   namespace: {{ include "dubbo-admin.namespace" . }}
   labels:
     {{- include "dubbo-admin.labels" . | nindent 4 }}
+  {{- with .Values.labels }}
+  {{- toYaml . | nindent 4 }}
+  {{- end }}
   {{- with .Values.annotations }}
   annotations:
     {{- toYaml . | nindent 4 }}
@@ -22,15 +25,5 @@
     resourceNames:
       - {{ include "dubbo-admin.fullname" . }}
   {{- end }}
-  {{- if .Values.rbac.namespaced }}
-  - apiGroups: [""] # "" indicates the core API group
-    resources: ["configmaps", "secrets"]
-    verbs: ["get", "watch", "list"]
-  {{- end }}
-  {{- with .Values.rbac.extraRoleRules }}
-  {{- toYaml . | nindent 2 }}
-  {{- end}}
-{{- else }}
-rules: []
 {{- end }}
 {{- end }}
diff --git a/charts/dubbo-admin/templates/admin-rolebinding.yaml b/charts/admin-stack/charts/dubbo-admin/templates/rolebinding.yaml
similarity index 85%
rename from charts/dubbo-admin/templates/admin-rolebinding.yaml
rename to charts/admin-stack/charts/dubbo-admin/templates/rolebinding.yaml
index 49034af..ecf0b94 100644
--- a/charts/dubbo-admin/templates/admin-rolebinding.yaml
+++ b/charts/admin-stack/charts/dubbo-admin/templates/rolebinding.yaml
@@ -6,6 +6,9 @@
   namespace: {{ include "dubbo-admin.namespace" . }}
   labels:
     {{- include "dubbo-admin.labels" . | nindent 4 }}
+  {{- with .Values.labels }}
+  {{- toYaml . | nindent 4 }}
+  {{- end }}
   {{- with .Values.annotations }}
   annotations:
     {{- toYaml . | nindent 4 }}
@@ -13,13 +16,9 @@
 roleRef:
   apiGroup: rbac.authorization.k8s.io
   kind: Role
-  {{- if .Values.rbac.useExistingRole }}
-  name: {{ .Values.rbac.useExistingRole }}
-  {{- else }}
   name: {{ include "dubbo-admin.fullname" . }}
   {{- end }}
 subjects:
   - kind: ServiceAccount
     name: {{ include "dubbo-admin.serviceAccountName" . }}
     namespace: {{ include "dubbo-admin.namespace" . }}
-{{- end }}
diff --git a/charts/dubbo-admin/templates/admin-secret.yaml b/charts/admin-stack/charts/dubbo-admin/templates/secret.yaml
similarity index 77%
rename from charts/dubbo-admin/templates/admin-secret.yaml
rename to charts/admin-stack/charts/dubbo-admin/templates/secret.yaml
index e18ce8c..fcad8fe 100644
--- a/charts/dubbo-admin/templates/admin-secret.yaml
+++ b/charts/admin-stack/charts/dubbo-admin/templates/secret.yaml
@@ -5,5 +5,9 @@
   namespace: {{ include "dubbo-admin.namespace" . }}
   labels:
     {{- include "dubbo-admin.labels" . | nindent 4 }}
+  {{- with .Values.labels }}
+  {{- toYaml . | nindent 4 }}
+  {{- end }}
+type: Opaque
 data:
   application.properties: {{ tpl (toYaml .Values.properties) . | b64enc }}
diff --git a/charts/dubbo-admin/templates/admin-serviceaccount.yaml b/charts/admin-stack/charts/dubbo-admin/templates/serviceaccount.yaml
similarity index 100%
rename from charts/dubbo-admin/templates/admin-serviceaccount.yaml
rename to charts/admin-stack/charts/dubbo-admin/templates/serviceaccount.yaml
diff --git a/charts/dubbo-admin/templates/admin-svc-headless.yaml b/charts/admin-stack/charts/dubbo-admin/templates/svc-headless.yaml
similarity index 94%
rename from charts/dubbo-admin/templates/admin-svc-headless.yaml
rename to charts/admin-stack/charts/dubbo-admin/templates/svc-headless.yaml
index 6776177..0a5c086 100644
--- a/charts/dubbo-admin/templates/admin-svc-headless.yaml
+++ b/charts/admin-stack/charts/dubbo-admin/templates/svc-headless.yaml
@@ -6,6 +6,9 @@
   namespace: {{ include "dubbo-admin.namespace" . }}
   labels:
     {{- include "dubbo-admin.labels" . | nindent 4 }}
+  {{- with .Values.labels }}
+  {{- toYaml . | nindent 4 }}
+  {{- end }}
 spec:
   {{- if (or (eq .Values.service.type "ClusterIP") (empty .Values.service.type)) }}
   type: {{ .Values.service.type }}
diff --git a/charts/dubbo-admin/templates/admin-svc.yaml b/charts/admin-stack/charts/dubbo-admin/templates/svc.yaml
similarity index 94%
rename from charts/dubbo-admin/templates/admin-svc.yaml
rename to charts/admin-stack/charts/dubbo-admin/templates/svc.yaml
index 7771dc6..941c917 100644
--- a/charts/dubbo-admin/templates/admin-svc.yaml
+++ b/charts/admin-stack/charts/dubbo-admin/templates/svc.yaml
@@ -6,6 +6,9 @@
   namespace: {{ include "dubbo-admin.namespace" . }}
   labels:
     {{- include "dubbo-admin.labels" . | nindent 4 }}
+  {{- with .Values.labels }}
+  {{- toYaml . | nindent 4 }}
+  {{- end }}
 spec:
   {{- if (or (eq .Values.service.type "ClusterIP") (empty .Values.service.type)) }}
   type: {{ .Values.service.type }}
diff --git a/charts/dubbo-admin/templates/tests/test-role.yaml b/charts/admin-stack/charts/dubbo-admin/templates/tests/test-role.yaml
similarity index 100%
rename from charts/dubbo-admin/templates/tests/test-role.yaml
rename to charts/admin-stack/charts/dubbo-admin/templates/tests/test-role.yaml
diff --git a/charts/dubbo-admin/templates/tests/test-rolebinding.yaml b/charts/admin-stack/charts/dubbo-admin/templates/tests/test-rolebinding.yaml
similarity index 100%
rename from charts/dubbo-admin/templates/tests/test-rolebinding.yaml
rename to charts/admin-stack/charts/dubbo-admin/templates/tests/test-rolebinding.yaml
diff --git a/charts/dubbo-admin/templates/tests/test-secret.yaml b/charts/admin-stack/charts/dubbo-admin/templates/tests/test-secret.yaml
similarity index 96%
rename from charts/dubbo-admin/templates/tests/test-secret.yaml
rename to charts/admin-stack/charts/dubbo-admin/templates/tests/test-secret.yaml
index 2fd8384..7ee857b 100644
--- a/charts/dubbo-admin/templates/tests/test-secret.yaml
+++ b/charts/admin-stack/charts/dubbo-admin/templates/tests/test-secret.yaml
@@ -8,6 +8,6 @@
     "helm.sh/hook-delete-policy": "before-hook-creation,hook-succeeded"
   labels:
     {{- include "dubbo-admin.labels" . | nindent 4 }}
-  type: Opaque
+type: Opaque
 data:
   application.properties: {{ tpl (toYaml .Values.properties) . | b64enc }}-test
diff --git a/charts/dubbo-admin/templates/tests/test-serviceaccount.yaml b/charts/admin-stack/charts/dubbo-admin/templates/tests/test-serviceaccount.yaml
similarity index 100%
rename from charts/dubbo-admin/templates/tests/test-serviceaccount.yaml
rename to charts/admin-stack/charts/dubbo-admin/templates/tests/test-serviceaccount.yaml
diff --git a/charts/dubbo-admin/templates/tests/test.yaml b/charts/admin-stack/charts/dubbo-admin/templates/tests/test.yaml
similarity index 100%
rename from charts/dubbo-admin/templates/tests/test.yaml
rename to charts/admin-stack/charts/dubbo-admin/templates/tests/test.yaml
diff --git a/charts/admin-stack/charts/dubbo-admin/values.yaml b/charts/admin-stack/charts/dubbo-admin/values.yaml
new file mode 100644
index 0000000..557d221
--- /dev/null
+++ b/charts/admin-stack/charts/dubbo-admin/values.yaml
@@ -0,0 +1,413 @@
+image:
+  registry: docker.io
+  ##  E.g registry.k8s.io
+  ##
+  repository: apache/dubbo-admin
+  ##
+  ##
+  tag: "0.5.0"
+  ##
+  ##
+  debug: false
+  ##
+  ## Specify a imagePullPolicy
+  ## Defaults to 'Always' if image tag is 'latest', else set to 'IfNotPresent'
+  ## ref: https://kubernetes.io/docs/user-guide/images/#pre-pulling-images
+  ##
+  pullPolicy: IfNotPresent
+  ##
+  ## Optionally specify an array of imagePullSecrets.
+  ## Secrets must be manually created in the namespace.
+  ## ref: https://kubernetes.io/docs/tasks/configure-pod-container/pull-image-private-registry/
+  ## Can be templated.
+  ##
+  pullSecrets: []
+  #   - RegisterKeySecretName
+
+replicas: 1
+
+## global.imageRegistry Global Docker image registry
+## global.imagePullSecrets Global Docker registry secret names as an array
+## global.storageClass Global StorageClass for Persistent Volume(s)
+##
+global:
+  imageRegistry: ""
+  ## E.g.
+  ## imagePullSecrets:
+  ##   - myRegistryKeySecretName
+  ##
+  imagePullSecrets: []
+
+
+rbac:
+  # Use an existing ClusterRole/Role (depending on rbac.namespaced false/true)
+  enabled: true
+  pspEnabled: true
+
+
+## serviceAccount
+serviceAccount:
+  enabled: true
+  ## ## ServiceAccount name.
+  name: {}
+  ## ServiceAccount nameTests.
+  nameTest: {}
+  ## ServiceAccount labels.
+  labels: {}
+  ## ServiceAccount annotations.
+  annotations: {}
+
+
+# -- Optional array of imagePullSecrets containing private registry credentials
+## Ref: https://kubernetes.io/docs/tasks/configure-pod-container/pull-image-private-registry/
+imagePullSecrets: []
+# - name: secretName
+
+
+## Create HorizontalPodAutoscaler object for deployment type
+autoscaling:
+  enabled: false
+  minReplicas: 1
+  maxReplicas: 5
+  targetCPU: "60"
+  targetMemory: ""
+  behavior: {}
+
+
+## See `kubectl explain deployment.spec.strategy` for more
+## ref: https://kubernetes.io/docs/concepts/workloads/controllers/deployment/#strategy
+deploymentStrategy:
+  type: RollingUpdate
+
+
+## @param readinessProbe.enabled Enable readinessProbe on containers
+readinessProbe:
+  httpGet:
+    path: /
+    port: 8080
+  ## @param readinessProbe.initialDelaySeconds Initial delay seconds for readinessProbe
+  initialDelaySeconds: 60
+  ## @param readinessProbe.timeoutSeconds Timeout seconds for readinessProbe
+  timeoutSeconds: 30
+  ## @param readinessProbe.periodSeconds Period seconds for readinessProbe
+  periodSeconds: 10
+  ## @param readinessProbe.successThreshold Success threshold for readinessProbe
+  successThreshold: 1
+  ## @param readinessProbe.failureThreshold Failure threshold for readinessProbe
+  failureThreshold: 3
+  ## @param readinessProbe.probeCommandTimeout Probe command timeout for readinessProbe
+  probeCommandTimeout: 1
+
+
+## @param livenessProbe.enabled Enable livenessProbe on containers
+livenessProbe:
+  httpGet:
+    path: /
+    port: 8080
+  ## @param livenessProbe.initialDelaySeconds Initial delay seconds for livenessProbe
+  initialDelaySeconds: 60
+  ## @param livenessProbe.timeoutSeconds Timeout seconds for livenessProbe
+  timeoutSeconds: 30
+  ## @param livenessProbe.periodSeconds Period seconds for livenessProbe
+  periodSeconds: 10
+  ## @param livenessProbe.successThreshold Success threshold for livenessProbe
+  successThreshold: 1
+  ## @param livenessProbe.failureThreshold Failure threshold for livenessProbe
+  failureThreshold: 3
+  ## @param livenessProbe.probeCommandTimeout Probe command timeout for livenessProbe
+  probeCommandTimeout: 1
+
+
+## @param startupProbe.enabled Enable startupProbe on containers
+startupProbe:
+  httpGet:
+    path: /
+    port: 8080
+  ## @param startupProbe.initialDelaySeconds Initial delay seconds for startupProbe
+  initialDelaySeconds: 60
+  ## @param startupProbe.timeoutSeconds Timeout seconds for startupProbe
+  timeoutSeconds: 30
+  ## @param startupProbe.periodSeconds Period seconds for startupProbe
+  periodSeconds: 10
+  ## @param startupProbe.successThreshold Success threshold for startupProbe
+  successThreshold: 1
+  ## @param startupProbe.failureThreshold Failure threshold for startupProbe
+  failureThreshold: 3
+
+
+tests:
+  enabled: true
+  image: busybox
+  tag: ""
+  imagePullPolicy: IfNotPresent
+  securityContext: {}
+
+
+## configmap mounts
+ConfigmapMounts: []
+  # - name: configMap-file
+  #   mountPath: /config
+  #   configMap: configMap-file
+  #   readOnly: true
+
+
+## secret mounts
+SecretMounts:
+#  - name: secret-file
+#    secret:
+#      secretName: secret-file
+
+
+## emptyDir mounts
+EmptyDirMounts: []
+# - name: ""
+#   mountPath: /
+
+
+## Expose the dubbo-admin service to be accessed from outside the cluster (LoadBalancer service).
+## or access it from within the cluster (ClusterIP service). Set the service type and the port to serve it.
+## ref: http://kubernetes.io/docs/user-guide/services/
+##
+service:
+  name: http
+  ##
+  ## Service name.
+  ##
+  enabled: true
+  ##
+  ## Service enable true or false.
+  ##
+  type: ClusterIP
+  ##
+  ## Service type.
+  ##
+  clusterIP: ""
+  ##
+  ## Service clusterIP.
+  ##
+  loadBalancerIP: ""
+  ##
+  ## Service loadBalancerIP.
+  ##
+  loadBalancerSourceRanges: ""
+  ##
+  ## Service loadBalancerSourceRanges.
+  ##
+  externalIPs: ""
+  ##
+  ## Service externalIPs.
+  ##
+  nodePort: ""
+  ##
+  ## Service nodePort.
+  ##
+  path: /
+  ##
+  ## Service path.
+  ##
+  port: 38080
+  ##
+  ## Service port.
+  ##
+  targetPort: http
+  ##
+  ## Service targetPort.
+  ##
+  containerPort: 8080
+  ##
+  ## Service containerPort.
+  ##
+  protocol: TCP
+  ##
+  ## Service protocol.
+  ##
+  ##
+  labels: {}
+  ##
+  ## Service labels.
+  ##
+  annotations: {}
+  ##
+  ## Service annotations. Can be templated.
+  ##
+  portName: service
+  ##
+  ## Service portName.
+  ##
+  appProtocol: ""
+  ##
+  ## Service appProtocol.
+  ##
+
+
+ingress:
+  enabled: false
+  # For Kubernetes >= 1.18 you should specify the ingress-controller via the field ingressClassName
+  # See https://kubernetes.io/blog/2020/04/02/improvements-to-the-ingress-api-in-kubernetes-1.18/#specifying-the-class-of-an-ingress
+  # ingressClassName: nginx
+  # Values can be templated
+  annotations: {}
+  # kubernetes.io/ingress.class: nginx
+  # kubernetes.io/tls-acme: "true"
+  labels: {}
+  path: /
+  ##
+  ##
+  # pathType is only for k8s >= 1.1=
+  pathType: Prefix
+  ##
+  ##
+  hosts:
+    - chart-example.local
+  ## Extra paths to prepend to every host configuration. This is useful when working with annotation based services.
+  extraPaths: []
+  # - path: /*
+  #   backend:
+  #     serviceName: ssl-redirect
+  #     servicePort: use-annotation
+  ## Or for k8s > 1.19
+  # - path: /*
+  #   pathType: Prefix
+  #   backend:
+  #     service:
+  #       name: ssl-redirect
+  #       port:
+  #         name: use-annotation
+  ##
+  ##
+  tls: []
+  #  - secretName: chart-example-tls
+  #    hosts:
+  #      - chart-example.local
+
+
+resources: {}
+#  limits:
+#    cpu: 100m
+#    memory: 128Mi
+#  requests:
+#    cpu: 100m
+#    memory: 128Mi
+
+
+## Enable persistence using Persistent Volume Claims
+## ref: http://kubernetes.io/docs/user-guide/persistent-volumes/
+##
+persistence:
+  enabled: false
+  storageClass: ""
+  accessModes:
+    - ReadWriteOnce
+  size: 10Gi
+  ## Name of an existing PVC. Can be templated.
+  ClaimName: {}
+  ##
+  ## persistence emptyDir
+  emptyDir: {}
+
+
+securityContext:
+  runAsNonRoot: false
+  runAsUser: 0
+
+
+## Container Lifecycle Hooks. Execute a specific bash command or make an HTTP request
+lifecycleHooks: {}
+  # postStart:
+  #   exec:
+  #     command: []
+  # preStop:
+  #   exec:
+  #     command: []
+
+
+## See `kubectl explain poddisruptionbudget.spec` for more
+## ref: https://kubernetes.io/docs/tasks/run-application/configure-pdb/
+podDisruptionBudget:
+  enabled: false
+  minAvailable: 1
+  # maxUnavailable: 1
+
+
+networkPolicy:
+  ## @param networkPolicy.enabled Enable creation of NetworkPolicy resources. Only Ingress traffic is filtered for now.
+  ##
+  enabled: false
+  ## @param networkPolicy.allowExternal Don't require client label for connections
+  ## The Policy model to apply. When set to false, only pods with the correct
+  ## client label will have network access to  dubbo-admin port defined.
+  ## When true, dubbo-admin will accept connections from any source
+  ## (with the correct destination port).
+  ##
+  ingress: true
+  ## @param networkPolicy.ingress When true enables the creation
+  ## an ingress network policy
+  ##
+  ##
+  ##
+  ##
+  egress:
+    ## @param networkPolicy.egress.enabled When enabled, an egress network policy will be
+    ## created allowing dubbo-admin to connect to external data sources from kubernetes cluster.
+    enabled: false
+    ##
+    ## @param networkPolicy.egress.ports Add individual ports to be allowed by the egress
+    ports: []
+      ## Add ports to the egress by specifying - port: <port number>
+      ## E.X.
+      ## ports:
+      ## - port: 80
+      ## - port: 443
+
+
+
+
+##  @param Dubbo-admin Default Enable Configuration
+properties:
+  admin.registry.address: zookeeper://zookeeper:2181
+  admin.config-center: zookeeper://zookeeper:2181
+  admin.metadata-report.address: zookeeper://zookeeper:2181
+  admin.root.user.name: root
+  admin.root.user.password: root
+  admin.check.sessionTimeoutMilli: 3600000
+  server.compression.enabled: true
+  server.compression.mime-types: text/css,text/javascript,application/javascript
+  server.compression.min-response-size: 10240
+  admin.check.tokenTimeoutMilli: 3600000
+  admin.check.signSecret: 86295dd0c4ef69a1036b0b0c15158d77
+  dubbo.application.name: dubbo-admin
+  dubbo.registry.address: ${admin.registry.address}
+  spring.datasource.url: jdbc:h2:mem:~/dubbo-admin;MODE=MYSQL;
+  spring.datasource.username: sa
+  spring.datasource.password:
+  mybatis-plus.global-config.db-config.id-type: none
+  dubbo.application.logger: slf4j
+
+  # nacos config, add parameters to url like username=nacos&password=nacos
+  # admin.registry.address: nacos://nacos:8848?group=DEFAULT_GROUP&namespace=public
+  # admin.config-center: nacos://nacos:8848?group=dubbo
+  # admin.metadata-report.address: nacos://nacos:8848?group=dubbo
+
+
+  # group (Deprecated it is recommended to use URL to add parameters,will be removed in the future)
+  # admin.registry.group: dubbo
+  # admin.config-center.group: dubbo
+  # admin.metadata-report.group: dubbo
+
+  # namespace used by nacos.(Deprecated it is recommended to use URL to add parameters,will be removed in the future)
+  # admin.registry.namespace: public
+  # admin.config-center.namespace: public
+  # admin.metadata-report.namespace: public
+
+  # apollo config
+  # admin.config-center: apollo://localhost:8070?token=e16e5cd903fd0c97a116c873b448544b9d086de9&app.id=test&env=dev&cluster=default&namespace=dubbo
+  # admin.apollo.token: e16e5cd903fd0c97a116c873b448544b9d086de9
+  # admin.apollo.appId: test
+  # admin.apollo.env: dev
+  # admin.apollo.cluster: default
+
+  # mysql
+  # spring.datasource.driver-class-name: com.mysql.jdbc.Driver
+  # spring.datasource.url: jdbc:mysql://localhost:3306/dubbo-admin?characterEncoding=utf8&connectTimeout=1000&socketTimeout=10000&autoReconnect=true
+  # spring.datasource.username: root
+  # spring.datasource.password: mysql
\ No newline at end of file
diff --git a/charts/dubbo-admin/.helmignore b/charts/admin-stack/charts/grafana/.helmignore
similarity index 100%
copy from charts/dubbo-admin/.helmignore
copy to charts/admin-stack/charts/grafana/.helmignore
diff --git a/charts/admin-stack/charts/grafana/Chart.yaml b/charts/admin-stack/charts/grafana/Chart.yaml
new file mode 100644
index 0000000..9886092
--- /dev/null
+++ b/charts/admin-stack/charts/grafana/Chart.yaml
@@ -0,0 +1,13 @@
+apiVersion: v2
+appVersion: 9.3.6
+description: The leading tool for querying and visualizing time series and metrics.
+home: https://grafana.net
+kubeVersion: ^1.8.0-0
+maintainers:
+  - email: dev@dubbo.apache.org
+    name: dubbo
+name: grafana
+sources:
+  - https://github.com/grafana/grafana
+type: application
+version: 6.50.6
diff --git a/charts/admin-stack/charts/grafana/dashboards/custom-dashboard.json b/charts/admin-stack/charts/grafana/dashboards/custom-dashboard.json
new file mode 100644
index 0000000..9e26dfe
--- /dev/null
+++ b/charts/admin-stack/charts/grafana/dashboards/custom-dashboard.json
@@ -0,0 +1 @@
+{}
\ No newline at end of file
diff --git a/charts/admin-stack/charts/grafana/templates/_helpers.tpl b/charts/admin-stack/charts/grafana/templates/_helpers.tpl
new file mode 100644
index 0000000..03db144
--- /dev/null
+++ b/charts/admin-stack/charts/grafana/templates/_helpers.tpl
@@ -0,0 +1,219 @@
+{{/* vim: set filetype=mustache: */}}
+{{/*
+Expand the name of the chart.
+*/}}
+{{- define "grafana.name" -}}
+{{- default .Chart.Name .Values.nameOverride | trunc 63 | trimSuffix "-" }}
+{{- end }}
+
+
+{{/*
+Create a default fully qualified app name.
+We truncate at 63 chars because some Kubernetes name fields are limited to this (by the DNS naming spec).
+If release name contains chart name it will be used as a full name.
+*/}}
+{{- define "grafana.fullname" -}}
+{{- if .Values.fullnameOverride }}
+{{- .Values.fullnameOverride | trunc 63 | trimSuffix "-" }}
+{{- else }}
+{{- $name := default .Chart.Name .Values.nameOverride }}
+{{- if contains $name .Release.Name }}
+{{- .Release.Name | trunc 63 | trimSuffix "-" }}
+{{- else }}
+{{- printf "%s-%s" .Release.Name $name | trunc 63 | trimSuffix "-" }}
+{{- end }}
+{{- end }}
+{{- end }}
+
+
+{{/*
+Create chart name and version as used by the chart label.
+*/}}
+{{- define "grafana.chart" -}}
+{{- printf "%s-%s" .Chart.Name .Chart.Version | replace "+" "_" | trunc 63 | trimSuffix "-" }}
+{{- end }}
+
+
+{{/*
+Create the name of the service account
+*/}}
+{{- define "grafana.serviceAccountName" -}}
+{{- if .Values.serviceAccount.create }}
+{{- default (include "grafana.fullname" .) .Values.serviceAccount.name }}
+{{- else }}
+{{- default "default" .Values.serviceAccount.name }}
+{{- end }}
+{{- end }}
+
+
+{{- define "grafana.serviceAccountNameTest" -}}
+{{- if .Values.serviceAccount.create }}
+{{- default (print (include "grafana.fullname" .) "-test") .Values.serviceAccount.nameTest }}
+{{- else }}
+{{- default "default" .Values.serviceAccount.nameTest }}
+{{- end }}
+{{- end }}
+
+
+{{/*
+Allow the release namespace to be overridden for multi-namespace deployments in combined charts
+*/}}
+{{- define "grafana.namespace" -}}
+{{- if .Values.namespaceOverride }}
+{{- .Values.namespaceOverride }}
+{{- else }}
+{{- .Release.Namespace }}
+{{- end }}
+{{- end }}
+
+
+{{/*
+Common labels
+*/}}
+{{- define "grafana.labels" -}}
+helm.sh/chart: {{ include "grafana.chart" . }}
+{{ include "grafana.selectorLabels" . }}
+{{- if or .Chart.AppVersion .Values.image.tag }}
+app.kubernetes.io/version: {{ mustRegexReplaceAllLiteral "@sha.*" .Values.image.tag "" | default .Chart.AppVersion | quote }}
+{{- end }}
+app.kubernetes.io/managed-by: {{ .Release.Service }}
+{{- with .Values.extraLabels }}
+{{ toYaml . }}
+{{- end }}
+{{- end }}
+
+
+{{/*
+Selector labels
+*/}}
+{{- define "grafana.selectorLabels" -}}
+app.kubernetes.io/name: {{ include "grafana.name" . }}
+app.kubernetes.io/instance: {{ .Release.Name }}
+{{- end }}
+
+
+{{/*
+Common labels
+*/}}
+{{- define "grafana.imageRenderer.labels" -}}
+helm.sh/chart: {{ include "grafana.chart" . }}
+{{ include "grafana.imageRenderer.selectorLabels" . }}
+{{- if or .Chart.AppVersion .Values.image.tag }}
+app.kubernetes.io/version: {{ mustRegexReplaceAllLiteral "@sha.*" .Values.image.tag "" | default .Chart.AppVersion | quote }}
+{{- end }}
+app.kubernetes.io/managed-by: {{ .Release.Service }}
+{{- end }}
+
+
+{{/*
+Selector labels ImageRenderer
+*/}}
+{{- define "grafana.imageRenderer.selectorLabels" -}}
+app.kubernetes.io/name: {{ include "grafana.name" . }}-image-renderer
+app.kubernetes.io/instance: {{ .Release.Name }}
+{{- end }}
+
+
+{{/*
+Looks if there's an existing secret and reuse its password. If not it generates
+new password and use it.
+*/}}
+{{- define "grafana.password" -}}
+{{- $secret := (lookup "v1" "Secret" (include "grafana.namespace" .) (include "grafana.fullname" .) ) }}
+{{- if $secret }}
+{{- index $secret "data" "admin-password" }}
+{{- else }}
+{{- (randAlphaNum 40) | b64enc | quote }}
+{{- end }}
+{{- end }}
+
+
+{{/*
+Return the appropriate apiVersion for rbac.
+*/}}
+{{- define "grafana.rbac.apiVersion" -}}
+{{- if $.Capabilities.APIVersions.Has "rbac.authorization.k8s.io/v1" }}
+{{- print "rbac.authorization.k8s.io/v1" }}
+{{- else }}
+{{- print "rbac.authorization.k8s.io/v1beta1" }}
+{{- end }}
+{{- end }}
+
+
+{{/*
+Return the appropriate apiVersion for ingress.
+*/}}
+{{- define "grafana.ingress.apiVersion" -}}
+{{- if and ($.Capabilities.APIVersions.Has "networking.k8s.io/v1") (semverCompare ">= 1.19-0" .Capabilities.KubeVersion.Version) }}
+{{- print "networking.k8s.io/v1" }}
+{{- else if $.Capabilities.APIVersions.Has "networking.k8s.io/v1beta1" }}
+{{- print "networking.k8s.io/v1beta1" }}
+{{- else }}
+{{- print "extensions/v1beta1" }}
+{{- end }}
+{{- end }}
+
+
+{{/*
+Return the appropriate apiVersion for Horizontal Pod Autoscaler.
+*/}}
+{{- define "grafana.hpa.apiVersion" -}}
+{{- if $.Capabilities.APIVersions.Has "autoscaling/v2/HorizontalPodAutoscaler" }}
+{{- print "autoscaling/v2" }}
+{{- else if $.Capabilities.APIVersions.Has "autoscaling/v2beta2/HorizontalPodAutoscaler" }}
+{{- print "autoscaling/v2beta2" }}
+{{- else }}
+{{- print "autoscaling/v2beta1" }}
+{{- end }}
+{{- end }}
+
+
+{{/*
+Return the appropriate apiVersion for podDisruptionBudget.
+*/}}
+{{- define "grafana.podDisruptionBudget.apiVersion" -}}
+{{- if $.Capabilities.APIVersions.Has "policy/v1/PodDisruptionBudget" }}
+{{- print "policy/v1" }}
+{{- else }}
+{{- print "policy/v1beta1" }}
+{{- end }}
+{{- end }}
+
+
+{{/*
+Return if ingress is stable.
+*/}}
+{{- define "grafana.ingress.isStable" -}}
+{{- eq (include "grafana.ingress.apiVersion" .) "networking.k8s.io/v1" }}
+{{- end }}
+
+
+{{/*
+Return if ingress supports ingressClassName.
+*/}}
+{{- define "grafana.ingress.supportsIngressClassName" -}}
+{{- or (eq (include "grafana.ingress.isStable" .) "true") (and (eq (include "grafana.ingress.apiVersion" .) "networking.k8s.io/v1beta1") (semverCompare ">= 1.18-0" .Capabilities.KubeVersion.Version)) }}
+{{- end }}
+
+
+{{/*
+Return if ingress supports pathType.
+*/}}
+{{- define "grafana.ingress.supportsPathType" -}}
+{{- or (eq (include "grafana.ingress.isStable" .) "true") (and (eq (include "grafana.ingress.apiVersion" .) "networking.k8s.io/v1beta1") (semverCompare ">= 1.18-0" .Capabilities.KubeVersion.Version)) }}
+{{- end }}
+
+
+{{/*
+Formats imagePullSecrets. Input is (dict "root" . "imagePullSecrets" .{specific imagePullSecrets})
+*/}}
+{{- define "grafana.imagePullSecrets" -}}
+{{- $root := .root }}
+{{- range (concat .root.Values.global.imagePullSecrets .imagePullSecrets) }}
+{{- if eq (typeOf .) "map[string]interface {}" }}
+- {{ toYaml (dict "name" (tpl .name $root)) | trim }}
+{{- else }}
+- name: {{ tpl . $root }}
+{{- end }}
+{{- end }}
+{{- end }}
diff --git a/charts/admin-stack/charts/grafana/templates/_pod.tpl b/charts/admin-stack/charts/grafana/templates/_pod.tpl
new file mode 100644
index 0000000..4c4755d
--- /dev/null
+++ b/charts/admin-stack/charts/grafana/templates/_pod.tpl
@@ -0,0 +1,1153 @@
+{{- define "grafana.pod" -}}
+{{- $sts := list "sts" "StatefulSet" "statefulset" -}}
+{{- $root := . -}}
+{{- with .Values.schedulerName }}
+schedulerName: "{{ . }}"
+{{- end }}
+serviceAccountName: {{ include "grafana.serviceAccountName" . }}
+automountServiceAccountToken: {{ .Values.serviceAccount.autoMount }}
+{{- with .Values.securityContext }}
+securityContext:
+  {{- toYaml . | nindent 2 }}
+{{- end }}
+{{- with .Values.hostAliases }}
+hostAliases:
+  {{- toYaml . | nindent 2 }}
+{{- end }}
+{{- with .Values.priorityClassName }}
+priorityClassName: {{ . }}
+{{- end }}
+{{- if ( or .Values.persistence.enabled .Values.dashboards .Values.extraInitContainers (and .Values.sidecar.datasources.enabled .Values.sidecar.datasources.initDatasources) (and .Values.sidecar.notifiers.enabled .Values.sidecar.notifiers.initNotifiers)) }}
+initContainers:
+{{- end }}
+{{- if ( and .Values.persistence.enabled .Values.initChownData.enabled ) }}
+  - name: init-chown-data
+    {{- if .Values.initChownData.image.sha }}
+    image: "{{ .Values.initChownData.image.repository }}:{{ .Values.initChownData.image.tag }}@sha256:{{ .Values.initChownData.image.sha }}"
+    {{- else }}
+    image: "{{ .Values.initChownData.image.repository }}:{{ .Values.initChownData.image.tag }}"
+    {{- end }}
+    imagePullPolicy: {{ .Values.initChownData.image.pullPolicy }}
+    {{- with .Values.initChownData.securityContext }}
+    securityContext:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    command:
+      - chown
+      - -R
+      - {{ .Values.securityContext.runAsUser }}:{{ .Values.securityContext.runAsGroup }}
+      - /var/lib/grafana
+    {{- with .Values.initChownData.resources }}
+    resources:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    volumeMounts:
+      - name: storage
+        mountPath: "/var/lib/grafana"
+        {{- with .Values.persistence.subPath }}
+        subPath: {{ tpl . $root }}
+        {{- end }}
+{{- end }}
+{{- if .Values.dashboards }}
+  - name: download-dashboards
+    {{- if .Values.downloadDashboardsImage.sha }}
+    image: "{{ .Values.downloadDashboardsImage.repository }}:{{ .Values.downloadDashboardsImage.tag }}@sha256:{{ .Values.downloadDashboardsImage.sha }}"
+    {{- else }}
+    image: "{{ .Values.downloadDashboardsImage.repository }}:{{ .Values.downloadDashboardsImage.tag }}"
+    {{- end }}
+    imagePullPolicy: {{ .Values.downloadDashboardsImage.pullPolicy }}
+    command: ["/bin/sh"]
+    args: [ "-c", "mkdir -p /var/lib/grafana/dashboards/default && /bin/sh -x /etc/grafana/download_dashboards.sh" ]
+    {{- with .Values.downloadDashboards.resources }}
+    resources:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    env:
+      {{- range $key, $value := .Values.downloadDashboards.env }}
+      - name: "{{ $key }}"
+        value: "{{ $value }}"
+      {{- end }}
+      {{- range $key, $value := .Values.downloadDashboards.envValueFrom }}
+      - name: {{ $key | quote }}
+        valueFrom:
+          {{- tpl (toYaml $value) $ | nindent 10 }}
+      {{- end }}
+    {{- with .Values.downloadDashboards.securityContext }}
+    securityContext:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    {{- with .Values.downloadDashboards.envFromSecret }}
+    envFrom:
+      - secretRef:
+          name: {{ tpl . $root }}
+    {{- end }}
+    volumeMounts:
+      - name: config
+        mountPath: "/etc/grafana/download_dashboards.sh"
+        subPath: download_dashboards.sh
+      - name: storage
+        mountPath: "/var/lib/grafana"
+        {{- with .Values.persistence.subPath }}
+        subPath: {{ tpl . $root }}
+        {{- end }}
+      {{- range .Values.extraSecretMounts }}
+      - name: {{ .name }}
+        mountPath: {{ .mountPath }}
+        readOnly: {{ .readOnly }}
+      {{- end }}
+{{- end }}
+{{- if and .Values.sidecar.datasources.enabled .Values.sidecar.datasources.initDatasources }}
+  - name: {{ include "grafana.name" . }}-init-sc-datasources
+    {{- if .Values.sidecar.image.sha }}
+    image: "{{ .Values.sidecar.image.repository }}:{{ .Values.sidecar.image.tag }}@sha256:{{ .Values.sidecar.image.sha }}"
+    {{- else }}
+    image: "{{ .Values.sidecar.image.repository }}:{{ .Values.sidecar.image.tag }}"
+    {{- end }}
+    imagePullPolicy: {{ .Values.sidecar.imagePullPolicy }}
+    env:
+      {{- range $key, $value := .Values.sidecar.datasources.env }}
+      - name: "{{ $key }}"
+        value: "{{ $value }}"
+      {{- end }}
+      {{- if .Values.sidecar.datasources.ignoreAlreadyProcessed }}
+      - name: IGNORE_ALREADY_PROCESSED
+        value: "true"
+      {{- end }}
+      - name: METHOD
+        value: "LIST"
+      - name: LABEL
+        value: "{{ .Values.sidecar.datasources.label }}"
+      {{- with .Values.sidecar.datasources.labelValue }}
+      - name: LABEL_VALUE
+        value: {{ quote . }}
+      {{- end }}
+      {{- if or .Values.sidecar.logLevel .Values.sidecar.datasources.logLevel }}
+      - name: LOG_LEVEL
+        value: {{ default .Values.sidecar.logLevel .Values.sidecar.datasources.logLevel }}
+      {{- end }}
+      - name: FOLDER
+        value: "/etc/grafana/provisioning/datasources"
+      - name: RESOURCE
+        value: {{ quote .Values.sidecar.datasources.resource }}
+      {{- with .Values.sidecar.enableUniqueFilenames }}
+      - name: UNIQUE_FILENAMES
+        value: "{{ . }}"
+      {{- end }}
+      {{- if .Values.sidecar.datasources.searchNamespace }}
+      - name: NAMESPACE
+        value: "{{ tpl (.Values.sidecar.datasources.searchNamespace | join ",") . }}"
+      {{- end }}
+      {{- with .Values.sidecar.skipTlsVerify }}
+      - name: SKIP_TLS_VERIFY
+        value: "{{ . }}"
+      {{- end }}
+    {{- with .Values.sidecar.resources }}
+    resources:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    {{- with .Values.sidecar.securityContext }}
+    securityContext:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    volumeMounts:
+      - name: sc-datasources-volume
+        mountPath: "/etc/grafana/provisioning/datasources"
+{{- end }}
+{{- if and .Values.sidecar.notifiers.enabled .Values.sidecar.notifiers.initNotifiers }}
+  - name: {{ include "grafana.name" . }}-init-sc-notifiers
+    {{- if .Values.sidecar.image.sha }}
+    image: "{{ .Values.sidecar.image.repository }}:{{ .Values.sidecar.image.tag }}@sha256:{{ .Values.sidecar.image.sha }}"
+    {{- else }}
+    image: "{{ .Values.sidecar.image.repository }}:{{ .Values.sidecar.image.tag }}"
+    {{- end }}
+    imagePullPolicy: {{ .Values.sidecar.imagePullPolicy }}
+    env:
+      {{- range $key, $value := .Values.sidecar.notifiers.env }}
+      - name: "{{ $key }}"
+        value: "{{ $value }}"
+      {{- end }}
+      {{- if .Values.sidecar.notifiers.ignoreAlreadyProcessed }}
+      - name: IGNORE_ALREADY_PROCESSED
+        value: "true"
+      {{- end }}
+      - name: METHOD
+        value: LIST
+      - name: LABEL
+        value: "{{ .Values.sidecar.notifiers.label }}"
+      {{- with .Values.sidecar.notifiers.labelValue }}
+      - name: LABEL_VALUE
+        value: {{ quote . }}
+      {{- end }}
+      {{- if or .Values.sidecar.logLevel .Values.sidecar.notifiers.logLevel }}
+      - name: LOG_LEVEL
+        value: {{ default .Values.sidecar.logLevel .Values.sidecar.notifiers.logLevel }}
+      {{- end }}
+      - name: FOLDER
+        value: "/etc/grafana/provisioning/notifiers"
+      - name: RESOURCE
+        value: {{ quote .Values.sidecar.notifiers.resource }}
+      {{- with .Values.sidecar.enableUniqueFilenames }}
+      - name: UNIQUE_FILENAMES
+        value: "{{ . }}"
+      {{- end }}
+      {{- with .Values.sidecar.notifiers.searchNamespace }}
+      - name: NAMESPACE
+        value: "{{ tpl (. | join ",") $root }}"
+      {{- end }}
+      {{- with .Values.sidecar.skipTlsVerify }}
+      - name: SKIP_TLS_VERIFY
+        value: "{{ . }}"
+      {{- end }}
+    {{- with .Values.sidecar.livenessProbe }}
+    livenessProbe:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    {{- with .Values.sidecar.readinessProbe }}
+    readinessProbe:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    {{- with .Values.sidecar.resources }}
+    resources:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    {{- with .Values.sidecar.securityContext }}
+    securityContext:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    volumeMounts:
+      - name: sc-notifiers-volume
+        mountPath: "/etc/grafana/provisioning/notifiers"
+{{- end}}
+{{- with .Values.extraInitContainers }}
+  {{- tpl (toYaml .) $root | nindent 2 }}
+{{- end }}
+{{- if or .Values.image.pullSecrets .Values.global.imagePullSecrets }}
+imagePullSecrets:
+  {{- include "grafana.imagePullSecrets" (dict "root" $root "imagePullSecrets" .Values.image.pullSecrets) | nindent 2 }}
+{{- end }}
+{{- if not .Values.enableKubeBackwardCompatibility }}
+enableServiceLinks: {{ .Values.enableServiceLinks }}
+{{- end }}
+containers:
+{{- if .Values.sidecar.alerts.enabled }}
+  - name: {{ include "grafana.name" . }}-sc-alerts
+    {{- if .Values.sidecar.image.sha }}
+    image: "{{ .Values.sidecar.image.repository }}:{{ .Values.sidecar.image.tag }}@sha256:{{ .Values.sidecar.image.sha }}"
+    {{- else }}
+    image: "{{ .Values.sidecar.image.repository }}:{{ .Values.sidecar.image.tag }}"
+    {{- end }}
+    imagePullPolicy: {{ .Values.sidecar.imagePullPolicy }}
+    env:
+      {{- range $key, $value := .Values.sidecar.alerts.env }}
+      - name: "{{ $key }}"
+        value: "{{ $value }}"
+      {{- end }}
+      {{- if .Values.sidecar.alerts.ignoreAlreadyProcessed }}
+      - name: IGNORE_ALREADY_PROCESSED
+        value: "true"
+      {{- end }}
+      - name: METHOD
+        value: {{ .Values.sidecar.alerts.watchMethod }}
+      - name: LABEL
+        value: "{{ .Values.sidecar.alerts.label }}"
+      {{- with .Values.sidecar.alerts.labelValue }}
+      - name: LABEL_VALUE
+        value: {{ quote . }}
+      {{- end }}
+      {{- if or .Values.sidecar.logLevel .Values.sidecar.alerts.logLevel }}
+      - name: LOG_LEVEL
+        value: {{ default .Values.sidecar.logLevel .Values.sidecar.alerts.logLevel }}
+      {{- end }}
+      - name: FOLDER
+        value: "/etc/grafana/provisioning/alerting"
+      - name: RESOURCE
+        value: {{ quote .Values.sidecar.alerts.resource }}
+      {{- with .Values.sidecar.enableUniqueFilenames }}
+      - name: UNIQUE_FILENAMES
+        value: "{{ . }}"
+      {{- end }}
+      {{- with .Values.sidecar.alerts.searchNamespace }}
+      - name: NAMESPACE
+        value: {{ . | join "," | quote }}
+      {{- end }}
+      {{- with .Values.sidecar.alerts.skipTlsVerify }}
+      - name: SKIP_TLS_VERIFY
+        value: {{ quote . }}
+      {{- end }}
+      {{- with .Values.sidecar.alerts.script }}
+      - name: SCRIPT
+        value: {{ quote . }}
+      {{- end }}
+      {{- if and (not .Values.env.GF_SECURITY_ADMIN_USER) (not .Values.env.GF_SECURITY_DISABLE_INITIAL_ADMIN_CREATION) }}
+      - name: REQ_USERNAME
+        valueFrom:
+          secretKeyRef:
+            name: {{ (tpl .Values.admin.existingSecret .) | default (include "grafana.fullname" .) }}
+            key: {{ .Values.admin.userKey | default "admin-user" }}
+      {{- end }}
+      {{- if and (not .Values.env.GF_SECURITY_ADMIN_PASSWORD) (not .Values.env.GF_SECURITY_ADMIN_PASSWORD__FILE) (not .Values.env.GF_SECURITY_DISABLE_INITIAL_ADMIN_CREATION) }}
+      - name: REQ_PASSWORD
+        valueFrom:
+          secretKeyRef:
+            name: {{ (tpl .Values.admin.existingSecret .) | default (include "grafana.fullname" .) }}
+            key: {{ .Values.admin.passwordKey | default "admin-password" }}
+      {{- end }}
+      {{- if not .Values.sidecar.alerts.skipReload }}
+      - name: REQ_URL
+        value: {{ .Values.sidecar.alerts.reloadURL }}
+      - name: REQ_METHOD
+        value: POST
+      {{- end }}
+      {{- if .Values.sidecar.alerts.watchServerTimeout }}
+      {{- if ne .Values.sidecar.alerts.watchMethod "WATCH" }}
+        {{- fail (printf "Cannot use .Values.sidecar.alerts.watchServerTimeout with .Values.sidecar.alerts.watchMethod %s" .Values.sidecar.alerts.watchMethod) }}
+      {{- end }}
+      - name: WATCH_SERVER_TIMEOUT
+        value: "{{ .Values.sidecar.alerts.watchServerTimeout }}"
+      {{- end }}
+      {{- if .Values.sidecar.alerts.watchClientTimeout }}
+      {{- if ne .Values.sidecar.alerts.watchMethod "WATCH" }}
+        {{- fail (printf "Cannot use .Values.sidecar.alerts.watchClientTimeout with .Values.sidecar.alerts.watchMethod %s" .Values.sidecar.alerts.watchMethod) }}
+      {{- end }}
+      - name: WATCH_CLIENT_TIMEOUT
+        value: "{{ .Values.sidecar.alerts.watchClientTimeout }}"
+      {{- end }}
+    {{- with .Values.sidecar.livenessProbe }}
+    livenessProbe:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    {{- with .Values.sidecar.readinessProbe }}
+    readinessProbe:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    {{- with .Values.sidecar.resources }}
+    resources:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    {{- with .Values.sidecar.securityContext }}
+    securityContext:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    volumeMounts:
+      - name: sc-alerts-volume
+        mountPath: "/etc/grafana/provisioning/alerting"
+{{- end}}
+{{- if .Values.sidecar.dashboards.enabled }}
+  - name: {{ include "grafana.name" . }}-sc-dashboard
+    {{- if .Values.sidecar.image.sha }}
+    image: "{{ .Values.sidecar.image.repository }}:{{ .Values.sidecar.image.tag }}@sha256:{{ .Values.sidecar.image.sha }}"
+    {{- else }}
+    image: "{{ .Values.sidecar.image.repository }}:{{ .Values.sidecar.image.tag }}"
+    {{- end }}
+    imagePullPolicy: {{ .Values.sidecar.imagePullPolicy }}
+    env:
+      {{- range $key, $value := .Values.sidecar.dashboards.env }}
+      - name: "{{ $key }}"
+        value: "{{ $value }}"
+      {{- end }}
+      {{- if .Values.sidecar.dashboards.ignoreAlreadyProcessed }}
+      - name: IGNORE_ALREADY_PROCESSED
+        value: "true"
+      {{- end }}
+      - name: METHOD
+        value: {{ .Values.sidecar.dashboards.watchMethod }}
+      - name: LABEL
+        value: "{{ .Values.sidecar.dashboards.label }}"
+      {{- with .Values.sidecar.dashboards.labelValue }}
+      - name: LABEL_VALUE
+        value: {{ quote . }}
+      {{- end }}
+      {{- if or .Values.sidecar.logLevel .Values.sidecar.dashboards.logLevel }}
+      - name: LOG_LEVEL
+        value: {{ default .Values.sidecar.logLevel .Values.sidecar.dashboards.logLevel }}
+      {{- end }}
+      - name: FOLDER
+        value: "{{ .Values.sidecar.dashboards.folder }}{{- with .Values.sidecar.dashboards.defaultFolderName }}/{{ . }}{{- end }}"
+      - name: RESOURCE
+        value: {{ quote .Values.sidecar.dashboards.resource }}
+      {{- with .Values.sidecar.enableUniqueFilenames }}
+      - name: UNIQUE_FILENAMES
+        value: "{{ . }}"
+      {{- end }}
+      {{- with .Values.sidecar.dashboards.searchNamespace }}
+      - name: NAMESPACE
+        value: "{{ tpl (. | join ",") $root }}"
+      {{- end }}
+      {{- with .Values.sidecar.skipTlsVerify }}
+      - name: SKIP_TLS_VERIFY
+        value: "{{ . }}"
+      {{- end }}
+      {{- with .Values.sidecar.dashboards.folderAnnotation }}
+      - name: FOLDER_ANNOTATION
+        value: "{{ . }}"
+      {{- end }}
+      {{- with .Values.sidecar.dashboards.script }}
+      - name: SCRIPT
+        value: "{{ . }}"
+      {{- end }}
+      {{- if and (not .Values.env.GF_SECURITY_ADMIN_USER) (not .Values.env.GF_SECURITY_DISABLE_INITIAL_ADMIN_CREATION) }}
+      - name: REQ_USERNAME
+        valueFrom:
+          secretKeyRef:
+            name: {{ (tpl .Values.admin.existingSecret .) | default (include "grafana.fullname" .) }}
+            key: {{ .Values.admin.userKey | default "admin-user" }}
+      {{- end }}
+      {{- if and (not .Values.env.GF_SECURITY_ADMIN_PASSWORD) (not .Values.env.GF_SECURITY_ADMIN_PASSWORD__FILE) (not .Values.env.GF_SECURITY_DISABLE_INITIAL_ADMIN_CREATION) }}
+      - name: REQ_PASSWORD
+        valueFrom:
+          secretKeyRef:
+            name: {{ (tpl .Values.admin.existingSecret .) | default (include "grafana.fullname" .) }}
+            key: {{ .Values.admin.passwordKey | default "admin-password" }}
+      {{- end }}
+      {{- if not .Values.sidecar.dashboards.skipReload }}
+      - name: REQ_URL
+        value: {{ .Values.sidecar.dashboards.reloadURL }}
+      - name: REQ_METHOD
+        value: POST
+      {{- end }}
+      {{- if .Values.sidecar.dashboards.watchServerTimeout }}
+      {{- if ne .Values.sidecar.dashboards.watchMethod "WATCH" }}
+        {{- fail (printf "Cannot use .Values.sidecar.dashboards.watchServerTimeout with .Values.sidecar.dashboards.watchMethod %s" .Values.sidecar.dashboards.watchMethod) }}
+      {{- end }}
+      - name: WATCH_SERVER_TIMEOUT
+        value: "{{ .Values.sidecar.dashboards.watchServerTimeout }}"
+      {{- end }}
+      {{- if .Values.sidecar.dashboards.watchClientTimeout }}
+      {{- if ne .Values.sidecar.dashboards.watchMethod "WATCH" }}
+        {{- fail (printf "Cannot use .Values.sidecar.dashboards.watchClientTimeout with .Values.sidecar.dashboards.watchMethod %s" .Values.sidecar.dashboards.watchMethod) }}
+      {{- end }}
+      - name: WATCH_CLIENT_TIMEOUT
+        value: {{ .Values.sidecar.dashboards.watchClientTimeout | quote }}
+      {{- end }}
+    {{- with .Values.sidecar.livenessProbe }}
+    livenessProbe:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    {{- with .Values.sidecar.readinessProbe }}
+    readinessProbe:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    {{- with .Values.sidecar.resources }}
+    resources:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    {{- with .Values.sidecar.securityContext }}
+    securityContext:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    volumeMounts:
+      - name: sc-dashboard-volume
+        mountPath: {{ .Values.sidecar.dashboards.folder | quote }}
+      {{- with .Values.sidecar.dashboards.extraMounts }}
+      {{- toYaml . | trim | nindent 6 }}
+      {{- end }}
+{{- end}}
+{{- if .Values.sidecar.datasources.enabled }}
+  - name: {{ include "grafana.name" . }}-sc-datasources
+    {{- if .Values.sidecar.image.sha }}
+    image: "{{ .Values.sidecar.image.repository }}:{{ .Values.sidecar.image.tag }}@sha256:{{ .Values.sidecar.image.sha }}"
+    {{- else }}
+    image: "{{ .Values.sidecar.image.repository }}:{{ .Values.sidecar.image.tag }}"
+    {{- end }}
+    imagePullPolicy: {{ .Values.sidecar.imagePullPolicy }}
+    env:
+      {{- range $key, $value := .Values.sidecar.datasources.env }}
+      - name: "{{ $key }}"
+        value: "{{ $value }}"
+      {{- end }}
+      {{- if .Values.sidecar.datasources.ignoreAlreadyProcessed }}
+      - name: IGNORE_ALREADY_PROCESSED
+        value: "true"
+      {{- end }}
+      - name: METHOD
+        value: {{ .Values.sidecar.datasources.watchMethod }}
+      - name: LABEL
+        value: "{{ .Values.sidecar.datasources.label }}"
+      {{- with .Values.sidecar.datasources.labelValue }}
+      - name: LABEL_VALUE
+        value: {{ quote . }}
+      {{- end }}
+      {{- if or .Values.sidecar.logLevel .Values.sidecar.datasources.logLevel }}
+      - name: LOG_LEVEL
+        value: {{ default .Values.sidecar.logLevel .Values.sidecar.datasources.logLevel }}
+      {{- end }}
+      - name: FOLDER
+        value: "/etc/grafana/provisioning/datasources"
+      - name: RESOURCE
+        value: {{ quote .Values.sidecar.datasources.resource }}
+      {{- with .Values.sidecar.enableUniqueFilenames }}
+      - name: UNIQUE_FILENAMES
+        value: "{{ . }}"
+      {{- end }}
+      {{- with .Values.sidecar.datasources.searchNamespace }}
+      - name: NAMESPACE
+        value: "{{ tpl (. | join ",") $root }}"
+      {{- end }}
+      {{- if .Values.sidecar.skipTlsVerify }}
+      - name: SKIP_TLS_VERIFY
+        value: "{{ .Values.sidecar.skipTlsVerify }}"
+      {{- end }}
+      {{- if .Values.sidecar.datasources.script }}
+      - name: SCRIPT
+        value: "{{ .Values.sidecar.datasources.script }}"
+      {{- end }}
+      {{- if and (not .Values.env.GF_SECURITY_ADMIN_USER) (not .Values.env.GF_SECURITY_DISABLE_INITIAL_ADMIN_CREATION) }}
+      - name: REQ_USERNAME
+        valueFrom:
+          secretKeyRef:
+            name: {{ (tpl .Values.admin.existingSecret .) | default (include "grafana.fullname" .) }}
+            key: {{ .Values.admin.userKey | default "admin-user" }}
+      {{- end }}
+      {{- if and (not .Values.env.GF_SECURITY_ADMIN_PASSWORD) (not .Values.env.GF_SECURITY_ADMIN_PASSWORD__FILE) (not .Values.env.GF_SECURITY_DISABLE_INITIAL_ADMIN_CREATION) }}
+      - name: REQ_PASSWORD
+        valueFrom:
+          secretKeyRef:
+            name: {{ (tpl .Values.admin.existingSecret .) | default (include "grafana.fullname" .) }}
+            key: {{ .Values.admin.passwordKey | default "admin-password" }}
+      {{- end }}
+      {{- if not .Values.sidecar.datasources.skipReload }}
+      - name: REQ_URL
+        value: {{ .Values.sidecar.datasources.reloadURL }}
+      - name: REQ_METHOD
+        value: POST
+      {{- end }}
+      {{- if .Values.sidecar.datasources.watchServerTimeout }}
+      {{- if ne .Values.sidecar.datasources.watchMethod "WATCH" }}
+        {{- fail (printf "Cannot use .Values.sidecar.datasources.watchServerTimeout with .Values.sidecar.datasources.watchMethod %s" .Values.sidecar.datasources.watchMethod) }}
+      {{- end }}
+      - name: WATCH_SERVER_TIMEOUT
+        value: "{{ .Values.sidecar.datasources.watchServerTimeout }}"
+      {{- end }}
+      {{- if .Values.sidecar.datasources.watchClientTimeout }}
+      {{- if ne .Values.sidecar.datasources.watchMethod "WATCH" }}
+        {{- fail (printf "Cannot use .Values.sidecar.datasources.watchClientTimeout with .Values.sidecar.datasources.watchMethod %s" .Values.sidecar.datasources.watchMethod) }}
+      {{- end }}
+      - name: WATCH_CLIENT_TIMEOUT
+        value: "{{ .Values.sidecar.datasources.watchClientTimeout }}"
+      {{- end }}
+    {{- with .Values.sidecar.livenessProbe }}
+    livenessProbe:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    {{- with .Values.sidecar.readinessProbe }}
+    readinessProbe:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    {{- with .Values.sidecar.resources }}
+    resources:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    {{- with .Values.sidecar.securityContext }}
+    securityContext:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    volumeMounts:
+      - name: sc-datasources-volume
+        mountPath: "/etc/grafana/provisioning/datasources"
+{{- end}}
+{{- if .Values.sidecar.notifiers.enabled }}
+  - name: {{ include "grafana.name" . }}-sc-notifiers
+    {{- if .Values.sidecar.image.sha }}
+    image: "{{ .Values.sidecar.image.repository }}:{{ .Values.sidecar.image.tag }}@sha256:{{ .Values.sidecar.image.sha }}"
+    {{- else }}
+    image: "{{ .Values.sidecar.image.repository }}:{{ .Values.sidecar.image.tag }}"
+    {{- end }}
+    imagePullPolicy: {{ .Values.sidecar.imagePullPolicy }}
+    env:
+      {{- range $key, $value := .Values.sidecar.notifiers.env }}
+      - name: "{{ $key }}"
+        value: "{{ $value }}"
+      {{- end }}
+      {{- if .Values.sidecar.notifiers.ignoreAlreadyProcessed }}
+      - name: IGNORE_ALREADY_PROCESSED
+        value: "true"
+      {{- end }}
+      - name: METHOD
+        value: {{ .Values.sidecar.notifiers.watchMethod }}
+      - name: LABEL
+        value: "{{ .Values.sidecar.notifiers.label }}"
+      {{- with .Values.sidecar.notifiers.labelValue }}
+      - name: LABEL_VALUE
+        value: {{ quote . }}
+      {{- end }}
+      {{- if or .Values.sidecar.logLevel .Values.sidecar.notifiers.logLevel }}
+      - name: LOG_LEVEL
+        value: {{ default .Values.sidecar.logLevel .Values.sidecar.notifiers.logLevel }}
+      {{- end }}
+      - name: FOLDER
+        value: "/etc/grafana/provisioning/notifiers"
+      - name: RESOURCE
+        value: {{ quote .Values.sidecar.notifiers.resource }}
+      {{- if .Values.sidecar.enableUniqueFilenames }}
+      - name: UNIQUE_FILENAMES
+        value: "{{ .Values.sidecar.enableUniqueFilenames }}"
+      {{- end }}
+      {{- with .Values.sidecar.notifiers.searchNamespace }}
+      - name: NAMESPACE
+        value: "{{ tpl (. | join ",") $root }}"
+      {{- end }}
+      {{- with .Values.sidecar.skipTlsVerify }}
+      - name: SKIP_TLS_VERIFY
+        value: "{{ . }}"
+      {{- end }}
+      {{- if .Values.sidecar.notifiers.script }}
+      - name: SCRIPT
+        value: "{{ .Values.sidecar.notifiers.script }}"
+      {{- end }}
+      {{- if and (not .Values.env.GF_SECURITY_ADMIN_USER) (not .Values.env.GF_SECURITY_DISABLE_INITIAL_ADMIN_CREATION) }}
+      - name: REQ_USERNAME
+        valueFrom:
+          secretKeyRef:
+            name: {{ (tpl .Values.admin.existingSecret .) | default (include "grafana.fullname" .) }}
+            key: {{ .Values.admin.userKey | default "admin-user" }}
+      {{- end }}
+      {{- if and (not .Values.env.GF_SECURITY_ADMIN_PASSWORD) (not .Values.env.GF_SECURITY_ADMIN_PASSWORD__FILE) (not .Values.env.GF_SECURITY_DISABLE_INITIAL_ADMIN_CREATION) }}
+      - name: REQ_PASSWORD
+        valueFrom:
+          secretKeyRef:
+            name: {{ (tpl .Values.admin.existingSecret .) | default (include "grafana.fullname" .) }}
+            key: {{ .Values.admin.passwordKey | default "admin-password" }}
+      {{- end }}
+      {{- if not .Values.sidecar.notifiers.skipReload }}
+      - name: REQ_URL
+        value: {{ .Values.sidecar.notifiers.reloadURL }}
+      - name: REQ_METHOD
+        value: POST
+      {{- end }}
+      {{- if .Values.sidecar.notifiers.watchServerTimeout }}
+      {{- if ne .Values.sidecar.notifiers.watchMethod "WATCH" }}
+        {{- fail (printf "Cannot use .Values.sidecar.notifiers.watchServerTimeout with .Values.sidecar.notifiers.watchMethod %s" .Values.sidecar.notifiers.watchMethod) }}
+      {{- end }}
+      - name: WATCH_SERVER_TIMEOUT
+        value: "{{ .Values.sidecar.notifiers.watchServerTimeout }}"
+      {{- end }}
+      {{- if .Values.sidecar.notifiers.watchClientTimeout }}
+      {{- if ne .Values.sidecar.notifiers.watchMethod "WATCH" }}
+        {{- fail (printf "Cannot use .Values.sidecar.notifiers.watchClientTimeout with .Values.sidecar.notifiers.watchMethod %s" .Values.sidecar.notifiers.watchMethod) }}
+      {{- end }}
+      - name: WATCH_CLIENT_TIMEOUT
+        value: "{{ .Values.sidecar.notifiers.watchClientTimeout }}"
+      {{- end }}
+    {{- with .Values.sidecar.livenessProbe }}
+    livenessProbe:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    {{- with .Values.sidecar.readinessProbe }}
+    readinessProbe:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    {{- with .Values.sidecar.resources }}
+    resources:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    {{- with .Values.sidecar.securityContext }}
+    securityContext:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    volumeMounts:
+      - name: sc-notifiers-volume
+        mountPath: "/etc/grafana/provisioning/notifiers"
+{{- end}}
+{{- if .Values.sidecar.plugins.enabled }}
+  - name: {{ include "grafana.name" . }}-sc-plugins
+    {{- if .Values.sidecar.image.sha }}
+    image: "{{ .Values.sidecar.image.repository }}:{{ .Values.sidecar.image.tag }}@sha256:{{ .Values.sidecar.image.sha }}"
+    {{- else }}
+    image: "{{ .Values.sidecar.image.repository }}:{{ .Values.sidecar.image.tag }}"
+    {{- end }}
+    imagePullPolicy: {{ .Values.sidecar.imagePullPolicy }}
+    env:
+      {{- range $key, $value := .Values.sidecar.plugins.env }}
+      - name: "{{ $key }}"
+        value: "{{ $value }}"
+      {{- end }}
+      {{- if .Values.sidecar.plugins.ignoreAlreadyProcessed }}
+      - name: IGNORE_ALREADY_PROCESSED
+        value: "true"
+      {{- end }}
+      - name: METHOD
+        value: {{ .Values.sidecar.plugins.watchMethod }}
+      - name: LABEL
+        value: "{{ .Values.sidecar.plugins.label }}"
+      {{- if .Values.sidecar.plugins.labelValue }}
+      - name: LABEL_VALUE
+        value: {{ quote .Values.sidecar.plugins.labelValue }}
+      {{- end }}
+      {{- if or .Values.sidecar.logLevel .Values.sidecar.plugins.logLevel }}
+      - name: LOG_LEVEL
+        value: {{ default .Values.sidecar.logLevel .Values.sidecar.plugins.logLevel }}
+      {{- end }}
+      - name: FOLDER
+        value: "/etc/grafana/provisioning/plugins"
+      - name: RESOURCE
+        value: {{ quote .Values.sidecar.plugins.resource }}
+      {{- with .Values.sidecar.enableUniqueFilenames }}
+      - name: UNIQUE_FILENAMES
+        value: "{{ . }}"
+      {{- end }}
+      {{- with .Values.sidecar.plugins.searchNamespace }}
+      - name: NAMESPACE
+        value: "{{ tpl (. | join ",") $root }}"
+      {{- end }}
+      {{- with .Values.sidecar.plugins.script }}
+      - name: SCRIPT
+        value: "{{ . }}"
+      {{- end }}
+      {{- with .Values.sidecar.skipTlsVerify }}
+      - name: SKIP_TLS_VERIFY
+        value: "{{ . }}"
+      {{- end }}
+      {{- if and (not .Values.env.GF_SECURITY_ADMIN_USER) (not .Values.env.GF_SECURITY_DISABLE_INITIAL_ADMIN_CREATION) }}
+      - name: REQ_USERNAME
+        valueFrom:
+          secretKeyRef:
+            name: {{ (tpl .Values.admin.existingSecret .) | default (include "grafana.fullname" .) }}
+            key: {{ .Values.admin.userKey | default "admin-user" }}
+      {{- end }}
+      {{- if and (not .Values.env.GF_SECURITY_ADMIN_PASSWORD) (not .Values.env.GF_SECURITY_ADMIN_PASSWORD__FILE) (not .Values.env.GF_SECURITY_DISABLE_INITIAL_ADMIN_CREATION) }}
+      - name: REQ_PASSWORD
+        valueFrom:
+          secretKeyRef:
+            name: {{ (tpl .Values.admin.existingSecret .) | default (include "grafana.fullname" .) }}
+            key: {{ .Values.admin.passwordKey | default "admin-password" }}
+      {{- end }}
+      {{- if not .Values.sidecar.plugins.skipReload }}
+      - name: REQ_URL
+        value: {{ .Values.sidecar.plugins.reloadURL }}
+      - name: REQ_METHOD
+        value: POST
+      {{- end }}
+      {{- if .Values.sidecar.plugins.watchServerTimeout }}
+      {{- if ne .Values.sidecar.plugins.watchMethod "WATCH" }}
+        {{- fail (printf "Cannot use .Values.sidecar.plugins.watchServerTimeout with .Values.sidecar.plugins.watchMethod %s" .Values.sidecar.plugins.watchMethod) }}
+      {{- end }}
+      - name: WATCH_SERVER_TIMEOUT
+        value: "{{ .Values.sidecar.plugins.watchServerTimeout }}"
+      {{- end }}
+      {{- if .Values.sidecar.plugins.watchClientTimeout }}
+      {{- if ne .Values.sidecar.plugins.watchMethod "WATCH" }}
+        {{- fail (printf "Cannot use .Values.sidecar.plugins.watchClientTimeout with .Values.sidecar.plugins.watchMethod %s" .Values.sidecar.plugins.watchMethod) }}
+      {{- end }}
+      - name: WATCH_CLIENT_TIMEOUT
+        value: "{{ .Values.sidecar.plugins.watchClientTimeout }}"
+      {{- end }}
+    {{- with .Values.sidecar.livenessProbe }}
+    livenessProbe:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    {{- with .Values.sidecar.readinessProbe }}
+    readinessProbe:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    {{- with .Values.sidecar.resources }}
+    resources:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    {{- with .Values.sidecar.securityContext }}
+    securityContext:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    volumeMounts:
+      - name: sc-plugins-volume
+        mountPath: "/etc/grafana/provisioning/plugins"
+{{- end}}
+  - name: {{ .Chart.Name }}
+    {{- if .Values.image.sha }}
+    image: "{{ .Values.image.repository }}:{{ .Values.image.tag | default .Chart.AppVersion }}@sha256:{{ .Values.image.sha }}"
+    {{- else }}
+    image: "{{ .Values.image.repository }}:{{ .Values.image.tag | default .Chart.AppVersion }}"
+    {{- end }}
+    imagePullPolicy: {{ .Values.image.pullPolicy }}
+    {{- if .Values.command }}
+    command:
+    {{- range .Values.command }}
+      - {{ . | quote }}
+    {{- end }}
+    {{- end}}
+    {{- with .Values.containerSecurityContext }}
+    securityContext:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    volumeMounts:
+      - name: config
+        mountPath: "/etc/grafana/grafana.ini"
+        subPath: grafana.ini
+      {{- if .Values.ldap.enabled }}
+      - name: ldap
+        mountPath: "/etc/grafana/ldap.toml"
+        subPath: ldap.toml
+      {{- end }}
+      {{- range .Values.extraConfigmapMounts }}
+      - name: {{ tpl .name $root }}
+        mountPath: {{ tpl .mountPath $root }}
+        subPath: {{ (tpl .subPath $root) | default "" }}
+        readOnly: {{ .readOnly }}
+      {{- end }}
+      - name: storage
+        mountPath: "/var/lib/grafana"
+        {{- with .Values.persistence.subPath }}
+        subPath: {{ tpl . $root }}
+        {{- end }}
+      {{- with .Values.dashboards }}
+      {{- range $provider, $dashboards := . }}
+      {{- range $key, $value := $dashboards }}
+      {{- if (or (hasKey $value "json") (hasKey $value "file")) }}
+      - name: dashboards-{{ $provider }}
+        mountPath: "/var/lib/grafana/dashboards/{{ $provider }}/{{ $key }}.json"
+        subPath: "{{ $key }}.json"
+      {{- end }}
+      {{- end }}
+      {{- end }}
+      {{- end }}
+      {{- with .Values.dashboardsConfigMaps }}
+      {{- range (keys . | sortAlpha) }}
+      - name: dashboards-{{ . }}
+        mountPath: "/var/lib/grafana/dashboards/{{ . }}"
+      {{- end }}
+      {{- end }}
+      {{- with .Values.datasources }}
+      {{- range (keys . | sortAlpha) }}
+      - name: config
+        mountPath: "/etc/grafana/provisioning/datasources/{{ . }}"
+        subPath: {{ . | quote }}
+      {{- end }}
+      {{- end }}
+      {{- with .Values.notifiers }}
+      {{- range (keys . | sortAlpha) }}
+      - name: config
+        mountPath: "/etc/grafana/provisioning/notifiers/{{ . }}"
+        subPath: {{ . | quote }}
+      {{- end }}
+      {{- end }}
+      {{- with .Values.alerting }}
+      {{- range (keys . | sortAlpha) }}
+      - name: config
+        mountPath: "/etc/grafana/provisioning/alerting/{{ . }}"
+        subPath: {{ . | quote }}
+      {{- end }}
+      {{- end }}
+      {{- with .Values.dashboardProviders }}
+      {{- range (keys . | sortAlpha) }}
+      - name: config
+        mountPath: "/etc/grafana/provisioning/dashboards/{{ . }}"
+        subPath: {{ . | quote }}
+      {{- end }}
+      {{- end }}
+      {{- with .Values.sidecar.alerts.enabled }}
+      - name: sc-alerts-volume
+        mountPath: "/etc/grafana/provisioning/alerting"
+      {{- end}}
+      {{- if .Values.sidecar.dashboards.enabled }}
+      - name: sc-dashboard-volume
+        mountPath: {{ .Values.sidecar.dashboards.folder | quote }}
+      {{- if .Values.sidecar.dashboards.SCProvider }}
+      - name: sc-dashboard-provider
+        mountPath: "/etc/grafana/provisioning/dashboards/sc-dashboardproviders.yaml"
+        subPath: provider.yaml
+      {{- end}}
+      {{- end}}
+      {{- if .Values.sidecar.datasources.enabled }}
+      - name: sc-datasources-volume
+        mountPath: "/etc/grafana/provisioning/datasources"
+      {{- end}}
+      {{- if .Values.sidecar.plugins.enabled }}
+      - name: sc-plugins-volume
+        mountPath: "/etc/grafana/provisioning/plugins"
+      {{- end}}
+      {{- if .Values.sidecar.notifiers.enabled }}
+      - name: sc-notifiers-volume
+        mountPath: "/etc/grafana/provisioning/notifiers"
+      {{- end}}
+      {{- range .Values.extraSecretMounts }}
+      - name: {{ .name }}
+        mountPath: {{ .mountPath }}
+        readOnly: {{ .readOnly }}
+        subPath: {{ .subPath | default "" }}
+      {{- end }}
+      {{- range .Values.extraVolumeMounts }}
+      - name: {{ .name }}
+        mountPath: {{ .mountPath }}
+        subPath: {{ .subPath | default "" }}
+        readOnly: {{ .readOnly }}
+      {{- end }}
+      {{- range .Values.extraEmptyDirMounts }}
+      - name: {{ .name }}
+        mountPath: {{ .mountPath }}
+      {{- end }}
+    ports:
+      - name: {{ .Values.podPortName }}
+        containerPort: {{ .Values.service.targetPort }}
+        protocol: TCP
+      - name: {{ .Values.gossipPortName }}-tcp
+        containerPort: 9094
+        protocol: TCP
+      - name: {{ .Values.gossipPortName }}-udp
+        containerPort: 9094
+        protocol: UDP
+    env:
+      - name: POD_IP
+        valueFrom:
+          fieldRef:
+            fieldPath: status.podIP
+      {{- if and (not .Values.env.GF_SECURITY_ADMIN_USER) (not .Values.env.GF_SECURITY_DISABLE_INITIAL_ADMIN_CREATION) }}
+      - name: GF_SECURITY_ADMIN_USER
+        valueFrom:
+          secretKeyRef:
+            name: {{ (tpl .Values.admin.existingSecret .) | default (include "grafana.fullname" .) }}
+            key: {{ .Values.admin.userKey | default "admin-user" }}
+      {{- end }}
+      {{- if and (not .Values.env.GF_SECURITY_ADMIN_PASSWORD) (not .Values.env.GF_SECURITY_ADMIN_PASSWORD__FILE) (not .Values.env.GF_SECURITY_DISABLE_INITIAL_ADMIN_CREATION) }}
+      - name: GF_SECURITY_ADMIN_PASSWORD
+        valueFrom:
+          secretKeyRef:
+            name: {{ (tpl .Values.admin.existingSecret .) | default (include "grafana.fullname" .) }}
+            key: {{ .Values.admin.passwordKey | default "admin-password" }}
+      {{- end }}
+      {{- if .Values.plugins }}
+      - name: GF_INSTALL_PLUGINS
+        valueFrom:
+          configMapKeyRef:
+            name: {{ include "grafana.fullname" . }}
+            key: plugins
+      {{- end }}
+      {{- if .Values.smtp.existingSecret }}
+      - name: GF_SMTP_USER
+        valueFrom:
+          secretKeyRef:
+            name: {{ .Values.smtp.existingSecret }}
+            key: {{ .Values.smtp.userKey | default "user" }}
+      - name: GF_SMTP_PASSWORD
+        valueFrom:
+          secretKeyRef:
+            name: {{ .Values.smtp.existingSecret }}
+            key: {{ .Values.smtp.passwordKey | default "password" }}
+      {{- end }}
+      {{- if .Values.imageRenderer.enabled }}
+      - name: GF_RENDERING_SERVER_URL
+        value: http://{{ include "grafana.fullname" . }}-image-renderer.{{ include "grafana.namespace" . }}:{{ .Values.imageRenderer.service.port }}/render
+      - name: GF_RENDERING_CALLBACK_URL
+        value: {{ .Values.imageRenderer.grafanaProtocol }}://{{ include "grafana.fullname" . }}.{{ include "grafana.namespace" . }}:{{ .Values.service.port }}/{{ .Values.imageRenderer.grafanaSubPath }}
+      {{- end }}
+      - name: GF_PATHS_DATA
+        value: {{ (get .Values "grafana.ini").paths.data }}
+      - name: GF_PATHS_LOGS
+        value: {{ (get .Values "grafana.ini").paths.logs }}
+      - name: GF_PATHS_PLUGINS
+        value: {{ (get .Values "grafana.ini").paths.plugins }}
+      - name: GF_PATHS_PROVISIONING
+        value: {{ (get .Values "grafana.ini").paths.provisioning }}
+      {{- range $key, $value := .Values.envValueFrom }}
+      - name: {{ $key | quote }}
+        valueFrom:
+          {{- tpl (toYaml $value) $ | nindent 10 }}
+      {{- end }}
+      {{- range $key, $value := .Values.env }}
+      - name: "{{ tpl $key $ }}"
+        value: "{{ tpl (print $value) $ }}"
+      {{- end }}
+    {{- if or .Values.envFromSecret (or .Values.envRenderSecret .Values.envFromSecrets) .Values.envFromConfigMaps }}
+    envFrom:
+      {{- if .Values.envFromSecret }}
+      - secretRef:
+          name: {{ tpl .Values.envFromSecret . }}
+      {{- end }}
+      {{- if .Values.envRenderSecret }}
+      - secretRef:
+          name: {{ include "grafana.fullname" . }}-env
+      {{- end }}
+      {{- range .Values.envFromSecrets }}
+      - secretRef:
+          name: {{ tpl .name $ }}
+          optional: {{ .optional | default false }}
+      {{- end }}
+      {{- range .Values.envFromConfigMaps }}
+      - configMapRef:
+          name: {{ tpl .name $ }}
+          optional: {{ .optional | default false }}
+      {{- end }}
+    {{- end }}
+    {{- with .Values.livenessProbe }}
+    livenessProbe:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    {{- with .Values.readinessProbe }}
+    readinessProbe:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+    {{- with .Values.lifecycleHooks }}
+    lifecycle:
+      {{- tpl (toYaml .) $root | nindent 6 }}
+    {{- end }}
+    {{- with .Values.resources }}
+    resources:
+      {{- toYaml . | nindent 6 }}
+    {{- end }}
+{{- with .Values.extraContainers }}
+  {{- tpl . $ | nindent 2 }}
+{{- end }}
+{{- with .Values.nodeSelector }}
+nodeSelector:
+  {{- toYaml . | nindent 2 }}
+{{- end }}
+{{- with .Values.affinity }}
+affinity:
+  {{- tpl (toYaml .) $root | nindent 2 }}
+{{- end }}
+{{- with .Values.topologySpreadConstraints }}
+topologySpreadConstraints:
+  {{- toYaml . | nindent 2 }}
+{{- end }}
+{{- with .Values.tolerations }}
+tolerations:
+  {{- toYaml . | nindent 2 }}
+{{- end }}
+volumes:
+  - name: config
+    configMap:
+      name: {{ include "grafana.fullname" . }}
+  {{- range .Values.extraConfigmapMounts }}
+  - name: {{ tpl .name $root }}
+    configMap:
+      name: {{ tpl .configMap $root }}
+      {{- with .items }}
+      items:
+        {{- toYaml . | nindent 8 }}
+      {{- end }}
+  {{- end }}
+  {{- if .Values.dashboards }}
+  {{- range (keys .Values.dashboards | sortAlpha) }}
+  - name: dashboards-{{ . }}
+    configMap:
+      name: {{ include "grafana.fullname" $ }}-dashboards-{{ . }}
+  {{- end }}
+  {{- end }}
+  {{- if .Values.dashboardsConfigMaps }}
+  {{- range $provider, $name := .Values.dashboardsConfigMaps }}
+  - name: dashboards-{{ $provider }}
+    configMap:
+      name: {{ tpl $name $root }}
+  {{- end }}
+  {{- end }}
+  {{- if .Values.ldap.enabled }}
+  - name: ldap
+    secret:
+      {{- if .Values.ldap.existingSecret }}
+      secretName: {{ .Values.ldap.existingSecret }}
+      {{- else }}
+      secretName: {{ include "grafana.fullname" . }}
+      {{- end }}
+      items:
+        - key: ldap-toml
+          path: ldap.toml
+  {{- end }}
+  {{- if and .Values.persistence.enabled (eq .Values.persistence.type "pvc") }}
+  - name: storage
+    persistentVolumeClaim:
+      claimName: {{ tpl (.Values.persistence.existingClaim | default (include "grafana.fullname" .)) . }}
+  {{- else if and .Values.persistence.enabled (has .Values.persistence.type $sts) }}
+  {{/* nothing */}}
+  {{- else }}
+  - name: storage
+    {{- if .Values.persistence.inMemory.enabled }}
+    emptyDir:
+      medium: Memory
+      {{- with .Values.persistence.inMemory.sizeLimit }}
+      sizeLimit: {{ . }}
+      {{- end }}
+    {{- else }}
+    emptyDir: {}
+    {{- end }}
+  {{- end }}
+  {{- if .Values.sidecar.alerts.enabled }}
+  - name: sc-alerts-volume
+    emptyDir:
+      {{- with .Values.sidecar.alerts.sizeLimit }}
+      sizeLimit: {{ . }}
+      {{- else }}
+      {}
+      {{- end }}
+  {{- end }}
+  {{- if .Values.sidecar.dashboards.enabled }}
+  - name: sc-dashboard-volume
+    emptyDir:
+      {{- with .Values.sidecar.dashboards.sizeLimit }}
+      sizeLimit: {{ . }}
+      {{- else }}
+      {}
+      {{- end }}
+  {{- if .Values.sidecar.dashboards.SCProvider }}
+  - name: sc-dashboard-provider
+    configMap:
+      name: {{ include "grafana.fullname" . }}-config-dashboards
+  {{- end }}
+  {{- end }}
+  {{- if .Values.sidecar.datasources.enabled }}
+  - name: sc-datasources-volume
+    emptyDir:
+      {{- with .Values.sidecar.datasources.sizeLimit }}
+      sizeLimit: {{ . }}
+      {{- else }}
+      {}
+      {{- end }}
+  {{- end }}
+  {{- if .Values.sidecar.plugins.enabled }}
+  - name: sc-plugins-volume
+    emptyDir:
+      {{- with .Values.sidecar.plugins.sizeLimit }}
+      sizeLimit: {{ . }}
+      {{- else }}
+      {}
+      {{- end }}
+  {{- end }}
+  {{- if .Values.sidecar.notifiers.enabled }}
+  - name: sc-notifiers-volume
+    emptyDir:
+      {{- with .Values.sidecar.notifiers.sizeLimit }}
+      sizeLimit: {{ . }}
+      {{- else }}
+      {}
+      {{- end }}
+  {{- end }}
+  {{- range .Values.extraSecretMounts }}
+  {{- if .secretName }}
+  - name: {{ .name }}
+    secret:
+      secretName: {{ .secretName }}
+      defaultMode: {{ .defaultMode }}
+      {{- with .items }}
+      items:
+        {{- toYaml . | nindent 8 }}
+      {{- end }}
+  {{- else if .projected }}
+  - name: {{ .name }}
+    projected:
+      {{- toYaml .projected | nindent 6 }}
+  {{- else if .csi }}
+  - name: {{ .name }}
+    csi:
+      {{- toYaml .csi | nindent 6 }}
+  {{- end }}
+  {{- end }}
+  {{- range .Values.extraVolumeMounts }}
+  - name: {{ .name }}
+    {{- if .existingClaim }}
+    persistentVolumeClaim:
+      claimName: {{ .existingClaim }}
+    {{- else if .hostPath }}
+    hostPath:
+      path: {{ .hostPath }}
+    {{- else if .csi }}
+    csi:
+      {{- toYaml .data | nindent 6 }}
+    {{- else }}
+    emptyDir: {}
+    {{- end }}
+  {{- end }}
+  {{- range .Values.extraEmptyDirMounts }}
+  - name: {{ .name }}
+    emptyDir: {}
+  {{- end }}
+  {{- with .Values.extraContainerVolumes }}
+  {{- tpl (toYaml .) $root | nindent 2 }}
+  {{- end }}
+{{- end }}
diff --git a/charts/admin-stack/charts/grafana/templates/clusterrole.yaml b/charts/admin-stack/charts/grafana/templates/clusterrole.yaml
new file mode 100644
index 0000000..3396713
--- /dev/null
+++ b/charts/admin-stack/charts/grafana/templates/clusterrole.yaml
@@ -0,0 +1,25 @@
+{{- if and .Values.rbac.create (not .Values.rbac.namespaced) (not .Values.rbac.useExistingRole) }}
+kind: ClusterRole
+apiVersion: rbac.authorization.k8s.io/v1
+metadata:
+  labels:
+    {{- include "grafana.labels" . | nindent 4 }}
+  {{- with .Values.annotations }}
+  annotations:
+    {{- toYaml . | nindent 4 }}
+  {{- end }}
+  name: {{ include "grafana.fullname" . }}-clusterrole
+{{- if or .Values.sidecar.dashboards.enabled (or .Values.rbac.extraClusterRoleRules (or .Values.sidecar.datasources.enabled .Values.sidecar.plugins.enabled)) }}
+rules:
+  {{- if or .Values.sidecar.dashboards.enabled (or .Values.sidecar.datasources.enabled .Values.sidecar.plugins.enabled) }}
+  - apiGroups: [""] # "" indicates the core API group
+    resources: ["configmaps", "secrets"]
+    verbs: ["get", "watch", "list"]
+  {{- end}}
+  {{- with .Values.rbac.extraClusterRoleRules }}
+  {{- toYaml . | nindent 2 }}
+  {{- end}}
+{{- else }}
+rules: []
+{{- end}}
+{{- end}}
diff --git a/charts/admin-stack/charts/grafana/templates/clusterrolebinding.yaml b/charts/admin-stack/charts/grafana/templates/clusterrolebinding.yaml
new file mode 100644
index 0000000..48411fe
--- /dev/null
+++ b/charts/admin-stack/charts/grafana/templates/clusterrolebinding.yaml
@@ -0,0 +1,24 @@
+{{- if and .Values.rbac.create (not .Values.rbac.namespaced) }}
+kind: ClusterRoleBinding
+apiVersion: rbac.authorization.k8s.io/v1
+metadata:
+  name: {{ include "grafana.fullname" . }}-clusterrolebinding
+  labels:
+    {{- include "grafana.labels" . | nindent 4 }}
+  {{- with .Values.annotations }}
+  annotations:
+    {{- toYaml . | nindent 4 }}
+  {{- end }}
+subjects:
+  - kind: ServiceAccount
+    name: {{ include "grafana.serviceAccountName" . }}
+    namespace: {{ include "grafana.namespace" . }}
+roleRef:
+  kind: ClusterRole
+  {{- if .Values.rbac.useExistingRole }}
+  name: {{ .Values.rbac.useExistingRole }}
+  {{- else }}
+  name: {{ include "grafana.fullname" . }}-clusterrole
+  {{- end }}
+  apiGroup: rbac.authorization.k8s.io
+{{- end }}
diff --git a/charts/admin-stack/charts/grafana/templates/configmap-dashboard-provider.yaml b/charts/admin-stack/charts/grafana/templates/configmap-dashboard-provider.yaml
new file mode 100644
index 0000000..1f706a8
--- /dev/null
+++ b/charts/admin-stack/charts/grafana/templates/configmap-dashboard-provider.yaml
@@ -0,0 +1,29 @@
+{{- if and .Values.sidecar.dashboards.enabled .Values.sidecar.dashboards.SCProvider }}
+apiVersion: v1
+kind: ConfigMap
+metadata:
+  labels:
+    {{- include "grafana.labels" . | nindent 4 }}
+  {{- with .Values.annotations }}
+  annotations:
+    {{- toYaml . | nindent 4 }}
+  {{- end }}
+  name: {{ include "grafana.fullname" . }}-config-dashboards
+  namespace: {{ include "grafana.namespace" . }}
+data:
+  provider.yaml: |-
+    apiVersion: 1
+    providers:
+      - name: '{{ .Values.sidecar.dashboards.provider.name }}'
+        orgId: {{ .Values.sidecar.dashboards.provider.orgid }}
+        {{- if not .Values.sidecar.dashboards.provider.foldersFromFilesStructure }}
+        folder: '{{ .Values.sidecar.dashboards.provider.folder }}'
+        {{- end }}
+        type: {{ .Values.sidecar.dashboards.provider.type }}
+        disableDeletion: {{ .Values.sidecar.dashboards.provider.disableDelete }}
+        allowUiUpdates: {{ .Values.sidecar.dashboards.provider.allowUiUpdates }}
+        updateIntervalSeconds: {{ .Values.sidecar.dashboards.provider.updateIntervalSeconds | default 30 }}
+        options:
+          foldersFromFilesStructure: {{ .Values.sidecar.dashboards.provider.foldersFromFilesStructure }}
+          path: {{ .Values.sidecar.dashboards.folder }}{{- with .Values.sidecar.dashboards.defaultFolderName }}/{{ . }}{{- end }}
+{{- end }}
diff --git a/charts/admin-stack/charts/grafana/templates/configmap.yaml b/charts/admin-stack/charts/grafana/templates/configmap.yaml
new file mode 100644
index 0000000..b0735a2
--- /dev/null
+++ b/charts/admin-stack/charts/grafana/templates/configmap.yaml
@@ -0,0 +1,125 @@
+{{- if .Values.createConfigmap }}
+{{- $root := . -}}
+apiVersion: v1
+kind: ConfigMap
+metadata:
+  name: {{ include "grafana.fullname" . }}
+  namespace: {{ include "grafana.namespace" . }}
+  labels:
+    {{- include "grafana.labels" . | nindent 4 }}
+  {{- with .Values.annotations }}
+  annotations:
+    {{- toYaml . | nindent 4 }}
+  {{- end }}
+data:
+  {{- with .Values.plugins }}
+  plugins: {{ join "," . }}
+  {{- end }}
+  grafana.ini: |
+  {{- range $elem, $elemVal := index .Values "grafana.ini" }}
+    {{- if not (kindIs "map" $elemVal) }}
+    {{- if kindIs "invalid" $elemVal }}
+    {{ $elem }} =
+    {{- else if kindIs "string" $elemVal }}
+    {{ $elem }} = {{ tpl $elemVal $ }}
+    {{- else }}
+    {{ $elem }} = {{ $elemVal }}
+    {{- end }}
+    {{- end }}
+  {{- end }}
+  {{- range $key, $value := index .Values "grafana.ini" }}
+    {{- if kindIs "map" $value }}
+    [{{ $key }}]
+    {{- range $elem, $elemVal := $value }}
+    {{- if kindIs "invalid" $elemVal }}
+    {{ $elem }} =
+    {{- else if kindIs "string" $elemVal }}
+    {{ $elem }} = {{ tpl $elemVal $ }}
+    {{- else }}
+    {{ $elem }} = {{ $elemVal }}
+    {{- end }}
+    {{- end }}
+    {{- end }}
+  {{- end }}
+
+  {{- range $key, $value := .Values.datasources }}
+  {{- $key | nindent 2 }}: |
+    {{- tpl (toYaml $value | nindent 4) $root }}
+  {{- end }}
+
+  {{- range $key, $value := .Values.notifiers }}
+  {{- $key | nindent 2 }}: |
+    {{- toYaml $value | nindent 4 }}
+  {{- end }}
+
+  {{- range $key, $value := .Values.alerting }}
+  {{- $key | nindent 2 }}: |
+    {{- tpl (toYaml $value | nindent 4) $root }}
+  {{- end }}
+
+  {{- range $key, $value := .Values.dashboardProviders }}
+  {{- $key | nindent 2 }}: |
+    {{- toYaml $value | nindent 4 }}
+  {{- end }}
+
+{{- if .Values.dashboards  }}
+  download_dashboards.sh: |
+    #!/usr/bin/env sh
+    set -euf
+    {{- if .Values.dashboardProviders }}
+      {{- range $key, $value := .Values.dashboardProviders }}
+        {{- range $value.providers }}
+    mkdir -p {{ .options.path }}
+        {{- end }}
+      {{- end }}
+    {{- end }}
+  {{ $dashboardProviders := .Values.dashboardProviders }}
+  {{- range $provider, $dashboards := .Values.dashboards }}
+    {{- range $key, $value := $dashboards }}
+      {{- if (or (hasKey $value "gnetId") (hasKey $value "url")) }}
+    curl -skf \
+    --connect-timeout 60 \
+    --max-time 60 \
+      {{- if not $value.b64content }}
+    -H "Accept: application/json" \
+        {{- if $value.token }}
+    -H "Authorization: token {{ $value.token }}" \
+        {{- end }}
+        {{- if $value.bearerToken }}
+    -H "Authorization: Bearer {{ $value.bearerToken }}" \
+        {{- end }}
+        {{- if $value.gitlabToken }}
+    -H "PRIVATE-TOKEN: {{ $value.gitlabToken }}" \
+        {{- end }}
+    -H "Content-Type: application/json;charset=UTF-8" \
+      {{- end }}
+    {{- $dpPath := "" -}}
+    {{- range $kd := (index $dashboardProviders "dashboardproviders.yaml").providers }}
+      {{- if eq $kd.name $provider }}
+      {{- $dpPath = $kd.options.path }}
+      {{- end }}
+    {{- end }}
+    {{- if $value.url }}
+      "{{ $value.url }}" \
+    {{- else }}
+      "https://grafana.com/api/dashboards/{{ $value.gnetId }}/revisions/{{- if $value.revision -}}{{ $value.revision }}{{- else -}}1{{- end -}}/download" \
+    {{- end }}
+    {{- if $value.datasource }}
+      {{- if kindIs "string" $value.datasource }}
+      | sed '/-- .* --/! s/"datasource":.*,/"datasource": "{{ $value.datasource }}",/g' \
+      {{- end }}
+      {{- if kindIs "slice" $value.datasource }}
+        {{- range $value.datasource }}
+          | sed '/-- .* --/! s/${{"{"}}{{ .name }}}/{{ .value }}/g' \
+        {{- end }}
+      {{- end }}
+    {{- end }}
+    {{- if $value.b64content }}
+      | base64 -d \
+    {{- end }}
+    > "{{- if $dpPath -}}{{ $dpPath }}{{- else -}}/var/lib/grafana/dashboards/{{ $provider }}{{- end -}}/{{ $key }}.json"
+      {{ end }}
+    {{- end }}
+  {{- end }}
+{{- end }}
+{{- end }}
diff --git a/charts/admin-stack/charts/grafana/templates/dashboards-json-configmap.yaml b/charts/admin-stack/charts/grafana/templates/dashboards-json-configmap.yaml
new file mode 100644
index 0000000..df0ed0d
--- /dev/null
+++ b/charts/admin-stack/charts/grafana/templates/dashboards-json-configmap.yaml
@@ -0,0 +1,35 @@
+{{- if .Values.dashboards }}
+{{ $files := .Files }}
+{{- range $provider, $dashboards := .Values.dashboards }}
+apiVersion: v1
+kind: ConfigMap
+metadata:
+  name: {{ include "grafana.fullname" $ }}-dashboards-{{ $provider }}
+  namespace: {{ include "grafana.namespace" $ }}
+  labels:
+    {{- include "grafana.labels" $ | nindent 4 }}
+    dashboard-provider: {{ $provider }}
+{{- if $dashboards }}
+data:
+{{- $dashboardFound := false }}
+{{- range $key, $value := $dashboards }}
+{{- if (or (hasKey $value "json") (hasKey $value "file")) }}
+{{- $dashboardFound = true }}
+  {{- print $key | nindent 2 }}.json:
+    {{- if hasKey $value "json" }}
+    |-
+      {{- $value.json | nindent 6 }}
+    {{- end }}
+    {{- if hasKey $value "file" }}
+    {{- toYaml ( $files.Get $value.file ) | nindent 4}}
+    {{- end }}
+{{- end }}
+{{- end }}
+{{- if not $dashboardFound }}
+  {}
+{{- end }}
+{{- end }}
+---
+{{- end }}
+
+{{- end }}
diff --git a/charts/admin-stack/charts/grafana/templates/deployment.yaml b/charts/admin-stack/charts/grafana/templates/deployment.yaml
new file mode 100644
index 0000000..42bde46
--- /dev/null
+++ b/charts/admin-stack/charts/grafana/templates/deployment.yaml
@@ -0,0 +1,52 @@
+{{- if (and (not .Values.useStatefulSet) (or (not .Values.persistence.enabled) (eq .Values.persistence.type "pvc"))) }}
+{{- if .Values.enabled }}
+apiVersion: apps/v1
+kind: Deployment
+metadata:
+  name: {{ include "grafana.fullname" . }}
+  namespace: {{ include "grafana.namespace" . }}
+  labels:
+    {{- include "grafana.labels" . | nindent 4 }}
+    {{- with .Values.labels }}
+    {{- toYaml . | nindent 4 }}
+    {{- end }}
+  {{- with .Values.annotations }}
+  annotations:
+    {{- toYaml . | nindent 4 }}
+  {{- end }}
+spec:
+  {{- if and (not .Values.autoscaling.enabled) (.Values.replicas) }}
+  replicas: {{ .Values.replicas }}
+  {{- end }}
+  revisionHistoryLimit: {{ .Values.revisionHistoryLimit }}
+  selector:
+    matchLabels:
+      {{- include "grafana.selectorLabels" . | nindent 6 }}
+  {{- with .Values.deploymentStrategy }}
+  strategy:
+      {{- toYaml . | trim | nindent 4 }}
+  {{- end }}
+  template:
+    metadata:
+      labels:
+        {{- include "grafana.selectorLabels" . | nindent 8 }}
+        {{- with .Values.podLabels }}
+        {{- toYaml . | nindent 8 }}
+        {{- end }}
+      annotations:
+        checksum/config: {{ include (print $.Template.BasePath "/configmap.yaml") . | sha256sum }}
+        checksum/dashboards-json-config: {{ include (print $.Template.BasePath "/dashboards-json-configmap.yaml") . | sha256sum }}
+        checksum/sc-dashboard-provider-config: {{ include (print $.Template.BasePath "/configmap-dashboard-provider.yaml") . | sha256sum }}
+        {{- if and (or (and (not .Values.admin.existingSecret) (not .Values.env.GF_SECURITY_ADMIN_PASSWORD__FILE) (not .Values.env.GF_SECURITY_ADMIN_PASSWORD)) (and .Values.ldap.enabled (not .Values.ldap.existingSecret))) (not .Values.env.GF_SECURITY_DISABLE_INITIAL_ADMIN_CREATION) }}
+        checksum/secret: {{ include (print $.Template.BasePath "/secret.yaml") . | sha256sum }}
+        {{- end }}
+        {{- if .Values.envRenderSecret }}
+        checksum/secret-env: {{ include (print $.Template.BasePath "/secret-env.yaml") . | sha256sum }}
+        {{- end }}
+        {{- with .Values.podAnnotations }}
+        {{- toYaml . | nindent 8 }}
+        {{- end }}
+    spec:
+      {{- include "grafana.pod" . | nindent 6 }}
+{{- end }}
+{{- end }}
diff --git a/charts/admin-stack/charts/grafana/templates/headless-service.yaml b/charts/admin-stack/charts/grafana/templates/headless-service.yaml
new file mode 100644
index 0000000..3028589
--- /dev/null
+++ b/charts/admin-stack/charts/grafana/templates/headless-service.yaml
@@ -0,0 +1,22 @@
+{{- $sts := list "sts" "StatefulSet" "statefulset" -}}
+{{- if or .Values.headlessService (and .Values.persistence.enabled (not .Values.persistence.existingClaim) (has .Values.persistence.type $sts)) }}
+apiVersion: v1
+kind: Service
+metadata:
+  name: {{ include "grafana.fullname" . }}-headless
+  namespace: {{ include "grafana.namespace" . }}
+  labels:
+    {{- include "grafana.labels" . | nindent 4 }}
+  {{- with .Values.annotations }}
+  annotations:
+    {{- toYaml . | nindent 4 }}
+  {{- end }}
+spec:
+  clusterIP: None
+  selector:
+    {{- include "grafana.selectorLabels" . | nindent 4 }}
+  type: ClusterIP
+  ports:
+  - name: {{ .Values.gossipPortName }}-tcp
+    port: 9094
+{{- end }}
diff --git a/charts/admin-stack/charts/grafana/templates/ingress.yaml b/charts/admin-stack/charts/grafana/templates/ingress.yaml
new file mode 100644
index 0000000..063cdfa
--- /dev/null
+++ b/charts/admin-stack/charts/grafana/templates/ingress.yaml
@@ -0,0 +1,78 @@
+{{- if .Values.ingress.enabled -}}
+{{- $ingressApiIsStable := eq (include "grafana.ingress.isStable" .) "true" -}}
+{{- $ingressSupportsIngressClassName := eq (include "grafana.ingress.supportsIngressClassName" .) "true" -}}
+{{- $ingressSupportsPathType := eq (include "grafana.ingress.supportsPathType" .) "true" -}}
+{{- $fullName := include "grafana.fullname" . -}}
+{{- $servicePort := .Values.service.port -}}
+{{- $ingressPath := .Values.ingress.path -}}
+{{- $ingressPathType := .Values.ingress.pathType -}}
+{{- $extraPaths := .Values.ingress.extraPaths -}}
+apiVersion: {{ include "grafana.ingress.apiVersion" . }}
+kind: Ingress
+metadata:
+  name: {{ $fullName }}
+  namespace: {{ include "grafana.namespace" . }}
+  labels:
+    {{- include "grafana.labels" . | nindent 4 }}
+    {{- with .Values.ingress.labels }}
+    {{- toYaml . | nindent 4 }}
+    {{- end }}
+  {{- with .Values.ingress.annotations }}
+  annotations:
+    {{- range $key, $value := . }}
+    {{ $key }}: {{ tpl $value $ | quote }}
+    {{- end }}
+  {{- end }}
+spec:
+  {{- if and $ingressSupportsIngressClassName .Values.ingress.ingressClassName }}
+  ingressClassName: {{ .Values.ingress.ingressClassName }}
+  {{- end -}}
+  {{- with .Values.ingress.tls }}
+  tls:
+    {{- tpl (toYaml .) $ | nindent 4 }}
+  {{- end }}
+  rules:
+  {{- if .Values.ingress.hosts  }}
+  {{- range .Values.ingress.hosts }}
+    - host: {{ tpl . $ }}
+      http:
+        paths:
+          {{- with $extraPaths }}
+          {{- toYaml . | nindent 10 }}
+          {{- end }}
+          - path: {{ $ingressPath }}
+            {{- if $ingressSupportsPathType }}
+            pathType: {{ $ingressPathType }}
+            {{- end }}
+            backend:
+              {{- if $ingressApiIsStable }}
+              service:
+                name: {{ $fullName }}
+                port:
+                  number: {{ $servicePort }}
+              {{- else }}
+              serviceName: {{ $fullName }}
+              servicePort: {{ $servicePort }}
+              {{- end }}
+  {{- end }}
+  {{- else }}
+    - http:
+        paths:
+          - backend:
+              {{- if $ingressApiIsStable }}
+              service:
+                name: {{ $fullName }}
+                port:
+                  number: {{ $servicePort }}
+              {{- else }}
+              serviceName: {{ $fullName }}
+              servicePort: {{ $servicePort }}
+              {{- end }}
+            {{- with $ingressPath }}
+            path: {{ . }}
+            {{- end }}
+            {{- if $ingressSupportsPathType }}
+            pathType: {{ $ingressPathType }}
+            {{- end }}
+  {{- end -}}
+{{- end }}
diff --git a/charts/admin-stack/charts/grafana/templates/networkpolicy.yaml b/charts/admin-stack/charts/grafana/templates/networkpolicy.yaml
new file mode 100644
index 0000000..ea4578b
--- /dev/null
+++ b/charts/admin-stack/charts/grafana/templates/networkpolicy.yaml
@@ -0,0 +1,52 @@
+{{- if .Values.networkPolicy.enabled }}
+apiVersion: networking.k8s.io/v1
+kind: NetworkPolicy
+metadata:
+  name: {{ include "grafana.fullname" . }}
+  namespace: {{ include "grafana.namespace" . }}
+  labels:
+    {{- include "grafana.labels" . | nindent 4 }}
+    {{- with .Values.labels }}
+    {{- toYaml . | nindent 4 }}
+    {{- end }}
+  {{- with .Values.annotations }}
+  annotations:
+    {{- toYaml . | nindent 4 }}
+  {{- end }}
+spec:
+  policyTypes:
+    {{- if .Values.networkPolicy.ingress }}
+    - Ingress
+    {{- end }}
+    {{- if .Values.networkPolicy.egress.enabled }}
+    - Egress
+    {{- end }}
+  podSelector:
+    matchLabels:
+      {{- include "grafana.selectorLabels" . | nindent 6 }}
+
+  {{- if .Values.networkPolicy.egress.enabled }}
+  egress:
+    - ports:
+        {{ .Values.networkPolicy.egress.ports | toJson }}
+  {{- end }}
+  {{- if .Values.networkPolicy.ingress }}
+  ingress:
+    - ports:
+      - port: {{ .Values.service.targetPort }}
+      {{- if not .Values.networkPolicy.allowExternal }}
+      from:
+        - podSelector:
+            matchLabels:
+              {{ include "grafana.fullname" . }}-client: "true"
+        {{- with .Values.networkPolicy.explicitNamespacesSelector }}
+        - namespaceSelector:
+            {{- toYaml . | nindent 12 }}
+        {{- end }}
+        - podSelector:
+            matchLabels:
+              {{- include "grafana.labels" . | nindent 14 }}
+              role: read
+      {{- end }}
+  {{- end }}
+{{- end }}
diff --git a/charts/admin-stack/charts/grafana/templates/poddisruptionbudget.yaml b/charts/admin-stack/charts/grafana/templates/poddisruptionbudget.yaml
new file mode 100644
index 0000000..0525121
--- /dev/null
+++ b/charts/admin-stack/charts/grafana/templates/poddisruptionbudget.yaml
@@ -0,0 +1,22 @@
+{{- if .Values.podDisruptionBudget }}
+apiVersion: {{ include "grafana.podDisruptionBudget.apiVersion" . }}
+kind: PodDisruptionBudget
+metadata:
+  name: {{ include "grafana.fullname" . }}
+  namespace: {{ include "grafana.namespace" . }}
+  labels:
+    {{- include "grafana.labels" . | nindent 4 }}
+    {{- with .Values.labels }}
+    {{- toYaml . | nindent 4 }}
+    {{- end }}
+spec:
+  {{- with .Values.podDisruptionBudget.minAvailable }}
+  minAvailable: {{ . }}
+  {{- end }}
+  {{- with .Values.podDisruptionBudget.maxUnavailable }}
+  maxUnavailable: {{ . }}
+  {{- end }}
+  selector:
+    matchLabels:
+      {{- include "grafana.selectorLabels" . | nindent 6 }}
+{{- end }}
diff --git a/charts/dubbo-admin/templates/admin-pvc.yaml b/charts/admin-stack/charts/grafana/templates/pvc.yaml
similarity index 80%
rename from charts/dubbo-admin/templates/admin-pvc.yaml
rename to charts/admin-stack/charts/grafana/templates/pvc.yaml
index 80a2565..eb8f87f 100644
--- a/charts/dubbo-admin/templates/admin-pvc.yaml
+++ b/charts/admin-stack/charts/grafana/templates/pvc.yaml
@@ -1,11 +1,11 @@
-{{- if and .Values.persistence.enabled (not .Values.persistence.ClaimName) (eq .Values.persistence.type "pvc")}}
+{{- if and .Values.persistence.enabled (not .Values.persistence.existingClaim) (eq .Values.persistence.type "pvc")}}
 apiVersion: v1
 kind: PersistentVolumeClaim
 metadata:
-  name: {{ include "dubbo-admin.fullname" . }}
-  namespace: {{ include "dubbo-admin.namespace" . }}
+  name: {{ include "grafana.fullname" . }}
+  namespace: {{ include "grafana.namespace" . }}
   labels:
-    {{- include "dubbo-admin.labels" . | nindent 4 }}
+    {{- include "grafana.labels" . | nindent 4 }}
     {{- with .Values.persistence.extraPvcLabels }}
     {{- toYaml . | nindent 4 }}
     {{- end }}
diff --git a/charts/admin-stack/charts/grafana/templates/role.yaml b/charts/admin-stack/charts/grafana/templates/role.yaml
new file mode 100644
index 0000000..ffdb16f
--- /dev/null
+++ b/charts/admin-stack/charts/grafana/templates/role.yaml
@@ -0,0 +1,32 @@
+{{- if and .Values.rbac.create (not .Values.rbac.useExistingRole) -}}
+apiVersion: {{ include "grafana.rbac.apiVersion" . }}
+kind: Role
+metadata:
+  name: {{ include "grafana.fullname" . }}
+  namespace: {{ include "grafana.namespace" . }}
+  labels:
+    {{- include "grafana.labels" . | nindent 4 }}
+  {{- with .Values.annotations }}
+  annotations:
+    {{- toYaml . | nindent 4 }}
+  {{- end }}
+{{- if or .Values.rbac.pspEnabled (and .Values.rbac.namespaced (or .Values.sidecar.dashboards.enabled .Values.sidecar.datasources.enabled .Values.sidecar.plugins.enabled .Values.rbac.extraRoleRules)) }}
+rules:
+  {{- if .Values.rbac.pspEnabled }}
+  - apiGroups:      ['extensions']
+    resources:      ['podsecuritypolicies']
+    verbs:          ['use']
+    resourceNames:  [{{ include "grafana.fullname" . }}]
+  {{- end }}
+  {{- if and .Values.rbac.namespaced (or .Values.sidecar.dashboards.enabled .Values.sidecar.datasources.enabled .Values.sidecar.plugins.enabled) }}
+  - apiGroups: [""] # "" indicates the core API group
+    resources: ["configmaps", "secrets"]
+    verbs: ["get", "watch", "list"]
+  {{- end }}
+  {{- with .Values.rbac.extraRoleRules }}
+  {{- toYaml . | nindent 2 }}
+  {{- end}}
+{{- else }}
+rules: []
+{{- end }}
+{{- end }}
diff --git a/charts/admin-stack/charts/grafana/templates/rolebinding.yaml b/charts/admin-stack/charts/grafana/templates/rolebinding.yaml
new file mode 100644
index 0000000..cc07bd9
--- /dev/null
+++ b/charts/admin-stack/charts/grafana/templates/rolebinding.yaml
@@ -0,0 +1,25 @@
+{{- if .Values.rbac.create }}
+apiVersion: {{ include "grafana.rbac.apiVersion" . }}
+kind: RoleBinding
+metadata:
+  name: {{ include "grafana.fullname" . }}
+  namespace: {{ include "grafana.namespace" . }}
+  labels:
+    {{- include "grafana.labels" . | nindent 4 }}
+  {{- with .Values.annotations }}
+  annotations:
+    {{- toYaml . | nindent 4 }}
+  {{- end }}
+roleRef:
+  apiGroup: rbac.authorization.k8s.io
+  kind: Role
+  {{- if .Values.rbac.useExistingRole }}
+  name: {{ .Values.rbac.useExistingRole }}
+  {{- else }}
+  name: {{ include "grafana.fullname" . }}
+  {{- end }}
+subjects:
+- kind: ServiceAccount
+  name: {{ include "grafana.serviceAccountName" . }}
+  namespace: {{ include "grafana.namespace" . }}
+{{- end }}
diff --git a/charts/admin-stack/charts/grafana/templates/secret-env.yaml b/charts/admin-stack/charts/grafana/templates/secret-env.yaml
new file mode 100644
index 0000000..c765567
--- /dev/null
+++ b/charts/admin-stack/charts/grafana/templates/secret-env.yaml
@@ -0,0 +1,14 @@
+{{- if .Values.envRenderSecret }}
+apiVersion: v1
+kind: Secret
+metadata:
+  name: {{ include "grafana.fullname" . }}-env
+  namespace: {{ include "grafana.namespace" . }}
+  labels:
+    {{- include "grafana.labels" . | nindent 4 }}
+type: Opaque
+data:
+{{- range $key, $val := .Values.envRenderSecret }}
+  {{ $key }}: {{ $val | b64enc | quote }}
+{{- end }}
+{{- end }}
diff --git a/charts/admin-stack/charts/grafana/templates/secret.yaml b/charts/admin-stack/charts/grafana/templates/secret.yaml
new file mode 100644
index 0000000..5cbd527
--- /dev/null
+++ b/charts/admin-stack/charts/grafana/templates/secret.yaml
@@ -0,0 +1,26 @@
+{{- if or (and (not .Values.admin.existingSecret) (not .Values.env.GF_SECURITY_ADMIN_PASSWORD__FILE) (not .Values.env.GF_SECURITY_ADMIN_PASSWORD) (not .Values.env.GF_SECURITY_DISABLE_INITIAL_ADMIN_CREATION)) (and .Values.ldap.enabled (not .Values.ldap.existingSecret)) }}
+apiVersion: v1
+kind: Secret
+metadata:
+  name: {{ include "grafana.fullname" . }}
+  namespace: {{ include "grafana.namespace" . }}
+  labels:
+    {{- include "grafana.labels" . | nindent 4 }}
+  {{- with .Values.annotations }}
+  annotations:
+    {{- toYaml . | nindent 4 }}
+  {{- end }}
+type: Opaque
+data:
+  {{- if and (not .Values.env.GF_SECURITY_DISABLE_INITIAL_ADMIN_CREATION) (not .Values.admin.existingSecret) (not .Values.env.GF_SECURITY_ADMIN_PASSWORD__FILE) (not .Values.env.GF_SECURITY_ADMIN_PASSWORD) }}
+  admin-user: {{ .Values.adminUser | b64enc | quote }}
+  {{- if .Values.adminPassword }}
+  admin-password: {{ .Values.adminPassword | b64enc | quote }}
+  {{- else }}
+  admin-password: {{ include "grafana.password" . }}
+  {{- end }}
+  {{- end }}
+  {{- if not .Values.ldap.existingSecret }}
+  ldap-toml: {{ tpl .Values.ldap.config $ | b64enc | quote }}
+  {{- end }}
+{{- end }}
diff --git a/charts/admin-stack/charts/grafana/templates/service.yaml b/charts/admin-stack/charts/grafana/templates/service.yaml
new file mode 100644
index 0000000..17b2c4b
--- /dev/null
+++ b/charts/admin-stack/charts/grafana/templates/service.yaml
@@ -0,0 +1,51 @@
+{{- if .Values.service.enabled }}
+{{- $root := . }}
+apiVersion: v1
+kind: Service
+metadata:
+  name: {{ include "grafana.fullname" . }}
+  namespace: {{ include "grafana.namespace" . }}
+  labels:
+    {{- include "grafana.labels" . | nindent 4 }}
+    {{- with .Values.service.labels }}
+    {{- toYaml . | nindent 4 }}
+    {{- end }}
+spec:
+  {{- if (or (eq .Values.service.type "ClusterIP") (empty .Values.service.type)) }}
+  type: ClusterIP
+  {{- with .Values.service.clusterIP }}
+  clusterIP: {{ . }}
+  {{- end }}
+  {{- else if eq .Values.service.type "LoadBalancer" }}
+  type: {{ .Values.service.type }}
+  {{- with .Values.service.loadBalancerIP }}
+  loadBalancerIP: {{ . }}
+  {{- end }}
+  {{- with .Values.service.loadBalancerSourceRanges }}
+  loadBalancerSourceRanges:
+    {{- toYaml . | nindent 4 }}
+  {{- end }}
+  {{- else }}
+  type: {{ .Values.service.type }}
+  {{- end }}
+  {{- with .Values.service.externalIPs }}
+  externalIPs:
+    {{- toYaml . | nindent 4 }}
+  {{- end }}
+  ports:
+    - name: {{ .Values.service.portName }}
+      port: {{ .Values.service.port }}
+      protocol: TCP
+      targetPort: {{ .Values.service.targetPort }}
+      {{- with .Values.service.appProtocol }}
+      appProtocol: {{ . }}
+      {{- end }}
+      {{- if (and (eq .Values.service.type "NodePort") (not (empty .Values.service.nodePort))) }}
+      nodePort: {{ .Values.service.nodePort }}
+      {{- end }}
+      {{- with .Values.extraExposePorts }}
+      {{- tpl (toYaml . | nindent 4) $root }}
+      {{- end }}
+  selector:
+      {{- include "grafana.selectorLabels" . | nindent 4 }}
+{{- end }}
diff --git a/charts/admin-stack/charts/grafana/templates/serviceaccount.yaml b/charts/admin-stack/charts/grafana/templates/serviceaccount.yaml
new file mode 100644
index 0000000..784e71b
--- /dev/null
+++ b/charts/admin-stack/charts/grafana/templates/serviceaccount.yaml
@@ -0,0 +1,17 @@
+{{- if .Values.serviceAccount.create }}
+{{- $root := . -}}
+apiVersion: v1
+kind: ServiceAccount
+metadata:
+  labels:
+    {{- include "grafana.labels" . | nindent 4 }}
+    {{- with .Values.serviceAccount.labels }}
+    {{- toYaml . | nindent 4 }}
+    {{- end }}
+  {{- with .Values.serviceAccount.annotations }}
+  annotations:
+    {{- tpl (toYaml . | nindent 4) $root }}
+  {{- end }}
+  name: {{ include "grafana.serviceAccountName" . }}
+  namespace: {{ include "grafana.namespace" . }}
+{{- end }}
diff --git a/charts/admin-stack/charts/grafana/templates/statefulset.yaml b/charts/admin-stack/charts/grafana/templates/statefulset.yaml
new file mode 100644
index 0000000..da2a5c4
--- /dev/null
+++ b/charts/admin-stack/charts/grafana/templates/statefulset.yaml
@@ -0,0 +1,57 @@
+{{- if .Values.enabled }}
+{{- $sts := list "sts" "StatefulSet" "statefulset" -}}
+{{- if (or (.Values.useStatefulSet) (and .Values.persistence.enabled (not .Values.persistence.existingClaim) (has .Values.persistence.type $sts)))}}
+apiVersion: apps/v1
+kind: StatefulSet
+metadata:
+  name: {{ include "grafana.fullname" . }}
+  namespace: {{ include "grafana.namespace" . }}
+  labels:
+    {{- include "grafana.labels" . | nindent 4 }}
+  {{- with .Values.annotations }}
+  annotations:
+    {{- toYaml . | nindent 4 }}
+  {{- end }}
+spec:
+  replicas: {{ .Values.replicas }}
+  selector:
+    matchLabels:
+      {{- include "grafana.selectorLabels" . | nindent 6 }}
+  serviceName: {{ include "grafana.fullname" . }}-headless
+  template:
+    metadata:
+      labels:
+        {{- include "grafana.selectorLabels" . | nindent 8 }}
+        {{- with .Values.podLabels }}
+        {{- toYaml . | nindent 8 }}
+        {{- end }}
+      annotations:
+        checksum/config: {{ include (print $.Template.BasePath "/configmap.yaml") . | sha256sum }}
+        checksum/dashboards-json-config: {{ include (print $.Template.BasePath "/dashboards-json-configmap.yaml") . | sha256sum }}
+        checksum/sc-dashboard-provider-config: {{ include (print $.Template.BasePath "/configmap-dashboard-provider.yaml") . | sha256sum }}
+        {{- if and (or (and (not .Values.admin.existingSecret) (not .Values.env.GF_SECURITY_ADMIN_PASSWORD__FILE) (not .Values.env.GF_SECURITY_ADMIN_PASSWORD)) (and .Values.ldap.enabled (not .Values.ldap.existingSecret))) (not .Values.env.GF_SECURITY_DISABLE_INITIAL_ADMIN_CREATION) }}
+        checksum/secret: {{ include (print $.Template.BasePath "/secret.yaml") . | sha256sum }}
+        {{- end }}
+        {{- with .Values.podAnnotations }}
+        {{- toYaml . | nindent 8 }}
+        {{- end }}
+    spec:
+      {{- include "grafana.pod" . | nindent 6 }}
+  {{- if .Values.persistence.enabled}}
+  volumeClaimTemplates:
+  - metadata:
+      name: storage
+    spec:
+      accessModes: {{ .Values.persistence.accessModes }}
+      storageClassName: {{ .Values.persistence.storageClassName }}
+      resources:
+        requests:
+          storage: {{ .Values.persistence.size }}
+      {{- with .Values.persistence.selectorLabels }}
+      selector:
+        matchLabels:
+          {{- toYaml . | nindent 10 }}
+      {{- end }}
+  {{- end }}
+{{- end }}
+{{- end }}
diff --git a/charts/admin-stack/charts/grafana/values.yaml b/charts/admin-stack/charts/grafana/values.yaml
new file mode 100644
index 0000000..c845ae1
--- /dev/null
+++ b/charts/admin-stack/charts/grafana/values.yaml
@@ -0,0 +1,1062 @@
+image:
+  repository: grafana/grafana
+  # Overrides the Grafana image tag whose default is the chart appVersion
+  tag: ""
+  sha: ""
+  pullPolicy: IfNotPresent
+
+  ## Optionally specify an array of imagePullSecrets.
+  ## Secrets must be manually created in the namespace.
+  ## ref: https://kubernetes.io/docs/tasks/configure-pod-container/pull-image-private-registry/
+  ## Can be templated.
+  ##
+  pullSecrets: []
+  #   - myRegistrKeySecretName
+
+replicas: 1
+
+persistence:
+  enabled: false
+  type: pvc
+  # storageClassName: default
+  accessModes:
+    - ReadWriteOnce
+  size: 10Gi
+  # annotations: {}
+  finalizers:
+    - kubernetes.io/pvc-protection
+  # selectorLabels: {}
+  ## Sub-directory of the PV to mount. Can be templated.
+  # subPath: ""
+  ## Name of an existing PVC. Can be templated.
+  # existingClaim:
+  ## Extra labels to apply to a PVC.
+  extraPvcLabels: {}
+
+  ## If persistence is not enabled, this allows to mount the
+  ## local storage in-memory to improve performance
+  ##
+  inMemory:
+    enabled: false
+    ## The maximum usage on memory medium EmptyDir would be
+    ## the minimum value between the SizeLimit specified
+    ## here and the sum of memory limits of all containers in a pod
+    ##
+    # sizeLimit: 300Mi
+
+
+## Expose the grafana service to be accessed from outside the cluster (LoadBalancer service).
+## or access it from within the cluster (ClusterIP service). Set the service type and the port to serve it.
+## ref: http://kubernetes.io/docs/user-guide/services/
+##
+service:
+  enabled: true
+  type: ClusterIP
+  clusterIP: ""
+  loadBalancerIP: ""
+  loadBalancerSourceRanges: ""
+  externalIPs: ""
+  nodePort: ""
+  port: 80
+  targetPort: 3000
+  # targetPort: 4181 To be used with a proxy extraContainer
+  ## Service annotations. Can be templated.
+  annotations: {}
+  labels: {}
+  portName: service
+  # Adds the appProtocol field to the service. This allows to work with istio protocol selection. Ex: "http" or "tcp"
+  appProtocol: ""
+
+downloadDashboardsImage:
+  repository: curlimages/curl
+  tag: 7.85.0
+  sha: ""
+  pullPolicy: IfNotPresent
+
+
+downloadDashboards:
+  env: {}
+  envFromSecret: ""
+  resources: {}
+  securityContext: {}
+  envValueFrom: {}
+  #  ENV_NAME:
+  #    configMapKeyRef:
+  #      name: configmap-name
+  #      key: value_key
+
+
+## Pod Annotations
+# podAnnotations: {}
+
+
+## Pod Labels
+# podLabels: {}
+
+
+podPortName: grafana
+gossipPortName: gossip
+## Deployment annotations
+# annotations: {}
+
+
+# Enable creating the grafana configmap
+createConfigmap: true
+
+
+## See `kubectl explain poddisruptionbudget.spec` for more
+## ref: https://kubernetes.io/docs/tasks/run-application/configure-pdb/
+podDisruptionBudget:
+#  minAvailable: 1
+#  maxUnavailable: 1
+
+
+readinessProbe:
+  httpGet:
+    path: /api/health
+    port: 3000
+
+livenessProbe:
+  httpGet:
+    path: /api/health
+    port: 3000
+  initialDelaySeconds: 60
+  timeoutSeconds: 30
+  failureThreshold: 10
+
+
+## Use an alternate scheduler, e.g. "stork".
+## ref: https://kubernetes.io/docs/tasks/administer-cluster/configure-multiple-schedulers/
+##
+# schedulerName: "default-scheduler"
+
+
+## See `kubectl explain deployment.spec.strategy` for more
+## ref: https://kubernetes.io/docs/concepts/workloads/controllers/deployment/#strategy
+deploymentStrategy:
+  type: RollingUpdate
+
+
+## Create HorizontalPodAutoscaler object for deployment type
+#
+autoscaling:
+  enabled: false
+  minReplicas: 1
+  maxReplicas: 5
+  targetCPU: "60"
+  targetMemory: ""
+  behavior: {}
+
+
+## Number of old ReplicaSets to retain
+##
+revisionHistoryLimit: 10
+
+
+rbac:
+  create: true
+  ## Use an existing ClusterRole/Role (depending on rbac.namespaced false/true)
+  # useExistingRole: name-of-some-(cluster)role
+  pspEnabled: true
+  pspUseAppArmor: true
+  namespaced: false
+  extraRoleRules: []
+  # - apiGroups: []
+  #   resources: []
+  #   verbs: []
+  extraClusterRoleRules: []
+  # - apiGroups: []
+  #   resources: []
+  #   verbs: []
+
+
+serviceAccount:
+  create: true
+  name:
+  nameTest:
+  ## ServiceAccount labels.
+  labels: {}
+  ## Service account annotations. Can be templated.
+  #  annotations:
+  #    eks.amazonaws.com/role-arn: arn:aws:iam::123456789000:role/iam-role-name-here
+  autoMount: true
+
+
+## Create a headless service for the deployment
+headlessService: false
+
+
+# Administrator credentials when not using an existing secret (see below)
+adminUser: admin
+# adminPassword: strongpassword
+
+# Use an existing secret for the admin user.
+admin:
+  ## Name of the secret. Can be templated.
+  existingSecret: ""
+  userKey: admin-user
+  passwordKey: admin-password
+
+## Define command to be executed at startup by grafana container
+## Needed if using `vault-env` to manage secrets (ref: https://banzaicloud.com/blog/inject-secrets-into-pods-vault/)
+## Default is "run.sh" as defined in grafana's Dockerfile
+# command:
+# - "sh"
+# - "/run.sh"
+
+## Extra environment variables that will be pass onto deployment pods
+##
+## to provide grafana with access to CloudWatch on AWS EKS:
+## 1. create an iam role of type "Web identity" with provider oidc.eks.* (note the provider for later)
+## 2. edit the "Trust relationships" of the role, add a line inside the StringEquals clause using the
+## same oidc eks provider as noted before (same as the existing line)
+## also, replace NAMESPACE and prometheus-operator-grafana with the service account namespace and name
+##
+##  "oidc.eks.us-east-1.amazonaws.com/id/XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX:sub": "system:serviceaccount:NAMESPACE:prometheus-operator-grafana",
+##
+## 3. attach a policy to the role, you can use a built in policy called CloudWatchReadOnlyAccess
+## 4. use the following env: (replace 123456789000 and iam-role-name-here with your aws account number and role name)
+##
+## env:
+##   AWS_ROLE_ARN: arn:aws:iam::123456789000:role/iam-role-name-here
+##   AWS_WEB_IDENTITY_TOKEN_FILE: /var/run/secrets/eks.amazonaws.com/serviceaccount/token
+##   AWS_REGION: us-east-1
+##
+## 5. uncomment the EKS section in extraSecretMounts: below
+## 6. uncomment the annotation section in the serviceAccount: above
+## make sure to replace arn:aws:iam::123456789000:role/iam-role-name-here with your role arn
+
+env: {}
+
+## "valueFrom" environment variable references that will be added to deployment pods. Name is templated.
+## ref: https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.19/#envvarsource-v1-core
+## Renders in container spec as:
+##   env:
+##     ...
+##     - name: <key>
+##       valueFrom:
+##         <value rendered as YAML>
+envValueFrom: {}
+  #  ENV_NAME:
+  #    configMapKeyRef:
+  #      name: configmap-name
+#      key: value_key
+
+## The name of a secret in the same kubernetes namespace which contain values to be added to the environment
+## This can be useful for auth tokens, etc. Value is templated.
+envFromSecret: ""
+
+## Sensible environment variables that will be rendered as new secret object
+## This can be useful for auth tokens, etc
+envRenderSecret: {}
+
+## The names of secrets in the same kubernetes namespace which contain values to be added to the environment
+## Each entry should contain a name key, and can optionally specify whether the secret must be defined with an optional key.
+## Name is templated.
+envFromSecrets: []
+## - name: secret-name
+##   optional: true
+
+## The names of conifgmaps in the same kubernetes namespace which contain values to be added to the environment
+## Each entry should contain a name key, and can optionally specify whether the configmap must be defined with an optional key.
+## Name is templated.
+## ref: https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.23/#configmapenvsource-v1-core
+envFromConfigMaps: []
+## - name: configmap-name
+##   optional: true
+
+# Inject Kubernetes services as environment variables.
+# See https://kubernetes.io/docs/concepts/services-networking/connect-applications-service/#environment-variables
+enableServiceLinks: true
+
+## Additional grafana server secret mounts
+# Defines additional mounts with secrets. Secrets must be manually created in the namespace.
+extraSecretMounts: []
+  # - name: secret-files
+  #   mountPath: /etc/secrets
+  #   secretName: grafana-secret-files
+  #   readOnly: true
+  #   subPath: ""
+  #
+  # for AWS EKS (cloudwatch) use the following (see also instruction in env: above)
+  # - name: aws-iam-token
+  #   mountPath: /var/run/secrets/eks.amazonaws.com/serviceaccount
+  #   readOnly: true
+  #   projected:
+  #     defaultMode: 420
+  #     sources:
+  #       - serviceAccountToken:
+  #           audience: sts.amazonaws.com
+  #           expirationSeconds: 86400
+  #           path: token
+  #
+  # for CSI e.g. Azure Key Vault use the following
+  # - name: secrets-store-inline
+  #  mountPath: /run/secrets
+  #  readOnly: true
+  #  csi:
+  #    driver: secrets-store.csi.k8s.io
+  #    readOnly: true
+  #    volumeAttributes:
+  #      secretProviderClass: "akv-grafana-spc"
+  #    nodePublishSecretRef:                       # Only required when using service principal mode
+#       name: grafana-akv-creds                  # Only required when using service principal mode
+
+## Additional grafana server volume mounts
+# Defines additional volume mounts.
+extraVolumeMounts: []
+  # - name: extra-volume-0
+  #   mountPath: /mnt/volume0
+  #   readOnly: true
+  #   existingClaim: volume-claim
+  # - name: extra-volume-1
+  #   mountPath: /mnt/volume1
+  #   readOnly: true
+  #   hostPath: /usr/shared/
+  # - name: grafana-secrets
+  #   csi: true
+  #   data:
+  #     driver: secrets-store.csi.k8s.io
+  #     readOnly: true
+  #     volumeAttributes:
+#       secretProviderClass: "grafana-env-spc"
+
+## Container Lifecycle Hooks. Execute a specific bash command or make an HTTP request
+lifecycleHooks: {}
+  # postStart:
+  #   exec:
+#     command: []
+
+## Pass the plugins you want installed as a list.
+##
+plugins: []
+  # - digrich-bubblechart-panel
+# - grafana-clock-panel
+
+initChownData:
+  ## If false, data ownership will not be reset at startup
+  ## This allows the grafana-server to be run with an arbitrary user
+  ##
+  enabled: true
+
+
+  ## initChownData container image
+  ##
+  image:
+    repository: busybox
+    tag: "1.31.1"
+    sha: ""
+    pullPolicy: IfNotPresent
+
+  ## initChownData resource requests and limits
+  ## Ref: http://kubernetes.io/docs/user-guide/compute-resources/
+  ##
+  resources: {}
+  #  limits:
+  #    cpu: 100m
+  #    memory: 128Mi
+  #  requests:
+  #    cpu: 100m
+  #    memory: 128Mi
+  securityContext:
+    runAsNonRoot: false
+    runAsUser: 0
+
+
+# Administrator credentials when not using an existing secret (see below)
+adminUser: admin
+# adminPassword: strongpassword
+
+
+## Configure grafana datasources
+## ref: http://docs.grafana.org/administration/provisioning/#datasources
+##
+datasources: {}
+#  datasources.yaml:
+#    apiVersion: 1
+#    datasources:
+#    - name: Prometheus
+#      type: prometheus
+#      url: http://prometheus-prometheus-server
+#      access: proxy
+#      isDefault: true
+#    - name: CloudWatch
+#      type: cloudwatch
+#      access: proxy
+#      uid: cloudwatch
+#      editable: false
+#      jsonData:
+#        authType: default
+#        defaultRegion: us-east-1
+
+## Configure grafana alerting (can be templated)
+## ref: http://docs.grafana.org/administration/provisioning/#alerting
+##
+alerting: {}
+  # rules.yaml:
+  #   apiVersion: 1
+  #   groups:
+  #     - orgId: 1
+  #       name: '{{ .Chart.Name }}_my_rule_group'
+  #       folder: my_first_folder
+  #       interval: 60s
+  #       rules:
+  #         - uid: my_id_1
+  #           title: my_first_rule
+  #           condition: A
+  #           data:
+  #             - refId: A
+  #               datasourceUid: '-100'
+  #               model:
+  #                 conditions:
+  #                   - evaluator:
+  #                       params:
+  #                         - 3
+  #                       type: gt
+  #                     operator:
+  #                       type: and
+  #                     query:
+  #                       params:
+  #                         - A
+  #                     reducer:
+  #                       type: last
+  #                     type: query
+  #                 datasource:
+  #                   type: __expr__
+  #                   uid: '-100'
+  #                 expression: 1==0
+  #                 intervalMs: 1000
+  #                 maxDataPoints: 43200
+  #                 refId: A
+  #                 type: math
+  #           dashboardUid: my_dashboard
+  #           panelId: 123
+  #           noDataState: Alerting
+  #           for: 60s
+  #           annotations:
+  #             some_key: some_value
+  #           labels:
+  #             team: sre_team_1
+  # contactpoints.yaml:
+  #   apiVersion: 1
+  #   contactPoints:
+  #     - orgId: 1
+  #       name: cp_1
+  #       receivers:
+  #         - uid: first_uid
+  #           type: pagerduty
+  #           settings:
+  #             integrationKey: XXX
+  #             severity: critical
+  #             class: ping failure
+  #             component: Grafana
+  #             group: app-stack
+  #             summary: |
+#               {{ `{{ include "default.message" . }}` }}
+
+## Configure notifiers
+## ref: http://docs.grafana.org/administration/provisioning/#alert-notification-channels
+##
+notifiers: {}
+#  notifiers.yaml:
+#    notifiers:
+#    - name: email-notifier
+#      type: email
+#      uid: email1
+#      # either:
+#      org_id: 1
+#      # or
+#      org_name: Main Org.
+#      is_default: true
+#      settings:
+#        addresses: an_email_address@example.com
+#    delete_notifiers:
+
+## Configure grafana dashboard providers
+## ref: http://docs.grafana.org/administration/provisioning/#dashboards
+##
+## `path` must be /var/lib/grafana/dashboards/<provider_name>
+##
+dashboardProviders: {}
+#  dashboardproviders.yaml:
+#    apiVersion: 1
+#    providers:
+#    - name: 'default'
+#      orgId: 1
+#      folder: ''
+#      type: file
+#      disableDeletion: false
+#      editable: true
+#      options:
+#        path: /var/lib/grafana/dashboards/default
+
+## Configure grafana dashboard to import
+## NOTE: To use dashboards you must also enable/configure dashboardProviders
+## ref: https://grafana.com/dashboards
+##
+## dashboards per provider, use provider name as key.
+##
+dashboards: {}
+  # default:
+  #   some-dashboard:
+  #     json: |
+  #       $RAW_JSON
+  #   custom-dashboard:
+  #     file: dashboards/custom-dashboard.json
+  #   prometheus-stats:
+  #     gnetId: 2
+  #     revision: 2
+  #     datasource: Prometheus
+  #   local-dashboard:
+  #     url: https://example.com/repository/test.json
+  #     token: ''
+  #   local-dashboard-base64:
+  #     url: https://example.com/repository/test-b64.json
+  #     token: ''
+  #     b64content: true
+  #   local-dashboard-gitlab:
+  #     url: https://example.com/repository/test-gitlab.json
+  #     gitlabToken: ''
+  #   local-dashboard-bitbucket:
+  #     url: https://example.com/repository/test-bitbucket.json
+#     bearerToken: ''
+
+## Reference to external ConfigMap per provider. Use provider name as key and ConfigMap name as value.
+## A provider dashboards must be defined either by external ConfigMaps or in values.yaml, not in both.
+## ConfigMap data example:
+##
+## data:
+##   example-dashboard.json: |
+##     RAW_JSON
+##
+dashboardsConfigMaps: {}
+#  default: ""
+
+## Grafana's primary configuration
+## NOTE: values in map will be converted to ini format
+## ref: http://docs.grafana.org/installation/configuration/
+##
+grafana.ini:
+  paths:
+    data: /var/lib/grafana/
+    logs: /var/log/grafana
+    plugins: /var/lib/grafana/plugins
+    provisioning: /etc/grafana/provisioning
+  analytics:
+    check_for_updates: true
+  log:
+    mode: console
+  grafana_net:
+    url: https://grafana.net
+  server:
+    domain: "{{ if (and .Values.ingress.enabled .Values.ingress.hosts) }}{{ .Values.ingress.hosts | first }}{{ else }}''{{ end }}"
+      ## grafana Authentication can be enabled with the following values on grafana.ini
+      # server:
+    # The full public facing url you use in browser, used for redirects and emails
+  #    root_url:
+  # https://grafana.com/docs/grafana/latest/auth/github/#enable-github-in-grafana
+  # auth.github:
+  #    enabled: false
+  #    allow_sign_up: false
+  #    scopes: user:email,read:org
+  #    auth_url: https://github.com/login/oauth/authorize
+  #    token_url: https://github.com/login/oauth/access_token
+  #    api_url: https://api.github.com/user
+  #    team_ids:
+  #    allowed_organizations:
+  #    client_id:
+  #    client_secret:
+  ## LDAP Authentication can be enabled with the following values on grafana.ini
+  ## NOTE: Grafana will fail to start if the value for ldap.toml is invalid
+  # auth.ldap:
+  #   enabled: true
+  #   allow_sign_up: true
+  #   config_file: /etc/grafana/ldap.toml
+
+## Grafana's LDAP configuration
+## Templated by the template in _helpers.tpl
+## NOTE: To enable the grafana.ini must be configured with auth.ldap.enabled
+## ref: http://docs.grafana.org/installation/configuration/#auth-ldap
+## ref: http://docs.grafana.org/installation/ldap/#configuration
+ldap:
+  enabled: false
+  # `existingSecret` is a reference to an existing secret containing the ldap configuration
+  # for Grafana in a key `ldap-toml`.
+  existingSecret: ""
+  # `config` is the content of `ldap.toml` that will be stored in the created secret
+  config: ""
+  # config: |-
+  #   verbose_logging = true
+
+  #   [[servers]]
+  #   host = "my-ldap-server"
+  #   port = 636
+  #   use_ssl = true
+  #   start_tls = false
+  #   ssl_skip_verify = false
+  #   bind_dn = "uid=%s,ou=users,dc=myorg,dc=com"
+
+## Grafana's SMTP configuration
+## NOTE: To enable, grafana.ini must be configured with smtp.enabled
+## ref: http://docs.grafana.org/installation/configuration/#smtp
+smtp:
+  # `existingSecret` is a reference to an existing secret containing the smtp configuration
+  # for Grafana.
+  existingSecret: ""
+  userKey: "user"
+  passwordKey: "password"
+
+## Sidecars that collect the configmaps with specified label and stores the included files them into the respective folders
+## Requires at least Grafana 5 to work and can't be used together with parameters dashboardProviders, datasources and dashboards
+sidecar:
+  image:
+    repository: quay.io/kiwigrid/k8s-sidecar
+    tag: 1.22.0
+    sha: ""
+  imagePullPolicy: IfNotPresent
+  resources: {}
+  #   limits:
+  #     cpu: 100m
+  #     memory: 100Mi
+  #   requests:
+  #     cpu: 50m
+  #     memory: 50Mi
+  securityContext: {}
+  # skipTlsVerify Set to true to skip tls verification for kube api calls
+  # skipTlsVerify: true
+  enableUniqueFilenames: false
+  readinessProbe: {}
+  livenessProbe: {}
+  # Log level default for all sidecars. Can be one of: DEBUG, INFO, WARN, ERROR, CRITICAL. Defaults to INFO
+  # logLevel: INFO
+  alerts:
+    enabled: false
+    # Additional environment variables for the alerts sidecar
+    env: {}
+    # Do not reprocess already processed unchanged resources on k8s API reconnect.
+    # ignoreAlreadyProcessed: true
+    # label that the configmaps with alert are marked with
+    label: grafana_alert
+    # value of label that the configmaps with alert are set to
+    labelValue: ""
+    # Log level. Can be one of: DEBUG, INFO, WARN, ERROR, CRITICAL.
+    # logLevel: INFO
+    # If specified, the sidecar will search for alert config-maps inside this namespace.
+    # Otherwise the namespace in which the sidecar is running will be used.
+    # It's also possible to specify ALL to search in all namespaces
+    searchNamespace: null
+    # Method to use to detect ConfigMap changes. With WATCH the sidecar will do a WATCH requests, with SLEEP it will list all ConfigMaps, then sleep for 60 seconds.
+    watchMethod: WATCH
+    # search in configmap, secret or both
+    resource: both
+    # watchServerTimeout: request to the server, asking it to cleanly close the connection after that.
+    # defaults to 60sec; much higher values like 3600 seconds (1h) are feasible for non-Azure K8S
+    # watchServerTimeout: 3600
+    #
+    # watchClientTimeout: is a client-side timeout, configuring your local socket.
+    # If you have a network outage dropping all packets with no RST/FIN,
+    # this is how long your client waits before realizing & dropping the connection.
+    # defaults to 66sec (sic!)
+    # watchClientTimeout: 60
+    #
+    # Endpoint to send request to reload alerts
+    reloadURL: "http://localhost:3000/api/admin/provisioning/alerting/reload"
+    # Absolute path to shell script to execute after a alert got reloaded
+    script: null
+    skipReload: false
+    # Deploy the alert sidecar as an initContainer in addition to a container.
+    # Sets the size limit of the alert sidecar emptyDir volume
+    sizeLimit: {}
+  dashboards:
+    enabled: false
+    # Additional environment variables for the dashboards sidecar
+    env: {}
+    # Do not reprocess already processed unchanged resources on k8s API reconnect.
+    # ignoreAlreadyProcessed: true
+    SCProvider: true
+    # label that the configmaps with dashboards are marked with
+    label: grafana_dashboard
+    # value of label that the configmaps with dashboards are set to
+    labelValue: ""
+    # Log level. Can be one of: DEBUG, INFO, WARN, ERROR, CRITICAL.
+    # logLevel: INFO
+    # folder in the pod that should hold the collected dashboards (unless `defaultFolderName` is set)
+    folder: /tmp/dashboards
+    # The default folder name, it will create a subfolder under the `folder` and put dashboards in there instead
+    defaultFolderName: null
+    # Namespaces list. If specified, the sidecar will search for config-maps/secrets inside these namespaces.
+    # Otherwise the namespace in which the sidecar is running will be used.
+    # It's also possible to specify ALL to search in all namespaces.
+    searchNamespace: null
+    # Method to use to detect ConfigMap changes. With WATCH the sidecar will do a WATCH requests, with SLEEP it will list all ConfigMaps, then sleep for 60 seconds.
+    watchMethod: WATCH
+    # search in configmap, secret or both
+    resource: both
+    # If specified, the sidecar will look for annotation with this name to create folder and put graph here.
+    # You can use this parameter together with `provider.foldersFromFilesStructure`to annotate configmaps and create folder structure.
+    folderAnnotation: null
+    # Endpoint to send request to reload alerts
+    reloadURL: "http://localhost:3000/api/admin/provisioning/dashboards/reload"
+    # Absolute path to shell script to execute after a configmap got reloaded
+    script: null
+    skipReload: false
+    # watchServerTimeout: request to the server, asking it to cleanly close the connection after that.
+    # defaults to 60sec; much higher values like 3600 seconds (1h) are feasible for non-Azure K8S
+    # watchServerTimeout: 3600
+    #
+    # watchClientTimeout: is a client-side timeout, configuring your local socket.
+    # If you have a network outage dropping all packets with no RST/FIN,
+    # this is how long your client waits before realizing & dropping the connection.
+    # defaults to 66sec (sic!)
+    # watchClientTimeout: 60
+    #
+    # provider configuration that lets grafana manage the dashboards
+    provider:
+      # name of the provider, should be unique
+      name: sidecarProvider
+      # orgid as configured in grafana
+      orgid: 1
+      # folder in which the dashboards should be imported in grafana
+      folder: ''
+      # type of the provider
+      type: file
+      # disableDelete to activate a import-only behaviour
+      disableDelete: false
+      # allow updating provisioned dashboards from the UI
+      allowUiUpdates: false
+      # allow Grafana to replicate dashboard structure from filesystem
+      foldersFromFilesStructure: false
+    # Additional dashboard sidecar volume mounts
+    extraMounts: []
+    # Sets the size limit of the dashboard sidecar emptyDir volume
+    sizeLimit: {}
+  datasources:
+    enabled: false
+    # Additional environment variables for the datasourcessidecar
+    env: {}
+    # Do not reprocess already processed unchanged resources on k8s API reconnect.
+    # ignoreAlreadyProcessed: true
+    # label that the configmaps with datasources are marked with
+    label: grafana_datasource
+    # value of label that the configmaps with datasources are set to
+    labelValue: ""
+    # Log level. Can be one of: DEBUG, INFO, WARN, ERROR, CRITICAL.
+    # logLevel: INFO
+    # If specified, the sidecar will search for datasource config-maps inside this namespace.
+    # Otherwise the namespace in which the sidecar is running will be used.
+    # It's also possible to specify ALL to search in all namespaces
+    searchNamespace: null
+    # Method to use to detect ConfigMap changes. With WATCH the sidecar will do a WATCH requests, with SLEEP it will list all ConfigMaps, then sleep for 60 seconds.
+    watchMethod: WATCH
+    # search in configmap, secret or both
+    resource: both
+    # watchServerTimeout: request to the server, asking it to cleanly close the connection after that.
+    # defaults to 60sec; much higher values like 3600 seconds (1h) are feasible for non-Azure K8S
+    # watchServerTimeout: 3600
+    #
+    # watchClientTimeout: is a client-side timeout, configuring your local socket.
+    # If you have a network outage dropping all packets with no RST/FIN,
+    # this is how long your client waits before realizing & dropping the connection.
+    # defaults to 66sec (sic!)
+    # watchClientTimeout: 60
+    #
+    # Endpoint to send request to reload datasources
+    reloadURL: "http://localhost:3000/api/admin/provisioning/datasources/reload"
+    # Absolute path to shell script to execute after a datasource got reloaded
+    script: null
+    skipReload: false
+    # Deploy the datasource sidecar as an initContainer in addition to a container.
+    # This is needed if skipReload is true, to load any datasources defined at startup time.
+    initDatasources: false
+    # Sets the size limit of the datasource sidecar emptyDir volume
+    sizeLimit: {}
+  plugins:
+    enabled: false
+    # Additional environment variables for the plugins sidecar
+    env: {}
+    # Do not reprocess already processed unchanged resources on k8s API reconnect.
+    # ignoreAlreadyProcessed: true
+    # label that the configmaps with plugins are marked with
+    label: grafana_plugin
+    # value of label that the configmaps with plugins are set to
+    labelValue: ""
+    # Log level. Can be one of: DEBUG, INFO, WARN, ERROR, CRITICAL.
+    # logLevel: INFO
+    # If specified, the sidecar will search for plugin config-maps inside this namespace.
+    # Otherwise the namespace in which the sidecar is running will be used.
+    # It's also possible to specify ALL to search in all namespaces
+    searchNamespace: null
+    # Method to use to detect ConfigMap changes. With WATCH the sidecar will do a WATCH requests, with SLEEP it will list all ConfigMaps, then sleep for 60 seconds.
+    watchMethod: WATCH
+    # search in configmap, secret or both
+    resource: both
+    # watchServerTimeout: request to the server, asking it to cleanly close the connection after that.
+    # defaults to 60sec; much higher values like 3600 seconds (1h) are feasible for non-Azure K8S
+    # watchServerTimeout: 3600
+    #
+    # watchClientTimeout: is a client-side timeout, configuring your local socket.
+    # If you have a network outage dropping all packets with no RST/FIN,
+    # this is how long your client waits before realizing & dropping the connection.
+    # defaults to 66sec (sic!)
+    # watchClientTimeout: 60
+    #
+    # Endpoint to send request to reload plugins
+    reloadURL: "http://localhost:3000/api/admin/provisioning/plugins/reload"
+    # Absolute path to shell script to execute after a plugin got reloaded
+    script: null
+    skipReload: false
+    # Deploy the datasource sidecar as an initContainer in addition to a container.
+    # This is needed if skipReload is true, to load any plugins defined at startup time.
+    initPlugins: false
+    # Sets the size limit of the plugin sidecar emptyDir volume
+    sizeLimit: {}
+  notifiers:
+    enabled: false
+    # Additional environment variables for the notifierssidecar
+    env: {}
+    # Do not reprocess already processed unchanged resources on k8s API reconnect.
+    # ignoreAlreadyProcessed: true
+    # label that the configmaps with notifiers are marked with
+    label: grafana_notifier
+    # value of label that the configmaps with notifiers are set to
+    labelValue: ""
+    # Log level. Can be one of: DEBUG, INFO, WARN, ERROR, CRITICAL.
+    # logLevel: INFO
+    # If specified, the sidecar will search for notifier config-maps inside this namespace.
+    # Otherwise the namespace in which the sidecar is running will be used.
+    # It's also possible to specify ALL to search in all namespaces
+    searchNamespace: null
+    # Method to use to detect ConfigMap changes. With WATCH the sidecar will do a WATCH requests, with SLEEP it will list all ConfigMaps, then sleep for 60 seconds.
+    watchMethod: WATCH
+    # search in configmap, secret or both
+    resource: both
+    # watchServerTimeout: request to the server, asking it to cleanly close the connection after that.
+    # defaults to 60sec; much higher values like 3600 seconds (1h) are feasible for non-Azure K8S
+    # watchServerTimeout: 3600
+    #
+    # watchClientTimeout: is a client-side timeout, configuring your local socket.
+    # If you have a network outage dropping all packets with no RST/FIN,
+    # this is how long your client waits before realizing & dropping the connection.
+    # defaults to 66sec (sic!)
+    # watchClientTimeout: 60
+    #
+    # Endpoint to send request to reload notifiers
+    reloadURL: "http://localhost:3000/api/admin/provisioning/notifications/reload"
+    # Absolute path to shell script to execute after a notifier got reloaded
+    script: null
+    skipReload: false
+    # Deploy the notifier sidecar as an initContainer in addition to a container.
+    # This is needed if skipReload is true, to load any notifiers defined at startup time.
+    initNotifiers: false
+    # Sets the size limit of the notifier sidecar emptyDir volume
+    sizeLimit: {}
+
+## Override the deployment namespace
+##
+namespaceOverride: ""
+
+
+## Add a seperate remote image renderer deployment/service
+imageRenderer:
+  deploymentStrategy: {}
+  # Enable the image-renderer deployment & service
+  enabled: false
+  replicas: 1
+  autoscaling:
+    enabled: false
+    minReplicas: 1
+    maxReplicas: 5
+    targetCPU: "60"
+    targetMemory: ""
+    behavior: {}
+  image:
+    # image-renderer Image repository
+    repository: grafana/grafana-image-renderer
+    # image-renderer Image tag
+    tag: latest
+    # image-renderer Image sha (optional)
+    sha: ""
+    # image-renderer ImagePullPolicy
+    pullPolicy: Always
+  # extra environment variables
+  env:
+    HTTP_HOST: "0.0.0.0"
+    # RENDERING_ARGS: --no-sandbox,--disable-gpu,--window-size=1280x758
+    # RENDERING_MODE: clustered
+    # IGNORE_HTTPS_ERRORS: true
+  # image-renderer deployment serviceAccount
+  serviceAccountName: ""
+  # image-renderer deployment securityContext
+  securityContext: {}
+  # image-renderer deployment container securityContext
+  containerSecurityContext:
+    capabilities:
+      drop: ['ALL']
+    allowPrivilegeEscalation: false
+    readOnlyRootFilesystem: true
+  # image-renderer deployment Host Aliases
+  hostAliases: []
+  # image-renderer deployment priority class
+  priorityClassName: ''
+  service:
+    # Enable the image-renderer service
+    enabled: true
+    # image-renderer service port name
+    portName: 'http'
+    # image-renderer service port used by both service and deployment
+    port: 8081
+    targetPort: 8081
+    # Adds the appProtocol field to the image-renderer service. This allows to work with istio protocol selection. Ex: "http" or "tcp"
+    appProtocol: ""
+  serviceMonitor:
+    ## If true, a ServiceMonitor CRD is created for a prometheus operator
+    ## https://github.com/coreos/prometheus-operator
+    ##
+    enabled: false
+    path: /metrics
+    #  namespace: monitoring  (defaults to use the namespace this chart is deployed to)
+    labels: {}
+    interval: 1m
+    scheme: http
+    tlsConfig: {}
+    scrapeTimeout: 30s
+    relabelings: []
+    # See: https://doc.crds.dev/github.com/prometheus-operator/kube-prometheus/monitoring.coreos.com/ServiceMonitor/v1@v0.11.0#spec-targetLabels
+    targetLabels: []
+      # - targetLabel1
+    # - targetLabel2
+  # If https is enabled in Grafana, this needs to be set as 'https' to correctly configure the callback used in Grafana
+  grafanaProtocol: http
+  # In case a sub_path is used this needs to be added to the image renderer callback
+  grafanaSubPath: ""
+  # name of the image-renderer port on the pod
+  podPortName: http
+  # number of image-renderer replica sets to keep
+  revisionHistoryLimit: 10
+  networkPolicy:
+    # Enable a NetworkPolicy to limit inbound traffic to only the created grafana pods
+    limitIngress: true
+    # Enable a NetworkPolicy to limit outbound traffic to only the created grafana pods
+    limitEgress: false
+    # Allow additional services to access image-renderer (eg. Prometheus operator when ServiceMonitor is enabled)
+    extraIngressSelectors: []
+  resources: {}
+  #   limits:
+  #     cpu: 100m
+  #     memory: 100Mi
+  #   requests:
+  #     cpu: 50m
+  #     memory: 50Mi
+  ## Node labels for pod assignment
+  ## ref: https://kubernetes.io/docs/user-guide/node-selection/
+  #
+  nodeSelector: {}
+
+  ## Tolerations for pod assignment
+  ## ref: https://kubernetes.io/docs/concepts/configuration/taint-and-toleration/
+  ##
+  tolerations: []
+
+  ## Affinity for pod assignment (evaluated as template)
+  ## ref: https://kubernetes.io/docs/concepts/configuration/assign-pod-node/#affinity-and-anti-affinity
+  ##
+  affinity: {}
+
+  ## Use an alternate scheduler, e.g. "stork".
+  ## ref: https://kubernetes.io/docs/tasks/administer-cluster/configure-multiple-schedulers/
+  ##
+  # schedulerName: "default-scheduler"
+
+
+ingress:
+  enabled: false
+  # For Kubernetes >= 1.18 you should specify the ingress-controller via the field ingressClassName
+  # See https://kubernetes.io/blog/2020/04/02/improvements-to-the-ingress-api-in-kubernetes-1.18/#specifying-the-class-of-an-ingress
+  # ingressClassName: nginx
+  # Values can be templated
+  annotations: {}
+    # kubernetes.io/ingress.class: nginx
+  # kubernetes.io/tls-acme: "true"
+  labels: {}
+  path: /
+
+  # pathType is only for k8s >= 1.1=
+  pathType: Prefix
+
+  hosts:
+    - chart-example.local
+  ## Extra paths to prepend to every host configuration. This is useful when working with annotation based services.
+  extraPaths: []
+  # - path: /*
+  #   backend:
+  #     serviceName: ssl-redirect
+  #     servicePort: use-annotation
+  ## Or for k8s > 1.19
+  # - path: /*
+  #   pathType: Prefix
+  #   backend:
+  #     service:
+  #       name: ssl-redirect
+  #       port:
+  #         name: use-annotation
+
+
+  tls: []
+  #  - secretName: chart-example-tls
+  #    hosts:
+  #      - chart-example.local
+
+
+networkPolicy:
+  ## @param networkPolicy.enabled Enable creation of NetworkPolicy resources. Only Ingress traffic is filtered for now.
+  ##
+  enabled: false
+  ## @param networkPolicy.allowExternal Don't require client label for connections
+  ## The Policy model to apply. When set to false, only pods with the correct
+  ## client label will have network access to  grafana port defined.
+  ## When true, grafana will accept connections from any source
+  ## (with the correct destination port).
+  ##
+  ingress: true
+  ## @param networkPolicy.ingress When true enables the creation
+  ## an ingress network policy
+  ##
+  allowExternal: true
+  ## @param networkPolicy.explicitNamespacesSelector A Kubernetes LabelSelector to explicitly select namespaces from which traffic could be allowed
+  ## If explicitNamespacesSelector is missing or set to {}, only client Pods that are in the networkPolicy's namespace
+  ## and that match other criteria, the ones that have the good label, can reach the grafana.
+  ## But sometimes, we want the grafana to be accessible to clients from other namespaces, in this case, we can use this
+  ## LabelSelector to select these namespaces, note that the networkPolicy's namespace should also be explicitly added.
+  ##
+  ## Example:
+  ## explicitNamespacesSelector:
+  ##   matchLabels:
+  ##     role: frontend
+  ##   matchExpressions:
+  ##    - {key: role, operator: In, values: [frontend]}
+  ##
+  explicitNamespacesSelector: {}
+  ##
+  ##
+  ##
+  ##
+  ##
+  ##
+  egress:
+    ## @param networkPolicy.egress.enabled When enabled, an egress network policy will be
+    ## created allowing grafana to connect to external data sources from kubernetes cluster.
+    enabled: false
+    ##
+    ## @param networkPolicy.egress.ports Add individual ports to be allowed by the egress
+    ports: []
+      ## Add ports to the egress by specifying - port: <port number>
+      ## E.X.
+      ## ports:
+      ## - port: 80
+    ## - port: 443
+  ##
+  ##
+  ##
+  ##
+  ##
+  ##
\ No newline at end of file
diff --git a/charts/admin-stack/charts/nacos/.helmignore b/charts/admin-stack/charts/nacos/.helmignore
new file mode 100644
index 0000000..50af031
--- /dev/null
+++ b/charts/admin-stack/charts/nacos/.helmignore
@@ -0,0 +1,22 @@
+# 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
+.vscode/
diff --git a/charts/admin-stack/charts/nacos/Chart.yaml b/charts/admin-stack/charts/nacos/Chart.yaml
new file mode 100644
index 0000000..54abb3f
--- /dev/null
+++ b/charts/admin-stack/charts/nacos/Chart.yaml
@@ -0,0 +1,13 @@
+apiVersion: v2
+appVersion: "1.0"
+name: nacos
+description: an easy-to-use dynamic service discovery, configuration and service management platform for building cloud native applications.
+home: https://nacos.io
+kubeVersion: '>=1.20.0-0'
+maintainers:
+  - email: dev@dubbo.apache.org
+    name: dubbo
+sources:
+  - https://github.com/alibaba/nacos
+type: application
+version: 0.1.5
diff --git a/charts/dubbo-admin/templates/tpl/_images.tpl b/charts/admin-stack/charts/nacos/templates/NOTES.txt
similarity index 100%
copy from charts/dubbo-admin/templates/tpl/_images.tpl
copy to charts/admin-stack/charts/nacos/templates/NOTES.txt
diff --git a/charts/admin-stack/charts/nacos/templates/_helpers.tpl b/charts/admin-stack/charts/nacos/templates/_helpers.tpl
new file mode 100644
index 0000000..fd703f0
--- /dev/null
+++ b/charts/admin-stack/charts/nacos/templates/_helpers.tpl
@@ -0,0 +1,61 @@
+
+{{/*
+Create chart name and version as used by the chart label.
+*/}}
+{{- define "nacos.chart" -}}
+{{- printf "%s-%s" .Chart.Name .Chart.Version | replace "+" "_" | trunc 63 | trimSuffix "-" -}}
+{{- end -}}
+
+
+{{/* vim: set filetype=mustache: */}}
+{{/*
+Expand the name of the chart.
+*/}}
+{{- define "nacos.name" -}}
+{{- default .Chart.Name .Values.nameOverride | trunc 63 | trimSuffix "-" -}}
+{{- end -}}
+
+{{/*
+Create a default fully qualified app name.
+We truncate at 63 chars because some Kubernetes name fields are limited to this (by the DNS naming spec).
+If release name contains chart name it will be used as a full name.
+*/}}
+{{- define "nacos.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 -}}
+
+
+{{/*
+Nacos Namespace to use
+*/}}
+{{- define "nacos.namespace" -}}
+{{- if .Values.namespaceOverride -}}
+    {{- .Values.namespaceOverride -}}
+{{- else -}}
+    {{- .Release.Namespace -}}
+{{- end -}}
+{{- end -}}
+
+{{- define "nacos.labels" -}}
+app.kubernetes.io/name: {{ include "nacos.name" . }}
+helm.sh/chart: {{ include "nacos.chart" . }}
+app.kubernetes.io/instance: {{ .Release.Name }}
+app.kubernetes.io/managed-by: {{ .Release.Service }}
+{{- end -}}
+
+
+{{/*
+Labels to use on sts.spec.selector.matchLabels and svc.spec.selector
+*/}}
+{{- define "nacos.matchLabels" -}}
+app.kubernetes.io/name: {{ include "nacos.name" . }}
+{{- end -}}
\ No newline at end of file
diff --git a/charts/dubbo-admin/templates/admin-nacos/admin-nacos-configmap.yaml b/charts/admin-stack/charts/nacos/templates/configmap.yaml
similarity index 79%
rename from charts/dubbo-admin/templates/admin-nacos/admin-nacos-configmap.yaml
rename to charts/admin-stack/charts/nacos/templates/configmap.yaml
index 027cb94..f2243bf 100644
--- a/charts/dubbo-admin/templates/admin-nacos/admin-nacos-configmap.yaml
+++ b/charts/admin-stack/charts/nacos/templates/configmap.yaml
@@ -1,12 +1,12 @@
-{{- if .Values.nacos.enabled }}
-{{- if eq .Values.nacos.storage.type "mysql"}}
+{{- if .Values.enabled }}
+{{- if eq .Values.storage.type "mysql"}}
 apiVersion: v1
 kind: ConfigMap
 metadata:
   name: {{ template "nacos.fullname" . }}-configmap
   namespace: {{ template "nacos.namespace" . }}
 data:
-  {{- with .Values.nacos.storage.db }}
+  {{- with .Values.storage.db }}
   mysql.db.host: {{ .host }}
   mysql.db.name: {{ .name }}
   mysql.port: "{{ .port | default 3306 }}"
diff --git a/charts/admin-stack/charts/nacos/templates/networkpolicy.yaml b/charts/admin-stack/charts/nacos/templates/networkpolicy.yaml
new file mode 100644
index 0000000..195b068
--- /dev/null
+++ b/charts/admin-stack/charts/nacos/templates/networkpolicy.yaml
@@ -0,0 +1,27 @@
+{{- if .Values.networkPolicy.enabled }}
+kind: NetworkPolicy
+apiVersion: networking.k8s.io/v1 {{ include "nacos.networkPolicy.apiVersion" . }}
+metadata:
+  name: {{ include "nacos.fullname" . }}
+  namespace: {{ template "nacos.namespace" . }}
+  labels: {{- include "nacos.labels" . | nindent 4 }}
+spec:
+  podSelector:
+    matchLabels: {{- include "nacos.matchLabels" . | nindent 6 }}
+  policyTypes:
+    - Ingress
+  ingress:
+    - ports:
+        - port: {{ .Values.service.port }}
+      from:
+        - podSelector:
+            matchLabels:
+              {{ include "nacos.fullname" . }}-client: "true"
+        - podSelector:
+            matchLabels: {{- include "nacos.matchLabels" . | nindent 14 }}
+    - ports:
+        - port: {{ .Values.service.port }}
+      from:
+        - podSelector:
+            matchLabels: {{- include "nacos.matchLabels" . | nindent 14 }}
+  {{- end }}
\ No newline at end of file
diff --git a/charts/dubbo-admin/templates/admin-nacos/admin-nacos-pdb.yaml b/charts/admin-stack/charts/nacos/templates/pdb.yaml
similarity index 100%
rename from charts/dubbo-admin/templates/admin-nacos/admin-nacos-pdb.yaml
rename to charts/admin-stack/charts/nacos/templates/pdb.yaml
diff --git a/charts/dubbo-admin/templates/admin-nacos/admin-nacos-statefulset.yaml b/charts/admin-stack/charts/nacos/templates/statefulset.yaml
similarity index 75%
rename from charts/dubbo-admin/templates/admin-nacos/admin-nacos-statefulset.yaml
rename to charts/admin-stack/charts/nacos/templates/statefulset.yaml
index 420cff8..563fc2e 100644
--- a/charts/dubbo-admin/templates/admin-nacos/admin-nacos-statefulset.yaml
+++ b/charts/admin-stack/charts/nacos/templates/statefulset.yaml
@@ -1,4 +1,4 @@
-{{- if .Values.nacos.enabled }}
+{{- if .Values.enabled }}
 apiVersion: apps/v1
 kind: StatefulSet
 metadata:
@@ -30,11 +30,11 @@
       tolerations:
       {{- toYaml . | nindent 8 }}
       {{- end }}
-      {{- if and (eq .Values.nacos.mode "cluster") (.Values.nacos.plugin.enable) }}
+      {{- if and (eq .Values.global.mode "cluster") (.Values.plugin.enable) }}
       initContainers:
         - name: peer-finder-plugin-install
-          image: {{.Values.nacos.plugin.image.repository}}:{{.Values.nacos.plugin.image.tag}}
-          imagePullPolicy: {{ .Values.nacos.plugin.image.pullPolicy }}
+          image: {{.Values.plugin.image.repository }}:{{.Values.plugin.image.tag }}
+          imagePullPolicy: {{ .Values.plugin.image.pullPolicy }}
           volumeMounts:
             - mountPath: /home/nacos/plugins/peer-finder
               name: data
@@ -42,8 +42,8 @@
       {{- end }}
       containers:
         - name: nacos
-          image: "{{ .Values.nacos.image.repository }}:{{ .Values.nacos.image.tag }}"
-          imagePullPolicy: {{ .Values.nacos.image.pullPolicy }}
+          image: "{{ .Values.image.repository }}:{{ .Values.image.tag }}"
+          imagePullPolicy: {{ .Values.image.pullPolicy }}
           startupProbe:
             initialDelaySeconds: 180
             periodSeconds: 5
@@ -58,15 +58,15 @@
             timeoutSeconds: 10
             httpGet:
               scheme: HTTP
-              port: {{ .Values.nacos.service.port }}
+              port: {{ .Values.service.port }}
               path: /nacos/v1/console/health/liveness
           ports:
             - name: http
-              containerPort: {{ .Values.nacos.service.port }}
+              containerPort: {{ .Values.service.port }}
               protocol: TCP
-            - containerPort: {{ add .Values.nacos.service.port 1000 }}
+            - containerPort: {{ add .Values.service.port 1000 }}
               name: client-rpc
-            - containerPort: {{ add .Values.nacos.service.port 1001 }}
+            - containerPort: {{ add .Values.service.port 1001 }}
               name: raft-rpc
             - containerPort: 7848
               name: old-raft-rpc
@@ -74,16 +74,16 @@
           {{- toYaml .Values.resources | nindent 12 }}
           env:
             - name: NACOS_SERVER_PORT
-              value: {{ .Values.nacos.service.port | quote }}
+              value: {{ .Values.service.port | quote }}
             - name: NACOS_APPLICATION_PORT
-              value: {{ .Values.nacos.service.port | quote }}
+              value: {{ .Values.service.port | quote }}
             - name: PREFER_HOST_MODE
-              value: {{ .Values.nacos.service.port | quote }}
+              value: {{ .Values.service.port | quote }}
             {{- if eq .Values.nacos.mode "standalone" }}
             - name: MODE
               value: "standalone"
 
-            {{- else if eq .Values.nacos.mode "cluster" }}
+            {{- else if eq .Values.global.mode "cluster" }}
             - name: SERVICE_NAME
               value: "nacos-hs"
             - name: DOMAIN_NAME
@@ -94,7 +94,7 @@
                   apiVersion: v1
                   fieldPath: metadata.namespace
             {{- end }}
-            {{- if eq .Values.nacos.storage.type "mysql" }}
+            {{- if eq .Values.storage.type "mysql" }}
             - name: SPRING_DATASOURCE_PLATFORM
               value: "mysql"
             - name: MYSQL_SERVICE_HOST
@@ -151,7 +151,17 @@
     - metadata:
         name: data
       spec:
-  {{- toYaml .Values.nacos.persistence.data | nindent 8 }}
+        accessModes:
+        {{- range .Values.persistence.accessModes }}
+          - {{ . | quote }}
+        {{- end }}
+        resources:
+          requests:
+            storage: {{ .Values.persistence.size }}
+        {{ if .Values.persistence.ClaimName }}
+            claimName: {{ .Values.persistence.ClaimName }}
+        {{- else -}}
+            emptyDir: {{ .Values.persistence.emptyDir }}
   {{- end }}
   {{- end }}
-
+  {{- end }}
\ No newline at end of file
diff --git a/charts/admin-stack/charts/nacos/templates/svc-headless.yaml b/charts/admin-stack/charts/nacos/templates/svc-headless.yaml
new file mode 100644
index 0000000..4ac1bff
--- /dev/null
+++ b/charts/admin-stack/charts/nacos/templates/svc-headless.yaml
@@ -0,0 +1,28 @@
+{{- if .Values.enabled }}
+{{- if and (eq .Values.global.mode "cluster") }}
+apiVersion: v1
+kind: Service
+metadata:
+  name: {{ template "nacos.name" . }}-headless
+  namespace: {{ template "nacos.namespace" }}
+  labels: {{- include "nacos.labels" . | nindent 4 }}
+spec:
+  clusterIP: None
+  ports:
+    - port: {{ .Values.service.port }}
+      targetPort: {{ .Values.service.port }}
+      protocol: TCP
+      name: http
+    - port: {{ add .Values.service.port 1000 }}
+      name: client-rpc
+      targetPort: {{ add .Values.service.port 1000 }}
+    - port: {{ add .Values.service.port 1001 }}
+      name: raft-rpc
+      targetPort: {{ add .Values.service.port 1001 }}
+    - port: 7848
+      name: old-raft-rpc
+      targetPort: 7848
+      protocol: TCP
+  selector: {{- include "nacos.matchLabels" . | nindent 4 }}
+  {{- end }}
+  {{- end }}
\ No newline at end of file
diff --git a/charts/admin-stack/charts/nacos/templates/svc.yaml b/charts/admin-stack/charts/nacos/templates/svc.yaml
new file mode 100644
index 0000000..bbcbb55
--- /dev/null
+++ b/charts/admin-stack/charts/nacos/templates/svc.yaml
@@ -0,0 +1,29 @@
+{{- if .Values.enabled }}
+apiVersion: v1
+kind: Service
+metadata:
+  name: {{ template "nacos.name" . }}
+  namespace: {{ template "nacos.namespace" . }}
+  labels: {{- include "nacos.labels" . | nindent 4 }}
+spec:
+  type: {{ .Values.service.type }}
+  ports:
+    - port: {{ .Values.service.port }}
+      targetPort: {{ .Values.service.port }}
+      protocol: TCP
+      name: http
+    - port: {{ add .Values.service.port 1000 }}
+      name: client-rpc
+      targetPort: {{add .Values.service.port 1000 }}
+    - port: {{add .Values.service.port 1001 }}
+      name: raft-rpc
+      targetPort: {{add .Values.service.port 1001 }}
+    - port: 7848
+      name: old-raft-rpc
+      targetPort: 7848
+      protocol: TCP
+      {{- if eq .Values.service.type "NodePort" }}
+      nodePort: {{ .Values.service.nodePort }}
+  {{- end }}
+  selector: {{- include "nacos.matchLabels" . | nindent 4 }}
+  {{- end }}
\ No newline at end of file
diff --git a/charts/admin-stack/charts/nacos/values.yaml b/charts/admin-stack/charts/nacos/values.yaml
new file mode 100644
index 0000000..8bd3e6d
--- /dev/null
+++ b/charts/admin-stack/charts/nacos/values.yaml
@@ -0,0 +1,162 @@
+global:
+  mode: standalone
+  # mode: cluster
+
+
+image:
+  registry: docker.io
+  ##  e.g registry.k8s.io
+  repository: nacos/nacos-server
+  tag: latest
+  pullPolicy: IfNotPresent
+
+
+plugin:
+  enable: true
+  image:
+    repository: nacos/nacos-peer-finder-plugin
+    tag: 1.1
+    pullPolicy: IfNotPresent
+
+
+replicas: 1
+
+
+domainName: cluster.local
+
+
+storage:
+  type: ""
+#    type: mysql
+#    db:
+#      host: localhost
+#      name: nacos
+#      port: 3306
+#      username: usernmae
+#      password: password
+#      param: characterEncoding=utf8&connectTimeout=1000&socketTimeout=3000&autoReconnect=true&useSSL=false
+
+
+service:
+  name: http
+  ##
+  ## Service name.
+  ##
+  type: NodePort
+  ##
+  ## Service type.
+  ##
+  port: 8848
+  ##
+  ## Service port.
+  ##
+  nodePort: 30000
+  ##
+  ## Service nodePort.
+  ##
+  clusterIP: ""
+  ##
+  ## Service clusterIP.
+  ##
+  loadBalancerIP: ""
+  ##
+  ## Service loadBalancerIP.
+  ##
+  loadBalancerSourceRanges: ""
+  ##
+  ## Service loadBalancerSourceRanges.
+  ##
+  externalIPs: ""
+  ##
+  ## Service externalIPs.
+
+
+persistence:
+  enabled: false
+  accessModes:
+    - ReadWriteOnce
+  storageClassName: ""
+  size: 5Gi
+  ClaimName: {}
+  ## persistence emptyDir
+  emptyDir: {}
+
+
+## See `kubectl explain poddisruptionbudget.spec` for more
+## ref: https://kubernetes.io/docs/tasks/run-application/configure-pdb/
+podDisruptionBudget:
+  enabled: false
+  minAvailable: 1
+  # maxUnavailable: 1
+
+
+ingress:
+  enabled: false
+  # For Kubernetes >= 1.18 you should specify the ingress-controller via the field ingressClassName
+  # See https://kubernetes.io/blog/2020/04/02/improvements-to-the-ingress-api-in-kubernetes-1.18/#specifying-the-class-of-an-ingress
+  # ingressClassName: nginx
+  # Values can be templated
+  annotations: {}
+  # kubernetes.io/ingress.class: nginx
+  # kubernetes.io/tls-acme: "true"
+  labels: {}
+  path: /
+  ##
+  ##
+  # pathType is only for k8s >= 1.1=
+  pathType: Prefix
+  ##
+  ##
+  hosts:
+    - chart-example.local
+  ## Extra paths to prepend to every host configuration. This is useful when working with annotation based services.
+  extraPaths: []
+  # - path: /*
+  #   backend:
+  #     serviceName: ssl-redirect
+  #     servicePort: use-annotation
+  ## Or for k8s > 1.19
+  # - path: /*
+  #   pathType: Prefix
+  #   backend:
+  #     service:
+  #       name: ssl-redirect
+  #       port:
+  #         name: use-annotation
+  ##
+  ##
+  tls: []
+  #  - secretName: chart-example-tls
+  #    hosts:
+  #      - chart-example.local
+
+
+networkPolicy:
+  ## @param networkPolicy.enabled Enable creation of NetworkPolicy resources. Only Ingress traffic is filtered for now.
+  ##
+  enabled: false
+  ## @param networkPolicy.allowExternal Don't require client label for connections
+  ## The Policy model to apply. When set to false, only pods with the correct
+  ## client label will have network access to  dubbo-admin port defined.
+  ## When true, dubbo-admin will accept connections from any source
+  ## (with the correct destination port).
+  ##
+  ingress: true
+  ## @param networkPolicy.ingress When true enables the creation
+  ## an ingress network policy
+  ##
+  ##
+  ##
+  ##
+  egress:
+    ## @param networkPolicy.egress.enabled When enabled, an egress network policy will be
+    ## created allowing dubbo-admin to connect to external data sources from kubernetes cluster.
+    enabled: false
+    ##
+    ## @param networkPolicy.egress.ports Add individual ports to be allowed by the egress
+    ports: []
+      ## Add ports to the egress by specifying - port: <port number>
+      ## E.X.
+      ## ports:
+      ## - port: 80
+    ## - port: 443
\ No newline at end of file
diff --git a/charts/admin-stack/charts/zookeeper/.helmignore b/charts/admin-stack/charts/zookeeper/.helmignore
new file mode 100644
index 0000000..0e8a0eb
--- /dev/null
+++ b/charts/admin-stack/charts/zookeeper/.helmignore
@@ -0,0 +1,23 @@
+# Patterns to ignore when building packages.
+# This supports shell glob matching, relative path matching, and
+# negation (prefixed with !). Only one pattern per line.
+.DS_Store
+# Common VCS dirs
+.git/
+.gitignore
+.bzr/
+.bzrignore
+.hg/
+.hgignore
+.svn/
+# Common backup files
+*.swp
+*.bak
+*.tmp
+*.orig
+*~
+# Various IDEs
+.project
+.idea/
+*.tmproj
+.vscode/
diff --git a/charts/admin-stack/charts/zookeeper/Chart.yaml b/charts/admin-stack/charts/zookeeper/Chart.yaml
new file mode 100644
index 0000000..1cea2e7
--- /dev/null
+++ b/charts/admin-stack/charts/zookeeper/Chart.yaml
@@ -0,0 +1,12 @@
+apiVersion: v2
+appVersion: 3.8.1
+description: Apache ZooKeeper provides a reliable, centralized register of configuration
+  data and services for distributed applications.
+home: https://github.com/bitnami/charts/tree/main/bitnami/zookeeper
+maintainers:
+  - name: Bitnami
+    url: https://github.com/bitnami/charts
+name: zookeeper
+sources:
+  - https://zookeeper.apache.org/
+version: 11.1.2
diff --git a/charts/dubbo-admin/templates/tpl/_images.tpl b/charts/admin-stack/charts/zookeeper/templates/NOTES.txt
similarity index 100%
copy from charts/dubbo-admin/templates/tpl/_images.tpl
copy to charts/admin-stack/charts/zookeeper/templates/NOTES.txt
diff --git a/charts/admin-stack/charts/zookeeper/templates/_helpers.tpl b/charts/admin-stack/charts/zookeeper/templates/_helpers.tpl
new file mode 100644
index 0000000..210ffd3
--- /dev/null
+++ b/charts/admin-stack/charts/zookeeper/templates/_helpers.tpl
@@ -0,0 +1,62 @@
+{{/*
+Create chart name and version as used by the chart label.
+*/}}
+{{- define "zookeeper.chart" -}}
+{{- printf "%s-%s" .Chart.Name .Chart.Version | replace "+" "_" | trunc 63 | trimSuffix "-" -}}
+{{- end -}}
+
+
+{{/* vim: set filetype=mustache: */}}
+{{/*
+Expand the name of the chart.
+*/}}
+{{- define "zookeeper.name" -}}
+{{- default .Chart.Name .Values.nameOverride | trunc 63 | trimSuffix "-" -}}
+{{- end -}}
+
+
+{{/*
+Create a default fully qualified app name.
+We truncate at 63 chars because some Kubernetes name fields are limited to this (by the DNS naming spec).
+If release name contains chart name it will be used as a full name.
+*/}}
+{{- define "zookeeper.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 -}}
+
+
+{{/*
+Return ZooKeeper Namespace to use
+*/}}
+{{- define "zookeeper.namespace" -}}
+{{- if .Values.namespaceOverride -}}
+    {{- .Values.namespaceOverride -}}
+{{- else -}}
+    {{- .Release.Namespace -}}
+{{- end -}}
+{{- end -}}
+
+{{- define "zookeeper.labels" -}}
+app.kubernetes.io/name: {{ include "zookeeper.name" . }}
+helm.sh/chart: {{ include "zookeeper.chart" . }}
+app.kubernetes.io/instance: {{ .Release.Name }}
+app.kubernetes.io/managed-by: {{ .Release.Service }}
+{{- end -}}
+
+
+
+{{/*
+Labels to use on sts.spec.selector.matchLabels and svc.spec.selector
+*/}}
+{{- define "zookeeper.matchLabels" -}}
+app.kubernetes.io/name: {{ include "zookeeper.name" . }}
+{{- end -}}
\ No newline at end of file
diff --git a/charts/dubbo-admin/templates/admin-zookeeper/admin-zk-configmap.yaml b/charts/admin-stack/charts/zookeeper/templates/configmap.yaml
similarity index 95%
rename from charts/dubbo-admin/templates/admin-zookeeper/admin-zk-configmap.yaml
rename to charts/admin-stack/charts/zookeeper/templates/configmap.yaml
index df46791..8532f0d 100644
--- a/charts/dubbo-admin/templates/admin-zookeeper/admin-zk-configmap.yaml
+++ b/charts/admin-stack/charts/zookeeper/templates/configmap.yaml
@@ -1,4 +1,4 @@
-{{- if .Values.zookeeper.enabled }}
+{{- if .Values.enabled }}
 apiVersion: v1
 kind: ConfigMap
 metadata:
diff --git a/charts/dubbo-admin/templates/admin-zookeeper/admin-zk-networkpolicy.yaml b/charts/admin-stack/charts/zookeeper/templates/networkpolicy.yaml
similarity index 100%
rename from charts/dubbo-admin/templates/admin-zookeeper/admin-zk-networkpolicy.yaml
rename to charts/admin-stack/charts/zookeeper/templates/networkpolicy.yaml
diff --git a/charts/dubbo-admin/templates/admin-zookeeper/admin-zk-pdb.yaml b/charts/admin-stack/charts/zookeeper/templates/pdb.yaml
similarity index 100%
rename from charts/dubbo-admin/templates/admin-zookeeper/admin-zk-pdb.yaml
rename to charts/admin-stack/charts/zookeeper/templates/pdb.yaml
diff --git a/charts/dubbo-admin/templates/admin-zookeeper/admin-zk-statefulset.yaml b/charts/admin-stack/charts/zookeeper/templates/statefulset.yaml
similarity index 96%
rename from charts/dubbo-admin/templates/admin-zookeeper/admin-zk-statefulset.yaml
rename to charts/admin-stack/charts/zookeeper/templates/statefulset.yaml
index 67da933..4d07bdf 100644
--- a/charts/dubbo-admin/templates/admin-zookeeper/admin-zk-statefulset.yaml
+++ b/charts/admin-stack/charts/zookeeper/templates/statefulset.yaml
@@ -1,4 +1,4 @@
-{{- if .Values.zookeeper.enabled }}
+{{- if .Values.enabled }}
 apiVersion: {{ include "zookeeper.statefulset.apiVersion" . }}
 kind: StatefulSet
 metadata:
@@ -16,8 +16,8 @@
     spec:
       containers:
         - name: zookeeper
-          image: {{ .Values.zookeeper.image.repository }}:{{ .Values.zookeeper.image.tag }}
-          imagePullPolicy: {{ .Values.zookeeper.image.pullPolicy | quote }}
+          image: {{ .Values.image.repository }}:{{ .Values.image.tag }}
+          imagePullPolicy: {{ .Values.image.pullPolicy | quote }}
           {{- if .Values.containerSecurityContext.enabled }}
           securityContext: {{- omit .Values.containerSecurityContext "enabled" | toYaml | nindent 12 }}
           {{- end }}
diff --git a/charts/dubbo-admin/templates/admin-zookeeper/admin-zk-svc-headless.yaml b/charts/admin-stack/charts/zookeeper/templates/svc-headless.yaml
similarity index 78%
rename from charts/dubbo-admin/templates/admin-zookeeper/admin-zk-svc-headless.yaml
rename to charts/admin-stack/charts/zookeeper/templates/svc-headless.yaml
index b68d0e4..008a04b 100644
--- a/charts/dubbo-admin/templates/admin-zookeeper/admin-zk-svc-headless.yaml
+++ b/charts/admin-stack/charts/zookeeper/templates/svc-headless.yaml
@@ -1,19 +1,17 @@
-{{- if .Values.zookeeper.enabled }}
+{{- if .Values.enabled }}
 apiVersion: v1
 kind: Service
 metadata:
-  name: {{ template "zookeeper.fullname" . }}-headless
+  name: {{ template "zookeeper.name" . }}-headless
   namespace: {{ template "zookeeper.namespace" . }}
   labels: {{- include "zookeeper.labels" . | nindent 4 }}
 spec:
   type: {{ .Values.service.type }}
   clusterIP: None
   ports:
-    {{- if not .Values.service.disableBaseClientPort }}
     - name: tcp-client
       port: {{ .Values.service.ports.client }}
       targetPort: client
-    {{- end }}
     - name: tcp-follower
       port: {{ .Values.service.ports.follower }}
       targetPort: follower
diff --git a/charts/dubbo-admin/templates/admin-zookeeper/admin-zk-svc.yaml b/charts/admin-stack/charts/zookeeper/templates/svc.yaml
similarity index 95%
rename from charts/dubbo-admin/templates/admin-zookeeper/admin-zk-svc.yaml
rename to charts/admin-stack/charts/zookeeper/templates/svc.yaml
index 80ee6cd..a08c07b 100644
--- a/charts/dubbo-admin/templates/admin-zookeeper/admin-zk-svc.yaml
+++ b/charts/admin-stack/charts/zookeeper/templates/svc.yaml
@@ -1,8 +1,8 @@
-{{- if .Values.zookeeper.enabled }}
+{{- if .Values.enabled }}
 apiVersion: v1
 kind: Service
 metadata:
-  name: {{ template "zookeeper.fullname" . }}
+  name: {{ template "zookeeper.name" . }}
   namespace: {{ template "zookeeper.namespace" . }}
   labels: {{- include "zookeeper.labels" . | nindent 4 }}
 spec:
diff --git a/charts/admin-stack/charts/zookeeper/values.yaml b/charts/admin-stack/charts/zookeeper/values.yaml
new file mode 100644
index 0000000..670779e
--- /dev/null
+++ b/charts/admin-stack/charts/zookeeper/values.yaml
@@ -0,0 +1,499 @@
+image:
+  repository: bitnami/zookeeper
+  tag: 3.8.1-debian-11-r0
+  digest: ""
+  debug: false
+  pullPolicy: IfNotPresent
+
+replicas: 1
+
+persistence:
+  ## @param persistence.enabled Enable ZooKeeper data persistence using PVC. If false, use emptyDir
+  ##
+  enabled: false
+  ## @param persistence.existingClaim Name of an existing PVC to use (only when deploying a single replica)
+  ##
+  existingClaim: ""
+  ## @param persistence.storageClass PVC Storage Class for ZooKeeper data volume
+  ## If defined, storageClassName: <storageClass>
+  ## If set to "-", storageClassName: "", which disables dynamic provisioning
+  ## If undefined (the default) or set to null, no storageClassName spec is
+  ##   set, choosing the default provisioner.  (gp2 on AWS, standard on
+  ##   GKE, AWS & OpenStack)
+  ##
+  storageClass: ""
+  ## @param persistence.accessModes PVC Access modes
+  ##
+  accessModes:
+    - ReadWriteOnce
+  ## @param persistence.size PVC Storage Request for ZooKeeper data volume
+  ##
+  size: 8Gi
+  ## @param persistence.labels Labels for the PVC
+  ##
+  labels: {}
+  ## @param persistence.selector Selector to match an existing Persistent Volume for ZooKeeper's data PVC
+  ## If set, the PVC can't have a PV dynamically provisioned for it
+  ## E.g.
+  ## selector:
+  ##   matchLabels:
+  ##     app: my-app
+  ##
+  selector: {}
+  ## Persistence for a dedicated data log directory
+  ##
+  dataLogDir:
+    ## @param persistence.dataLogDir.size PVC Storage Request for ZooKeeper's dedicated data log directory
+    ##
+    size: 8Gi
+    ## @param persistence.dataLogDir.existingClaim Provide an existing `PersistentVolumeClaim` for ZooKeeper's data log directory
+    ## If defined, PVC must be created manually before volume will be bound
+    ## The value is evaluated as a template
+    ##
+    existingClaim: ""
+    ## @param persistence.dataLogDir.selector Selector to match an existing Persistent Volume for ZooKeeper's data log PVC
+    ## If set, the PVC can't have a PV dynamically provisioned for it
+    ## E.g.
+    ## selector:
+    ##   matchLabels:
+    ##     app: my-app
+    ##
+    selector: {}
+
+
+## Create HorizontalPodAutoscaler object for deployment type
+autoscaling:
+  enabled: false
+  minReplicas: 1
+  maxReplicas: 5
+  targetCPU: "60"
+  targetMemory: ""
+  behavior: {}
+
+
+service:
+  type: ClusterIP
+  ports:
+    client: 2181
+    follower: 2888
+    election: 3888
+  ## Node ports to expose
+  ## NOTE: choose port between <30000-32767>
+  ## @param service.nodePorts.client Node port for clients
+  ## @param service.nodePorts.tls Node port for TLS
+  ##
+  nodePorts:
+    client: ""
+    tls: ""
+  ## @param service.disableBaseClientPort Remove client port from service definitions.
+  ##
+  disableBaseClientPort: false
+  ## @param service.sessionAffinity Control where client requests go, to the same pod or round-robin
+  ## Values: ClientIP or None
+  ## ref: https://kubernetes.io/docs/user-guide/services/
+  ##
+  sessionAffinity: None
+  ## @param service.sessionAffinityConfig Additional settings for the sessionAffinity
+  ## sessionAffinityConfig:
+  ##   clientIP:
+  ##     timeoutSeconds: 300
+  ##
+  sessionAffinityConfig: {}
+  ## @param service.clusterIP ZooKeeper service Cluster IP
+  ## e.g.:
+  ## clusterIP: None
+  ##
+  clusterIP: ""
+  ## @param service.loadBalancerIP ZooKeeper service Load Balancer IP
+  ## ref: https://kubernetes.io/docs/user-guide/services/#type-loadbalancer
+  ##
+  loadBalancerIP: ""
+  ## @param service.loadBalancerSourceRanges ZooKeeper service Load Balancer sources
+  ## ref: https://kubernetes.io/docs/tasks/access-application-cluster/configure-cloud-provider-firewall/#restrict-access-for-loadbalancer-service
+  ## e.g:
+  ## loadBalancerSourceRanges:
+  ##   - 10.10.10.0/24
+  ##
+  loadBalancerSourceRanges: []
+  ## @param service.externalTrafficPolicy ZooKeeper service external traffic policy
+  ## ref https://kubernetes.io/docs/tasks/access-application-cluster/create-external-load-balancer/#preserving-the-client-source-ip
+  ##
+  externalTrafficPolicy: Cluster
+  ## @param service.annotations Additional custom annotations for ZooKeeper service
+  ##
+  annotations: {}
+  ## @param service.extraPorts Extra ports to expose in the ZooKeeper service (normally used with the `sidecar` value)
+  ##
+  extraPorts: []
+  ## @param service.headless.annotations Annotations for the Headless Service
+  ## @param service.headless.publishNotReadyAddresses If the ZooKeeper headless service should publish DNS records for not ready pods
+  ## @param service.headless.servicenameOverride String to partially override headless service name
+  ##
+  headless:
+    publishNotReadyAddresses: true
+    annotations: {}
+    servicenameOverride: ""
+
+
+## @param containerPorts.client ZooKeeper client container port
+## @param containerPorts.tls ZooKeeper TLS container port
+## @param containerPorts.follower ZooKeeper follower container port
+## @param containerPorts.election ZooKeeper election container port
+##
+containerPorts:
+  client: 2181
+  tls: 3181
+  follower: 2888
+  election: 3888
+## Configure extra options for ZooKeeper containers' liveness, readiness and startup probes
+## ref: https://kubernetes.io/docs/tasks/configure-pod-container/configure-liveness-readiness-startup-probes/#configure-probes
+## @param livenessProbe.enabled Enable livenessProbe on ZooKeeper containers
+## @param livenessProbe.initialDelaySeconds Initial delay seconds for livenessProbe
+## @param livenessProbe.periodSeconds Period seconds for livenessProbe
+## @param livenessProbe.timeoutSeconds Timeout seconds for livenessProbe
+## @param livenessProbe.failureThreshold Failure threshold for livenessProbe
+## @param livenessProbe.successThreshold Success threshold for livenessProbe
+## @param livenessProbe.probeCommandTimeout Probe command timeout for livenessProbe
+##
+livenessProbe:
+  enabled: true
+  initialDelaySeconds: 30
+  periodSeconds: 10
+  timeoutSeconds: 5
+  failureThreshold: 6
+  successThreshold: 1
+  probeCommandTimeout: 2
+## @param readinessProbe.enabled Enable readinessProbe on ZooKeeper containers
+## @param readinessProbe.initialDelaySeconds Initial delay seconds for readinessProbe
+## @param readinessProbe.periodSeconds Period seconds for readinessProbe
+## @param readinessProbe.timeoutSeconds Timeout seconds for readinessProbe
+## @param readinessProbe.failureThreshold Failure threshold for readinessProbe
+## @param readinessProbe.successThreshold Success threshold for readinessProbe
+## @param readinessProbe.probeCommandTimeout Probe command timeout for readinessProbe
+##
+readinessProbe:
+  enabled: true
+  initialDelaySeconds: 5
+  periodSeconds: 10
+  timeoutSeconds: 5
+  failureThreshold: 6
+  successThreshold: 1
+  probeCommandTimeout: 2
+## @param startupProbe.enabled Enable startupProbe on ZooKeeper containers
+## @param startupProbe.initialDelaySeconds Initial delay seconds for startupProbe
+## @param startupProbe.periodSeconds Period seconds for startupProbe
+## @param startupProbe.timeoutSeconds Timeout seconds for startupProbe
+## @param startupProbe.failureThreshold Failure threshold for startupProbe
+## @param startupProbe.successThreshold Success threshold for startupProbe
+##
+startupProbe:
+  enabled: false
+  initialDelaySeconds: 30
+  periodSeconds: 10
+  timeoutSeconds: 1
+  failureThreshold: 15
+  successThreshold: 1
+## @param customLivenessProbe Custom livenessProbe that overrides the default one
+##
+customLivenessProbe: {}
+## @param customReadinessProbe Custom readinessProbe that overrides the default one
+##
+customReadinessProbe: {}
+## @param customStartupProbe Custom startupProbe that overrides the default one
+##
+customStartupProbe: {}
+## @param lifecycleHooks for the ZooKeeper container(s) to automate configuration before or after startup
+##
+lifecycleHooks: {}
+## ZooKeeper resource requests and limits
+## ref: https://kubernetes.io/docs/user-guide/compute-resources/
+## @param resources.limits The resources limits for the ZooKeeper containers
+## @param resources.requests.memory The requested memory for the ZooKeeper containers
+## @param resources.requests.cpu The requested cpu for the ZooKeeper containers
+##
+resources:
+  limits: {}
+  requests:
+    memory: 256Mi
+    cpu: 250m
+## Configure Pods Security Context
+## ref: https://kubernetes.io/docs/tasks/configure-pod-container/security-context/#set-the-security-context-for-a-pod
+## @param podSecurityContext.enabled Enabled ZooKeeper pods' Security Context
+## @param podSecurityContext.fsGroup Set ZooKeeper pod's Security Context fsGroup
+##
+podSecurityContext:
+  enabled: true
+  fsGroup: 1001
+## Configure Container Security Context
+## ref: https://kubernetes.io/docs/tasks/configure-pod-container/security-context/#set-the-security-context-for-a-container
+## @param containerSecurityContext.enabled Enabled ZooKeeper containers' Security Context
+## @param containerSecurityContext.runAsUser Set ZooKeeper containers' Security Context runAsUser
+## @param containerSecurityContext.runAsNonRoot Set ZooKeeper containers' Security Context runAsNonRoot
+## @param containerSecurityContext.allowPrivilegeEscalation Force the child process to be run as nonprivilege
+##
+containerSecurityContext:
+  enabled: true
+  runAsUser: 1001
+  runAsNonRoot: true
+  allowPrivilegeEscalation: false
+## @param hostAliases ZooKeeper pods host aliases
+## https://kubernetes.io/docs/concepts/services-networking/add-entries-to-pod-etc-hosts-with-host-aliases/
+##
+hostAliases: []
+## @param podLabels Extra labels for ZooKeeper pods
+## ref: https://kubernetes.io/docs/concepts/overview/working-with-objects/labels/
+##
+
+
+extraVolumes: []
+## @param extraVolumeMounts Optionally specify extra list of additional volumeMounts for the ZooKeeper container(s)
+## Example Use Case: mount certificates to enable TLS
+## e.g:
+## extraVolumeMounts:
+## - name: zookeeper-keystore
+##   mountPath: /certs/keystore
+##   readOnly: true
+## - name: zookeeper-truststore
+##   mountPath: /certs/truststore
+##   readOnly: true
+##
+extraVolumeMounts: []
+## @param sidecars Add additional sidecar containers to the ZooKeeper pod(s)
+## e.g:
+## sidecars:
+##   - name: your-image-name
+##     image: your-image
+##     imagePullPolicy: Always
+##     ports:
+##       - name: portname
+##         containerPort: 1234
+##
+## @param tickTime Basic time unit (in milliseconds) used by ZooKeeper for heartbeats
+##
+##
+
+
+auth:
+  client:
+    ## @param auth.client.enabled Enable ZooKeeper client-server authentication. It uses SASL/Digest-MD5
+    ##
+    enabled: false
+    ## @param auth.client.clientUser User that will use ZooKeeper clients to auth
+    ##
+    clientUser: ""
+    ## @param auth.client.clientPassword Password that will use ZooKeeper clients to auth
+    ##
+    clientPassword: ""
+    ## @param auth.client.serverUsers Comma, semicolon or whitespace separated list of user to be created
+    ## Specify them as a string, for example: "user1,user2,admin"
+    ##
+    serverUsers: ""
+    ## @param auth.client.serverPasswords Comma, semicolon or whitespace separated list of passwords to assign to users when created
+    ## Specify them as a string, for example: "pass4user1, pass4user2, pass4admin"
+    ##
+    serverPasswords: ""
+    ## @param auth.client.existingSecret Use existing secret (ignores previous passwords)
+    ##
+    existingSecret: ""
+  quorum:
+    ## @param auth.quorum.enabled Enable ZooKeeper server-server authentication. It uses SASL/Digest-MD5
+    ##
+    enabled: false
+    ## @param auth.quorum.learnerUser User that the ZooKeeper quorumLearner will use to authenticate to quorumServers.
+    ## Note: Make sure the user is included in auth.quorum.serverUsers
+    ##
+    learnerUser: ""
+    ## @param auth.quorum.learnerPassword Password that the ZooKeeper quorumLearner will use to authenticate to quorumServers.
+    ##
+    learnerPassword: ""
+    ## @param auth.quorum.serverUsers Comma, semicolon or whitespace separated list of users for the quorumServers.
+    ## Specify them as a string, for example: "user1,user2,admin"
+    ##
+    serverUsers: ""
+    ## @param auth.quorum.serverPasswords Comma, semicolon or whitespace separated list of passwords to assign to users when created
+    ## Specify them as a string, for example: "pass4user1, pass4user2, pass4admin"
+    ##
+    serverPasswords: ""
+    ## @param auth.quorum.existingSecret Use existing secret (ignores previous passwords)
+    ##
+    existingSecret: ""
+## @param tickTime Basic time unit (in milliseconds) used by ZooKeeper for heartbeats
+##
+tickTime: 2000
+## @param initLimit ZooKeeper uses to limit the length of time the ZooKeeper servers in quorum have to connect to a leader
+##
+initLimit: 10
+## @param syncLimit How far out of date a server can be from a leader
+##
+syncLimit: 5
+## @param preAllocSize Block size for transaction log file
+##
+preAllocSize: 65536
+## @param snapCount The number of transactions recorded in the transaction log before a snapshot can be taken (and the transaction log rolled)
+##
+snapCount: 100000
+## @param maxClientCnxns Limits the number of concurrent connections that a single client may make to a single member of the ZooKeeper ensemble
+##
+maxClientCnxns: 60
+## @param maxSessionTimeout Maximum session timeout (in milliseconds) that the server will allow the client to negotiate
+## Defaults to 20 times the tickTime
+##
+maxSessionTimeout: 40000
+## @param heapSize Size (in MB) for the Java Heap options (Xmx and Xms)
+## This env var is ignored if Xmx an Xms are configured via `jvmFlags`
+##
+heapSize: 1024
+## @param fourlwCommandsWhitelist A list of comma separated Four Letter Words commands that can be executed
+##
+fourlwCommandsWhitelist: srvr, mntr, ruok
+## @param minServerId Minimal SERVER_ID value, nodes increment their IDs respectively
+## Servers increment their ID starting at this minimal value.
+## E.g., with `minServerId=10` and 3 replicas, server IDs will be 10, 11, 12 for z-0, z-1 and z-2 respectively.
+##
+minServerId: 1
+## @param listenOnAllIPs Allow ZooKeeper to listen for connections from its peers on all available IP addresses
+##
+listenOnAllIPs: false
+## Ongoing data directory cleanup configuration
+##
+autopurge:
+  ## @param autopurge.snapRetainCount The most recent snapshots amount (and corresponding transaction logs) to retain
+  ##
+  snapRetainCount: 3
+  ## @param autopurge.purgeInterval The time interval (in hours) for which the purge task has to be triggered
+  ## Set to a positive integer to enable the auto purging
+  ##
+  purgeInterval: 0
+## @param logLevel Log level for the ZooKeeper server. ERROR by default
+## Have in mind if you set it to INFO or WARN the ReadinessProve will produce a lot of logs
+##
+logLevel: ERROR
+## @param jvmFlags Default JVM flags for the ZooKeeper process
+##
+jvmFlags: ""
+## @param dataLogDir Dedicated data log directory
+## This allows a dedicated log device to be used, and helps avoid competition between logging and snapshots.
+## E.g.
+## dataLogDir: /bitnami/zookeeper/dataLog
+##
+dataLogDir: ""
+##
+##
+configuration: ""
+## @param existingConfigmap The name of an existing ConfigMap with your custom configuration for ZooKeeper
+## NOTE: When it's set the `configuration` parameter is ignored
+##
+existingConfigmap: ""
+## @param extraEnvVars Array with extra environment variables to add to ZooKeeper nodes
+## e.g:
+## extraEnvVars:
+##   - name: FOO
+##     value: "bar"
+##
+##
+## @param clusterDomain Kubernetes Cluster Domain
+##
+clusterDomain: cluster.local
+## @param extraDeploy Extra objects to deploy (evaluated as a template)
+##
+extraDeploy: []
+## @param commonLabels Add labels to all the deployed resources
+##
+Labels: {}
+## @param commonAnnotations Add annotations to all the deployed resources
+##
+Annotations: {}
+## @param namespaceOverride Override namespace for ZooKeeper resources
+## Useful when including ZooKeeper as a chart dependency, so it can be released into a different namespace than the parent
+##
+diagnosticMode:
+  ## @param diagnosticMode.enabled Enable diagnostic mode (all probes will be disabled and the command will be overridden)
+  ##
+  enabled: false
+  ## @param diagnosticMode.command Command to override all containers in the statefulset
+  ##
+  command:
+    - sleep
+  ## @param diagnosticMode.args Args to override all containers in the statefulset
+  ##
+  args:
+    - infinity
+
+## See `kubectl explain poddisruptionbudget.spec` for more
+## ref: https://kubernetes.io/docs/tasks/run-application/configure-pdb/
+podDisruptionBudget:
+  enabled: false
+  minAvailable: 1
+    # maxUnavailable: 1
+
+
+ingress:
+  enabled: false
+  # For Kubernetes >= 1.18 you should specify the ingress-controller via the field ingressClassName
+  # See https://kubernetes.io/blog/2020/04/02/improvements-to-the-ingress-api-in-kubernetes-1.18/#specifying-the-class-of-an-ingress
+  # ingressClassName: nginx
+  # Values can be templated
+  annotations: {}
+  # kubernetes.io/ingress.class: nginx
+  # kubernetes.io/tls-acme: "true"
+  labels: {}
+  path: /
+  ##
+  ##
+  # pathType is only for k8s >= 1.1=
+  pathType: Prefix
+  ##
+  ##
+  hosts:
+    - chart-example.local
+  ## Extra paths to prepend to every host configuration. This is useful when working with annotation based services.
+  extraPaths: []
+  # - path: /*
+  #   backend:
+  #     serviceName: ssl-redirect
+  #     servicePort: use-annotation
+  ## Or for k8s > 1.19
+  # - path: /*
+  #   pathType: Prefix
+  #   backend:
+  #     service:
+  #       name: ssl-redirect
+  #       port:
+  #         name: use-annotation
+  ##
+  ##
+  tls: []
+  #  - secretName: chart-example-tls
+  #    hosts:
+  #      - chart-example.local
+
+
+networkPolicy:
+  ## @param networkPolicy.enabled Enable creation of NetworkPolicy resources. Only Ingress traffic is filtered for now.
+  ##
+  enabled: false
+  ## @param networkPolicy.allowExternal Don't require client label for connections
+  ## The Policy model to apply. When set to false, only pods with the correct
+  ## client label will have network access to  dubbo-admin port defined.
+  ## When true, dubbo-admin will accept connections from any source
+  ## (with the correct destination port).
+  ##
+  ingress: true
+  ## @param networkPolicy.ingress When true enables the creation
+  ## an ingress network policy
+  ##
+  ##
+  ##
+  ##
+  egress:
+    ## @param networkPolicy.egress.enabled When enabled, an egress network policy will be
+    ## created allowing dubbo-admin to connect to external data sources from kubernetes cluster.
+    enabled: false
+    ##
+    ## @param networkPolicy.egress.ports Add individual ports to be allowed by the egress
+    ports: []
+      ## Add ports to the egress by specifying - port: <port number>
+      ## E.X.
+      ## ports:
+    ## - port: 80
+    ## - port: 443
\ No newline at end of file
diff --git a/charts/admin-stack/templates/tpl/_helpers.tpl b/charts/admin-stack/templates/tpl/_helpers.tpl
new file mode 100644
index 0000000..9f30c93
--- /dev/null
+++ b/charts/admin-stack/templates/tpl/_helpers.tpl
@@ -0,0 +1,27 @@
+{{/*
+Formats imagePullSecrets. Input is (dict "root" . "imagePullSecrets" .{specific imagePullSecrets})
+*/}}
+{{- define "dubbo-admin.imagePullSecrets" -}}
+{{- $root := .root }}
+{{- range (concat .root.Values.global.imagePullSecrets .imagePullSecrets) }}
+{{- if eq (typeOf .) "map[string]interface {}" }}
+- {{ toYaml (dict "name" (tpl .name $root)) | trim }}
+{{- else }}
+- name: {{ tpl . $root }}
+{{- end }}
+{{- end }}
+{{- end }}
+
+
+{{/*
+Return the ZooKeeper configuration ConfigMap name
+*/}}
+{{- define "zookeeper.configmapName" -}}
+{{- if .Values.existingConfigmap -}}
+    {{- printf "%s" (tpl .Values.existingConfigmap $) -}}
+{{- else -}}
+    {{- printf "%s" (include "zookeeper.fullname" .) -}}
+{{- end -}}
+{{- end -}}
+
+
diff --git a/charts/dubbo-admin/templates/tpl/_ingress.tpl b/charts/admin-stack/templates/tpl/_ingress.tpl
similarity index 100%
rename from charts/dubbo-admin/templates/tpl/_ingress.tpl
rename to charts/admin-stack/templates/tpl/_ingress.tpl
diff --git a/charts/admin-stack/templates/tpl/_kubeversions.tpl b/charts/admin-stack/templates/tpl/_kubeversions.tpl
new file mode 100644
index 0000000..f403a0c
--- /dev/null
+++ b/charts/admin-stack/templates/tpl/_kubeversions.tpl
@@ -0,0 +1,33 @@
+{{/*
+Return the target Kubernetes version
+*/}}
+{{- define "zookeeper.kubeVersion" -}}
+{{- if .Values.global }}
+    {{- if .Values.global.kubeVersion }}
+    {{- .Values.global.kubeVersion -}}
+    {{- else }}
+    {{- default .Capabilities.KubeVersion.Version .Values.kubeVersion -}}
+    {{- end -}}
+{{- else }}
+{{- default .Capabilities.KubeVersion.Version .Values.kubeVersion -}}
+{{- end -}}
+{{- end -}}
+
+
+{{/*
+Return the target Kubernetes version
+*/}}
+{{- define "nacos.kubeVersion" -}}
+{{- if .Values.global }}
+    {{- if .Values.global.kubeVersion }}
+    {{- .Values.global.kubeVersion -}}
+    {{- else }}
+    {{- default .Capabilities.KubeVersion.Version .Values.kubeVersion -}}
+    {{- end -}}
+{{- else }}
+{{- default .Capabilities.KubeVersion.Version .Values.kubeVersion -}}
+{{- end -}}
+{{- end -}}
+{{/*
+Return the appropriate apiVersion for statefulset.
+*/}}
\ No newline at end of file
diff --git a/charts/dubbo-admin/templates/tpl/_storages.tpl b/charts/admin-stack/templates/tpl/_storages.tpl
similarity index 91%
rename from charts/dubbo-admin/templates/tpl/_storages.tpl
rename to charts/admin-stack/templates/tpl/_storages.tpl
index 198a3d6..b92c9ca 100644
--- a/charts/dubbo-admin/templates/tpl/_storages.tpl
+++ b/charts/admin-stack/templates/tpl/_storages.tpl
@@ -5,7 +5,7 @@
 */}}
 {{- define "zookeeper.storage.class" -}}
 
-{{- $storageClass := .vpersistence.storageClass -}}
+{{- $storageClass := .persistence.storageClass -}}
 {{- if .global -}}
     {{- if .global.storageClass -}}
         {{- $storageClass = .global.storageClass -}}
diff --git a/charts/admin-stack/templates/tpl/_tplvalues.tpl b/charts/admin-stack/templates/tpl/_tplvalues.tpl
new file mode 100644
index 0000000..2fec362
--- /dev/null
+++ b/charts/admin-stack/templates/tpl/_tplvalues.tpl
@@ -0,0 +1,13 @@
+{{/* vim: set filetype=mustache: */}}
+{{/*
+Renders a value that contains template.
+Usage:
+{{ include "zookeeper.tplvalues" ( dict "value" .Values.path.to.the.Value "context" $) }}
+*/}}
+{{- define "zookeeper.tplvalues" -}}
+    {{- if typeIs "string" .value }}
+        {{- tpl .value .context }}
+    {{- else }}
+        {{- tpl (.value | toYaml) .context }}
+    {{- end }}
+{{- end -}}
\ No newline at end of file
diff --git a/charts/dubbo-admin/templates/tpl/_versions.tpl b/charts/admin-stack/templates/tpl/_versions.tpl
similarity index 71%
rename from charts/dubbo-admin/templates/tpl/_versions.tpl
rename to charts/admin-stack/templates/tpl/_versions.tpl
index c37a573..82611a4 100644
--- a/charts/dubbo-admin/templates/tpl/_versions.tpl
+++ b/charts/admin-stack/templates/tpl/_versions.tpl
@@ -36,44 +36,6 @@
 {{- end }}
 
 
-{{/*
-Create chart name and version as used by the chart label.
-*/}}
-{{- define "zookeeper.chart" -}}
-{{- end -}}
-{{/*
-Return the target Kubernetes version
-*/}}
-{{- define "zookeeper.kubeVersion" -}}
-{{- if .Values.global }}
-    {{- if .Values.global.kubeVersion }}
-    {{- .Values.global.kubeVersion -}}
-    {{- else }}
-    {{- default .Capabilities.KubeVersion.Version .Values.kubeVersion -}}
-    {{- end -}}
-{{- else }}
-{{- default .Capabilities.KubeVersion.Version .Values.kubeVersion -}}
-{{- end -}}
-{{- end -}}
-
-
-{{/*
-Return the target Kubernetes version
-*/}}
-{{- define "nacos.kubeVersion" -}}
-{{- if .Values.global }}
-    {{- if .Values.global.kubeVersion }}
-    {{- .Values.global.kubeVersion -}}
-    {{- else }}
-    {{- default .Capabilities.KubeVersion.Version .Values.kubeVersion -}}
-    {{- end -}}
-{{- else }}
-{{- default .Capabilities.KubeVersion.Version .Values.kubeVersion -}}
-{{- end -}}
-{{- end -}}
-{{/*
-Return the appropriate apiVersion for statefulset.
-*/}}
 {{- define "zookeeper.statefulset.apiVersion" -}}
 {{- if semverCompare "<1.14-0" (include "zookeeper.kubeVersion" .) -}}
 {{- print "apps/v1beta1" -}}
@@ -82,6 +44,7 @@
 {{- end -}}
 {{- end -}}
 
+
 {{/*
 Return the appropriate apiVersion for networkpolicy.
 */}}
@@ -105,6 +68,7 @@
 {{- end -}}
 {{- end -}}
 
+
 {{/*
 Return the appropriate apiVersion for poddisruptionbudget.
 */}}
diff --git a/charts/admin-stack/values.yaml b/charts/admin-stack/values.yaml
new file mode 100644
index 0000000..f26689c
--- /dev/null
+++ b/charts/admin-stack/values.yaml
@@ -0,0 +1,66 @@
+nacos:
+  enabled: false
+  default: false
+
+
+zookeeper:
+  enabled: true
+  default: true
+
+
+grafana:
+  enabled: false
+  default: false
+
+
+dubbo-admin:
+  enabled: true
+  default: true
+  properties:
+    admin.registry.address: zookeeper://zookeeper:2181
+    admin.config-center: zookeeper://zookeeper:2181
+    admin.metadata-report.address: zookeeper://zookeeper:2181
+    admin.root.user.name: root
+    admin.root.user.password: root
+    admin.check.sessionTimeoutMilli: 3600000
+    server.compression.enabled: true
+    server.compression.mime-types: text/css,text/javascript,application/javascript
+    server.compression.min-response-size: 10240
+    admin.check.tokenTimeoutMilli: 3600000
+    admin.check.signSecret: 86295dd0c4ef69a1036b0b0c15158d77
+    dubbo.application.name: dubbo-admin
+    dubbo.registry.address: ${admin.registry.address}
+    spring.datasource.url: jdbc:h2:mem:~/dubbo-admin;MODE=MYSQL;
+    spring.datasource.username: sa
+    spring.datasource.password:
+    mybatis-plus.global-config.db-config.id-type: none
+    dubbo.application.logger: slf4j
+
+    # nacos config, add parameters to url like username=nacos&password=nacos
+    # admin.registry.address: nacos://nacos:8848?group=DEFAULT_GROUP&namespace=public
+    # admin.config-center: nacos://nacos:8848?group=dubbo
+    # admin.metadata-report.address: nacos://nacos:8848?group=dubbo
+
+
+    # group (Deprecated it is recommended to use URL to add parameters,will be removed in the future)
+    # admin.registry.group: dubbo
+    # admin.config-center.group: dubbo
+    # admin.metadata-report.group: dubbo
+
+    # namespace used by nacos.(Deprecated it is recommended to use URL to add parameters,will be removed in the future)
+    # admin.registry.namespace: public
+    # admin.config-center.namespace: public
+    # admin.metadata-report.namespace: public
+
+    # apollo config
+    # admin.config-center: apollo://localhost:8070?token=e16e5cd903fd0c97a116c873b448544b9d086de9&app.id=test&env=dev&cluster=default&namespace=dubbo
+    # admin.apollo.token: e16e5cd903fd0c97a116c873b448544b9d086de9
+    # admin.apollo.appId: test
+    # admin.apollo.env: dev
+    # admin.apollo.cluster: default
+
+    # mysql
+    # spring.datasource.driver-class-name: com.mysql.jdbc.Driver
+    # spring.datasource.url: jdbc:mysql://localhost:3306/dubbo-admin?characterEncoding=utf8&connectTimeout=1000&socketTimeout=10000&autoReconnect=true
+    # spring.datasource.username: root
+    # spring.datasource.password: mysql
\ No newline at end of file
diff --git a/charts/dubbo-admin/templates/NOTES.txt b/charts/dubbo-admin/templates/NOTES.txt
deleted file mode 100644
index b22cf41..0000000
--- a/charts/dubbo-admin/templates/NOTES.txt
+++ /dev/null
@@ -1,59 +0,0 @@
-====================================================
-CHART NAME: {{ .Chart.Name }}
-VERSION: {{ .Chart.Name }}:{{ .Chart.AppVersion }}
-====================================================
-{{- if .Values.zookeeper.enabled }}
-Registration Center:{{ .Values.zookeeper.name }}
-VERSION: {{ .Values.zookeeper.name }}:{{ .Values.zookeeper.image.tag }}
-{{- end }}
-{{- if .Values.nacos.enabled }}
-Registration Center:{{ .Values.nacos.name }}
-VERSION: {{ .Values.nacos.name }}:{{ .Values.nacos.image.tag }}
-{{- end }}
-====================================================
-
-   Get the Dubbo-admin URL to visit by running these commands in the same shell:
-   {{- if contains "NodePort" .Values.service.type }}
-     export NODE_PORT=$(kubectl get --namespace {{ include "dubbo-admin.namespace" . }} -o jsonpath="{.spec.ports[0].nodePort}" services {{ include "dubbo-admin.fullname" . }})
-
-     export NODE_IP=$(kubectl get nodes --namespace {{ include "dubbo-admin.namespace" . }} -o jsonpath="{.items[0].status.addresses[0].address}")
-
-     echo http://$NODE_IP:$NODE_PORT
-   {{- else if contains "LoadBalancer" .Values.service.type }}
-   NOTE: It may take a few minutes for the LoadBalancer IP to be available.
-        You can watch the status of by running 'kubectl get svc --namespace {{ include "dubbo-admin.namespace" . }} -w {{ include "dubbo-admin.fullname" . }}'
-
-     export SERVICE_IP=$(kubectl get svc --namespace {{ include "dubbo-admin.namespace" . }} {{ include "dubbo-admin.fullname" . }} -o jsonpath='{.status.loadBalancer.ingress[0].ip}')
-
-     http://$SERVICE_IP:{{ .Values.service.port -}}
-   {{- else if contains "ClusterIP"  .Values.service.type }}
-
-     export POD_NAME=$(kubectl get pods --namespace {{ include "dubbo-admin.namespace" . }} -l "app.kubernetes.io/name={{ include "dubbo-admin.name" . }},app.kubernetes.io/instance={{ .Release.Name }}" -o jsonpath="{.items[0].metadata.name}")
-
-     kubectl --namespace {{ include "dubbo-admin.namespace" . }} port-forward $POD_NAME 38080
-   {{- end }}
-
-    Login Dubbo-admin default user and password
-   **********************************************
-          {{ .Chart.Name }}-username: root
-          {{ .Chart.Name }}-password: root
-   **********************************************
-
-
-   {{ if .Values.ingress.enabled }}
-   If you bind Dubbo-admin to 38080, please update values in values.yaml and reinstall:
-
-   From outside the cluster, the server URL(s) are:
-     {{- range .Values.ingress.hosts }}
-     http://{{ . }}
-     {{- end }}
-   {{- else }}
-
-
-{{- if not .Values.persistence.enabled }}
-#################################################################################
-######   WARNING: Persistence is disabled!!! You will lose your data when   #####
-######            the Dubbo-admin pod is terminated.                        #####
-#################################################################################
-{{- end }}
-{{- end }}
\ No newline at end of file
diff --git a/charts/dubbo-admin/templates/admin-hpa.yaml b/charts/dubbo-admin/templates/admin-hpa.yaml
deleted file mode 100644
index 6424890..0000000
--- a/charts/dubbo-admin/templates/admin-hpa.yaml
+++ /dev/null
@@ -1,28 +0,0 @@
-{{- if .Values.autoscaling.enabled }}
-apiVersion: autoscaling/v2beta1
-kind: HorizontalPodAutoscaler
-metadata:
-  name: {{ include "dubbo-admin.fullname" . }}
-  labels:
-    {{- include "dubbo-admin.labels" . | nindent 4 }}
-spec:
-  scaleTargetRef:
-    apiVersion: apps/v1
-    kind: Deployment
-    name: {{ include "dubbo-admin.fullname" . }}
-  minReplicas: {{ .Values.autoscaling.minReplicas }}
-  maxReplicas: {{ .Values.autoscaling.maxReplicas }}
-  metrics:
-    {{- if .Values.autoscaling.targetCPUUtilizationPercentage }}
-    - type: Resource
-      resource:
-        name: cpu
-        targetAverageUtilization: {{ .Values.autoscaling.targetCPUUtilizationPercentage }}
-    {{- end }}
-    {{- if .Values.autoscaling.targetMemoryUtilizationPercentage }}
-    - type: Resource
-      resource:
-        name: memory
-        targetAverageUtilization: {{ .Values.autoscaling.targetMemoryUtilizationPercentage }}
-    {{- end }}
-{{- end }}
diff --git a/charts/dubbo-admin/templates/admin-nacos/admin-nacos-networkpolicy.yaml b/charts/dubbo-admin/templates/admin-nacos/admin-nacos-networkpolicy.yaml
deleted file mode 100644
index c2adfb5..0000000
--- a/charts/dubbo-admin/templates/admin-nacos/admin-nacos-networkpolicy.yaml
+++ /dev/null
@@ -1,29 +0,0 @@
-{{- if .Values.networkPolicy.enabled }}
-kind: NetworkPolicy
-apiVersion: {{ include "nacos.networkPolicy.apiVersion" . }}
-metadata:
-  name: {{ include "nacos.fullname" . }}
-  namespace: {{ template "nacos.namespace" . }}
-  labels: {{- include "nacos.labels" . | nindent 4 }}
-spec:
-  podSelector:
-    matchLabels: {{- include "nacos.matchLabels" . | nindent 6 }}
-  policyTypes:
-    - Ingress
-  ingress:
-    - ports:
-        - port: {{ .Values.nacos.service.port }}
-      {{- if not .Values.networkPolicy.allowExternal }}
-      from:
-        - podSelector:
-            matchLabels:
-              {{ include "zookeeper.fullname" . }}-client: "true"
-        - podSelector:
-            matchLabels: {{- include "zookeeper.matchLabels" . | nindent 14 }}
-      {{- end }}
-    - ports:
-        - port: {{ .Values.nacos.service.port }}
-      from:
-        - podSelector:
-            matchLabels: {{- include "zookeeper.matchLabels" . | nindent 14 }}
-{{- end }}
diff --git a/charts/dubbo-admin/templates/admin-nacos/admin-nacos-svc-headless.yaml b/charts/dubbo-admin/templates/admin-nacos/admin-nacos-svc-headless.yaml
deleted file mode 100644
index 4d66c4a..0000000
--- a/charts/dubbo-admin/templates/admin-nacos/admin-nacos-svc-headless.yaml
+++ /dev/null
@@ -1,28 +0,0 @@
-{{- if .Values.nacos.enabled }}
-{{- if and (eq .Values.nacos.mode "cluster") }}
-apiVersion: v1
-kind: Service
-metadata:
-  name: {{ template "nacos.fullname" . }}-headless
-  namespace: {{ template "nacos.namespace" }}
-  labels: {{- include "nacos.labels" . | nindent 4 }}
-spec:
-  clusterIP: None
-  ports:
-    - port: {{ .Values.nacos.service.port }}
-      targetPort: {{ .Values.nacos.service.port }}
-      protocol: TCP
-      name: http
-    - port: {{ add .Values.nacos.service.port 1000 }}
-      name: client-rpc
-      targetPort: {{ add .Values.nacos.service.port 1000 }}
-    - port: {{add .Values.nacos.service.port 1001}}
-      name: raft-rpc
-      targetPort: {{ add .Values.nacos.service.port 1001 }}
-    - port: 7848
-      name: old-raft-rpc
-      targetPort: 7848
-      protocol: TCP
-  selector: {{- include "nacos.matchLabels" . | nindent 4 }}
-  {{- end }}
-  {{- end }}
\ No newline at end of file
diff --git a/charts/dubbo-admin/templates/admin-nacos/admin-nacos-svc.yaml b/charts/dubbo-admin/templates/admin-nacos/admin-nacos-svc.yaml
deleted file mode 100644
index 75ac3ef..0000000
--- a/charts/dubbo-admin/templates/admin-nacos/admin-nacos-svc.yaml
+++ /dev/null
@@ -1,29 +0,0 @@
-{{- if .Values.nacos.enabled }}
-apiVersion: v1
-kind: Service
-metadata:
-  name: {{ template "nacos.fullname" . }}
-  namespace: {{ template "nacos.namespace" . }}
-  labels: {{- include "nacos.labels" . | nindent 4 }}
-spec:
-  type: {{ .Values.nacos.service.type }}
-  ports:
-    - port: {{ .Values.nacos.service.port }}
-      targetPort: {{ .Values.nacos.service.port }}
-      protocol: TCP
-      name: http
-    - port: {{ add .Values.nacos.service.port 1000 }}
-      name: client-rpc
-      targetPort: {{add .Values.nacos.service.port 1000 }}
-    - port: {{add .Values.nacos.service.port 1001 }}
-      name: raft-rpc
-      targetPort: {{add .Values.nacos.service.port 1001 }}
-    - port: 7848
-      name: old-raft-rpc
-      targetPort: 7848
-      protocol: TCP
-      {{- if eq .Values.nacos.service.type "NodePort" }}
-      nodePort: {{ .Values.nacos.service.nodePort }}
-  {{- end }}
-  selector: {{- include "nacos.matchLabels" . | nindent 4 }}
-  {{- end }}
\ No newline at end of file
diff --git a/charts/dubbo-admin/templates/admin-secret-env.yaml b/charts/dubbo-admin/templates/admin-secret-env.yaml
deleted file mode 100644
index 73525e0..0000000
--- a/charts/dubbo-admin/templates/admin-secret-env.yaml
+++ /dev/null
@@ -1,14 +0,0 @@
-{{- if .Values.envSecret }}
-apiVersion: v1
-kind: Secret
-metadata:
-  name: {{ include "dubbo-admin.fullname" . }}-env
-  namespace: {{ include "dubbo-admin.namespace" . }}
-  labels:
-    {{- include "dubbo-admin.labels" . | nindent 4 }}
-type: Opaque
-data:
-{{- range $key, $val := .Values.envSecret }}
-  {{ $key }}: {{ $val | b64enc | quote }}
-{{- end }}
-{{- end }}
\ No newline at end of file
diff --git a/charts/dubbo-admin/templates/tpl/_charts.tpl b/charts/dubbo-admin/templates/tpl/_charts.tpl
deleted file mode 100644
index 8270792..0000000
--- a/charts/dubbo-admin/templates/tpl/_charts.tpl
+++ /dev/null
@@ -1,22 +0,0 @@
-{{/*
-Create chart name and version as used by the chart label.
-*/}}
-{{- define "dubbo-admin.chart" -}}
-{{- printf "%s-%s" .Chart.Name .Chart.Version | replace "+" "_" | trunc 63 | trimSuffix "-" }}
-{{- end }}
-
-
-{{/*
-Create chart name and version as used by the chart label.
-*/}}
-{{- define "zookeeper.chart" -}}
-{{- printf "%s-%s" .Chart.Name .Chart.Version | replace "+" "_" | trunc 63 | trimSuffix "-" -}}
-{{- end -}}
-
-
-{{/*
-Create chart name and version as used by the chart label.
-*/}}
-{{- define "nacos.chart" -}}
-{{- printf "%s-%s" .Chart.Name .Chart.Version | replace "+" "_" | trunc 63 | trimSuffix "-" -}}
-{{- end -}}
\ No newline at end of file
diff --git a/charts/dubbo-admin/templates/tpl/_helpers.tpl b/charts/dubbo-admin/templates/tpl/_helpers.tpl
deleted file mode 100644
index b230a99..0000000
--- a/charts/dubbo-admin/templates/tpl/_helpers.tpl
+++ /dev/null
@@ -1,138 +0,0 @@
-{{/*
-Create a default fully qualified app name.
-We truncate at 63 chars because some Kubernetes name fields are limited to this (by the DNS naming spec).
-If release name contains chart name it will be used as a full name.
-*/}}
-{{- define "dubbo-admin.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 fully qualified app name.
-We truncate at 63 chars because some Kubernetes name fields are limited to this (by the DNS naming spec).
-If release name contains chart name it will be used as a full name.
-*/}}
-{{- define "zookeeper.fullname" -}}
-{{- if .Values.zookeeper.zoo_name -}}
-{{- .Values.zookeeper.zoo_name | trunc 63 | trimSuffix "-" -}}
-{{- else -}}
-{{- $name := default .Values.zookeeper.zoo_name -}}
-{{- 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 fully qualified app name.
-We truncate at 63 chars because some Kubernetes name fields are limited to this (by the DNS naming spec).
-If release name contains chart name it will be used as a full name.
-*/}}
-{{- define "nacos.fullname" -}}
-{{- if .Values.nacos.name -}}
-{{- .Values.nacos.name | trunc 63 | trimSuffix "-" -}}
-{{- else -}}
-{{- $name := default .Values.nacos.name -}}
-{{- if contains $name .Release.Name -}}
-{{- .Release.Name | trunc 63 | trimSuffix "-" -}}
-{{- else -}}
-{{- printf "%s-%s" .Release.Name $name | trunc 63 | trimSuffix "-" -}}
-{{- end -}}
-{{- end -}}
-{{- end -}}
-
-
-{{/*
-Labels to use on sts.spec.selector.matchLabels and svc.spec.selector
-*/}}
-{{- define "zookeeper.matchLabels" -}}
-app.kubernetes.io/name: {{ include "zookeeper.name" . }}
-{{- end -}}
-
-{{/*
-Labels to use on sts.spec.selector.matchLabels and svc.spec.selector
-*/}}
-{{- define "nacos.matchLabels" -}}
-app.kubernetes.io/name: {{ include "nacos.name" . }}
-{{- end -}}
-
-
-{{- define "dubbo-admin.selectorLabels" -}}
-app.kubernetes.io/name: {{ include "dubbo-admin.name" . }}
-app.kubernetes.io/instance: {{ .Release.Name }}
-{{- end }}
-
-
-{{/*
-Create the name of the service account to use
-*/}}
-{{- define "dubbo-admin.serviceAccountName" -}}
-{{- if .Values.serviceAccount.enabled }}
-{{- default (include "dubbo-admin.fullname" .) .Values.serviceAccount.name }}
-{{- else }}
-{{- default "default" .Values.serviceAccount.name }}
-{{- end }}
-{{- end }}
-
-
-{{- define "dubbo-admin.serviceAccountNameTest" -}}
-{{- if .Values.serviceAccount.enabled }}
-{{- default (print (include "dubbo-admin.fullname" .) "-test") .Values.serviceAccount.nameTest }}
-{{- else }}
-{{- default "default" .Values.serviceAccount.nameTest }}
-{{- end }}
-{{- end }}
-
-
-{{/*
-Return the ZooKeeper configuration ConfigMap name
-*/}}
-{{- define "zookeeper.configmapName" -}}
-{{- if .Values.existingConfigmap -}}
-    {{- printf "%s" (tpl .Values.existingConfigmap $) -}}
-{{- else -}}
-    {{- printf "%s" (include "zookeeper.fullname" .) -}}
-{{- end -}}
-{{- end -}}
-
-
-{{/*
-Formats imagePullSecrets. Input is (dict "root" . "imagePullSecrets" .{specific imagePullSecrets})
-*/}}
-{{- define "dubbo-admin.imagePullSecrets" -}}
-{{- $root := .root }}
-{{- range (concat .root.Values.global.imagePullSecrets .imagePullSecrets) }}
-{{- if eq (typeOf .) "map[string]interface {}" }}
-- {{ toYaml (dict "name" (tpl .name $root)) | trim }}
-{{- else }}
-- name: {{ tpl . $root }}
-{{- end }}
-{{- end }}
-{{- end }}
-
-
-{{/* vim: set filetype=mustache: */}}
-{{/*
-Renders a value that contains template.
-Usage:
-{{ include "zookeeper.tplvalues" ( dict "value" .Values.path.to.the.Value "context" $) }}
-*/}}
-{{- define "zookeeper.tplvalues" -}}
-    {{- if typeIs "string" .value }}
-        {{- tpl .value .context }}
-    {{- else }}
-        {{- tpl (.value | toYaml) .context }}
-    {{- end }}
-{{- end -}}
\ No newline at end of file
diff --git a/charts/dubbo-admin/templates/tpl/_labels.tpl b/charts/dubbo-admin/templates/tpl/_labels.tpl
deleted file mode 100644
index 6739dd9..0000000
--- a/charts/dubbo-admin/templates/tpl/_labels.tpl
+++ /dev/null
@@ -1,24 +0,0 @@
-{{- define "dubbo-admin.labels" -}}
-helm.sh/chart: {{ include "dubbo-admin.chart" . }}
-{{ include "dubbo-admin.selectorLabels" . }}
-{{- if .Chart.AppVersion }}
-app.kubernetes.io/version: {{ .Chart.AppVersion | quote }}
-{{- end }}
-app.kubernetes.io/managed-by: {{ .Release.Service }}
-{{- end }}
-
-
-{{- define "zookeeper.labels" -}}
-app.kubernetes.io/name: {{ include "zookeeper.name" . }}
-helm.sh/chart: {{ include "zookeeper.chart" . }}
-app.kubernetes.io/instance: {{ .Release.Name }}
-app.kubernetes.io/managed-by: {{ .Release.Service }}
-{{- end -}}
-
-
-{{- define "nacos.labels" -}}
-app.kubernetes.io/name: {{ include "nacos.name" . }}
-helm.sh/chart: {{ include "nacos.chart" . }}
-app.kubernetes.io/instance: {{ .Release.Name }}
-app.kubernetes.io/managed-by: {{ .Release.Service }}
-{{- end -}}
\ No newline at end of file
diff --git a/charts/dubbo-admin/templates/tpl/_names.tpl b/charts/dubbo-admin/templates/tpl/_names.tpl
deleted file mode 100644
index cdfddce..0000000
--- a/charts/dubbo-admin/templates/tpl/_names.tpl
+++ /dev/null
@@ -1,25 +0,0 @@
-{{/* vim: set filetype=mustache: */}}
-{{/*
-Expand the name of the chart.
-*/}}
-{{- define "dubbo-admin.name" -}}
-{{- default .Chart.Name .Values.nameOverride | trunc 63 | trimSuffix "-" -}}
-{{- end -}}
-
-
-{{/* vim: set filetype=mustache: */}}
-{{/*
-Expand the name of the chart.
-*/}}
-{{- define "zookeeper.name" -}}
-{{- default .Values.zookeeper.name | trunc 63 | trimSuffix "-" -}}
-{{- end -}}
-
-
-{{/* vim: set filetype=mustache: */}}
-{{/*
-Expand the name of the chart.
-*/}}
-{{- define "nacos.name" -}}
-{{- default .Values.nacos.name | trunc 63 | trimSuffix "-" -}}
-{{- end -}}
\ No newline at end of file
diff --git a/charts/dubbo-admin/templates/tpl/_namespaces.tpl b/charts/dubbo-admin/templates/tpl/_namespaces.tpl
deleted file mode 100644
index cfc7e2b..0000000
--- a/charts/dubbo-admin/templates/tpl/_namespaces.tpl
+++ /dev/null
@@ -1,34 +0,0 @@
-{{/*
-Allow the release namespace to be overridden for multi-namespace deployments in combined charts
-*/}}
-{{- define "dubbo-admin.namespace" -}}
-{{- if .Values.namespaceOverride }}
-{{- .Values.namespaceOverride }}
-{{- else }}
-{{- .Release.Namespace }}
-{{- end }}
-{{- end }}
-
-
-{{/*
-Return ZooKeeper Namespace to use
-*/}}
-{{- define "zookeeper.namespace" -}}
-{{- if .Values.namespaceOverride -}}
-    {{- .Values.namespaceOverride -}}
-{{- else -}}
-    {{- .Release.Namespace -}}
-{{- end -}}
-{{- end -}}
-
-
-{{/*
-Nacos Namespace to use
-*/}}
-{{- define "nacos.namespace" -}}
-{{- if .Values.namespaceOverride -}}
-    {{- .Values.namespaceOverride -}}
-{{- else -}}
-    {{- .Release.Namespace -}}
-{{- end -}}
-{{- end -}}
\ No newline at end of file
diff --git a/charts/dubbo-admin/values.yaml b/charts/dubbo-admin/values.yaml
deleted file mode 100644
index ff07b6a..0000000
--- a/charts/dubbo-admin/values.yaml
+++ /dev/null
@@ -1,977 +0,0 @@
-## fullnameOverride String to fully override common.names.fullname template
-##
-##
-fullnameOverride: ""
-##
-##
-## nameOverride String to partially override common.names.fullname template (will maintain the release name)
-##
-nameOverride: ""
-##
-##
-## namespaceOverride String to partially override common.names.namespace template
-##
-namespaceOverride: ""
-##
-##
-## labels String to override common.names.labels template
-##
-labels: ""
-##
-##
-## annotations String to override common.names.annotations template
-##
-annotations: ""
-##
-##
-##
-##
-## global.imageRegistry Global Docker image registry
-## global.imagePullSecrets Global Docker registry secret names as an array
-## global.storageClass Global StorageClass for Persistent Volume(s)
-##
-global:
-  imageRegistry: ""
-  ## E.g.
-  ## imagePullSecrets:
-  ##   - myRegistryKeySecretName
-  ##
-  imagePullSecrets: []
-
-
-
-rbac:
-  enabled: true
-  # Use an existing ClusterRole/Role (depending on rbac.namespaced false/true)
-  pspEnabled: true
-  pspUseAppArmor: true
-  namespaced: false
-  extraRoleRules: []
-  useExistingRole: []
-  # - apiGroups: []
-  #   resources: []
-  #   verbs: []
-  extraClusterRoleRules: []
-  # - apiGroups: []
-  #   resources: []
-  #   verbs: []
-
-## serviceAccount
-serviceAccount:
-  enabled: true
-  ## ## ServiceAccount name.
-  name: {}
-  ## ServiceAccount nameTests.
-  nameTest: {}
-  ## ServiceAccount labels.
-  labels: {}
-  ## ServiceAccount annotations.
-  annotations: {}
-
-
-## replicas
-replicas: 1
-
-
-# -- Optional array of imagePullSecrets containing private registry credentials
-## Ref: https://kubernetes.io/docs/tasks/configure-pod-container/pull-image-private-registry/
-imagePullSecrets: []
-# - name: secretName
-
-
-## Create a headless service for the deployment
-headlessService: false
-
-
-## Create HorizontalPodAutoscaler object for deployment type
-autoscaling:
-  enabled: false
-  minReplicas: 1
-  maxReplicas: 5
-  targetCPU: "60"
-  targetMemory: ""
-  behavior: {}
-
-## Number of old ReplicaSets to retain
-##
-revisionHistoryLimit: 10
-
-
-## See `kubectl explain deployment.spec.strategy` for more
-## ref: https://kubernetes.io/docs/concepts/workloads/controllers/deployment/#strategy
-deploymentStrategy:
-  type: RollingUpdate
-
-
-## @param readinessProbe.enabled Enable readinessProbe on containers
-readinessProbe:
-  httpGet:
-    path: /
-    port: 8080
-  ## @param readinessProbe.initialDelaySeconds Initial delay seconds for readinessProbe
-  initialDelaySeconds: 60
-  ## @param readinessProbe.timeoutSeconds Timeout seconds for readinessProbe
-  timeoutSeconds: 30
-  ## @param readinessProbe.periodSeconds Period seconds for readinessProbe
-  periodSeconds: 10
-  ## @param readinessProbe.successThreshold Success threshold for readinessProbe
-  successThreshold: 1
-  ## @param readinessProbe.failureThreshold Failure threshold for readinessProbe
-  failureThreshold: 3
-  ## @param readinessProbe.probeCommandTimeout Probe command timeout for readinessProbe
-  probeCommandTimeout: 1
-
-
-##
-## @param livenessProbe.enabled Enable livenessProbe on containers
-livenessProbe:
-  httpGet:
-    path: /
-    port: 8080
-  ## @param livenessProbe.initialDelaySeconds Initial delay seconds for livenessProbe
-  initialDelaySeconds: 60
-  ## @param livenessProbe.timeoutSeconds Timeout seconds for livenessProbe
-  timeoutSeconds: 30
-  ## @param livenessProbe.periodSeconds Period seconds for livenessProbe
-  periodSeconds: 10
-  ## @param livenessProbe.successThreshold Success threshold for livenessProbe
-  successThreshold: 1
-  ## @param livenessProbe.failureThreshold Failure threshold for livenessProbe
-  failureThreshold: 3
-  ## @param livenessProbe.probeCommandTimeout Probe command timeout for livenessProbe
-  probeCommandTimeout: 1
-
-
-
-## @param startupProbe.enabled Enable startupProbe on containers
-startupProbe:
-  httpGet:
-    path: /
-    port: 8080
-  ## @param startupProbe.initialDelaySeconds Initial delay seconds for startupProbe
-  initialDelaySeconds: 60
-  ## @param startupProbe.timeoutSeconds Timeout seconds for startupProbe
-  timeoutSeconds: 30
-  ## @param startupProbe.periodSeconds Period seconds for startupProbe
-  periodSeconds: 10
-  ## @param startupProbe.successThreshold Success threshold for startupProbe
-  successThreshold: 1
-  ## @param startupProbe.failureThreshold Failure threshold for startupProbe
-  failureThreshold: 3
-
-
-## This module is the image acquisition method
-image:
-  registry: docker.io
-  ##  e.g registry.k8s.io
-  ##
-  ##
-  repository: apache/dubbo-admin
-  ##
-  ##
-  tag: "0.5.0"
-  ##
-  ##
-  debug: false
-  ##
-  ## Specify a imagePullPolicy
-  ## Defaults to 'Always' if image tag is 'latest', else set to 'IfNotPresent'
-  ## ref: https://kubernetes.io/docs/user-guide/images/#pre-pulling-images
-  ##
-  pullPolicy: IfNotPresent
-  ##
-  ## Optionally specify an array of imagePullSecrets.
-  ## Secrets must be manually created in the namespace.
-  ## ref: https://kubernetes.io/docs/tasks/configure-pod-container/pull-image-private-registry/
-  ## Can be templated.
-  ##
-  pullSecrets: []
-  #   - RegisterKeySecretName
-
-
-## Configure Pods Security Context
-securityContext:
-  # runAsUser: 570
-  # runAsGroup: 570
-  # fsGroup: 570
-
-
-tests:
-  enabled: true
-  image: busybox
-  tag: ""
-  imagePullPolicy: IfNotPresent
-  securityContext: {}
-
-
-## Init container Security Context
-containerSecurityContext:
-  enabled: false
-
-
-## Sensible environment variables that will be rendered as new secret object
-## This can be useful for auth tokens, etc
-envSecret: {}
-
-
-# -- `minReadySeconds` to avoid killing pods before we are ready
-##
-minReadySeconds: 0
-# -- Node tolerations for server scheduling to nodes with taints
-## Ref: https://kubernetes.io/docs/concepts/configuration/assign-pod-node/
-##
-
-
-## Create or not configmap
-ConfigmapEnabled: true
-
-
-## configmap mounts
-ConfigmapMounts: []
-  # - name: configMap-file
-  #   mountPath: /config
-  #   configMap: configMap-file
-  #   readOnly: true
-
-
-## secret mounts
-SecretMounts:
-#  - name: secret-file
-#    secret:
-#      secretName: secret-file
-
-
-## extraSecret Mounts
-extraSecretMounts: []
-  # - name: secret-files
-  #   mountPath: /etc/secrets
-  #   secretName: secret-files
-  #   readOnly: true
-  #   subPath: ""
-
-
-## emptyDir mounts
-EmptyDirMounts: []
-# - name: ""
-#   mountPath: /
-
-
-## Apply extra labels.
-extraLabels: {}
-
-
-## Assign a PriorityClassName to pods if set
-# priorityClassName: {}
-
-
-## Pod Annotations
-# podAnnotations: {}
-
-
-## Pod Labels
-# podLabels: {}
-
-
-## Expose the dubbo-admin service to be accessed from outside the cluster (LoadBalancer service).
-## or access it from within the cluster (ClusterIP service). Set the service type and the port to serve it.
-## ref: http://kubernetes.io/docs/user-guide/services/
-##
-service:
-  name: http
-  ##
-  ## Service name.
-  ##
-  enabled: true
-  ##
-  ## Service enable true or false.
-  ##
-  type: ClusterIP
-  ##
-  ## Service type.
-  ##
-  clusterIP: ""
-  ##
-  ## Service clusterIP.
-  ##
-  loadBalancerIP: ""
-  ##
-  ## Service loadBalancerIP.
-  ##
-  loadBalancerSourceRanges: ""
-  ##
-  ## Service loadBalancerSourceRanges.
-  ##
-  externalIPs: ""
-  ##
-  ## Service externalIPs.
-  ##
-  nodePort: ""
-  ##
-  ## Service nodePort.
-  ##
-  path: /
-  ##
-  ## Service path.
-  ##
-  port: 38080
-  ##
-  ## Service port.
-  ##
-  targetPort: http
-  ##
-  ## Service targetPort.
-  ##
-  containerPort: 8080
-  ##
-  ## Service containerPort.
-  ##
-  protocol: TCP
-  ##
-  ## Service protocol.
-  ##
-  ##
-  annotations: {}
-  ##
-  ## Service annotations. Can be templated.
-  ##
-  labels: {}
-  ##
-  ## Service labels.
-  ##
-  portName: service
-  ##
-  ## Service portName.
-  ##
-  appProtocol: ""
-  ##
-  ## Service appProtocol.
-  ##
-  ## Zookeeper Service.
-  ## @param service.type Kubernetes Service type
-  ##
-  ports:
-    client: 2181
-    follower: 2888
-    election: 3888
-  ## Node ports to expose
-  ## NOTE: choose port between <30000-32767>
-  ## @param service.nodePorts.client Node port for clients
-  ## @param service.nodePorts.tls Node port for TLS
-  ##
-  nodePorts:
-    client: ""
-  ## @param service.disableBaseClientPort Remove client port from service definitions.
-  ##
-  disableBaseClientPort: false
-  ## @param service.sessionAffinity Control where client requests go, to the same pod or round-robin
-  ## Values: ClientIP or None
-  ## ref: https://kubernetes.io/docs/user-guide/services/
-  ##
-  sessionAffinity: None
-  ## @param service.sessionAffinityConfig Additional settings for the sessionAffinity
-  ## sessionAffinityConfig:
-  ##   clientIP:
-  ##     timeoutSeconds: 300
-  ##
-  sessionAffinityConfig: {}
-  ##
-  ##
-  ##
-  externalTrafficPolicy: Cluster
-  ## @param service.annotations Additional custom annotations for ZooKeeper service
-  ##
-  ##
-  extraPorts: []
-  ## @param service.headless.annotations Annotations for the Headless Service
-  ## @param service.headless.publishNotReadyAddresses If the ZooKeeper headless service should publish DNS records for not ready pods
-  ## @param service.headless.servicenameOverride String to partially override headless service name
-  ##
-  headless:
-    publishNotReadyAddresses: true
-    annotations: {}
-    servicenameOverride: ""
-
-
-ingress:
-  enabled: false
-  # For Kubernetes >= 1.18 you should specify the ingress-controller via the field ingressClassName
-  # See https://kubernetes.io/blog/2020/04/02/improvements-to-the-ingress-api-in-kubernetes-1.18/#specifying-the-class-of-an-ingress
-  # ingressClassName: nginx
-  # Values can be templated
-  annotations: {}
-    # kubernetes.io/ingress.class: nginx
-  # kubernetes.io/tls-acme: "true"
-  labels: {}
-  path: /
-  ##
-  ##
-  # pathType is only for k8s >= 1.1=
-  pathType: Prefix
-  ##
-  ##
-  hosts:
-    - chart-example.local
-  ## Extra paths to prepend to every host configuration. This is useful when working with annotation based services.
-  extraPaths: []
-  # - path: /*
-  #   backend:
-  #     serviceName: ssl-redirect
-  #     servicePort: use-annotation
-  ## Or for k8s > 1.19
-  # - path: /*
-  #   pathType: Prefix
-  #   backend:
-  #     service:
-  #       name: ssl-redirect
-  #       port:
-  #         name: use-annotation
-  ##
-  ##
-  tls: []
-  #  - secretName: chart-example-tls
-  #    hosts:
-  #      - chart-example.local
-
-
-resources: {}
-#  limits:
-#    cpu: 100m
-#    memory: 128Mi
-#  requests:
-#    cpu: 100m
-#    memory: 128Mi
-
-
-extraresources: {}
-#  limits:
-#    cpu: 100m
-#    memory: 128Mi
-#  requests:
-#    cpu: 100m
-#    memory: 128Mi
-
-
-## Node labels for pod assignment
-## ref: https://kubernetes.io/docs/user-guide/node-selection/
-#
-nodeSelector: {}
-
-
-## Tolerations for pod assignment
-## ref: https://kubernetes.io/docs/concepts/configuration/taint-and-toleration/
-##
-tolerations: []
-
-
-## Affinity for pod assignment (evaluated as template)
-## ref: https://kubernetes.io/docs/concepts/configuration/assign-pod-node/#affinity-and-anti-affinity
-##
-affinity: {}
-
-
-## Topology Spread Constraints
-## ref: https://kubernetes.io/docs/concepts/workloads/pods/pod-topology-spread-constraints/
-##
-topologySpreadConstraints: []
-
-
-## Additional init containers (evaluated as template)
-## ref: https://kubernetes.io/docs/concepts/workloads/pods/init-containers/
-##
-InitContainers: []
-
-
-## Enable persistence using Persistent Volume Claims
-## ref: http://kubernetes.io/docs/user-guide/persistent-volumes/
-##
-persistence:
-  enabled: false
-  type: pvc
-  storageClassName: ""
-  accessModes:
-    - ReadWriteOnce
-  size: 10Gi
-  labels: {}
-  annotations: {}
-  existingClaim: ""
-  finalizers:
-    - kubernetes.io/pvc-protection
-  selectorLabels: {}
-  ## Sub-directory of the PV to mount. Can be templated.
-  # subPath: ""
-  ## Name of an existing PVC. Can be templated.
-  ClaimName: {}
-  ## Extra labels to apply to a PVC.
-  extraPvcLabels: {}
-
-  ## If persistence is not enabled, this allows to mount the
-  ## local storage in-memory to improve performance
-  ##
-  inMemory:
-    enabled: false
-    ## The maximum usage on memory medium EmptyDir would be
-    ## the minimum value between the SizeLimit specified
-    ## here and the sum of memory limits of all containers in a pod
-    ##
-    # sizeLimit: 300Mi
-  emptyDir:
-    ## dubbo-admin emptyDir volume size limit
-    ##
-    sizeLimit: ""
-  selector: {}
-    ## Persistence for a dedicated data log directory
-    ##
-  dataLogDir:
-    ## @param persistence.dataLogDir.size PVC Storage Request for ZooKeeper's dedicated data log directory
-    ##
-    size: 8Gi
-    ## @param persistence.dataLogDir.existingClaim Provide an existing `PersistentVolumeClaim` for ZooKeeper's data log directory
-    ## If defined, PVC must be created manually before volume will be bound
-    ## The value is evaluated as a template
-    ##
-    existingClaim: ""
-    ## @param persistence.dataLogDir.selector Selector to match an existing Persistent Volume for ZooKeeper's data log PVC
-    ## If set, the PVC can't have a PV dynamically provisioned for it
-    ## E.g.
-    ## selector:
-    ##   matchLabels:
-    ##     app: my-app
-    ##
-    selector: {}
-
-
-initChown:
-  ## If false, data ownership will not be reset at startup
-  ## This allows the dubbo-admin-server to be run with an arbitrary user
-  ##
-  ##
-  ##
-  enabled: true
-  ##
-  ##
-  ## initChownData container image
-  ##
-  ##
-  image:
-    repository: busybox
-    tag: "1.31.1"
-    sha: ""
-    pullPolicy: IfNotPresent
-  ##
-  ##
-  ##
-  ##
-  ## initChown resource requests and limits
-  ## Ref: http://kubernetes.io/docs/user-guide/compute-resources/
-  ##
-  resources: {}
-  #  limits:
-  #    cpu: 100m
-  #    memory: 128Mi
-  #  requests:
-  #    cpu: 100m
-  #    memory: 128Mi
-
-  securityContext:
-    runAsNonRoot: false
-    runAsUser: 0
-
-
-## Container Lifecycle Hooks. Execute a specific bash command or make an HTTP request
-lifecycleHooks: {}
-  # postStart:
-  #   exec:
-  #     command: []
-  # preStop:
-  #   exec:
-  #     command: []
-
-
-## See `kubectl explain poddisruptionbudget.spec` for more
-## ref: https://kubernetes.io/docs/tasks/run-application/configure-pdb/
-podDisruptionBudget:
-  enabled: false
-  minAvailable: 1
-  # maxUnavailable: 1
-
-
-networkPolicy:
-  ## @param networkPolicy.enabled Enable creation of NetworkPolicy resources. Only Ingress traffic is filtered for now.
-  ##
-  enabled: false
-  ## @param networkPolicy.allowExternal Don't require client label for connections
-  ## The Policy model to apply. When set to false, only pods with the correct
-  ## client label will have network access to  dubbo-admin port defined.
-  ## When true, dubbo-admin will accept connections from any source
-  ## (with the correct destination port).
-  ##
-  ingress: true
-  ## @param networkPolicy.ingress When true enables the creation
-  ## an ingress network policy
-  ##
-  allowExternal: true
-  ## @param networkPolicy.explicitNamespacesSelector A Kubernetes LabelSelector to explicitly select namespaces from which traffic could be allowed
-  ## If explicitNamespacesSelector is missing or set to {}, only client Pods that are in the networkPolicy's namespace
-  ## and that match other criteria, the ones that have the good label, can reach the dubbo-admin.
-  ## But sometimes, we want the dubbo-admin to be accessible to clients from other namespaces, in this case, we can use this
-  ## LabelSelector to select these namespaces, note that the networkPolicy's namespace should also be explicitly added.
-  ##
-  ## Example:
-  ## explicitNamespacesSelector:
-  ##   matchLabels:
-  ##     role: frontend
-  ##   matchExpressions:
-  ##    - {key: role, operator: In, values: [frontend]}
-  ##
-  explicitNamespacesSelector: {}
-  ##
-  ##
-  ##
-  ##
-  ##
-  ##
-  egress:
-    ## @param networkPolicy.egress.enabled When enabled, an egress network policy will be
-    ## created allowing dubbo-admin to connect to external data sources from kubernetes cluster.
-    enabled: false
-    ##
-    ## @param networkPolicy.egress.ports Add individual ports to be allowed by the egress
-    ports: []
-      ## Add ports to the egress by specifying - port: <port number>
-      ## E.X.
-      ## ports:
-      ## - port: 80
-      ## - port: 443
-
-
-## Zookeeper Necessary configuration
-zookeeper:
-  name: zookeeper
-  ##
-  ##
-  enabled: false
-  ## enabled of false
-  ##
-  ## replicas
-  replicas: 1
-  ## Create a headless service for the deployment
-  headlessService: false
-  ##
-  ##
-  image:
-    repository: bitnami/zookeeper
-    tag: 3.8.1-debian-11-r0
-    digest: ""
-    debug: false
-    pullPolicy: IfNotPresent
-  ## Create HorizontalPodAutoscaler object for deployment type
-  autoscaling:
-    enabled: false
-    minReplicas: 1
-    maxReplicas: 5
-    targetCPU: "60"
-    targetMemory: ""
-    behavior: {}
-  ##
-  ##
-  ## Number of old ReplicaSets to retain
-  ##
-  revisionHistoryLimit: 10
-  ##
-  ##
-  ## See `kubectl explain deployment.spec.strategy` for more
-  ## ref: https://kubernetes.io/docs/concepts/workloads/controllers/deployment/#strategy
-  deploymentStrategy:
-    type: RollingUpdate
-  ##
-  ##
-## zookeeper container Ports
-containerPorts:
-  client: 2181
-  follower: 2888
-  election: 3888
-##
-##
-extraVolumes: []
-## @param extraVolumeMounts Optionally specify extra list of additional volumeMounts for the ZooKeeper container(s)
-## Example Use Case: mount certificates to enable TLS
-## e.g:
-## extraVolumeMounts:
-## - name: zookeeper-keystore
-##   mountPath: /certs/keystore
-##   readOnly: true
-## - name: zookeeper-truststore
-##   mountPath: /certs/truststore
-##   readOnly: true
-##
-extraVolumeMounts: []
-## @param sidecars Add additional sidecar containers to the ZooKeeper pod(s)
-## e.g:
-## sidecars:
-##   - name: your-image-name
-##     image: your-image
-##     imagePullPolicy: Always
-##     ports:
-##       - name: portname
-##         containerPort: 1234
-##
-## @param tickTime Basic time unit (in milliseconds) used by ZooKeeper for heartbeats
-##
-##
-auth:
-  client:
-    ## @param auth.client.enabled Enable ZooKeeper client-server authentication. It uses SASL/Digest-MD5
-    ##
-    enabled: false
-    ## @param auth.client.clientUser User that will use ZooKeeper clients to auth
-    ##
-    clientUser: ""
-    ## @param auth.client.clientPassword Password that will use ZooKeeper clients to auth
-    ##
-    clientPassword: ""
-    ## @param auth.client.serverUsers Comma, semicolon or whitespace separated list of user to be created
-    ## Specify them as a string, for example: "user1,user2,admin"
-    ##
-    serverUsers: ""
-    ## @param auth.client.serverPasswords Comma, semicolon or whitespace separated list of passwords to assign to users when created
-    ## Specify them as a string, for example: "pass4user1, pass4user2, pass4admin"
-    ##
-    serverPasswords: ""
-    ## @param auth.client.existingSecret Use existing secret (ignores previous passwords)
-    ##
-    existingSecret: ""
-  quorum:
-    ## @param auth.quorum.enabled Enable ZooKeeper server-server authentication. It uses SASL/Digest-MD5
-    ##
-    enabled: false
-    ## @param auth.quorum.learnerUser User that the ZooKeeper quorumLearner will use to authenticate to quorumServers.
-    ## Note: Make sure the user is included in auth.quorum.serverUsers
-    ##
-    learnerUser: ""
-    ## @param auth.quorum.learnerPassword Password that the ZooKeeper quorumLearner will use to authenticate to quorumServers.
-    ##
-    learnerPassword: ""
-    ## @param auth.quorum.serverUsers Comma, semicolon or whitespace separated list of users for the quorumServers.
-    ## Specify them as a string, for example: "user1,user2,admin"
-    ##
-    serverUsers: ""
-    ## @param auth.quorum.serverPasswords Comma, semicolon or whitespace separated list of passwords to assign to users when created
-    ## Specify them as a string, for example: "pass4user1, pass4user2, pass4admin"
-    ##
-    serverPasswords: ""
-    ## @param auth.quorum.existingSecret Use existing secret (ignores previous passwords)
-    ##
-    existingSecret: ""
-## @param tickTime Basic time unit (in milliseconds) used by ZooKeeper for heartbeats
-##
-tickTime: 2000
-## @param initLimit ZooKeeper uses to limit the length of time the ZooKeeper servers in quorum have to connect to a leader
-##
-initLimit: 10
-## @param syncLimit How far out of date a server can be from a leader
-##
-syncLimit: 5
-## @param preAllocSize Block size for transaction log file
-##
-preAllocSize: 65536
-## @param snapCount The number of transactions recorded in the transaction log before a snapshot can be taken (and the transaction log rolled)
-##
-snapCount: 100000
-## @param maxClientCnxns Limits the number of concurrent connections that a single client may make to a single member of the ZooKeeper ensemble
-##
-maxClientCnxns: 60
-## @param maxSessionTimeout Maximum session timeout (in milliseconds) that the server will allow the client to negotiate
-## Defaults to 20 times the tickTime
-##
-maxSessionTimeout: 40000
-## @param heapSize Size (in MB) for the Java Heap options (Xmx and Xms)
-## This env var is ignored if Xmx an Xms are configured via `jvmFlags`
-##
-heapSize: 1024
-## @param fourlwCommandsWhitelist A list of comma separated Four Letter Words commands that can be executed
-##
-fourlwCommandsWhitelist: srvr, mntr, ruok
-## @param minServerId Minimal SERVER_ID value, nodes increment their IDs respectively
-## Servers increment their ID starting at this minimal value.
-## E.g., with `minServerId=10` and 3 replicas, server IDs will be 10, 11, 12 for z-0, z-1 and z-2 respectively.
-##
-minServerId: 1
-## @param listenOnAllIPs Allow ZooKeeper to listen for connections from its peers on all available IP addresses
-##
-listenOnAllIPs: false
-## Ongoing data directory cleanup configuration
-##
-autopurge:
-  ## @param autopurge.snapRetainCount The most recent snapshots amount (and corresponding transaction logs) to retain
-  ##
-  snapRetainCount: 3
-  ## @param autopurge.purgeInterval The time interval (in hours) for which the purge task has to be triggered
-  ## Set to a positive integer to enable the auto purging
-  ##
-  purgeInterval: 0
-## @param logLevel Log level for the ZooKeeper server. ERROR by default
-## Have in mind if you set it to INFO or WARN the ReadinessProve will produce a lot of logs
-##
-logLevel: ERROR
-## @param jvmFlags Default JVM flags for the ZooKeeper process
-##
-jvmFlags: ""
-## @param dataLogDir Dedicated data log directory
-## This allows a dedicated log device to be used, and helps avoid competition between logging and snapshots.
-## E.g.
-## dataLogDir: /bitnami/zookeeper/dataLog
-##
-dataLogDir: ""
-##
-##
-configuration: ""
-## @param existingConfigmap The name of an existing ConfigMap with your custom configuration for ZooKeeper
-## NOTE: When it's set the `configuration` parameter is ignored
-##
-existingConfigmap: ""
-## @param extraEnvVars Array with extra environment variables to add to ZooKeeper nodes
-## e.g:
-## extraEnvVars:
-##   - name: FOO
-##     value: "bar"
-##
-##
-## @param clusterDomain Kubernetes Cluster Domain
-##
-clusterDomain: cluster.local
-## @param extraDeploy Extra objects to deploy (evaluated as a template)
-##
-extraDeploy: []
-## @param commonLabels Add labels to all the deployed resources
-##
-Labels: {}
-## @param commonAnnotations Add annotations to all the deployed resources
-##
-Annotations: {}
-## @param namespaceOverride Override namespace for ZooKeeper resources
-## Useful when including ZooKeeper as a chart dependency, so it can be released into a different namespace than the parent
-##
-diagnosticMode:
-  ## @param diagnosticMode.enabled Enable diagnostic mode (all probes will be disabled and the command will be overridden)
-  ##
-  enabled: false
-  ## @param diagnosticMode.command Command to override all containers in the statefulset
-  ##
-  command:
-    - sleep
-  ## @param diagnosticMode.args Args to override all containers in the statefulset
-  ##
-  args:
-    - infinity
-
-
-## Nacos Necessary configuration
-nacos:
-  name: nacos
-  ## nacos name
-  ##
-  enabled: true
-  ## true of false
-  ##
-  replicas: 1
-  ## replicas
-  ##
-  mode: standalone
-  # mode: cluster
-  ##
-  ##
-  domainName: cluster.local
-  ##
-  ## image
-  image:
-    registry: docker.io
-    ##  e.g registry.k8s.io
-    repository: nacos/nacos-server
-    tag: latest
-    pullPolicy: IfNotPresent
-  ## plugin
-  plugin:
-    enable: true
-    image:
-      repository: nacos/nacos-peer-finder-plugin
-      tag: 1.1
-      pullPolicy: IfNotPresent
-  ## service
-  service:
-    type: NodePort
-    port: 8848
-    nodePort: 30000
-  ## persistence
-  persistence:
-    enabled: false
-    data:
-      accessModes:
-        - ReadWriteOnce
-      storageClassName: ""
-      resources:
-        requests:
-          storage: 5Gi
-  ## storage
-  storage:
-    type: embedded
-#    type: mysql
-#    db:
-#      host: localhost
-#      name: nacos
-#      port: 3306
-#      username: usernmae
-#      password: password
-#      param: characterEncoding=utf8&connectTimeout=1000&socketTimeout=3000&autoReconnect=true&useSSL=false
-
-
-
-
-##  @param Dubbo-admin Default Enable Configuration
-properties:
-  admin.registry.address: zookeeper://zookeeper:2181
-  admin.config-center: zookeeper://zookeeper:2181
-  admin.metadata-report.address: zookeeper://zookeeper:2181
-  admin.root.user.name: root
-  admin.root.user.password: root
-  admin.check.sessionTimeoutMilli: 3600000
-  server.compression.enabled: true
-  server.compression.mime-types: text/css,text/javascript,application/javascript
-  server.compression.min-response-size: 10240
-  admin.check.tokenTimeoutMilli: 3600000
-  admin.check.signSecret: 86295dd0c4ef69a1036b0b0c15158d77
-  dubbo.application.name: dubbo-admin
-  dubbo.registry.address: ${admin.registry.address}
-  spring.datasource.url: jdbc:h2:mem:~/dubbo-admin;MODE=MYSQL;
-  spring.datasource.username: sa
-  spring.datasource.password:
-  mybatis-plus.global-config.db-config.id-type: none
-  dubbo.application.logger: slf4j
-  
-  # nacos config, add parameters to url like username=nacos&password=nacos
-  # admin.registry.address: nacos://nacos:8848?group=DEFAULT_GROUP&namespace=public
-  # admin.config-center: nacos://nacos:8848?group=dubbo
-  # admin.metadata-report.address: nacos://nacos:8848?group=dubbo
-  
-  
-  # group (Deprecated it is recommended to use URL to add parameters,will be removed in the future)
-  # admin.registry.group: dubbo
-  # admin.config-center.group: dubbo
-  # admin.metadata-report.group: dubbo
-  
-  # namespace used by nacos.(Deprecated it is recommended to use URL to add parameters,will be removed in the future)
-  # admin.registry.namespace: public
-  # admin.config-center.namespace: public
-  # admin.metadata-report.namespace: public
-  
-  # apollo config
-  # admin.config-center: apollo://localhost:8070?token=e16e5cd903fd0c97a116c873b448544b9d086de9&app.id=test&env=dev&cluster=default&namespace=dubbo
-  # admin.apollo.token: e16e5cd903fd0c97a116c873b448544b9d086de9
-  # admin.apollo.appId: test
-  # admin.apollo.env: dev
-  # admin.apollo.cluster: default
-  
-  # mysql
-  # spring.datasource.driver-class-name: com.mysql.jdbc.Driver
-  # spring.datasource.url: jdbc:mysql://localhost:3306/dubbo-admin?characterEncoding=utf8&connectTimeout=1000&socketTimeout=10000&autoReconnect=true
-  # spring.datasource.username: root
-  # spring.datasource.password: mysql
\ No newline at end of file