Просмотр исходного кода

Merge pull request #808 from duhow/kubernetes

feat(kubernetes)!: Major Helm Chart refactor
Timothy Jaeryang Baek 1 год назад
Родитель
Сommit
8b38724bd2

+ 1 - 0
kubernetes/helm/.helmignore

@@ -0,0 +1 @@
+values-minikube.yaml

+ 17 - 1
kubernetes/helm/Chart.yaml

@@ -1,5 +1,21 @@
 apiVersion: v2
 name: open-webui
-description: "Open WebUI: A User-Friendly Web Interface for Chat Interactions 👋"
 version: 1.0.0
+appVersion: "latest"
+
+home: https://www.openwebui.com/
 icon: https://raw.githubusercontent.com/open-webui/open-webui/main/static/favicon.png
+
+description: "Open WebUI: A User-Friendly Web Interface for Chat Interactions 👋"
+keywords:
+- llm
+- chat
+- web-ui
+
+sources:
+- https://github.com/open-webui/open-webui/tree/main/kubernetes/helm
+- https://hub.docker.com/r/ollama/ollama
+- https://github.com/open-webui/open-webui/pkgs/container/open-webui
+
+annotations:
+  licenses: MIT

+ 47 - 0
kubernetes/helm/templates/_helpers.tpl

@@ -0,0 +1,47 @@
+{{- define "open-webui.name" -}}
+{{- default .Chart.Name .Values.nameOverride | trunc 63 | trimSuffix "-" }}
+{{- end -}}
+
+{{- define "ollama.name" -}}
+ollama
+{{- end -}}
+
+{{- define "ollama.url" -}}
+{{- printf "http://%s.%s.svc.cluster.local:%d/api" (include "ollama.name" .) (.Release.Namespace) (.Values.ollama.service.port | int) }}
+{{- end }}
+
+{{- define "chart.name" -}}
+{{- printf "%s-%s" .Chart.Name .Chart.Version | replace "+" "_" | trunc 63 | trimSuffix "-" }}
+{{- end }}
+
+{{- define "base.labels" -}}
+helm.sh/chart: {{ include "chart.name" . }}
+{{- if .Chart.AppVersion }}
+app.kubernetes.io/version: {{ .Chart.AppVersion | quote }}
+{{- end }}
+app.kubernetes.io/managed-by: {{ .Release.Service }}
+{{- end }}
+
+{{- define "base.selectorLabels" -}}
+app.kubernetes.io/instance: {{ .Release.Name }}
+{{- end -}}
+
+{{- define "open-webui.selectorLabels" -}}
+{{ include "base.selectorLabels" . }}
+app.kubernetes.io/component: {{ .Chart.Name }}
+{{- end }}
+
+{{- define "open-webui.labels" -}}
+{{ include "base.labels" . }}
+{{ include "open-webui.selectorLabels" . }}
+{{- end }}
+
+{{- define "ollama.selectorLabels" -}}
+{{ include "base.selectorLabels" . }}
+app.kubernetes.io/component: {{ include "ollama.name" . }}
+{{- end }}
+
+{{- define "ollama.labels" -}}
+{{ include "base.labels" . }}
+{{ include "ollama.selectorLabels" . }}
+{{- end }}

+ 0 - 4
kubernetes/helm/templates/ollama-namespace.yaml

@@ -1,4 +0,0 @@
-apiVersion: v1
-kind: Namespace
-metadata:
-  name: {{ .Values.namespace }}

+ 14 - 6
kubernetes/helm/templates/ollama-service.yaml

@@ -1,13 +1,21 @@
 apiVersion: v1
 kind: Service
 metadata:
-  name: ollama-service
-  namespace: {{ .Values.namespace }}
+  name: {{ include "ollama.name" . }}
+  labels:
+    {{- include "ollama.labels" . | nindent 4 }}
+  {{- with .Values.ollama.service.annotations }}
+  annotations:
+    {{- toYaml . | nindent 4 }}
+  {{- end }}
 spec:
