commit bbe86c55d90098c9c0d54e28953f4b68092e8b2a Author: Sascha Dodenhöft Date: Sun May 3 13:46:47 2026 +0200 Initial commit: Infrastructure documentation Co-Authored-By: Claude Sonnet 4.6 diff --git a/README.md b/README.md new file mode 100644 index 0000000..e28c9eb --- /dev/null +++ b/README.md @@ -0,0 +1,43 @@ +# ExpertFab – Infrastruktur Dokumentation + +Zentrale Dokumentation der ExpertFab IT-Infrastruktur. + +## Inhalt + +| Dokument | Beschreibung | +|---|---| +| [docs/infrastructure.md](docs/infrastructure.md) | VM-Inventar, Proxmox-Hosts, Netzwerk | +| [docs/access.md](docs/access.md) | SSH-Zugänge, API-Token, Credentials | +| [docs/k3s.md](docs/k3s.md) | K3s-Cluster, Namespaces, Ingresses, ERPNext | +| [docs/storage.md](docs/storage.md) | Longhorn Storage, PVCs, StorageClasses | + +## Schaubilder + +| Datei | Beschreibung | +|---|---| +| [diagrams/k8s_cluster.png](diagrams/k8s_cluster.png) | Gesamte Infrastruktur (Proxmox + K3s) | +| [diagrams/storage_architecture.png](diagrams/storage_architecture.png) | Longhorn Storage Architektur | + +Schaubilder neu generieren: +```bash +cd diagrams +python3 k8s_cluster_diagram.py +python3 storage_diagram.py +``` + +## Schnellzugriff + +```bash +# Proxmox +ssh -i ~/.ssh/hetzner_key root@10.42.70.1 + +# K3s Control Plane +ssh -i ~/.ssh/hetzner_key sd@10.42.71.50 + +# kubectl (am Control Plane) +sudo KUBECONFIG=/etc/rancher/k3s/k3s.yaml kubectl get pods -A + +# kubectl via Proxmox (ohne sudo-Passwort) +ssh -i ~/.ssh/hetzner_key root@10.42.70.1 \ + "qm guest exec 119 -- bash -c 'KUBECONFIG=/etc/rancher/k3s/k3s.yaml kubectl get pods -A'" +``` diff --git a/diagrams/k8s_cluster.png b/diagrams/k8s_cluster.png new file mode 100644 index 0000000..4e4d73b Binary files /dev/null and b/diagrams/k8s_cluster.png differ diff --git a/diagrams/k8s_cluster_diagram.py b/diagrams/k8s_cluster_diagram.py new file mode 100644 index 0000000..76e3da5 --- /dev/null +++ b/diagrams/k8s_cluster_diagram.py @@ -0,0 +1,97 @@ +from diagrams import Cluster, Diagram, Edge +from diagrams.k8s.network import Ingress +from diagrams.k8s.compute import Deployment, StatefulSet +from diagrams.k8s.storage import PVC, StorageClass +from diagrams.onprem.network import Opnsense +from diagrams.onprem.certificates import CertManager +from diagrams.onprem.proxmox import ProxmoxVE +from diagrams.onprem.vcs import Gitea +from diagrams.generic.os import Windows + +graph_attr = { + "fontsize": "13", + "pad": "0.6", + "nodesep": "0.5", + "ranksep": "1.0", + "splines": "ortho", +} + +with Diagram( + "ExpertFab Infrastruktur", + filename="k8s_cluster", + outformat="png", + show=False, + direction="TB", + graph_attr=graph_attr, +): + # ── Physische Ebene ─────────────────────────────────────────────────────── + with Cluster("Proxmox Cluster efproxcl02 – 95.156.232.42"): + + with Cluster("efproxcl02n01 – 64 vCPU / 128 GB"): + fw = Opnsense("efscfw01\nOPNsense / FW\n10.42.70.1") + n01_kctl = ProxmoxVE("efsckubctl\nK3s control plane") + n01_kn02 = ProxmoxVE("efsckubnode02\nK3s worker") + n01_smtp = ProxmoxVE("efsmtprelay") + n01_trade = ProxmoxVE("eftrade01") + n01_git = Gitea("efgit01 / Gitea\ngit.expertfab.de") + + with Cluster("efproxcl02n02 – 64 vCPU / 128 GB"): + n02_kn1 = ProxmoxVE("efsckubnode1\nK3s worker") + n02_af = ProxmoxVE("efscairflow01\nAirflow") + n02_veeam = ProxmoxVE("efscveeam01\nVeeam Backup") + n02_dc = Windows("efscdc01\nDomain Controller") + n02_print = ProxmoxVE("efscprint01\nPrintserver") + n02_moni = ProxmoxVE("efscmoni01\nMonitoring") + + # ── Logische K3s-Ebene ──────────────────────────────────────────────────── + # K3s läuft auf: efsckubctl (control) + efsckubnode1 + efsckubnode02 + with Cluster("K3s Cluster (efsckubctl · efsckubnode1 · efsckubnode02)"): + + cert = CertManager("cert-manager\nLet's Encrypt") + traefik = Ingress("Traefik Ingress\n10.42.71.60") + cert >> traefik + + with Cluster("erpnext – expertfab.de / www.expertfab.de"): + nginx = Deployment("Nginx") + gunicorn = Deployment("Gunicorn") + workers = Deployment("Workers\ndefault / short / long") + mariadb = StatefulSet("MariaDB 10.6") + df_cache = Deployment("DragonflyDB\ncache") + df_queue = Deployment("DragonflyDB\nqueue") + nginx >> gunicorn >> workers + [gunicorn, workers] >> mariadb + [gunicorn, workers] >> df_cache + workers >> df_queue + + with Cluster("paperless – docs.expertfab.de"): + paperless = Deployment("Paperless-NGX") + + with Cluster("zitadel – auth.expertfab.de"): + zitadel = Deployment("Zitadel") + + with Cluster("rabbitmq – api.expertfab.de"): + fastapi = Deployment("FastAPI") + + with Cluster("coworkbase – coworkbase.de"): + cowork = Deployment("Coworkbase") + + with Cluster("qubicticker – qubicticker.qchief.io"): + ticker = Deployment("Qubicticker") + + traefik >> [nginx, paperless, zitadel, fastapi, cowork, ticker] + + with Cluster("Longhorn Storage"): + sc = StorageClass("longhorn") + pvc_mariadb = PVC("MariaDB 10 Gi RWO") + pvc_sites = PVC("Sites 10 Gi RWX") + pvc_logs = PVC("Logs 5 Gi RWX") + pvc_queue = PVC("Queue 2 Gi RWO") + sc >> [pvc_mariadb, pvc_sites, pvc_logs, pvc_queue] + mariadb >> Edge(style="dashed") >> pvc_mariadb + gunicorn >> Edge(style="dashed") >> pvc_sites + nginx >> Edge(style="dashed") >> pvc_logs + df_queue >> Edge(style="dashed") >> pvc_queue + + # ── Verbindungen ────────────────────────────────────────────────────────── + fw >> traefik + n01_git >> Edge(label="image pull", style="dashed") >> nginx diff --git a/diagrams/storage_architecture.png b/diagrams/storage_architecture.png new file mode 100644 index 0000000..b1eacf4 Binary files /dev/null and b/diagrams/storage_architecture.png differ diff --git a/diagrams/storage_diagram.py b/diagrams/storage_diagram.py new file mode 100644 index 0000000..3779b29 --- /dev/null +++ b/diagrams/storage_diagram.py @@ -0,0 +1,82 @@ +from diagrams import Cluster, Diagram, Edge +from diagrams.k8s.compute import Deployment, StatefulSet, Pod, DaemonSet, Job +from diagrams.k8s.storage import PVC, StorageClass +from diagrams.generic.storage import Storage + +graph_attr = { + "fontsize": "13", + "pad": "0.8", + "nodesep": "0.6", + "ranksep": "1.2", +} + +with Diagram( + "ExpertFab – Longhorn Storage Architektur", + filename="storage_architecture", + outformat="png", + show=False, + direction="TB", + graph_attr=graph_attr, +): + + # ── Longhorn System Pods pro Node ───────────────────────────────────────── + with Cluster("K3s Worker Nodes (Longhorn System Pods)"): + + with Cluster("efsckubnode1 (4 vCPU / 8 GB)"): + n1_mgr = Pod("longhorn-manager") + n1_csi = Pod("longhorn-csi-plugin") + n1_eng = Pod("engine-image") + n1_inst = Pod("instance-manager") + n1_driver = Deployment("driver-deployer") + n1_ui = Deployment("longhorn-ui (2×)") + n1_attacher = Deployment("csi-attacher (3×)") + n1_prov = Deployment("csi-provisioner (3×)") + n1_resizer = Deployment("csi-resizer (3×)") + n1_snap = Deployment("csi-snapshotter (3×)") + + with Cluster("efsckubnode2 (4 vCPU / 8 GB)"): + n2_mgr = Pod("longhorn-manager") + n2_csi = Pod("longhorn-csi-plugin") + n2_eng = Pod("engine-image") + n2_inst = Pod("instance-manager") + n2_smgr1 = Pod("share-manager\n(erpnext RWX)") + n2_smgr2 = Pod("share-manager\n(erpnext-logs RWX)") + n2_backup = Job("daily-backup\n(CronJob)") + + # ── StorageClasses ──────────────────────────────────────────────────────── + with Cluster("StorageClasses (driver.longhorn.io)"): + sc_erpnext = StorageClass("longhorn-erpnext\nRetain / Immediate") + sc_paperless = StorageClass("longhorn-paperless\nRetain / Immediate") + sc_default = StorageClass("longhorn\nDelete / Immediate") + + # ── PVCs pro Namespace ──────────────────────────────────────────────────── + with Cluster("PVCs"): + + with Cluster("namespace: erpnext"): + pvc_mariadb = PVC("data-erpnext-mariadb-sts-0\n3 Gi RWO") + pvc_sites = PVC("erpnext\n3 Gi RWX") + pvc_logs = PVC("erpnext-logs\n1 Gi RWX") + + with Cluster("namespace: paperless"): + pvc_pl_media = PVC("paperless-media\n10 Gi RWO") + pvc_pl_consume = PVC("paperless-consume\n5 Gi RWO") + pvc_pl_data = PVC("paperless-data\n5 Gi RWO") + pvc_pl_pg = PVC("postgres-data\n5 Gi RWO") + + with Cluster("namespace: rabbitmq"): + pvc_rmq = PVC("rabbitmq-data-rabbitmq-0\n5 Gi RWO") + + with Cluster("namespace: zitadel"): + pvc_zit_pg = PVC("postgres-data-postgres-0\n10 Gi RWO") + + # ── StorageClass → PVC ──────────────────────────────────────────────────── + sc_erpnext >> [pvc_mariadb, pvc_sites, pvc_logs] + sc_paperless >> [pvc_pl_media, pvc_pl_consume, pvc_pl_data, pvc_pl_pg] + sc_default >> [pvc_rmq, pvc_zit_pg] + + # ── Share-Manager bedient die RWX-Volumes ───────────────────────────────── + n2_smgr1 >> Edge(label="serves", style="dashed") >> pvc_sites + n2_smgr2 >> Edge(label="serves", style="dashed") >> pvc_logs + + # ── Longhorn Manager koordiniert über beide Nodes ───────────────────────── + n1_mgr >> Edge(style="dotted", color="gray") >> n2_mgr diff --git a/docs/access.md b/docs/access.md new file mode 100644 index 0000000..82e4d40 --- /dev/null +++ b/docs/access.md @@ -0,0 +1,98 @@ +# ExpertFab – Zugangsdaten & Verbindungen + +> **SSH-Key:** `~/.ssh/hetzner_key` (für alle Server) + +--- + +## Proxmox + +| Zugang | Wert | +|----------------|-------------------------------------------| +| Web-UI | https://95.156.232.42:8006 | +| SSH (Node 1) | `ssh -i ~/.ssh/hetzner_key root@10.42.70.1` | +| SSH (Node 2) | `ssh -i ~/.ssh/hetzner_key root@10.42.70.2` | +| Benutzer | `root` | + +--- + +## K3s Cluster + +| Zugang | Wert | +|---------------------|--------------------------------------------------------| +| SSH Control Plane | `ssh -i ~/.ssh/hetzner_key sd@10.42.71.50` | +| kubectl (am Node) | `sudo KUBECONFIG=/etc/rancher/k3s/k3s.yaml kubectl …` | +| kubectl via Proxmox | `ssh root@10.42.70.1 "qm guest exec 119 -- bash -c 'KUBECONFIG=/etc/rancher/k3s/k3s.yaml kubectl …'"` | + +**K3s Version:** v1.34.6+k3s1 +**Container Runtime:** containerd 2.2.2 +**OS:** Ubuntu 24.04.4 LTS + +### Nodes + +| Node | IP | Rolle | +|---------------|--------------|----------------| +| efsckubadm | 10.42.71.50 | control-plane | +| efsckubnode1 | 10.42.71.51 | worker | +| efsckubnode2 | 10.42.71.52 | worker | + +> Proxmox-VM `efsckubctl` = K3s-Node `efsckubadm` + +--- + +## Paperless-NGX + +| Zugang | Wert | +|-------------|----------------------------------------------| +| URL | https://docs.expertfab.de | +| API Token | `3960b56c7c56d21af06af7d32e49613d8e7f78c8` | +| API Header | `Authorization: Token ` | + +--- + +## ERPNext + +| Zugang | Wert | +|--------------|-------------------------------------------------------------------| +| URL | https://expertfab.de / https://www.expertfab.de | +| Helm Chart | frappe/erpnext 8.0.14 (ERPNext v15) | +| Namespace | `erpnext` | +| Auth Token | Airflow Variable: `ErpnextAuthToken` | +| Base URL | Airflow Variable: `ErpnextBaseurl` | +| Docker Image | git.expertfab.de/expertfab/customdocker:1.0.2 | +| Image Pull | Secret `gitea-registry` im Namespace `erpnext` | + +--- + +## Gitea + +| Zugang | Wert | +|--------|-----------------------------| +| URL | https://git.expertfab.de | +| VM | efgit01 (Proxmox n01 / 110) | + +--- + +## SMTP (Accounting) + +| Parameter | Airflow Variable | +|-----------|---------------------------| +| Server | `smtpAccountingServer` | +| Port | `smtpAccountingPort` | +| User | `smtpAccountingUser` | +| Password | `smtpAccountingPassword` | +| Sender | `smtpAccountingSenderName`| + +--- + +## Öffentlich erreichbare Dienste + +| Dienst | URL | Namespace | +|--------------|------------------------------|--------------| +| ERPNext | https://expertfab.de | erpnext | +| ERPNext | https://www.expertfab.de | erpnext | +| Paperless | https://docs.expertfab.de | paperless | +| Zitadel SSO | https://auth.expertfab.de | zitadel | +| FastAPI | https://api.expertfab.de | rabbitmq | +| Coworkbase | https://coworkbase.de | coworkbase | +| Qubicticker | https://qubicticker.qchief.io| qubicticker | +| Gitea | https://git.expertfab.de | – | diff --git a/docs/infrastructure.md b/docs/infrastructure.md new file mode 100644 index 0000000..31ce2ef --- /dev/null +++ b/docs/infrastructure.md @@ -0,0 +1,66 @@ +# ExpertFab – VM-Inventar + +## Proxmox Cluster + +| Hostname | URL / IP | Rolle | +|--------------------|-----------------------------------|-----------------------------| +| efproxcl02 | https://95.156.232.42:8006 | Proxmox Web-UI (Cluster) | +| efproxcl02n01 | 10.42.70.1 | Proxmox Host Node 1 | +| efproxcl02n02 | 10.42.70.2 | Proxmox Host Node 2 | + +**Specs je Node:** 64 vCPU / 128 GB RAM +**DNS:** efproxcl02n01.sc.expertfab.de / efproxcl02n02.sc.expertfab.de + +--- + +## VMs – efproxcl02n01 + +| VM-ID | Name | Status | CPU | RAM | IP | Rolle | +|-------|-----------------|---------|--------|-------|-----------------|------------------------------| +| 100 | efscfw01 | stopped | – | 16 GB | – | OPNsense Backup (inaktiv) | +| 101 | efsmtprelay | running | 4 vCPU | 16 GB | 109.230.227.36 | SMTP Relay | +| 102 | efscweb01 | stopped | – | 16 GB | – | Webserver (inaktiv) | +| 105 | efcacert | running | – | 4 GB | – | CA / Zertifikatsserver | +| 110 | efgit01 | running | – | 8 GB | – | Gitea (git.expertfab.de) | +| 111 | eftrade01 | running | 16vCPU | 16 GB | 10.42.71.102 | Trading-VM | +| 112 | efbtcpay | stopped | – | 8 GB | – | BTCPay Server (inaktiv) | +| 114 | efubutemp | stopped | – | 4 GB | – | Ubuntu Template | +| 115 | efxmr01 | stopped | – | 16 GB | – | Monero Node (inaktiv) | +| 116 | efscbank | stopped | – | 4 GB | – | Bank-VM (inaktiv) | +| 117 | efmatrix01 | running | – | 4 GB | – | Matrix Chat Server | +| 118 | efubu24lts* | – | – | 4 GB | – | Template (Ubuntu 24.04 LTS) | +| 119 | efsckubctl | running | 4 vCPU | 8 GB | 10.42.71.50 | K3s Control Plane | +| 121 | efsckubnode02 | running | 4 vCPU | 8 GB | 10.42.71.52 | K3s Worker Node 2 | +| 150 | efscfw01 | running | 8 vCPU | 16 GB | 109.230.227.38 | OPNsense Firewall (aktiv) | + +*Template + +## VMs – efproxcl02n02 + +| VM-ID | Name | Status | CPU | RAM | IP | Rolle | +|-------|-----------------|---------|---------|-------|-----------------|------------------------------| +| 103 | efscdc01 | running | 8 vCPU | 32 GB | 10.42.71.15 | Domain Controller (Windows) | +| 104 | efscveeam01 | running | 16 vCPU | 16 GB | 10.42.71.16 | Veeam Backup Server | +| 106 | efscprint01 | running | – | 8 GB | – | Printserver | +| 107 | eferp01 | stopped | – | 4 GB | – | Alt-ERP (inaktiv) | +| 108 | efscairflow01 | running | – | 8 GB | – | Apache Airflow | +| 109 | efscmoni01 | running | – | 4 GB | – | Monitoring | +| 113 | efbookstack01 | running | – | 8 GB | – | BookStack Wiki | +| 120 | efsckubnode1 | running | 4 vCPU | 8 GB | 10.42.71.51 | K3s Worker Node 1 | +| 122 | efscNffsBackup | running | – | – | – | NFS Backup | + +--- + +## Netzwerk + +| Netz | Bereich | Verwendung | +|--------------|-----------------|-----------------------------------| +| Public | 109.230.227.x | Öffentliche IPs (Hetzner) | +| Intern | 10.42.70.x | Proxmox Hosts / Management | +| Intern | 10.42.71.x | VMs / Server | +| K3s Pod-CIDR | 172.16.0.0/16 | Kubernetes Pod-Netzwerk (Flannel) | +| K3s SVC-CIDR | 10.43.0.0/16 | Kubernetes Services | + +**Traefik LoadBalancer IP:** 10.42.71.60 +**OPNsense** löst `www.expertfab.de` → `10.42.71.60` (intern), `expertfab.de` → öffentliche IP +→ Wichtig: `host_name` in ERPNext muss `https://www.expertfab.de` sein (Hairpin-NAT-Fix) diff --git a/docs/k3s.md b/docs/k3s.md new file mode 100644 index 0000000..81a3c60 --- /dev/null +++ b/docs/k3s.md @@ -0,0 +1,96 @@ +# ExpertFab – K3s Cluster + +**Schaubild:** [../diagrams/k8s_cluster.png](../diagrams/k8s_cluster.png) + +--- + +## Cluster-Übersicht + +| Eigenschaft | Wert | +|-------------------|----------------------------------| +| Distribution | K3s v1.34.6+k3s1 | +| Container Runtime | containerd 2.2.2 | +| OS | Ubuntu 24.04.4 LTS | +| Kernel | 6.8.0-107-generic | +| Ingress | Traefik (websecure / TLS) | +| TLS | cert-manager + Let's Encrypt | +| Storage | Longhorn (verteiltes Block-Storage)| +| CNI | Flannel | +| LB | MetalLB → 10.42.71.60 | + +--- + +## Nodes + +| Name | IP | Proxmox-VM | Proxmox-Host | Rolle | +|---------------|--------------|---------------|---------------|---------------| +| efsckubadm | 10.42.71.50 | efsckubctl | efproxcl02n01 | control-plane | +| efsckubnode1 | 10.42.71.51 | efsckubnode1 | efproxcl02n02 | worker | +| efsckubnode2 | 10.42.71.52 | efsckubnode02 | efproxcl02n01 | worker | + +--- + +## Namespaces + +| Namespace | Inhalt | +|------------------|-----------------------------------------| +| `erpnext` | ERPNext + MariaDB + DragonflyDB | +| `paperless` | Paperless-NGX + PostgreSQL | +| `zitadel` | Zitadel SSO + PostgreSQL | +| `rabbitmq` | RabbitMQ + FastAPI | +| `coworkbase` | Coworkbase | +| `qubicticker` | Qubic Ticker | +| `longhorn-system`| Longhorn Storage | +| `cert-manager` | cert-manager (Let's Encrypt) | +| `metallb-system` | MetalLB LoadBalancer | +| `kube-system` | Traefik, CoreDNS, etc. | + +--- + +## Ingresses (Traefik) + +| Host | Namespace | TLS | +|-----------------------------|--------------|-----| +| expertfab.de | erpnext | ✓ | +| www.expertfab.de | erpnext | ✓ | +| docs.expertfab.de | paperless | ✓ | +| auth.expertfab.de | zitadel | ✓ | +| api.expertfab.de | rabbitmq | ✓ | +| coworkbase.de | coworkbase | ✓ | +| www.coworkbase.de | coworkbase | ✓ | +| qubicticker.qchief.io | qubicticker | ✓ | + +**ClusterIssuer:** `letsencrypt` +**TLS Secret (ERPNext):** `expertfab-tls` + +--- + +## ERPNext Deployment + +| Komponente | Typ | Details | +|--------------------|------------|--------------------------------------------| +| Nginx | Deployment | Frontend, `frappeSiteNameHeader=expertfab.de` | +| Gunicorn | Deployment | Web Workers | +| Worker default | Deployment | Background Jobs | +| Worker short | Deployment | Kurze Jobs | +| Worker long | Deployment | Lange Jobs | +| MariaDB | StatefulSet| v10.6, PVC: 3Gi RWO | +| DragonflyDB cache | Deployment | Redis-kompatibel | +| DragonflyDB queue | Deployment | Redis-kompatibel, PVC: 2Gi RWO (Anmerkung¹)| + +> ¹ Helm-Values definieren 2Gi für Queue, tatsächliche PVC zeigt 3Gi Sites-Volume als RWX + +**Helm Chart:** frappe/erpnext 8.0.14 +**Custom Image:** git.expertfab.de/expertfab/customdocker:1.0.2 +**Apps:** erpnext, hrms, payments, webshop, ecommerce_integrations, efrevolutgateway + +--- + +## DNS-Besonderheit (Hairpin-NAT) + +OPNsense löst nur `www.expertfab.de` → `10.42.71.60` (intern) auf. +`expertfab.de` (ohne www) → öffentliche IP → von innen nicht erreichbar. + +**Fix:** Frappe `host_name` = `https://www.expertfab.de` +**Pfad:** `/home/frappe/frappe-bench/sites/expertfab.de/site_config.json` +**Betrifft:** wkhtmltopdf PDF-Generierung (hängt sonst 120s → 504) diff --git a/docs/storage.md b/docs/storage.md new file mode 100644 index 0000000..6491ed4 --- /dev/null +++ b/docs/storage.md @@ -0,0 +1,86 @@ +# ExpertFab – Longhorn Storage Architektur + +**Schaubild:** [../diagrams/storage_architecture.png](../diagrams/storage_architecture.png) + +--- + +## StorageClasses + +| Name | Reclaim | Binding | Verwendung | +|---------------------|---------|-----------|--------------------------| +| `longhorn` | Delete | Immediate | RabbitMQ, Zitadel | +| `longhorn-erpnext` | Retain | Immediate | ERPNext (Daten bleiben!) | +| `longhorn-paperless`| Retain | Immediate | Paperless (Daten bleiben!)| +| `longhorn-static` | Delete | Immediate | Manuell provisionierte Volumes | +| `local-path` | Delete | WaitForFirstConsumer | Rancher local-path | + +> **Retain** = PV bleibt erhalten wenn PVC gelöscht wird → Schutz vor Datenverlust + +--- + +## PVCs nach Namespace + +### namespace: erpnext +| PVC | Größe | Mode | StorageClass | +|----------------------------|-------|------|---------------------| +| data-erpnext-mariadb-sts-0 | 3 Gi | RWO | longhorn-erpnext | +| erpnext | 3 Gi | RWX | longhorn-erpnext | +| erpnext-logs | 1 Gi | RWX | longhorn-erpnext | + +### namespace: paperless +| PVC | Größe | Mode | StorageClass | +|--------------------|-------|------|----------------------| +| paperless-media | 10 Gi | RWO | longhorn-paperless | +| paperless-consume | 5 Gi | RWO | longhorn-paperless | +| paperless-data | 5 Gi | RWO | longhorn-paperless | +| postgres-data | 5 Gi | RWO | longhorn-paperless | + +### namespace: rabbitmq +| PVC | Größe | Mode | StorageClass | +|--------------------------|-------|------|--------------| +| rabbitmq-data-rabbitmq-0 | 5 Gi | RWO | longhorn | + +### namespace: zitadel +| PVC | Größe | Mode | StorageClass | +|-------------------------|-------|------|--------------| +| postgres-data-postgres-0| 10 Gi | RWO | longhorn | + +--- + +## Longhorn Pods nach Node + +### efsckubnode1 (10.42.71.51) +| Pod | Typ | Replicas | +|---------------------------|------------|----------| +| longhorn-manager | DaemonSet | 1 | +| longhorn-csi-plugin | DaemonSet | 1 | +| engine-image | DaemonSet | 1 | +| instance-manager | – | 1 | +| longhorn-driver-deployer | Deployment | 1 | +| longhorn-ui | Deployment | 2 | +| csi-attacher | Deployment | 3 | +| csi-provisioner | Deployment | 3 | +| csi-resizer | Deployment | 3 | +| csi-snapshotter | Deployment | 3 | + +### efsckubnode2 (10.42.71.52) +| Pod | Typ | Beschreibung | +|-----------------------------|-----------|-------------------------------------| +| longhorn-manager | DaemonSet | – | +| longhorn-csi-plugin | DaemonSet | – | +| engine-image | DaemonSet | – | +| instance-manager | – | – | +| share-manager (erpnext) | – | Bedient RWX-Volume `erpnext` (3Gi) | +| share-manager (erpnext-logs)| – | Bedient RWX-Volume `erpnext-logs` (1Gi) | +| daily-backup | CronJob | Tägliches Backup | + +> **share-manager** Pods werden für RWX-Volumes benötigt: Longhorn stellt RWX über NFS-Share-Manager bereit. +> CSI-Controller-Pods (attacher, provisioner, resizer, snapshotter) laufen nur auf `efsckubnode1`. + +--- + +## Hinweise + +- Longhorn UI: erreichbar über Port-Forward `kubectl port-forward -n longhorn-system svc/longhorn-frontend 8080:80` +- Replikation: Standard 2 Replicas (beide Worker-Nodes) +- Backups: `daily-backup` CronJob auf efsckubnode2