From b1f5dedfda418ccf09c107b07e67bec5c8858b5b Mon Sep 17 00:00:00 2001 From: KnightArtorias Date: Fri, 24 Jul 2026 18:33:23 -0400 Subject: [PATCH] Set up windmill and proton bridge --- .../technical/backups-and-recovery.md | 19 ------ .../monitoring-external-secrets.yaml | 0 .../{stack => }/monitoring-services.yaml | 0 monitoring/{stack => }/monitoring-stack.yaml | 0 .../proton-bridge-deployment.yaml | 49 ++++++++++++++ .../proton-bridge/proton-bridge-monitor.yaml | 32 +++++++++ .../proton-bridge/proton-bridge-pvcs.yaml | 14 ++++ .../proton-bridge/proton-bridge-service.yaml | 14 ++++ .../vaultwarden/vaultwarden-deployment.yaml | 3 + .../vaultwarden-external-secrets.yaml | 18 +++++ services/windmill/windmill-deployment.yaml | 66 +++++++++++++++++++ .../windmill/windmill-external-secrets.yaml | 29 ++++++++ services/windmill/windmill-ingress.yaml | 18 +++++ services/windmill/windmill-pvcs.yaml | 14 ++++ services/windmill/windmill-service.yaml | 21 ++++++ 15 files changed, 278 insertions(+), 19 deletions(-) rename monitoring/{stack => }/monitoring-external-secrets.yaml (100%) rename monitoring/{stack => }/monitoring-services.yaml (100%) rename monitoring/{stack => }/monitoring-stack.yaml (100%) create mode 100644 services/proton-bridge/proton-bridge-deployment.yaml create mode 100644 services/proton-bridge/proton-bridge-monitor.yaml create mode 100644 services/proton-bridge/proton-bridge-pvcs.yaml create mode 100644 services/proton-bridge/proton-bridge-service.yaml create mode 100644 services/vaultwarden/vaultwarden-external-secrets.yaml create mode 100644 services/windmill/windmill-deployment.yaml create mode 100644 services/windmill/windmill-external-secrets.yaml create mode 100644 services/windmill/windmill-ingress.yaml create mode 100644 services/windmill/windmill-pvcs.yaml create mode 100644 services/windmill/windmill-service.yaml diff --git a/documentation/technical/backups-and-recovery.md b/documentation/technical/backups-and-recovery.md index 0beda4b..730b9a1 100644 --- a/documentation/technical/backups-and-recovery.md +++ b/documentation/technical/backups-and-recovery.md @@ -3,26 +3,7 @@ The Nest uses a two-tier backup strategy: **Longhorn volume snapshots** for application configuration data (backed up to Backblaze B2 weekly), and **Restic** for Nextcloud user data (backed up daily). Media storage is not backed up. ## Backup Architecture - -┌─────────────┐ ┌──────────────────┐ ┌─────────────────┐ - -│ Longhorn │────▶│ Recurring Jobs │────▶│ Backblaze B2 │ - -│ Volumes │ │ (weekly) │ │ (offsite) │ - - -└─────────────┘ └──────────────────┘ └─────────────────┘ - - -┌─────────────┐ ┌──────────────────┐ ┌─────────────────┐ - - -│ Nextcloud │────▶│ Restic CronJob │────▶│ Backblaze B2 │ - -│ User Data │ │ (daily) │ │ (offsite) │ - -└─────────────┘ └──────────────────┘ └─────────────────┘ ## Longhorn Recurring Backups diff --git a/monitoring/stack/monitoring-external-secrets.yaml b/monitoring/monitoring-external-secrets.yaml similarity index 100% rename from monitoring/stack/monitoring-external-secrets.yaml rename to monitoring/monitoring-external-secrets.yaml diff --git a/monitoring/stack/monitoring-services.yaml b/monitoring/monitoring-services.yaml similarity index 100% rename from monitoring/stack/monitoring-services.yaml rename to monitoring/monitoring-services.yaml diff --git a/monitoring/stack/monitoring-stack.yaml b/monitoring/monitoring-stack.yaml similarity index 100% rename from monitoring/stack/monitoring-stack.yaml rename to monitoring/monitoring-stack.yaml diff --git a/services/proton-bridge/proton-bridge-deployment.yaml b/services/proton-bridge/proton-bridge-deployment.yaml new file mode 100644 index 0000000..3b2056d --- /dev/null +++ b/services/proton-bridge/proton-bridge-deployment.yaml @@ -0,0 +1,49 @@ +apiVersion: apps/v1 +kind: Deployment +metadata: + name: proton-bridge + annotations: + keel.sh/policy: "all" + keel.sh/match-tag: "true" + keel.sh/schedule: "0 3 * * *" +spec: + replicas: 1 + selector: + matchLabels: + app: proton-bridge + template: + metadata: + labels: + app: proton-bridge + spec: + nodeSelector: + kubernetes.io/arch: amd64 + # The initContainer runs first, scrubs the broken update, and locks the folder + initContainers: + - name: disable-auto-update + image: busybox:latest + command: + - "/bin/sh" + - "-c" + - | + mkdir -p /root/.local/share/protonmail/bridge-v3/updates + rm -rf /root/.local/share/protonmail/bridge-v3/updates/* + chmod 555 /root/.local/share/protonmail/bridge-v3/updates + volumeMounts: + - name: bridge-data + mountPath: /root + containers: + - name: bridge + image: shenxn/protonmail-bridge:latest + ports: + - containerPort: 25 + name: smtp + - containerPort: 143 + name: imap + volumeMounts: + - name: bridge-data + mountPath: /root + volumes: + - name: bridge-data + persistentVolumeClaim: + claimName: proton-bridge-data diff --git a/services/proton-bridge/proton-bridge-monitor.yaml b/services/proton-bridge/proton-bridge-monitor.yaml new file mode 100644 index 0000000..acea099 --- /dev/null +++ b/services/proton-bridge/proton-bridge-monitor.yaml @@ -0,0 +1,32 @@ +apiVersion: helm.cattle.io/v1 +kind: HelmChart +metadata: + name: prometheus-blackbox-exporter + namespace: kube-system +spec: + chart: prometheus-blackbox-exporter + repo: https://prometheus-community.github.io/helm-charts + targetNamespace: monitoring + createNamespace: true + valuesContent: |- + config: + modules: + proton_smtp_auth: + prober: tcp + timeout: 10s + tcp: + query_response: + - expect: "^220" + - send: "EHLO blackbox\r\n" + - expect: "^250" + # --- Remove these 3 lines if Bridge Connection Mode is "None" --- + - send: "STARTTLS\r\n" + - expect: "^220" + - starttls: true + # ---------------------------------------------------------------- + - send: "EHLO blackbox\r\n" + - expect: "^250" + # Insert your generated Base64 string below + - send: "AUTH PLAIN \AG5lc3RAbXluZXN0LmxvdmUAZ0pibVNBamdVaF83ejdUNEg4NGhxdw==r\n" + - expect: "^235" # 235 = Auth successful. Any 5xx error fails the probe. + - send: "QUIT\r\n" diff --git a/services/proton-bridge/proton-bridge-pvcs.yaml b/services/proton-bridge/proton-bridge-pvcs.yaml new file mode 100644 index 0000000..8bb0bf1 --- /dev/null +++ b/services/proton-bridge/proton-bridge-pvcs.yaml @@ -0,0 +1,14 @@ +apiVersion: v1 +kind: PersistentVolumeClaim +metadata: + name: proton-bridge-data + labels: + recurring-job.longhorn.io/source: "enabled" + recurring-job-group.longhorn.io/app-config-group: "enabled" +spec: + storageClassName: longhorn + accessModes: + - ReadWriteOnce + resources: + requests: + storage: 5Gi diff --git a/services/proton-bridge/proton-bridge-service.yaml b/services/proton-bridge/proton-bridge-service.yaml new file mode 100644 index 0000000..6a0b130 --- /dev/null +++ b/services/proton-bridge/proton-bridge-service.yaml @@ -0,0 +1,14 @@ +apiVersion: v1 +kind: Service +metadata: + name: proton-bridge +spec: + ports: + - port: 25 + targetPort: 25 + name: smtp + - port: 143 + targetPort: 143 + name: imap + selector: + app: proton-bridge diff --git a/services/vaultwarden/vaultwarden-deployment.yaml b/services/vaultwarden/vaultwarden-deployment.yaml index 2662cb8..8ce0113 100644 --- a/services/vaultwarden/vaultwarden-deployment.yaml +++ b/services/vaultwarden/vaultwarden-deployment.yaml @@ -23,6 +23,9 @@ spec: value: "false" - name: WEBSOCKET_ENABLED value: "true" + envFrom: + - secretRef: + name: vaultwarden-secret image: vaultwarden/server:latest name: vaultwarden ports: diff --git a/services/vaultwarden/vaultwarden-external-secrets.yaml b/services/vaultwarden/vaultwarden-external-secrets.yaml new file mode 100644 index 0000000..6da7cb6 --- /dev/null +++ b/services/vaultwarden/vaultwarden-external-secrets.yaml @@ -0,0 +1,18 @@ +apiVersion: external-secrets.io/v1 +kind: ExternalSecret +metadata: + name: vaultwarden-secret + namespace: default +spec: + refreshInterval: "1h" + secretStoreRef: + name: vault-external-secrets-store + kind: ClusterSecretStore + target: + name: vaultwarden-secret + creationPolicy: Owner + data: + - secretKey: ADMIN_TOKEN + remoteRef: + key: vaultwarden + property: admin-token diff --git a/services/windmill/windmill-deployment.yaml b/services/windmill/windmill-deployment.yaml new file mode 100644 index 0000000..20a378c --- /dev/null +++ b/services/windmill/windmill-deployment.yaml @@ -0,0 +1,66 @@ +apiVersion: apps/v1 +kind: Deployment +metadata: + name: windmill-server + annotations: + keel.sh/policy: "all" + keel.sh/match-tag: "true" + keel.sh/schedule: "0 3 * * *" +spec: + replicas: 1 + selector: + matchLabels: + app: windmill-server + template: + metadata: + labels: + app: windmill-server + spec: + nodeSelector: + kubernetes.io/arch: amd64 + containers: + - name: server + image: ghcr.io/windmill-labs/windmill:latest + env: + - name: MODE + value: "standalone" + - name: BASE_URL + value: "http://windmill.k3s.home.nest" + - name: DATABASE_URL + valueFrom: + secretKeyRef: + name: windmill-secret + key: DATABASE_URL + ports: + - containerPort: 8000 +--- +apiVersion: apps/v1 +kind: Deployment +metadata: + name: windmill-postgres +spec: + replicas: 1 + selector: + matchLabels: + app: windmill-postgres + template: + metadata: + labels: + app: windmill-postgres + spec: + containers: + - name: postgres + image: postgres:16-alpine + ports: + - containerPort: 5432 + envFrom: + - secretRef: + name: windmill-secret + volumeMounts: + - name: postgres-storage + mountPath: /var/lib/postgresql/data + subPath: windmill-data + volumes: + - name: postgres-storage + persistentVolumeClaim: + claimName: windmill-postgres-pvc diff --git a/services/windmill/windmill-external-secrets.yaml b/services/windmill/windmill-external-secrets.yaml new file mode 100644 index 0000000..3fcae14 --- /dev/null +++ b/services/windmill/windmill-external-secrets.yaml @@ -0,0 +1,29 @@ +apiVersion: external-secrets.io/v1 +kind: ExternalSecret +metadata: + name: windmill-secret +spec: + refreshInterval: "1h" + secretStoreRef: + name: vault-external-secrets-store + kind: ClusterSecretStore + target: + name: windmill-secret + creationPolicy: Owner + data: + - secretKey: POSTGRES_DB + remoteRef: + key: windmill + property: postgres-db + - secretKey: POSTGRES_USER + remoteRef: + key: windmill + property: postgres-user + - secretKey: POSTGRES_PASSWORD + remoteRef: + key: windmill + property: postgres-password + - secretKey: DATABASE_URL + remoteRef: + key: windmill + property: database-url diff --git a/services/windmill/windmill-ingress.yaml b/services/windmill/windmill-ingress.yaml new file mode 100644 index 0000000..c7866fe --- /dev/null +++ b/services/windmill/windmill-ingress.yaml @@ -0,0 +1,18 @@ +apiVersion: networking.k8s.io/v1 +kind: Ingress +metadata: + name: windmill-ingress + annotations: + traefik.ingress.kubernetes.io/router.entrypoints: web +spec: + rules: + - host: windmill.k3s.home.nest + http: + paths: + - path: / + pathType: Prefix + backend: + service: + name: windmill-server + port: + number: 8000 diff --git a/services/windmill/windmill-pvcs.yaml b/services/windmill/windmill-pvcs.yaml new file mode 100644 index 0000000..cb4c82d --- /dev/null +++ b/services/windmill/windmill-pvcs.yaml @@ -0,0 +1,14 @@ +apiVersion: v1 +kind: PersistentVolumeClaim +metadata: + name: windmill-postgres-pvc + labels: + recurring-job.longhorn.io/source: "enabled" + recurring-job-group.longhorn.io/app-config-group: "enabled" +spec: + storageClassName: longhorn + accessModes: + - ReadWriteOnce + resources: + requests: + storage: 5Gi diff --git a/services/windmill/windmill-service.yaml b/services/windmill/windmill-service.yaml new file mode 100644 index 0000000..eae335b --- /dev/null +++ b/services/windmill/windmill-service.yaml @@ -0,0 +1,21 @@ +apiVersion: v1 +kind: Service +metadata: + name: windmill-server +spec: + ports: + - port: 8000 + targetPort: 8000 + selector: + app: windmill-server +--- +apiVersion: v1 +kind: Service +metadata: + name: windmill-postgres +spec: + ports: + - port: 5432 + targetPort: 5432 + selector: + app: windmill-postgres