-  type: {{ .Values.ollama.service.type }}
   selector:
-    app: ollama
+    {{- include "ollama.selectorLabels" . | nindent 4 }}
+{{- with .Values.ollama.service }}
+  type: {{ .type }}
   ports:
   - protocol: TCP
-    port: {{ .Values.ollama.servicePort }}
-    targetPort: {{ .Values.ollama.servicePort }}
+    name: http
+    port: {{ .port }}
+    targetPort: http
+{{- end }}

+ 62 - 21
kubernetes/helm/templates/ollama-statefulset.yaml

@@ -1,24 +1,43 @@
 apiVersion: apps/v1
 kind: StatefulSet
 metadata:
-  name: ollama
-  namespace: {{ .Values.namespace }}
+  name: {{ include "ollama.name" . }}
+  labels:
+    {{- include "ollama.labels" . | nindent 4 }}
+  {{- with .Values.ollama.annotations }}
+  annotations:
+    {{- toYaml . | nindent 4 }}
+  {{- end }}
 spec:
-  serviceName: "ollama"
+  serviceName: {{ include "ollama.name" . }}
   replicas: {{ .Values.ollama.replicaCount }}
   selector:
     matchLabels:
-      app: ollama
+      {{- include "ollama.selectorLabels" . | nindent 6 }}
   template:
     metadata:
       labels:
-        app: ollama
+        {{- include "ollama.labels" . | nindent 8 }}
+      {{- with .Values.ollama.podAnnotations }}
+      annotations:
+        {{- toYaml . | nindent 8 }}
+      {{- end }}
     spec:
+      enableServiceLinks: false
+      automountServiceAccountToken: false
+      {{- with .Values.ollama.runtimeClassName }}
+      runtimeClassName: {{ . }}
+      {{- end }}
       containers:
-      - name: ollama
-        image: {{ .Values.ollama.image }}
+      - name: {{ include "ollama.name" . }}
+        {{- with .Values.ollama.image }}
+        image: {{ .repository }}:{{ .tag }}
+        imagePullPolicy: {{ .pullPolicy }}
+        {{- end }}
+        tty: true
         ports:
-        - containerPort: {{ .Values.ollama.servicePort }}
+        - name: http
+          containerPort: {{ .Values.ollama.service.containerPort }}
         env:
         {{- if .Values.ollama.gpu.enabled }}
           - name: PATH
@@ -27,29 +46,51 @@ spec:
             value: /usr/local/nvidia/lib:/usr/local/nvidia/lib64
           - name: NVIDIA_DRIVER_CAPABILITIES
             value: compute,utility
-        {{- end}}
-        {{- if .Values.ollama.resources }}
-        resources: {{- toYaml .Values.ollama.resources | nindent 10 }}
+        {{- end }}
+        {{- with .Values.ollama.resources }}
+        resources: {{- toYaml . | nindent 10 }}
         {{- end }}
         volumeMounts:
-        - name: ollama-volume
+        - name: data
           mountPath: /root/.ollama
-        tty: true
       {{- with .Values.ollama.nodeSelector }}
       nodeSelector:
         {{- toYaml . | nindent 8 }}
       {{- end }}
+      {{- with .Values.ollama.tolerations }}
       tolerations:
-        {{- if .Values.ollama.gpu.enabled }}
-        - key: nvidia.com/gpu
-          operator: Exists
-          effect: NoSchedule
-        {{- end }}
+        {{- toYaml . | nindent 8 }}
+      {{- end }}
+      volumes:
+      {{- if and .Values.ollama.persistence.enabled .Values.ollama.persistence.existingClaim }}
+      - name: data
+        persistentVolumeClaim:
+          claimName: {{ .Values.ollama.persistence.existingClaim }}
+      {{- else if not .Values.ollama.persistence.enabled }}
+      - name: data
+        emptyDir: {}
+      {{- else if and .Values.ollama.persistence.enabled (not .Values.ollama.persistence.existingClaim) }}
+        []
   volumeClaimTemplates:
   - metadata:
