From cab0866e14749b9b00efa88dfe5a740d1f9ad10e Mon Sep 17 00:00:00 2001 From: Danijel Simeunovic Date: Wed, 22 Apr 2026 13:31:09 +0200 Subject: [PATCH 01/15] multi-cloud no mcp --- README.md | 40 +++++--- _app-of-apps-aws-dev.yaml | 32 ++++++ _app-of-apps-aws-prod.yaml | 32 ++++++ _app-of-apps-azure-dev.yaml | 32 ++++++ _app-of-apps-azure-prod.yaml | 32 ++++++ _app-of-apps-gcp-dev.yaml | 32 ++++++ _app-of-apps-gcp-prod.yaml | 32 ++++++ cluster-resources/gitea-backup-cronjob.yaml | 6 +- clusters/aws-dev.yaml | 10 ++ clusters/aws-prod.yaml | 10 ++ clusters/azure-dev.yaml | 10 ++ clusters/azure-prod.yaml | 10 ++ clusters/gcp-dev.yaml | 10 ++ clusters/gcp-prod.yaml | 10 ++ docs/GITOPS-ARCHITECTURE.md | 49 +++++---- docs/OPERATIONS-RUNBOOK.md | 68 +++++++++---- docs/README.md | 11 +- docs/REFERENCE.md | 22 ++-- infra/base/gitea.yaml | 1 + infra/base/opencost.yaml | 1 + infra/overlays/aws-dev/kustomization.yaml | 35 +++++++ infra/overlays/aws-prod/kustomization.yaml | 35 +++++++ infra/overlays/azure-dev/kustomization.yaml | 35 +++++++ infra/overlays/azure-prod/kustomization.yaml | 35 +++++++ infra/overlays/gcp-dev/kustomization.yaml | 35 +++++++ infra/overlays/gcp-prod/kustomization.yaml | 35 +++++++ infra/overlays/upc-prod/kustomization.yaml | 18 ++++ infra/values/aws-dev/gitea-values.yaml | 7 ++ infra/values/aws-dev/opencost-values.yaml | 13 +++ infra/values/aws-dev/traefik-values.yaml | 18 ++++ infra/values/aws-prod/gitea-values.yaml | 7 ++ infra/values/aws-prod/opencost-values.yaml | 13 +++ infra/values/aws-prod/traefik-values.yaml | 18 ++++ infra/values/azure-dev/gitea-values.yaml | 7 ++ infra/values/azure-dev/opencost-values.yaml | 11 ++ infra/values/azure-dev/traefik-values.yaml | 16 +++ infra/values/azure-prod/gitea-values.yaml | 7 ++ infra/values/azure-prod/opencost-values.yaml | 11 ++ infra/values/azure-prod/traefik-values.yaml | 16 +++ infra/values/base/gitea-values.yaml | 2 - infra/values/base/opencost-values.yaml | 14 +-- infra/values/gcp-dev/gitea-values.yaml | 7 ++ infra/values/gcp-dev/opencost-values.yaml | 9 ++ infra/values/gcp-dev/traefik-values.yaml | 15 +++ infra/values/gcp-prod/gitea-values.yaml | 7 ++ infra/values/gcp-prod/opencost-values.yaml | 9 ++ infra/values/gcp-prod/traefik-values.yaml | 15 +++ infra/values/upc-dev/gitea-values.yaml | 7 ++ infra/values/upc-dev/opencost-values.yaml | 15 +++ infra/values/upc-prod/gitea-values.yaml | 7 ++ infra/values/upc-prod/opencost-values.yaml | 15 +++ scripts/gitea-backup-aws.sh | 94 +++++++++++++++++ scripts/gitea-backup-azure.sh | 100 +++++++++++++++++++ scripts/gitea-backup-gcp.sh | 95 ++++++++++++++++++ 54 files changed, 1150 insertions(+), 83 deletions(-) create mode 100644 _app-of-apps-aws-dev.yaml create mode 100644 _app-of-apps-aws-prod.yaml create mode 100644 _app-of-apps-azure-dev.yaml create mode 100644 _app-of-apps-azure-prod.yaml create mode 100644 _app-of-apps-gcp-dev.yaml create mode 100644 _app-of-apps-gcp-prod.yaml create mode 100644 clusters/aws-dev.yaml create mode 100644 clusters/aws-prod.yaml create mode 100644 clusters/azure-dev.yaml create mode 100644 clusters/azure-prod.yaml create mode 100644 clusters/gcp-dev.yaml create mode 100644 clusters/gcp-prod.yaml create mode 100644 infra/overlays/aws-dev/kustomization.yaml create mode 100644 infra/overlays/aws-prod/kustomization.yaml create mode 100644 infra/overlays/azure-dev/kustomization.yaml create mode 100644 infra/overlays/azure-prod/kustomization.yaml create mode 100644 infra/overlays/gcp-dev/kustomization.yaml create mode 100644 infra/overlays/gcp-prod/kustomization.yaml create mode 100644 infra/values/aws-dev/gitea-values.yaml create mode 100644 infra/values/aws-dev/opencost-values.yaml create mode 100644 infra/values/aws-dev/traefik-values.yaml create mode 100644 infra/values/aws-prod/gitea-values.yaml create mode 100644 infra/values/aws-prod/opencost-values.yaml create mode 100644 infra/values/aws-prod/traefik-values.yaml create mode 100644 infra/values/azure-dev/gitea-values.yaml create mode 100644 infra/values/azure-dev/opencost-values.yaml create mode 100644 infra/values/azure-dev/traefik-values.yaml create mode 100644 infra/values/azure-prod/gitea-values.yaml create mode 100644 infra/values/azure-prod/opencost-values.yaml create mode 100644 infra/values/azure-prod/traefik-values.yaml create mode 100644 infra/values/gcp-dev/gitea-values.yaml create mode 100644 infra/values/gcp-dev/opencost-values.yaml create mode 100644 infra/values/gcp-dev/traefik-values.yaml create mode 100644 infra/values/gcp-prod/gitea-values.yaml create mode 100644 infra/values/gcp-prod/opencost-values.yaml create mode 100644 infra/values/gcp-prod/traefik-values.yaml create mode 100644 infra/values/upc-dev/gitea-values.yaml create mode 100644 infra/values/upc-dev/opencost-values.yaml create mode 100644 infra/values/upc-prod/gitea-values.yaml create mode 100644 infra/values/upc-prod/opencost-values.yaml create mode 100755 scripts/gitea-backup-aws.sh create mode 100755 scripts/gitea-backup-azure.sh create mode 100755 scripts/gitea-backup-gcp.sh diff --git a/README.md b/README.md index d419e33..c9511e0 100644 --- a/README.md +++ b/README.md @@ -1,9 +1,9 @@ # Kubernetes Cluster - GitOps Configuration -> **Kubernetes cluster bootstrapping and GitOps configuration repository** using ArgoCD for UpCloud Managed Kubernetes +> **Kubernetes cluster bootstrapping and GitOps configuration repository** using ArgoCD for multi-cloud Kubernetes (UpCloud, AWS EKS, Azure AKS, GCP GKE) [![GitOps](https://img.shields.io/badge/GitOps-ArgoCD-blue)](https://argoproj.github.io/cd/) -[![Kubernetes](https://img.shields.io/badge/Kubernetes-UpCloud-orange)](https://upcloud.com/) +[![Kubernetes](https://img.shields.io/badge/Kubernetes-Multi--Cloud-orange)]() --- @@ -95,14 +95,26 @@ This repository contains the complete GitOps configuration for our Kubernetes cl │ │ ├── renovate.yaml │ │ ├── ... # All other Application manifests │ │ └── secrets.yaml -│ ├── overlays/ # Per-cluster overrides -│ │ ├── upc-dev/ # UpCloud Dev cluster (uses base as-is) -│ │ └── upc-prod/ # UpCloud Prod cluster (patches value paths) +│ ├── overlays/ # Per-cluster overrides (Kustomize) +│ │ ├── upc-dev/ # UpCloud Dev (uses base as-is) +│ │ ├── upc-prod/ # UpCloud Prod (patches value paths) +│ │ ├── aws-dev/ # AWS EKS Dev +│ │ ├── aws-prod/ # AWS EKS Prod +│ │ ├── azure-dev/ # Azure AKS Dev +│ │ ├── azure-prod/ # Azure AKS Prod +│ │ ├── gcp-dev/ # GCP GKE Dev +│ │ └── gcp-prod/ # GCP GKE Prod │ ├── dashboards/ # Grafana dashboard ConfigMaps │ └── values/ # Helm value overrides -│ ├── base/ # Shared values (all clusters) -│ ├── upc-dev/ # UpCloud Dev-specific values -│ └── upc-prod/ # UpCloud Prod-specific values +│ ├── base/ # Shared cloud-agnostic values +│ ├── upc-dev/ # UpCloud Dev (storage, LB, pricing) +│ ├── upc-prod/ # UpCloud Prod +│ ├── aws-dev/ # AWS EKS Dev +│ ├── aws-prod/ # AWS EKS Prod +│ ├── azure-dev/ # Azure AKS Dev +│ ├── azure-prod/ # Azure AKS Prod +│ ├── gcp-dev/ # GCP GKE Dev +│ └── gcp-prod/ # GCP GKE Prod │ ├── apps/ # Business Applications │ ├── mcp10x.yaml @@ -361,7 +373,7 @@ kubectl patch application myapp -n argocd \ ## 📖 Key Concepts ### App-of-Apps Pattern -`_app-of-apps.yaml` is the root Application that manages all other Applications in `infra/`. Kustomize overlays in `infra/overlays/{upc-dev,upc-prod}/` render the base Applications with per-cluster patches (e.g., swapping value file paths from `upc-dev` to `upc-prod`). +`_app-of-apps-{cluster}.yaml` is the root Application that manages all other Applications in `infra/`. Kustomize overlays in `infra/overlays/{cluster}/` render the base Applications with per-cluster patches (e.g., swapping value file paths). Supported clusters: `upc-dev`, `upc-prod`, `aws-dev`, `aws-prod`, `azure-dev`, `azure-prod`, `gcp-dev`, `gcp-prod`. ### Multi-Source Pattern Applications reference both: @@ -458,16 +470,14 @@ Documentation lives in `docs/`. To update: ## 📝 Notes ### Current Environment -- **Provider**: UpCloud Managed Kubernetes +- **Provider**: Multi-cloud (UpCloud, AWS EKS, Azure AKS, GCP GKE) +- **Active clusters**: UpCloud (upc-dev, upc-prod) - **Environment**: Production (internal use only) -- **Clusters**: Multi-cluster (upc-dev, upc-prod) via Kustomize overlays - **Auth**: Disabled for ArgoCD (internal access) -- **Backup**: None (cluster rebuildable via GitOps) +- **Backup**: Gitea daily backup to S3-compatible storage ### Known Limitations -- No automated backups (yet) - Secret rotation not automated -- Multi-cluster limited to upc-dev and upc-prod environments - DNS management is manual **Future improvements**: See [Operations Runbook - Disaster Recovery](docs/OPERATIONS-RUNBOOK.md#disaster-recovery) @@ -504,7 +514,7 @@ Internal use only. Not for public distribution. --- -**Last Updated**: 2026-03-16 +**Last Updated**: 2026-04-22 **Documentation Version**: 1.0.0 **🚀 Ready to get started? Check out the [Documentation Index](docs/README.md)!** diff --git a/_app-of-apps-aws-dev.yaml b/_app-of-apps-aws-dev.yaml new file mode 100644 index 0000000..061d19b --- /dev/null +++ b/_app-of-apps-aws-dev.yaml @@ -0,0 +1,32 @@ +apiVersion: v1 +kind: Namespace +metadata: + name: monitoring + annotations: + argocd.argoproj.io/sync-wave: "-1" +--- +apiVersion: argoproj.io/v1alpha1 +kind: Application +metadata: + name: infrastructure-apps + namespace: argocd + labels: + app.kubernetes.io/name: infrastructure-apps + app.kubernetes.io/part-of: platform + finalizers: + - resources-finalizer.argocd.argoproj.io +spec: + project: default + source: + repoURL: git@github.com:fortedigital/sturdy-adventure.git + targetRevision: HEAD + path: infra/overlays/aws-dev + destination: + server: https://kubernetes.default.svc + namespace: default + syncPolicy: + automated: + prune: true + selfHeal: true + syncOptions: + - CreateNamespace=true diff --git a/_app-of-apps-aws-prod.yaml b/_app-of-apps-aws-prod.yaml new file mode 100644 index 0000000..62fd689 --- /dev/null +++ b/_app-of-apps-aws-prod.yaml @@ -0,0 +1,32 @@ +apiVersion: v1 +kind: Namespace +metadata: + name: monitoring + annotations: + argocd.argoproj.io/sync-wave: "-1" +--- +apiVersion: argoproj.io/v1alpha1 +kind: Application +metadata: + name: infrastructure-apps + namespace: argocd + labels: + app.kubernetes.io/name: infrastructure-apps + app.kubernetes.io/part-of: platform + finalizers: + - resources-finalizer.argocd.argoproj.io +spec: + project: default + source: + repoURL: git@github.com:fortedigital/sturdy-adventure.git + targetRevision: HEAD + path: infra/overlays/aws-prod + destination: + server: https://kubernetes.default.svc + namespace: default + syncPolicy: + automated: + prune: true + selfHeal: true + syncOptions: + - CreateNamespace=true diff --git a/_app-of-apps-azure-dev.yaml b/_app-of-apps-azure-dev.yaml new file mode 100644 index 0000000..deeaefa --- /dev/null +++ b/_app-of-apps-azure-dev.yaml @@ -0,0 +1,32 @@ +apiVersion: v1 +kind: Namespace +metadata: + name: monitoring + annotations: + argocd.argoproj.io/sync-wave: "-1" +--- +apiVersion: argoproj.io/v1alpha1 +kind: Application +metadata: + name: infrastructure-apps + namespace: argocd + labels: + app.kubernetes.io/name: infrastructure-apps + app.kubernetes.io/part-of: platform + finalizers: + - resources-finalizer.argocd.argoproj.io +spec: + project: default + source: + repoURL: git@github.com:fortedigital/sturdy-adventure.git + targetRevision: HEAD + path: infra/overlays/azure-dev + destination: + server: https://kubernetes.default.svc + namespace: default + syncPolicy: + automated: + prune: true + selfHeal: true + syncOptions: + - CreateNamespace=true diff --git a/_app-of-apps-azure-prod.yaml b/_app-of-apps-azure-prod.yaml new file mode 100644 index 0000000..9794896 --- /dev/null +++ b/_app-of-apps-azure-prod.yaml @@ -0,0 +1,32 @@ +apiVersion: v1 +kind: Namespace +metadata: + name: monitoring + annotations: + argocd.argoproj.io/sync-wave: "-1" +--- +apiVersion: argoproj.io/v1alpha1 +kind: Application +metadata: + name: infrastructure-apps + namespace: argocd + labels: + app.kubernetes.io/name: infrastructure-apps + app.kubernetes.io/part-of: platform + finalizers: + - resources-finalizer.argocd.argoproj.io +spec: + project: default + source: + repoURL: git@github.com:fortedigital/sturdy-adventure.git + targetRevision: HEAD + path: infra/overlays/azure-prod + destination: + server: https://kubernetes.default.svc + namespace: default + syncPolicy: + automated: + prune: true + selfHeal: true + syncOptions: + - CreateNamespace=true diff --git a/_app-of-apps-gcp-dev.yaml b/_app-of-apps-gcp-dev.yaml new file mode 100644 index 0000000..63843ce --- /dev/null +++ b/_app-of-apps-gcp-dev.yaml @@ -0,0 +1,32 @@ +apiVersion: v1 +kind: Namespace +metadata: + name: monitoring + annotations: + argocd.argoproj.io/sync-wave: "-1" +--- +apiVersion: argoproj.io/v1alpha1 +kind: Application +metadata: + name: infrastructure-apps + namespace: argocd + labels: + app.kubernetes.io/name: infrastructure-apps + app.kubernetes.io/part-of: platform + finalizers: + - resources-finalizer.argocd.argoproj.io +spec: + project: default + source: + repoURL: git@github.com:fortedigital/sturdy-adventure.git + targetRevision: HEAD + path: infra/overlays/gcp-dev + destination: + server: https://kubernetes.default.svc + namespace: default + syncPolicy: + automated: + prune: true + selfHeal: true + syncOptions: + - CreateNamespace=true diff --git a/_app-of-apps-gcp-prod.yaml b/_app-of-apps-gcp-prod.yaml new file mode 100644 index 0000000..32ae05f --- /dev/null +++ b/_app-of-apps-gcp-prod.yaml @@ -0,0 +1,32 @@ +apiVersion: v1 +kind: Namespace +metadata: + name: monitoring + annotations: + argocd.argoproj.io/sync-wave: "-1" +--- +apiVersion: argoproj.io/v1alpha1 +kind: Application +metadata: + name: infrastructure-apps + namespace: argocd + labels: + app.kubernetes.io/name: infrastructure-apps + app.kubernetes.io/part-of: platform + finalizers: + - resources-finalizer.argocd.argoproj.io +spec: + project: default + source: + repoURL: git@github.com:fortedigital/sturdy-adventure.git + targetRevision: HEAD + path: infra/overlays/gcp-prod + destination: + server: https://kubernetes.default.svc + namespace: default + syncPolicy: + automated: + prune: true + selfHeal: true + syncOptions: + - CreateNamespace=true diff --git a/cluster-resources/gitea-backup-cronjob.yaml b/cluster-resources/gitea-backup-cronjob.yaml index d05ec17..e8a6fa4 100644 --- a/cluster-resources/gitea-backup-cronjob.yaml +++ b/cluster-resources/gitea-backup-cronjob.yaml @@ -57,17 +57,17 @@ spec: - sh - -c - | - mc alias set upcloud "${S3_ENDPOINT}" "${AWS_ACCESS_KEY_ID}" "${AWS_SECRET_ACCESS_KEY}" + mc alias set s3 "${S3_ENDPOINT}" "${AWS_ACCESS_KEY_ID}" "${AWS_SECRET_ACCESS_KEY}" TIMESTAMP=$(date +%Y%m%d-%H%M%S) KEY="gitea-dump-${TIMESTAMP}.zip" echo "Uploading ${KEY}..." - mc cp /backup/gitea-dump.zip "upcloud/${S3_BUCKET}/${KEY}" && \ + mc cp /backup/gitea-dump.zip "s3/${S3_BUCKET}/${KEY}" && \ echo "Upload complete." # Prune backups older than 7 days echo "Pruning backups older than 7 days..." - mc rm --older-than 7d --force "upcloud/${S3_BUCKET}/" 2>&1 || true + mc rm --older-than 7d --force "s3/${S3_BUCKET}/" 2>&1 || true echo "Pruning complete." envFrom: - secretRef: diff --git a/clusters/aws-dev.yaml b/clusters/aws-dev.yaml new file mode 100644 index 0000000..02f3034 --- /dev/null +++ b/clusters/aws-dev.yaml @@ -0,0 +1,10 @@ +clusterName: dev-eks # <- adjust to your EKS cluster name +domain: example.com # <- adjust to your domain +argocdDomain: argocd.example.com +grafanaDomain: grafana.example.com +keycloakDomain: id.example.com +dotaiDomain: kubemcp.example.com +dotaiUiDomain: kubemcpui.example.com +letsencryptEmail: admin@example.com # <- adjust +trustedIPs: "10.0.0.0/8" # <- adjust to your VPC CIDR +cloudProvider: aws diff --git a/clusters/aws-prod.yaml b/clusters/aws-prod.yaml new file mode 100644 index 0000000..c5973f9 --- /dev/null +++ b/clusters/aws-prod.yaml @@ -0,0 +1,10 @@ +clusterName: prod-eks # <- adjust to your EKS cluster name +domain: example.com # <- adjust to your domain +argocdDomain: argocd.example.com +grafanaDomain: grafana.example.com +keycloakDomain: id.example.com +dotaiDomain: kubemcp.example.com +dotaiUiDomain: kubemcpui.example.com +letsencryptEmail: admin@example.com # <- adjust +trustedIPs: "10.0.0.0/8" # <- adjust to your VPC CIDR +cloudProvider: aws diff --git a/clusters/azure-dev.yaml b/clusters/azure-dev.yaml new file mode 100644 index 0000000..5a3ace2 --- /dev/null +++ b/clusters/azure-dev.yaml @@ -0,0 +1,10 @@ +clusterName: dev-aks # <- adjust to your AKS cluster name +domain: example.com # <- adjust to your domain +argocdDomain: argocd.example.com +grafanaDomain: grafana.example.com +keycloakDomain: id.example.com +dotaiDomain: kubemcp.example.com +dotaiUiDomain: kubemcpui.example.com +letsencryptEmail: admin@example.com # <- adjust +trustedIPs: "10.0.0.0/8,168.63.129.16/32" # <- VNet CIDR + Azure health probe +cloudProvider: azure diff --git a/clusters/azure-prod.yaml b/clusters/azure-prod.yaml new file mode 100644 index 0000000..0be858e --- /dev/null +++ b/clusters/azure-prod.yaml @@ -0,0 +1,10 @@ +clusterName: prod-aks # <- adjust to your AKS cluster name +domain: example.com # <- adjust to your domain +argocdDomain: argocd.example.com +grafanaDomain: grafana.example.com +keycloakDomain: id.example.com +dotaiDomain: kubemcp.example.com +dotaiUiDomain: kubemcpui.example.com +letsencryptEmail: admin@example.com # <- adjust +trustedIPs: "10.0.0.0/8,168.63.129.16/32" # <- VNet CIDR + Azure health probe +cloudProvider: azure diff --git a/clusters/gcp-dev.yaml b/clusters/gcp-dev.yaml new file mode 100644 index 0000000..43f3861 --- /dev/null +++ b/clusters/gcp-dev.yaml @@ -0,0 +1,10 @@ +clusterName: dev-gke # <- adjust to your GKE cluster name +domain: example.com # <- adjust to your domain +argocdDomain: argocd.example.com +grafanaDomain: grafana.example.com +keycloakDomain: id.example.com +dotaiDomain: kubemcp.example.com +dotaiUiDomain: kubemcpui.example.com +letsencryptEmail: admin@example.com # <- adjust +trustedIPs: "10.0.0.0/8,35.191.0.0/16,130.211.0.0/22" # <- subnet CIDR + GCP health checks +cloudProvider: gcp diff --git a/clusters/gcp-prod.yaml b/clusters/gcp-prod.yaml new file mode 100644 index 0000000..ec814f7 --- /dev/null +++ b/clusters/gcp-prod.yaml @@ -0,0 +1,10 @@ +clusterName: prod-gke # <- adjust to your GKE cluster name +domain: example.com # <- adjust to your domain +argocdDomain: argocd.example.com +grafanaDomain: grafana.example.com +keycloakDomain: id.example.com +dotaiDomain: kubemcp.example.com +dotaiUiDomain: kubemcpui.example.com +letsencryptEmail: admin@example.com # <- adjust +trustedIPs: "10.0.0.0/8,35.191.0.0/16,130.211.0.0/22" # <- subnet CIDR + GCP health checks +cloudProvider: gcp diff --git a/docs/GITOPS-ARCHITECTURE.md b/docs/GITOPS-ARCHITECTURE.md index ec9769f..a57fb4b 100644 --- a/docs/GITOPS-ARCHITECTURE.md +++ b/docs/GITOPS-ARCHITECTURE.md @@ -12,11 +12,11 @@ ## Overview -This Kubernetes cluster uses a **GitOps approach** powered by **ArgoCD**, where Git repositories serve as the single source of truth for both infrastructure and application deployments. The cluster is running on **UpCloud Managed Kubernetes** but is designed to be cloud-agnostic. +This Kubernetes cluster uses a **GitOps approach** powered by **ArgoCD**, where Git repositories serve as the single source of truth for both infrastructure and application deployments. The cluster setup is **cloud-agnostic**, with ready-to-use configurations for **UpCloud**, **AWS EKS**, **Azure AKS**, and **GCP GKE**. ### Key Characteristics - **Environment**: Production (internal use only) -- **Cluster Type**: Multi-cluster (upc-dev, upc-prod) via Kustomize overlays +- **Cluster Type**: Multi-cloud, multi-cluster via Kustomize overlays (UpCloud, AWS, Azure, GCP) - **GitOps Tool**: ArgoCD - **Deployment Pattern**: App-of-Apps - **Secret Management**: Sealed Secrets (kubeseal) @@ -63,7 +63,7 @@ This Kubernetes cluster uses a **GitOps approach** powered by **ArgoCD**, where ▼ ┌────────────────────────────────┐ │ Kubernetes Clusters │ - │ (UpCloud: upc-dev, upc-prod) │ + │ (UpCloud, AWS, Azure, GCP) │ │ │ │ ┌──────────────────────────┐ │ │ │ ArgoCD │ │ @@ -131,26 +131,22 @@ launchpad/ │ │ ├── renovate.yaml │ │ ├── ... # All other Application manifests │ │ └── secrets.yaml -│ ├── overlays/ # Per-cluster overrides +│ ├── overlays/ # Per-cluster Kustomize overrides │ │ ├── upc-dev/ # UpCloud Dev (uses base as-is) -│ │ └── upc-prod/ # UpCloud Prod (patches value paths) +│ │ ├── upc-prod/ # UpCloud Prod (patches value paths) +│ │ ├── aws-dev/ # AWS EKS Dev +│ │ ├── aws-prod/ # AWS EKS Prod +│ │ ├── azure-dev/ # Azure AKS Dev +│ │ ├── azure-prod/ # Azure AKS Prod +│ │ ├── gcp-dev/ # GCP GKE Dev +│ │ └── gcp-prod/ # GCP GKE Prod │ ├── dashboards/ # Grafana dashboard ConfigMaps │ └── values/ # Helm value overrides for infra -│ ├── base/ # Shared values (all clusters) -│ │ ├── traefik-values.yaml -│ │ ├── keycloak-values.yaml -│ │ ├── grafana-values.yaml -│ │ ├── prometheus-values.yaml -│ │ ├── gitea-values.yaml -│ │ └── ... -│ ├── upc-dev/ # upc-dev cluster-specific values -│ │ ├── traefik-values.yaml -│ │ ├── keycloak-values.yaml -│ │ └── grafana-values.yaml -│ └── upc-prod/ # upc-prod cluster-specific values -│ ├── traefik-values.yaml -│ ├── keycloak-values.yaml -│ └── grafana-values.yaml +│ ├── base/ # Cloud-agnostic shared values +│ ├── upc-{dev,prod}/ # UpCloud: storage class, LB, pricing +│ ├── aws-{dev,prod}/ # AWS: gp3, NLB, CUR pricing +│ ├── azure-{dev,prod}/ # Azure: managed-csi-premium, Standard LB +│ └── gcp-{dev,prod}/ # GCP: premium-rwo, L4 LB │ ├── apps/ # Business Application ArgoCD manifests (Kustomize) │ ├── base/ # Base app manifests @@ -287,7 +283,7 @@ app-repository/ ### The App-of-Apps Pattern ``` -_app-of-apps-{upc-dev,upc-prod}.yaml (Root, per cluster) +_app-of-apps-{cluster}.yaml (Root, per cluster — e.g. upc-dev, aws-prod, gcp-dev) │ ├── infrastructure-apps (manages infra/) │ ├── cluster-resources-application @@ -377,6 +373,15 @@ patches: value: $values/infra/values/upc-prod/traefik-values.yaml ``` +Cloud-specific values (storage classes, load balancer annotations, cost model) are isolated in per-cluster value files. Base values are fully cloud-agnostic: + +| Cloud | Storage Class | Load Balancer | OpenCost Provider | +|-------|--------------|---------------|-------------------| +| **UpCloud** | `upcloud-block-storage-maxiops` | UpCloud LB (ProxyProtocol v2) | Custom pricing | +| **AWS EKS** | `gp3` (EBS CSI) | NLB (ProxyProtocol v2) | AWS CUR | +| **Azure AKS** | `managed-csi-premium` | Standard LB (`externalTrafficPolicy: Local`) | Azure Billing API | +| **GCP GKE** | `premium-rwo` (PD CSI) | L4 passthrough NLB | GCP Cloud Billing | + **Benefits**: - Single source of truth for Application definitions - Cluster-specific values isolated per overlay @@ -658,6 +663,6 @@ Notifications include: --- -**Last Updated**: 2026-03-16 +**Last Updated**: 2026-04-22 **Maintained By**: Platform Team **Questions?**: Contact #platform-support on Slack diff --git a/docs/OPERATIONS-RUNBOOK.md b/docs/OPERATIONS-RUNBOOK.md index a02a239..03ea097 100644 --- a/docs/OPERATIONS-RUNBOOK.md +++ b/docs/OPERATIONS-RUNBOOK.md @@ -37,7 +37,7 @@ Bootstrap a new cluster from scratch: #### Prerequisites -1. **Kubernetes cluster running** (UpCloud or any K8s cluster) +1. **Kubernetes cluster running** (UpCloud, AWS EKS, Azure AKS, GCP GKE, or any K8s cluster) 2. **kubectl configured** with admin access 3. **Repositories cloned** locally @@ -54,11 +54,13 @@ kubectl get nodes git clone https://git.forteapps.net/Forte/launchpad cd launchpad -# 2. Set cluster name (optional) -export CLUSTER_NAME="prod-cluster-01" +# 2. Run bootstrap script with cluster target +# Available clusters: upc-dev, upc-prod, aws-dev, aws-prod, +# azure-dev, azure-prod, gcp-dev, gcp-prod +./bootstrap.sh upc-dev -# 3. Run bootstrap script -./bootstrap.sh +# Cluster config is loaded from clusters/.yaml +# (cloudProvider, trustedIPs, domain, etc.) ``` **What Happens:** @@ -1262,13 +1264,21 @@ spec: ### Backup Strategy -**Current State**: No automated backups +**Current State**: Gitea daily backups to S3-compatible storage -**What Needs Backup**: -- ❌ Cluster state (not backed up - recreate via GitOps) -- ❌ Persistent volumes (currently not critical) -- ✅ Git repositories (Gitea provides backup) -- ⚠️ Secrets (sealed secrets in Git, unseal keys need safekeeping) +**What Is Backed Up**: +- ✅ Gitea repositories + database: Daily CronJob (`cluster-resources/gitea-backup-cronjob.yaml`) uploads to S3-compatible storage with 7-day retention +- ✅ Git repositories: Full cluster config recoverable from Git +- ⚠️ Secrets: Sealed secrets in Git; unseal keys need safekeeping + +**What Is NOT Backed Up**: +- ❌ Cluster state (recreate via GitOps) +- ❌ Other persistent volumes (Prometheus, Loki, Tempo data) + +**Per-cloud backup scripts** (manual restore helpers): +- UpCloud/AWS: `scripts/gitea-backup.sh` / `scripts/gitea-backup-aws.sh` (MinIO CLI, S3-compatible) +- Azure: `scripts/gitea-backup-azure.sh` (Azure CLI + Blob Storage) +- GCP: `scripts/gitea-backup-gcp.sh` (gsutil + GCS) ### Cluster Rebuild @@ -1370,6 +1380,9 @@ kubectl get pods -n argocd ```bash # UpCloud: Upgrade via control panel or CLI +# AWS EKS: eksctl upgrade cluster / AWS Console +# Azure AKS: az aks upgrade / Azure Portal +# GCP GKE: gcloud container clusters upgrade / Cloud Console # After upgrade, verify cluster kubectl version @@ -1507,18 +1520,35 @@ git push ### Multi-Cluster Setup -The repository supports multiple clusters via Kustomize overlays: +The repository supports multiple clusters across multiple clouds via Kustomize overlays: +**Active clusters:** - **upc-dev** (default): `infra/overlays/upc-dev/` — uses base Applications as-is - **upc-prod**: `infra/overlays/upc-prod/` — patches value file paths from `upc-dev` to `upc-prod` -Each cluster has its own: -- Root app-of-apps file: `_app-of-apps-upc-dev.yaml` / `_app-of-apps-upc-prod.yaml` -- Cluster-specific Helm values: `infra/values/upc-dev/` / `infra/values/upc-prod/` -- Sealed secrets: `secrets/upc-dev/` (others as needed) -- Apps overlay: `apps/overlays/upc-dev/` / `apps/overlays/upc-prod/` +**Cloud-ready templates (fill in `clusters/*.yaml` before use):** +- **aws-dev** / **aws-prod**: AWS EKS with NLB, gp3 storage, AWS CUR pricing +- **azure-dev** / **azure-prod**: Azure AKS with Standard LB, managed-csi-premium storage +- **gcp-dev** / **gcp-prod**: GCP GKE with L4 LB, premium-rwo storage -To add a new cluster, create a new overlay directory (e.g., `infra/overlays/upc-staging/`) with patches that swap the value file paths. +Each cluster has its own: +- Root app-of-apps: `_app-of-apps-{cluster}.yaml` +- Cluster config: `clusters/{cluster}.yaml` (domain, trustedIPs, cloudProvider) +- Kustomize overlay: `infra/overlays/{cluster}/kustomization.yaml` +- Helm value overrides: `infra/values/{cluster}/` (traefik, gitea, opencost) +- Sealed secrets: `secrets/{cluster}/` (as needed) +- Apps overlay: `apps/overlays/{cluster}/` + +Cloud-specific values handled per-cluster: + +| Concern | UpCloud | AWS EKS | Azure AKS | GCP GKE | +|---------|---------|---------|-----------|---------| +| **Storage class** | `upcloud-block-storage-maxiops` | `gp3` | `managed-csi-premium` | `premium-rwo` | +| **Load balancer** | UpCloud LB + ProxyProtocol v2 | NLB + ProxyProtocol v2 | Standard LB + `externalTrafficPolicy: Local` | L4 passthrough NLB | +| **Cost monitoring** | Custom pricing | AWS CUR | Azure Billing API | GCP Cloud Billing | +| **Backup storage** | UpCloud S3-compat | AWS S3 (native) | Azure Blob Storage | GCS | + +To add a new cluster, create a new overlay directory (e.g., `infra/overlays/aws-staging/`) with patches that swap the value file paths, and a matching `clusters/aws-staging.yaml`. ### Blue-Green Deployments @@ -1661,6 +1691,6 @@ echo "Remember to delete: $SECRET_FILE" --- -**Last Updated**: 2026-03-16 +**Last Updated**: 2026-04-22 **Maintained By**: Platform Team **Emergency Contact**: #platform-support on Slack diff --git a/docs/README.md b/docs/README.md index 47a394e..6b48500 100644 --- a/docs/README.md +++ b/docs/README.md @@ -180,7 +180,7 @@ Reference for: │ ▼ ┌──────────────────────────────────────────────────────────────┐ -│ Kubernetes Clusters (UpCloud: upc-dev, upc-prod) │ +│ Kubernetes Clusters (UpCloud, AWS, Azure, GCP) │ │ ┌──────────────────────────────────────────────────────┐ │ │ │ Infrastructure: Traefik, Cert-Manager, Kyverno │ │ │ ├──────────────────────────────────────────────────────┤ │ @@ -194,7 +194,7 @@ Reference for: ### Key Technologies - **GitOps**: ArgoCD -- **Kubernetes**: UpCloud Managed Kubernetes (multi-cluster: upc-dev, upc-prod) +- **Kubernetes**: Multi-cloud (UpCloud, AWS EKS, Azure AKS, GCP GKE) - **Ingress**: Traefik v2 - **Certificates**: Cert-Manager + Let's Encrypt - **Policies**: Kyverno @@ -299,11 +299,16 @@ docs/ ## 🔄 Documentation Versions **Current Version**: 1.0.0 -**Last Updated**: 2026-03-16 +**Last Updated**: 2026-04-22 **Maintained By**: Platform Team ### Changelog +- **v1.1.0 (2026-04-22)**: Multi-cloud support + - Cloud-agnostic base values (storage, LB, pricing moved to per-cluster overlays) + - Added AWS EKS, Azure AKS, GCP GKE configurations + - Per-cloud backup scripts + - Updated all documentation - **v1.0.0 (2026-03-16)**: Initial comprehensive documentation release - GitOps Architecture guide - Developer Onboarding guide diff --git a/docs/REFERENCE.md b/docs/REFERENCE.md index 5ba17aa..f5be8f5 100644 --- a/docs/REFERENCE.md +++ b/docs/REFERENCE.md @@ -19,9 +19,9 @@ | Component | Value | |-----------|-------| -| **Provider** | UpCloud Managed Kubernetes | -| **Environment** | Production (internal use) | -| **Cluster Count** | Multi-cluster (upc-dev, upc-prod) | +| **Provider** | Multi-cloud (UpCloud, AWS EKS, Azure AKS, GCP GKE) | +| **Active clusters** | UpCloud (upc-dev, upc-prod) | +| **Cloud-ready templates** | AWS, Azure, GCP (dev + prod each) | | **GitOps Tool** | ArgoCD | | **Ingress Controller** | Traefik v2 | | **Certificate Management** | Cert-Manager + Let's Encrypt | @@ -42,7 +42,7 @@ Internet [DNS: *.forteapps.net] │ ▼ -[UpCloud LoadBalancer] +[Cloud Load Balancer] │ ▼ [Traefik Ingress Controller] @@ -1470,14 +1470,22 @@ Recommended resource allocation: ### Storage Classes -Default storage class used: **UpCloud default** (varies by provider) +Storage classes are cloud-specific and configured in per-cluster value overrides (`infra/values/{cluster}/gitea-values.yaml`): + +| Cloud | Storage Class | Driver | +|-------|--------------|--------| +| **UpCloud** | `upcloud-block-storage-maxiops` | UpCloud CSI | +| **AWS EKS** | `gp3` | EBS CSI | +| **Azure AKS** | `managed-csi-premium` | Azure Disk CSI | +| **GCP GKE** | `premium-rwo` | PD CSI | ```yaml +# Example: base values omit storageClass (set in per-cluster overlay) persistence: enabled: true - storageClass: "" # Uses default accessMode: ReadWriteOnce size: 5Gi + # storageClass set by infra/values/{cluster}/gitea-values.yaml ``` --- @@ -1673,6 +1681,6 @@ team: platform --- -**Last Updated**: 2026-04-16 +**Last Updated**: 2026-04-22 **Maintained By**: Platform Team **Version**: 1.0.0 diff --git a/infra/base/gitea.yaml b/infra/base/gitea.yaml index ba806f5..cc4f60f 100644 --- a/infra/base/gitea.yaml +++ b/infra/base/gitea.yaml @@ -22,6 +22,7 @@ spec: releaseName: gitea valueFiles: - $values/infra/values/base/gitea-values.yaml + - $values/infra/values/upc-dev/gitea-values.yaml - repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD diff --git a/infra/base/opencost.yaml b/infra/base/opencost.yaml index 6984f3b..a102906 100644 --- a/infra/base/opencost.yaml +++ b/infra/base/opencost.yaml @@ -22,6 +22,7 @@ spec: releaseName: opencost valueFiles: - $values/infra/values/base/opencost-values.yaml + - $values/infra/values/upc-dev/opencost-values.yaml - repoURL: git@github.com:fortedigital/sturdy-adventure.git targetRevision: HEAD diff --git a/infra/overlays/aws-dev/kustomization.yaml b/infra/overlays/aws-dev/kustomization.yaml new file mode 100644 index 0000000..4be71fc --- /dev/null +++ b/infra/overlays/aws-dev/kustomization.yaml @@ -0,0 +1,35 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: +- ../../base + +patches: +# Traefik: swap upc-dev → aws-dev +- target: + kind: Application + name: traefik + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/aws-dev/traefik-values.yaml + +# Gitea: swap upc-dev → aws-dev +- target: + kind: Application + name: gitea + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/aws-dev/gitea-values.yaml + +# OpenCost: swap upc-dev → aws-dev +- target: + kind: Application + name: opencost + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/aws-dev/opencost-values.yaml + +# TODO: add patches for keycloak, grafana, secrets, enterprise-apps +# when deploying to this cluster (these are deployment-specific, not cloud-specific) diff --git a/infra/overlays/aws-prod/kustomization.yaml b/infra/overlays/aws-prod/kustomization.yaml new file mode 100644 index 0000000..ce22faf --- /dev/null +++ b/infra/overlays/aws-prod/kustomization.yaml @@ -0,0 +1,35 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: +- ../../base + +patches: +# Traefik: swap upc-dev → aws-prod +- target: + kind: Application + name: traefik + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/aws-prod/traefik-values.yaml + +# Gitea: swap upc-dev → aws-prod +- target: + kind: Application + name: gitea + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/aws-prod/gitea-values.yaml + +# OpenCost: swap upc-dev → aws-prod +- target: + kind: Application + name: opencost + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/aws-prod/opencost-values.yaml + +# TODO: add patches for keycloak, grafana, secrets, enterprise-apps +# when deploying to this cluster (these are deployment-specific, not cloud-specific) diff --git a/infra/overlays/azure-dev/kustomization.yaml b/infra/overlays/azure-dev/kustomization.yaml new file mode 100644 index 0000000..d7a014d --- /dev/null +++ b/infra/overlays/azure-dev/kustomization.yaml @@ -0,0 +1,35 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: +- ../../base + +patches: +# Traefik: swap upc-dev → azure-dev +- target: + kind: Application + name: traefik + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/azure-dev/traefik-values.yaml + +# Gitea: swap upc-dev → azure-dev +- target: + kind: Application + name: gitea + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/azure-dev/gitea-values.yaml + +# OpenCost: swap upc-dev → azure-dev +- target: + kind: Application + name: opencost + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/azure-dev/opencost-values.yaml + +# TODO: add patches for keycloak, grafana, secrets, enterprise-apps +# when deploying to this cluster (these are deployment-specific, not cloud-specific) diff --git a/infra/overlays/azure-prod/kustomization.yaml b/infra/overlays/azure-prod/kustomization.yaml new file mode 100644 index 0000000..4a9d6cf --- /dev/null +++ b/infra/overlays/azure-prod/kustomization.yaml @@ -0,0 +1,35 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: +- ../../base + +patches: +# Traefik: swap upc-dev → azure-prod +- target: + kind: Application + name: traefik + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/azure-prod/traefik-values.yaml + +# Gitea: swap upc-dev → azure-prod +- target: + kind: Application + name: gitea + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/azure-prod/gitea-values.yaml + +# OpenCost: swap upc-dev → azure-prod +- target: + kind: Application + name: opencost + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/azure-prod/opencost-values.yaml + +# TODO: add patches for keycloak, grafana, secrets, enterprise-apps +# when deploying to this cluster (these are deployment-specific, not cloud-specific) diff --git a/infra/overlays/gcp-dev/kustomization.yaml b/infra/overlays/gcp-dev/kustomization.yaml new file mode 100644 index 0000000..491065e --- /dev/null +++ b/infra/overlays/gcp-dev/kustomization.yaml @@ -0,0 +1,35 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: +- ../../base + +patches: +# Traefik: swap upc-dev → gcp-dev +- target: + kind: Application + name: traefik + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/gcp-dev/traefik-values.yaml + +# Gitea: swap upc-dev → gcp-dev +- target: + kind: Application + name: gitea + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/gcp-dev/gitea-values.yaml + +# OpenCost: swap upc-dev → gcp-dev +- target: + kind: Application + name: opencost + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/gcp-dev/opencost-values.yaml + +# TODO: add patches for keycloak, grafana, secrets, enterprise-apps +# when deploying to this cluster (these are deployment-specific, not cloud-specific) diff --git a/infra/overlays/gcp-prod/kustomization.yaml b/infra/overlays/gcp-prod/kustomization.yaml new file mode 100644 index 0000000..9971aa9 --- /dev/null +++ b/infra/overlays/gcp-prod/kustomization.yaml @@ -0,0 +1,35 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: +- ../../base + +patches: +# Traefik: swap upc-dev → gcp-prod +- target: + kind: Application + name: traefik + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/gcp-prod/traefik-values.yaml + +# Gitea: swap upc-dev → gcp-prod +- target: + kind: Application + name: gitea + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/gcp-prod/gitea-values.yaml + +# OpenCost: swap upc-dev → gcp-prod +- target: + kind: Application + name: opencost + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/gcp-prod/opencost-values.yaml + +# TODO: add patches for keycloak, grafana, secrets, enterprise-apps +# when deploying to this cluster (these are deployment-specific, not cloud-specific) diff --git a/infra/overlays/upc-prod/kustomization.yaml b/infra/overlays/upc-prod/kustomization.yaml index ebfc179..5a6c53d 100644 --- a/infra/overlays/upc-prod/kustomization.yaml +++ b/infra/overlays/upc-prod/kustomization.yaml @@ -48,3 +48,21 @@ patches: - op: replace path: /spec/source/path value: apps/overlays/upc-prod + +# Gitea: swap upc-dev → upc-prod +- target: + kind: Application + name: gitea + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/upc-prod/gitea-values.yaml + +# OpenCost: swap upc-dev → upc-prod +- target: + kind: Application + name: opencost + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/upc-prod/opencost-values.yaml diff --git a/infra/values/aws-dev/gitea-values.yaml b/infra/values/aws-dev/gitea-values.yaml new file mode 100644 index 0000000..597af4f --- /dev/null +++ b/infra/values/aws-dev/gitea-values.yaml @@ -0,0 +1,7 @@ +# AWS EBS gp3 storage class (requires EBS CSI driver) +persistence: + storageClass: gp3 +postgresql: + primary: + persistence: + storageClass: gp3 diff --git a/infra/values/aws-dev/opencost-values.yaml b/infra/values/aws-dev/opencost-values.yaml new file mode 100644 index 0000000..93ff67a --- /dev/null +++ b/infra/values/aws-dev/opencost-values.yaml @@ -0,0 +1,13 @@ +# AWS native pricing via Cost and Usage Reports +opencost: + exporter: + customPricing: + enabled: true + provider: aws + aws: + service_key_name: "" # <- populate or use IRSA + service_key_secret: "" + spot_data_region: "" + spot_data_bucket: "" + spot_data_prefix: "" + account_id: "" diff --git a/infra/values/aws-dev/traefik-values.yaml b/infra/values/aws-dev/traefik-values.yaml new file mode 100644 index 0000000..34306f7 --- /dev/null +++ b/infra/values/aws-dev/traefik-values.yaml @@ -0,0 +1,18 @@ +# AWS EKS — NLB with Proxy Protocol v2 for real client IPs +service: + annotations: + service.beta.kubernetes.io/aws-load-balancer-type: "external" + service.beta.kubernetes.io/aws-load-balancer-nlb-target-type: "ip" + service.beta.kubernetes.io/aws-load-balancer-scheme: "internet-facing" + service.beta.kubernetes.io/aws-load-balancer-proxy-protocol: "*" +ports: + web: + proxyProtocol: + trustedIPs: "10.0.0.0/8" # <- adjust to your VPC CIDR + forwardedHeaders: + trustedIPs: "10.0.0.0/8" + websecure: + proxyProtocol: + trustedIPs: "10.0.0.0/8" + forwardedHeaders: + trustedIPs: "10.0.0.0/8" diff --git a/infra/values/aws-prod/gitea-values.yaml b/infra/values/aws-prod/gitea-values.yaml new file mode 100644 index 0000000..597af4f --- /dev/null +++ b/infra/values/aws-prod/gitea-values.yaml @@ -0,0 +1,7 @@ +# AWS EBS gp3 storage class (requires EBS CSI driver) +persistence: + storageClass: gp3 +postgresql: + primary: + persistence: + storageClass: gp3 diff --git a/infra/values/aws-prod/opencost-values.yaml b/infra/values/aws-prod/opencost-values.yaml new file mode 100644 index 0000000..93ff67a --- /dev/null +++ b/infra/values/aws-prod/opencost-values.yaml @@ -0,0 +1,13 @@ +# AWS native pricing via Cost and Usage Reports +opencost: + exporter: + customPricing: + enabled: true + provider: aws + aws: + service_key_name: "" # <- populate or use IRSA + service_key_secret: "" + spot_data_region: "" + spot_data_bucket: "" + spot_data_prefix: "" + account_id: "" diff --git a/infra/values/aws-prod/traefik-values.yaml b/infra/values/aws-prod/traefik-values.yaml new file mode 100644 index 0000000..34306f7 --- /dev/null +++ b/infra/values/aws-prod/traefik-values.yaml @@ -0,0 +1,18 @@ +# AWS EKS — NLB with Proxy Protocol v2 for real client IPs +service: + annotations: + service.beta.kubernetes.io/aws-load-balancer-type: "external" + service.beta.kubernetes.io/aws-load-balancer-nlb-target-type: "ip" + service.beta.kubernetes.io/aws-load-balancer-scheme: "internet-facing" + service.beta.kubernetes.io/aws-load-balancer-proxy-protocol: "*" +ports: + web: + proxyProtocol: + trustedIPs: "10.0.0.0/8" # <- adjust to your VPC CIDR + forwardedHeaders: + trustedIPs: "10.0.0.0/8" + websecure: + proxyProtocol: + trustedIPs: "10.0.0.0/8" + forwardedHeaders: + trustedIPs: "10.0.0.0/8" diff --git a/infra/values/azure-dev/gitea-values.yaml b/infra/values/azure-dev/gitea-values.yaml new file mode 100644 index 0000000..5bb20ff --- /dev/null +++ b/infra/values/azure-dev/gitea-values.yaml @@ -0,0 +1,7 @@ +# Azure Managed Disk (Premium SSD via CSI driver) +persistence: + storageClass: managed-csi-premium +postgresql: + primary: + persistence: + storageClass: managed-csi-premium diff --git a/infra/values/azure-dev/opencost-values.yaml b/infra/values/azure-dev/opencost-values.yaml new file mode 100644 index 0000000..98b30cd --- /dev/null +++ b/infra/values/azure-dev/opencost-values.yaml @@ -0,0 +1,11 @@ +# Azure native pricing via Billing API +opencost: + exporter: + customPricing: + enabled: true + provider: azure + azure: + subscriptionID: "" # <- populate + clientID: "" + clientSecret: "" + tenantID: "" diff --git a/infra/values/azure-dev/traefik-values.yaml b/infra/values/azure-dev/traefik-values.yaml new file mode 100644 index 0000000..7efa198 --- /dev/null +++ b/infra/values/azure-dev/traefik-values.yaml @@ -0,0 +1,16 @@ +# Azure AKS — Standard Load Balancer +# Note: Azure Standard LB does not support Proxy Protocol. +# Use externalTrafficPolicy: Local on the Traefik service to preserve +# client IPs, or deploy behind Azure Application Gateway. +service: + annotations: + service.beta.kubernetes.io/azure-load-balancer-health-probe-request-path: "/ping" + spec: + externalTrafficPolicy: Local +ports: + web: + forwardedHeaders: + trustedIPs: "10.0.0.0/8,168.63.129.16/32" # <- VNet CIDR + Azure health probe + websecure: + forwardedHeaders: + trustedIPs: "10.0.0.0/8,168.63.129.16/32" diff --git a/infra/values/azure-prod/gitea-values.yaml b/infra/values/azure-prod/gitea-values.yaml new file mode 100644 index 0000000..5bb20ff --- /dev/null +++ b/infra/values/azure-prod/gitea-values.yaml @@ -0,0 +1,7 @@ +# Azure Managed Disk (Premium SSD via CSI driver) +persistence: + storageClass: managed-csi-premium +postgresql: + primary: + persistence: + storageClass: managed-csi-premium diff --git a/infra/values/azure-prod/opencost-values.yaml b/infra/values/azure-prod/opencost-values.yaml new file mode 100644 index 0000000..98b30cd --- /dev/null +++ b/infra/values/azure-prod/opencost-values.yaml @@ -0,0 +1,11 @@ +# Azure native pricing via Billing API +opencost: + exporter: + customPricing: + enabled: true + provider: azure + azure: + subscriptionID: "" # <- populate + clientID: "" + clientSecret: "" + tenantID: "" diff --git a/infra/values/azure-prod/traefik-values.yaml b/infra/values/azure-prod/traefik-values.yaml new file mode 100644 index 0000000..7efa198 --- /dev/null +++ b/infra/values/azure-prod/traefik-values.yaml @@ -0,0 +1,16 @@ +# Azure AKS — Standard Load Balancer +# Note: Azure Standard LB does not support Proxy Protocol. +# Use externalTrafficPolicy: Local on the Traefik service to preserve +# client IPs, or deploy behind Azure Application Gateway. +service: + annotations: + service.beta.kubernetes.io/azure-load-balancer-health-probe-request-path: "/ping" + spec: + externalTrafficPolicy: Local +ports: + web: + forwardedHeaders: + trustedIPs: "10.0.0.0/8,168.63.129.16/32" # <- VNet CIDR + Azure health probe + websecure: + forwardedHeaders: + trustedIPs: "10.0.0.0/8,168.63.129.16/32" diff --git a/infra/values/base/gitea-values.yaml b/infra/values/base/gitea-values.yaml index e34f256..75c2e72 100644 --- a/infra/values/base/gitea-values.yaml +++ b/infra/values/base/gitea-values.yaml @@ -127,7 +127,6 @@ persistence: size: 10Gi accessModes: - ReadWriteOnce - storageClass: upcloud-block-storage-maxiops # -- Recreate strategy to avoid Multi-Attach errors with RWO volumes strategy: @@ -153,7 +152,6 @@ postgresql: persistence: enabled: true size: 8Gi - storageClass: upcloud-block-storage-maxiops resources: requests: cpu: 100m diff --git a/infra/values/base/opencost-values.yaml b/infra/values/base/opencost-values.yaml index 39d73cc..dde13fb 100644 --- a/infra/values/base/opencost-values.yaml +++ b/infra/values/base/opencost-values.yaml @@ -10,18 +10,8 @@ opencost: serviceName: prometheus-server namespaceName: monitoring port: 80 - customPricing: - enabled: true - provider: custom - costModel: - description: "UpCloud 4-node cluster pricing" - CPU: "5.86" - RAM: "1.46" - GPU: "0" - storage: "0.34" - zoneNetworkEgress: "0" - regionNetworkEgress: "0" - internetNetworkEgress: "0" + # Cloud-specific pricing is in per-cluster value overrides + # (e.g. infra/values/upc-dev/opencost-values.yaml) ui: enabled: false service: diff --git a/infra/values/gcp-dev/gitea-values.yaml b/infra/values/gcp-dev/gitea-values.yaml new file mode 100644 index 0000000..b825aee --- /dev/null +++ b/infra/values/gcp-dev/gitea-values.yaml @@ -0,0 +1,7 @@ +# GCP Persistent Disk (SSD via CSI driver) +persistence: + storageClass: premium-rwo +postgresql: + primary: + persistence: + storageClass: premium-rwo diff --git a/infra/values/gcp-dev/opencost-values.yaml b/infra/values/gcp-dev/opencost-values.yaml new file mode 100644 index 0000000..f3ea481 --- /dev/null +++ b/infra/values/gcp-dev/opencost-values.yaml @@ -0,0 +1,9 @@ +# GCP native pricing via Cloud Billing API +opencost: + exporter: + customPricing: + enabled: true + provider: gcp + gcp: + projectID: "" # <- populate with your GCP project ID + key: "" # <- or use Workload Identity diff --git a/infra/values/gcp-dev/traefik-values.yaml b/infra/values/gcp-dev/traefik-values.yaml new file mode 100644 index 0000000..55351c0 --- /dev/null +++ b/infra/values/gcp-dev/traefik-values.yaml @@ -0,0 +1,15 @@ +# GCP GKE — External passthrough Network Load Balancer +service: + annotations: + cloud.google.com/l4-rbs: "enabled" +ports: + web: + proxyProtocol: + trustedIPs: "10.0.0.0/8,35.191.0.0/16,130.211.0.0/22" # <- subnet CIDR + GCP health checks + forwardedHeaders: + trustedIPs: "10.0.0.0/8,35.191.0.0/16,130.211.0.0/22" + websecure: + proxyProtocol: + trustedIPs: "10.0.0.0/8,35.191.0.0/16,130.211.0.0/22" + forwardedHeaders: + trustedIPs: "10.0.0.0/8,35.191.0.0/16,130.211.0.0/22" diff --git a/infra/values/gcp-prod/gitea-values.yaml b/infra/values/gcp-prod/gitea-values.yaml new file mode 100644 index 0000000..b825aee --- /dev/null +++ b/infra/values/gcp-prod/gitea-values.yaml @@ -0,0 +1,7 @@ +# GCP Persistent Disk (SSD via CSI driver) +persistence: + storageClass: premium-rwo +postgresql: + primary: + persistence: + storageClass: premium-rwo diff --git a/infra/values/gcp-prod/opencost-values.yaml b/infra/values/gcp-prod/opencost-values.yaml new file mode 100644 index 0000000..f3ea481 --- /dev/null +++ b/infra/values/gcp-prod/opencost-values.yaml @@ -0,0 +1,9 @@ +# GCP native pricing via Cloud Billing API +opencost: + exporter: + customPricing: + enabled: true + provider: gcp + gcp: + projectID: "" # <- populate with your GCP project ID + key: "" # <- or use Workload Identity diff --git a/infra/values/gcp-prod/traefik-values.yaml b/infra/values/gcp-prod/traefik-values.yaml new file mode 100644 index 0000000..55351c0 --- /dev/null +++ b/infra/values/gcp-prod/traefik-values.yaml @@ -0,0 +1,15 @@ +# GCP GKE — External passthrough Network Load Balancer +service: + annotations: + cloud.google.com/l4-rbs: "enabled" +ports: + web: + proxyProtocol: + trustedIPs: "10.0.0.0/8,35.191.0.0/16,130.211.0.0/22" # <- subnet CIDR + GCP health checks + forwardedHeaders: + trustedIPs: "10.0.0.0/8,35.191.0.0/16,130.211.0.0/22" + websecure: + proxyProtocol: + trustedIPs: "10.0.0.0/8,35.191.0.0/16,130.211.0.0/22" + forwardedHeaders: + trustedIPs: "10.0.0.0/8,35.191.0.0/16,130.211.0.0/22" diff --git a/infra/values/upc-dev/gitea-values.yaml b/infra/values/upc-dev/gitea-values.yaml new file mode 100644 index 0000000..ef1f8eb --- /dev/null +++ b/infra/values/upc-dev/gitea-values.yaml @@ -0,0 +1,7 @@ +# UpCloud storage class for Gitea and its embedded PostgreSQL +persistence: + storageClass: upcloud-block-storage-maxiops +postgresql: + primary: + persistence: + storageClass: upcloud-block-storage-maxiops diff --git a/infra/values/upc-dev/opencost-values.yaml b/infra/values/upc-dev/opencost-values.yaml new file mode 100644 index 0000000..06a7488 --- /dev/null +++ b/infra/values/upc-dev/opencost-values.yaml @@ -0,0 +1,15 @@ +# UpCloud custom pricing (no native OpenCost integration) +opencost: + exporter: + customPricing: + enabled: true + provider: custom + costModel: + description: "UpCloud 4-node cluster pricing" + CPU: "5.86" + RAM: "1.46" + GPU: "0" + storage: "0.34" + zoneNetworkEgress: "0" + regionNetworkEgress: "0" + internetNetworkEgress: "0" diff --git a/infra/values/upc-prod/gitea-values.yaml b/infra/values/upc-prod/gitea-values.yaml new file mode 100644 index 0000000..ef1f8eb --- /dev/null +++ b/infra/values/upc-prod/gitea-values.yaml @@ -0,0 +1,7 @@ +# UpCloud storage class for Gitea and its embedded PostgreSQL +persistence: + storageClass: upcloud-block-storage-maxiops +postgresql: + primary: + persistence: + storageClass: upcloud-block-storage-maxiops diff --git a/infra/values/upc-prod/opencost-values.yaml b/infra/values/upc-prod/opencost-values.yaml new file mode 100644 index 0000000..06a7488 --- /dev/null +++ b/infra/values/upc-prod/opencost-values.yaml @@ -0,0 +1,15 @@ +# UpCloud custom pricing (no native OpenCost integration) +opencost: + exporter: + customPricing: + enabled: true + provider: custom + costModel: + description: "UpCloud 4-node cluster pricing" + CPU: "5.86" + RAM: "1.46" + GPU: "0" + storage: "0.34" + zoneNetworkEgress: "0" + regionNetworkEgress: "0" + internetNetworkEgress: "0" diff --git a/scripts/gitea-backup-aws.sh b/scripts/gitea-backup-aws.sh new file mode 100755 index 0000000..ebf0894 --- /dev/null +++ b/scripts/gitea-backup-aws.sh @@ -0,0 +1,94 @@ +#!/usr/bin/env bash +set -euo pipefail + +# Gitea backup helper for AWS S3 +# Uses the gitea-backup-s3 secret in the gitea namespace +# (same secret schema: S3_ENDPOINT, AWS_ACCESS_KEY_ID, AWS_SECRET_ACCESS_KEY, S3_BUCKET) +# +# For AWS, S3_ENDPOINT is typically https://s3..amazonaws.com +# +# Usage: +# ./scripts/gitea-backup-aws.sh list # list all backups +# ./scripts/gitea-backup-aws.sh download # download a backup to current dir +# ./scripts/gitea-backup-aws.sh download latest # download the most recent backup + +NAMESPACE="gitea" +SECRET="gitea-backup-s3" +IMAGE="minio/mc:latest" +POD_NAME="gitea-backup-helper" +ALIAS_CMD='mc alias set s3 ${S3_ENDPOINT} ${AWS_ACCESS_KEY_ID} ${AWS_SECRET_ACCESS_KEY} > /dev/null' + +cleanup() { + kubectl -n "$NAMESPACE" delete pod "$POD_NAME" --ignore-not-found --grace-period=0 > /dev/null 2>&1 || true +} + +mc_run() { + cleanup + kubectl -n "$NAMESPACE" run "$POD_NAME" --restart=Never \ + --image="$IMAGE" \ + --overrides="{ + \"spec\":{\"containers\":[{ + \"name\":\"$POD_NAME\", + \"image\":\"$IMAGE\", + \"env\":[{\"name\":\"HOME\",\"value\":\"/tmp\"}], + \"command\":[\"sh\",\"-c\",\"${ALIAS_CMD}; $1\"], + \"envFrom\":[{\"secretRef\":{\"name\":\"$SECRET\"}}] + }]} + }" > /dev/null 2>&1 + + kubectl -n "$NAMESPACE" wait --for=jsonpath='{.status.phase}'=Succeeded "pod/$POD_NAME" --timeout=120s > /dev/null 2>&1 + kubectl -n "$NAMESPACE" logs "$POD_NAME" + cleanup +} + +case "${1:-help}" in + list) + echo "Listing backups..." + mc_run 'mc ls s3/${S3_BUCKET}/' + ;; + + download) + FILE="${2:?Usage: $0 download }" + + if [ "$FILE" = "latest" ]; then + echo "Finding latest backup..." + FILE=$(mc_run 'mc ls s3/${S3_BUCKET}/' | sort | tail -1 | awk '{print $NF}' | tr -d '[:space:]') + if [ -z "$FILE" ]; then + echo "No backups found." + exit 1 + fi + echo "Latest: $FILE" + fi + + echo "Downloading $FILE..." + cleanup + kubectl -n "$NAMESPACE" run "$POD_NAME" --restart=Never \ + --image="$IMAGE" \ + --overrides="{ + \"spec\":{\"containers\":[{ + \"name\":\"$POD_NAME\", + \"image\":\"$IMAGE\", + \"env\":[{\"name\":\"HOME\",\"value\":\"/tmp\"}], + \"command\":[\"sh\",\"-c\",\"sleep 300\"], + \"envFrom\":[{\"secretRef\":{\"name\":\"$SECRET\"}}] + }]} + }" > /dev/null 2>&1 + + kubectl -n "$NAMESPACE" wait --for=condition=Ready "pod/$POD_NAME" --timeout=60s > /dev/null 2>&1 + + echo "Saving to ./$FILE ..." + kubectl -n "$NAMESPACE" exec "$POD_NAME" -- sh -c "${ALIAS_CMD} && mc cat s3/\${S3_BUCKET}/$FILE" > "./$FILE" + cleanup + + echo "Downloaded: ./$FILE" + ;; + + *) + echo "Gitea backup helper (AWS S3)" + echo "" + echo "Usage:" + echo " $0 list List all backups in S3" + echo " $0 download Download a specific backup" + echo " $0 download latest Download the most recent backup" + ;; +esac diff --git a/scripts/gitea-backup-azure.sh b/scripts/gitea-backup-azure.sh new file mode 100755 index 0000000..e2f14d7 --- /dev/null +++ b/scripts/gitea-backup-azure.sh @@ -0,0 +1,100 @@ +#!/usr/bin/env bash +set -euo pipefail + +# Gitea backup helper for Azure Blob Storage +# Uses the gitea-backup-azure secret in the gitea namespace +# Required secret keys: +# AZURE_STORAGE_ACCOUNT — storage account name +# AZURE_STORAGE_KEY — storage account key +# AZURE_CONTAINER — blob container name +# +# Usage: +# ./scripts/gitea-backup-azure.sh list # list all backups +# ./scripts/gitea-backup-azure.sh download # download a backup +# ./scripts/gitea-backup-azure.sh download latest # download the most recent backup + +NAMESPACE="gitea" +SECRET="gitea-backup-azure" +IMAGE="mcr.microsoft.com/azure-cli:latest" +POD_NAME="gitea-backup-helper" + +cleanup() { + kubectl -n "$NAMESPACE" delete pod "$POD_NAME" --ignore-not-found --grace-period=0 > /dev/null 2>&1 || true +} + +az_run() { + cleanup + kubectl -n "$NAMESPACE" run "$POD_NAME" --restart=Never \ + --image="$IMAGE" \ + --overrides="{ + \"spec\":{\"containers\":[{ + \"name\":\"$POD_NAME\", + \"image\":\"$IMAGE\", + \"env\":[{\"name\":\"HOME\",\"value\":\"/tmp\"}], + \"command\":[\"sh\",\"-c\",\"$1\"], + \"envFrom\":[{\"secretRef\":{\"name\":\"$SECRET\"}}] + }]} + }" > /dev/null 2>&1 + + kubectl -n "$NAMESPACE" wait --for=jsonpath='{.status.phase}'=Succeeded "pod/$POD_NAME" --timeout=120s > /dev/null 2>&1 + kubectl -n "$NAMESPACE" logs "$POD_NAME" + cleanup +} + +case "${1:-help}" in + list) + echo "Listing backups..." + az_run 'az storage blob list --account-name ${AZURE_STORAGE_ACCOUNT} --account-key ${AZURE_STORAGE_KEY} --container-name ${AZURE_CONTAINER} --output table --query "[].{Name:name, Size:properties.contentLength, Modified:properties.lastModified}"' + ;; + + download) + FILE="${2:?Usage: $0 download }" + + if [ "$FILE" = "latest" ]; then + echo "Finding latest backup..." + FILE=$(az_run 'az storage blob list --account-name ${AZURE_STORAGE_ACCOUNT} --account-key ${AZURE_STORAGE_KEY} --container-name ${AZURE_CONTAINER} --query "sort_by([], &properties.lastModified)[-1].name" -o tsv' | tr -d '[:space:]') + if [ -z "$FILE" ]; then + echo "No backups found." + exit 1 + fi + echo "Latest: $FILE" + fi + + echo "Downloading $FILE..." + cleanup + kubectl -n "$NAMESPACE" run "$POD_NAME" --restart=Never \ + --image="$IMAGE" \ + --overrides="{ + \"spec\":{\"containers\":[{ + \"name\":\"$POD_NAME\", + \"image\":\"$IMAGE\", + \"env\":[{\"name\":\"HOME\",\"value\":\"/tmp\"}], + \"command\":[\"sh\",\"-c\",\"sleep 300\"], + \"envFrom\":[{\"secretRef\":{\"name\":\"$SECRET\"}}] + }]} + }" > /dev/null 2>&1 + + kubectl -n "$NAMESPACE" wait --for=condition=Ready "pod/$POD_NAME" --timeout=60s > /dev/null 2>&1 + + echo "Saving to ./$FILE ..." + kubectl -n "$NAMESPACE" exec "$POD_NAME" -- \ + az storage blob download \ + --account-name "\${AZURE_STORAGE_ACCOUNT}" \ + --account-key "\${AZURE_STORAGE_KEY}" \ + --container-name "\${AZURE_CONTAINER}" \ + --name "$FILE" \ + --file /dev/stdout 2>/dev/null > "./$FILE" + cleanup + + echo "Downloaded: ./$FILE" + ;; + + *) + echo "Gitea backup helper (Azure Blob Storage)" + echo "" + echo "Usage:" + echo " $0 list List all backups in Azure Blob" + echo " $0 download Download a specific backup" + echo " $0 download latest Download the most recent backup" + ;; +esac diff --git a/scripts/gitea-backup-gcp.sh b/scripts/gitea-backup-gcp.sh new file mode 100755 index 0000000..54fb7ef --- /dev/null +++ b/scripts/gitea-backup-gcp.sh @@ -0,0 +1,95 @@ +#!/usr/bin/env bash +set -euo pipefail + +# Gitea backup helper for Google Cloud Storage +# Uses the gitea-backup-gcs secret in the gitea namespace +# Required secret keys: +# GCS_BUCKET — bucket name (without gs:// prefix) +# GOOGLE_APPLICATION_CREDENTIALS_JSON — service account key JSON +# (alternatively, use Workload Identity and omit the key) +# +# Usage: +# ./scripts/gitea-backup-gcp.sh list # list all backups +# ./scripts/gitea-backup-gcp.sh download # download a backup +# ./scripts/gitea-backup-gcp.sh download latest # download the most recent backup + +NAMESPACE="gitea" +SECRET="gitea-backup-gcs" +IMAGE="gcr.io/google.com/cloudsdktool/google-cloud-cli:slim" +POD_NAME="gitea-backup-helper" +AUTH_CMD='if [ -n "${GOOGLE_APPLICATION_CREDENTIALS_JSON:-}" ]; then echo "${GOOGLE_APPLICATION_CREDENTIALS_JSON}" > /tmp/gcs-key.json && gcloud auth activate-service-account --key-file=/tmp/gcs-key.json > /dev/null 2>&1; fi' + +cleanup() { + kubectl -n "$NAMESPACE" delete pod "$POD_NAME" --ignore-not-found --grace-period=0 > /dev/null 2>&1 || true +} + +gcs_run() { + cleanup + kubectl -n "$NAMESPACE" run "$POD_NAME" --restart=Never \ + --image="$IMAGE" \ + --overrides="{ + \"spec\":{\"containers\":[{ + \"name\":\"$POD_NAME\", + \"image\":\"$IMAGE\", + \"env\":[{\"name\":\"HOME\",\"value\":\"/tmp\"}], + \"command\":[\"sh\",\"-c\",\"${AUTH_CMD}; $1\"], + \"envFrom\":[{\"secretRef\":{\"name\":\"$SECRET\"}}] + }]} + }" > /dev/null 2>&1 + + kubectl -n "$NAMESPACE" wait --for=jsonpath='{.status.phase}'=Succeeded "pod/$POD_NAME" --timeout=120s > /dev/null 2>&1 + kubectl -n "$NAMESPACE" logs "$POD_NAME" + cleanup +} + +case "${1:-help}" in + list) + echo "Listing backups..." + gcs_run 'gsutil ls -l gs://${GCS_BUCKET}/' + ;; + + download) + FILE="${2:?Usage: $0 download }" + + if [ "$FILE" = "latest" ]; then + echo "Finding latest backup..." + FILE=$(gcs_run 'gsutil ls gs://${GCS_BUCKET}/' | grep -v '^$' | grep -v 'TOTAL' | sort | tail -1 | xargs -I{} basename {} | tr -d '[:space:]') + if [ -z "$FILE" ]; then + echo "No backups found." + exit 1 + fi + echo "Latest: $FILE" + fi + + echo "Downloading $FILE..." + cleanup + kubectl -n "$NAMESPACE" run "$POD_NAME" --restart=Never \ + --image="$IMAGE" \ + --overrides="{ + \"spec\":{\"containers\":[{ + \"name\":\"$POD_NAME\", + \"image\":\"$IMAGE\", + \"env\":[{\"name\":\"HOME\",\"value\":\"/tmp\"}], + \"command\":[\"sh\",\"-c\",\"sleep 300\"], + \"envFrom\":[{\"secretRef\":{\"name\":\"$SECRET\"}}] + }]} + }" > /dev/null 2>&1 + + kubectl -n "$NAMESPACE" wait --for=condition=Ready "pod/$POD_NAME" --timeout=60s > /dev/null 2>&1 + + echo "Saving to ./$FILE ..." + kubectl -n "$NAMESPACE" exec "$POD_NAME" -- sh -c "${AUTH_CMD} && gsutil cat gs://\${GCS_BUCKET}/$FILE" > "./$FILE" + cleanup + + echo "Downloaded: ./$FILE" + ;; + + *) + echo "Gitea backup helper (Google Cloud Storage)" + echo "" + echo "Usage:" + echo " $0 list List all backups in GCS" + echo " $0 download Download a specific backup" + echo " $0 download latest Download the most recent backup" + ;; +esac -- 2.49.1 From e0bdaab4223209955dd07c385b3c1f421c36da93 Mon Sep 17 00:00:00 2001 From: Danijel Simeunovic Date: Wed, 22 Apr 2026 13:34:48 +0200 Subject: [PATCH 02/15] multi-cloud + mcp --- cluster-resources/gitea-backup-cronjob.yaml | 6 +- docs/REFERENCE.md | 119 ++++++++++++++++++-- infra/base/gitea.yaml | 1 + infra/base/opencost.yaml | 1 + infra/overlays/upc-prod/kustomization.yaml | 18 +++ infra/values/base/gitea-values.yaml | 2 - infra/values/base/opencost-values.yaml | 12 -- infra/values/upc-dev/gitea-values.yaml | 7 ++ infra/values/upc-dev/opencost-values.yaml | 15 +++ infra/values/upc-prod/gitea-values.yaml | 7 ++ infra/values/upc-prod/opencost-values.yaml | 15 +++ scripts/backup/aws-s3.sh | 23 ++++ scripts/backup/azure-blob.sh | 36 ++++++ scripts/backup/gcp-gcs.sh | 26 +++++ scripts/backup/s3-minio.sh | 20 ++++ scripts/gitea-backup.sh | 8 +- 16 files changed, 286 insertions(+), 30 deletions(-) create mode 100644 infra/values/upc-dev/gitea-values.yaml create mode 100644 infra/values/upc-dev/opencost-values.yaml create mode 100644 infra/values/upc-prod/gitea-values.yaml create mode 100644 infra/values/upc-prod/opencost-values.yaml create mode 100644 scripts/backup/aws-s3.sh create mode 100644 scripts/backup/azure-blob.sh create mode 100644 scripts/backup/gcp-gcs.sh create mode 100644 scripts/backup/s3-minio.sh diff --git a/cluster-resources/gitea-backup-cronjob.yaml b/cluster-resources/gitea-backup-cronjob.yaml index d05ec17..e8a6fa4 100644 --- a/cluster-resources/gitea-backup-cronjob.yaml +++ b/cluster-resources/gitea-backup-cronjob.yaml @@ -57,17 +57,17 @@ spec: - sh - -c - | - mc alias set upcloud "${S3_ENDPOINT}" "${AWS_ACCESS_KEY_ID}" "${AWS_SECRET_ACCESS_KEY}" + mc alias set s3 "${S3_ENDPOINT}" "${AWS_ACCESS_KEY_ID}" "${AWS_SECRET_ACCESS_KEY}" TIMESTAMP=$(date +%Y%m%d-%H%M%S) KEY="gitea-dump-${TIMESTAMP}.zip" echo "Uploading ${KEY}..." - mc cp /backup/gitea-dump.zip "upcloud/${S3_BUCKET}/${KEY}" && \ + mc cp /backup/gitea-dump.zip "s3/${S3_BUCKET}/${KEY}" && \ echo "Upload complete." # Prune backups older than 7 days echo "Pruning backups older than 7 days..." - mc rm --older-than 7d --force "upcloud/${S3_BUCKET}/" 2>&1 || true + mc rm --older-than 7d --force "s3/${S3_BUCKET}/" 2>&1 || true echo "Pruning complete." envFrom: - secretRef: diff --git a/docs/REFERENCE.md b/docs/REFERENCE.md index 0ba2013..4bab669 100644 --- a/docs/REFERENCE.md +++ b/docs/REFERENCE.md @@ -9,6 +9,7 @@ - [Kyverno Policies](#kyverno-policies) - [Configuration Reference](#configuration-reference) - [API Endpoints](#api-endpoints) +- [Cloud Overlay Pattern](#cloud-overlay-pattern) - [Glossary](#glossary) --- @@ -92,16 +93,34 @@ launchpad/ │ ├── sealedsecrets.yaml │ ├── secrets.yaml │ ├── renovate.yaml +│ ├── base/ # ArgoCD Application manifests (Kustomize base) +│ │ ├── gitea.yaml +│ │ ├── opencost.yaml +│ │ ├── traefik-application.yaml +│ │ ├── keycloak.yaml +│ │ ├── grafana.yaml +│ │ └── ... +│ ├── overlays/ +│ │ └── upc-prod/ +│ │ └── kustomization.yaml # Patches upc-dev → upc-prod valueFile paths │ └── values/ -│ ├── argocd-values.yaml -│ ├── prometheus-values.yaml -│ ├── grafana-values.yaml -│ ├── loki-values.yaml -│ ├── tempo-values.yaml -│ ├── gitea-values.yaml -│ ├── gitea-actions-values.yaml -│ ├── fluent-bit-values.yaml -│ └── renovate-values.yaml +│ ├── base/ # Cloud-agnostic Helm values +│ │ ├── gitea-values.yaml +│ │ ├── opencost-values.yaml +│ │ ├── prometheus-values.yaml +│ │ └── ... +│ ├── upc-dev/ # UpCloud dev overlay values +│ │ ├── traefik-values.yaml +│ │ ├── keycloak-values.yaml +│ │ ├── grafana-values.yaml +│ │ ├── gitea-values.yaml +│ │ └── opencost-values.yaml +│ └── upc-prod/ # UpCloud prod overlay values +│ ├── traefik-values.yaml +│ ├── keycloak-values.yaml +│ ├── grafana-values.yaml +│ ├── gitea-values.yaml +│ └── opencost-values.yaml │ ├── apps/ # Business applications │ ├── mcp10x.yaml @@ -135,6 +154,15 @@ launchpad/ │ ├── mcp10x-credentials-sealed.yaml │ └── musicman-credentials.yaml │ +├── scripts/ # Operational helper scripts +│ ├── gitea-backup.sh # S3 backup helper (list/download) +│ ├── gitea-restore.sh +│ └── backup/ # Per-cloud backup reference scripts +│ ├── s3-minio.sh # S3-compatible (UpCloud, MinIO, Wasabi) +│ ├── aws-s3.sh # Native AWS S3 +│ ├── azure-blob.sh # Azure Blob Storage +│ └── gcp-gcs.sh # GCP Cloud Storage +│ ├── private/ # Local-only (Git-ignored) │ ├── *.yaml │ └── *.sh @@ -1621,6 +1649,79 @@ POST /loki/api/v1/push --- +## Cloud Overlay Pattern + +### Overview + +Cloud-specific configuration (StorageClass, LoadBalancer annotations, pricing models, etc.) lives in per-cloud overlay value files, **not** in `base/`. This means adding a new cloud provider (AKS, EKS, GKE) only requires a new overlay directory — no base changes. + +### How It Works + +Each ArgoCD Application uses **multi-source Helm values** with two value files: + +```yaml +# infra/base/gitea.yaml (example) +helm: + valueFiles: + - $values/infra/values/base/gitea-values.yaml # [0] cloud-agnostic + - $values/infra/values/upc-dev/gitea-values.yaml # [1] cloud-specific (default: upc-dev) +``` + +The `upc-prod` Kustomize overlay patches index `[1]` to swap the cloud-specific file: + +```yaml +# infra/overlays/upc-prod/kustomization.yaml +- target: + kind: Application + name: gitea + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/upc-prod/gitea-values.yaml +``` + +### Components Using Cloud Overlays + +| Component | Cloud-specific config | Overlay value file | +|-----------|----------------------|-------------------| +| **Traefik** | LB annotations, proxy protocol IPs | `traefik-values.yaml` | +| **Keycloak** | Hostname, TLS settings | `keycloak-values.yaml` | +| **Grafana** | Hostname, datasource URLs | `grafana-values.yaml` | +| **Gitea** | StorageClass (persistence + PostgreSQL) | `gitea-values.yaml` | +| **OpenCost** | Custom pricing model (CPU/RAM/storage rates) | `opencost-values.yaml` | + +### Backup CronJob + +The `gitea-backup` CronJob uses a generic `s3` alias for `minio/mc`. The actual endpoint and credentials come from the `gitea-backup-s3` Sealed Secret, which is per-cloud. Reference scripts for different cloud providers are in `scripts/backup/`: + +| Script | Provider | Tool | +|--------|----------|------| +| `s3-minio.sh` | S3-compatible (UpCloud, MinIO, Wasabi) | `minio/mc` | +| `aws-s3.sh` | AWS S3 | `aws` CLI | +| `azure-blob.sh` | Azure Blob Storage | `az` CLI | +| `gcp-gcs.sh` | GCP Cloud Storage | `gsutil` | + +### Adding a New Cloud Provider + +To add support for a new cloud (e.g., `aks-dev`): + +1. **Create overlay value directory**: `infra/values/aks-dev/` +2. **Add cloud-specific value files** for each component that needs one: + - `traefik-values.yaml` — LB annotations, proxy protocol config + - `keycloak-values.yaml` — hostname/TLS if different + - `grafana-values.yaml` — hostname/datasources if different + - `gitea-values.yaml` — `storageClass` for persistence + PostgreSQL + - `opencost-values.yaml` — `customPricing` cost model for your cloud +3. **Create a Kustomize overlay** (if needed): `infra/overlays/aks-prod/kustomization.yaml` + - Patch each Application's `valueFiles[1]` to point to `aks-prod/` files +4. **Create a root Application**: `_app-of-apps-aks-dev.yaml` pointing to the overlay +5. **Create Sealed Secrets** for the new cluster: + - `secrets/aks-dev/` — TLS certs, credentials, backup S3 config +6. **Update `gitea-backup-s3` secret** with the new cloud's S3-compatible endpoint +7. **Bootstrap**: `kubectl apply -f _app-of-apps-aks-dev.yaml -n argocd` + +--- + ## Glossary ### Terms diff --git a/infra/base/gitea.yaml b/infra/base/gitea.yaml index ba806f5..cc4f60f 100644 --- a/infra/base/gitea.yaml +++ b/infra/base/gitea.yaml @@ -22,6 +22,7 @@ spec: releaseName: gitea valueFiles: - $values/infra/values/base/gitea-values.yaml + - $values/infra/values/upc-dev/gitea-values.yaml - repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD diff --git a/infra/base/opencost.yaml b/infra/base/opencost.yaml index 6984f3b..a102906 100644 --- a/infra/base/opencost.yaml +++ b/infra/base/opencost.yaml @@ -22,6 +22,7 @@ spec: releaseName: opencost valueFiles: - $values/infra/values/base/opencost-values.yaml + - $values/infra/values/upc-dev/opencost-values.yaml - repoURL: git@github.com:fortedigital/sturdy-adventure.git targetRevision: HEAD diff --git a/infra/overlays/upc-prod/kustomization.yaml b/infra/overlays/upc-prod/kustomization.yaml index ebfc179..9242d39 100644 --- a/infra/overlays/upc-prod/kustomization.yaml +++ b/infra/overlays/upc-prod/kustomization.yaml @@ -31,6 +31,24 @@ patches: path: /spec/sources/0/helm/valueFiles/1 value: $values/infra/values/upc-prod/grafana-values.yaml +# Gitea: swap upc-dev → upc-prod +- target: + kind: Application + name: gitea + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/upc-prod/gitea-values.yaml + +# OpenCost: swap upc-dev → upc-prod +- target: + kind: Application + name: opencost + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/upc-prod/opencost-values.yaml + # Secrets: change path to upc-prod - target: kind: Application diff --git a/infra/values/base/gitea-values.yaml b/infra/values/base/gitea-values.yaml index 2153b89..635ae37 100644 --- a/infra/values/base/gitea-values.yaml +++ b/infra/values/base/gitea-values.yaml @@ -130,7 +130,6 @@ persistence: size: 10Gi accessModes: - ReadWriteOnce - storageClass: upcloud-block-storage-maxiops # -- Recreate strategy to avoid Multi-Attach errors with RWO volumes strategy: @@ -156,7 +155,6 @@ postgresql: persistence: enabled: true size: 8Gi - storageClass: upcloud-block-storage-maxiops resources: requests: cpu: 100m diff --git a/infra/values/base/opencost-values.yaml b/infra/values/base/opencost-values.yaml index 39d73cc..1b97209 100644 --- a/infra/values/base/opencost-values.yaml +++ b/infra/values/base/opencost-values.yaml @@ -10,18 +10,6 @@ opencost: serviceName: prometheus-server namespaceName: monitoring port: 80 - customPricing: - enabled: true - provider: custom - costModel: - description: "UpCloud 4-node cluster pricing" - CPU: "5.86" - RAM: "1.46" - GPU: "0" - storage: "0.34" - zoneNetworkEgress: "0" - regionNetworkEgress: "0" - internetNetworkEgress: "0" ui: enabled: false service: diff --git a/infra/values/upc-dev/gitea-values.yaml b/infra/values/upc-dev/gitea-values.yaml new file mode 100644 index 0000000..151047f --- /dev/null +++ b/infra/values/upc-dev/gitea-values.yaml @@ -0,0 +1,7 @@ +# UpCloud-specific: block storage class for Gitea + PostgreSQL +persistence: + storageClass: upcloud-block-storage-maxiops +postgresql: + primary: + persistence: + storageClass: upcloud-block-storage-maxiops diff --git a/infra/values/upc-dev/opencost-values.yaml b/infra/values/upc-dev/opencost-values.yaml new file mode 100644 index 0000000..51fd0a4 --- /dev/null +++ b/infra/values/upc-dev/opencost-values.yaml @@ -0,0 +1,15 @@ +# UpCloud-specific: custom pricing model +opencost: + exporter: + customPricing: + enabled: true + provider: custom + costModel: + description: "UpCloud 4-node cluster pricing" + CPU: "5.86" + RAM: "1.46" + GPU: "0" + storage: "0.34" + zoneNetworkEgress: "0" + regionNetworkEgress: "0" + internetNetworkEgress: "0" diff --git a/infra/values/upc-prod/gitea-values.yaml b/infra/values/upc-prod/gitea-values.yaml new file mode 100644 index 0000000..151047f --- /dev/null +++ b/infra/values/upc-prod/gitea-values.yaml @@ -0,0 +1,7 @@ +# UpCloud-specific: block storage class for Gitea + PostgreSQL +persistence: + storageClass: upcloud-block-storage-maxiops +postgresql: + primary: + persistence: + storageClass: upcloud-block-storage-maxiops diff --git a/infra/values/upc-prod/opencost-values.yaml b/infra/values/upc-prod/opencost-values.yaml new file mode 100644 index 0000000..51fd0a4 --- /dev/null +++ b/infra/values/upc-prod/opencost-values.yaml @@ -0,0 +1,15 @@ +# UpCloud-specific: custom pricing model +opencost: + exporter: + customPricing: + enabled: true + provider: custom + costModel: + description: "UpCloud 4-node cluster pricing" + CPU: "5.86" + RAM: "1.46" + GPU: "0" + storage: "0.34" + zoneNetworkEgress: "0" + regionNetworkEgress: "0" + internetNetworkEgress: "0" diff --git a/scripts/backup/aws-s3.sh b/scripts/backup/aws-s3.sh new file mode 100644 index 0000000..679245b --- /dev/null +++ b/scripts/backup/aws-s3.sh @@ -0,0 +1,23 @@ +#!/usr/bin/env bash +set -euo pipefail +# AWS S3 backup upload (native AWS CLI) +# Uses: aws cli v2 +# Env: AWS_ACCESS_KEY_ID, AWS_SECRET_ACCESS_KEY, AWS_DEFAULT_REGION, S3_BUCKET + +BACKUP_FILE="${1:?Usage: $0 }" +TIMESTAMP=$(date +%Y%m%d-%H%M%S) +KEY="gitea-dump-${TIMESTAMP}.zip" + +echo "Uploading ${KEY}..." +aws s3 cp "$BACKUP_FILE" "s3://${S3_BUCKET}/${KEY}" +echo "Upload complete." + +# Prune backups older than 7 days +echo "Pruning backups older than 7 days..." +CUTOFF=$(date -d '7 days ago' +%Y-%m-%dT%H:%M:%S 2>/dev/null || date -v-7d +%Y-%m-%dT%H:%M:%S) +aws s3api list-objects-v2 --bucket "${S3_BUCKET}" --query "Contents[?LastModified<'${CUTOFF}'].Key" --output text \ + | tr '\t' '\n' \ + | while read -r key; do + [ -n "$key" ] && aws s3 rm "s3://${S3_BUCKET}/${key}" && echo "Deleted: ${key}" + done +echo "Pruning complete." diff --git a/scripts/backup/azure-blob.sh b/scripts/backup/azure-blob.sh new file mode 100644 index 0000000..bb095ab --- /dev/null +++ b/scripts/backup/azure-blob.sh @@ -0,0 +1,36 @@ +#!/usr/bin/env bash +set -euo pipefail +# Azure Blob Storage backup upload +# Uses: az cli +# Env: AZURE_STORAGE_ACCOUNT, AZURE_STORAGE_KEY, AZURE_CONTAINER + +BACKUP_FILE="${1:?Usage: $0 }" +TIMESTAMP=$(date +%Y%m%d-%H%M%S) +KEY="gitea-dump-${TIMESTAMP}.zip" + +echo "Uploading ${KEY}..." +az storage blob upload \ + --account-name "${AZURE_STORAGE_ACCOUNT}" \ + --account-key "${AZURE_STORAGE_KEY}" \ + --container-name "${AZURE_CONTAINER}" \ + --name "${KEY}" \ + --file "$BACKUP_FILE" \ + --overwrite +echo "Upload complete." + +# Prune backups older than 7 days +echo "Pruning backups older than 7 days..." +CUTOFF=$(date -d '7 days ago' +%Y-%m-%dT%H:%M:%SZ 2>/dev/null || date -v-7d +%Y-%m-%dT%H:%M:%SZ) +az storage blob list \ + --account-name "${AZURE_STORAGE_ACCOUNT}" \ + --account-key "${AZURE_STORAGE_KEY}" \ + --container-name "${AZURE_CONTAINER}" \ + --query "[?properties.lastModified<'${CUTOFF}'].name" -o tsv \ + | while read -r name; do + [ -n "$name" ] && az storage blob delete \ + --account-name "${AZURE_STORAGE_ACCOUNT}" \ + --account-key "${AZURE_STORAGE_KEY}" \ + --container-name "${AZURE_CONTAINER}" \ + --name "$name" && echo "Deleted: ${name}" + done +echo "Pruning complete." diff --git a/scripts/backup/gcp-gcs.sh b/scripts/backup/gcp-gcs.sh new file mode 100644 index 0000000..7e9ed60 --- /dev/null +++ b/scripts/backup/gcp-gcs.sh @@ -0,0 +1,26 @@ +#!/usr/bin/env bash +set -euo pipefail +# GCP Cloud Storage backup upload +# Uses: gsutil (gcloud SDK) +# Env: GCS_BUCKET (e.g. gs://my-bucket) + +BACKUP_FILE="${1:?Usage: $0 }" +TIMESTAMP=$(date +%Y%m%d-%H%M%S) +KEY="gitea-dump-${TIMESTAMP}.zip" + +echo "Uploading ${KEY}..." +gsutil cp "$BACKUP_FILE" "${GCS_BUCKET}/${KEY}" +echo "Upload complete." + +# Prune backups older than 7 days — GCS lifecycle rules are preferred, +# but this works as a manual fallback +echo "Pruning backups older than 7 days..." +CUTOFF=$(date -d '7 days ago' +%Y-%m-%dT%H:%M:%SZ 2>/dev/null || date -v-7d +%Y-%m-%dT%H:%M:%SZ) +gsutil ls -l "${GCS_BUCKET}/" \ + | grep 'gitea-dump-' \ + | while read -r size date name; do + if [[ "$date" < "$CUTOFF" ]]; then + gsutil rm "$name" && echo "Deleted: ${name}" + fi + done +echo "Pruning complete." diff --git a/scripts/backup/s3-minio.sh b/scripts/backup/s3-minio.sh new file mode 100644 index 0000000..fb73537 --- /dev/null +++ b/scripts/backup/s3-minio.sh @@ -0,0 +1,20 @@ +#!/usr/bin/env bash +set -euo pipefail +# S3-compatible backup upload (UpCloud Objects, MinIO, Wasabi, etc.) +# Uses: minio/mc +# Env: S3_ENDPOINT, AWS_ACCESS_KEY_ID, AWS_SECRET_ACCESS_KEY, S3_BUCKET + +BACKUP_FILE="${1:?Usage: $0 }" +TIMESTAMP=$(date +%Y%m%d-%H%M%S) +KEY="gitea-dump-${TIMESTAMP}.zip" + +mc alias set s3 "${S3_ENDPOINT}" "${AWS_ACCESS_KEY_ID}" "${AWS_SECRET_ACCESS_KEY}" + +echo "Uploading ${KEY}..." +mc cp "$BACKUP_FILE" "s3/${S3_BUCKET}/${KEY}" +echo "Upload complete." + +# Prune backups older than 7 days +echo "Pruning backups older than 7 days..." +mc rm --older-than 7d --force "s3/${S3_BUCKET}/" 2>&1 || true +echo "Pruning complete." diff --git a/scripts/gitea-backup.sh b/scripts/gitea-backup.sh index 397a6fa..9d6cdb0 100644 --- a/scripts/gitea-backup.sh +++ b/scripts/gitea-backup.sh @@ -13,7 +13,7 @@ NAMESPACE="gitea" SECRET="gitea-backup-s3" IMAGE="minio/mc:latest" POD_NAME="gitea-backup-helper" -ALIAS_CMD='mc alias set upcloud ${S3_ENDPOINT} ${AWS_ACCESS_KEY_ID} ${AWS_SECRET_ACCESS_KEY} > /dev/null' +ALIAS_CMD='mc alias set s3 ${S3_ENDPOINT} ${AWS_ACCESS_KEY_ID} ${AWS_SECRET_ACCESS_KEY} > /dev/null' cleanup() { kubectl -n "$NAMESPACE" delete pod "$POD_NAME" --ignore-not-found --grace-period=0 > /dev/null 2>&1 || true @@ -41,7 +41,7 @@ mc_run() { case "${1:-help}" in list) echo "Listing backups..." - mc_run 'mc ls upcloud/${S3_BUCKET}/' + mc_run 'mc ls s3/${S3_BUCKET}/' ;; download) @@ -49,7 +49,7 @@ case "${1:-help}" in if [ "$FILE" = "latest" ]; then echo "Finding latest backup..." - FILE=$(mc_run 'mc ls upcloud/${S3_BUCKET}/' | sort | tail -1 | awk '{print $NF}' | tr -d '[:space:]') + FILE=$(mc_run 'mc ls s3/${S3_BUCKET}/' | sort | tail -1 | awk '{print $NF}' | tr -d '[:space:]') if [ -z "$FILE" ]; then echo "No backups found." exit 1 @@ -74,7 +74,7 @@ case "${1:-help}" in kubectl -n "$NAMESPACE" wait --for=condition=Ready "pod/$POD_NAME" --timeout=60s > /dev/null 2>&1 echo "Saving to ./$FILE ..." - kubectl -n "$NAMESPACE" exec "$POD_NAME" -- sh -c "${ALIAS_CMD} && mc cat upcloud/\${S3_BUCKET}/$FILE" > "./$FILE" + kubectl -n "$NAMESPACE" exec "$POD_NAME" -- sh -c "${ALIAS_CMD} && mc cat s3/\${S3_BUCKET}/$FILE" > "./$FILE" cleanup echo "Downloaded: ./$FILE" -- 2.49.1 From 4e6a84785a8dd0a6352372a40a65d6afcda6a7cd Mon Sep 17 00:00:00 2001 From: Danijel Simeunovic Date: Wed, 22 Apr 2026 13:37:32 +0200 Subject: [PATCH 03/15] token --- .gitea/workflows/ai-review.yaml | 1 + 1 file changed, 1 insertion(+) diff --git a/.gitea/workflows/ai-review.yaml b/.gitea/workflows/ai-review.yaml index 808bb33..178a0ad 100644 --- a/.gitea/workflows/ai-review.yaml +++ b/.gitea/workflows/ai-review.yaml @@ -34,6 +34,7 @@ jobs: with: submodules: true fetch-depth: 0 + token: ${{ secrets.AI_REVIEW_TOKEN }} - name: Run inline review uses: docker://nikitafilonov/ai-review:v0.64.0 -- 2.49.1 From 4144b1c1ac1f2500ba7bff386982adbd1efab483 Mon Sep 17 00:00:00 2001 From: Danijel Simeunovic Date: Wed, 22 Apr 2026 13:39:43 +0200 Subject: [PATCH 04/15] token --- .gitea/workflows/ai-review.yaml | 1 + 1 file changed, 1 insertion(+) diff --git a/.gitea/workflows/ai-review.yaml b/.gitea/workflows/ai-review.yaml index 808bb33..178a0ad 100644 --- a/.gitea/workflows/ai-review.yaml +++ b/.gitea/workflows/ai-review.yaml @@ -34,6 +34,7 @@ jobs: with: submodules: true fetch-depth: 0 + token: ${{ secrets.AI_REVIEW_TOKEN }} - name: Run inline review uses: docker://nikitafilonov/ai-review:v0.64.0 -- 2.49.1 From 333acdea260787235e213574b993000ae5571408 Mon Sep 17 00:00:00 2001 From: Danijel Simeunovic Date: Wed, 22 Apr 2026 14:30:13 +0200 Subject: [PATCH 05/15] multi-cloud overlays --- _app-of-apps-aks-dev.yaml | 32 ++++++++++ _app-of-apps-aks-prod.yaml | 32 ++++++++++ _app-of-apps-eks-dev.yaml | 32 ++++++++++ _app-of-apps-eks-prod.yaml | 32 ++++++++++ _app-of-apps-gke-dev.yaml | 32 ++++++++++ _app-of-apps-gke-prod.yaml | 32 ++++++++++ bootstrap.sh | 2 +- clusters/aks-dev.yaml | 10 ++++ clusters/aks-prod.yaml | 10 ++++ clusters/eks-dev.yaml | 10 ++++ clusters/eks-prod.yaml | 10 ++++ clusters/gke-dev.yaml | 10 ++++ clusters/gke-prod.yaml | 10 ++++ docs/REFERENCE.md | 42 +++++++------ infra/overlays/aks-dev/kustomization.yaml | 68 ++++++++++++++++++++++ infra/overlays/aks-prod/kustomization.yaml | 68 ++++++++++++++++++++++ infra/overlays/eks-dev/kustomization.yaml | 68 ++++++++++++++++++++++ infra/overlays/eks-prod/kustomization.yaml | 68 ++++++++++++++++++++++ infra/overlays/gke-dev/kustomization.yaml | 68 ++++++++++++++++++++++ infra/overlays/gke-prod/kustomization.yaml | 68 ++++++++++++++++++++++ infra/values/aks-dev/gitea-values.yaml | 7 +++ infra/values/aks-dev/grafana-values.yaml | 4 ++ infra/values/aks-dev/keycloak-values.yaml | 3 + infra/values/aks-dev/opencost-values.yaml | 8 +++ infra/values/aks-dev/traefik-values.yaml | 11 ++++ infra/values/aks-prod/gitea-values.yaml | 7 +++ infra/values/aks-prod/grafana-values.yaml | 4 ++ infra/values/aks-prod/keycloak-values.yaml | 3 + infra/values/aks-prod/opencost-values.yaml | 8 +++ infra/values/aks-prod/traefik-values.yaml | 12 ++++ infra/values/eks-dev/gitea-values.yaml | 7 +++ infra/values/eks-dev/grafana-values.yaml | 4 ++ infra/values/eks-dev/keycloak-values.yaml | 3 + infra/values/eks-dev/opencost-values.yaml | 11 ++++ infra/values/eks-dev/traefik-values.yaml | 17 ++++++ infra/values/eks-prod/gitea-values.yaml | 7 +++ infra/values/eks-prod/grafana-values.yaml | 4 ++ infra/values/eks-prod/keycloak-values.yaml | 3 + infra/values/eks-prod/opencost-values.yaml | 11 ++++ infra/values/eks-prod/traefik-values.yaml | 18 ++++++ infra/values/gke-dev/gitea-values.yaml | 7 +++ infra/values/gke-dev/grafana-values.yaml | 4 ++ infra/values/gke-dev/keycloak-values.yaml | 3 + infra/values/gke-dev/opencost-values.yaml | 10 ++++ infra/values/gke-dev/traefik-values.yaml | 12 ++++ infra/values/gke-prod/gitea-values.yaml | 7 +++ infra/values/gke-prod/grafana-values.yaml | 4 ++ infra/values/gke-prod/keycloak-values.yaml | 3 + infra/values/gke-prod/opencost-values.yaml | 10 ++++ infra/values/gke-prod/traefik-values.yaml | 12 ++++ 50 files changed, 910 insertions(+), 18 deletions(-) create mode 100644 _app-of-apps-aks-dev.yaml create mode 100644 _app-of-apps-aks-prod.yaml create mode 100644 _app-of-apps-eks-dev.yaml create mode 100644 _app-of-apps-eks-prod.yaml create mode 100644 _app-of-apps-gke-dev.yaml create mode 100644 _app-of-apps-gke-prod.yaml create mode 100644 clusters/aks-dev.yaml create mode 100644 clusters/aks-prod.yaml create mode 100644 clusters/eks-dev.yaml create mode 100644 clusters/eks-prod.yaml create mode 100644 clusters/gke-dev.yaml create mode 100644 clusters/gke-prod.yaml create mode 100644 infra/overlays/aks-dev/kustomization.yaml create mode 100644 infra/overlays/aks-prod/kustomization.yaml create mode 100644 infra/overlays/eks-dev/kustomization.yaml create mode 100644 infra/overlays/eks-prod/kustomization.yaml create mode 100644 infra/overlays/gke-dev/kustomization.yaml create mode 100644 infra/overlays/gke-prod/kustomization.yaml create mode 100644 infra/values/aks-dev/gitea-values.yaml create mode 100644 infra/values/aks-dev/grafana-values.yaml create mode 100644 infra/values/aks-dev/keycloak-values.yaml create mode 100644 infra/values/aks-dev/opencost-values.yaml create mode 100644 infra/values/aks-dev/traefik-values.yaml create mode 100644 infra/values/aks-prod/gitea-values.yaml create mode 100644 infra/values/aks-prod/grafana-values.yaml create mode 100644 infra/values/aks-prod/keycloak-values.yaml create mode 100644 infra/values/aks-prod/opencost-values.yaml create mode 100644 infra/values/aks-prod/traefik-values.yaml create mode 100644 infra/values/eks-dev/gitea-values.yaml create mode 100644 infra/values/eks-dev/grafana-values.yaml create mode 100644 infra/values/eks-dev/keycloak-values.yaml create mode 100644 infra/values/eks-dev/opencost-values.yaml create mode 100644 infra/values/eks-dev/traefik-values.yaml create mode 100644 infra/values/eks-prod/gitea-values.yaml create mode 100644 infra/values/eks-prod/grafana-values.yaml create mode 100644 infra/values/eks-prod/keycloak-values.yaml create mode 100644 infra/values/eks-prod/opencost-values.yaml create mode 100644 infra/values/eks-prod/traefik-values.yaml create mode 100644 infra/values/gke-dev/gitea-values.yaml create mode 100644 infra/values/gke-dev/grafana-values.yaml create mode 100644 infra/values/gke-dev/keycloak-values.yaml create mode 100644 infra/values/gke-dev/opencost-values.yaml create mode 100644 infra/values/gke-dev/traefik-values.yaml create mode 100644 infra/values/gke-prod/gitea-values.yaml create mode 100644 infra/values/gke-prod/grafana-values.yaml create mode 100644 infra/values/gke-prod/keycloak-values.yaml create mode 100644 infra/values/gke-prod/opencost-values.yaml create mode 100644 infra/values/gke-prod/traefik-values.yaml diff --git a/_app-of-apps-aks-dev.yaml b/_app-of-apps-aks-dev.yaml new file mode 100644 index 0000000..9547bfe --- /dev/null +++ b/_app-of-apps-aks-dev.yaml @@ -0,0 +1,32 @@ +apiVersion: v1 +kind: Namespace +metadata: + name: monitoring + annotations: + argocd.argoproj.io/sync-wave: "-1" +--- +apiVersion: argoproj.io/v1alpha1 +kind: Application +metadata: + name: infrastructure-apps + namespace: argocd + labels: + app.kubernetes.io/name: infrastructure-apps + app.kubernetes.io/part-of: platform + finalizers: + - resources-finalizer.argocd.argoproj.io +spec: + project: default + source: + repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git + targetRevision: HEAD + path: infra/overlays/aks-dev + destination: + server: https://kubernetes.default.svc + namespace: default + syncPolicy: + automated: + prune: true + selfHeal: true + syncOptions: + - CreateNamespace=true diff --git a/_app-of-apps-aks-prod.yaml b/_app-of-apps-aks-prod.yaml new file mode 100644 index 0000000..6d945ac --- /dev/null +++ b/_app-of-apps-aks-prod.yaml @@ -0,0 +1,32 @@ +apiVersion: v1 +kind: Namespace +metadata: + name: monitoring + annotations: + argocd.argoproj.io/sync-wave: "-1" +--- +apiVersion: argoproj.io/v1alpha1 +kind: Application +metadata: + name: infrastructure-apps + namespace: argocd + labels: + app.kubernetes.io/name: infrastructure-apps + app.kubernetes.io/part-of: platform + finalizers: + - resources-finalizer.argocd.argoproj.io +spec: + project: default + source: + repoURL: git@github.com:fortedigital/sturdy-adventure.git + targetRevision: HEAD + path: infra/overlays/aks-prod + destination: + server: https://kubernetes.default.svc + namespace: default + syncPolicy: + automated: + prune: true + selfHeal: true + syncOptions: + - CreateNamespace=true diff --git a/_app-of-apps-eks-dev.yaml b/_app-of-apps-eks-dev.yaml new file mode 100644 index 0000000..f40e164 --- /dev/null +++ b/_app-of-apps-eks-dev.yaml @@ -0,0 +1,32 @@ +apiVersion: v1 +kind: Namespace +metadata: + name: monitoring + annotations: + argocd.argoproj.io/sync-wave: "-1" +--- +apiVersion: argoproj.io/v1alpha1 +kind: Application +metadata: + name: infrastructure-apps + namespace: argocd + labels: + app.kubernetes.io/name: infrastructure-apps + app.kubernetes.io/part-of: platform + finalizers: + - resources-finalizer.argocd.argoproj.io +spec: + project: default + source: + repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git + targetRevision: HEAD + path: infra/overlays/eks-dev + destination: + server: https://kubernetes.default.svc + namespace: default + syncPolicy: + automated: + prune: true + selfHeal: true + syncOptions: + - CreateNamespace=true diff --git a/_app-of-apps-eks-prod.yaml b/_app-of-apps-eks-prod.yaml new file mode 100644 index 0000000..1e51d04 --- /dev/null +++ b/_app-of-apps-eks-prod.yaml @@ -0,0 +1,32 @@ +apiVersion: v1 +kind: Namespace +metadata: + name: monitoring + annotations: + argocd.argoproj.io/sync-wave: "-1" +--- +apiVersion: argoproj.io/v1alpha1 +kind: Application +metadata: + name: infrastructure-apps + namespace: argocd + labels: + app.kubernetes.io/name: infrastructure-apps + app.kubernetes.io/part-of: platform + finalizers: + - resources-finalizer.argocd.argoproj.io +spec: + project: default + source: + repoURL: git@github.com:fortedigital/sturdy-adventure.git + targetRevision: HEAD + path: infra/overlays/eks-prod + destination: + server: https://kubernetes.default.svc + namespace: default + syncPolicy: + automated: + prune: true + selfHeal: true + syncOptions: + - CreateNamespace=true diff --git a/_app-of-apps-gke-dev.yaml b/_app-of-apps-gke-dev.yaml new file mode 100644 index 0000000..faf753c --- /dev/null +++ b/_app-of-apps-gke-dev.yaml @@ -0,0 +1,32 @@ +apiVersion: v1 +kind: Namespace +metadata: + name: monitoring + annotations: + argocd.argoproj.io/sync-wave: "-1" +--- +apiVersion: argoproj.io/v1alpha1 +kind: Application +metadata: + name: infrastructure-apps + namespace: argocd + labels: + app.kubernetes.io/name: infrastructure-apps + app.kubernetes.io/part-of: platform + finalizers: + - resources-finalizer.argocd.argoproj.io +spec: + project: default + source: + repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git + targetRevision: HEAD + path: infra/overlays/gke-dev + destination: + server: https://kubernetes.default.svc + namespace: default + syncPolicy: + automated: + prune: true + selfHeal: true + syncOptions: + - CreateNamespace=true diff --git a/_app-of-apps-gke-prod.yaml b/_app-of-apps-gke-prod.yaml new file mode 100644 index 0000000..8c6fc27 --- /dev/null +++ b/_app-of-apps-gke-prod.yaml @@ -0,0 +1,32 @@ +apiVersion: v1 +kind: Namespace +metadata: + name: monitoring + annotations: + argocd.argoproj.io/sync-wave: "-1" +--- +apiVersion: argoproj.io/v1alpha1 +kind: Application +metadata: + name: infrastructure-apps + namespace: argocd + labels: + app.kubernetes.io/name: infrastructure-apps + app.kubernetes.io/part-of: platform + finalizers: + - resources-finalizer.argocd.argoproj.io +spec: + project: default + source: + repoURL: git@github.com:fortedigital/sturdy-adventure.git + targetRevision: HEAD + path: infra/overlays/gke-prod + destination: + server: https://kubernetes.default.svc + namespace: default + syncPolicy: + automated: + prune: true + selfHeal: true + syncOptions: + - CreateNamespace=true diff --git a/bootstrap.sh b/bootstrap.sh index 2265d6b..6c1170a 100644 --- a/bootstrap.sh +++ b/bootstrap.sh @@ -2,7 +2,7 @@ # in case of $'\r': command not found error, run command below first # sed -i 's/\r$//' ./bootstrap.sh -CLUSTER="${1:?Usage: ./bootstrap.sh (upc-dev|upc-prod)}" +CLUSTER="${1:?Usage: ./bootstrap.sh (upc-dev|upc-prod|aks-dev|aks-prod|eks-dev|eks-prod|gke-dev|gke-prod)}" echo "running $0 for cluster: ${CLUSTER}..." diff --git a/clusters/aks-dev.yaml b/clusters/aks-dev.yaml new file mode 100644 index 0000000..db86d2b --- /dev/null +++ b/clusters/aks-dev.yaml @@ -0,0 +1,10 @@ +clusterName: dev-fd-aks +domain: forteapps.net +argocdDomain: argocd.127.0.0.1.nip.io +grafanaDomain: grafana.forteapps.net +keycloakDomain: id.forteapps.net +dotaiDomain: kubemcp.forteapps.net +dotaiUiDomain: kubemcpui.forteapps.net +letsencryptEmail: danijels@gmail.com +trustedIPs: "10.0.0.0/8" +cloudProvider: azure diff --git a/clusters/aks-prod.yaml b/clusters/aks-prod.yaml new file mode 100644 index 0000000..d230b08 --- /dev/null +++ b/clusters/aks-prod.yaml @@ -0,0 +1,10 @@ +clusterName: prod-fd-aks +domain: fortedigital.com +argocdDomain: argocd.127.0.0.1.nip.io +grafanaDomain: grafana.fortedigital.com +keycloakDomain: id.fortedigital.com +dotaiDomain: kubemcp.fortedigital.com +dotaiUiDomain: kubemcpui.fortedigital.com +letsencryptEmail: danijel.simeunovic@fortedigital.com +trustedIPs: "10.0.0.0/8" +cloudProvider: azure diff --git a/clusters/eks-dev.yaml b/clusters/eks-dev.yaml new file mode 100644 index 0000000..e822b84 --- /dev/null +++ b/clusters/eks-dev.yaml @@ -0,0 +1,10 @@ +clusterName: dev-fd-eks +domain: forteapps.net +argocdDomain: argocd.127.0.0.1.nip.io +grafanaDomain: grafana.forteapps.net +keycloakDomain: id.forteapps.net +dotaiDomain: kubemcp.forteapps.net +dotaiUiDomain: kubemcpui.forteapps.net +letsencryptEmail: danijels@gmail.com +trustedIPs: "10.0.0.0/8" +cloudProvider: aws diff --git a/clusters/eks-prod.yaml b/clusters/eks-prod.yaml new file mode 100644 index 0000000..dd5cc83 --- /dev/null +++ b/clusters/eks-prod.yaml @@ -0,0 +1,10 @@ +clusterName: prod-fd-eks +domain: fortedigital.com +argocdDomain: argocd.127.0.0.1.nip.io +grafanaDomain: grafana.fortedigital.com +keycloakDomain: id.fortedigital.com +dotaiDomain: kubemcp.fortedigital.com +dotaiUiDomain: kubemcpui.fortedigital.com +letsencryptEmail: danijel.simeunovic@fortedigital.com +trustedIPs: "10.0.0.0/8" +cloudProvider: aws diff --git a/clusters/gke-dev.yaml b/clusters/gke-dev.yaml new file mode 100644 index 0000000..fd5afd5 --- /dev/null +++ b/clusters/gke-dev.yaml @@ -0,0 +1,10 @@ +clusterName: dev-fd-gke +domain: forteapps.net +argocdDomain: argocd.127.0.0.1.nip.io +grafanaDomain: grafana.forteapps.net +keycloakDomain: id.forteapps.net +dotaiDomain: kubemcp.forteapps.net +dotaiUiDomain: kubemcpui.forteapps.net +letsencryptEmail: danijels@gmail.com +trustedIPs: "10.0.0.0/8" +cloudProvider: gcp diff --git a/clusters/gke-prod.yaml b/clusters/gke-prod.yaml new file mode 100644 index 0000000..9c6751d --- /dev/null +++ b/clusters/gke-prod.yaml @@ -0,0 +1,10 @@ +clusterName: prod-fd-gke +domain: fortedigital.com +argocdDomain: argocd.127.0.0.1.nip.io +grafanaDomain: grafana.fortedigital.com +keycloakDomain: id.fortedigital.com +dotaiDomain: kubemcp.fortedigital.com +dotaiUiDomain: kubemcpui.fortedigital.com +letsencryptEmail: danijel.simeunovic@fortedigital.com +trustedIPs: "10.0.0.0/8" +cloudProvider: gcp diff --git a/docs/REFERENCE.md b/docs/REFERENCE.md index 4bab669..74645c2 100644 --- a/docs/REFERENCE.md +++ b/docs/REFERENCE.md @@ -20,9 +20,9 @@ | Component | Value | |-----------|-------| -| **Provider** | UpCloud Managed Kubernetes | -| **Environment** | Production (internal use) | -| **Cluster Count** | Multi-cluster (upc-dev, upc-prod) | +| **Provider** | Multi-cloud (UpCloud, AKS, EKS, GKE) | +| **Environment** | Dev + Production per cloud | +| **Cluster Count** | Multi-cluster (upc-dev/prod, aks-dev/prod, eks-dev/prod, gke-dev/prod) | | **GitOps Tool** | ArgoCD | | **Ingress Controller** | Traefik v2 | | **Certificate Management** | Cert-Manager + Let's Encrypt | @@ -1653,7 +1653,18 @@ POST /loki/api/v1/push ### Overview -Cloud-specific configuration (StorageClass, LoadBalancer annotations, pricing models, etc.) lives in per-cloud overlay value files, **not** in `base/`. This means adding a new cloud provider (AKS, EKS, GKE) only requires a new overlay directory — no base changes. +Cloud-specific configuration (StorageClass, LoadBalancer annotations, pricing models, etc.) lives in per-cloud overlay value files, **not** in `base/`. Adding a new cloud provider only requires a new overlay directory — no base changes. + +### Supported Clouds + +| Cloud | Dev overlay | Prod overlay | StorageClass | LB type | +|-------|-----------|-------------|-------------|---------| +| **UpCloud** | `upc-dev` | `upc-prod` | `upcloud-block-storage-maxiops` | UpCloud LB (proxy protocol v2) | +| **Azure AKS** | `aks-dev` | `aks-prod` | `managed-csi-premium` | Azure LB | +| **AWS EKS** | `eks-dev` | `eks-prod` | `gp3` | AWS NLB (proxy protocol) | +| **GCP GKE** | `gke-dev` | `gke-prod` | `premium-rwo` | GCP NEG | + +Bootstrap any cluster with: `./bootstrap.sh ` (e.g., `./bootstrap.sh aks-dev`) ### How It Works @@ -1703,22 +1714,19 @@ The `gitea-backup` CronJob uses a generic `s3` alias for `minio/mc`. The actual ### Adding a New Cloud Provider -To add support for a new cloud (e.g., `aks-dev`): +To add support for a new cloud (e.g., `oci-dev` for Oracle Cloud): -1. **Create overlay value directory**: `infra/values/aks-dev/` -2. **Add cloud-specific value files** for each component that needs one: +1. **Cluster config**: `clusters/oci-dev.yaml` — clusterName, domain, trustedIPs, cloudProvider +2. **Overlay value files** in `infra/values/oci-dev/`: - `traefik-values.yaml` — LB annotations, proxy protocol config - - `keycloak-values.yaml` — hostname/TLS if different - - `grafana-values.yaml` — hostname/datasources if different + - `keycloak-values.yaml` — hostname + - `grafana-values.yaml` — hostname - `gitea-values.yaml` — `storageClass` for persistence + PostgreSQL - - `opencost-values.yaml` — `customPricing` cost model for your cloud -3. **Create a Kustomize overlay** (if needed): `infra/overlays/aks-prod/kustomization.yaml` - - Patch each Application's `valueFiles[1]` to point to `aks-prod/` files -4. **Create a root Application**: `_app-of-apps-aks-dev.yaml` pointing to the overlay -5. **Create Sealed Secrets** for the new cluster: - - `secrets/aks-dev/` — TLS certs, credentials, backup S3 config -6. **Update `gitea-backup-s3` secret** with the new cloud's S3-compatible endpoint -7. **Bootstrap**: `kubectl apply -f _app-of-apps-aks-dev.yaml -n argocd` + - `opencost-values.yaml` — pricing model or cloud billing integration +3. **Kustomize overlay**: `infra/overlays/oci-dev/kustomization.yaml` — patch `valueFiles[1]` for each Application +4. **App-of-apps**: `_app-of-apps-oci-dev.yaml` — points to `infra/overlays/oci-dev` +5. **Sealed Secrets**: `secrets/oci-dev/` — TLS certs, credentials, backup S3 config +6. **Bootstrap**: `./bootstrap.sh oci-dev` --- diff --git a/infra/overlays/aks-dev/kustomization.yaml b/infra/overlays/aks-dev/kustomization.yaml new file mode 100644 index 0000000..185869f --- /dev/null +++ b/infra/overlays/aks-dev/kustomization.yaml @@ -0,0 +1,68 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: +- ../../base + +patches: +# Traefik: swap upc-dev → aks-dev +- target: + kind: Application + name: traefik + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/aks-dev/traefik-values.yaml + +# Keycloak: swap upc-dev → aks-dev +- target: + kind: Application + name: keycloak + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/aks-dev/keycloak-values.yaml + +# Grafana: swap upc-dev → aks-dev +- target: + kind: Application + name: grafana + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/aks-dev/grafana-values.yaml + +# Gitea: swap upc-dev → aks-dev +- target: + kind: Application + name: gitea + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/aks-dev/gitea-values.yaml + +# OpenCost: swap upc-dev → aks-dev +- target: + kind: Application + name: opencost + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/aks-dev/opencost-values.yaml + +# Secrets: change path to aks-dev +- target: + kind: Application + name: secrets + patch: | + - op: replace + path: /spec/source/path + value: secrets/aks-dev + +# Enterprise-apps: point to aks-dev overlay +- target: + kind: Application + name: enterprise-apps + patch: | + - op: replace + path: /spec/source/path + value: apps/overlays/aks-dev diff --git a/infra/overlays/aks-prod/kustomization.yaml b/infra/overlays/aks-prod/kustomization.yaml new file mode 100644 index 0000000..73b0aaa --- /dev/null +++ b/infra/overlays/aks-prod/kustomization.yaml @@ -0,0 +1,68 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: +- ../../base + +patches: +# Traefik: swap upc-dev → aks-prod +- target: + kind: Application + name: traefik + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/aks-prod/traefik-values.yaml + +# Keycloak: swap upc-dev → aks-prod +- target: + kind: Application + name: keycloak + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/aks-prod/keycloak-values.yaml + +# Grafana: swap upc-dev → aks-prod +- target: + kind: Application + name: grafana + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/aks-prod/grafana-values.yaml + +# Gitea: swap upc-dev → aks-prod +- target: + kind: Application + name: gitea + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/aks-prod/gitea-values.yaml + +# OpenCost: swap upc-dev → aks-prod +- target: + kind: Application + name: opencost + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/aks-prod/opencost-values.yaml + +# Secrets: change path to aks-prod +- target: + kind: Application + name: secrets + patch: | + - op: replace + path: /spec/source/path + value: secrets/aks-prod + +# Enterprise-apps: point to aks-prod overlay +- target: + kind: Application + name: enterprise-apps + patch: | + - op: replace + path: /spec/source/path + value: apps/overlays/aks-prod diff --git a/infra/overlays/eks-dev/kustomization.yaml b/infra/overlays/eks-dev/kustomization.yaml new file mode 100644 index 0000000..16e542a --- /dev/null +++ b/infra/overlays/eks-dev/kustomization.yaml @@ -0,0 +1,68 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: +- ../../base + +patches: +# Traefik: swap upc-dev → eks-dev +- target: + kind: Application + name: traefik + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/eks-dev/traefik-values.yaml + +# Keycloak: swap upc-dev → eks-dev +- target: + kind: Application + name: keycloak + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/eks-dev/keycloak-values.yaml + +# Grafana: swap upc-dev → eks-dev +- target: + kind: Application + name: grafana + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/eks-dev/grafana-values.yaml + +# Gitea: swap upc-dev → eks-dev +- target: + kind: Application + name: gitea + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/eks-dev/gitea-values.yaml + +# OpenCost: swap upc-dev → eks-dev +- target: + kind: Application + name: opencost + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/eks-dev/opencost-values.yaml + +# Secrets: change path to eks-dev +- target: + kind: Application + name: secrets + patch: | + - op: replace + path: /spec/source/path + value: secrets/eks-dev + +# Enterprise-apps: point to eks-dev overlay +- target: + kind: Application + name: enterprise-apps + patch: | + - op: replace + path: /spec/source/path + value: apps/overlays/eks-dev diff --git a/infra/overlays/eks-prod/kustomization.yaml b/infra/overlays/eks-prod/kustomization.yaml new file mode 100644 index 0000000..46be9a9 --- /dev/null +++ b/infra/overlays/eks-prod/kustomization.yaml @@ -0,0 +1,68 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: +- ../../base + +patches: +# Traefik: swap upc-dev → eks-prod +- target: + kind: Application + name: traefik + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/eks-prod/traefik-values.yaml + +# Keycloak: swap upc-dev → eks-prod +- target: + kind: Application + name: keycloak + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/eks-prod/keycloak-values.yaml + +# Grafana: swap upc-dev → eks-prod +- target: + kind: Application + name: grafana + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/eks-prod/grafana-values.yaml + +# Gitea: swap upc-dev → eks-prod +- target: + kind: Application + name: gitea + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/eks-prod/gitea-values.yaml + +# OpenCost: swap upc-dev → eks-prod +- target: + kind: Application + name: opencost + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/eks-prod/opencost-values.yaml + +# Secrets: change path to eks-prod +- target: + kind: Application + name: secrets + patch: | + - op: replace + path: /spec/source/path + value: secrets/eks-prod + +# Enterprise-apps: point to eks-prod overlay +- target: + kind: Application + name: enterprise-apps + patch: | + - op: replace + path: /spec/source/path + value: apps/overlays/eks-prod diff --git a/infra/overlays/gke-dev/kustomization.yaml b/infra/overlays/gke-dev/kustomization.yaml new file mode 100644 index 0000000..4d3da3e --- /dev/null +++ b/infra/overlays/gke-dev/kustomization.yaml @@ -0,0 +1,68 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: +- ../../base + +patches: +# Traefik: swap upc-dev → gke-dev +- target: + kind: Application + name: traefik + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/gke-dev/traefik-values.yaml + +# Keycloak: swap upc-dev → gke-dev +- target: + kind: Application + name: keycloak + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/gke-dev/keycloak-values.yaml + +# Grafana: swap upc-dev → gke-dev +- target: + kind: Application + name: grafana + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/gke-dev/grafana-values.yaml + +# Gitea: swap upc-dev → gke-dev +- target: + kind: Application + name: gitea + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/gke-dev/gitea-values.yaml + +# OpenCost: swap upc-dev → gke-dev +- target: + kind: Application + name: opencost + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/gke-dev/opencost-values.yaml + +# Secrets: change path to gke-dev +- target: + kind: Application + name: secrets + patch: | + - op: replace + path: /spec/source/path + value: secrets/gke-dev + +# Enterprise-apps: point to gke-dev overlay +- target: + kind: Application + name: enterprise-apps + patch: | + - op: replace + path: /spec/source/path + value: apps/overlays/gke-dev diff --git a/infra/overlays/gke-prod/kustomization.yaml b/infra/overlays/gke-prod/kustomization.yaml new file mode 100644 index 0000000..0f4a583 --- /dev/null +++ b/infra/overlays/gke-prod/kustomization.yaml @@ -0,0 +1,68 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: +- ../../base + +patches: +# Traefik: swap upc-dev → gke-prod +- target: + kind: Application + name: traefik + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/gke-prod/traefik-values.yaml + +# Keycloak: swap upc-dev → gke-prod +- target: + kind: Application + name: keycloak + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/gke-prod/keycloak-values.yaml + +# Grafana: swap upc-dev → gke-prod +- target: + kind: Application + name: grafana + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/gke-prod/grafana-values.yaml + +# Gitea: swap upc-dev → gke-prod +- target: + kind: Application + name: gitea + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/gke-prod/gitea-values.yaml + +# OpenCost: swap upc-dev → gke-prod +- target: + kind: Application + name: opencost + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/gke-prod/opencost-values.yaml + +# Secrets: change path to gke-prod +- target: + kind: Application + name: secrets + patch: | + - op: replace + path: /spec/source/path + value: secrets/gke-prod + +# Enterprise-apps: point to gke-prod overlay +- target: + kind: Application + name: enterprise-apps + patch: | + - op: replace + path: /spec/source/path + value: apps/overlays/gke-prod diff --git a/infra/values/aks-dev/gitea-values.yaml b/infra/values/aks-dev/gitea-values.yaml new file mode 100644 index 0000000..94e9760 --- /dev/null +++ b/infra/values/aks-dev/gitea-values.yaml @@ -0,0 +1,7 @@ +# AKS-specific: Azure managed disk storage class +persistence: + storageClass: managed-csi-premium +postgresql: + primary: + persistence: + storageClass: managed-csi-premium diff --git a/infra/values/aks-dev/grafana-values.yaml b/infra/values/aks-dev/grafana-values.yaml new file mode 100644 index 0000000..3b10135 --- /dev/null +++ b/infra/values/aks-dev/grafana-values.yaml @@ -0,0 +1,4 @@ +# AKS-specific: Grafana hostname +ingress: + hosts: + - grafana.forteapps.net diff --git a/infra/values/aks-dev/keycloak-values.yaml b/infra/values/aks-dev/keycloak-values.yaml new file mode 100644 index 0000000..f66b945 --- /dev/null +++ b/infra/values/aks-dev/keycloak-values.yaml @@ -0,0 +1,3 @@ +# AKS-specific: Keycloak hostname +ingress: + hostname: id.forteapps.net diff --git a/infra/values/aks-dev/opencost-values.yaml b/infra/values/aks-dev/opencost-values.yaml new file mode 100644 index 0000000..64dcfa1 --- /dev/null +++ b/infra/values/aks-dev/opencost-values.yaml @@ -0,0 +1,8 @@ +# AKS-specific: Azure pricing via Cloud Billing API +opencost: + exporter: + cloudProviderApiKey: "" + customPricing: + enabled: false + azure: + secretName: opencost-azure-billing diff --git a/infra/values/aks-dev/traefik-values.yaml b/infra/values/aks-dev/traefik-values.yaml new file mode 100644 index 0000000..fd5c882 --- /dev/null +++ b/infra/values/aks-dev/traefik-values.yaml @@ -0,0 +1,11 @@ +# AKS-specific: Azure Load Balancer for Traefik +service: + annotations: + service.beta.kubernetes.io/azure-load-balancer-health-probe-request-path: /ping +ports: + web: + forwardedHeaders: + trustedIPs: "10.0.0.0/8" + websecure: + forwardedHeaders: + trustedIPs: "10.0.0.0/8" diff --git a/infra/values/aks-prod/gitea-values.yaml b/infra/values/aks-prod/gitea-values.yaml new file mode 100644 index 0000000..d035b5d --- /dev/null +++ b/infra/values/aks-prod/gitea-values.yaml @@ -0,0 +1,7 @@ +# AKS-specific: Azure managed disk storage class (prod) +persistence: + storageClass: managed-csi-premium +postgresql: + primary: + persistence: + storageClass: managed-csi-premium diff --git a/infra/values/aks-prod/grafana-values.yaml b/infra/values/aks-prod/grafana-values.yaml new file mode 100644 index 0000000..b1f7504 --- /dev/null +++ b/infra/values/aks-prod/grafana-values.yaml @@ -0,0 +1,4 @@ +# AKS-specific: Grafana hostname (prod) +ingress: + hosts: + - grafana.fortedigital.com diff --git a/infra/values/aks-prod/keycloak-values.yaml b/infra/values/aks-prod/keycloak-values.yaml new file mode 100644 index 0000000..97096e4 --- /dev/null +++ b/infra/values/aks-prod/keycloak-values.yaml @@ -0,0 +1,3 @@ +# AKS-specific: Keycloak hostname (prod) +ingress: + hostname: id.fortedigital.com diff --git a/infra/values/aks-prod/opencost-values.yaml b/infra/values/aks-prod/opencost-values.yaml new file mode 100644 index 0000000..d465129 --- /dev/null +++ b/infra/values/aks-prod/opencost-values.yaml @@ -0,0 +1,8 @@ +# AKS-specific: Azure pricing via Cloud Billing API (prod) +opencost: + exporter: + cloudProviderApiKey: "" + customPricing: + enabled: false + azure: + secretName: opencost-azure-billing diff --git a/infra/values/aks-prod/traefik-values.yaml b/infra/values/aks-prod/traefik-values.yaml new file mode 100644 index 0000000..469f276 --- /dev/null +++ b/infra/values/aks-prod/traefik-values.yaml @@ -0,0 +1,12 @@ +# AKS-specific: Azure Load Balancer for Traefik (prod) +service: + annotations: + service.beta.kubernetes.io/azure-load-balancer-health-probe-request-path: /ping + service.beta.kubernetes.io/azure-load-balancer-internal: "false" +ports: + web: + forwardedHeaders: + trustedIPs: "10.0.0.0/8" + websecure: + forwardedHeaders: + trustedIPs: "10.0.0.0/8" diff --git a/infra/values/eks-dev/gitea-values.yaml b/infra/values/eks-dev/gitea-values.yaml new file mode 100644 index 0000000..c55964f --- /dev/null +++ b/infra/values/eks-dev/gitea-values.yaml @@ -0,0 +1,7 @@ +# EKS-specific: gp3 storage class +persistence: + storageClass: gp3 +postgresql: + primary: + persistence: + storageClass: gp3 diff --git a/infra/values/eks-dev/grafana-values.yaml b/infra/values/eks-dev/grafana-values.yaml new file mode 100644 index 0000000..e5d932e --- /dev/null +++ b/infra/values/eks-dev/grafana-values.yaml @@ -0,0 +1,4 @@ +# EKS-specific: Grafana hostname +ingress: + hosts: + - grafana.forteapps.net diff --git a/infra/values/eks-dev/keycloak-values.yaml b/infra/values/eks-dev/keycloak-values.yaml new file mode 100644 index 0000000..ee027eb --- /dev/null +++ b/infra/values/eks-dev/keycloak-values.yaml @@ -0,0 +1,3 @@ +# EKS-specific: Keycloak hostname +ingress: + hostname: id.forteapps.net diff --git a/infra/values/eks-dev/opencost-values.yaml b/infra/values/eks-dev/opencost-values.yaml new file mode 100644 index 0000000..efd110a --- /dev/null +++ b/infra/values/eks-dev/opencost-values.yaml @@ -0,0 +1,11 @@ +# EKS-specific: AWS pricing via Cost and Usage Report +opencost: + exporter: + cloudProviderApiKey: "" + customPricing: + enabled: false + aws: + spot_data_region: "" + spot_data_bucket: "" + spot_data_prefix: "" + account_id: "" diff --git a/infra/values/eks-dev/traefik-values.yaml b/infra/values/eks-dev/traefik-values.yaml new file mode 100644 index 0000000..1390d17 --- /dev/null +++ b/infra/values/eks-dev/traefik-values.yaml @@ -0,0 +1,17 @@ +# EKS-specific: AWS NLB for Traefik +service: + annotations: + service.beta.kubernetes.io/aws-load-balancer-type: nlb + service.beta.kubernetes.io/aws-load-balancer-scheme: internet-facing + service.beta.kubernetes.io/aws-load-balancer-proxy-protocol: "*" +ports: + web: + proxyProtocol: + trustedIPs: "10.0.0.0/8" + forwardedHeaders: + trustedIPs: "10.0.0.0/8" + websecure: + proxyProtocol: + trustedIPs: "10.0.0.0/8" + forwardedHeaders: + trustedIPs: "10.0.0.0/8" diff --git a/infra/values/eks-prod/gitea-values.yaml b/infra/values/eks-prod/gitea-values.yaml new file mode 100644 index 0000000..7aae415 --- /dev/null +++ b/infra/values/eks-prod/gitea-values.yaml @@ -0,0 +1,7 @@ +# EKS-specific: gp3 storage class (prod) +persistence: + storageClass: gp3 +postgresql: + primary: + persistence: + storageClass: gp3 diff --git a/infra/values/eks-prod/grafana-values.yaml b/infra/values/eks-prod/grafana-values.yaml new file mode 100644 index 0000000..2034392 --- /dev/null +++ b/infra/values/eks-prod/grafana-values.yaml @@ -0,0 +1,4 @@ +# EKS-specific: Grafana hostname (prod) +ingress: + hosts: + - grafana.fortedigital.com diff --git a/infra/values/eks-prod/keycloak-values.yaml b/infra/values/eks-prod/keycloak-values.yaml new file mode 100644 index 0000000..9797896 --- /dev/null +++ b/infra/values/eks-prod/keycloak-values.yaml @@ -0,0 +1,3 @@ +# EKS-specific: Keycloak hostname (prod) +ingress: + hostname: id.fortedigital.com diff --git a/infra/values/eks-prod/opencost-values.yaml b/infra/values/eks-prod/opencost-values.yaml new file mode 100644 index 0000000..ac86a76 --- /dev/null +++ b/infra/values/eks-prod/opencost-values.yaml @@ -0,0 +1,11 @@ +# EKS-specific: AWS pricing via Cost and Usage Report (prod) +opencost: + exporter: + cloudProviderApiKey: "" + customPricing: + enabled: false + aws: + spot_data_region: "" + spot_data_bucket: "" + spot_data_prefix: "" + account_id: "" diff --git a/infra/values/eks-prod/traefik-values.yaml b/infra/values/eks-prod/traefik-values.yaml new file mode 100644 index 0000000..fd64496 --- /dev/null +++ b/infra/values/eks-prod/traefik-values.yaml @@ -0,0 +1,18 @@ +# EKS-specific: AWS NLB for Traefik (prod) +service: + annotations: + service.beta.kubernetes.io/aws-load-balancer-type: nlb + service.beta.kubernetes.io/aws-load-balancer-scheme: internet-facing + service.beta.kubernetes.io/aws-load-balancer-proxy-protocol: "*" + service.beta.kubernetes.io/aws-load-balancer-cross-zone-load-balancing-enabled: "true" +ports: + web: + proxyProtocol: + trustedIPs: "10.0.0.0/8" + forwardedHeaders: + trustedIPs: "10.0.0.0/8" + websecure: + proxyProtocol: + trustedIPs: "10.0.0.0/8" + forwardedHeaders: + trustedIPs: "10.0.0.0/8" diff --git a/infra/values/gke-dev/gitea-values.yaml b/infra/values/gke-dev/gitea-values.yaml new file mode 100644 index 0000000..04ec9aa --- /dev/null +++ b/infra/values/gke-dev/gitea-values.yaml @@ -0,0 +1,7 @@ +# GKE-specific: SSD persistent disk storage class +persistence: + storageClass: premium-rwo +postgresql: + primary: + persistence: + storageClass: premium-rwo diff --git a/infra/values/gke-dev/grafana-values.yaml b/infra/values/gke-dev/grafana-values.yaml new file mode 100644 index 0000000..db36770 --- /dev/null +++ b/infra/values/gke-dev/grafana-values.yaml @@ -0,0 +1,4 @@ +# GKE-specific: Grafana hostname +ingress: + hosts: + - grafana.forteapps.net diff --git a/infra/values/gke-dev/keycloak-values.yaml b/infra/values/gke-dev/keycloak-values.yaml new file mode 100644 index 0000000..4c67591 --- /dev/null +++ b/infra/values/gke-dev/keycloak-values.yaml @@ -0,0 +1,3 @@ +# GKE-specific: Keycloak hostname +ingress: + hostname: id.forteapps.net diff --git a/infra/values/gke-dev/opencost-values.yaml b/infra/values/gke-dev/opencost-values.yaml new file mode 100644 index 0000000..6534718 --- /dev/null +++ b/infra/values/gke-dev/opencost-values.yaml @@ -0,0 +1,10 @@ +# GKE-specific: GCP pricing via BigQuery billing export +opencost: + exporter: + cloudProviderApiKey: "" + customPricing: + enabled: false + google: + key: "" + project_id: "" + billing_account: "" diff --git a/infra/values/gke-dev/traefik-values.yaml b/infra/values/gke-dev/traefik-values.yaml new file mode 100644 index 0000000..96a78ab --- /dev/null +++ b/infra/values/gke-dev/traefik-values.yaml @@ -0,0 +1,12 @@ +# GKE-specific: Google Cloud Load Balancer for Traefik +service: + annotations: + cloud.google.com/neg: '{"ingress":true}' + networking.gke.io/load-balancer-type: External +ports: + web: + forwardedHeaders: + trustedIPs: "10.0.0.0/8" + websecure: + forwardedHeaders: + trustedIPs: "10.0.0.0/8" diff --git a/infra/values/gke-prod/gitea-values.yaml b/infra/values/gke-prod/gitea-values.yaml new file mode 100644 index 0000000..5df877a --- /dev/null +++ b/infra/values/gke-prod/gitea-values.yaml @@ -0,0 +1,7 @@ +# GKE-specific: SSD persistent disk storage class (prod) +persistence: + storageClass: premium-rwo +postgresql: + primary: + persistence: + storageClass: premium-rwo diff --git a/infra/values/gke-prod/grafana-values.yaml b/infra/values/gke-prod/grafana-values.yaml new file mode 100644 index 0000000..e0b0d37 --- /dev/null +++ b/infra/values/gke-prod/grafana-values.yaml @@ -0,0 +1,4 @@ +# GKE-specific: Grafana hostname (prod) +ingress: + hosts: + - grafana.fortedigital.com diff --git a/infra/values/gke-prod/keycloak-values.yaml b/infra/values/gke-prod/keycloak-values.yaml new file mode 100644 index 0000000..76ab384 --- /dev/null +++ b/infra/values/gke-prod/keycloak-values.yaml @@ -0,0 +1,3 @@ +# GKE-specific: Keycloak hostname (prod) +ingress: + hostname: id.fortedigital.com diff --git a/infra/values/gke-prod/opencost-values.yaml b/infra/values/gke-prod/opencost-values.yaml new file mode 100644 index 0000000..404f49b --- /dev/null +++ b/infra/values/gke-prod/opencost-values.yaml @@ -0,0 +1,10 @@ +# GKE-specific: GCP pricing via BigQuery billing export (prod) +opencost: + exporter: + cloudProviderApiKey: "" + customPricing: + enabled: false + google: + key: "" + project_id: "" + billing_account: "" diff --git a/infra/values/gke-prod/traefik-values.yaml b/infra/values/gke-prod/traefik-values.yaml new file mode 100644 index 0000000..7d70c40 --- /dev/null +++ b/infra/values/gke-prod/traefik-values.yaml @@ -0,0 +1,12 @@ +# GKE-specific: Google Cloud Load Balancer for Traefik (prod) +service: + annotations: + cloud.google.com/neg: '{"ingress":true}' + networking.gke.io/load-balancer-type: External +ports: + web: + forwardedHeaders: + trustedIPs: "10.0.0.0/8" + websecure: + forwardedHeaders: + trustedIPs: "10.0.0.0/8" -- 2.49.1 From dea54e469e8ab46436f9147fe0a677512016f1b9 Mon Sep 17 00:00:00 2001 From: Danijel Simeunovic Date: Wed, 22 Apr 2026 14:34:20 +0200 Subject: [PATCH 06/15] repo url --- _app-of-apps-aws-dev.yaml | 2 +- _app-of-apps-aws-prod.yaml | 2 +- _app-of-apps-azure-dev.yaml | 2 +- _app-of-apps-azure-prod.yaml | 2 +- _app-of-apps-gcp-dev.yaml | 2 +- _app-of-apps-gcp-prod.yaml | 2 +- _app-of-apps-upc-prod.yaml | 2 +- apps/base/dot-ai-stack.yaml | 2 +- infra/base/opencost.yaml | 2 +- infra/base/traefik-application.yaml | 2 +- 10 files changed, 10 insertions(+), 10 deletions(-) diff --git a/_app-of-apps-aws-dev.yaml b/_app-of-apps-aws-dev.yaml index 061d19b..fa364c8 100644 --- a/_app-of-apps-aws-dev.yaml +++ b/_app-of-apps-aws-dev.yaml @@ -18,7 +18,7 @@ metadata: spec: project: default source: - repoURL: git@github.com:fortedigital/sturdy-adventure.git + repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD path: infra/overlays/aws-dev destination: diff --git a/_app-of-apps-aws-prod.yaml b/_app-of-apps-aws-prod.yaml index 62fd689..9922276 100644 --- a/_app-of-apps-aws-prod.yaml +++ b/_app-of-apps-aws-prod.yaml @@ -18,7 +18,7 @@ metadata: spec: project: default source: - repoURL: git@github.com:fortedigital/sturdy-adventure.git + repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD path: infra/overlays/aws-prod destination: diff --git a/_app-of-apps-azure-dev.yaml b/_app-of-apps-azure-dev.yaml index deeaefa..bd8ab3c 100644 --- a/_app-of-apps-azure-dev.yaml +++ b/_app-of-apps-azure-dev.yaml @@ -18,7 +18,7 @@ metadata: spec: project: default source: - repoURL: git@github.com:fortedigital/sturdy-adventure.git + repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD path: infra/overlays/azure-dev destination: diff --git a/_app-of-apps-azure-prod.yaml b/_app-of-apps-azure-prod.yaml index 9794896..1a9721f 100644 --- a/_app-of-apps-azure-prod.yaml +++ b/_app-of-apps-azure-prod.yaml @@ -18,7 +18,7 @@ metadata: spec: project: default source: - repoURL: git@github.com:fortedigital/sturdy-adventure.git + repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD path: infra/overlays/azure-prod destination: diff --git a/_app-of-apps-gcp-dev.yaml b/_app-of-apps-gcp-dev.yaml index 63843ce..d3ed8f7 100644 --- a/_app-of-apps-gcp-dev.yaml +++ b/_app-of-apps-gcp-dev.yaml @@ -18,7 +18,7 @@ metadata: spec: project: default source: - repoURL: git@github.com:fortedigital/sturdy-adventure.git + repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD path: infra/overlays/gcp-dev destination: diff --git a/_app-of-apps-gcp-prod.yaml b/_app-of-apps-gcp-prod.yaml index 32ae05f..51b3b90 100644 --- a/_app-of-apps-gcp-prod.yaml +++ b/_app-of-apps-gcp-prod.yaml @@ -18,7 +18,7 @@ metadata: spec: project: default source: - repoURL: git@github.com:fortedigital/sturdy-adventure.git + repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD path: infra/overlays/gcp-prod destination: diff --git a/_app-of-apps-upc-prod.yaml b/_app-of-apps-upc-prod.yaml index f5ccaca..64624f9 100644 --- a/_app-of-apps-upc-prod.yaml +++ b/_app-of-apps-upc-prod.yaml @@ -18,7 +18,7 @@ metadata: spec: project: default source: - repoURL: git@github.com:fortedigital/sturdy-adventure.git + repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD path: infra/overlays/upc-prod destination: diff --git a/apps/base/dot-ai-stack.yaml b/apps/base/dot-ai-stack.yaml index 3fd1284..23c93dc 100644 --- a/apps/base/dot-ai-stack.yaml +++ b/apps/base/dot-ai-stack.yaml @@ -37,7 +37,7 @@ spec: - $values/infra/values/base/dot-ai-stack-values.yaml - $values/infra/values/upc-dev/dot-ai-stack-values.yaml - - repoURL: git@github.com:fortedigital/sturdy-adventure.git + - repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD ref: values diff --git a/infra/base/opencost.yaml b/infra/base/opencost.yaml index a102906..c379cbf 100644 --- a/infra/base/opencost.yaml +++ b/infra/base/opencost.yaml @@ -24,7 +24,7 @@ spec: - $values/infra/values/base/opencost-values.yaml - $values/infra/values/upc-dev/opencost-values.yaml - - repoURL: git@github.com:fortedigital/sturdy-adventure.git + - repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD ref: values diff --git a/infra/base/traefik-application.yaml b/infra/base/traefik-application.yaml index eb9fd2c..8d585c8 100644 --- a/infra/base/traefik-application.yaml +++ b/infra/base/traefik-application.yaml @@ -31,7 +31,7 @@ spec: - $values/infra/values/base/traefik-values.yaml - $values/infra/values/upc-dev/traefik-values.yaml - - repoURL: git@github.com:fortedigital/sturdy-adventure.git + - repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD ref: values -- 2.49.1 From 79f9c62012f861e2b307a5c60c1b535fe6cf5a2a Mon Sep 17 00:00:00 2001 From: Danijel Simeunovic Date: Wed, 22 Apr 2026 14:35:59 +0200 Subject: [PATCH 07/15] azure>aks --- README.md | 10 +++++----- ...-apps-azure-dev.yaml => _app-of-apps-aks-dev.yaml | 2 +- ...pps-azure-prod.yaml => _app-of-apps-aks-prod.yaml | 2 +- docs/GITOPS-ARCHITECTURE.md | 4 ++-- docs/OPERATIONS-RUNBOOK.md | 4 ++-- infra/overlays/azure-dev/kustomization.yaml | 12 ++++++------ infra/overlays/azure-prod/kustomization.yaml | 12 ++++++------ 7 files changed, 23 insertions(+), 23 deletions(-) rename _app-of-apps-azure-dev.yaml => _app-of-apps-aks-dev.yaml (95%) rename _app-of-apps-azure-prod.yaml => _app-of-apps-aks-prod.yaml (95%) diff --git a/README.md b/README.md index c9511e0..0727622 100644 --- a/README.md +++ b/README.md @@ -100,8 +100,8 @@ This repository contains the complete GitOps configuration for our Kubernetes cl │ │ ├── upc-prod/ # UpCloud Prod (patches value paths) │ │ ├── aws-dev/ # AWS EKS Dev │ │ ├── aws-prod/ # AWS EKS Prod -│ │ ├── azure-dev/ # Azure AKS Dev -│ │ ├── azure-prod/ # Azure AKS Prod +│ │ ├── aks-dev/ # Azure AKS Dev +│ │ ├── aks-prod/ # Azure AKS Prod │ │ ├── gcp-dev/ # GCP GKE Dev │ │ └── gcp-prod/ # GCP GKE Prod │ ├── dashboards/ # Grafana dashboard ConfigMaps @@ -111,8 +111,8 @@ This repository contains the complete GitOps configuration for our Kubernetes cl │ ├── upc-prod/ # UpCloud Prod │ ├── aws-dev/ # AWS EKS Dev │ ├── aws-prod/ # AWS EKS Prod -│ ├── azure-dev/ # Azure AKS Dev -│ ├── azure-prod/ # Azure AKS Prod +│ ├── aks-dev/ # Azure AKS Dev +│ ├── aks-prod/ # Azure AKS Prod │ ├── gcp-dev/ # GCP GKE Dev │ └── gcp-prod/ # GCP GKE Prod │ @@ -373,7 +373,7 @@ kubectl patch application myapp -n argocd \ ## 📖 Key Concepts ### App-of-Apps Pattern -`_app-of-apps-{cluster}.yaml` is the root Application that manages all other Applications in `infra/`. Kustomize overlays in `infra/overlays/{cluster}/` render the base Applications with per-cluster patches (e.g., swapping value file paths). Supported clusters: `upc-dev`, `upc-prod`, `aws-dev`, `aws-prod`, `azure-dev`, `azure-prod`, `gcp-dev`, `gcp-prod`. +`_app-of-apps-{cluster}.yaml` is the root Application that manages all other Applications in `infra/`. Kustomize overlays in `infra/overlays/{cluster}/` render the base Applications with per-cluster patches (e.g., swapping value file paths). Supported clusters: `upc-dev`, `upc-prod`, `aws-dev`, `aws-prod`, `aks-dev`, `aks-prod`, `gcp-dev`, `gcp-prod`. ### Multi-Source Pattern Applications reference both: diff --git a/_app-of-apps-azure-dev.yaml b/_app-of-apps-aks-dev.yaml similarity index 95% rename from _app-of-apps-azure-dev.yaml rename to _app-of-apps-aks-dev.yaml index bd8ab3c..9547bfe 100644 --- a/_app-of-apps-azure-dev.yaml +++ b/_app-of-apps-aks-dev.yaml @@ -20,7 +20,7 @@ spec: source: repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD - path: infra/overlays/azure-dev + path: infra/overlays/aks-dev destination: server: https://kubernetes.default.svc namespace: default diff --git a/_app-of-apps-azure-prod.yaml b/_app-of-apps-aks-prod.yaml similarity index 95% rename from _app-of-apps-azure-prod.yaml rename to _app-of-apps-aks-prod.yaml index 1a9721f..8b0b817 100644 --- a/_app-of-apps-azure-prod.yaml +++ b/_app-of-apps-aks-prod.yaml @@ -20,7 +20,7 @@ spec: source: repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD - path: infra/overlays/azure-prod + path: infra/overlays/aks-prod destination: server: https://kubernetes.default.svc namespace: default diff --git a/docs/GITOPS-ARCHITECTURE.md b/docs/GITOPS-ARCHITECTURE.md index a57fb4b..d811340 100644 --- a/docs/GITOPS-ARCHITECTURE.md +++ b/docs/GITOPS-ARCHITECTURE.md @@ -136,8 +136,8 @@ launchpad/ │ │ ├── upc-prod/ # UpCloud Prod (patches value paths) │ │ ├── aws-dev/ # AWS EKS Dev │ │ ├── aws-prod/ # AWS EKS Prod -│ │ ├── azure-dev/ # Azure AKS Dev -│ │ ├── azure-prod/ # Azure AKS Prod +│ │ ├── aks-dev/ # Azure AKS Dev +│ │ ├── aks-prod/ # Azure AKS Prod │ │ ├── gcp-dev/ # GCP GKE Dev │ │ └── gcp-prod/ # GCP GKE Prod │ ├── dashboards/ # Grafana dashboard ConfigMaps diff --git a/docs/OPERATIONS-RUNBOOK.md b/docs/OPERATIONS-RUNBOOK.md index 03ea097..dee0280 100644 --- a/docs/OPERATIONS-RUNBOOK.md +++ b/docs/OPERATIONS-RUNBOOK.md @@ -56,7 +56,7 @@ cd launchpad # 2. Run bootstrap script with cluster target # Available clusters: upc-dev, upc-prod, aws-dev, aws-prod, -# azure-dev, azure-prod, gcp-dev, gcp-prod +# aks-dev, aks-prod, gcp-dev, gcp-prod ./bootstrap.sh upc-dev # Cluster config is loaded from clusters/.yaml @@ -1528,7 +1528,7 @@ The repository supports multiple clusters across multiple clouds via Kustomize o **Cloud-ready templates (fill in `clusters/*.yaml` before use):** - **aws-dev** / **aws-prod**: AWS EKS with NLB, gp3 storage, AWS CUR pricing -- **azure-dev** / **azure-prod**: Azure AKS with Standard LB, managed-csi-premium storage +- **aks-dev** / **aks-prod**: Azure AKS with Standard LB, managed-csi-premium storage - **gcp-dev** / **gcp-prod**: GCP GKE with L4 LB, premium-rwo storage Each cluster has its own: diff --git a/infra/overlays/azure-dev/kustomization.yaml b/infra/overlays/azure-dev/kustomization.yaml index d7a014d..c230763 100644 --- a/infra/overlays/azure-dev/kustomization.yaml +++ b/infra/overlays/azure-dev/kustomization.yaml @@ -4,32 +4,32 @@ resources: - ../../base patches: -# Traefik: swap upc-dev → azure-dev +# Traefik: swap upc-dev → aks-dev - target: kind: Application name: traefik patch: | - op: replace path: /spec/sources/0/helm/valueFiles/1 - value: $values/infra/values/azure-dev/traefik-values.yaml + value: $values/infra/values/aks-dev/traefik-values.yaml -# Gitea: swap upc-dev → azure-dev +# Gitea: swap upc-dev → aks-dev - target: kind: Application name: gitea patch: | - op: replace path: /spec/sources/0/helm/valueFiles/1 - value: $values/infra/values/azure-dev/gitea-values.yaml + value: $values/infra/values/aks-dev/gitea-values.yaml -# OpenCost: swap upc-dev → azure-dev +# OpenCost: swap upc-dev → aks-dev - target: kind: Application name: opencost patch: | - op: replace path: /spec/sources/0/helm/valueFiles/1 - value: $values/infra/values/azure-dev/opencost-values.yaml + value: $values/infra/values/aks-dev/opencost-values.yaml # TODO: add patches for keycloak, grafana, secrets, enterprise-apps # when deploying to this cluster (these are deployment-specific, not cloud-specific) diff --git a/infra/overlays/azure-prod/kustomization.yaml b/infra/overlays/azure-prod/kustomization.yaml index 4a9d6cf..5cadfd5 100644 --- a/infra/overlays/azure-prod/kustomization.yaml +++ b/infra/overlays/azure-prod/kustomization.yaml @@ -4,32 +4,32 @@ resources: - ../../base patches: -# Traefik: swap upc-dev → azure-prod +# Traefik: swap upc-dev → aks-prod - target: kind: Application name: traefik patch: | - op: replace path: /spec/sources/0/helm/valueFiles/1 - value: $values/infra/values/azure-prod/traefik-values.yaml + value: $values/infra/values/aks-prod/traefik-values.yaml -# Gitea: swap upc-dev → azure-prod +# Gitea: swap upc-dev → aks-prod - target: kind: Application name: gitea patch: | - op: replace path: /spec/sources/0/helm/valueFiles/1 - value: $values/infra/values/azure-prod/gitea-values.yaml + value: $values/infra/values/aks-prod/gitea-values.yaml -# OpenCost: swap upc-dev → azure-prod +# OpenCost: swap upc-dev → aks-prod - target: kind: Application name: opencost patch: | - op: replace path: /spec/sources/0/helm/valueFiles/1 - value: $values/infra/values/azure-prod/opencost-values.yaml + value: $values/infra/values/aks-prod/opencost-values.yaml # TODO: add patches for keycloak, grafana, secrets, enterprise-apps # when deploying to this cluster (these are deployment-specific, not cloud-specific) -- 2.49.1 From 7d2fb8bc0c04a639295c4f057375d6aeba70ec32 Mon Sep 17 00:00:00 2001 From: Danijel Simeunovic Date: Wed, 22 Apr 2026 14:41:42 +0200 Subject: [PATCH 08/15] azure>aks --- clusters/{azure-dev.yaml => aks-dev.yaml} | 0 clusters/{azure-prod.yaml => aks-prod.yaml} | 0 .../overlays/{azure-dev => aks-dev}/kustomization.yaml | 0 .../{azure-prod => aks-prod}/kustomization.yaml | 0 infra/values/{azure-dev => aks-dev}/gitea-values.yaml | 0 .../values/{azure-dev => aks-dev}/opencost-values.yaml | 0 .../values/{azure-dev => aks-dev}/traefik-values.yaml | 0 .../values/{azure-prod => aks-prod}/gitea-values.yaml | 0 .../{azure-prod => aks-prod}/opencost-values.yaml | 0 .../{azure-prod => aks-prod}/traefik-values.yaml | 0 scripts/{gitea-backup-azure.sh => gitea-backup-aks.sh} | 10 +++++----- 11 files changed, 5 insertions(+), 5 deletions(-) rename clusters/{azure-dev.yaml => aks-dev.yaml} (100%) rename clusters/{azure-prod.yaml => aks-prod.yaml} (100%) rename infra/overlays/{azure-dev => aks-dev}/kustomization.yaml (100%) rename infra/overlays/{azure-prod => aks-prod}/kustomization.yaml (100%) rename infra/values/{azure-dev => aks-dev}/gitea-values.yaml (100%) rename infra/values/{azure-dev => aks-dev}/opencost-values.yaml (100%) rename infra/values/{azure-dev => aks-dev}/traefik-values.yaml (100%) rename infra/values/{azure-prod => aks-prod}/gitea-values.yaml (100%) rename infra/values/{azure-prod => aks-prod}/opencost-values.yaml (100%) rename infra/values/{azure-prod => aks-prod}/traefik-values.yaml (100%) rename scripts/{gitea-backup-azure.sh => gitea-backup-aks.sh} (90%) mode change 100755 => 100644 diff --git a/clusters/azure-dev.yaml b/clusters/aks-dev.yaml similarity index 100% rename from clusters/azure-dev.yaml rename to clusters/aks-dev.yaml diff --git a/clusters/azure-prod.yaml b/clusters/aks-prod.yaml similarity index 100% rename from clusters/azure-prod.yaml rename to clusters/aks-prod.yaml diff --git a/infra/overlays/azure-dev/kustomization.yaml b/infra/overlays/aks-dev/kustomization.yaml similarity index 100% rename from infra/overlays/azure-dev/kustomization.yaml rename to infra/overlays/aks-dev/kustomization.yaml diff --git a/infra/overlays/azure-prod/kustomization.yaml b/infra/overlays/aks-prod/kustomization.yaml similarity index 100% rename from infra/overlays/azure-prod/kustomization.yaml rename to infra/overlays/aks-prod/kustomization.yaml diff --git a/infra/values/azure-dev/gitea-values.yaml b/infra/values/aks-dev/gitea-values.yaml similarity index 100% rename from infra/values/azure-dev/gitea-values.yaml rename to infra/values/aks-dev/gitea-values.yaml diff --git a/infra/values/azure-dev/opencost-values.yaml b/infra/values/aks-dev/opencost-values.yaml similarity index 100% rename from infra/values/azure-dev/opencost-values.yaml rename to infra/values/aks-dev/opencost-values.yaml diff --git a/infra/values/azure-dev/traefik-values.yaml b/infra/values/aks-dev/traefik-values.yaml similarity index 100% rename from infra/values/azure-dev/traefik-values.yaml rename to infra/values/aks-dev/traefik-values.yaml diff --git a/infra/values/azure-prod/gitea-values.yaml b/infra/values/aks-prod/gitea-values.yaml similarity index 100% rename from infra/values/azure-prod/gitea-values.yaml rename to infra/values/aks-prod/gitea-values.yaml diff --git a/infra/values/azure-prod/opencost-values.yaml b/infra/values/aks-prod/opencost-values.yaml similarity index 100% rename from infra/values/azure-prod/opencost-values.yaml rename to infra/values/aks-prod/opencost-values.yaml diff --git a/infra/values/azure-prod/traefik-values.yaml b/infra/values/aks-prod/traefik-values.yaml similarity index 100% rename from infra/values/azure-prod/traefik-values.yaml rename to infra/values/aks-prod/traefik-values.yaml diff --git a/scripts/gitea-backup-azure.sh b/scripts/gitea-backup-aks.sh old mode 100755 new mode 100644 similarity index 90% rename from scripts/gitea-backup-azure.sh rename to scripts/gitea-backup-aks.sh index e2f14d7..5ab2653 --- a/scripts/gitea-backup-azure.sh +++ b/scripts/gitea-backup-aks.sh @@ -2,19 +2,19 @@ set -euo pipefail # Gitea backup helper for Azure Blob Storage -# Uses the gitea-backup-azure secret in the gitea namespace +# Uses the gitea-backup-aks secret in the gitea namespace # Required secret keys: # AZURE_STORAGE_ACCOUNT — storage account name # AZURE_STORAGE_KEY — storage account key # AZURE_CONTAINER — blob container name # # Usage: -# ./scripts/gitea-backup-azure.sh list # list all backups -# ./scripts/gitea-backup-azure.sh download # download a backup -# ./scripts/gitea-backup-azure.sh download latest # download the most recent backup +# ./scripts/gitea-backup-aks.sh list # list all backups +# ./scripts/gitea-backup-aks.sh download # download a backup +# ./scripts/gitea-backup-aks.sh download latest # download the most recent backup NAMESPACE="gitea" -SECRET="gitea-backup-azure" +SECRET="gitea-backup-aks" IMAGE="mcr.microsoft.com/azure-cli:latest" POD_NAME="gitea-backup-helper" -- 2.49.1 From 92ddc22322a23dacb397d859aa94bf4882061f5f Mon Sep 17 00:00:00 2001 From: Danijel Simeunovic Date: Wed, 22 Apr 2026 14:42:02 +0200 Subject: [PATCH 09/15] azure>aks --- docs/GITOPS-ARCHITECTURE.md | 2 +- docs/OPERATIONS-RUNBOOK.md | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/docs/GITOPS-ARCHITECTURE.md b/docs/GITOPS-ARCHITECTURE.md index d811340..3105321 100644 --- a/docs/GITOPS-ARCHITECTURE.md +++ b/docs/GITOPS-ARCHITECTURE.md @@ -145,7 +145,7 @@ launchpad/ │ ├── base/ # Cloud-agnostic shared values │ ├── upc-{dev,prod}/ # UpCloud: storage class, LB, pricing │ ├── aws-{dev,prod}/ # AWS: gp3, NLB, CUR pricing -│ ├── azure-{dev,prod}/ # Azure: managed-csi-premium, Standard LB +│ ├── aks-{dev,prod}/ # Azure: managed-csi-premium, Standard LB │ └── gcp-{dev,prod}/ # GCP: premium-rwo, L4 LB │ ├── apps/ # Business Application ArgoCD manifests (Kustomize) diff --git a/docs/OPERATIONS-RUNBOOK.md b/docs/OPERATIONS-RUNBOOK.md index dee0280..8d0f101 100644 --- a/docs/OPERATIONS-RUNBOOK.md +++ b/docs/OPERATIONS-RUNBOOK.md @@ -1277,7 +1277,7 @@ spec: **Per-cloud backup scripts** (manual restore helpers): - UpCloud/AWS: `scripts/gitea-backup.sh` / `scripts/gitea-backup-aws.sh` (MinIO CLI, S3-compatible) -- Azure: `scripts/gitea-backup-azure.sh` (Azure CLI + Blob Storage) +- Azure: `scripts/gitea-backup-aks.sh` (Azure CLI + Blob Storage) - GCP: `scripts/gitea-backup-gcp.sh` (gsutil + GCS) ### Cluster Rebuild -- 2.49.1 From a471f1174072f1fbf7bb234dff0fb14dd4cae905 Mon Sep 17 00:00:00 2001 From: Danijel Simeunovic Date: Wed, 22 Apr 2026 14:45:23 +0200 Subject: [PATCH 10/15] repo url --- _app-of-apps-aks-prod.yaml | 2 +- _app-of-apps-eks-prod.yaml | 2 +- _app-of-apps-gke-prod.yaml | 2 +- _app-of-apps-upc-prod.yaml | 2 +- apps/base/dot-ai-stack.yaml | 2 +- infra/base/opencost.yaml | 2 +- infra/base/traefik-application.yaml | 2 +- 7 files changed, 7 insertions(+), 7 deletions(-) diff --git a/_app-of-apps-aks-prod.yaml b/_app-of-apps-aks-prod.yaml index 6d945ac..8b0b817 100644 --- a/_app-of-apps-aks-prod.yaml +++ b/_app-of-apps-aks-prod.yaml @@ -18,7 +18,7 @@ metadata: spec: project: default source: - repoURL: git@github.com:fortedigital/sturdy-adventure.git + repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD path: infra/overlays/aks-prod destination: diff --git a/_app-of-apps-eks-prod.yaml b/_app-of-apps-eks-prod.yaml index 1e51d04..29337cb 100644 --- a/_app-of-apps-eks-prod.yaml +++ b/_app-of-apps-eks-prod.yaml @@ -18,7 +18,7 @@ metadata: spec: project: default source: - repoURL: git@github.com:fortedigital/sturdy-adventure.git + repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD path: infra/overlays/eks-prod destination: diff --git a/_app-of-apps-gke-prod.yaml b/_app-of-apps-gke-prod.yaml index 8c6fc27..874cebd 100644 --- a/_app-of-apps-gke-prod.yaml +++ b/_app-of-apps-gke-prod.yaml @@ -18,7 +18,7 @@ metadata: spec: project: default source: - repoURL: git@github.com:fortedigital/sturdy-adventure.git + repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD path: infra/overlays/gke-prod destination: diff --git a/_app-of-apps-upc-prod.yaml b/_app-of-apps-upc-prod.yaml index f5ccaca..64624f9 100644 --- a/_app-of-apps-upc-prod.yaml +++ b/_app-of-apps-upc-prod.yaml @@ -18,7 +18,7 @@ metadata: spec: project: default source: - repoURL: git@github.com:fortedigital/sturdy-adventure.git + repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD path: infra/overlays/upc-prod destination: diff --git a/apps/base/dot-ai-stack.yaml b/apps/base/dot-ai-stack.yaml index 3fd1284..23c93dc 100644 --- a/apps/base/dot-ai-stack.yaml +++ b/apps/base/dot-ai-stack.yaml @@ -37,7 +37,7 @@ spec: - $values/infra/values/base/dot-ai-stack-values.yaml - $values/infra/values/upc-dev/dot-ai-stack-values.yaml - - repoURL: git@github.com:fortedigital/sturdy-adventure.git + - repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD ref: values diff --git a/infra/base/opencost.yaml b/infra/base/opencost.yaml index a102906..c379cbf 100644 --- a/infra/base/opencost.yaml +++ b/infra/base/opencost.yaml @@ -24,7 +24,7 @@ spec: - $values/infra/values/base/opencost-values.yaml - $values/infra/values/upc-dev/opencost-values.yaml - - repoURL: git@github.com:fortedigital/sturdy-adventure.git + - repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD ref: values diff --git a/infra/base/traefik-application.yaml b/infra/base/traefik-application.yaml index eb9fd2c..8d585c8 100644 --- a/infra/base/traefik-application.yaml +++ b/infra/base/traefik-application.yaml @@ -31,7 +31,7 @@ spec: - $values/infra/values/base/traefik-values.yaml - $values/infra/values/upc-dev/traefik-values.yaml - - repoURL: git@github.com:fortedigital/sturdy-adventure.git + - repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD ref: values -- 2.49.1 From c8c2dedea5b72582af68f1dca9aa5e69db7bc7c4 Mon Sep 17 00:00:00 2001 From: Danijel Simeunovic Date: Wed, 22 Apr 2026 21:48:02 +0200 Subject: [PATCH 11/15] rename --- README.md | 18 +++++++++--------- ...s-aws-dev.yaml => _app-of-apps-eks-dev.yaml | 2 +- ...aws-prod.yaml => _app-of-apps-eks-prod.yaml | 2 +- ...s-gcp-dev.yaml => _app-of-apps-gke-dev.yaml | 2 +- ...gcp-prod.yaml => _app-of-apps-gke-prod.yaml | 2 +- clusters/{aws-dev.yaml => eks-dev.yaml} | 2 +- clusters/{aws-prod.yaml => eks-prod.yaml} | 2 +- clusters/{gcp-dev.yaml => gke-dev.yaml} | 2 +- clusters/{gcp-prod.yaml => gke-prod.yaml} | 2 +- docs/GITOPS-ARCHITECTURE.md | 10 +++++----- docs/OPERATIONS-RUNBOOK.md | 14 +++++++------- docs/REFERENCE.md | 2 +- .../{gcp-dev => eks-dev}/kustomization.yaml | 12 ++++++------ .../{gcp-prod => eks-prod}/kustomization.yaml | 12 ++++++------ .../{aws-dev => gke-dev}/kustomization.yaml | 12 ++++++------ .../{aws-prod => gke-prod}/kustomization.yaml | 12 ++++++------ .../{aws-dev => eks-dev}/gitea-values.yaml | 0 .../{aws-dev => eks-dev}/opencost-values.yaml | 0 .../{aws-dev => eks-dev}/traefik-values.yaml | 0 .../{aws-prod => eks-prod}/gitea-values.yaml | 0 .../opencost-values.yaml | 0 .../{aws-prod => eks-prod}/traefik-values.yaml | 0 .../{gcp-dev => gke-dev}/gitea-values.yaml | 0 .../{gcp-dev => gke-dev}/opencost-values.yaml | 0 .../{gcp-dev => gke-dev}/traefik-values.yaml | 0 .../{gcp-prod => gke-prod}/gitea-values.yaml | 0 .../opencost-values.yaml | 0 .../{gcp-prod => gke-prod}/traefik-values.yaml | 0 ...gitea-backup-aws.sh => gitea-backup-eks.sh} | 6 +++--- ...gitea-backup-gcp.sh => gitea-backup-gke.sh} | 6 +++--- 30 files changed, 60 insertions(+), 60 deletions(-) rename _app-of-apps-aws-dev.yaml => _app-of-apps-eks-dev.yaml (95%) rename _app-of-apps-aws-prod.yaml => _app-of-apps-eks-prod.yaml (95%) rename _app-of-apps-gcp-dev.yaml => _app-of-apps-gke-dev.yaml (95%) rename _app-of-apps-gcp-prod.yaml => _app-of-apps-gke-prod.yaml (95%) rename clusters/{aws-dev.yaml => eks-dev.yaml} (95%) rename clusters/{aws-prod.yaml => eks-prod.yaml} (95%) rename clusters/{gcp-dev.yaml => gke-dev.yaml} (95%) rename clusters/{gcp-prod.yaml => gke-prod.yaml} (95%) rename infra/overlays/{gcp-dev => eks-dev}/kustomization.yaml (68%) rename infra/overlays/{gcp-prod => eks-prod}/kustomization.yaml (67%) rename infra/overlays/{aws-dev => gke-dev}/kustomization.yaml (68%) rename infra/overlays/{aws-prod => gke-prod}/kustomization.yaml (67%) rename infra/values/{aws-dev => eks-dev}/gitea-values.yaml (100%) rename infra/values/{aws-dev => eks-dev}/opencost-values.yaml (100%) rename infra/values/{aws-dev => eks-dev}/traefik-values.yaml (100%) rename infra/values/{aws-prod => eks-prod}/gitea-values.yaml (100%) rename infra/values/{aws-prod => eks-prod}/opencost-values.yaml (100%) rename infra/values/{aws-prod => eks-prod}/traefik-values.yaml (100%) rename infra/values/{gcp-dev => gke-dev}/gitea-values.yaml (100%) rename infra/values/{gcp-dev => gke-dev}/opencost-values.yaml (100%) rename infra/values/{gcp-dev => gke-dev}/traefik-values.yaml (100%) rename infra/values/{gcp-prod => gke-prod}/gitea-values.yaml (100%) rename infra/values/{gcp-prod => gke-prod}/opencost-values.yaml (100%) rename infra/values/{gcp-prod => gke-prod}/traefik-values.yaml (100%) rename scripts/{gitea-backup-aws.sh => gitea-backup-eks.sh} (93%) mode change 100755 => 100644 rename scripts/{gitea-backup-gcp.sh => gitea-backup-gke.sh} (94%) mode change 100755 => 100644 diff --git a/README.md b/README.md index 0727622..b560f46 100644 --- a/README.md +++ b/README.md @@ -98,23 +98,23 @@ This repository contains the complete GitOps configuration for our Kubernetes cl │ ├── overlays/ # Per-cluster overrides (Kustomize) │ │ ├── upc-dev/ # UpCloud Dev (uses base as-is) │ │ ├── upc-prod/ # UpCloud Prod (patches value paths) -│ │ ├── aws-dev/ # AWS EKS Dev -│ │ ├── aws-prod/ # AWS EKS Prod +│ │ ├── eks-dev/ # AWS EKS Dev +│ │ ├── eks-prod/ # AWS EKS Prod │ │ ├── aks-dev/ # Azure AKS Dev │ │ ├── aks-prod/ # Azure AKS Prod -│ │ ├── gcp-dev/ # GCP GKE Dev -│ │ └── gcp-prod/ # GCP GKE Prod +│ │ ├── gke-dev/ # GCP GKE Dev +│ │ └── gke-prod/ # GCP GKE Prod │ ├── dashboards/ # Grafana dashboard ConfigMaps │ └── values/ # Helm value overrides │ ├── base/ # Shared cloud-agnostic values │ ├── upc-dev/ # UpCloud Dev (storage, LB, pricing) │ ├── upc-prod/ # UpCloud Prod -│ ├── aws-dev/ # AWS EKS Dev -│ ├── aws-prod/ # AWS EKS Prod +│ ├── eks-dev/ # AWS EKS Dev +│ ├── eks-prod/ # AWS EKS Prod │ ├── aks-dev/ # Azure AKS Dev │ ├── aks-prod/ # Azure AKS Prod -│ ├── gcp-dev/ # GCP GKE Dev -│ └── gcp-prod/ # GCP GKE Prod +│ ├── gke-dev/ # GCP GKE Dev +│ └── gke-prod/ # GCP GKE Prod │ ├── apps/ # Business Applications │ ├── mcp10x.yaml @@ -373,7 +373,7 @@ kubectl patch application myapp -n argocd \ ## 📖 Key Concepts ### App-of-Apps Pattern -`_app-of-apps-{cluster}.yaml` is the root Application that manages all other Applications in `infra/`. Kustomize overlays in `infra/overlays/{cluster}/` render the base Applications with per-cluster patches (e.g., swapping value file paths). Supported clusters: `upc-dev`, `upc-prod`, `aws-dev`, `aws-prod`, `aks-dev`, `aks-prod`, `gcp-dev`, `gcp-prod`. +`_app-of-apps-{cluster}.yaml` is the root Application that manages all other Applications in `infra/`. Kustomize overlays in `infra/overlays/{cluster}/` render the base Applications with per-cluster patches (e.g., swapping value file paths). Supported clusters: `upc-dev`, `upc-prod`, `eks-dev`, `eks-prod`, `aks-dev`, `aks-prod`, `gke-dev`, `gke-prod`. ### Multi-Source Pattern Applications reference both: diff --git a/_app-of-apps-aws-dev.yaml b/_app-of-apps-eks-dev.yaml similarity index 95% rename from _app-of-apps-aws-dev.yaml rename to _app-of-apps-eks-dev.yaml index fa364c8..f40e164 100644 --- a/_app-of-apps-aws-dev.yaml +++ b/_app-of-apps-eks-dev.yaml @@ -20,7 +20,7 @@ spec: source: repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD - path: infra/overlays/aws-dev + path: infra/overlays/eks-dev destination: server: https://kubernetes.default.svc namespace: default diff --git a/_app-of-apps-aws-prod.yaml b/_app-of-apps-eks-prod.yaml similarity index 95% rename from _app-of-apps-aws-prod.yaml rename to _app-of-apps-eks-prod.yaml index 9922276..29337cb 100644 --- a/_app-of-apps-aws-prod.yaml +++ b/_app-of-apps-eks-prod.yaml @@ -20,7 +20,7 @@ spec: source: repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD - path: infra/overlays/aws-prod + path: infra/overlays/eks-prod destination: server: https://kubernetes.default.svc namespace: default diff --git a/_app-of-apps-gcp-dev.yaml b/_app-of-apps-gke-dev.yaml similarity index 95% rename from _app-of-apps-gcp-dev.yaml rename to _app-of-apps-gke-dev.yaml index d3ed8f7..faf753c 100644 --- a/_app-of-apps-gcp-dev.yaml +++ b/_app-of-apps-gke-dev.yaml @@ -20,7 +20,7 @@ spec: source: repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD - path: infra/overlays/gcp-dev + path: infra/overlays/gke-dev destination: server: https://kubernetes.default.svc namespace: default diff --git a/_app-of-apps-gcp-prod.yaml b/_app-of-apps-gke-prod.yaml similarity index 95% rename from _app-of-apps-gcp-prod.yaml rename to _app-of-apps-gke-prod.yaml index 51b3b90..874cebd 100644 --- a/_app-of-apps-gcp-prod.yaml +++ b/_app-of-apps-gke-prod.yaml @@ -20,7 +20,7 @@ spec: source: repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git targetRevision: HEAD - path: infra/overlays/gcp-prod + path: infra/overlays/gke-prod destination: server: https://kubernetes.default.svc namespace: default diff --git a/clusters/aws-dev.yaml b/clusters/eks-dev.yaml similarity index 95% rename from clusters/aws-dev.yaml rename to clusters/eks-dev.yaml index 02f3034..55ffa95 100644 --- a/clusters/aws-dev.yaml +++ b/clusters/eks-dev.yaml @@ -7,4 +7,4 @@ dotaiDomain: kubemcp.example.com dotaiUiDomain: kubemcpui.example.com letsencryptEmail: admin@example.com # <- adjust trustedIPs: "10.0.0.0/8" # <- adjust to your VPC CIDR -cloudProvider: aws +cloudProvider: eks diff --git a/clusters/aws-prod.yaml b/clusters/eks-prod.yaml similarity index 95% rename from clusters/aws-prod.yaml rename to clusters/eks-prod.yaml index c5973f9..8dcfc90 100644 --- a/clusters/aws-prod.yaml +++ b/clusters/eks-prod.yaml @@ -7,4 +7,4 @@ dotaiDomain: kubemcp.example.com dotaiUiDomain: kubemcpui.example.com letsencryptEmail: admin@example.com # <- adjust trustedIPs: "10.0.0.0/8" # <- adjust to your VPC CIDR -cloudProvider: aws +cloudProvider: eks diff --git a/clusters/gcp-dev.yaml b/clusters/gke-dev.yaml similarity index 95% rename from clusters/gcp-dev.yaml rename to clusters/gke-dev.yaml index 43f3861..2bd2801 100644 --- a/clusters/gcp-dev.yaml +++ b/clusters/gke-dev.yaml @@ -7,4 +7,4 @@ dotaiDomain: kubemcp.example.com dotaiUiDomain: kubemcpui.example.com letsencryptEmail: admin@example.com # <- adjust trustedIPs: "10.0.0.0/8,35.191.0.0/16,130.211.0.0/22" # <- subnet CIDR + GCP health checks -cloudProvider: gcp +cloudProvider: gke diff --git a/clusters/gcp-prod.yaml b/clusters/gke-prod.yaml similarity index 95% rename from clusters/gcp-prod.yaml rename to clusters/gke-prod.yaml index ec814f7..7d8740f 100644 --- a/clusters/gcp-prod.yaml +++ b/clusters/gke-prod.yaml @@ -7,4 +7,4 @@ dotaiDomain: kubemcp.example.com dotaiUiDomain: kubemcpui.example.com letsencryptEmail: admin@example.com # <- adjust trustedIPs: "10.0.0.0/8,35.191.0.0/16,130.211.0.0/22" # <- subnet CIDR + GCP health checks -cloudProvider: gcp +cloudProvider: gke diff --git a/docs/GITOPS-ARCHITECTURE.md b/docs/GITOPS-ARCHITECTURE.md index 3105321..b199cc8 100644 --- a/docs/GITOPS-ARCHITECTURE.md +++ b/docs/GITOPS-ARCHITECTURE.md @@ -134,12 +134,12 @@ launchpad/ │ ├── overlays/ # Per-cluster Kustomize overrides │ │ ├── upc-dev/ # UpCloud Dev (uses base as-is) │ │ ├── upc-prod/ # UpCloud Prod (patches value paths) -│ │ ├── aws-dev/ # AWS EKS Dev -│ │ ├── aws-prod/ # AWS EKS Prod +│ │ ├── eks-dev/ # AWS EKS Dev +│ │ ├── eks-prod/ # AWS EKS Prod │ │ ├── aks-dev/ # Azure AKS Dev │ │ ├── aks-prod/ # Azure AKS Prod -│ │ ├── gcp-dev/ # GCP GKE Dev -│ │ └── gcp-prod/ # GCP GKE Prod +│ │ ├── gke-dev/ # GCP GKE Dev +│ │ └── gke-prod/ # GCP GKE Prod │ ├── dashboards/ # Grafana dashboard ConfigMaps │ └── values/ # Helm value overrides for infra │ ├── base/ # Cloud-agnostic shared values @@ -283,7 +283,7 @@ app-repository/ ### The App-of-Apps Pattern ``` -_app-of-apps-{cluster}.yaml (Root, per cluster — e.g. upc-dev, aws-prod, gcp-dev) +_app-of-apps-{cluster}.yaml (Root, per cluster — e.g. upc-dev, eks-prod, gke-dev) │ ├── infrastructure-apps (manages infra/) │ ├── cluster-resources-application diff --git a/docs/OPERATIONS-RUNBOOK.md b/docs/OPERATIONS-RUNBOOK.md index 8d0f101..586a806 100644 --- a/docs/OPERATIONS-RUNBOOK.md +++ b/docs/OPERATIONS-RUNBOOK.md @@ -55,8 +55,8 @@ git clone https://git.forteapps.net/Forte/launchpad cd launchpad # 2. Run bootstrap script with cluster target -# Available clusters: upc-dev, upc-prod, aws-dev, aws-prod, -# aks-dev, aks-prod, gcp-dev, gcp-prod +# Available clusters: upc-dev, upc-prod, eks-dev, eks-prod, +# aks-dev, aks-prod, gke-dev, gke-prod ./bootstrap.sh upc-dev # Cluster config is loaded from clusters/.yaml @@ -1276,9 +1276,9 @@ spec: - ❌ Other persistent volumes (Prometheus, Loki, Tempo data) **Per-cloud backup scripts** (manual restore helpers): -- UpCloud/AWS: `scripts/gitea-backup.sh` / `scripts/gitea-backup-aws.sh` (MinIO CLI, S3-compatible) +- UpCloud/AWS: `scripts/gitea-backup.sh` / `scripts/gitea-backup-eks.sh` (MinIO CLI, S3-compatible) - Azure: `scripts/gitea-backup-aks.sh` (Azure CLI + Blob Storage) -- GCP: `scripts/gitea-backup-gcp.sh` (gsutil + GCS) +- GCP: `scripts/gitea-backup-gke.sh` (gsutil + GCS) ### Cluster Rebuild @@ -1527,9 +1527,9 @@ The repository supports multiple clusters across multiple clouds via Kustomize o - **upc-prod**: `infra/overlays/upc-prod/` — patches value file paths from `upc-dev` to `upc-prod` **Cloud-ready templates (fill in `clusters/*.yaml` before use):** -- **aws-dev** / **aws-prod**: AWS EKS with NLB, gp3 storage, AWS CUR pricing +- **eks-dev** / **eks-prod**: AWS EKS with NLB, gp3 storage, AWS CUR pricing - **aks-dev** / **aks-prod**: Azure AKS with Standard LB, managed-csi-premium storage -- **gcp-dev** / **gcp-prod**: GCP GKE with L4 LB, premium-rwo storage +- **gke-dev** / **gke-prod**: GCP GKE with L4 LB, premium-rwo storage Each cluster has its own: - Root app-of-apps: `_app-of-apps-{cluster}.yaml` @@ -1548,7 +1548,7 @@ Cloud-specific values handled per-cluster: | **Cost monitoring** | Custom pricing | AWS CUR | Azure Billing API | GCP Cloud Billing | | **Backup storage** | UpCloud S3-compat | AWS S3 (native) | Azure Blob Storage | GCS | -To add a new cluster, create a new overlay directory (e.g., `infra/overlays/aws-staging/`) with patches that swap the value file paths, and a matching `clusters/aws-staging.yaml`. +To add a new cluster, create a new overlay directory (e.g., `infra/overlays/eks-staging/`) with patches that swap the value file paths, and a matching `clusters/eks-staging.yaml`. ### Blue-Green Deployments diff --git a/docs/REFERENCE.md b/docs/REFERENCE.md index 50ba6b3..029cdda 100644 --- a/docs/REFERENCE.md +++ b/docs/REFERENCE.md @@ -21,7 +21,7 @@ |-----------|-------| | **Provider** | Multi-cloud (UpCloud, AWS EKS, Azure AKS, GCP GKE) | | **Active clusters** | UpCloud (upc-dev, upc-prod) | -| **Cloud-ready templates** | AWS, Azure, GCP (dev + prod each) | +| **Cloud-ready templates** | EKS, AKS, GKE (dev + prod each) | | **GitOps Tool** | ArgoCD | | **Ingress Controller** | Traefik v2 | | **Certificate Management** | Cert-Manager + Let's Encrypt | diff --git a/infra/overlays/gcp-dev/kustomization.yaml b/infra/overlays/eks-dev/kustomization.yaml similarity index 68% rename from infra/overlays/gcp-dev/kustomization.yaml rename to infra/overlays/eks-dev/kustomization.yaml index 491065e..c8690bf 100644 --- a/infra/overlays/gcp-dev/kustomization.yaml +++ b/infra/overlays/eks-dev/kustomization.yaml @@ -4,32 +4,32 @@ resources: - ../../base patches: -# Traefik: swap upc-dev → gcp-dev +# Traefik: swap upc-dev → eks-dev - target: kind: Application name: traefik patch: | - op: replace path: /spec/sources/0/helm/valueFiles/1 - value: $values/infra/values/gcp-dev/traefik-values.yaml + value: $values/infra/values/eks-dev/traefik-values.yaml -# Gitea: swap upc-dev → gcp-dev +# Gitea: swap upc-dev → eks-dev - target: kind: Application name: gitea patch: | - op: replace path: /spec/sources/0/helm/valueFiles/1 - value: $values/infra/values/gcp-dev/gitea-values.yaml + value: $values/infra/values/eks-dev/gitea-values.yaml -# OpenCost: swap upc-dev → gcp-dev +# OpenCost: swap upc-dev → eks-dev - target: kind: Application name: opencost patch: | - op: replace path: /spec/sources/0/helm/valueFiles/1 - value: $values/infra/values/gcp-dev/opencost-values.yaml + value: $values/infra/values/eks-dev/opencost-values.yaml # TODO: add patches for keycloak, grafana, secrets, enterprise-apps # when deploying to this cluster (these are deployment-specific, not cloud-specific) diff --git a/infra/overlays/gcp-prod/kustomization.yaml b/infra/overlays/eks-prod/kustomization.yaml similarity index 67% rename from infra/overlays/gcp-prod/kustomization.yaml rename to infra/overlays/eks-prod/kustomization.yaml index 9971aa9..7ab683d 100644 --- a/infra/overlays/gcp-prod/kustomization.yaml +++ b/infra/overlays/eks-prod/kustomization.yaml @@ -4,32 +4,32 @@ resources: - ../../base patches: -# Traefik: swap upc-dev → gcp-prod +# Traefik: swap upc-dev → eks-prod - target: kind: Application name: traefik patch: | - op: replace path: /spec/sources/0/helm/valueFiles/1 - value: $values/infra/values/gcp-prod/traefik-values.yaml + value: $values/infra/values/eks-prod/traefik-values.yaml -# Gitea: swap upc-dev → gcp-prod +# Gitea: swap upc-dev → eks-prod - target: kind: Application name: gitea patch: | - op: replace path: /spec/sources/0/helm/valueFiles/1 - value: $values/infra/values/gcp-prod/gitea-values.yaml + value: $values/infra/values/eks-prod/gitea-values.yaml -# OpenCost: swap upc-dev → gcp-prod +# OpenCost: swap upc-dev → eks-prod - target: kind: Application name: opencost patch: | - op: replace path: /spec/sources/0/helm/valueFiles/1 - value: $values/infra/values/gcp-prod/opencost-values.yaml + value: $values/infra/values/eks-prod/opencost-values.yaml # TODO: add patches for keycloak, grafana, secrets, enterprise-apps # when deploying to this cluster (these are deployment-specific, not cloud-specific) diff --git a/infra/overlays/aws-dev/kustomization.yaml b/infra/overlays/gke-dev/kustomization.yaml similarity index 68% rename from infra/overlays/aws-dev/kustomization.yaml rename to infra/overlays/gke-dev/kustomization.yaml index 4be71fc..147bb76 100644 --- a/infra/overlays/aws-dev/kustomization.yaml +++ b/infra/overlays/gke-dev/kustomization.yaml @@ -4,32 +4,32 @@ resources: - ../../base patches: -# Traefik: swap upc-dev → aws-dev +# Traefik: swap upc-dev → gke-dev - target: kind: Application name: traefik patch: | - op: replace path: /spec/sources/0/helm/valueFiles/1 - value: $values/infra/values/aws-dev/traefik-values.yaml + value: $values/infra/values/gke-dev/traefik-values.yaml -# Gitea: swap upc-dev → aws-dev +# Gitea: swap upc-dev → gke-dev - target: kind: Application name: gitea patch: | - op: replace path: /spec/sources/0/helm/valueFiles/1 - value: $values/infra/values/aws-dev/gitea-values.yaml + value: $values/infra/values/gke-dev/gitea-values.yaml -# OpenCost: swap upc-dev → aws-dev +# OpenCost: swap upc-dev → gke-dev - target: kind: Application name: opencost patch: | - op: replace path: /spec/sources/0/helm/valueFiles/1 - value: $values/infra/values/aws-dev/opencost-values.yaml + value: $values/infra/values/gke-dev/opencost-values.yaml # TODO: add patches for keycloak, grafana, secrets, enterprise-apps # when deploying to this cluster (these are deployment-specific, not cloud-specific) diff --git a/infra/overlays/aws-prod/kustomization.yaml b/infra/overlays/gke-prod/kustomization.yaml similarity index 67% rename from infra/overlays/aws-prod/kustomization.yaml rename to infra/overlays/gke-prod/kustomization.yaml index ce22faf..d040c85 100644 --- a/infra/overlays/aws-prod/kustomization.yaml +++ b/infra/overlays/gke-prod/kustomization.yaml @@ -4,32 +4,32 @@ resources: - ../../base patches: -# Traefik: swap upc-dev → aws-prod +# Traefik: swap upc-dev → gke-prod - target: kind: Application name: traefik patch: | - op: replace path: /spec/sources/0/helm/valueFiles/1 - value: $values/infra/values/aws-prod/traefik-values.yaml + value: $values/infra/values/gke-prod/traefik-values.yaml -# Gitea: swap upc-dev → aws-prod +# Gitea: swap upc-dev → gke-prod - target: kind: Application name: gitea patch: | - op: replace path: /spec/sources/0/helm/valueFiles/1 - value: $values/infra/values/aws-prod/gitea-values.yaml + value: $values/infra/values/gke-prod/gitea-values.yaml -# OpenCost: swap upc-dev → aws-prod +# OpenCost: swap upc-dev → gke-prod - target: kind: Application name: opencost patch: | - op: replace path: /spec/sources/0/helm/valueFiles/1 - value: $values/infra/values/aws-prod/opencost-values.yaml + value: $values/infra/values/gke-prod/opencost-values.yaml # TODO: add patches for keycloak, grafana, secrets, enterprise-apps # when deploying to this cluster (these are deployment-specific, not cloud-specific) diff --git a/infra/values/aws-dev/gitea-values.yaml b/infra/values/eks-dev/gitea-values.yaml similarity index 100% rename from infra/values/aws-dev/gitea-values.yaml rename to infra/values/eks-dev/gitea-values.yaml diff --git a/infra/values/aws-dev/opencost-values.yaml b/infra/values/eks-dev/opencost-values.yaml similarity index 100% rename from infra/values/aws-dev/opencost-values.yaml rename to infra/values/eks-dev/opencost-values.yaml diff --git a/infra/values/aws-dev/traefik-values.yaml b/infra/values/eks-dev/traefik-values.yaml similarity index 100% rename from infra/values/aws-dev/traefik-values.yaml rename to infra/values/eks-dev/traefik-values.yaml diff --git a/infra/values/aws-prod/gitea-values.yaml b/infra/values/eks-prod/gitea-values.yaml similarity index 100% rename from infra/values/aws-prod/gitea-values.yaml rename to infra/values/eks-prod/gitea-values.yaml diff --git a/infra/values/aws-prod/opencost-values.yaml b/infra/values/eks-prod/opencost-values.yaml similarity index 100% rename from infra/values/aws-prod/opencost-values.yaml rename to infra/values/eks-prod/opencost-values.yaml diff --git a/infra/values/aws-prod/traefik-values.yaml b/infra/values/eks-prod/traefik-values.yaml similarity index 100% rename from infra/values/aws-prod/traefik-values.yaml rename to infra/values/eks-prod/traefik-values.yaml diff --git a/infra/values/gcp-dev/gitea-values.yaml b/infra/values/gke-dev/gitea-values.yaml similarity index 100% rename from infra/values/gcp-dev/gitea-values.yaml rename to infra/values/gke-dev/gitea-values.yaml diff --git a/infra/values/gcp-dev/opencost-values.yaml b/infra/values/gke-dev/opencost-values.yaml similarity index 100% rename from infra/values/gcp-dev/opencost-values.yaml rename to infra/values/gke-dev/opencost-values.yaml diff --git a/infra/values/gcp-dev/traefik-values.yaml b/infra/values/gke-dev/traefik-values.yaml similarity index 100% rename from infra/values/gcp-dev/traefik-values.yaml rename to infra/values/gke-dev/traefik-values.yaml diff --git a/infra/values/gcp-prod/gitea-values.yaml b/infra/values/gke-prod/gitea-values.yaml similarity index 100% rename from infra/values/gcp-prod/gitea-values.yaml rename to infra/values/gke-prod/gitea-values.yaml diff --git a/infra/values/gcp-prod/opencost-values.yaml b/infra/values/gke-prod/opencost-values.yaml similarity index 100% rename from infra/values/gcp-prod/opencost-values.yaml rename to infra/values/gke-prod/opencost-values.yaml diff --git a/infra/values/gcp-prod/traefik-values.yaml b/infra/values/gke-prod/traefik-values.yaml similarity index 100% rename from infra/values/gcp-prod/traefik-values.yaml rename to infra/values/gke-prod/traefik-values.yaml diff --git a/scripts/gitea-backup-aws.sh b/scripts/gitea-backup-eks.sh old mode 100755 new mode 100644 similarity index 93% rename from scripts/gitea-backup-aws.sh rename to scripts/gitea-backup-eks.sh index ebf0894..c4c5c02 --- a/scripts/gitea-backup-aws.sh +++ b/scripts/gitea-backup-eks.sh @@ -8,9 +8,9 @@ set -euo pipefail # For AWS, S3_ENDPOINT is typically https://s3..amazonaws.com # # Usage: -# ./scripts/gitea-backup-aws.sh list # list all backups -# ./scripts/gitea-backup-aws.sh download # download a backup to current dir -# ./scripts/gitea-backup-aws.sh download latest # download the most recent backup +# ./scripts/gitea-backup-eks.sh list # list all backups +# ./scripts/gitea-backup-eks.sh download # download a backup to current dir +# ./scripts/gitea-backup-eks.sh download latest # download the most recent backup NAMESPACE="gitea" SECRET="gitea-backup-s3" diff --git a/scripts/gitea-backup-gcp.sh b/scripts/gitea-backup-gke.sh old mode 100755 new mode 100644 similarity index 94% rename from scripts/gitea-backup-gcp.sh rename to scripts/gitea-backup-gke.sh index 54fb7ef..bfed6b6 --- a/scripts/gitea-backup-gcp.sh +++ b/scripts/gitea-backup-gke.sh @@ -9,9 +9,9 @@ set -euo pipefail # (alternatively, use Workload Identity and omit the key) # # Usage: -# ./scripts/gitea-backup-gcp.sh list # list all backups -# ./scripts/gitea-backup-gcp.sh download # download a backup -# ./scripts/gitea-backup-gcp.sh download latest # download the most recent backup +# ./scripts/gitea-backup-gke.sh list # list all backups +# ./scripts/gitea-backup-gke.sh download # download a backup +# ./scripts/gitea-backup-gke.sh download latest # download the most recent backup NAMESPACE="gitea" SECRET="gitea-backup-gcs" -- 2.49.1 From acc9bb1a856a5567f08e307df07d02545c24fbcc Mon Sep 17 00:00:00 2001 From: Danijel Simeunovic Date: Wed, 22 Apr 2026 21:53:44 +0200 Subject: [PATCH 12/15] sync --- infra/overlays/aks-dev/kustomization.yaml | 37 ++++++++++++++++++++-- infra/overlays/aks-prod/kustomization.yaml | 37 ++++++++++++++++++++-- infra/overlays/eks-dev/kustomization.yaml | 37 ++++++++++++++++++++-- infra/overlays/eks-prod/kustomization.yaml | 37 ++++++++++++++++++++-- infra/overlays/gke-dev/kustomization.yaml | 37 ++++++++++++++++++++-- infra/overlays/gke-prod/kustomization.yaml | 37 ++++++++++++++++++++-- 6 files changed, 210 insertions(+), 12 deletions(-) diff --git a/infra/overlays/aks-dev/kustomization.yaml b/infra/overlays/aks-dev/kustomization.yaml index c230763..185869f 100644 --- a/infra/overlays/aks-dev/kustomization.yaml +++ b/infra/overlays/aks-dev/kustomization.yaml @@ -13,6 +13,24 @@ patches: path: /spec/sources/0/helm/valueFiles/1 value: $values/infra/values/aks-dev/traefik-values.yaml +# Keycloak: swap upc-dev → aks-dev +- target: + kind: Application + name: keycloak + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/aks-dev/keycloak-values.yaml + +# Grafana: swap upc-dev → aks-dev +- target: + kind: Application + name: grafana + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/aks-dev/grafana-values.yaml + # Gitea: swap upc-dev → aks-dev - target: kind: Application @@ -31,5 +49,20 @@ patches: path: /spec/sources/0/helm/valueFiles/1 value: $values/infra/values/aks-dev/opencost-values.yaml -# TODO: add patches for keycloak, grafana, secrets, enterprise-apps -# when deploying to this cluster (these are deployment-specific, not cloud-specific) +# Secrets: change path to aks-dev +- target: + kind: Application + name: secrets + patch: | + - op: replace + path: /spec/source/path + value: secrets/aks-dev + +# Enterprise-apps: point to aks-dev overlay +- target: + kind: Application + name: enterprise-apps + patch: | + - op: replace + path: /spec/source/path + value: apps/overlays/aks-dev diff --git a/infra/overlays/aks-prod/kustomization.yaml b/infra/overlays/aks-prod/kustomization.yaml index 5cadfd5..73b0aaa 100644 --- a/infra/overlays/aks-prod/kustomization.yaml +++ b/infra/overlays/aks-prod/kustomization.yaml @@ -13,6 +13,24 @@ patches: path: /spec/sources/0/helm/valueFiles/1 value: $values/infra/values/aks-prod/traefik-values.yaml +# Keycloak: swap upc-dev → aks-prod +- target: + kind: Application + name: keycloak + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/aks-prod/keycloak-values.yaml + +# Grafana: swap upc-dev → aks-prod +- target: + kind: Application + name: grafana + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/aks-prod/grafana-values.yaml + # Gitea: swap upc-dev → aks-prod - target: kind: Application @@ -31,5 +49,20 @@ patches: path: /spec/sources/0/helm/valueFiles/1 value: $values/infra/values/aks-prod/opencost-values.yaml -# TODO: add patches for keycloak, grafana, secrets, enterprise-apps -# when deploying to this cluster (these are deployment-specific, not cloud-specific) +# Secrets: change path to aks-prod +- target: + kind: Application + name: secrets + patch: | + - op: replace + path: /spec/source/path + value: secrets/aks-prod + +# Enterprise-apps: point to aks-prod overlay +- target: + kind: Application + name: enterprise-apps + patch: | + - op: replace + path: /spec/source/path + value: apps/overlays/aks-prod diff --git a/infra/overlays/eks-dev/kustomization.yaml b/infra/overlays/eks-dev/kustomization.yaml index c8690bf..16e542a 100644 --- a/infra/overlays/eks-dev/kustomization.yaml +++ b/infra/overlays/eks-dev/kustomization.yaml @@ -13,6 +13,24 @@ patches: path: /spec/sources/0/helm/valueFiles/1 value: $values/infra/values/eks-dev/traefik-values.yaml +# Keycloak: swap upc-dev → eks-dev +- target: + kind: Application + name: keycloak + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/eks-dev/keycloak-values.yaml + +# Grafana: swap upc-dev → eks-dev +- target: + kind: Application + name: grafana + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/eks-dev/grafana-values.yaml + # Gitea: swap upc-dev → eks-dev - target: kind: Application @@ -31,5 +49,20 @@ patches: path: /spec/sources/0/helm/valueFiles/1 value: $values/infra/values/eks-dev/opencost-values.yaml -# TODO: add patches for keycloak, grafana, secrets, enterprise-apps -# when deploying to this cluster (these are deployment-specific, not cloud-specific) +# Secrets: change path to eks-dev +- target: + kind: Application + name: secrets + patch: | + - op: replace + path: /spec/source/path + value: secrets/eks-dev + +# Enterprise-apps: point to eks-dev overlay +- target: + kind: Application + name: enterprise-apps + patch: | + - op: replace + path: /spec/source/path + value: apps/overlays/eks-dev diff --git a/infra/overlays/eks-prod/kustomization.yaml b/infra/overlays/eks-prod/kustomization.yaml index 7ab683d..46be9a9 100644 --- a/infra/overlays/eks-prod/kustomization.yaml +++ b/infra/overlays/eks-prod/kustomization.yaml @@ -13,6 +13,24 @@ patches: path: /spec/sources/0/helm/valueFiles/1 value: $values/infra/values/eks-prod/traefik-values.yaml +# Keycloak: swap upc-dev → eks-prod +- target: + kind: Application + name: keycloak + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/eks-prod/keycloak-values.yaml + +# Grafana: swap upc-dev → eks-prod +- target: + kind: Application + name: grafana + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/eks-prod/grafana-values.yaml + # Gitea: swap upc-dev → eks-prod - target: kind: Application @@ -31,5 +49,20 @@ patches: path: /spec/sources/0/helm/valueFiles/1 value: $values/infra/values/eks-prod/opencost-values.yaml -# TODO: add patches for keycloak, grafana, secrets, enterprise-apps -# when deploying to this cluster (these are deployment-specific, not cloud-specific) +# Secrets: change path to eks-prod +- target: + kind: Application + name: secrets + patch: | + - op: replace + path: /spec/source/path + value: secrets/eks-prod + +# Enterprise-apps: point to eks-prod overlay +- target: + kind: Application + name: enterprise-apps + patch: | + - op: replace + path: /spec/source/path + value: apps/overlays/eks-prod diff --git a/infra/overlays/gke-dev/kustomization.yaml b/infra/overlays/gke-dev/kustomization.yaml index 147bb76..4d3da3e 100644 --- a/infra/overlays/gke-dev/kustomization.yaml +++ b/infra/overlays/gke-dev/kustomization.yaml @@ -13,6 +13,24 @@ patches: path: /spec/sources/0/helm/valueFiles/1 value: $values/infra/values/gke-dev/traefik-values.yaml +# Keycloak: swap upc-dev → gke-dev +- target: + kind: Application + name: keycloak + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/gke-dev/keycloak-values.yaml + +# Grafana: swap upc-dev → gke-dev +- target: + kind: Application + name: grafana + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/gke-dev/grafana-values.yaml + # Gitea: swap upc-dev → gke-dev - target: kind: Application @@ -31,5 +49,20 @@ patches: path: /spec/sources/0/helm/valueFiles/1 value: $values/infra/values/gke-dev/opencost-values.yaml -# TODO: add patches for keycloak, grafana, secrets, enterprise-apps -# when deploying to this cluster (these are deployment-specific, not cloud-specific) +# Secrets: change path to gke-dev +- target: + kind: Application + name: secrets + patch: | + - op: replace + path: /spec/source/path + value: secrets/gke-dev + +# Enterprise-apps: point to gke-dev overlay +- target: + kind: Application + name: enterprise-apps + patch: | + - op: replace + path: /spec/source/path + value: apps/overlays/gke-dev diff --git a/infra/overlays/gke-prod/kustomization.yaml b/infra/overlays/gke-prod/kustomization.yaml index d040c85..0f4a583 100644 --- a/infra/overlays/gke-prod/kustomization.yaml +++ b/infra/overlays/gke-prod/kustomization.yaml @@ -13,6 +13,24 @@ patches: path: /spec/sources/0/helm/valueFiles/1 value: $values/infra/values/gke-prod/traefik-values.yaml +# Keycloak: swap upc-dev → gke-prod +- target: + kind: Application + name: keycloak + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/gke-prod/keycloak-values.yaml + +# Grafana: swap upc-dev → gke-prod +- target: + kind: Application + name: grafana + patch: | + - op: replace + path: /spec/sources/0/helm/valueFiles/1 + value: $values/infra/values/gke-prod/grafana-values.yaml + # Gitea: swap upc-dev → gke-prod - target: kind: Application @@ -31,5 +49,20 @@ patches: path: /spec/sources/0/helm/valueFiles/1 value: $values/infra/values/gke-prod/opencost-values.yaml -# TODO: add patches for keycloak, grafana, secrets, enterprise-apps -# when deploying to this cluster (these are deployment-specific, not cloud-specific) +# Secrets: change path to gke-prod +- target: + kind: Application + name: secrets + patch: | + - op: replace + path: /spec/source/path + value: secrets/gke-prod + +# Enterprise-apps: point to gke-prod overlay +- target: + kind: Application + name: enterprise-apps + patch: | + - op: replace + path: /spec/source/path + value: apps/overlays/gke-prod -- 2.49.1 From f1dd61cecea913f412892162b3aa664a831012f9 Mon Sep 17 00:00:00 2001 From: Danijel Simeunovic Date: Wed, 22 Apr 2026 21:56:43 +0200 Subject: [PATCH 13/15] sync --- infra/values/aks-dev/gitea-values.yaml | 2 +- infra/values/aks-dev/grafana-values.yaml | 4 ++++ infra/values/aks-dev/keycloak-values.yaml | 3 +++ infra/values/aks-dev/opencost-values.yaml | 11 ++++------- infra/values/aks-dev/traefik-values.yaml | 13 ++++--------- infra/values/aks-prod/gitea-values.yaml | 2 +- infra/values/aks-prod/grafana-values.yaml | 4 ++++ infra/values/aks-prod/keycloak-values.yaml | 3 +++ infra/values/aks-prod/opencost-values.yaml | 11 ++++------- infra/values/aks-prod/traefik-values.yaml | 14 +++++--------- infra/values/eks-dev/gitea-values.yaml | 2 +- infra/values/eks-dev/grafana-values.yaml | 4 ++++ infra/values/eks-dev/keycloak-values.yaml | 3 +++ infra/values/eks-dev/opencost-values.yaml | 8 +++----- infra/values/eks-dev/traefik-values.yaml | 9 ++++----- infra/values/eks-prod/gitea-values.yaml | 2 +- infra/values/eks-prod/grafana-values.yaml | 4 ++++ infra/values/eks-prod/keycloak-values.yaml | 3 +++ infra/values/eks-prod/opencost-values.yaml | 8 +++----- infra/values/eks-prod/traefik-values.yaml | 10 +++++----- infra/values/gke-dev/gitea-values.yaml | 2 +- infra/values/gke-dev/grafana-values.yaml | 4 ++++ infra/values/gke-dev/keycloak-values.yaml | 3 +++ infra/values/gke-dev/opencost-values.yaml | 13 +++++++------ infra/values/gke-dev/traefik-values.yaml | 13 +++++-------- infra/values/gke-prod/gitea-values.yaml | 2 +- infra/values/gke-prod/grafana-values.yaml | 4 ++++ infra/values/gke-prod/keycloak-values.yaml | 3 +++ infra/values/gke-prod/opencost-values.yaml | 13 +++++++------ infra/values/gke-prod/traefik-values.yaml | 13 +++++-------- 30 files changed, 104 insertions(+), 86 deletions(-) create mode 100644 infra/values/aks-dev/grafana-values.yaml create mode 100644 infra/values/aks-dev/keycloak-values.yaml create mode 100644 infra/values/aks-prod/grafana-values.yaml create mode 100644 infra/values/aks-prod/keycloak-values.yaml create mode 100644 infra/values/eks-dev/grafana-values.yaml create mode 100644 infra/values/eks-dev/keycloak-values.yaml create mode 100644 infra/values/eks-prod/grafana-values.yaml create mode 100644 infra/values/eks-prod/keycloak-values.yaml create mode 100644 infra/values/gke-dev/grafana-values.yaml create mode 100644 infra/values/gke-dev/keycloak-values.yaml create mode 100644 infra/values/gke-prod/grafana-values.yaml create mode 100644 infra/values/gke-prod/keycloak-values.yaml diff --git a/infra/values/aks-dev/gitea-values.yaml b/infra/values/aks-dev/gitea-values.yaml index 5bb20ff..94e9760 100644 --- a/infra/values/aks-dev/gitea-values.yaml +++ b/infra/values/aks-dev/gitea-values.yaml @@ -1,4 +1,4 @@ -# Azure Managed Disk (Premium SSD via CSI driver) +# AKS-specific: Azure managed disk storage class persistence: storageClass: managed-csi-premium postgresql: diff --git a/infra/values/aks-dev/grafana-values.yaml b/infra/values/aks-dev/grafana-values.yaml new file mode 100644 index 0000000..3b10135 --- /dev/null +++ b/infra/values/aks-dev/grafana-values.yaml @@ -0,0 +1,4 @@ +# AKS-specific: Grafana hostname +ingress: + hosts: + - grafana.forteapps.net diff --git a/infra/values/aks-dev/keycloak-values.yaml b/infra/values/aks-dev/keycloak-values.yaml new file mode 100644 index 0000000..f66b945 --- /dev/null +++ b/infra/values/aks-dev/keycloak-values.yaml @@ -0,0 +1,3 @@ +# AKS-specific: Keycloak hostname +ingress: + hostname: id.forteapps.net diff --git a/infra/values/aks-dev/opencost-values.yaml b/infra/values/aks-dev/opencost-values.yaml index 98b30cd..64dcfa1 100644 --- a/infra/values/aks-dev/opencost-values.yaml +++ b/infra/values/aks-dev/opencost-values.yaml @@ -1,11 +1,8 @@ -# Azure native pricing via Billing API +# AKS-specific: Azure pricing via Cloud Billing API opencost: exporter: + cloudProviderApiKey: "" customPricing: - enabled: true - provider: azure + enabled: false azure: - subscriptionID: "" # <- populate - clientID: "" - clientSecret: "" - tenantID: "" + secretName: opencost-azure-billing diff --git a/infra/values/aks-dev/traefik-values.yaml b/infra/values/aks-dev/traefik-values.yaml index 7efa198..fd5c882 100644 --- a/infra/values/aks-dev/traefik-values.yaml +++ b/infra/values/aks-dev/traefik-values.yaml @@ -1,16 +1,11 @@ -# Azure AKS — Standard Load Balancer -# Note: Azure Standard LB does not support Proxy Protocol. -# Use externalTrafficPolicy: Local on the Traefik service to preserve -# client IPs, or deploy behind Azure Application Gateway. +# AKS-specific: Azure Load Balancer for Traefik service: annotations: - service.beta.kubernetes.io/azure-load-balancer-health-probe-request-path: "/ping" - spec: - externalTrafficPolicy: Local + service.beta.kubernetes.io/azure-load-balancer-health-probe-request-path: /ping ports: web: forwardedHeaders: - trustedIPs: "10.0.0.0/8,168.63.129.16/32" # <- VNet CIDR + Azure health probe + trustedIPs: "10.0.0.0/8" websecure: forwardedHeaders: - trustedIPs: "10.0.0.0/8,168.63.129.16/32" + trustedIPs: "10.0.0.0/8" diff --git a/infra/values/aks-prod/gitea-values.yaml b/infra/values/aks-prod/gitea-values.yaml index 5bb20ff..d035b5d 100644 --- a/infra/values/aks-prod/gitea-values.yaml +++ b/infra/values/aks-prod/gitea-values.yaml @@ -1,4 +1,4 @@ -# Azure Managed Disk (Premium SSD via CSI driver) +# AKS-specific: Azure managed disk storage class (prod) persistence: storageClass: managed-csi-premium postgresql: diff --git a/infra/values/aks-prod/grafana-values.yaml b/infra/values/aks-prod/grafana-values.yaml new file mode 100644 index 0000000..b1f7504 --- /dev/null +++ b/infra/values/aks-prod/grafana-values.yaml @@ -0,0 +1,4 @@ +# AKS-specific: Grafana hostname (prod) +ingress: + hosts: + - grafana.fortedigital.com diff --git a/infra/values/aks-prod/keycloak-values.yaml b/infra/values/aks-prod/keycloak-values.yaml new file mode 100644 index 0000000..97096e4 --- /dev/null +++ b/infra/values/aks-prod/keycloak-values.yaml @@ -0,0 +1,3 @@ +# AKS-specific: Keycloak hostname (prod) +ingress: + hostname: id.fortedigital.com diff --git a/infra/values/aks-prod/opencost-values.yaml b/infra/values/aks-prod/opencost-values.yaml index 98b30cd..d465129 100644 --- a/infra/values/aks-prod/opencost-values.yaml +++ b/infra/values/aks-prod/opencost-values.yaml @@ -1,11 +1,8 @@ -# Azure native pricing via Billing API +# AKS-specific: Azure pricing via Cloud Billing API (prod) opencost: exporter: + cloudProviderApiKey: "" customPricing: - enabled: true - provider: azure + enabled: false azure: - subscriptionID: "" # <- populate - clientID: "" - clientSecret: "" - tenantID: "" + secretName: opencost-azure-billing diff --git a/infra/values/aks-prod/traefik-values.yaml b/infra/values/aks-prod/traefik-values.yaml index 7efa198..469f276 100644 --- a/infra/values/aks-prod/traefik-values.yaml +++ b/infra/values/aks-prod/traefik-values.yaml @@ -1,16 +1,12 @@ -# Azure AKS — Standard Load Balancer -# Note: Azure Standard LB does not support Proxy Protocol. -# Use externalTrafficPolicy: Local on the Traefik service to preserve -# client IPs, or deploy behind Azure Application Gateway. +# AKS-specific: Azure Load Balancer for Traefik (prod) service: annotations: - service.beta.kubernetes.io/azure-load-balancer-health-probe-request-path: "/ping" - spec: - externalTrafficPolicy: Local + service.beta.kubernetes.io/azure-load-balancer-health-probe-request-path: /ping + service.beta.kubernetes.io/azure-load-balancer-internal: "false" ports: web: forwardedHeaders: - trustedIPs: "10.0.0.0/8,168.63.129.16/32" # <- VNet CIDR + Azure health probe + trustedIPs: "10.0.0.0/8" websecure: forwardedHeaders: - trustedIPs: "10.0.0.0/8,168.63.129.16/32" + trustedIPs: "10.0.0.0/8" diff --git a/infra/values/eks-dev/gitea-values.yaml b/infra/values/eks-dev/gitea-values.yaml index 597af4f..c55964f 100644 --- a/infra/values/eks-dev/gitea-values.yaml +++ b/infra/values/eks-dev/gitea-values.yaml @@ -1,4 +1,4 @@ -# AWS EBS gp3 storage class (requires EBS CSI driver) +# EKS-specific: gp3 storage class persistence: storageClass: gp3 postgresql: diff --git a/infra/values/eks-dev/grafana-values.yaml b/infra/values/eks-dev/grafana-values.yaml new file mode 100644 index 0000000..e5d932e --- /dev/null +++ b/infra/values/eks-dev/grafana-values.yaml @@ -0,0 +1,4 @@ +# EKS-specific: Grafana hostname +ingress: + hosts: + - grafana.forteapps.net diff --git a/infra/values/eks-dev/keycloak-values.yaml b/infra/values/eks-dev/keycloak-values.yaml new file mode 100644 index 0000000..ee027eb --- /dev/null +++ b/infra/values/eks-dev/keycloak-values.yaml @@ -0,0 +1,3 @@ +# EKS-specific: Keycloak hostname +ingress: + hostname: id.forteapps.net diff --git a/infra/values/eks-dev/opencost-values.yaml b/infra/values/eks-dev/opencost-values.yaml index 93ff67a..efd110a 100644 --- a/infra/values/eks-dev/opencost-values.yaml +++ b/infra/values/eks-dev/opencost-values.yaml @@ -1,12 +1,10 @@ -# AWS native pricing via Cost and Usage Reports +# EKS-specific: AWS pricing via Cost and Usage Report opencost: exporter: + cloudProviderApiKey: "" customPricing: - enabled: true - provider: aws + enabled: false aws: - service_key_name: "" # <- populate or use IRSA - service_key_secret: "" spot_data_region: "" spot_data_bucket: "" spot_data_prefix: "" diff --git a/infra/values/eks-dev/traefik-values.yaml b/infra/values/eks-dev/traefik-values.yaml index 34306f7..1390d17 100644 --- a/infra/values/eks-dev/traefik-values.yaml +++ b/infra/values/eks-dev/traefik-values.yaml @@ -1,14 +1,13 @@ -# AWS EKS — NLB with Proxy Protocol v2 for real client IPs +# EKS-specific: AWS NLB for Traefik service: annotations: - service.beta.kubernetes.io/aws-load-balancer-type: "external" - service.beta.kubernetes.io/aws-load-balancer-nlb-target-type: "ip" - service.beta.kubernetes.io/aws-load-balancer-scheme: "internet-facing" + service.beta.kubernetes.io/aws-load-balancer-type: nlb + service.beta.kubernetes.io/aws-load-balancer-scheme: internet-facing service.beta.kubernetes.io/aws-load-balancer-proxy-protocol: "*" ports: web: proxyProtocol: - trustedIPs: "10.0.0.0/8" # <- adjust to your VPC CIDR + trustedIPs: "10.0.0.0/8" forwardedHeaders: trustedIPs: "10.0.0.0/8" websecure: diff --git a/infra/values/eks-prod/gitea-values.yaml b/infra/values/eks-prod/gitea-values.yaml index 597af4f..7aae415 100644 --- a/infra/values/eks-prod/gitea-values.yaml +++ b/infra/values/eks-prod/gitea-values.yaml @@ -1,4 +1,4 @@ -# AWS EBS gp3 storage class (requires EBS CSI driver) +# EKS-specific: gp3 storage class (prod) persistence: storageClass: gp3 postgresql: diff --git a/infra/values/eks-prod/grafana-values.yaml b/infra/values/eks-prod/grafana-values.yaml new file mode 100644 index 0000000..2034392 --- /dev/null +++ b/infra/values/eks-prod/grafana-values.yaml @@ -0,0 +1,4 @@ +# EKS-specific: Grafana hostname (prod) +ingress: + hosts: + - grafana.fortedigital.com diff --git a/infra/values/eks-prod/keycloak-values.yaml b/infra/values/eks-prod/keycloak-values.yaml new file mode 100644 index 0000000..9797896 --- /dev/null +++ b/infra/values/eks-prod/keycloak-values.yaml @@ -0,0 +1,3 @@ +# EKS-specific: Keycloak hostname (prod) +ingress: + hostname: id.fortedigital.com diff --git a/infra/values/eks-prod/opencost-values.yaml b/infra/values/eks-prod/opencost-values.yaml index 93ff67a..ac86a76 100644 --- a/infra/values/eks-prod/opencost-values.yaml +++ b/infra/values/eks-prod/opencost-values.yaml @@ -1,12 +1,10 @@ -# AWS native pricing via Cost and Usage Reports +# EKS-specific: AWS pricing via Cost and Usage Report (prod) opencost: exporter: + cloudProviderApiKey: "" customPricing: - enabled: true - provider: aws + enabled: false aws: - service_key_name: "" # <- populate or use IRSA - service_key_secret: "" spot_data_region: "" spot_data_bucket: "" spot_data_prefix: "" diff --git a/infra/values/eks-prod/traefik-values.yaml b/infra/values/eks-prod/traefik-values.yaml index 34306f7..fd64496 100644 --- a/infra/values/eks-prod/traefik-values.yaml +++ b/infra/values/eks-prod/traefik-values.yaml @@ -1,14 +1,14 @@ -# AWS EKS — NLB with Proxy Protocol v2 for real client IPs +# EKS-specific: AWS NLB for Traefik (prod) service: annotations: - service.beta.kubernetes.io/aws-load-balancer-type: "external" - service.beta.kubernetes.io/aws-load-balancer-nlb-target-type: "ip" - service.beta.kubernetes.io/aws-load-balancer-scheme: "internet-facing" + service.beta.kubernetes.io/aws-load-balancer-type: nlb + service.beta.kubernetes.io/aws-load-balancer-scheme: internet-facing service.beta.kubernetes.io/aws-load-balancer-proxy-protocol: "*" + service.beta.kubernetes.io/aws-load-balancer-cross-zone-load-balancing-enabled: "true" ports: web: proxyProtocol: - trustedIPs: "10.0.0.0/8" # <- adjust to your VPC CIDR + trustedIPs: "10.0.0.0/8" forwardedHeaders: trustedIPs: "10.0.0.0/8" websecure: diff --git a/infra/values/gke-dev/gitea-values.yaml b/infra/values/gke-dev/gitea-values.yaml index b825aee..04ec9aa 100644 --- a/infra/values/gke-dev/gitea-values.yaml +++ b/infra/values/gke-dev/gitea-values.yaml @@ -1,4 +1,4 @@ -# GCP Persistent Disk (SSD via CSI driver) +# GKE-specific: SSD persistent disk storage class persistence: storageClass: premium-rwo postgresql: diff --git a/infra/values/gke-dev/grafana-values.yaml b/infra/values/gke-dev/grafana-values.yaml new file mode 100644 index 0000000..db36770 --- /dev/null +++ b/infra/values/gke-dev/grafana-values.yaml @@ -0,0 +1,4 @@ +# GKE-specific: Grafana hostname +ingress: + hosts: + - grafana.forteapps.net diff --git a/infra/values/gke-dev/keycloak-values.yaml b/infra/values/gke-dev/keycloak-values.yaml new file mode 100644 index 0000000..4c67591 --- /dev/null +++ b/infra/values/gke-dev/keycloak-values.yaml @@ -0,0 +1,3 @@ +# GKE-specific: Keycloak hostname +ingress: + hostname: id.forteapps.net diff --git a/infra/values/gke-dev/opencost-values.yaml b/infra/values/gke-dev/opencost-values.yaml index f3ea481..6534718 100644 --- a/infra/values/gke-dev/opencost-values.yaml +++ b/infra/values/gke-dev/opencost-values.yaml @@ -1,9 +1,10 @@ -# GCP native pricing via Cloud Billing API +# GKE-specific: GCP pricing via BigQuery billing export opencost: exporter: + cloudProviderApiKey: "" customPricing: - enabled: true - provider: gcp - gcp: - projectID: "" # <- populate with your GCP project ID - key: "" # <- or use Workload Identity + enabled: false + google: + key: "" + project_id: "" + billing_account: "" diff --git a/infra/values/gke-dev/traefik-values.yaml b/infra/values/gke-dev/traefik-values.yaml index 55351c0..96a78ab 100644 --- a/infra/values/gke-dev/traefik-values.yaml +++ b/infra/values/gke-dev/traefik-values.yaml @@ -1,15 +1,12 @@ -# GCP GKE — External passthrough Network Load Balancer +# GKE-specific: Google Cloud Load Balancer for Traefik service: annotations: - cloud.google.com/l4-rbs: "enabled" + cloud.google.com/neg: '{"ingress":true}' + networking.gke.io/load-balancer-type: External ports: web: - proxyProtocol: - trustedIPs: "10.0.0.0/8,35.191.0.0/16,130.211.0.0/22" # <- subnet CIDR + GCP health checks forwardedHeaders: - trustedIPs: "10.0.0.0/8,35.191.0.0/16,130.211.0.0/22" + trustedIPs: "10.0.0.0/8" websecure: - proxyProtocol: - trustedIPs: "10.0.0.0/8,35.191.0.0/16,130.211.0.0/22" forwardedHeaders: - trustedIPs: "10.0.0.0/8,35.191.0.0/16,130.211.0.0/22" + trustedIPs: "10.0.0.0/8" diff --git a/infra/values/gke-prod/gitea-values.yaml b/infra/values/gke-prod/gitea-values.yaml index b825aee..5df877a 100644 --- a/infra/values/gke-prod/gitea-values.yaml +++ b/infra/values/gke-prod/gitea-values.yaml @@ -1,4 +1,4 @@ -# GCP Persistent Disk (SSD via CSI driver) +# GKE-specific: SSD persistent disk storage class (prod) persistence: storageClass: premium-rwo postgresql: diff --git a/infra/values/gke-prod/grafana-values.yaml b/infra/values/gke-prod/grafana-values.yaml new file mode 100644 index 0000000..e0b0d37 --- /dev/null +++ b/infra/values/gke-prod/grafana-values.yaml @@ -0,0 +1,4 @@ +# GKE-specific: Grafana hostname (prod) +ingress: + hosts: + - grafana.fortedigital.com diff --git a/infra/values/gke-prod/keycloak-values.yaml b/infra/values/gke-prod/keycloak-values.yaml new file mode 100644 index 0000000..76ab384 --- /dev/null +++ b/infra/values/gke-prod/keycloak-values.yaml @@ -0,0 +1,3 @@ +# GKE-specific: Keycloak hostname (prod) +ingress: + hostname: id.fortedigital.com diff --git a/infra/values/gke-prod/opencost-values.yaml b/infra/values/gke-prod/opencost-values.yaml index f3ea481..404f49b 100644 --- a/infra/values/gke-prod/opencost-values.yaml +++ b/infra/values/gke-prod/opencost-values.yaml @@ -1,9 +1,10 @@ -# GCP native pricing via Cloud Billing API +# GKE-specific: GCP pricing via BigQuery billing export (prod) opencost: exporter: + cloudProviderApiKey: "" customPricing: - enabled: true - provider: gcp - gcp: - projectID: "" # <- populate with your GCP project ID - key: "" # <- or use Workload Identity + enabled: false + google: + key: "" + project_id: "" + billing_account: "" diff --git a/infra/values/gke-prod/traefik-values.yaml b/infra/values/gke-prod/traefik-values.yaml index 55351c0..7d70c40 100644 --- a/infra/values/gke-prod/traefik-values.yaml +++ b/infra/values/gke-prod/traefik-values.yaml @@ -1,15 +1,12 @@ -# GCP GKE — External passthrough Network Load Balancer +# GKE-specific: Google Cloud Load Balancer for Traefik (prod) service: annotations: - cloud.google.com/l4-rbs: "enabled" + cloud.google.com/neg: '{"ingress":true}' + networking.gke.io/load-balancer-type: External ports: web: - proxyProtocol: - trustedIPs: "10.0.0.0/8,35.191.0.0/16,130.211.0.0/22" # <- subnet CIDR + GCP health checks forwardedHeaders: - trustedIPs: "10.0.0.0/8,35.191.0.0/16,130.211.0.0/22" + trustedIPs: "10.0.0.0/8" websecure: - proxyProtocol: - trustedIPs: "10.0.0.0/8,35.191.0.0/16,130.211.0.0/22" forwardedHeaders: - trustedIPs: "10.0.0.0/8,35.191.0.0/16,130.211.0.0/22" + trustedIPs: "10.0.0.0/8" -- 2.49.1 From a89f2f30cefbd47fea660d6fd9430ede82c6ad1c Mon Sep 17 00:00:00 2001 From: Danijel Simeunovic Date: Wed, 22 Apr 2026 22:26:57 +0200 Subject: [PATCH 14/15] details --- clusters/aks-dev.yaml | 22 ++++++++++++---------- clusters/aks-prod.yaml | 22 ++++++++++++---------- clusters/eks-dev.yaml | 22 ++++++++++++---------- clusters/eks-prod.yaml | 22 ++++++++++++---------- clusters/gke-dev.yaml | 22 ++++++++++++---------- clusters/gke-prod.yaml | 22 ++++++++++++---------- clusters/upc-dev.yaml | 22 ++++++++++++---------- clusters/upc-prod.yaml | 22 ++++++++++++---------- infra/overlays/upc-prod/kustomization.yaml | 18 ------------------ 9 files changed, 96 insertions(+), 98 deletions(-) diff --git a/clusters/aks-dev.yaml b/clusters/aks-dev.yaml index 5a3ace2..739b81e 100644 --- a/clusters/aks-dev.yaml +++ b/clusters/aks-dev.yaml @@ -1,10 +1,12 @@ -clusterName: dev-aks # <- adjust to your AKS cluster name -domain: example.com # <- adjust to your domain -argocdDomain: argocd.example.com -grafanaDomain: grafana.example.com -keycloakDomain: id.example.com -dotaiDomain: kubemcp.example.com -dotaiUiDomain: kubemcpui.example.com -letsencryptEmail: admin@example.com # <- adjust -trustedIPs: "10.0.0.0/8,168.63.129.16/32" # <- VNet CIDR + Azure health probe -cloudProvider: azure +# Cluster config reference — values must match the corresponding overlay files. +# Read by bootstrap.sh at install time; NOT auto-propagated to ArgoCD value files. +clusterName: dev-aks # → infra/values/aks-dev/argocd-values.yaml (notifications.context.clusterName) +domain: example.com # → infra/values/base/gitea-values.yaml, renovate-values.yaml, keycloak-values.yaml (subdomains) +argocdDomain: argocd.example.com # → infra/values/aks-dev/argocd-values.yaml (global.domain) +grafanaDomain: grafana.example.com # → infra/values/aks-dev/grafana-values.yaml (ingress.hosts) +keycloakDomain: id.example.com # → infra/values/aks-dev/keycloak-values.yaml (ingress.hostname) +dotaiDomain: kubemcp.example.com # → infra/values/aks-dev/dot-ai-stack-values.yaml (dot-ai.ingress.host) — create if needed +dotaiUiDomain: kubemcpui.example.com # → infra/values/aks-dev/dot-ai-stack-values.yaml (dot-ai-ui.ingress.host) — create if needed +letsencryptEmail: admin@example.com # → cluster-resources/letsencrypt-issuer.yaml (spec.acme.email) +trustedIPs: "10.0.0.0/8,168.63.129.16/32" # → infra/values/aks-dev/traefik-values.yaml (ports.*.trustedIPs) — VNet CIDR + Azure health probe +cloudProvider: azure # → determines overlay directory and cloud-specific LB/storage annotations diff --git a/clusters/aks-prod.yaml b/clusters/aks-prod.yaml index 0be858e..1cbf06e 100644 --- a/clusters/aks-prod.yaml +++ b/clusters/aks-prod.yaml @@ -1,10 +1,12 @@ -clusterName: prod-aks # <- adjust to your AKS cluster name -domain: example.com # <- adjust to your domain -argocdDomain: argocd.example.com -grafanaDomain: grafana.example.com -keycloakDomain: id.example.com -dotaiDomain: kubemcp.example.com -dotaiUiDomain: kubemcpui.example.com -letsencryptEmail: admin@example.com # <- adjust -trustedIPs: "10.0.0.0/8,168.63.129.16/32" # <- VNet CIDR + Azure health probe -cloudProvider: azure +# Cluster config reference — values must match the corresponding overlay files. +# Read by bootstrap.sh at install time; NOT auto-propagated to ArgoCD value files. +clusterName: prod-aks # → infra/values/aks-prod/argocd-values.yaml (notifications.context.clusterName) +domain: example.com # → infra/values/base/gitea-values.yaml, renovate-values.yaml, keycloak-values.yaml (subdomains) +argocdDomain: argocd.example.com # → infra/values/aks-prod/argocd-values.yaml (global.domain) +grafanaDomain: grafana.example.com # → infra/values/aks-prod/grafana-values.yaml (ingress.hosts) +keycloakDomain: id.example.com # → infra/values/aks-prod/keycloak-values.yaml (ingress.hostname) +dotaiDomain: kubemcp.example.com # → infra/values/aks-prod/dot-ai-stack-values.yaml (dot-ai.ingress.host) — create if needed +dotaiUiDomain: kubemcpui.example.com # → infra/values/aks-prod/dot-ai-stack-values.yaml (dot-ai-ui.ingress.host) — create if needed +letsencryptEmail: admin@example.com # → cluster-resources/letsencrypt-issuer.yaml (spec.acme.email) +trustedIPs: "10.0.0.0/8,168.63.129.16/32" # → infra/values/aks-prod/traefik-values.yaml (ports.*.trustedIPs) — VNet CIDR + Azure health probe +cloudProvider: azure # → determines overlay directory and cloud-specific LB/storage annotations diff --git a/clusters/eks-dev.yaml b/clusters/eks-dev.yaml index 55ffa95..d110573 100644 --- a/clusters/eks-dev.yaml +++ b/clusters/eks-dev.yaml @@ -1,10 +1,12 @@ -clusterName: dev-eks # <- adjust to your EKS cluster name -domain: example.com # <- adjust to your domain -argocdDomain: argocd.example.com -grafanaDomain: grafana.example.com -keycloakDomain: id.example.com -dotaiDomain: kubemcp.example.com -dotaiUiDomain: kubemcpui.example.com -letsencryptEmail: admin@example.com # <- adjust -trustedIPs: "10.0.0.0/8" # <- adjust to your VPC CIDR -cloudProvider: eks +# Cluster config reference — values must match the corresponding overlay files. +# Read by bootstrap.sh at install time; NOT auto-propagated to ArgoCD value files. +clusterName: dev-eks # → infra/values/eks-dev/argocd-values.yaml (notifications.context.clusterName) +domain: example.com # → infra/values/base/gitea-values.yaml, renovate-values.yaml, keycloak-values.yaml (subdomains) +argocdDomain: argocd.example.com # → infra/values/eks-dev/argocd-values.yaml (global.domain) +grafanaDomain: grafana.example.com # → infra/values/eks-dev/grafana-values.yaml (ingress.hosts) +keycloakDomain: id.example.com # → infra/values/eks-dev/keycloak-values.yaml (ingress.hostname) +dotaiDomain: kubemcp.example.com # → infra/values/eks-dev/dot-ai-stack-values.yaml (dot-ai.ingress.host) — create if needed +dotaiUiDomain: kubemcpui.example.com # → infra/values/eks-dev/dot-ai-stack-values.yaml (dot-ai-ui.ingress.host) — create if needed +letsencryptEmail: admin@example.com # → cluster-resources/letsencrypt-issuer.yaml (spec.acme.email) +trustedIPs: "10.0.0.0/8" # → infra/values/eks-dev/traefik-values.yaml (ports.*.trustedIPs) — VPC CIDR +cloudProvider: eks # → determines overlay directory and cloud-specific LB/storage annotations diff --git a/clusters/eks-prod.yaml b/clusters/eks-prod.yaml index 8dcfc90..fcea9ca 100644 --- a/clusters/eks-prod.yaml +++ b/clusters/eks-prod.yaml @@ -1,10 +1,12 @@ -clusterName: prod-eks # <- adjust to your EKS cluster name -domain: example.com # <- adjust to your domain -argocdDomain: argocd.example.com -grafanaDomain: grafana.example.com -keycloakDomain: id.example.com -dotaiDomain: kubemcp.example.com -dotaiUiDomain: kubemcpui.example.com -letsencryptEmail: admin@example.com # <- adjust -trustedIPs: "10.0.0.0/8" # <- adjust to your VPC CIDR -cloudProvider: eks +# Cluster config reference — values must match the corresponding overlay files. +# Read by bootstrap.sh at install time; NOT auto-propagated to ArgoCD value files. +clusterName: prod-eks # → infra/values/eks-prod/argocd-values.yaml (notifications.context.clusterName) +domain: example.com # → infra/values/base/gitea-values.yaml, renovate-values.yaml, keycloak-values.yaml (subdomains) +argocdDomain: argocd.example.com # → infra/values/eks-prod/argocd-values.yaml (global.domain) +grafanaDomain: grafana.example.com # → infra/values/eks-prod/grafana-values.yaml (ingress.hosts) +keycloakDomain: id.example.com # → infra/values/eks-prod/keycloak-values.yaml (ingress.hostname) +dotaiDomain: kubemcp.example.com # → infra/values/eks-prod/dot-ai-stack-values.yaml (dot-ai.ingress.host) — create if needed +dotaiUiDomain: kubemcpui.example.com # → infra/values/eks-prod/dot-ai-stack-values.yaml (dot-ai-ui.ingress.host) — create if needed +letsencryptEmail: admin@example.com # → cluster-resources/letsencrypt-issuer.yaml (spec.acme.email) +trustedIPs: "10.0.0.0/8" # → infra/values/eks-prod/traefik-values.yaml (ports.*.trustedIPs) — VPC CIDR +cloudProvider: eks # → determines overlay directory and cloud-specific LB/storage annotations diff --git a/clusters/gke-dev.yaml b/clusters/gke-dev.yaml index 2bd2801..2c1ddbe 100644 --- a/clusters/gke-dev.yaml +++ b/clusters/gke-dev.yaml @@ -1,10 +1,12 @@ -clusterName: dev-gke # <- adjust to your GKE cluster name -domain: example.com # <- adjust to your domain -argocdDomain: argocd.example.com -grafanaDomain: grafana.example.com -keycloakDomain: id.example.com -dotaiDomain: kubemcp.example.com -dotaiUiDomain: kubemcpui.example.com -letsencryptEmail: admin@example.com # <- adjust -trustedIPs: "10.0.0.0/8,35.191.0.0/16,130.211.0.0/22" # <- subnet CIDR + GCP health checks -cloudProvider: gke +# Cluster config reference — values must match the corresponding overlay files. +# Read by bootstrap.sh at install time; NOT auto-propagated to ArgoCD value files. +clusterName: dev-gke # → infra/values/gke-dev/argocd-values.yaml (notifications.context.clusterName) +domain: example.com # → infra/values/base/gitea-values.yaml, renovate-values.yaml, keycloak-values.yaml (subdomains) +argocdDomain: argocd.example.com # → infra/values/gke-dev/argocd-values.yaml (global.domain) +grafanaDomain: grafana.example.com # → infra/values/gke-dev/grafana-values.yaml (ingress.hosts) +keycloakDomain: id.example.com # → infra/values/gke-dev/keycloak-values.yaml (ingress.hostname) +dotaiDomain: kubemcp.example.com # → infra/values/gke-dev/dot-ai-stack-values.yaml (dot-ai.ingress.host) — create if needed +dotaiUiDomain: kubemcpui.example.com # → infra/values/gke-dev/dot-ai-stack-values.yaml (dot-ai-ui.ingress.host) — create if needed +letsencryptEmail: admin@example.com # → cluster-resources/letsencrypt-issuer.yaml (spec.acme.email) +trustedIPs: "10.0.0.0/8,35.191.0.0/16,130.211.0.0/22" # → infra/values/gke-dev/traefik-values.yaml (ports.*.trustedIPs) — subnet + GCP health checks +cloudProvider: gke # → determines overlay directory and cloud-specific LB/storage annotations diff --git a/clusters/gke-prod.yaml b/clusters/gke-prod.yaml index 7d8740f..1283ec0 100644 --- a/clusters/gke-prod.yaml +++ b/clusters/gke-prod.yaml @@ -1,10 +1,12 @@ -clusterName: prod-gke # <- adjust to your GKE cluster name -domain: example.com # <- adjust to your domain -argocdDomain: argocd.example.com -grafanaDomain: grafana.example.com -keycloakDomain: id.example.com -dotaiDomain: kubemcp.example.com -dotaiUiDomain: kubemcpui.example.com -letsencryptEmail: admin@example.com # <- adjust -trustedIPs: "10.0.0.0/8,35.191.0.0/16,130.211.0.0/22" # <- subnet CIDR + GCP health checks -cloudProvider: gke +# Cluster config reference — values must match the corresponding overlay files. +# Read by bootstrap.sh at install time; NOT auto-propagated to ArgoCD value files. +clusterName: prod-gke # → infra/values/gke-prod/argocd-values.yaml (notifications.context.clusterName) +domain: example.com # → infra/values/base/gitea-values.yaml, renovate-values.yaml, keycloak-values.yaml (subdomains) +argocdDomain: argocd.example.com # → infra/values/gke-prod/argocd-values.yaml (global.domain) +grafanaDomain: grafana.example.com # → infra/values/gke-prod/grafana-values.yaml (ingress.hosts) +keycloakDomain: id.example.com # → infra/values/gke-prod/keycloak-values.yaml (ingress.hostname) +dotaiDomain: kubemcp.example.com # → infra/values/gke-prod/dot-ai-stack-values.yaml (dot-ai.ingress.host) — create if needed +dotaiUiDomain: kubemcpui.example.com # → infra/values/gke-prod/dot-ai-stack-values.yaml (dot-ai-ui.ingress.host) — create if needed +letsencryptEmail: admin@example.com # → cluster-resources/letsencrypt-issuer.yaml (spec.acme.email) +trustedIPs: "10.0.0.0/8,35.191.0.0/16,130.211.0.0/22" # → infra/values/gke-prod/traefik-values.yaml (ports.*.trustedIPs) — subnet + GCP health checks +cloudProvider: gke # → determines overlay directory and cloud-specific LB/storage annotations diff --git a/clusters/upc-dev.yaml b/clusters/upc-dev.yaml index 4813591..275c81d 100644 --- a/clusters/upc-dev.yaml +++ b/clusters/upc-dev.yaml @@ -1,10 +1,12 @@ -clusterName: dev-fd-no-svg1 -domain: forteapps.net -argocdDomain: argocd.127.0.0.1.nip.io -grafanaDomain: grafana.forteapps.net -keycloakDomain: id.forteapps.net -dotaiDomain: kubemcp.forteapps.net -dotaiUiDomain: kubemcpui.forteapps.net -letsencryptEmail: danijels@gmail.com -trustedIPs: "172.16.1.0/24" -cloudProvider: upcloud +# Cluster config reference — values must match the corresponding overlay files. +# Read by bootstrap.sh at install time; NOT auto-propagated to ArgoCD value files. +clusterName: dev-fd-no-svg1 # → infra/values/upc-dev/argocd-values.yaml (notifications.context.clusterName) +domain: forteapps.net # → infra/values/base/gitea-values.yaml, renovate-values.yaml, keycloak-values.yaml (subdomains) +argocdDomain: argocd.127.0.0.1.nip.io # → infra/values/upc-dev/argocd-values.yaml (global.domain) +grafanaDomain: grafana.forteapps.net # → infra/values/upc-dev/grafana-values.yaml (ingress.hosts) +keycloakDomain: id.forteapps.net # → infra/values/upc-dev/keycloak-values.yaml (ingress.hostname) +dotaiDomain: kubemcp.forteapps.net # → infra/values/upc-dev/dot-ai-stack-values.yaml (dot-ai.ingress.host) +dotaiUiDomain: kubemcpui.forteapps.net # → infra/values/upc-dev/dot-ai-stack-values.yaml (dot-ai-ui.ingress.host) +letsencryptEmail: danijels@gmail.com # → cluster-resources/letsencrypt-issuer.yaml (spec.acme.email) +trustedIPs: "172.16.1.0/24" # → infra/values/upc-dev/traefik-values.yaml (ports.*.trustedIPs) +cloudProvider: upcloud # → determines overlay directory and cloud-specific LB/storage annotations diff --git a/clusters/upc-prod.yaml b/clusters/upc-prod.yaml index feb6500..0397af9 100644 --- a/clusters/upc-prod.yaml +++ b/clusters/upc-prod.yaml @@ -1,10 +1,12 @@ -clusterName: prod-fd-no-svg1 -domain: fortedigital.com -argocdDomain: argocd.127.0.0.1.nip.io -grafanaDomain: grafana.fortedigital.com -keycloakDomain: id.fortedigital.com -dotaiDomain: kubemcp.fortedigital.com -dotaiUiDomain: kubemcpui.fortedigital.com -letsencryptEmail: danijel.simeunovic@fortedigital.com -trustedIPs: "172.16.1.0/24" -cloudProvider: upcloud +# Cluster config reference — values must match the corresponding overlay files. +# Read by bootstrap.sh at install time; NOT auto-propagated to ArgoCD value files. +clusterName: prod-fd-no-svg1 # → infra/values/upc-prod/argocd-values.yaml (notifications.context.clusterName) +domain: fortedigital.com # → infra/values/base/gitea-values.yaml, renovate-values.yaml, keycloak-values.yaml (subdomains) +argocdDomain: argocd.127.0.0.1.nip.io # → infra/values/upc-prod/argocd-values.yaml (global.domain) +grafanaDomain: grafana.fortedigital.com # → infra/values/upc-prod/grafana-values.yaml (ingress.hosts) +keycloakDomain: id.fortedigital.com # → infra/values/upc-prod/keycloak-values.yaml (ingress.hostname) +dotaiDomain: kubemcp.fortedigital.com # → infra/values/upc-prod/dot-ai-stack-values.yaml (dot-ai.ingress.host) +dotaiUiDomain: kubemcpui.fortedigital.com # → infra/values/upc-prod/dot-ai-stack-values.yaml (dot-ai-ui.ingress.host) +letsencryptEmail: danijel.simeunovic@fortedigital.com # → cluster-resources/letsencrypt-issuer.yaml (spec.acme.email) +trustedIPs: "172.16.1.0/24" # → infra/values/upc-prod/traefik-values.yaml (ports.*.trustedIPs) +cloudProvider: upcloud # → determines overlay directory and cloud-specific LB/storage annotations diff --git a/infra/overlays/upc-prod/kustomization.yaml b/infra/overlays/upc-prod/kustomization.yaml index 164a6b6..9242d39 100644 --- a/infra/overlays/upc-prod/kustomization.yaml +++ b/infra/overlays/upc-prod/kustomization.yaml @@ -66,21 +66,3 @@ patches: - op: replace path: /spec/source/path value: apps/overlays/upc-prod - -# Gitea: swap upc-dev → upc-prod -- target: - kind: Application - name: gitea - patch: | - - op: replace - path: /spec/sources/0/helm/valueFiles/1 - value: $values/infra/values/upc-prod/gitea-values.yaml - -# OpenCost: swap upc-dev → upc-prod -- target: - kind: Application - name: opencost - patch: | - - op: replace - path: /spec/sources/0/helm/valueFiles/1 - value: $values/infra/values/upc-prod/opencost-values.yaml -- 2.49.1 From c7cbfc712e75172a9ed7e09343e3e49741c66e67 Mon Sep 17 00:00:00 2001 From: Danijel Simeunovic Date: Fri, 24 Apr 2026 10:48:03 +0200 Subject: [PATCH 15/15] overlays --- docs/REFERENCE.md | 39 +++++++++++++++---- infra/base/secrets.yaml | 2 +- infra/overlays/upc-prod/kustomization.yaml | 2 +- .../argocd-forte-helm-secret-sealed.yaml | 0 .../argocd-mcp-credentials.yaml | 0 .../argocdmcp-auth-oidc-sealed.yaml | 0 secrets/{upc-dev => base}/dot-ai-secrets.yaml | 0 .../forte10x-app-credentials-sealed.yaml | 0 .../{ => base}/gitea-backup-s3-sealed.yaml | 0 .../{ => base}/gitea-credentials-sealed.yaml | 0 .../{ => base}/gitea-runner-token-sealed.yaml | 0 .../{ => base}/gitea-smtp-secret-sealed.yaml | 0 .../keycloak-credentials-sealed.yaml | 0 secrets/base/kustomization.yaml | 16 ++++++++ .../{ => base}/musicman-auth-oidc-sealed.yaml | 0 .../musicman-credentials.yaml | 0 secrets/{ => base}/renovate-env-sealed.yaml | 0 secrets/dot-ai-secrets-sealed.yaml | 18 --------- secrets/overlays/aks-dev/kustomization.yaml | 4 ++ secrets/overlays/aks-prod/kustomization.yaml | 4 ++ secrets/overlays/eks-dev/kustomization.yaml | 4 ++ secrets/overlays/eks-prod/kustomization.yaml | 4 ++ secrets/overlays/gke-dev/kustomization.yaml | 4 ++ secrets/overlays/gke-prod/kustomization.yaml | 4 ++ secrets/overlays/upc-dev/kustomization.yaml | 4 ++ secrets/overlays/upc-prod/kustomization.yaml | 4 ++ 26 files changed, 81 insertions(+), 28 deletions(-) rename secrets/{ => base}/argocd-forte-helm-secret-sealed.yaml (100%) rename secrets/{upc-dev => base}/argocd-mcp-credentials.yaml (100%) rename secrets/{upc-dev => base}/argocdmcp-auth-oidc-sealed.yaml (100%) rename secrets/{upc-dev => base}/dot-ai-secrets.yaml (100%) rename secrets/{upc-dev => base}/forte10x-app-credentials-sealed.yaml (100%) rename secrets/{ => base}/gitea-backup-s3-sealed.yaml (100%) rename secrets/{ => base}/gitea-credentials-sealed.yaml (100%) rename secrets/{ => base}/gitea-runner-token-sealed.yaml (100%) rename secrets/{ => base}/gitea-smtp-secret-sealed.yaml (100%) rename secrets/{upc-dev => base}/keycloak-credentials-sealed.yaml (100%) create mode 100644 secrets/base/kustomization.yaml rename secrets/{ => base}/musicman-auth-oidc-sealed.yaml (100%) rename secrets/{upc-dev => base}/musicman-credentials.yaml (100%) rename secrets/{ => base}/renovate-env-sealed.yaml (100%) delete mode 100644 secrets/dot-ai-secrets-sealed.yaml create mode 100644 secrets/overlays/aks-dev/kustomization.yaml create mode 100644 secrets/overlays/aks-prod/kustomization.yaml create mode 100644 secrets/overlays/eks-dev/kustomization.yaml create mode 100644 secrets/overlays/eks-prod/kustomization.yaml create mode 100644 secrets/overlays/gke-dev/kustomization.yaml create mode 100644 secrets/overlays/gke-prod/kustomization.yaml create mode 100644 secrets/overlays/upc-dev/kustomization.yaml create mode 100644 secrets/overlays/upc-prod/kustomization.yaml diff --git a/docs/REFERENCE.md b/docs/REFERENCE.md index ab162f3..e3ad7bc 100644 --- a/docs/REFERENCE.md +++ b/docs/REFERENCE.md @@ -148,12 +148,30 @@ launchpad/ │ └── auth-sidecar-injector.yaml │ ├── secrets/ # Application secrets (sealed) -│ ├── argocd-mcp-credentials.yaml -│ ├── dot-ai-secrets.yaml -│ ├── gitea-credentials-sealed.yaml -│ ├── gitea-runner-token-sealed.yaml -│ ├── mcp10x-credentials-sealed.yaml -│ └── musicman-credentials.yaml +│ ├── base/ # All SealedSecrets (shared across clouds) +│ │ ├── kustomization.yaml +│ │ ├── argocd-forte-helm-secret-sealed.yaml +│ │ ├── argocd-mcp-credentials.yaml +│ │ ├── argocdmcp-auth-oidc-sealed.yaml +│ │ ├── dot-ai-secrets.yaml +│ │ ├── forte10x-app-credentials-sealed.yaml +│ │ ├── gitea-backup-s3-sealed.yaml +│ │ ├── gitea-credentials-sealed.yaml +│ │ ├── gitea-runner-token-sealed.yaml +│ │ ├── gitea-smtp-secret-sealed.yaml +│ │ ├── keycloak-credentials-sealed.yaml +│ │ ├── musicman-auth-oidc-sealed.yaml +│ │ ├── musicman-credentials.yaml +│ │ └── renovate-env-sealed.yaml +│ └── overlays/ # Per-cloud overlays (reference base) +│ ├── aks-dev/kustomization.yaml +│ ├── aks-prod/kustomization.yaml +│ ├── eks-dev/kustomization.yaml +│ ├── eks-prod/kustomization.yaml +│ ├── gke-dev/kustomization.yaml +│ ├── gke-prod/kustomization.yaml +│ ├── upc-dev/kustomization.yaml +│ └── upc-prod/kustomization.yaml │ ├── scripts/ # Operational helper scripts │ ├── gitea-backup.sh # S3 backup helper (list/download) @@ -706,6 +724,10 @@ spec: **Chart**: `sealed-secrets/sealed-secrets-controller` **Namespace**: `kube-system` +**Directory Structure**: `secrets/base/` contains all SealedSecrets with a `kustomization.yaml`. Per-cloud overlays in `secrets/overlays//` reference the base via Kustomize. The ArgoCD `secrets` Application points to the active overlay (e.g., `secrets/overlays/upc-dev`), and `infra/overlays/upc-prod` patches the path to `secrets/overlays/upc-prod`. + +To add cloud-specific secrets, create a new SealedSecret in the overlay directory and add it to the overlay's `kustomization.yaml`. + **Public Certificate**: ```bash kubeseal --fetch-cert \ @@ -1734,8 +1756,9 @@ To add support for a new cloud (e.g., `oci-dev` for Oracle Cloud): - `opencost-values.yaml` — pricing model or cloud billing integration 3. **Kustomize overlay**: `infra/overlays/oci-dev/kustomization.yaml` — patch `valueFiles[1]` for each Application 4. **App-of-apps**: `_app-of-apps-oci-dev.yaml` — points to `infra/overlays/oci-dev` -5. **Sealed Secrets**: `secrets/oci-dev/` — TLS certs, credentials, backup S3 config -6. **Bootstrap**: `./bootstrap.sh oci-dev` +5. **Secrets overlay**: `secrets/overlays/oci-dev/kustomization.yaml` — references `../../base`, add cloud-specific SealedSecrets if needed +6. **Secrets patch**: Add patch to `infra/overlays/oci-dev/kustomization.yaml` to swap secrets path to `secrets/overlays/oci-dev` +7. **Bootstrap**: `./bootstrap.sh oci-dev` --- diff --git a/infra/base/secrets.yaml b/infra/base/secrets.yaml index 7eb57f9..8bb24e9 100644 --- a/infra/base/secrets.yaml +++ b/infra/base/secrets.yaml @@ -18,7 +18,7 @@ spec: project: default source: repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git - path: secrets/upc-dev + path: secrets/overlays/upc-dev destination: server: https://kubernetes.default.svc namespace: secrets diff --git a/infra/overlays/upc-prod/kustomization.yaml b/infra/overlays/upc-prod/kustomization.yaml index 9242d39..59ae0fa 100644 --- a/infra/overlays/upc-prod/kustomization.yaml +++ b/infra/overlays/upc-prod/kustomization.yaml @@ -56,7 +56,7 @@ patches: patch: | - op: replace path: /spec/source/path - value: secrets/upc-prod + value: secrets/overlays/upc-prod # Enterprise-apps: point to upc-prod overlay - target: diff --git a/secrets/argocd-forte-helm-secret-sealed.yaml b/secrets/base/argocd-forte-helm-secret-sealed.yaml similarity index 100% rename from secrets/argocd-forte-helm-secret-sealed.yaml rename to secrets/base/argocd-forte-helm-secret-sealed.yaml diff --git a/secrets/upc-dev/argocd-mcp-credentials.yaml b/secrets/base/argocd-mcp-credentials.yaml similarity index 100% rename from secrets/upc-dev/argocd-mcp-credentials.yaml rename to secrets/base/argocd-mcp-credentials.yaml diff --git a/secrets/upc-dev/argocdmcp-auth-oidc-sealed.yaml b/secrets/base/argocdmcp-auth-oidc-sealed.yaml similarity index 100% rename from secrets/upc-dev/argocdmcp-auth-oidc-sealed.yaml rename to secrets/base/argocdmcp-auth-oidc-sealed.yaml diff --git a/secrets/upc-dev/dot-ai-secrets.yaml b/secrets/base/dot-ai-secrets.yaml similarity index 100% rename from secrets/upc-dev/dot-ai-secrets.yaml rename to secrets/base/dot-ai-secrets.yaml diff --git a/secrets/upc-dev/forte10x-app-credentials-sealed.yaml b/secrets/base/forte10x-app-credentials-sealed.yaml similarity index 100% rename from secrets/upc-dev/forte10x-app-credentials-sealed.yaml rename to secrets/base/forte10x-app-credentials-sealed.yaml diff --git a/secrets/gitea-backup-s3-sealed.yaml b/secrets/base/gitea-backup-s3-sealed.yaml similarity index 100% rename from secrets/gitea-backup-s3-sealed.yaml rename to secrets/base/gitea-backup-s3-sealed.yaml diff --git a/secrets/gitea-credentials-sealed.yaml b/secrets/base/gitea-credentials-sealed.yaml similarity index 100% rename from secrets/gitea-credentials-sealed.yaml rename to secrets/base/gitea-credentials-sealed.yaml diff --git a/secrets/gitea-runner-token-sealed.yaml b/secrets/base/gitea-runner-token-sealed.yaml similarity index 100% rename from secrets/gitea-runner-token-sealed.yaml rename to secrets/base/gitea-runner-token-sealed.yaml diff --git a/secrets/gitea-smtp-secret-sealed.yaml b/secrets/base/gitea-smtp-secret-sealed.yaml similarity index 100% rename from secrets/gitea-smtp-secret-sealed.yaml rename to secrets/base/gitea-smtp-secret-sealed.yaml diff --git a/secrets/upc-dev/keycloak-credentials-sealed.yaml b/secrets/base/keycloak-credentials-sealed.yaml similarity index 100% rename from secrets/upc-dev/keycloak-credentials-sealed.yaml rename to secrets/base/keycloak-credentials-sealed.yaml diff --git a/secrets/base/kustomization.yaml b/secrets/base/kustomization.yaml new file mode 100644 index 0000000..5c103d2 --- /dev/null +++ b/secrets/base/kustomization.yaml @@ -0,0 +1,16 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: +- argocd-forte-helm-secret-sealed.yaml +- argocd-mcp-credentials.yaml +- argocdmcp-auth-oidc-sealed.yaml +- dot-ai-secrets.yaml +- forte10x-app-credentials-sealed.yaml +- gitea-backup-s3-sealed.yaml +- gitea-credentials-sealed.yaml +- gitea-runner-token-sealed.yaml +- gitea-smtp-secret-sealed.yaml +- keycloak-credentials-sealed.yaml +- musicman-auth-oidc-sealed.yaml +- musicman-credentials.yaml +- renovate-env-sealed.yaml diff --git a/secrets/musicman-auth-oidc-sealed.yaml b/secrets/base/musicman-auth-oidc-sealed.yaml similarity index 100% rename from secrets/musicman-auth-oidc-sealed.yaml rename to secrets/base/musicman-auth-oidc-sealed.yaml diff --git a/secrets/upc-dev/musicman-credentials.yaml b/secrets/base/musicman-credentials.yaml similarity index 100% rename from secrets/upc-dev/musicman-credentials.yaml rename to secrets/base/musicman-credentials.yaml diff --git a/secrets/renovate-env-sealed.yaml b/secrets/base/renovate-env-sealed.yaml similarity index 100% rename from secrets/renovate-env-sealed.yaml rename to secrets/base/renovate-env-sealed.yaml diff --git a/secrets/dot-ai-secrets-sealed.yaml b/secrets/dot-ai-secrets-sealed.yaml deleted file mode 100644 index 5dd9590..0000000 --- a/secrets/dot-ai-secrets-sealed.yaml +++ /dev/null @@ -1,18 +0,0 @@ ---- -apiVersion: bitnami.com/v1alpha1 -kind: SealedSecret -metadata: - creationTimestamp: null - name: dot-ai-secrets - namespace: dot-ai -spec: - encryptedData: - anthropic-api-key: AgAdnPQzl2SNSqyAZkoBdEEGEjXfpMJUNMg4e040vxri4jbjoTnmwQ/DjmmIGtoInjhQA3NZRUKcIuDrO7nGMXFOPY9tSfhpdaAMWTji1CVZvmdJnrQwZY1LFBwgbozq3RSZZQQcZd2EPrhhsU5UlmacKk2WpuQdq76twfdU5WVD8xalxbt0H5UDvihuQa3sYX/rUIDZK2Th5IfaFqYZk5JvaxR8PFwBh9IOooGewWXWrsxVT510lxHRotSDIgKt/jl8ymsVA7IpddnbQHr6K77it7BxR6fLvDGaTQeQW0RtPZwsLvB268OTwp338RQ2sjmVuUDErWViLuk1V6UFmj5vhRR0X2dy/EipkWEJwR0Zf8JCW+vAXJ4NFiVFjmOsiTXoLHCYp0k01EwFcPQpnswKSdaQ3tuCEa4Q+rHu2DiXyfSuZ1MnWnTyLSx9H51VYUgIPwQa+BUVoVnAswypw4yLQHrfLu9TSvsNl/OonP0dSmgSGaByTc1RzwpvHBUAaOYII2LuuvkF90oA4cChGkGe1KuYKHFqiBdaT9jrsfeBUpgqFAH0uH9DNjBjU5EjlUtV3bdO7wXDHct9EOBZniKMH7cIbXfT2TBaormeHNqFtXxSRXy1szDpXiDD1QDoAJx0ylrwwqix7XPBlqSt91OZ8N1VPSUPvfnTQf7zirVWJNckU9fW6tsnQ+GDOOEwERPEAhqxWuw6V0HMab4VzpbGgWuvtQY5CsI2bFUYWSZAIJ6H8E5ip3lb8ilWtYadhx8QZD3aKi7k5h4bFWd6M0rg0uj7bfbW8YXauTS6Uz4b9FlvgrAPkmcWG84um/jsmP6a0YhvJDGKHMHoUmY= - auth-token: AgBq/MM/+fqi1H6L5o/xFeKYMfcn6+bmbkepbq97O0Ob+dFKWuyfXmzqM2Dha+NKpXcu47qSBbLpaOdLS5ONq7JDIcZ2byW0ae9khBuL7k2mCa5ZPh96LS46c+v1qNJb6F4NQe+jWSx2H9LIShoihom+lRueBT1/uthW3hnUUUgQMgXU3NYimDNAg6JK6VgX3yKkI7ePLPAet7+ykaL1aPXwcfCAldcobPmls0vxMQDtgd+o4nLqx2sKArFplnwZ9G1SEz2dRXNFm8HI4HhgtOBdv1ISjXO8XGRZWnFqgX3s3BqcwFcPqVuFGHo+2ZvAUW+mdkuAEJOloJEoZXJkFCP+l7/yMV7/FmFAhntqfdTwijEJ+rP/sUbUNSzn6BKM2ITRGXEJkOeNq4xfpgS16AOs+O0DWkIAr0kWCJG+mkn94U7ALCGYQXtKLy0g/87MJ3IwaUU7gowVawHoDmpY0QoAYDJwpbIa9yMnlPOzJANkc99dl85sbLeQMvkkb4RqQlbMc80gkFFhbU5/0kKX483ylqhRi0b4ZjGHgl72s/8+FhxTDkSXJQ2HbrNPGlna+B7TAgxYZ9IS1cpw4wSNzSCk23Rt3STHnXuu/QXRLeMijXGBDFNJgU0JNKLp63JC1gftHcNhqRL6lxK1tLyo5+0Cnh/KJN64b1DpPXZnzdaeR25GQFSDxsymjLm2BFATtufRPJqeIT7tn5TRGTr97fH6LQv/LuJ4VnjS6WLsQoFdUhDuNug2LDuyLHjpKg== - openai-api-key: AgCQR+HezEHwiwFD1pIkla1Byzz91SBoUyaWVTTuBrBDq201KvlLmqahjQwpKWs4YvqhmKkbF/mXKuMSyFut72IwH025tfmzzmTryOD6bOQDxI0Ws5NndnztzKv2qw2Js0c+6lAOJR+lEuo1ynGlG3hfS+bGShShvLZIDcD/hDa8IfhQBh7fKyFslJ52KxKK+zeEFDVQcx6Lrq/zP9IPH2QXz0bVQYlRyrQ4vqONO9h2pjxNAhDxuJ5FPk+Hb4ClGjyRPHFT34ZYsYdvHUgkjL3nOeaOUrc0GGJOKYZChfsK/JrqX8iOqgbE+0vQvMX+q8Tr6Ynr0KRKMcGPr6ak3eCNknJaZ1EABtkyUS2u5TzKqMzYq5DF4kpvPApIvaQW+VS05zD8piTQSZEFNRwwXDpyru/R4MmPvwt7OdSM0SJpQ8kR7tsuRgBPFY2Eduk6fhrDmMVgHze3AoRaqyh87CeqR3Z7/XofbdgZBqEp2vwiY425ArB6yMLpVvO6eB+yoTgCJ/UpfOxBDHE1M6U3goJhk/YeOy9UpTfRD1VyA2OuzJliDNtC784wxnGAsOk3qKk1bjjBqUzwITK41mOWqNLKCn4Ol9lXZtbbqLIiU4lXv4Pl93mVSuPLOIXINLGMRFl0rlvDICEjrrfE+JmwKx6i45sqsk3/hz1Fb+/bKFo7pl9JnAXvr5WfDW/rflwBrokfJVeYsSm6R2yxGWlosrKZIwIRctOut1EbbylurI5pIPp6vHguyIvZDDxwj3Qk3ewU/WVAcI9989aLR++UrZ5FGXt3apMk8BY9bq7DIQOUtgfPO98+cVPdoZSIh5bhQpCHAVPMGcGTdIPkuQbxSai0FsP8ipdHx0fluI6p/4v1Rv/BqZH0X8dnwPQoqUhSD+C575w511Fc8PEzgaG63S9hHx5Azw== - ui-auth-token: AgBgKRwErv5MtWIdqSN5BSQ/deHFE4469gzqL6gwp/3JidtBEiAAyuOIbc9dRCWuJNcdtixKOZT1rKuI8O/e6oJ6ABGAx+ckDfH468VKsR4AJhdZGcxub5j79NKccbNA5MKTnqxlU05zukUOkgw3wdsOyuQr3RnfL31GFbEVyDMej+Xr7Rs0fWrfqpasCi45/PEi8fkofMg45kGc+LMfDgovNtkKla2MAXwYlUk24SA+lgCFoG2DHB50GdTK2byCks4Px4J3jQqqHdLUfC+/gyqimPoVUsVGb5SY0xeNepKfTz7lHEkmDOB9R1wfv7pUaLMapc+eVrVN7reLHKOA47IEedDpnlLm/fyEfPe7ktkejc59tPyIyxBubrN+Vb/+6bDgi7xsXy/N5uD/2sPqWVgI2D7veWOJEjM+GYOYeb2iRbf7KlrokCXD/gRMiQBKqYyUdjWx40MjrhxzPArOa+cL0kb1CUgwuyjmqq5hNIUO2wo6/kkeNtUeT7r067LE5rtMoZG2EAfw/xrL1CI2F+3c72JzRd//aClt1MsSfPPPoFz0TlWSSc7qNDhYHuQf//G/Zd29Nk/Ac52HVwdkl2AXJE/GIFdwi+ypqK5mjmSUTn/JVE0ZaA3OpHOF/01meISuqBo+HuAWCV8sw6en0F8AF+DF8rw8t5hDdexScXep5QuJmm4CYgqThyjz2V5xME9oMmGA+Yiu/MJ4AlkLowijpXkKEWpEOBRpRRhu2q2szhZqmx1oKJw+qJ40CQ== - template: - metadata: - creationTimestamp: null - name: dot-ai-secrets - namespace: dot-ai diff --git a/secrets/overlays/aks-dev/kustomization.yaml b/secrets/overlays/aks-dev/kustomization.yaml new file mode 100644 index 0000000..4e4f197 --- /dev/null +++ b/secrets/overlays/aks-dev/kustomization.yaml @@ -0,0 +1,4 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: +- ../../base diff --git a/secrets/overlays/aks-prod/kustomization.yaml b/secrets/overlays/aks-prod/kustomization.yaml new file mode 100644 index 0000000..4e4f197 --- /dev/null +++ b/secrets/overlays/aks-prod/kustomization.yaml @@ -0,0 +1,4 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: +- ../../base diff --git a/secrets/overlays/eks-dev/kustomization.yaml b/secrets/overlays/eks-dev/kustomization.yaml new file mode 100644 index 0000000..4e4f197 --- /dev/null +++ b/secrets/overlays/eks-dev/kustomization.yaml @@ -0,0 +1,4 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: +- ../../base diff --git a/secrets/overlays/eks-prod/kustomization.yaml b/secrets/overlays/eks-prod/kustomization.yaml new file mode 100644 index 0000000..4e4f197 --- /dev/null +++ b/secrets/overlays/eks-prod/kustomization.yaml @@ -0,0 +1,4 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: +- ../../base diff --git a/secrets/overlays/gke-dev/kustomization.yaml b/secrets/overlays/gke-dev/kustomization.yaml new file mode 100644 index 0000000..4e4f197 --- /dev/null +++ b/secrets/overlays/gke-dev/kustomization.yaml @@ -0,0 +1,4 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: +- ../../base diff --git a/secrets/overlays/gke-prod/kustomization.yaml b/secrets/overlays/gke-prod/kustomization.yaml new file mode 100644 index 0000000..4e4f197 --- /dev/null +++ b/secrets/overlays/gke-prod/kustomization.yaml @@ -0,0 +1,4 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: +- ../../base diff --git a/secrets/overlays/upc-dev/kustomization.yaml b/secrets/overlays/upc-dev/kustomization.yaml new file mode 100644 index 0000000..4e4f197 --- /dev/null +++ b/secrets/overlays/upc-dev/kustomization.yaml @@ -0,0 +1,4 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: +- ../../base diff --git a/secrets/overlays/upc-prod/kustomization.yaml b/secrets/overlays/upc-prod/kustomization.yaml new file mode 100644 index 0000000..4e4f197 --- /dev/null +++ b/secrets/overlays/upc-prod/kustomization.yaml @@ -0,0 +1,4 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: +- ../../base -- 2.49.1