-      name: ollama-volume
+      name: data
+      labels:
+        {{- include "ollama.selectorLabels" . | nindent 8 }}
+      {{- with .Values.ollama.persistence.annotations }}
+      annotations:
+        {{- toYaml . | nindent 8 }}
+      {{- end }}
     spec:
-      accessModes: [ "ReadWriteOnce" ]
+      accessModes:
+        {{- range .Values.ollama.persistence.accessModes }}
+        - {{ . | quote }}
+        {{- end }}
       resources:
         requests:
-          storage: {{ .Values.ollama.volumeSize }}
+          storage: {{ .Values.ollama.persistence.size | quote }}
+      storageClass: {{ .Values.ollama.persistence.storageClass }}
+      {{- with .Values.ollama.persistence.selector }}
+      selector:
+        {{- toYaml . | nindent 8 }}
+      {{- end }}
+      {{- end }}

+ 38 - 14
kubernetes/helm/templates/webui-deployment.yaml

@@ -1,38 +1,62 @@
 apiVersion: apps/v1
 kind: Deployment
 metadata:
-  name: open-webui-deployment
-  namespace: {{ .Values.namespace }}
+  name: {{ include "open-webui.name" . }}
+  labels:
+    {{- include "open-webui.labels" . | nindent 4 }}
+  {{- with .Values.webui.annotations }}
+  annotations:
+    {{- toYaml . | nindent 4 }}
+  {{- end }}
 spec:
-  replicas: 1
+  replicas: {{ .Values.webui.replicaCount }}
   selector:
     matchLabels:
-      app: open-webui
+      {{- include "open-webui.selectorLabels" . | nindent 6 }}
   template:
     metadata:
       labels:
-        app: open-webui
+        {{- include "open-webui.labels" . | nindent 8 }}
+      {{- with .Values.webui.podAnnotations }}
+      annotations:
+        {{- toYaml . | nindent 8 }}
+      {{- end }}
     spec:
+      enableServiceLinks: false
+      automountServiceAccountToken: false
       containers:
-      - name: open-webui
-        image: {{ .Values.webui.image }}
+      - name: {{ .Chart.Name }}
+        {{- with .Values.webui.image }}
+        image: {{ .repository }}:{{ .tag | default $.Chart.AppVersion }}
+        imagePullPolicy: {{ .pullPolicy }}
+        {{- end }}
         ports:
-        - containerPort: 8080
-        {{- if .Values.webui.resources }}
-        resources: {{- toYaml .Values.webui.resources | nindent 10 }}
+        - name: http
+          containerPort: {{ .Values.webui.service.containerPort }}
+        {{- with .Values.webui.resources }}
+        resources: {{- toYaml . | nindent 10 }}
         {{- end }}
         volumeMounts:
-        - name: webui-volume
+        - name: data
           mountPath: /app/backend/data
         env:
         - name: OLLAMA_API_BASE_URL
-          value: "http://ollama-service.{{ .Values.namespace }}.svc.cluster.local:{{ .Values.ollama.servicePort }}/api"
+          value: {{ include "ollama.url" . | quote }}
         tty: true
       {{- with .Values.webui.nodeSelector }}
       nodeSelector:
         {{- toYaml . | nindent 8 }}
       {{- end }}
       volumes:
-      - name: webui-volume
+      {{- if and .Values.webui.persistence.enabled .Values.webui.persistence.existingClaim }}
+      - name: data
         persistentVolumeClaim:
-          claimName: open-webui-pvc
+          claimName: {{ .Values.webui.persistence.existingClaim }}
+      {{- else if not .Values.webui.persistence.enabled }}
+      - name: data
+        emptyDir: {}
+      {{- else if and .Values.webui.persistence.enabled (not .Values.webui.persistence.existingClaim) }}
+      - name: data
+        persistentVolumeClaim:
+          claimName: {{ include "open-webui.name" . }}
+      {{- end }}

+ 17 - 7
kubernetes/helm/templates/webui-ingress.yaml

@@ -2,13 +2,23 @@
 apiVersion: networking.k8s.io/v1
 kind: Ingress
 metadata:
-  name: open-webui-ingress
-  namespace: {{ .Values.namespace }}
-{{- if .Values.webui.ingress.annotations }}
+  name: {{ include "open-webui.name" . }}
+  labels:
+    {{- include "open-webui.labels" . | nindent 4 }}
+  {{- with .Values.webui.ingress.annotations }}
   annotations:
-{{ toYaml .Values.webui.ingress.annotations | trimSuffix "\n" | indent 4 }}
-{{- end }}
+    {{- toYaml . | nindent 4 }}
+  {{- end }}
 spec:
+  {{- with .Values.webui.ingress.class }}
+  ingressClassName: {{ . }}
+  {{- end }}
+  {{- if .Values.webui.ingress.tls }}
+  tls:
+    - hosts:
+      - {{ .Values.webui.ingress.host | quote }}
+      secretName: {{ default (printf "%s-tls" .Release.Name) .Values.webui.ingress.existingSecret }}
+  {{- end }}
   rules:
   - host: {{ .Values.webui.ingress.host }}
     http:
@@ -17,7 +27,7 @@ spec:
         pathType: Prefix
         backend:
           service:
-            name: open-webui-service
+            name: {{ include "open-webui.name" . }}
             port:
-              number: {{ .Values.webui.servicePort }}
+              name: http
 {{- end }}

+ 18 - 5
kubernetes/helm/templates/webui-pvc.yaml

@@ -1,12 +1,25 @@
+{{- if and .Values.webui.persistence.enabled (not .Values.webui.persistence.existingClaim) }}
 apiVersion: v1
 kind: PersistentVolumeClaim
 metadata:
+  name: {{ include "open-webui.name" . }}
   labels:
-    app: open-webui
-  name: open-webui-pvc
-  namespace: {{ .Values.namespace }}  
+    {{- include "open-webui.selectorLabels" . | nindent 4 }}
+  {{- with .Values.webui.persistence.annotations }}
+  annotations:
+    {{- toYaml . | nindent 8 }}
+  {{- end }}
 spec:
-  accessModes: [ "ReadWriteOnce" ]
+  accessModes:
+    {{- range .Values.webui.persistence.accessModes }}
+    - {{ . | quote }}
+    {{- end }}
   resources:
     requests:
-      storage: {{ .Values.webui.volumeSize }}
+      storage: {{ .Values.webui.persistence.size }}
+  storageClass: {{ .Values.webui.persistence.storageClass }}
+  {{- with .Values.webui.persistence.selector }}
+  selector:
+    {{- toYaml . | nindent 4 }}
+  {{- end }}
+{{- end }}

+ 18 - 9
kubernetes/helm/templates/webui-service.yaml

@@ -1,15 +1,24 @@
 apiVersion: v1
 kind: Service
 metadata:
-  name: open-webui-service
-  namespace: {{ .Values.namespace }}
+  name: {{ include "open-webui.name" . }}
+  labels:
+    {{- include "open-webui.labels" . | nindent 4 }}
+  {{- with .Values.webui.service.annotations }}
+  annotations:
+    {{- toYaml . | nindent 4 }}
+  {{- end }}
 spec:
-  type: {{ .Values.webui.service.type }} # Default: NodePort  # Use LoadBalancer if you're on a cloud that supports it
   selector:
-    app: open-webui
+    {{- include "open-webui.selectorLabels" . | nindent 4 }}
+{{- with .Values.webui.service }}
+  type: {{ .type }}
   ports:
-    - protocol: TCP
-      port: {{ .Values.webui.servicePort }}
-      targetPort: {{ .Values.webui.servicePort }}
-      # If using NodePort, you can optionally specify the nodePort:
-      # nodePort: 30000
+  - protocol: TCP
+    name: http
+    port: {{ .port }}
+    targetPort: http
+    {{- if .nodePort }}
+    nodePort: {{ .nodePort | int }}
+    {{- end }}
+{{- end }}

+ 27 - 0
kubernetes/helm/values-minikube.yaml

@@ -0,0 +1,27 @@
+ollama:
+  resources:
+    requests:
+      cpu: "2000m"
+      memory: "2Gi"
+    limits:
+      cpu: "4000m"
+      memory: "4Gi"
+      nvidia.com/gpu: "0"
+  service:
+    type: ClusterIP
+  gpu:
+    enabled: false
+
+webui:
+  resources:
+    requests:
+      cpu: "500m"
+      memory: "500Mi"
+    limits:
+      cpu: "1000m"
+      memory: "1Gi"
+  ingress:
+    enabled: true
+    host: open-webui.minikube.local
+  service:
+    type: NodePort

+ 56 - 28
kubernetes/helm/values.yaml

@@ -1,44 +1,72 @@
-namespace: open-webui
+nameOverride: ""
 
 ollama:
+  annotations: {}
+  podAnnotations: {}
   replicaCount: 1
-  image: ollama/ollama:latest
-  servicePort: 11434
-  resources:
-    requests:
-      cpu: "2000m"
-      memory: "2Gi"
-    limits:
-      cpu: "4000m"
-      memory: "4Gi"
-      nvidia.com/gpu: "0"
-  volumeSize: 30Gi
+  image:
+    repository: ollama/ollama
+    tag: latest
+    pullPolicy: Always
+  resources: {}
+  persistence:
+    enabled: true
+    size: 30Gi
+    existingClaim: ""
+    accessModes:
+    - ReadWriteOnce
+    storageClass: ""
+    selector: {}
+    annotations: {}
   nodeSelector: {}
-  tolerations: []
+  # -- If using a special runtime container such as nvidia, set it here.
+  runtimeClassName: ""
+  tolerations:
+  - key: nvidia.com/gpu
+    operator: Exists
+    effect: NoSchedule
   service:
     type: ClusterIP
+    annotations: {}
+    port: 80
+    containerPort: 11434
   gpu:
+    # -- Enable additional ENV values to help Ollama discover GPU usage
     enabled: false
 
 webui:
+  annotations: {}
+  podAnnotations: {}
   replicaCount: 1
-  image: ghcr.io/open-webui/open-webui:main
-  servicePort: 8080
-  resources:
-    requests:
-      cpu: "500m"
-      memory: "500Mi"
-    limits:
-      cpu: "1000m"
-      memory: "1Gi"
+  image:
+    repository: ghcr.io/open-webui/open-webui
+    tag: ""
+    pullPolicy: Always
+  resources: {}
   ingress:
+    enabled: false
+    class: ""
+    # -- Use appropriate annotations for your Ingress controller, e.g., for NGINX:
+    # nginx.ingress.kubernetes.io/rewrite-target: /
+    annotations: {}
+    host: ""
+    tls: false
+    existingSecret: ""
+  persistence:
     enabled: true
-    annotations:
-    # Use appropriate annotations for your Ingress controller, e.g., for NGINX:
-      # nginx.ingress.kubernetes.io/rewrite-target: /
-    host: open-webui.minikube.local
-  volumeSize: 2Gi
+    size: 2Gi
+    existingClaim: ""
+    # -- If using multiple replicas, you must update accessModes to ReadWriteMany
+    accessModes:
+    - ReadWriteOnce
+    storageClass: ""
+    selector: {}
+    annotations: {}
   nodeSelector: {}
   tolerations: []
   service:
-    type: NodePort
+    type: ClusterIP
+    annotations: {}
+    port: 80
+    containerPort: 8080
+    nodePort: ""