From 55af9fbe55eca852c6eb0c01be682fa271f6be36 Mon Sep 17 00:00:00 2001 From: Thomas Deutsch Date: Thu, 20 Jun 2024 17:18:52 +0200 Subject: [PATCH] Initial commit for Talos :rocket: --- .sops.yaml | 12 + Taskfile.yaml | 2 +- .../cert-manager/app/helmrelease.yaml.j2 | 2 +- .../apps/cert-manager/cert-manager/ks.yaml.j2 | 4 +- .../webhooks/app/github/receiver.yaml.j2 | 2 +- .../apps/flux-system/webhooks/ks.yaml.j2 | 2 +- .../cilium/app/helmrelease.yaml.j2 | 2 +- .../apps/kube-system/cilium/ks.yaml.j2 | 4 +- .../apps/kube-system/coredns/ks.yaml.j2 | 2 +- .../kubelet-csr-approver/ks.yaml.j2 | 2 +- .../kube-system/metrics-server/ks.yaml.j2 | 2 +- .../reloader/app/helmrelease.yaml.j2 | 2 +- .../apps/kube-system/reloader/ks.yaml.j2 | 2 +- .../spegel/app/helmrelease.yaml.j2 | 2 +- .../apps/kube-system/spegel/ks.yaml.j2 | 2 +- .../cloudflared/app/helmrelease.yaml.j2 | 2 +- .../apps/network/cloudflared/ks.yaml.j2 | 2 +- .../apps/network/echo-server/ks.yaml.j2 | 2 +- .../external-dns/app/helmrelease.yaml.j2 | 2 +- .../apps/network/external-dns/ks.yaml.j2 | 2 +- .../apps/network/ingress-nginx/ks.yaml.j2 | 6 +- .../apps/network/k8s-gateway/ks.yaml.j2 | 2 +- .../prometheus-operator-crds/ks.yaml.j2 | 2 +- .../apps/openebs-system/openebs/ks.yaml.j2 | 2 +- .../kubernetes/bootstrap/helmfile.yaml.j2 | 4 +- .../bootstrap/talos/talconfig.yaml.j2 | 2 +- .../templates/kubernetes/flux/apps.yaml.j2 | 2 +- .../kubernetes/flux/config/cluster.yaml.j2 | 4 +- .../cert-manager/app/helmrelease.yaml | 30 ++ .../cert-manager/app/kustomization.yaml | 5 + .../cert-manager/issuers/issuers.yaml | 41 ++ .../cert-manager/issuers/kustomization.yaml | 6 + .../cert-manager/issuers/secret.sops.yaml | 26 + .../apps/cert-manager/cert-manager/ks.yaml | 42 ++ .../apps/cert-manager/kustomization.yaml | 6 + kubernetes/apps/cert-manager/namespace.yaml | 7 + .../apps/flux-system/kustomization.yaml | 8 + .../monitoring/app/kustomization.yaml | 8 + .../monitoring/app/podmonitor.yaml | 31 ++ .../monitoring/app/prometheusrule.yaml | 31 ++ .../apps/flux-system/monitoring/ks.yaml | 22 + kubernetes/apps/flux-system/namespace.yaml | 7 + .../weave-gitops/app/externalsecret.yaml | 47 ++ .../weave-gitops/app/helmrelease.yaml | 71 +++ .../weave-gitops/app/kustomization.yaml | 9 + .../flux-system/weave-gitops/app/rbac.yaml | 13 + .../apps/flux-system/weave-gitops/ks.yaml | 21 + .../webhooks/app/github/ingress.yaml | 21 + .../webhooks/app/github/kustomization.yaml | 7 + .../webhooks/app/github/receiver.yaml | 25 + .../webhooks/app/github/secret.sops.yaml | 26 + .../webhooks/app/kustomization.yaml | 5 + kubernetes/apps/flux-system/webhooks/ks.yaml | 20 + .../kube-system/cilium/app/helm-values.yaml | 57 +++ .../kube-system/cilium/app/helmrelease.yaml | 74 +++ .../kube-system/cilium/app/kustomization.yaml | 11 + .../cilium/app/kustomizeconfig.yaml | 7 + .../kube-system/cilium/config/cilium-l2.yaml | 24 + .../cilium/config/kustomization.yaml | 5 + kubernetes/apps/kube-system/cilium/ks.yaml | 42 ++ .../kube-system/coredns/app/helm-values.yaml | 50 ++ .../kube-system/coredns/app/helmrelease.yaml | 26 + .../coredns/app/kustomization.yaml | 11 + .../coredns/app/kustomizeconfig.yaml | 7 + kubernetes/apps/kube-system/coredns/ks.yaml | 20 + .../kubelet-csr-approver/app/helm-values.yaml | 3 + .../kubelet-csr-approver/app/helmrelease.yaml | 30 ++ .../app/kustomization.yaml | 11 + .../app/kustomizeconfig.yaml | 7 + .../kube-system/kubelet-csr-approver/ks.yaml | 20 + .../app/helmrelease.yaml | 23 + .../app/kustomization.yaml | 5 + .../kube-system/kubernetes-replicator/ks.yaml | 20 + .../apps/kube-system/kustomization.yaml | 12 + .../metrics-server/app/helmrelease.yaml | 31 ++ .../metrics-server/app/kustomization.yaml | 5 + .../apps/kube-system/metrics-server/ks.yaml | 20 + kubernetes/apps/kube-system/namespace.yaml | 7 + .../kube-system/reloader/app/helmrelease.yaml | 29 ++ .../reloader/app/kustomization.yaml | 5 + kubernetes/apps/kube-system/reloader/ks.yaml | 20 + .../kube-system/spegel/app/helm-values.yaml | 7 + .../kube-system/spegel/app/helmrelease.yaml | 28 + .../kube-system/spegel/app/kustomization.yaml | 11 + .../spegel/app/kustomizeconfig.yaml | 7 + kubernetes/apps/kube-system/spegel/ks.yaml | 20 + .../media/calibre-web/app/helmrelease.yaml | 105 ++++ .../media/calibre-web/app/kustomization.yaml | 6 + kubernetes/apps/media/calibre-web/ks.yaml | 20 + kubernetes/apps/media/kustomization.yaml | 12 + .../media/mediabox/app/bazarr-ingress.yaml | 33 ++ .../apps/media/mediabox/app/gaps-ingress.yaml | 33 ++ .../media/mediabox/app/kustomization.yaml | 15 + .../media/mediabox/app/lldap-ingress.yaml | 25 + .../media/mediabox/app/notifiarr-ingress.yaml | 26 + .../media/mediabox/app/prowlarr-ingress.yaml | 33 ++ .../media/mediabox/app/radarr-ingress.yaml | 33 ++ .../media/mediabox/app/sabnzbd-ingress.yaml | 33 ++ .../apps/media/mediabox/app/service.yaml | 42 ++ .../media/mediabox/app/sonarr-ingress.yaml | 33 ++ kubernetes/apps/media/mediabox/ks.yaml | 21 + kubernetes/apps/media/namespace.yaml | 7 + .../apps/media/overseerr/app/helmrelease.yaml | 109 ++++ .../media/overseerr/app/kustomization.yaml | 5 + kubernetes/apps/media/overseerr/ks.yaml | 19 + .../media/plex-exporter/app/configmap.yaml | 19 + .../media/plex-exporter/app/deployment.yaml | 50 ++ .../plex-exporter/app/grafana-dashboard.yaml | 477 ++++++++++++++++++ .../plex-exporter/app/kustomization.yaml | 11 + .../app/plex-exporter-grafana-dashboard.json | 464 +++++++++++++++++ .../plex-exporter/app/service-monitor.yaml | 18 + .../apps/media/plex-exporter/app/service.yaml | 16 + kubernetes/apps/media/plex-exporter/ks.yaml | 21 + .../plex-trakt-sync/app/config/config.yml | 34 ++ .../plex-trakt-sync/app/helmrelease.yaml | 123 +++++ .../plex-trakt-sync/app/kustomization.yaml | 20 + kubernetes/apps/media/plex-trakt-sync/ks.yaml | 22 + .../apps/media/podsync/app/config/config.toml | 110 ++++ .../apps/media/podsync/app/helmrelease.yaml | 102 ++++ .../apps/media/podsync/app/kustomization.yaml | 12 + kubernetes/apps/media/podsync/ks.dis | 21 + .../media/readarr/app/externalsecret.yaml | 19 + .../apps/media/readarr/app/helmrelease.yaml | 118 +++++ .../apps/media/readarr/app/kustomization.yaml | 6 + kubernetes/apps/media/readarr/ks.yaml | 21 + .../apps/media/tautulli/app/helmrelease.yaml | 108 ++++ .../media/tautulli/app/kustomization.yaml | 7 + .../media/tautulli/exporter/helmrelease.yaml | 68 +++ .../tautulli/exporter/kustomization.yaml | 7 + kubernetes/apps/media/tautulli/ks.yaml | 44 ++ .../cloudflared/app/configs/config.yaml | 10 + .../network/cloudflared/app/dnsendpoint.yaml | 10 + .../network/cloudflared/app/helmrelease.yaml | 109 ++++ .../cloudflared/app/kustomization.yaml | 13 + .../network/cloudflared/app/secret.sops.yaml | 27 + kubernetes/apps/network/cloudflared/ks.yaml | 22 + .../network/echo-server/app/helmrelease.yaml | 91 ++++ .../echo-server/app/kustomization.yaml | 5 + kubernetes/apps/network/echo-server/ks.yaml | 20 + .../network/external-dns/app/helmrelease.yaml | 48 ++ .../external-dns/app/kustomization.yaml | 6 + .../network/external-dns/app/secret.sops.yaml | 26 + kubernetes/apps/network/external-dns/ks.yaml | 20 + .../certificates/kustomization.yaml | 6 + .../certificates/production.yaml | 34 ++ .../ingress-nginx/certificates/staging.yaml | 34 ++ .../ingress-nginx/external/helmrelease.yaml | 75 +++ .../ingress-nginx/external/kustomization.yaml | 5 + .../ingress-nginx/internal/helmrelease.yaml | 72 +++ .../ingress-nginx/internal/kustomization.yaml | 5 + kubernetes/apps/network/ingress-nginx/ks.yaml | 66 +++ .../network/k8s-gateway/app/helmrelease.yaml | 51 ++ .../k8s-gateway/app/kustomization.yaml | 5 + kubernetes/apps/network/k8s-gateway/ks.yaml | 20 + kubernetes/apps/network/kustomization.yaml | 10 + kubernetes/apps/network/namespace.yaml | 7 + .../app/alertmanager-discord-config.yaml | 23 + .../app/alertmanager-discord-deployment.yaml | 35 ++ .../app/alertmanager-discord-service.yaml | 15 + .../app/externalsecret.yaml | 19 + .../app/kustomization.yaml | 10 + .../alertmanager-discord/ks.yaml | 23 + .../blackbox-exporter/app/helmrelease.yaml | 85 ++++ .../blackbox-exporter/app/kustomization.yaml | 5 + .../observability/blackbox-exporter/ks.yaml | 37 ++ .../blackbox-exporter/probes/homelab.yaml | 14 + .../probes/kustomization.yaml | 5 + .../gatus/app/config/config.yaml | 51 ++ .../gatus/app/externalsecret.yaml | 19 + .../observability/gatus/app/helmrelease.yaml | 128 +++++ .../gatus/app/kustomization.yaml | 14 + .../apps/observability/gatus/app/rbac.yaml | 22 + kubernetes/apps/observability/gatus/ks.yaml | 23 + .../app/helmrelease.yaml | 452 +++++++++++++++++ .../app/kustomization.yaml | 7 + .../config/kustomization.yaml | 8 + .../config/prometheusrules.yaml | 26 + .../config/scrapeconfigs.yaml | 35 ++ .../kube-prometheus-stack/ks.yaml | 46 ++ .../apps/observability/kustomization.yaml | 17 + kubernetes/apps/observability/namespace.yaml | 7 + .../app/externalsecret.yaml | 19 + .../overseerr-exporter/app/helmrelease.yaml | 80 +++ .../overseerr-exporter/app/kustomization.yaml | 6 + .../observability/overseerr-exporter/ks.yaml | 21 + .../app/helmrelease.yaml | 22 + .../app/kustomization.yaml | 5 + .../prometheus-operator-crds/ks.yaml | 20 + .../prowlarr-exporter/app/externalsecret.yaml | 19 + .../prowlarr-exporter/app/helmrelease.yaml | 81 +++ .../prowlarr-exporter/app/kustomization.yaml | 6 + .../observability/prowlarr-exporter/ks.yaml | 20 + .../radarr-exporter/app/externalsecret.yaml | 19 + .../radarr-exporter/app/helmrelease.yaml | 82 +++ .../radarr-exporter/app/kustomization.yaml | 6 + .../observability/radarr-exporter/ks.yaml | 20 + .../sabnzbd-exporter/app/externalsecret.yaml | 19 + .../sabnzbd-exporter/app/helmrelease.yaml | 80 +++ .../sabnzbd-exporter/app/kustomization.yaml | 6 + .../observability/sabnzbd-exporter/ks.yaml | 20 + .../sonarr-exporter/app/externalsecret.yaml | 19 + .../sonarr-exporter/app/helmrelease.yaml | 82 +++ .../sonarr-exporter/app/kustomization.yaml | 6 + .../observability/sonarr-exporter/ks.yaml | 20 + .../speedtest-exporter/app/helmrelease.yaml | 77 +++ .../speedtest-exporter/app/kustomization.yaml | 5 + .../observability/speedtest-exporter/ks.yaml | 19 + .../tautulli-exporter/app/externalsecret.yaml | 19 + .../tautulli-exporter/app/helmrelease.yaml | 78 +++ .../tautulli-exporter/app/kustomization.yaml | 6 + .../observability/tautulli-exporter/ks.yaml | 21 + .../apps/openebs-system/kustomization.yaml | 6 + kubernetes/apps/openebs-system/namespace.yaml | 7 + .../openebs/app/helmrelease.yaml | 45 ++ .../openebs/app/kustomization.yaml | 5 + .../apps/openebs-system/openebs/ks.yaml | 20 + .../apps/productivity/kasm/app/ingress.yaml | 35 ++ .../productivity/kasm/app/kustomization.yaml | 8 + .../apps/productivity/kasm/app/service.yaml | 17 + kubernetes/apps/productivity/kasm/ks.yaml | 21 + .../apps/productivity/kustomization.yaml | 10 + .../linkding/app/externalsecret.yaml | 27 + .../linkding/app/helmrelease.yaml | 190 +++++++ .../linkding/app/kustomization.yaml | 7 + kubernetes/apps/productivity/linkding/ks.yaml | 23 + kubernetes/apps/productivity/namespace.yaml | 7 + .../productivity/octoprint/app/ingress.yaml | 33 ++ .../octoprint/app/kustomization.yaml | 8 + .../productivity/octoprint/app/service.yaml | 14 + .../apps/productivity/octoprint/ks.yaml | 21 + .../paperless/app/helmrelease-gotenberg.yaml | 40 ++ .../paperless/app/helmrelease-tika.yaml | 38 ++ .../paperless/app/helmrelease.yaml | 143 ++++++ .../paperless/app/kustomization.yaml | 8 + .../paperless/app/secret.sops.yaml | 28 + .../apps/productivity/paperless/ks.yaml | 42 ++ .../paperless/redis/helmrelease.yaml | 43 ++ .../paperless/redis/kustomization.yaml | 5 + .../webtrees/app/helmrelease.yaml | 137 +++++ .../webtrees/app/kustomization.yaml | 8 + .../webtrees/app/secret.sops.yaml | 26 + .../productivity/webtrees/db/cronjob.yaml | 53 ++ .../productivity/webtrees/db/helmrelease.yaml | 38 ++ .../webtrees/db/kustomization.yaml | 9 + .../productivity/webtrees/db/secret.sops.yaml | 28 + kubernetes/apps/productivity/webtrees/ks.yaml | 46 ++ .../apps/security/external-secrets/ks.yaml | 44 ++ .../operator/helmrelease.yaml | 33 ++ .../operator/kustomization.yaml | 6 + .../secretstores/doppler/kustomization.yaml | 7 + .../secretstores/doppler/secret.sops.yaml | 26 + .../secretstores/doppler/secretstore.yaml | 14 + .../secretstores/kustomization.yaml | 8 + .../secretstores/onepassword/helmrelease.yaml | 138 +++++ .../onepassword/kustomization.yaml | 8 + .../secretstores/onepassword/secret.sops.yaml | 28 + .../secretstores/onepassword/secretstore.yaml | 17 + kubernetes/apps/security/kustomization.yaml | 7 + .../security/kyverno/app/helmrelease.yaml | 84 +++ .../security/kyverno/app/kustomization.yaml | 5 + kubernetes/apps/security/kyverno/ks.yaml | 36 ++ .../kyverno/policies/gatus-external.yaml | 77 +++ .../kyverno/policies/gatus-internal.yaml | 77 +++ .../security/kyverno/policies/ingress.yaml | 32 ++ .../kyverno/policies/kustomization.yaml | 9 + .../security/kyverno/policies/limits.yaml | 44 ++ .../apps/security/kyverno/policies/ndots.yaml | 41 ++ kubernetes/apps/security/namespace.yaml | 7 + kubernetes/apps/storage/kustomization.yaml | 6 + .../storage/longhorn/app/helm-release.yaml | 82 +++ .../storage/longhorn/app/kustomization.yaml | 7 + .../storage/longhorn/conf/kustomization.yaml | 10 + .../conf/monitoring/kustomization.yaml | 8 + .../conf/monitoring/prometheusrule.yaml | 110 ++++ .../conf/monitoring/servicemonitor.yaml | 16 + .../longhorn/conf/other/kustomization.yaml | 7 + .../longhorn/conf/other/systembackup.yaml | 7 + .../conf/recurringjobs/30min-snapshot.yaml | 13 + .../conf/recurringjobs/daily-backup.yaml | 13 + .../conf/recurringjobs/daily-cleanup.yaml | 13 + .../conf/recurringjobs/daily-delete.yaml | 13 + .../conf/recurringjobs/daily-trim.yaml | 13 + .../conf/recurringjobs/hourly-backup.yaml | 13 + .../conf/recurringjobs/kustomization.yaml | 12 + .../storage/longhorn/conf/snap-class.yaml | 9 + kubernetes/apps/storage/longhorn/ks.yaml | 63 +++ .../longhorn/prereq/kustomization.yaml | 12 + .../prereq/longhorn-iscsi-installation.yaml | 40 ++ kubernetes/apps/storage/namespace.yaml | 7 + kubernetes/apps/tools/kustomization.yaml | 6 + kubernetes/apps/tools/namespace.yaml | 7 + .../tools/smtp-relay/app/config/maddy.conf | 24 + .../tools/smtp-relay/app/externalsecret.yaml | 22 + .../tools/smtp-relay/app/helmrelease.yaml | 98 ++++ .../tools/smtp-relay/app/kustomization.yaml | 13 + kubernetes/apps/tools/smtp-relay/ks.yaml | 24 + kubernetes/bootstrap/flux/kustomization.yaml | 61 +++ kubernetes/bootstrap/helmfile.yaml | 59 +++ .../bootstrap/talos/clusterconfig/.gitignore | 5 + kubernetes/bootstrap/talos/patches/README.md | 15 + .../talos/patches/controller/api-access.yaml | 8 + .../talos/patches/controller/cluster.yaml | 12 + .../disable-admission-controller.yaml | 2 + .../talos/patches/controller/etcd.yaml | 6 + .../patches/global/cluster-discovery.yaml | 7 + .../talos/patches/global/containerd.yaml | 12 + .../patches/global/disable-search-domain.yaml | 3 + .../talos/patches/global/hostdns.yaml | 6 + .../talos/patches/global/kubelet.yaml | 7 + .../talos/patches/global/openebs-local.yaml | 10 + .../talos/patches/global/sysctl.yaml | 7 + kubernetes/bootstrap/talos/talconfig.yaml | 114 +++++ .../bootstrap/talos/talsecret.sops.yaml | 43 ++ kubernetes/flux/apps.yaml | 56 ++ kubernetes/flux/config/cluster.yaml | 40 ++ kubernetes/flux/config/flux.yaml | 86 ++++ kubernetes/flux/config/kustomization.yaml | 6 + .../flux/repositories/git/kustomization.yaml | 4 + .../flux/repositories/helm/bitnami.yaml | 11 + kubernetes/flux/repositories/helm/bjw-s.yaml | 10 + kubernetes/flux/repositories/helm/cilium.yaml | 9 + .../flux/repositories/helm/coredns.yaml | 9 + .../flux/repositories/helm/external-dns.yaml | 9 + .../repositories/helm/external-secrets.yaml | 10 + .../flux/repositories/helm/ingress-nginx.yaml | 9 + .../flux/repositories/helm/jetstack.yaml | 9 + .../flux/repositories/helm/k8s-gateway.yaml | 9 + .../flux/repositories/helm/kustomization.yaml | 23 + .../repositories/helm/kyverno-charts.yaml | 10 + .../flux/repositories/helm/longhorn.yaml | 10 + .../repositories/helm/metrics-server.yaml | 9 + .../repositories/helm/mittwald-charts.yaml | 10 + .../flux/repositories/helm/openebs.yaml | 9 + .../flux/repositories/helm/postfinance.yaml | 9 + .../helm/prometheus-community.yaml | 10 + kubernetes/flux/repositories/helm/spegel.yaml | 10 + .../flux/repositories/helm/stakater.yaml | 9 + .../flux/repositories/helm/weave-gitops.yaml | 11 + .../flux/repositories/kustomization.yaml | 7 + .../flux/repositories/oci/kustomization.yaml | 4 + .../flux/vars/cluster-secrets.sops.yaml | 47 ++ kubernetes/flux/vars/cluster-settings.yaml | 9 + kubernetes/flux/vars/kustomization.yaml | 5 + scripts/rebuild-kustomizations.sh | 39 ++ 344 files changed, 10086 insertions(+), 33 deletions(-) create mode 100644 .sops.yaml create mode 100644 kubernetes/apps/cert-manager/cert-manager/app/helmrelease.yaml create mode 100644 kubernetes/apps/cert-manager/cert-manager/app/kustomization.yaml create mode 100644 kubernetes/apps/cert-manager/cert-manager/issuers/issuers.yaml create mode 100644 kubernetes/apps/cert-manager/cert-manager/issuers/kustomization.yaml create mode 100644 kubernetes/apps/cert-manager/cert-manager/issuers/secret.sops.yaml create mode 100644 kubernetes/apps/cert-manager/cert-manager/ks.yaml create mode 100644 kubernetes/apps/cert-manager/kustomization.yaml create mode 100644 kubernetes/apps/cert-manager/namespace.yaml create mode 100644 kubernetes/apps/flux-system/kustomization.yaml create mode 100644 kubernetes/apps/flux-system/monitoring/app/kustomization.yaml create mode 100644 kubernetes/apps/flux-system/monitoring/app/podmonitor.yaml create mode 100644 kubernetes/apps/flux-system/monitoring/app/prometheusrule.yaml create mode 100644 kubernetes/apps/flux-system/monitoring/ks.yaml create mode 100644 kubernetes/apps/flux-system/namespace.yaml create mode 100644 kubernetes/apps/flux-system/weave-gitops/app/externalsecret.yaml create mode 100644 kubernetes/apps/flux-system/weave-gitops/app/helmrelease.yaml create mode 100644 kubernetes/apps/flux-system/weave-gitops/app/kustomization.yaml create mode 100644 kubernetes/apps/flux-system/weave-gitops/app/rbac.yaml create mode 100644 kubernetes/apps/flux-system/weave-gitops/ks.yaml create mode 100644 kubernetes/apps/flux-system/webhooks/app/github/ingress.yaml create mode 100644 kubernetes/apps/flux-system/webhooks/app/github/kustomization.yaml create mode 100644 kubernetes/apps/flux-system/webhooks/app/github/receiver.yaml create mode 100644 kubernetes/apps/flux-system/webhooks/app/github/secret.sops.yaml create mode 100644 kubernetes/apps/flux-system/webhooks/app/kustomization.yaml create mode 100644 kubernetes/apps/flux-system/webhooks/ks.yaml create mode 100644 kubernetes/apps/kube-system/cilium/app/helm-values.yaml create mode 100644 kubernetes/apps/kube-system/cilium/app/helmrelease.yaml create mode 100644 kubernetes/apps/kube-system/cilium/app/kustomization.yaml create mode 100644 kubernetes/apps/kube-system/cilium/app/kustomizeconfig.yaml create mode 100644 kubernetes/apps/kube-system/cilium/config/cilium-l2.yaml create mode 100644 kubernetes/apps/kube-system/cilium/config/kustomization.yaml create mode 100644 kubernetes/apps/kube-system/cilium/ks.yaml create mode 100644 kubernetes/apps/kube-system/coredns/app/helm-values.yaml create mode 100644 kubernetes/apps/kube-system/coredns/app/helmrelease.yaml create mode 100644 kubernetes/apps/kube-system/coredns/app/kustomization.yaml create mode 100644 kubernetes/apps/kube-system/coredns/app/kustomizeconfig.yaml create mode 100644 kubernetes/apps/kube-system/coredns/ks.yaml create mode 100644 kubernetes/apps/kube-system/kubelet-csr-approver/app/helm-values.yaml create mode 100644 kubernetes/apps/kube-system/kubelet-csr-approver/app/helmrelease.yaml create mode 100644 kubernetes/apps/kube-system/kubelet-csr-approver/app/kustomization.yaml create mode 100644 kubernetes/apps/kube-system/kubelet-csr-approver/app/kustomizeconfig.yaml create mode 100644 kubernetes/apps/kube-system/kubelet-csr-approver/ks.yaml create mode 100644 kubernetes/apps/kube-system/kubernetes-replicator/app/helmrelease.yaml create mode 100644 kubernetes/apps/kube-system/kubernetes-replicator/app/kustomization.yaml create mode 100644 kubernetes/apps/kube-system/kubernetes-replicator/ks.yaml create mode 100644 kubernetes/apps/kube-system/kustomization.yaml create mode 100644 kubernetes/apps/kube-system/metrics-server/app/helmrelease.yaml create mode 100644 kubernetes/apps/kube-system/metrics-server/app/kustomization.yaml create mode 100644 kubernetes/apps/kube-system/metrics-server/ks.yaml create mode 100644 kubernetes/apps/kube-system/namespace.yaml create mode 100644 kubernetes/apps/kube-system/reloader/app/helmrelease.yaml create mode 100644 kubernetes/apps/kube-system/reloader/app/kustomization.yaml create mode 100644 kubernetes/apps/kube-system/reloader/ks.yaml create mode 100644 kubernetes/apps/kube-system/spegel/app/helm-values.yaml create mode 100644 kubernetes/apps/kube-system/spegel/app/helmrelease.yaml create mode 100644 kubernetes/apps/kube-system/spegel/app/kustomization.yaml create mode 100644 kubernetes/apps/kube-system/spegel/app/kustomizeconfig.yaml create mode 100644 kubernetes/apps/kube-system/spegel/ks.yaml create mode 100644 kubernetes/apps/media/calibre-web/app/helmrelease.yaml create mode 100644 kubernetes/apps/media/calibre-web/app/kustomization.yaml create mode 100644 kubernetes/apps/media/calibre-web/ks.yaml create mode 100644 kubernetes/apps/media/kustomization.yaml create mode 100755 kubernetes/apps/media/mediabox/app/bazarr-ingress.yaml create mode 100755 kubernetes/apps/media/mediabox/app/gaps-ingress.yaml create mode 100755 kubernetes/apps/media/mediabox/app/kustomization.yaml create mode 100644 kubernetes/apps/media/mediabox/app/lldap-ingress.yaml create mode 100755 kubernetes/apps/media/mediabox/app/notifiarr-ingress.yaml create mode 100755 kubernetes/apps/media/mediabox/app/prowlarr-ingress.yaml create mode 100755 kubernetes/apps/media/mediabox/app/radarr-ingress.yaml create mode 100755 kubernetes/apps/media/mediabox/app/sabnzbd-ingress.yaml create mode 100755 kubernetes/apps/media/mediabox/app/service.yaml create mode 100755 kubernetes/apps/media/mediabox/app/sonarr-ingress.yaml create mode 100644 kubernetes/apps/media/mediabox/ks.yaml create mode 100644 kubernetes/apps/media/namespace.yaml create mode 100644 kubernetes/apps/media/overseerr/app/helmrelease.yaml create mode 100644 kubernetes/apps/media/overseerr/app/kustomization.yaml create mode 100644 kubernetes/apps/media/overseerr/ks.yaml create mode 100755 kubernetes/apps/media/plex-exporter/app/configmap.yaml create mode 100755 kubernetes/apps/media/plex-exporter/app/deployment.yaml create mode 100755 kubernetes/apps/media/plex-exporter/app/grafana-dashboard.yaml create mode 100755 kubernetes/apps/media/plex-exporter/app/kustomization.yaml create mode 100755 kubernetes/apps/media/plex-exporter/app/plex-exporter-grafana-dashboard.json create mode 100755 kubernetes/apps/media/plex-exporter/app/service-monitor.yaml create mode 100755 kubernetes/apps/media/plex-exporter/app/service.yaml create mode 100644 kubernetes/apps/media/plex-exporter/ks.yaml create mode 100644 kubernetes/apps/media/plex-trakt-sync/app/config/config.yml create mode 100644 kubernetes/apps/media/plex-trakt-sync/app/helmrelease.yaml create mode 100644 kubernetes/apps/media/plex-trakt-sync/app/kustomization.yaml create mode 100644 kubernetes/apps/media/plex-trakt-sync/ks.yaml create mode 100755 kubernetes/apps/media/podsync/app/config/config.toml create mode 100644 kubernetes/apps/media/podsync/app/helmrelease.yaml create mode 100644 kubernetes/apps/media/podsync/app/kustomization.yaml create mode 100644 kubernetes/apps/media/podsync/ks.dis create mode 100644 kubernetes/apps/media/readarr/app/externalsecret.yaml create mode 100644 kubernetes/apps/media/readarr/app/helmrelease.yaml create mode 100644 kubernetes/apps/media/readarr/app/kustomization.yaml create mode 100644 kubernetes/apps/media/readarr/ks.yaml create mode 100644 kubernetes/apps/media/tautulli/app/helmrelease.yaml create mode 100644 kubernetes/apps/media/tautulli/app/kustomization.yaml create mode 100644 kubernetes/apps/media/tautulli/exporter/helmrelease.yaml create mode 100644 kubernetes/apps/media/tautulli/exporter/kustomization.yaml create mode 100644 kubernetes/apps/media/tautulli/ks.yaml create mode 100644 kubernetes/apps/network/cloudflared/app/configs/config.yaml create mode 100644 kubernetes/apps/network/cloudflared/app/dnsendpoint.yaml create mode 100644 kubernetes/apps/network/cloudflared/app/helmrelease.yaml create mode 100644 kubernetes/apps/network/cloudflared/app/kustomization.yaml create mode 100644 kubernetes/apps/network/cloudflared/app/secret.sops.yaml create mode 100644 kubernetes/apps/network/cloudflared/ks.yaml create mode 100644 kubernetes/apps/network/echo-server/app/helmrelease.yaml create mode 100644 kubernetes/apps/network/echo-server/app/kustomization.yaml create mode 100644 kubernetes/apps/network/echo-server/ks.yaml create mode 100644 kubernetes/apps/network/external-dns/app/helmrelease.yaml create mode 100644 kubernetes/apps/network/external-dns/app/kustomization.yaml create mode 100644 kubernetes/apps/network/external-dns/app/secret.sops.yaml create mode 100644 kubernetes/apps/network/external-dns/ks.yaml create mode 100644 kubernetes/apps/network/ingress-nginx/certificates/kustomization.yaml create mode 100644 kubernetes/apps/network/ingress-nginx/certificates/production.yaml create mode 100644 kubernetes/apps/network/ingress-nginx/certificates/staging.yaml create mode 100644 kubernetes/apps/network/ingress-nginx/external/helmrelease.yaml create mode 100644 kubernetes/apps/network/ingress-nginx/external/kustomization.yaml create mode 100644 kubernetes/apps/network/ingress-nginx/internal/helmrelease.yaml create mode 100644 kubernetes/apps/network/ingress-nginx/internal/kustomization.yaml create mode 100644 kubernetes/apps/network/ingress-nginx/ks.yaml create mode 100644 kubernetes/apps/network/k8s-gateway/app/helmrelease.yaml create mode 100644 kubernetes/apps/network/k8s-gateway/app/kustomization.yaml create mode 100644 kubernetes/apps/network/k8s-gateway/ks.yaml create mode 100644 kubernetes/apps/network/kustomization.yaml create mode 100644 kubernetes/apps/network/namespace.yaml create mode 100755 kubernetes/apps/observability/alertmanager-discord/app/alertmanager-discord-config.yaml create mode 100755 kubernetes/apps/observability/alertmanager-discord/app/alertmanager-discord-deployment.yaml create mode 100755 kubernetes/apps/observability/alertmanager-discord/app/alertmanager-discord-service.yaml create mode 100644 kubernetes/apps/observability/alertmanager-discord/app/externalsecret.yaml create mode 100755 kubernetes/apps/observability/alertmanager-discord/app/kustomization.yaml create mode 100644 kubernetes/apps/observability/alertmanager-discord/ks.yaml create mode 100644 kubernetes/apps/observability/blackbox-exporter/app/helmrelease.yaml create mode 100644 kubernetes/apps/observability/blackbox-exporter/app/kustomization.yaml create mode 100644 kubernetes/apps/observability/blackbox-exporter/ks.yaml create mode 100644 kubernetes/apps/observability/blackbox-exporter/probes/homelab.yaml create mode 100644 kubernetes/apps/observability/blackbox-exporter/probes/kustomization.yaml create mode 100644 kubernetes/apps/observability/gatus/app/config/config.yaml create mode 100644 kubernetes/apps/observability/gatus/app/externalsecret.yaml create mode 100644 kubernetes/apps/observability/gatus/app/helmrelease.yaml create mode 100644 kubernetes/apps/observability/gatus/app/kustomization.yaml create mode 100644 kubernetes/apps/observability/gatus/app/rbac.yaml create mode 100644 kubernetes/apps/observability/gatus/ks.yaml create mode 100644 kubernetes/apps/observability/kube-prometheus-stack/app/helmrelease.yaml create mode 100644 kubernetes/apps/observability/kube-prometheus-stack/app/kustomization.yaml create mode 100644 kubernetes/apps/observability/kube-prometheus-stack/config/kustomization.yaml create mode 100644 kubernetes/apps/observability/kube-prometheus-stack/config/prometheusrules.yaml create mode 100644 kubernetes/apps/observability/kube-prometheus-stack/config/scrapeconfigs.yaml create mode 100644 kubernetes/apps/observability/kube-prometheus-stack/ks.yaml create mode 100644 kubernetes/apps/observability/kustomization.yaml create mode 100644 kubernetes/apps/observability/namespace.yaml create mode 100644 kubernetes/apps/observability/overseerr-exporter/app/externalsecret.yaml create mode 100644 kubernetes/apps/observability/overseerr-exporter/app/helmrelease.yaml create mode 100644 kubernetes/apps/observability/overseerr-exporter/app/kustomization.yaml create mode 100644 kubernetes/apps/observability/overseerr-exporter/ks.yaml create mode 100644 kubernetes/apps/observability/prometheus-operator-crds/app/helmrelease.yaml create mode 100644 kubernetes/apps/observability/prometheus-operator-crds/app/kustomization.yaml create mode 100644 kubernetes/apps/observability/prometheus-operator-crds/ks.yaml create mode 100644 kubernetes/apps/observability/prowlarr-exporter/app/externalsecret.yaml create mode 100644 kubernetes/apps/observability/prowlarr-exporter/app/helmrelease.yaml create mode 100644 kubernetes/apps/observability/prowlarr-exporter/app/kustomization.yaml create mode 100644 kubernetes/apps/observability/prowlarr-exporter/ks.yaml create mode 100644 kubernetes/apps/observability/radarr-exporter/app/externalsecret.yaml create mode 100644 kubernetes/apps/observability/radarr-exporter/app/helmrelease.yaml create mode 100644 kubernetes/apps/observability/radarr-exporter/app/kustomization.yaml create mode 100644 kubernetes/apps/observability/radarr-exporter/ks.yaml create mode 100644 kubernetes/apps/observability/sabnzbd-exporter/app/externalsecret.yaml create mode 100644 kubernetes/apps/observability/sabnzbd-exporter/app/helmrelease.yaml create mode 100644 kubernetes/apps/observability/sabnzbd-exporter/app/kustomization.yaml create mode 100644 kubernetes/apps/observability/sabnzbd-exporter/ks.yaml create mode 100644 kubernetes/apps/observability/sonarr-exporter/app/externalsecret.yaml create mode 100644 kubernetes/apps/observability/sonarr-exporter/app/helmrelease.yaml create mode 100644 kubernetes/apps/observability/sonarr-exporter/app/kustomization.yaml create mode 100644 kubernetes/apps/observability/sonarr-exporter/ks.yaml create mode 100644 kubernetes/apps/observability/speedtest-exporter/app/helmrelease.yaml create mode 100644 kubernetes/apps/observability/speedtest-exporter/app/kustomization.yaml create mode 100644 kubernetes/apps/observability/speedtest-exporter/ks.yaml create mode 100644 kubernetes/apps/observability/tautulli-exporter/app/externalsecret.yaml create mode 100644 kubernetes/apps/observability/tautulli-exporter/app/helmrelease.yaml create mode 100644 kubernetes/apps/observability/tautulli-exporter/app/kustomization.yaml create mode 100644 kubernetes/apps/observability/tautulli-exporter/ks.yaml create mode 100644 kubernetes/apps/openebs-system/kustomization.yaml create mode 100644 kubernetes/apps/openebs-system/namespace.yaml create mode 100644 kubernetes/apps/openebs-system/openebs/app/helmrelease.yaml create mode 100644 kubernetes/apps/openebs-system/openebs/app/kustomization.yaml create mode 100644 kubernetes/apps/openebs-system/openebs/ks.yaml create mode 100755 kubernetes/apps/productivity/kasm/app/ingress.yaml create mode 100755 kubernetes/apps/productivity/kasm/app/kustomization.yaml create mode 100755 kubernetes/apps/productivity/kasm/app/service.yaml create mode 100644 kubernetes/apps/productivity/kasm/ks.yaml create mode 100644 kubernetes/apps/productivity/kustomization.yaml create mode 100644 kubernetes/apps/productivity/linkding/app/externalsecret.yaml create mode 100644 kubernetes/apps/productivity/linkding/app/helmrelease.yaml create mode 100644 kubernetes/apps/productivity/linkding/app/kustomization.yaml create mode 100644 kubernetes/apps/productivity/linkding/ks.yaml create mode 100644 kubernetes/apps/productivity/namespace.yaml create mode 100755 kubernetes/apps/productivity/octoprint/app/ingress.yaml create mode 100755 kubernetes/apps/productivity/octoprint/app/kustomization.yaml create mode 100755 kubernetes/apps/productivity/octoprint/app/service.yaml create mode 100644 kubernetes/apps/productivity/octoprint/ks.yaml create mode 100644 kubernetes/apps/productivity/paperless/app/helmrelease-gotenberg.yaml create mode 100644 kubernetes/apps/productivity/paperless/app/helmrelease-tika.yaml create mode 100644 kubernetes/apps/productivity/paperless/app/helmrelease.yaml create mode 100644 kubernetes/apps/productivity/paperless/app/kustomization.yaml create mode 100644 kubernetes/apps/productivity/paperless/app/secret.sops.yaml create mode 100644 kubernetes/apps/productivity/paperless/ks.yaml create mode 100644 kubernetes/apps/productivity/paperless/redis/helmrelease.yaml create mode 100644 kubernetes/apps/productivity/paperless/redis/kustomization.yaml create mode 100644 kubernetes/apps/productivity/webtrees/app/helmrelease.yaml create mode 100644 kubernetes/apps/productivity/webtrees/app/kustomization.yaml create mode 100644 kubernetes/apps/productivity/webtrees/app/secret.sops.yaml create mode 100644 kubernetes/apps/productivity/webtrees/db/cronjob.yaml create mode 100644 kubernetes/apps/productivity/webtrees/db/helmrelease.yaml create mode 100644 kubernetes/apps/productivity/webtrees/db/kustomization.yaml create mode 100644 kubernetes/apps/productivity/webtrees/db/secret.sops.yaml create mode 100644 kubernetes/apps/productivity/webtrees/ks.yaml create mode 100644 kubernetes/apps/security/external-secrets/ks.yaml create mode 100644 kubernetes/apps/security/external-secrets/operator/helmrelease.yaml create mode 100644 kubernetes/apps/security/external-secrets/operator/kustomization.yaml create mode 100644 kubernetes/apps/security/external-secrets/secretstores/doppler/kustomization.yaml create mode 100644 kubernetes/apps/security/external-secrets/secretstores/doppler/secret.sops.yaml create mode 100644 kubernetes/apps/security/external-secrets/secretstores/doppler/secretstore.yaml create mode 100644 kubernetes/apps/security/external-secrets/secretstores/kustomization.yaml create mode 100644 kubernetes/apps/security/external-secrets/secretstores/onepassword/helmrelease.yaml create mode 100644 kubernetes/apps/security/external-secrets/secretstores/onepassword/kustomization.yaml create mode 100644 kubernetes/apps/security/external-secrets/secretstores/onepassword/secret.sops.yaml create mode 100644 kubernetes/apps/security/external-secrets/secretstores/onepassword/secretstore.yaml create mode 100644 kubernetes/apps/security/kustomization.yaml create mode 100644 kubernetes/apps/security/kyverno/app/helmrelease.yaml create mode 100644 kubernetes/apps/security/kyverno/app/kustomization.yaml create mode 100644 kubernetes/apps/security/kyverno/ks.yaml create mode 100644 kubernetes/apps/security/kyverno/policies/gatus-external.yaml create mode 100644 kubernetes/apps/security/kyverno/policies/gatus-internal.yaml create mode 100644 kubernetes/apps/security/kyverno/policies/ingress.yaml create mode 100644 kubernetes/apps/security/kyverno/policies/kustomization.yaml create mode 100644 kubernetes/apps/security/kyverno/policies/limits.yaml create mode 100644 kubernetes/apps/security/kyverno/policies/ndots.yaml create mode 100644 kubernetes/apps/security/namespace.yaml create mode 100644 kubernetes/apps/storage/kustomization.yaml create mode 100644 kubernetes/apps/storage/longhorn/app/helm-release.yaml create mode 100755 kubernetes/apps/storage/longhorn/app/kustomization.yaml create mode 100755 kubernetes/apps/storage/longhorn/conf/kustomization.yaml create mode 100755 kubernetes/apps/storage/longhorn/conf/monitoring/kustomization.yaml create mode 100755 kubernetes/apps/storage/longhorn/conf/monitoring/prometheusrule.yaml create mode 100755 kubernetes/apps/storage/longhorn/conf/monitoring/servicemonitor.yaml create mode 100755 kubernetes/apps/storage/longhorn/conf/other/kustomization.yaml create mode 100644 kubernetes/apps/storage/longhorn/conf/other/systembackup.yaml create mode 100755 kubernetes/apps/storage/longhorn/conf/recurringjobs/30min-snapshot.yaml create mode 100755 kubernetes/apps/storage/longhorn/conf/recurringjobs/daily-backup.yaml create mode 100755 kubernetes/apps/storage/longhorn/conf/recurringjobs/daily-cleanup.yaml create mode 100755 kubernetes/apps/storage/longhorn/conf/recurringjobs/daily-delete.yaml create mode 100755 kubernetes/apps/storage/longhorn/conf/recurringjobs/daily-trim.yaml create mode 100755 kubernetes/apps/storage/longhorn/conf/recurringjobs/hourly-backup.yaml create mode 100755 kubernetes/apps/storage/longhorn/conf/recurringjobs/kustomization.yaml create mode 100755 kubernetes/apps/storage/longhorn/conf/snap-class.yaml create mode 100644 kubernetes/apps/storage/longhorn/ks.yaml create mode 100644 kubernetes/apps/storage/longhorn/prereq/kustomization.yaml create mode 100644 kubernetes/apps/storage/longhorn/prereq/longhorn-iscsi-installation.yaml create mode 100644 kubernetes/apps/storage/namespace.yaml create mode 100644 kubernetes/apps/tools/kustomization.yaml create mode 100644 kubernetes/apps/tools/namespace.yaml create mode 100644 kubernetes/apps/tools/smtp-relay/app/config/maddy.conf create mode 100644 kubernetes/apps/tools/smtp-relay/app/externalsecret.yaml create mode 100644 kubernetes/apps/tools/smtp-relay/app/helmrelease.yaml create mode 100644 kubernetes/apps/tools/smtp-relay/app/kustomization.yaml create mode 100644 kubernetes/apps/tools/smtp-relay/ks.yaml create mode 100644 kubernetes/bootstrap/flux/kustomization.yaml create mode 100644 kubernetes/bootstrap/helmfile.yaml create mode 100644 kubernetes/bootstrap/talos/clusterconfig/.gitignore create mode 100644 kubernetes/bootstrap/talos/patches/README.md create mode 100644 kubernetes/bootstrap/talos/patches/controller/api-access.yaml create mode 100644 kubernetes/bootstrap/talos/patches/controller/cluster.yaml create mode 100644 kubernetes/bootstrap/talos/patches/controller/disable-admission-controller.yaml create mode 100644 kubernetes/bootstrap/talos/patches/controller/etcd.yaml create mode 100644 kubernetes/bootstrap/talos/patches/global/cluster-discovery.yaml create mode 100644 kubernetes/bootstrap/talos/patches/global/containerd.yaml create mode 100644 kubernetes/bootstrap/talos/patches/global/disable-search-domain.yaml create mode 100644 kubernetes/bootstrap/talos/patches/global/hostdns.yaml create mode 100644 kubernetes/bootstrap/talos/patches/global/kubelet.yaml create mode 100644 kubernetes/bootstrap/talos/patches/global/openebs-local.yaml create mode 100644 kubernetes/bootstrap/talos/patches/global/sysctl.yaml create mode 100644 kubernetes/bootstrap/talos/talconfig.yaml create mode 100644 kubernetes/bootstrap/talos/talsecret.sops.yaml create mode 100644 kubernetes/flux/apps.yaml create mode 100644 kubernetes/flux/config/cluster.yaml create mode 100644 kubernetes/flux/config/flux.yaml create mode 100644 kubernetes/flux/config/kustomization.yaml create mode 100644 kubernetes/flux/repositories/git/kustomization.yaml create mode 100644 kubernetes/flux/repositories/helm/bitnami.yaml create mode 100644 kubernetes/flux/repositories/helm/bjw-s.yaml create mode 100644 kubernetes/flux/repositories/helm/cilium.yaml create mode 100644 kubernetes/flux/repositories/helm/coredns.yaml create mode 100644 kubernetes/flux/repositories/helm/external-dns.yaml create mode 100644 kubernetes/flux/repositories/helm/external-secrets.yaml create mode 100644 kubernetes/flux/repositories/helm/ingress-nginx.yaml create mode 100644 kubernetes/flux/repositories/helm/jetstack.yaml create mode 100644 kubernetes/flux/repositories/helm/k8s-gateway.yaml create mode 100644 kubernetes/flux/repositories/helm/kustomization.yaml create mode 100644 kubernetes/flux/repositories/helm/kyverno-charts.yaml create mode 100755 kubernetes/flux/repositories/helm/longhorn.yaml create mode 100644 kubernetes/flux/repositories/helm/metrics-server.yaml create mode 100755 kubernetes/flux/repositories/helm/mittwald-charts.yaml create mode 100644 kubernetes/flux/repositories/helm/openebs.yaml create mode 100644 kubernetes/flux/repositories/helm/postfinance.yaml create mode 100644 kubernetes/flux/repositories/helm/prometheus-community.yaml create mode 100644 kubernetes/flux/repositories/helm/spegel.yaml create mode 100644 kubernetes/flux/repositories/helm/stakater.yaml create mode 100644 kubernetes/flux/repositories/helm/weave-gitops.yaml create mode 100644 kubernetes/flux/repositories/kustomization.yaml create mode 100644 kubernetes/flux/repositories/oci/kustomization.yaml create mode 100644 kubernetes/flux/vars/cluster-secrets.sops.yaml create mode 100644 kubernetes/flux/vars/cluster-settings.yaml create mode 100644 kubernetes/flux/vars/kustomization.yaml create mode 100755 scripts/rebuild-kustomizations.sh diff --git a/.sops.yaml b/.sops.yaml new file mode 100644 index 000000000..d1164eb3f --- /dev/null +++ b/.sops.yaml @@ -0,0 +1,12 @@ +--- +creation_rules: + - # IMPORTANT: This rule MUST be above the others + path_regex: talos/.*\.sops\.ya?ml + key_groups: + - age: + - "age1y0kzuf0tn94a74whazwae4r9qal4snuqfuhl5jacscrpr7up5gts74fe5w" + - path_regex: kubernetes/.*\.sops\.ya?ml + encrypted_regex: "^(data|stringData)$" + key_groups: + - age: + - "age1y0kzuf0tn94a74whazwae4r9qal4snuqfuhl5jacscrpr7up5gts74fe5w" diff --git a/Taskfile.yaml b/Taskfile.yaml index c812b9db0..233f504b4 100644 --- a/Taskfile.yaml +++ b/Taskfile.yaml @@ -36,7 +36,6 @@ includes: optional: true tasks: - default: task --list init: @@ -58,6 +57,7 @@ tasks: - task: .template - task: sops:encrypt - task: .validate + - cmd: bash {{.ROOT_DIR}}/scripts/rebuild-kustomizations.sh .template: internal: true diff --git a/bootstrap/templates/kubernetes/apps/cert-manager/cert-manager/app/helmrelease.yaml.j2 b/bootstrap/templates/kubernetes/apps/cert-manager/cert-manager/app/helmrelease.yaml.j2 index b72a878df..1615fb43d 100644 --- a/bootstrap/templates/kubernetes/apps/cert-manager/cert-manager/app/helmrelease.yaml.j2 +++ b/bootstrap/templates/kubernetes/apps/cert-manager/cert-manager/app/helmrelease.yaml.j2 @@ -8,7 +8,7 @@ spec: chart: spec: chart: cert-manager - version: v1.14.5 + version: v1.15.0 sourceRef: kind: HelmRepository name: jetstack diff --git a/bootstrap/templates/kubernetes/apps/cert-manager/cert-manager/ks.yaml.j2 b/bootstrap/templates/kubernetes/apps/cert-manager/cert-manager/ks.yaml.j2 index 3efe99d81..289b7bba7 100644 --- a/bootstrap/templates/kubernetes/apps/cert-manager/cert-manager/ks.yaml.j2 +++ b/bootstrap/templates/kubernetes/apps/cert-manager/cert-manager/ks.yaml.j2 @@ -13,7 +13,7 @@ spec: prune: true sourceRef: kind: GitRepository - name: home-kubernetes + name: k8s-homelab wait: true interval: 30m retryInterval: 1m @@ -36,7 +36,7 @@ spec: prune: true sourceRef: kind: GitRepository - name: home-kubernetes + name: k8s-homelab wait: true interval: 30m retryInterval: 1m diff --git a/bootstrap/templates/kubernetes/apps/flux-system/webhooks/app/github/receiver.yaml.j2 b/bootstrap/templates/kubernetes/apps/flux-system/webhooks/app/github/receiver.yaml.j2 index cca5931bd..d178f1c3c 100644 --- a/bootstrap/templates/kubernetes/apps/flux-system/webhooks/app/github/receiver.yaml.j2 +++ b/bootstrap/templates/kubernetes/apps/flux-system/webhooks/app/github/receiver.yaml.j2 @@ -13,7 +13,7 @@ spec: resources: - apiVersion: source.toolkit.fluxcd.io/v1 kind: GitRepository - name: home-kubernetes + name: k8s-homelab namespace: flux-system - apiVersion: kustomize.toolkit.fluxcd.io/v1 kind: Kustomization diff --git a/bootstrap/templates/kubernetes/apps/flux-system/webhooks/ks.yaml.j2 b/bootstrap/templates/kubernetes/apps/flux-system/webhooks/ks.yaml.j2 index e80c50b23..afa7b0e84 100644 --- a/bootstrap/templates/kubernetes/apps/flux-system/webhooks/ks.yaml.j2 +++ b/bootstrap/templates/kubernetes/apps/flux-system/webhooks/ks.yaml.j2 @@ -13,7 +13,7 @@ spec: prune: true sourceRef: kind: GitRepository - name: home-kubernetes + name: k8s-homelab wait: true interval: 30m retryInterval: 1m diff --git a/bootstrap/templates/kubernetes/apps/kube-system/cilium/app/helmrelease.yaml.j2 b/bootstrap/templates/kubernetes/apps/kube-system/cilium/app/helmrelease.yaml.j2 index a433f46fa..10bf40a76 100644 --- a/bootstrap/templates/kubernetes/apps/kube-system/cilium/app/helmrelease.yaml.j2 +++ b/bootstrap/templates/kubernetes/apps/kube-system/cilium/app/helmrelease.yaml.j2 @@ -8,7 +8,7 @@ spec: chart: spec: chart: cilium - version: 1.15.5 + version: 1.15.6 sourceRef: kind: HelmRepository name: cilium diff --git a/bootstrap/templates/kubernetes/apps/kube-system/cilium/ks.yaml.j2 b/bootstrap/templates/kubernetes/apps/kube-system/cilium/ks.yaml.j2 index 2522f1dfe..dbcf6bbbd 100644 --- a/bootstrap/templates/kubernetes/apps/kube-system/cilium/ks.yaml.j2 +++ b/bootstrap/templates/kubernetes/apps/kube-system/cilium/ks.yaml.j2 @@ -13,7 +13,7 @@ spec: prune: false # never should be deleted sourceRef: kind: GitRepository - name: home-kubernetes + name: k8s-homelab wait: true interval: 30m retryInterval: 1m @@ -35,7 +35,7 @@ spec: prune: false # never should be deleted sourceRef: kind: GitRepository - name: home-kubernetes + name: k8s-homelab wait: false interval: 30m retryInterval: 1m diff --git a/bootstrap/templates/kubernetes/apps/kube-system/coredns/ks.yaml.j2 b/bootstrap/templates/kubernetes/apps/kube-system/coredns/ks.yaml.j2 index bf2a537e6..cec4bfef0 100644 --- a/bootstrap/templates/kubernetes/apps/kube-system/coredns/ks.yaml.j2 +++ b/bootstrap/templates/kubernetes/apps/kube-system/coredns/ks.yaml.j2 @@ -13,7 +13,7 @@ spec: prune: false # never should be deleted sourceRef: kind: GitRepository - name: home-kubernetes + name: k8s-homelab wait: false interval: 30m retryInterval: 1m diff --git a/bootstrap/templates/kubernetes/apps/kube-system/kubelet-csr-approver/ks.yaml.j2 b/bootstrap/templates/kubernetes/apps/kube-system/kubelet-csr-approver/ks.yaml.j2 index adfb4940a..936bac645 100644 --- a/bootstrap/templates/kubernetes/apps/kube-system/kubelet-csr-approver/ks.yaml.j2 +++ b/bootstrap/templates/kubernetes/apps/kube-system/kubelet-csr-approver/ks.yaml.j2 @@ -13,7 +13,7 @@ spec: prune: false # never should be deleted sourceRef: kind: GitRepository - name: home-kubernetes + name: k8s-homelab wait: false interval: 30m retryInterval: 1m diff --git a/bootstrap/templates/kubernetes/apps/kube-system/metrics-server/ks.yaml.j2 b/bootstrap/templates/kubernetes/apps/kube-system/metrics-server/ks.yaml.j2 index 244f53c16..090b2ae73 100644 --- a/bootstrap/templates/kubernetes/apps/kube-system/metrics-server/ks.yaml.j2 +++ b/bootstrap/templates/kubernetes/apps/kube-system/metrics-server/ks.yaml.j2 @@ -13,7 +13,7 @@ spec: prune: true sourceRef: kind: GitRepository - name: home-kubernetes + name: k8s-homelab wait: false interval: 30m retryInterval: 1m diff --git a/bootstrap/templates/kubernetes/apps/kube-system/reloader/app/helmrelease.yaml.j2 b/bootstrap/templates/kubernetes/apps/kube-system/reloader/app/helmrelease.yaml.j2 index 2b63a3b13..0a3965fcd 100644 --- a/bootstrap/templates/kubernetes/apps/kube-system/reloader/app/helmrelease.yaml.j2 +++ b/bootstrap/templates/kubernetes/apps/kube-system/reloader/app/helmrelease.yaml.j2 @@ -8,7 +8,7 @@ spec: chart: spec: chart: reloader - version: 1.0.101 + version: 1.0.107 sourceRef: kind: HelmRepository name: stakater diff --git a/bootstrap/templates/kubernetes/apps/kube-system/reloader/ks.yaml.j2 b/bootstrap/templates/kubernetes/apps/kube-system/reloader/ks.yaml.j2 index 9aa429934..6f9458dc1 100644 --- a/bootstrap/templates/kubernetes/apps/kube-system/reloader/ks.yaml.j2 +++ b/bootstrap/templates/kubernetes/apps/kube-system/reloader/ks.yaml.j2 @@ -13,7 +13,7 @@ spec: prune: true sourceRef: kind: GitRepository - name: home-kubernetes + name: k8s-homelab wait: false interval: 30m retryInterval: 1m diff --git a/bootstrap/templates/kubernetes/apps/kube-system/spegel/app/helmrelease.yaml.j2 b/bootstrap/templates/kubernetes/apps/kube-system/spegel/app/helmrelease.yaml.j2 index 4200fa89b..613d34ea9 100644 --- a/bootstrap/templates/kubernetes/apps/kube-system/spegel/app/helmrelease.yaml.j2 +++ b/bootstrap/templates/kubernetes/apps/kube-system/spegel/app/helmrelease.yaml.j2 @@ -8,7 +8,7 @@ spec: chart: spec: chart: spegel - version: v0.0.22 + version: v0.0.23 sourceRef: kind: HelmRepository name: spegel diff --git a/bootstrap/templates/kubernetes/apps/kube-system/spegel/ks.yaml.j2 b/bootstrap/templates/kubernetes/apps/kube-system/spegel/ks.yaml.j2 index 83c730b07..cb9f37ed4 100644 --- a/bootstrap/templates/kubernetes/apps/kube-system/spegel/ks.yaml.j2 +++ b/bootstrap/templates/kubernetes/apps/kube-system/spegel/ks.yaml.j2 @@ -13,7 +13,7 @@ spec: prune: true sourceRef: kind: GitRepository - name: home-kubernetes + name: k8s-homelab wait: false interval: 30m retryInterval: 1m diff --git a/bootstrap/templates/kubernetes/apps/network/cloudflared/app/helmrelease.yaml.j2 b/bootstrap/templates/kubernetes/apps/network/cloudflared/app/helmrelease.yaml.j2 index c10a58dd9..50c0c5c31 100644 --- a/bootstrap/templates/kubernetes/apps/network/cloudflared/app/helmrelease.yaml.j2 +++ b/bootstrap/templates/kubernetes/apps/network/cloudflared/app/helmrelease.yaml.j2 @@ -30,7 +30,7 @@ spec: app: image: repository: docker.io/cloudflare/cloudflared - tag: 2024.5.0 + tag: 2024.6.0 env: NO_AUTOUPDATE: true TUNNEL_CRED_FILE: /etc/cloudflared/creds/credentials.json diff --git a/bootstrap/templates/kubernetes/apps/network/cloudflared/ks.yaml.j2 b/bootstrap/templates/kubernetes/apps/network/cloudflared/ks.yaml.j2 index eb8d8da0b..da98a0f78 100644 --- a/bootstrap/templates/kubernetes/apps/network/cloudflared/ks.yaml.j2 +++ b/bootstrap/templates/kubernetes/apps/network/cloudflared/ks.yaml.j2 @@ -15,7 +15,7 @@ spec: prune: true sourceRef: kind: GitRepository - name: home-kubernetes + name: k8s-homelab wait: false interval: 30m retryInterval: 1m diff --git a/bootstrap/templates/kubernetes/apps/network/echo-server/ks.yaml.j2 b/bootstrap/templates/kubernetes/apps/network/echo-server/ks.yaml.j2 index 2984f219c..73aef89b6 100644 --- a/bootstrap/templates/kubernetes/apps/network/echo-server/ks.yaml.j2 +++ b/bootstrap/templates/kubernetes/apps/network/echo-server/ks.yaml.j2 @@ -13,7 +13,7 @@ spec: prune: true sourceRef: kind: GitRepository - name: home-kubernetes + name: k8s-homelab wait: false interval: 30m retryInterval: 1m diff --git a/bootstrap/templates/kubernetes/apps/network/external-dns/app/helmrelease.yaml.j2 b/bootstrap/templates/kubernetes/apps/network/external-dns/app/helmrelease.yaml.j2 index f9b23788e..5b7dee100 100644 --- a/bootstrap/templates/kubernetes/apps/network/external-dns/app/helmrelease.yaml.j2 +++ b/bootstrap/templates/kubernetes/apps/network/external-dns/app/helmrelease.yaml.j2 @@ -8,7 +8,7 @@ spec: chart: spec: chart: external-dns - version: 1.14.4 + version: 1.14.5 sourceRef: kind: HelmRepository name: external-dns diff --git a/bootstrap/templates/kubernetes/apps/network/external-dns/ks.yaml.j2 b/bootstrap/templates/kubernetes/apps/network/external-dns/ks.yaml.j2 index eaed4b566..56b8ed00d 100644 --- a/bootstrap/templates/kubernetes/apps/network/external-dns/ks.yaml.j2 +++ b/bootstrap/templates/kubernetes/apps/network/external-dns/ks.yaml.j2 @@ -13,7 +13,7 @@ spec: prune: true sourceRef: kind: GitRepository - name: home-kubernetes + name: k8s-homelab wait: true interval: 30m retryInterval: 1m diff --git a/bootstrap/templates/kubernetes/apps/network/ingress-nginx/ks.yaml.j2 b/bootstrap/templates/kubernetes/apps/network/ingress-nginx/ks.yaml.j2 index 99b1abb58..570f91947 100644 --- a/bootstrap/templates/kubernetes/apps/network/ingress-nginx/ks.yaml.j2 +++ b/bootstrap/templates/kubernetes/apps/network/ingress-nginx/ks.yaml.j2 @@ -15,7 +15,7 @@ spec: prune: true sourceRef: kind: GitRepository - name: home-kubernetes + name: k8s-homelab wait: true interval: 30m retryInterval: 1m @@ -37,7 +37,7 @@ spec: prune: true sourceRef: kind: GitRepository - name: home-kubernetes + name: k8s-homelab wait: false interval: 30m retryInterval: 1m @@ -59,7 +59,7 @@ spec: prune: true sourceRef: kind: GitRepository - name: home-kubernetes + name: k8s-homelab wait: false interval: 30m retryInterval: 1m diff --git a/bootstrap/templates/kubernetes/apps/network/k8s-gateway/ks.yaml.j2 b/bootstrap/templates/kubernetes/apps/network/k8s-gateway/ks.yaml.j2 index 06f442555..2d4c643f2 100644 --- a/bootstrap/templates/kubernetes/apps/network/k8s-gateway/ks.yaml.j2 +++ b/bootstrap/templates/kubernetes/apps/network/k8s-gateway/ks.yaml.j2 @@ -13,7 +13,7 @@ spec: prune: true sourceRef: kind: GitRepository - name: home-kubernetes + name: k8s-homelab wait: false interval: 30m retryInterval: 1m diff --git a/bootstrap/templates/kubernetes/apps/observability/prometheus-operator-crds/ks.yaml.j2 b/bootstrap/templates/kubernetes/apps/observability/prometheus-operator-crds/ks.yaml.j2 index ffbb5dcb5..19ed2ef9e 100644 --- a/bootstrap/templates/kubernetes/apps/observability/prometheus-operator-crds/ks.yaml.j2 +++ b/bootstrap/templates/kubernetes/apps/observability/prometheus-operator-crds/ks.yaml.j2 @@ -13,7 +13,7 @@ spec: prune: false # never should be deleted sourceRef: kind: GitRepository - name: home-kubernetes + name: k8s-homelab wait: false interval: 30m retryInterval: 1m diff --git a/bootstrap/templates/kubernetes/apps/openebs-system/openebs/ks.yaml.j2 b/bootstrap/templates/kubernetes/apps/openebs-system/openebs/ks.yaml.j2 index 170feca91..531f679ed 100644 --- a/bootstrap/templates/kubernetes/apps/openebs-system/openebs/ks.yaml.j2 +++ b/bootstrap/templates/kubernetes/apps/openebs-system/openebs/ks.yaml.j2 @@ -13,7 +13,7 @@ spec: prune: true sourceRef: kind: GitRepository - name: home-kubernetes + name: k8s-homelab wait: false interval: 30m retryInterval: 1m diff --git a/bootstrap/templates/kubernetes/bootstrap/helmfile.yaml.j2 b/bootstrap/templates/kubernetes/bootstrap/helmfile.yaml.j2 index 7e743b1e5..299267b0f 100644 --- a/bootstrap/templates/kubernetes/bootstrap/helmfile.yaml.j2 +++ b/bootstrap/templates/kubernetes/bootstrap/helmfile.yaml.j2 @@ -22,7 +22,7 @@ releases: - name: cilium namespace: kube-system chart: cilium/cilium - version: 1.15.5 + version: 1.15.6 values: - ../apps/kube-system/cilium/app/helm-values.yaml needs: @@ -49,7 +49,7 @@ releases: - name: spegel namespace: kube-system chart: oci://ghcr.io/spegel-org/helm-charts/spegel - version: v0.0.22 + version: v0.0.23 values: - ../apps/kube-system/spegel/app/helm-values.yaml needs: diff --git a/bootstrap/templates/kubernetes/bootstrap/talos/talconfig.yaml.j2 b/bootstrap/templates/kubernetes/bootstrap/talos/talconfig.yaml.j2 index 17ddf0349..07f08f0f0 100644 --- a/bootstrap/templates/kubernetes/bootstrap/talos/talconfig.yaml.j2 +++ b/bootstrap/templates/kubernetes/bootstrap/talos/talconfig.yaml.j2 @@ -3,7 +3,7 @@ # renovate: datasource=docker depName=ghcr.io/siderolabs/installer talosVersion: v1.7.4 # renovate: datasource=docker depName=ghcr.io/siderolabs/kubelet -kubernetesVersion: v1.30.1 +kubernetesVersion: v1.30.2 clusterName: "#{ bootstrap_cluster_name | default('home-kubernetes', true) }#" endpoint: https://#{ bootstrap_controller_vip }#:6443 diff --git a/bootstrap/templates/kubernetes/flux/apps.yaml.j2 b/bootstrap/templates/kubernetes/flux/apps.yaml.j2 index c4ebba999..408c48bff 100644 --- a/bootstrap/templates/kubernetes/flux/apps.yaml.j2 +++ b/bootstrap/templates/kubernetes/flux/apps.yaml.j2 @@ -10,7 +10,7 @@ spec: prune: true sourceRef: kind: GitRepository - name: home-kubernetes + name: k8s-homelab decryption: provider: sops secretRef: diff --git a/bootstrap/templates/kubernetes/flux/config/cluster.yaml.j2 b/bootstrap/templates/kubernetes/flux/config/cluster.yaml.j2 index bae21e831..e5282983b 100644 --- a/bootstrap/templates/kubernetes/flux/config/cluster.yaml.j2 +++ b/bootstrap/templates/kubernetes/flux/config/cluster.yaml.j2 @@ -2,7 +2,7 @@ apiVersion: source.toolkit.fluxcd.io/v1 kind: GitRepository metadata: - name: home-kubernetes + name: k8s-homelab namespace: flux-system spec: interval: 30m @@ -31,7 +31,7 @@ spec: wait: false sourceRef: kind: GitRepository - name: home-kubernetes + name: k8s-homelab decryption: provider: sops secretRef: diff --git a/kubernetes/apps/cert-manager/cert-manager/app/helmrelease.yaml b/kubernetes/apps/cert-manager/cert-manager/app/helmrelease.yaml new file mode 100644 index 000000000..1615fb43d --- /dev/null +++ b/kubernetes/apps/cert-manager/cert-manager/app/helmrelease.yaml @@ -0,0 +1,30 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: cert-manager +spec: + interval: 30m + chart: + spec: + chart: cert-manager + version: v1.15.0 + sourceRef: + kind: HelmRepository + name: jetstack + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + installCRDs: true + dns01RecursiveNameservers: https://1.1.1.1:443/dns-query,https://1.0.0.1:443/dns-query + dns01RecursiveNameserversOnly: true + prometheus: + enabled: true + servicemonitor: + enabled: true diff --git a/kubernetes/apps/cert-manager/cert-manager/app/kustomization.yaml b/kubernetes/apps/cert-manager/cert-manager/app/kustomization.yaml new file mode 100644 index 000000000..5dd7baca7 --- /dev/null +++ b/kubernetes/apps/cert-manager/cert-manager/app/kustomization.yaml @@ -0,0 +1,5 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml diff --git a/kubernetes/apps/cert-manager/cert-manager/issuers/issuers.yaml b/kubernetes/apps/cert-manager/cert-manager/issuers/issuers.yaml new file mode 100644 index 000000000..036a159ff --- /dev/null +++ b/kubernetes/apps/cert-manager/cert-manager/issuers/issuers.yaml @@ -0,0 +1,41 @@ +apiVersion: cert-manager.io/v1 +kind: ClusterIssuer +metadata: + name: letsencrypt-production +spec: + acme: + server: https://acme-v02.api.letsencrypt.org/directory + email: "${SECRET_ACME_EMAIL}" + privateKeySecretRef: + name: letsencrypt-production + solvers: + - dns01: + cloudflare: + apiTokenSecretRef: + name: cert-manager-secret + key: api-token + selector: + dnsZones: + - "${SECRET_DOMAIN}" + - "${SECRET_CH_DOMAIN}" +--- +apiVersion: cert-manager.io/v1 +kind: ClusterIssuer +metadata: + name: letsencrypt-staging +spec: + acme: + server: https://acme-staging-v02.api.letsencrypt.org/directory + email: "${SECRET_ACME_EMAIL}" + privateKeySecretRef: + name: letsencrypt-staging + solvers: + - dns01: + cloudflare: + apiTokenSecretRef: + name: cert-manager-secret + key: api-token + selector: + dnsZones: + - "${SECRET_DOMAIN}" + - "${SECRET_CH_DOMAIN}" diff --git a/kubernetes/apps/cert-manager/cert-manager/issuers/kustomization.yaml b/kubernetes/apps/cert-manager/cert-manager/issuers/kustomization.yaml new file mode 100644 index 000000000..17754be63 --- /dev/null +++ b/kubernetes/apps/cert-manager/cert-manager/issuers/kustomization.yaml @@ -0,0 +1,6 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./secret.sops.yaml + - ./issuers.yaml diff --git a/kubernetes/apps/cert-manager/cert-manager/issuers/secret.sops.yaml b/kubernetes/apps/cert-manager/cert-manager/issuers/secret.sops.yaml new file mode 100644 index 000000000..7c95d96a5 --- /dev/null +++ b/kubernetes/apps/cert-manager/cert-manager/issuers/secret.sops.yaml @@ -0,0 +1,26 @@ +apiVersion: v1 +kind: Secret +metadata: + name: cert-manager-secret +stringData: + api-token: ENC[AES256_GCM,data:F7C2CGVxyxT2aMKrmqW8DzRXMRXfj6ccg9z3jNG7hv/TJTjdipcKHg==,iv:ZeCw+YvvEi/OS4Eh11fttWWqmQw2dyia+8acraizYhw=,tag:46W7pIm9DBCG7h0Dsohm8w==,type:str] +sops: + kms: [] + gcp_kms: [] + azure_kv: [] + hc_vault: [] + age: + - recipient: age1y0kzuf0tn94a74whazwae4r9qal4snuqfuhl5jacscrpr7up5gts74fe5w + enc: | + -----BEGIN AGE ENCRYPTED FILE----- + YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBWSVdkV2xtQjVueHN6anpE + WTNTVE16eFpyS1NHYjNSUzZSY0IrT1c5ZWs4Cm5ib0I0VWpYTlp2cyt6L1ErVXBG + Wjh3dGIvelErTGtmUmc4YVpRc2dQaGsKLS0tIDFFYmtnelZjcm5nSzZiU2lLSDk3 + Y25wYWptbXV3aTczYVp6Zjd1dnp3YVUKdLZiofuhJoGueozdKTc5PkSwzPfQLllp + eA1ghGvyH2ux+RAobqDwFyD+JXXJ5aPNVTSc1C1dV0WI4QmzAwXi0Q== + -----END AGE ENCRYPTED FILE----- + lastmodified: "2024-06-06T09:08:40Z" + mac: ENC[AES256_GCM,data:M26XTz4ljTD3j9ojYiwPMMoDTWTeryJr5+g7UUvKgelYjVc/Aglb5TplwOfTS561crGGcDo2gRHJ9EsiCRlx0kMh/u7d09FeQLsEy1xrfqueELPczlhXVe1BjryqB34vNfO6QlCjD6QeITzPyRIrCIzjRykYbEQlVgW4ml99TR4=,iv:dqpyvLv7e+aBLvg6B01t0Y6iPxTDk7++z1DLhRr5x9s=,tag:Cq43iF3TWOZtubDb7ZJTSQ==,type:str] + pgp: [] + encrypted_regex: ^(data|stringData)$ + version: 3.8.1 diff --git a/kubernetes/apps/cert-manager/cert-manager/ks.yaml b/kubernetes/apps/cert-manager/cert-manager/ks.yaml new file mode 100644 index 000000000..04f818d63 --- /dev/null +++ b/kubernetes/apps/cert-manager/cert-manager/ks.yaml @@ -0,0 +1,42 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app cert-manager + namespace: flux-system +spec: + targetNamespace: cert-manager + commonMetadata: + labels: + app.kubernetes.io/name: *app + path: ./kubernetes/apps/cert-manager/cert-manager/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app cert-manager-issuers + namespace: flux-system +spec: + targetNamespace: cert-manager + commonMetadata: + labels: + app.kubernetes.io/name: *app + dependsOn: + - name: cert-manager + path: ./kubernetes/apps/cert-manager/cert-manager/issuers + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/cert-manager/kustomization.yaml b/kubernetes/apps/cert-manager/kustomization.yaml new file mode 100644 index 000000000..3ad7d0307 --- /dev/null +++ b/kubernetes/apps/cert-manager/kustomization.yaml @@ -0,0 +1,6 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - namespace.yaml + - cert-manager/ks.yaml diff --git a/kubernetes/apps/cert-manager/namespace.yaml b/kubernetes/apps/cert-manager/namespace.yaml new file mode 100644 index 000000000..ed788350f --- /dev/null +++ b/kubernetes/apps/cert-manager/namespace.yaml @@ -0,0 +1,7 @@ +--- +apiVersion: v1 +kind: Namespace +metadata: + name: cert-manager + labels: + kustomize.toolkit.fluxcd.io/prune: disabled diff --git a/kubernetes/apps/flux-system/kustomization.yaml b/kubernetes/apps/flux-system/kustomization.yaml new file mode 100644 index 000000000..e6213b101 --- /dev/null +++ b/kubernetes/apps/flux-system/kustomization.yaml @@ -0,0 +1,8 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - namespace.yaml + - monitoring/ks.yaml + - weave-gitops/ks.yaml + - webhooks/ks.yaml diff --git a/kubernetes/apps/flux-system/monitoring/app/kustomization.yaml b/kubernetes/apps/flux-system/monitoring/app/kustomization.yaml new file mode 100644 index 000000000..247c03744 --- /dev/null +++ b/kubernetes/apps/flux-system/monitoring/app/kustomization.yaml @@ -0,0 +1,8 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +namespace: flux-system +resources: + - ./podmonitor.yaml + - ./prometheusrule.yaml diff --git a/kubernetes/apps/flux-system/monitoring/app/podmonitor.yaml b/kubernetes/apps/flux-system/monitoring/app/podmonitor.yaml new file mode 100644 index 000000000..ece785133 --- /dev/null +++ b/kubernetes/apps/flux-system/monitoring/app/podmonitor.yaml @@ -0,0 +1,31 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/monitoring.coreos.com/podmonitor_v1.json +apiVersion: monitoring.coreos.com/v1 +kind: PodMonitor +metadata: + name: flux-system + labels: + app.kubernetes.io/part-of: flux + app.kubernetes.io/component: monitoring +spec: + namespaceSelector: + matchNames: + - flux-system + selector: + matchExpressions: + - key: app + operator: In + values: + - helm-controller + - source-controller + - kustomize-controller + - notification-controller + - image-automation-controller + - image-reflector-controller + podMetricsEndpoints: + - port: http-prom + relabelings: + # Ref: https://github.com/prometheus-operator/prometheus-operator/issues/4816 + - sourceLabels: [__meta_kubernetes_pod_phase] + action: keep + regex: Running diff --git a/kubernetes/apps/flux-system/monitoring/app/prometheusrule.yaml b/kubernetes/apps/flux-system/monitoring/app/prometheusrule.yaml new file mode 100644 index 000000000..17af8d62f --- /dev/null +++ b/kubernetes/apps/flux-system/monitoring/app/prometheusrule.yaml @@ -0,0 +1,31 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/monitoring.coreos.com/prometheusrule_v1.json +apiVersion: monitoring.coreos.com/v1 +kind: PrometheusRule +metadata: + name: flux-rules +spec: + groups: + - name: flux.rules + rules: + - alert: FluxComponentAbsent + annotations: + summary: Flux component has disappeared from Prometheus target discovery. + expr: | + absent(up{job=~".*flux-system.*"} == 1) + for: 15m + labels: + severity: critical + - alert: FluxReconciliationFailure + annotations: + summary: >- + {{ $labels.kind }} {{ $labels.namespace }}/{{ $labels.name }} reconciliation + has been failing for more than 15 minutes. + expr: | + max(gotk_reconcile_condition{status="False",type="Ready"}) by (namespace, name, kind) + + + on(namespace, name, kind) (max(gotk_reconcile_condition{status="Deleted"}) + by (namespace, name, kind)) * 2 == 1 + for: 15m + labels: + severity: critical diff --git a/kubernetes/apps/flux-system/monitoring/ks.yaml b/kubernetes/apps/flux-system/monitoring/ks.yaml new file mode 100644 index 000000000..5bc9dfb25 --- /dev/null +++ b/kubernetes/apps/flux-system/monitoring/ks.yaml @@ -0,0 +1,22 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app flux-monitoring + namespace: flux-system +spec: + targetNamespace: flux-system + commonMetadata: + labels: + app.kubernetes.io/name: *app + dependsOn: + - name: prometheus-operator-crds + path: ./kubernetes/apps/flux-system/monitoring/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/flux-system/namespace.yaml b/kubernetes/apps/flux-system/namespace.yaml new file mode 100644 index 000000000..b48db4521 --- /dev/null +++ b/kubernetes/apps/flux-system/namespace.yaml @@ -0,0 +1,7 @@ +--- +apiVersion: v1 +kind: Namespace +metadata: + name: flux-system + labels: + kustomize.toolkit.fluxcd.io/prune: disabled diff --git a/kubernetes/apps/flux-system/weave-gitops/app/externalsecret.yaml b/kubernetes/apps/flux-system/weave-gitops/app/externalsecret.yaml new file mode 100644 index 000000000..b731e807a --- /dev/null +++ b/kubernetes/apps/flux-system/weave-gitops/app/externalsecret.yaml @@ -0,0 +1,47 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/external-secrets.io/externalsecret_v1beta1.json +apiVersion: external-secrets.io/v1beta1 +kind: ExternalSecret +metadata: + name: weave-gitops-cluster-user-auth +spec: + secretStoreRef: + kind: ClusterSecretStore + name: onepassword + target: + name: cluster-user-auth + template: + engineVersion: v2 + data: + username: "{{ .username }}" + password: "{{ .password }}" + dataFrom: + - extract: + key: weave-gitops +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/external-secrets.io/externalsecret_v1beta1.json +apiVersion: external-secrets.io/v1beta1 +kind: ExternalSecret +metadata: + name: weave-gitops-oidc-auth +spec: + secretStoreRef: + kind: ClusterSecretStore + name: onepassword + target: + name: oidc-auth + template: + engineVersion: v2 + data: + issuerURL: "{{ .issuerURL }}" + clientID: "{{ .clientID }}" + clientSecret: "{{ .clientSecret }}" + redirectURL: "https://gitops.${SECRET_DOMAIN}/oauth2/callback" + customScopes: "{{ .customScopes }}" + claimGroups: "{{ .claimGroups }}" + claimUsername: "{{ .claimUsername }}" + dataFrom: + - extract: + key: weave-gitops + - extract: + key: oidc-general diff --git a/kubernetes/apps/flux-system/weave-gitops/app/helmrelease.yaml b/kubernetes/apps/flux-system/weave-gitops/app/helmrelease.yaml new file mode 100644 index 000000000..20641e748 --- /dev/null +++ b/kubernetes/apps/flux-system/weave-gitops/app/helmrelease.yaml @@ -0,0 +1,71 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: weave-gitops + namespace: flux-system +spec: + interval: 30m + chart: + spec: + chart: weave-gitops + version: 4.0.36 + sourceRef: + kind: HelmRepository + name: weave-gitops + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + envVars: + - name: WEAVE_GITOPS_FEATURE_TENANCY + value: "true" + - name: WEAVE_GITOPS_FEATURE_CLUSTER + value: "true" + - name: WEAVE_GITOPS_FEATURE_TELEMETRY + value: "true" + - name: WEAVE_GITOPS_FEATURE_OIDC_BUTTON_LABEL + value: "Login with Homelab Account" + additionalArgs: + - --auth-methods=oidc + adminUser: + create: true + createSecret: false + username: admin + ingress: + enabled: true + className: internal + annotations: + hajimari.io/icon: sawtooth-wave + hosts: + - host: &host gitops.${SECRET_DOMAIN} + paths: + - path: / + pathType: Prefix + tls: + - hosts: + - *host + networkPolicy: + create: false + metrics: + enabled: true + logLevel: info + rbac: + create: true + #impersonationResourceNames: ["tdeutsch"] + additionalRules: + - apiGroups: + - "infra.contrib.fluxcd.io" + resources: + - "terraforms" + verbs: + - "get" + - "list" + - "patch" + podAnnotations: + secret.reloader.stakater.com/reload: auto diff --git a/kubernetes/apps/flux-system/weave-gitops/app/kustomization.yaml b/kubernetes/apps/flux-system/weave-gitops/app/kustomization.yaml new file mode 100644 index 000000000..96d7856ef --- /dev/null +++ b/kubernetes/apps/flux-system/weave-gitops/app/kustomization.yaml @@ -0,0 +1,9 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +namespace: flux-system +resources: + - ./externalsecret.yaml + - ./helmrelease.yaml + - ./rbac.yaml diff --git a/kubernetes/apps/flux-system/weave-gitops/app/rbac.yaml b/kubernetes/apps/flux-system/weave-gitops/app/rbac.yaml new file mode 100644 index 000000000..639c8be31 --- /dev/null +++ b/kubernetes/apps/flux-system/weave-gitops/app/rbac.yaml @@ -0,0 +1,13 @@ +--- +apiVersion: rbac.authorization.k8s.io/v1 +kind: ClusterRoleBinding +metadata: + name: wego-admin-oidc +subjects: + - name: applications_weave_gitops + apiGroup: rbac.authorization.k8s.io + kind: Group +roleRef: + name: wego-admin-cluster-role + apiGroup: rbac.authorization.k8s.io + kind: ClusterRole diff --git a/kubernetes/apps/flux-system/weave-gitops/ks.yaml b/kubernetes/apps/flux-system/weave-gitops/ks.yaml new file mode 100644 index 000000000..34924e1af --- /dev/null +++ b/kubernetes/apps/flux-system/weave-gitops/ks.yaml @@ -0,0 +1,21 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/kustomize.toolkit.fluxcd.io/kustomization_v1.json +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app weave-gitops + namespace: flux-system +spec: + commonMetadata: + labels: + app.kubernetes.io/name: *app + targetNamespace: flux-system + path: ./kubernetes/apps/flux-system/weave-gitops/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false # no flux ks dependents + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/flux-system/webhooks/app/github/ingress.yaml b/kubernetes/apps/flux-system/webhooks/app/github/ingress.yaml new file mode 100644 index 000000000..c319b20d6 --- /dev/null +++ b/kubernetes/apps/flux-system/webhooks/app/github/ingress.yaml @@ -0,0 +1,21 @@ +--- +apiVersion: networking.k8s.io/v1 +kind: Ingress +metadata: + name: flux-webhook + annotations: + external-dns.alpha.kubernetes.io/target: "external.${SECRET_DOMAIN}" + gatus.io/enabled: false +spec: + ingressClassName: external + rules: + - host: "flux-webhook.${SECRET_DOMAIN}" + http: + paths: + - path: /hook/ + pathType: Prefix + backend: + service: + name: webhook-receiver + port: + number: 80 diff --git a/kubernetes/apps/flux-system/webhooks/app/github/kustomization.yaml b/kubernetes/apps/flux-system/webhooks/app/github/kustomization.yaml new file mode 100644 index 000000000..786e654a5 --- /dev/null +++ b/kubernetes/apps/flux-system/webhooks/app/github/kustomization.yaml @@ -0,0 +1,7 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./secret.sops.yaml + - ./ingress.yaml + - ./receiver.yaml diff --git a/kubernetes/apps/flux-system/webhooks/app/github/receiver.yaml b/kubernetes/apps/flux-system/webhooks/app/github/receiver.yaml new file mode 100644 index 000000000..d178f1c3c --- /dev/null +++ b/kubernetes/apps/flux-system/webhooks/app/github/receiver.yaml @@ -0,0 +1,25 @@ +--- +apiVersion: notification.toolkit.fluxcd.io/v1 +kind: Receiver +metadata: + name: github-receiver +spec: + type: github + events: + - ping + - push + secretRef: + name: github-webhook-token-secret + resources: + - apiVersion: source.toolkit.fluxcd.io/v1 + kind: GitRepository + name: k8s-homelab + namespace: flux-system + - apiVersion: kustomize.toolkit.fluxcd.io/v1 + kind: Kustomization + name: cluster + namespace: flux-system + - apiVersion: kustomize.toolkit.fluxcd.io/v1 + kind: Kustomization + name: cluster-apps + namespace: flux-system diff --git a/kubernetes/apps/flux-system/webhooks/app/github/secret.sops.yaml b/kubernetes/apps/flux-system/webhooks/app/github/secret.sops.yaml new file mode 100644 index 000000000..a2487d333 --- /dev/null +++ b/kubernetes/apps/flux-system/webhooks/app/github/secret.sops.yaml @@ -0,0 +1,26 @@ +apiVersion: v1 +kind: Secret +metadata: + name: github-webhook-token-secret +stringData: + token: ENC[AES256_GCM,data:jX/2BxoBAn+g2qpkqi0AXwGmhWnS3mfbLVbDfqkFKys=,iv:tFLobk2nZSTkVQubJk+RmYa4k05PBPG3RkRxPXvivxQ=,tag:o66TIrLrd44AXL9ESIyhNA==,type:str] +sops: + kms: [] + gcp_kms: [] + azure_kv: [] + hc_vault: [] + age: + - recipient: age1y0kzuf0tn94a74whazwae4r9qal4snuqfuhl5jacscrpr7up5gts74fe5w + enc: | + -----BEGIN AGE ENCRYPTED FILE----- + YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBqaFN5SUF5WS9JQWppYzcx + SitkVnZ5Y0w3ZkIyYk9xUHdOZ2VMWjFFOVRzCkJDekczN0ZJWFpKdXdZbDZRVUU4 + OWY2UW1YT1I0YXkvWkFOOElzVWkrZmcKLS0tIDhkTk5QNGs4clF2UkRKTE5zNWZS + T1p3NWlkUkRLZ2Z5OXlQb1ozcU0xWkUKT0zzBvr354akJnLBW/Bgh4j+KanLHjfJ + blq7yWE9pVHmCDaT4LFTktfAkAjP7DiN/ZilN74vY5zs/KSIH8ELtg== + -----END AGE ENCRYPTED FILE----- + lastmodified: "2024-06-06T09:08:40Z" + mac: ENC[AES256_GCM,data:i1/KO5tRck/N2ZCeFrf14h6NWdnUxX70IMHYY8dmz5ZVHF6iugpjucZdDvy3vTF73aMohMUFsxgOkll/iFcHJ674O4yfM/V1Cx84fzrAaGEfPuoya/IKvidYkGcVJ71VWVTKB+QlPpoPfavAPdP+V6XAoZ4ikfQTfJzZ1IfT73Q=,iv:G5aaEuVt3TlSFwjSlwQLhg6w+TekNpspPd0PJsMfpHI=,tag:W4pVeayUmYx8Wi285gVoeg==,type:str] + pgp: [] + encrypted_regex: ^(data|stringData)$ + version: 3.8.1 diff --git a/kubernetes/apps/flux-system/webhooks/app/kustomization.yaml b/kubernetes/apps/flux-system/webhooks/app/kustomization.yaml new file mode 100644 index 000000000..ccd8b3eb8 --- /dev/null +++ b/kubernetes/apps/flux-system/webhooks/app/kustomization.yaml @@ -0,0 +1,5 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./github diff --git a/kubernetes/apps/flux-system/webhooks/ks.yaml b/kubernetes/apps/flux-system/webhooks/ks.yaml new file mode 100644 index 000000000..afa7b0e84 --- /dev/null +++ b/kubernetes/apps/flux-system/webhooks/ks.yaml @@ -0,0 +1,20 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app flux-webhooks + namespace: flux-system +spec: + targetNamespace: flux-system + commonMetadata: + labels: + app.kubernetes.io/name: *app + path: ./kubernetes/apps/flux-system/webhooks/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/kube-system/cilium/app/helm-values.yaml b/kubernetes/apps/kube-system/cilium/app/helm-values.yaml new file mode 100644 index 000000000..cadf78a6d --- /dev/null +++ b/kubernetes/apps/kube-system/cilium/app/helm-values.yaml @@ -0,0 +1,57 @@ +--- +autoDirectNodeRoutes: true +bpf: + masquerade: false +cgroup: + automount: + enabled: false + hostRoot: /sys/fs/cgroup +cluster: + id: 1 + name: talos-test +cni: + exclusive: false +containerRuntime: + integration: containerd +# NOTE: devices might need to be set if you have more than one active NIC on your hosts +# devices: eno+ eth+ +endpointRoutes: + enabled: true +hubble: + enabled: false +ipam: + mode: kubernetes +ipv4NativeRoutingCIDR: 10.69.0.0/16 +k8sServiceHost: 127.0.0.1 +k8sServicePort: 7445 +kubeProxyReplacement: true +kubeProxyReplacementHealthzBindAddr: 0.0.0.0:10256 +l2announcements: + enabled: true +loadBalancer: + algorithm: maglev + mode: snat +localRedirectPolicy: true +operator: + replicas: 1 + rollOutPods: true +rollOutCiliumPods: true +routingMode: native +securityContext: + capabilities: + ciliumAgent: + - CHOWN + - KILL + - NET_ADMIN + - NET_RAW + - IPC_LOCK + - SYS_ADMIN + - SYS_RESOURCE + - DAC_OVERRIDE + - FOWNER + - SETGID + - SETUID + cleanCiliumState: + - NET_ADMIN + - SYS_ADMIN + - SYS_RESOURCE diff --git a/kubernetes/apps/kube-system/cilium/app/helmrelease.yaml b/kubernetes/apps/kube-system/cilium/app/helmrelease.yaml new file mode 100644 index 000000000..bfb6a4d48 --- /dev/null +++ b/kubernetes/apps/kube-system/cilium/app/helmrelease.yaml @@ -0,0 +1,74 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: cilium +spec: + interval: 30m + chart: + spec: + chart: cilium + version: 1.15.6 + sourceRef: + kind: HelmRepository + name: cilium + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + valuesFrom: + - kind: ConfigMap + name: cilium-helm-values + values: + hubble: + enabled: true + metrics: + enabled: + - dns:query + - drop + - tcp + - flow + - port-distribution + - icmp + - http + serviceMonitor: + enabled: true + dashboards: + enabled: true + annotations: + grafana_folder: Cilium + relay: + enabled: true + rollOutPods: true + prometheus: + serviceMonitor: + enabled: true + ui: + enabled: true + rollOutPods: true + ingress: + enabled: true + className: internal + hosts: ["hubble.${SECRET_DOMAIN}"] + operator: + prometheus: + enabled: true + serviceMonitor: + enabled: true + dashboards: + enabled: true + annotations: + grafana_folder: Cilium + prometheus: + enabled: true + serviceMonitor: + enabled: true + trustCRDsExist: true + dashboards: + enabled: true + annotations: + grafana_folder: Cilium diff --git a/kubernetes/apps/kube-system/cilium/app/kustomization.yaml b/kubernetes/apps/kube-system/cilium/app/kustomization.yaml new file mode 100644 index 000000000..b4f3860b0 --- /dev/null +++ b/kubernetes/apps/kube-system/cilium/app/kustomization.yaml @@ -0,0 +1,11 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml +configMapGenerator: + - name: cilium-helm-values + files: + - values.yaml=./helm-values.yaml +configurations: + - kustomizeconfig.yaml diff --git a/kubernetes/apps/kube-system/cilium/app/kustomizeconfig.yaml b/kubernetes/apps/kube-system/cilium/app/kustomizeconfig.yaml new file mode 100644 index 000000000..58f92ba15 --- /dev/null +++ b/kubernetes/apps/kube-system/cilium/app/kustomizeconfig.yaml @@ -0,0 +1,7 @@ +--- +nameReference: + - kind: ConfigMap + version: v1 + fieldSpecs: + - path: spec/valuesFrom/name + kind: HelmRelease diff --git a/kubernetes/apps/kube-system/cilium/config/cilium-l2.yaml b/kubernetes/apps/kube-system/cilium/config/cilium-l2.yaml new file mode 100644 index 000000000..8d8e66922 --- /dev/null +++ b/kubernetes/apps/kube-system/cilium/config/cilium-l2.yaml @@ -0,0 +1,24 @@ +--- +# https://docs.cilium.io/en/latest/network/l2-announcements +apiVersion: cilium.io/v2alpha1 +kind: CiliumL2AnnouncementPolicy +metadata: + name: l2-policy +spec: + loadBalancerIPs: true + # NOTE: interfaces might need to be set if you have more than one active NIC on your hosts + # interfaces: + # - ^eno[0-9]+ + # - ^eth[0-9]+ + nodeSelector: + matchLabels: + kubernetes.io/os: linux +--- +apiVersion: cilium.io/v2alpha1 +kind: CiliumLoadBalancerIPPool +metadata: + name: l2-pool +spec: + allowFirstLastIPs: "Yes" + blocks: + - cidr: "192.168.13.64/27" # Network range 192.168.13.64 - 192.168.13.95 / Usable range 192.168.13.65 - 192.168.13.94 diff --git a/kubernetes/apps/kube-system/cilium/config/kustomization.yaml b/kubernetes/apps/kube-system/cilium/config/kustomization.yaml new file mode 100644 index 000000000..f68996538 --- /dev/null +++ b/kubernetes/apps/kube-system/cilium/config/kustomization.yaml @@ -0,0 +1,5 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./cilium-l2.yaml diff --git a/kubernetes/apps/kube-system/cilium/ks.yaml b/kubernetes/apps/kube-system/cilium/ks.yaml new file mode 100644 index 000000000..dbcf6bbbd --- /dev/null +++ b/kubernetes/apps/kube-system/cilium/ks.yaml @@ -0,0 +1,42 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app cilium + namespace: flux-system +spec: + targetNamespace: kube-system + commonMetadata: + labels: + app.kubernetes.io/name: *app + path: ./kubernetes/apps/kube-system/cilium/app + prune: false # never should be deleted + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app cilium-config + namespace: flux-system +spec: + targetNamespace: kube-system + commonMetadata: + labels: + app.kubernetes.io/name: *app + dependsOn: + - name: cilium + path: ./kubernetes/apps/kube-system/cilium/config + prune: false # never should be deleted + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/kube-system/coredns/app/helm-values.yaml b/kubernetes/apps/kube-system/coredns/app/helm-values.yaml new file mode 100644 index 000000000..22da02986 --- /dev/null +++ b/kubernetes/apps/kube-system/coredns/app/helm-values.yaml @@ -0,0 +1,50 @@ +--- +fullnameOverride: coredns +k8sAppLabelOverride: kube-dns +serviceAccount: + create: true +service: + name: kube-dns + clusterIP: "10.96.0.10" +servers: + - zones: + - zone: . + scheme: dns:// + use_tcp: true + port: 53 + plugins: + - name: errors + - name: health + configBlock: |- + lameduck 5s + - name: ready + - name: log + configBlock: |- + class error + - name: prometheus + parameters: 0.0.0.0:9153 + - name: kubernetes + parameters: cluster.local in-addr.arpa ip6.arpa + configBlock: |- + pods insecure + fallthrough in-addr.arpa ip6.arpa + - name: forward + parameters: . /etc/resolv.conf + - name: cache + parameters: 30 + - name: loop + - name: reload + - name: loadbalance +affinity: + nodeAffinity: + requiredDuringSchedulingIgnoredDuringExecution: + nodeSelectorTerms: + - matchExpressions: + - key: node-role.kubernetes.io/control-plane + operator: Exists +tolerations: + - key: CriticalAddonsOnly + operator: Exists + - key: node-role.kubernetes.io/control-plane + operator: Exists + effect: NoSchedule diff --git a/kubernetes/apps/kube-system/coredns/app/helmrelease.yaml b/kubernetes/apps/kube-system/coredns/app/helmrelease.yaml new file mode 100644 index 000000000..eb6cd2f9a --- /dev/null +++ b/kubernetes/apps/kube-system/coredns/app/helmrelease.yaml @@ -0,0 +1,26 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: coredns +spec: + interval: 30m + chart: + spec: + chart: coredns + version: 1.30.0 + sourceRef: + kind: HelmRepository + name: coredns + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + strategy: rollback + retries: 3 + valuesFrom: + - kind: ConfigMap + name: coredns-helm-values diff --git a/kubernetes/apps/kube-system/coredns/app/kustomization.yaml b/kubernetes/apps/kube-system/coredns/app/kustomization.yaml new file mode 100644 index 000000000..691355b56 --- /dev/null +++ b/kubernetes/apps/kube-system/coredns/app/kustomization.yaml @@ -0,0 +1,11 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml +configMapGenerator: + - name: coredns-helm-values + files: + - values.yaml=./helm-values.yaml +configurations: + - kustomizeconfig.yaml diff --git a/kubernetes/apps/kube-system/coredns/app/kustomizeconfig.yaml b/kubernetes/apps/kube-system/coredns/app/kustomizeconfig.yaml new file mode 100644 index 000000000..58f92ba15 --- /dev/null +++ b/kubernetes/apps/kube-system/coredns/app/kustomizeconfig.yaml @@ -0,0 +1,7 @@ +--- +nameReference: + - kind: ConfigMap + version: v1 + fieldSpecs: + - path: spec/valuesFrom/name + kind: HelmRelease diff --git a/kubernetes/apps/kube-system/coredns/ks.yaml b/kubernetes/apps/kube-system/coredns/ks.yaml new file mode 100644 index 000000000..cec4bfef0 --- /dev/null +++ b/kubernetes/apps/kube-system/coredns/ks.yaml @@ -0,0 +1,20 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app coredns + namespace: flux-system +spec: + targetNamespace: kube-system + commonMetadata: + labels: + app.kubernetes.io/name: *app + path: ./kubernetes/apps/kube-system/coredns/app + prune: false # never should be deleted + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/kube-system/kubelet-csr-approver/app/helm-values.yaml b/kubernetes/apps/kube-system/kubelet-csr-approver/app/helm-values.yaml new file mode 100644 index 000000000..67bd17346 --- /dev/null +++ b/kubernetes/apps/kube-system/kubelet-csr-approver/app/helm-values.yaml @@ -0,0 +1,3 @@ +--- +providerRegex: ^(talos-test01|talos-test02|talos-test03|talos-test04)$ +bypassDnsResolution: true diff --git a/kubernetes/apps/kube-system/kubelet-csr-approver/app/helmrelease.yaml b/kubernetes/apps/kube-system/kubelet-csr-approver/app/helmrelease.yaml new file mode 100644 index 000000000..0c14465d2 --- /dev/null +++ b/kubernetes/apps/kube-system/kubelet-csr-approver/app/helmrelease.yaml @@ -0,0 +1,30 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: kubelet-csr-approver +spec: + interval: 30m + chart: + spec: + chart: kubelet-csr-approver + version: 1.2.1 + sourceRef: + kind: HelmRepository + name: postfinance + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + valuesFrom: + - kind: ConfigMap + name: kubelet-csr-approver-helm-values + values: + metrics: + enable: true + serviceMonitor: + enabled: true diff --git a/kubernetes/apps/kube-system/kubelet-csr-approver/app/kustomization.yaml b/kubernetes/apps/kube-system/kubelet-csr-approver/app/kustomization.yaml new file mode 100644 index 000000000..30dddafcb --- /dev/null +++ b/kubernetes/apps/kube-system/kubelet-csr-approver/app/kustomization.yaml @@ -0,0 +1,11 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml +configMapGenerator: + - name: kubelet-csr-approver-helm-values + files: + - values.yaml=./helm-values.yaml +configurations: + - kustomizeconfig.yaml diff --git a/kubernetes/apps/kube-system/kubelet-csr-approver/app/kustomizeconfig.yaml b/kubernetes/apps/kube-system/kubelet-csr-approver/app/kustomizeconfig.yaml new file mode 100644 index 000000000..58f92ba15 --- /dev/null +++ b/kubernetes/apps/kube-system/kubelet-csr-approver/app/kustomizeconfig.yaml @@ -0,0 +1,7 @@ +--- +nameReference: + - kind: ConfigMap + version: v1 + fieldSpecs: + - path: spec/valuesFrom/name + kind: HelmRelease diff --git a/kubernetes/apps/kube-system/kubelet-csr-approver/ks.yaml b/kubernetes/apps/kube-system/kubelet-csr-approver/ks.yaml new file mode 100644 index 000000000..936bac645 --- /dev/null +++ b/kubernetes/apps/kube-system/kubelet-csr-approver/ks.yaml @@ -0,0 +1,20 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app kubelet-csr-approver + namespace: flux-system +spec: + targetNamespace: kube-system + commonMetadata: + labels: + app.kubernetes.io/name: *app + path: ./kubernetes/apps/kube-system/kubelet-csr-approver/app + prune: false # never should be deleted + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/kube-system/kubernetes-replicator/app/helmrelease.yaml b/kubernetes/apps/kube-system/kubernetes-replicator/app/helmrelease.yaml new file mode 100644 index 000000000..408f7b237 --- /dev/null +++ b/kubernetes/apps/kube-system/kubernetes-replicator/app/helmrelease.yaml @@ -0,0 +1,23 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: &app kubernetes-replicator +spec: + interval: 30m + chart: + spec: + chart: *app + version: 2.9.2 + sourceRef: + kind: HelmRepository + name: mittwald-charts + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: diff --git a/kubernetes/apps/kube-system/kubernetes-replicator/app/kustomization.yaml b/kubernetes/apps/kube-system/kubernetes-replicator/app/kustomization.yaml new file mode 100644 index 000000000..5dd7baca7 --- /dev/null +++ b/kubernetes/apps/kube-system/kubernetes-replicator/app/kustomization.yaml @@ -0,0 +1,5 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml diff --git a/kubernetes/apps/kube-system/kubernetes-replicator/ks.yaml b/kubernetes/apps/kube-system/kubernetes-replicator/ks.yaml new file mode 100644 index 000000000..56c75fd69 --- /dev/null +++ b/kubernetes/apps/kube-system/kubernetes-replicator/ks.yaml @@ -0,0 +1,20 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app kubernetes-replicator + namespace: flux-system +spec: + targetNamespace: kube-system + commonMetadata: + labels: + app.kubernetes.io/name: *app + path: ./kubernetes/apps/kube-system/kubernetes-replicator/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/kube-system/kustomization.yaml b/kubernetes/apps/kube-system/kustomization.yaml new file mode 100644 index 000000000..d3a806426 --- /dev/null +++ b/kubernetes/apps/kube-system/kustomization.yaml @@ -0,0 +1,12 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - namespace.yaml + - cilium/ks.yaml + - coredns/ks.yaml + - kubelet-csr-approver/ks.yaml + - kubernetes-replicator/ks.yaml + - metrics-server/ks.yaml + - reloader/ks.yaml + - spegel/ks.yaml diff --git a/kubernetes/apps/kube-system/metrics-server/app/helmrelease.yaml b/kubernetes/apps/kube-system/metrics-server/app/helmrelease.yaml new file mode 100644 index 000000000..60298df66 --- /dev/null +++ b/kubernetes/apps/kube-system/metrics-server/app/helmrelease.yaml @@ -0,0 +1,31 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: metrics-server +spec: + interval: 30m + chart: + spec: + chart: metrics-server + version: 3.12.1 + sourceRef: + kind: HelmRepository + name: metrics-server + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + args: + - --kubelet-preferred-address-types=InternalIP,ExternalIP,Hostname + - --kubelet-use-node-status-port + - --metric-resolution=15s + metrics: + enabled: true + serviceMonitor: + enabled: true diff --git a/kubernetes/apps/kube-system/metrics-server/app/kustomization.yaml b/kubernetes/apps/kube-system/metrics-server/app/kustomization.yaml new file mode 100644 index 000000000..5dd7baca7 --- /dev/null +++ b/kubernetes/apps/kube-system/metrics-server/app/kustomization.yaml @@ -0,0 +1,5 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml diff --git a/kubernetes/apps/kube-system/metrics-server/ks.yaml b/kubernetes/apps/kube-system/metrics-server/ks.yaml new file mode 100644 index 000000000..090b2ae73 --- /dev/null +++ b/kubernetes/apps/kube-system/metrics-server/ks.yaml @@ -0,0 +1,20 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app metrics-server + namespace: flux-system +spec: + targetNamespace: kube-system + commonMetadata: + labels: + app.kubernetes.io/name: *app + path: ./kubernetes/apps/kube-system/metrics-server/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/kube-system/namespace.yaml b/kubernetes/apps/kube-system/namespace.yaml new file mode 100644 index 000000000..5eeb2c918 --- /dev/null +++ b/kubernetes/apps/kube-system/namespace.yaml @@ -0,0 +1,7 @@ +--- +apiVersion: v1 +kind: Namespace +metadata: + name: kube-system + labels: + kustomize.toolkit.fluxcd.io/prune: disabled diff --git a/kubernetes/apps/kube-system/reloader/app/helmrelease.yaml b/kubernetes/apps/kube-system/reloader/app/helmrelease.yaml new file mode 100644 index 000000000..0a3965fcd --- /dev/null +++ b/kubernetes/apps/kube-system/reloader/app/helmrelease.yaml @@ -0,0 +1,29 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: reloader +spec: + interval: 30m + chart: + spec: + chart: reloader + version: 1.0.107 + sourceRef: + kind: HelmRepository + name: stakater + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + fullnameOverride: reloader + reloader: + readOnlyRootFileSystem: true + podMonitor: + enabled: true + namespace: "{{ .Release.Namespace }}" diff --git a/kubernetes/apps/kube-system/reloader/app/kustomization.yaml b/kubernetes/apps/kube-system/reloader/app/kustomization.yaml new file mode 100644 index 000000000..5dd7baca7 --- /dev/null +++ b/kubernetes/apps/kube-system/reloader/app/kustomization.yaml @@ -0,0 +1,5 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml diff --git a/kubernetes/apps/kube-system/reloader/ks.yaml b/kubernetes/apps/kube-system/reloader/ks.yaml new file mode 100644 index 000000000..6f9458dc1 --- /dev/null +++ b/kubernetes/apps/kube-system/reloader/ks.yaml @@ -0,0 +1,20 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app reloader + namespace: flux-system +spec: + targetNamespace: kube-system + commonMetadata: + labels: + app.kubernetes.io/name: *app + path: ./kubernetes/apps/kube-system/reloader/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/kube-system/spegel/app/helm-values.yaml b/kubernetes/apps/kube-system/spegel/app/helm-values.yaml new file mode 100644 index 000000000..a4185ae36 --- /dev/null +++ b/kubernetes/apps/kube-system/spegel/app/helm-values.yaml @@ -0,0 +1,7 @@ +--- +spegel: + containerdSock: /run/containerd/containerd.sock + containerdRegistryConfigPath: /etc/cri/conf.d/hosts +service: + registry: + hostPort: 29999 diff --git a/kubernetes/apps/kube-system/spegel/app/helmrelease.yaml b/kubernetes/apps/kube-system/spegel/app/helmrelease.yaml new file mode 100644 index 000000000..613d34ea9 --- /dev/null +++ b/kubernetes/apps/kube-system/spegel/app/helmrelease.yaml @@ -0,0 +1,28 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: spegel +spec: + interval: 30m + chart: + spec: + chart: spegel + version: v0.0.23 + sourceRef: + kind: HelmRepository + name: spegel + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + valuesFrom: + - kind: ConfigMap + name: spegel-helm-values + values: + serviceMonitor: + enabled: true diff --git a/kubernetes/apps/kube-system/spegel/app/kustomization.yaml b/kubernetes/apps/kube-system/spegel/app/kustomization.yaml new file mode 100644 index 000000000..1e1aa1d17 --- /dev/null +++ b/kubernetes/apps/kube-system/spegel/app/kustomization.yaml @@ -0,0 +1,11 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml +configMapGenerator: + - name: spegel-helm-values + files: + - values.yaml=./helm-values.yaml +configurations: + - kustomizeconfig.yaml diff --git a/kubernetes/apps/kube-system/spegel/app/kustomizeconfig.yaml b/kubernetes/apps/kube-system/spegel/app/kustomizeconfig.yaml new file mode 100644 index 000000000..58f92ba15 --- /dev/null +++ b/kubernetes/apps/kube-system/spegel/app/kustomizeconfig.yaml @@ -0,0 +1,7 @@ +--- +nameReference: + - kind: ConfigMap + version: v1 + fieldSpecs: + - path: spec/valuesFrom/name + kind: HelmRelease diff --git a/kubernetes/apps/kube-system/spegel/ks.yaml b/kubernetes/apps/kube-system/spegel/ks.yaml new file mode 100644 index 000000000..cb9f37ed4 --- /dev/null +++ b/kubernetes/apps/kube-system/spegel/ks.yaml @@ -0,0 +1,20 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app spegel + namespace: flux-system +spec: + targetNamespace: kube-system + commonMetadata: + labels: + app.kubernetes.io/name: *app + path: ./kubernetes/apps/kube-system/spegel/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/media/calibre-web/app/helmrelease.yaml b/kubernetes/apps/media/calibre-web/app/helmrelease.yaml new file mode 100644 index 000000000..5722ed6f7 --- /dev/null +++ b/kubernetes/apps/media/calibre-web/app/helmrelease.yaml @@ -0,0 +1,105 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: &app calibre-web +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + global: + nameOverride: *app + controllers: + app: + strategy: Recreate + annotations: + reloader.stakater.com/auto: "true" + containers: + main: + image: + repository: lscr.io/linuxserver/calibre-web + tag: 0.6.20-ls229 + env: + TZ: ${TIMEZONE} + PUID: 1027 + PGID: 100 + DOCKER_MODS: linuxserver/mods:universal-calibre + CACHE_DIR: /cache + resources: + requests: + cpu: 5m + memory: 100Mi + limits: + memory: 500Mi + initContainers: + update-volume-permission: + image: + repository: busybox + tag: 1.36.1 + command: [sh, -c, chown -R 1000:1000 /config] + securityContext: + runAsUser: 0 + service: + app: + controller: app + ports: + http: + port: &port 8083 + ingress: + app: + enabled: true + className: internal + annotations: + # nginx.ingress.kubernetes.io/auth-method: GET + # nginx.ingress.kubernetes.io/auth-url: https://auth.${SECRET_DOMAIN}/api/verify + # nginx.ingress.kubernetes.io/auth-signin: https://auth.${SECRET_DOMAIN}?rm=$request_method + # nginx.ingress.kubernetes.io/auth-response-headers: Remote-User,Remote-Name,Remote-Groups,Remote-Email + # nginx.ingress.kubernetes.io/auth-snippet: | + # proxy_set_header X-Forwarded-Method $request_method; + # proxy_set_header X-Forwarded-Scheme $scheme; + hajimari.io/icon: bookshelf + hosts: + - host: &host books.${SECRET_DOMAIN} + paths: + - path: / + pathType: Prefix + service: + identifier: app + port: *port + tls: + - hosts: + - *host + persistence: + config: + enabled: true + type: persistentVolumeClaim + accessMode: ReadWriteOnce + size: 5Gi + storageClass: ${MAIN_SC} + globalMounts: + - path: /config + data: + enabled: true + type: nfs + server: 10.20.30.40 + path: /volume2/data/calibre + globalMounts: + - path: /data/calibre + cache: + type: emptyDir + globalMounts: + - path: /cache diff --git a/kubernetes/apps/media/calibre-web/app/kustomization.yaml b/kubernetes/apps/media/calibre-web/app/kustomization.yaml new file mode 100644 index 000000000..17cbc72b2 --- /dev/null +++ b/kubernetes/apps/media/calibre-web/app/kustomization.yaml @@ -0,0 +1,6 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml diff --git a/kubernetes/apps/media/calibre-web/ks.yaml b/kubernetes/apps/media/calibre-web/ks.yaml new file mode 100644 index 000000000..d459a4924 --- /dev/null +++ b/kubernetes/apps/media/calibre-web/ks.yaml @@ -0,0 +1,20 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app calibre-web + namespace: flux-system +spec: + commonMetadata: + labels: + app.kubernetes.io/name: *app + targetNamespace: media + path: ./kubernetes/apps/media/calibre-web/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/media/kustomization.yaml b/kubernetes/apps/media/kustomization.yaml new file mode 100644 index 000000000..2e2fd7413 --- /dev/null +++ b/kubernetes/apps/media/kustomization.yaml @@ -0,0 +1,12 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - namespace.yaml + - calibre-web/ks.yaml + - mediabox/ks.yaml + - overseerr/ks.yaml + - plex-exporter/ks.yaml + - plex-trakt-sync/ks.yaml + - readarr/ks.yaml + - tautulli/ks.yaml diff --git a/kubernetes/apps/media/mediabox/app/bazarr-ingress.yaml b/kubernetes/apps/media/mediabox/app/bazarr-ingress.yaml new file mode 100755 index 000000000..be76468a3 --- /dev/null +++ b/kubernetes/apps/media/mediabox/app/bazarr-ingress.yaml @@ -0,0 +1,33 @@ +--- +apiVersion: networking.k8s.io/v1 +kind: Ingress +metadata: + name: bazarr + annotations: + external-dns.alpha.kubernetes.io/target: "external.${SECRET_DOMAIN}" + nginx.ingress.kubernetes.io/auth-method: GET + nginx.ingress.kubernetes.io/auth-url: https://auth.${SECRET_DOMAIN}/api/verify + nginx.ingress.kubernetes.io/auth-signin: https://auth.${SECRET_DOMAIN}?rm=$request_method + nginx.ingress.kubernetes.io/auth-response-headers: Remote-User,Remote-Name,Remote-Groups,Remote-Email + nginx.ingress.kubernetes.io/auth-snippet: | + proxy_set_header X-Forwarded-Method $request_method; + proxy_set_header X-Forwarded-Scheme $scheme; + hajimari.io/enable: "true" + hajimari.io/icon: chart-bar +spec: + ingressClassName: external + tls: + - secretName: ${SECRET_DOMAIN/./-}-production-tls + hosts: + - bazarr.${SECRET_DOMAIN} + rules: + - host: bazarr.${SECRET_DOMAIN} + http: + paths: + - path: / + pathType: Prefix + backend: + service: + name: mediabox + port: + name: bazarr diff --git a/kubernetes/apps/media/mediabox/app/gaps-ingress.yaml b/kubernetes/apps/media/mediabox/app/gaps-ingress.yaml new file mode 100755 index 000000000..440c56e21 --- /dev/null +++ b/kubernetes/apps/media/mediabox/app/gaps-ingress.yaml @@ -0,0 +1,33 @@ +--- +apiVersion: networking.k8s.io/v1 +kind: Ingress +metadata: + name: gaps + annotations: + external-dns.alpha.kubernetes.io/target: "external.${SECRET_DOMAIN}" + nginx.ingress.kubernetes.io/auth-method: GET + nginx.ingress.kubernetes.io/auth-url: https://auth.${SECRET_DOMAIN}/api/verify + nginx.ingress.kubernetes.io/auth-signin: https://auth.${SECRET_DOMAIN}?rm=$request_method + nginx.ingress.kubernetes.io/auth-response-headers: Remote-User,Remote-Name,Remote-Groups,Remote-Email + nginx.ingress.kubernetes.io/auth-snippet: | + proxy_set_header X-Forwarded-Method $request_method; + proxy_set_header X-Forwarded-Scheme $scheme; + hajimari.io/enable: "true" + hajimari.io/icon: filmstrip +spec: + ingressClassName: external + tls: + - secretName: ${SECRET_DOMAIN/./-}-production-tls + hosts: + - gaps.${SECRET_DOMAIN} + rules: + - host: gaps.${SECRET_DOMAIN} + http: + paths: + - path: / + pathType: Prefix + backend: + service: + name: mediabox + port: + name: gaps diff --git a/kubernetes/apps/media/mediabox/app/kustomization.yaml b/kubernetes/apps/media/mediabox/app/kustomization.yaml new file mode 100755 index 000000000..699c3b5cd --- /dev/null +++ b/kubernetes/apps/media/mediabox/app/kustomization.yaml @@ -0,0 +1,15 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +namespace: media +resources: + - bazarr-ingress.yaml + - gaps-ingress.yaml + - lldap-ingress.yaml + - sabnzbd-ingress.yaml + - prowlarr-ingress.yaml + - radarr-ingress.yaml + - service.yaml + - sonarr-ingress.yaml + - notifiarr-ingress.yaml diff --git a/kubernetes/apps/media/mediabox/app/lldap-ingress.yaml b/kubernetes/apps/media/mediabox/app/lldap-ingress.yaml new file mode 100644 index 000000000..33f2f112a --- /dev/null +++ b/kubernetes/apps/media/mediabox/app/lldap-ingress.yaml @@ -0,0 +1,25 @@ +--- +apiVersion: networking.k8s.io/v1 +kind: Ingress +metadata: + name: lldap + annotations: + hajimari.io/enable: "true" + hajimari.io/icon: account-group +spec: + ingressClassName: internal + tls: + - secretName: ${SECRET_DOMAIN/./-}-production-tls + hosts: + - lldap.${SECRET_DOMAIN} + rules: + - host: lldap.${SECRET_DOMAIN} + http: + paths: + - path: / + pathType: Prefix + backend: + service: + name: mediabox + port: + name: lldap diff --git a/kubernetes/apps/media/mediabox/app/notifiarr-ingress.yaml b/kubernetes/apps/media/mediabox/app/notifiarr-ingress.yaml new file mode 100755 index 000000000..714eb850d --- /dev/null +++ b/kubernetes/apps/media/mediabox/app/notifiarr-ingress.yaml @@ -0,0 +1,26 @@ +--- +apiVersion: networking.k8s.io/v1 +kind: Ingress +metadata: + name: notifiarr + annotations: + external-dns.alpha.kubernetes.io/target: "external.${SECRET_DOMAIN}" + hajimari.io/enable: "true" + hajimari.io/icon: filmstrip +spec: + ingressClassName: external + tls: + - secretName: ${SECRET_DOMAIN/./-}-production-tls + hosts: + - notifiarr.${SECRET_DOMAIN} + rules: + - host: notifiarr.${SECRET_DOMAIN} + http: + paths: + - path: / + pathType: Prefix + backend: + service: + name: mediabox + port: + name: notifiarr diff --git a/kubernetes/apps/media/mediabox/app/prowlarr-ingress.yaml b/kubernetes/apps/media/mediabox/app/prowlarr-ingress.yaml new file mode 100755 index 000000000..295563c44 --- /dev/null +++ b/kubernetes/apps/media/mediabox/app/prowlarr-ingress.yaml @@ -0,0 +1,33 @@ +--- +apiVersion: networking.k8s.io/v1 +kind: Ingress +metadata: + name: prowlarr + annotations: + external-dns.alpha.kubernetes.io/target: "external.${SECRET_DOMAIN}" + nginx.ingress.kubernetes.io/auth-method: GET + nginx.ingress.kubernetes.io/auth-url: https://auth.${SECRET_DOMAIN}/api/verify + nginx.ingress.kubernetes.io/auth-signin: https://auth.${SECRET_DOMAIN}?rm=$request_method + nginx.ingress.kubernetes.io/auth-response-headers: Remote-User,Remote-Name,Remote-Groups,Remote-Email + nginx.ingress.kubernetes.io/auth-snippet: | + proxy_set_header X-Forwarded-Method $request_method; + proxy_set_header X-Forwarded-Scheme $scheme; + hajimari.io/enable: "true" + hajimari.io/icon: plex +spec: + ingressClassName: external + tls: + - secretName: ${SECRET_DOMAIN/./-}-production-tls + hosts: + - prowlarr.${SECRET_DOMAIN} + rules: + - host: prowlarr.${SECRET_DOMAIN} + http: + paths: + - path: / + pathType: Prefix + backend: + service: + name: mediabox + port: + name: prowlarr diff --git a/kubernetes/apps/media/mediabox/app/radarr-ingress.yaml b/kubernetes/apps/media/mediabox/app/radarr-ingress.yaml new file mode 100755 index 000000000..af86b1c3b --- /dev/null +++ b/kubernetes/apps/media/mediabox/app/radarr-ingress.yaml @@ -0,0 +1,33 @@ +--- +apiVersion: networking.k8s.io/v1 +kind: Ingress +metadata: + name: radarr + annotations: + external-dns.alpha.kubernetes.io/target: "external.${SECRET_DOMAIN}" + nginx.ingress.kubernetes.io/auth-method: GET + nginx.ingress.kubernetes.io/auth-url: https://auth.${SECRET_DOMAIN}/api/verify + nginx.ingress.kubernetes.io/auth-signin: https://auth.${SECRET_DOMAIN}?rm=$request_method + nginx.ingress.kubernetes.io/auth-response-headers: Remote-User,Remote-Name,Remote-Groups,Remote-Email + nginx.ingress.kubernetes.io/auth-snippet: | + proxy_set_header X-Forwarded-Method $request_method; + proxy_set_header X-Forwarded-Scheme $scheme; + hajimari.io/enable: "true" + hajimari.io/icon: filmstrip +spec: + ingressClassName: external + tls: + - secretName: ${SECRET_DOMAIN/./-}-production-tls + hosts: + - radarr.${SECRET_DOMAIN} + rules: + - host: radarr.${SECRET_DOMAIN} + http: + paths: + - path: / + pathType: Prefix + backend: + service: + name: mediabox + port: + name: radarr diff --git a/kubernetes/apps/media/mediabox/app/sabnzbd-ingress.yaml b/kubernetes/apps/media/mediabox/app/sabnzbd-ingress.yaml new file mode 100755 index 000000000..fdb4ad25d --- /dev/null +++ b/kubernetes/apps/media/mediabox/app/sabnzbd-ingress.yaml @@ -0,0 +1,33 @@ +--- +apiVersion: networking.k8s.io/v1 +kind: Ingress +metadata: + name: sabnzbd + annotations: + external-dns.alpha.kubernetes.io/target: "external.${SECRET_DOMAIN}" + nginx.ingress.kubernetes.io/auth-method: GET + nginx.ingress.kubernetes.io/auth-url: https://auth.${SECRET_DOMAIN}/api/verify + nginx.ingress.kubernetes.io/auth-signin: https://auth.${SECRET_DOMAIN}?rm=$request_method + nginx.ingress.kubernetes.io/auth-response-headers: Remote-User,Remote-Name,Remote-Groups,Remote-Email + nginx.ingress.kubernetes.io/auth-snippet: | + proxy_set_header X-Forwarded-Method $request_method; + proxy_set_header X-Forwarded-Scheme $scheme; + hajimari.io/enable: "true" + hajimari.io/icon: cloud-download +spec: + ingressClassName: external + tls: + - secretName: ${SECRET_DOMAIN/./-}-production-tls + hosts: + - sabnzbd.${SECRET_DOMAIN} + rules: + - host: sabnzbd.${SECRET_DOMAIN} + http: + paths: + - path: / + pathType: Prefix + backend: + service: + name: mediabox + port: + name: sabnzbd diff --git a/kubernetes/apps/media/mediabox/app/service.yaml b/kubernetes/apps/media/mediabox/app/service.yaml new file mode 100755 index 000000000..616954b4c --- /dev/null +++ b/kubernetes/apps/media/mediabox/app/service.yaml @@ -0,0 +1,42 @@ +--- +apiVersion: v1 +kind: Service +metadata: + name: mediabox +spec: + externalName: thiazi.home + ports: + - name: sonarr + port: 8989 + protocol: TCP + targetPort: 8989 + - name: radarr + port: 7878 + protocol: TCP + targetPort: 7878 + - name: prowlarr + port: 9696 + protocol: TCP + targetPort: 9696 + - name: sabnzbd + port: 8080 + protocol: TCP + targetPort: 8080 + - name: gaps + port: 8484 + protocol: TCP + targetPort: 8484 + - name: bazarr + port: 6767 + protocol: TCP + targetPort: 6767 + - name: notifiarr + port: 5454 + protocol: TCP + targetPort: 5454 + - name: lldap + port: 17170 + protocol: TCP + targetPort: 17170 + sessionAffinity: None + type: ExternalName diff --git a/kubernetes/apps/media/mediabox/app/sonarr-ingress.yaml b/kubernetes/apps/media/mediabox/app/sonarr-ingress.yaml new file mode 100755 index 000000000..031a87401 --- /dev/null +++ b/kubernetes/apps/media/mediabox/app/sonarr-ingress.yaml @@ -0,0 +1,33 @@ +--- +apiVersion: networking.k8s.io/v1 +kind: Ingress +metadata: + name: sonarr + annotations: + external-dns.alpha.kubernetes.io/target: "external.${SECRET_DOMAIN}" + nginx.ingress.kubernetes.io/auth-method: GET + nginx.ingress.kubernetes.io/auth-url: https://auth.${SECRET_DOMAIN}/api/verify + nginx.ingress.kubernetes.io/auth-signin: https://auth.${SECRET_DOMAIN}?rm=$request_method + nginx.ingress.kubernetes.io/auth-response-headers: Remote-User,Remote-Name,Remote-Groups,Remote-Email + nginx.ingress.kubernetes.io/auth-snippet: | + proxy_set_header X-Forwarded-Method $request_method; + proxy_set_header X-Forwarded-Scheme $scheme; + hajimari.io/enable: "true" + hajimari.io/icon: television-box +spec: + ingressClassName: external + tls: + - secretName: ${SECRET_DOMAIN/./-}-production-tls + hosts: + - sonarr.${SECRET_DOMAIN} + rules: + - host: sonarr.${SECRET_DOMAIN} + http: + paths: + - path: / + pathType: Prefix + backend: + service: + name: mediabox + port: + name: sonarr diff --git a/kubernetes/apps/media/mediabox/ks.yaml b/kubernetes/apps/media/mediabox/ks.yaml new file mode 100644 index 000000000..91fa2bfed --- /dev/null +++ b/kubernetes/apps/media/mediabox/ks.yaml @@ -0,0 +1,21 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/kustomize.toolkit.fluxcd.io/kustomization_v1.json +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app mediabox + namespace: flux-system +spec: + commonMetadata: + labels: + app.kubernetes.io/name: *app + targetNamespace: media + path: ./kubernetes/apps/media/mediabox/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/media/namespace.yaml b/kubernetes/apps/media/namespace.yaml new file mode 100644 index 000000000..e4b066b2a --- /dev/null +++ b/kubernetes/apps/media/namespace.yaml @@ -0,0 +1,7 @@ +--- +apiVersion: v1 +kind: Namespace +metadata: + name: media + labels: + kustomize.toolkit.fluxcd.io/prune: disabled diff --git a/kubernetes/apps/media/overseerr/app/helmrelease.yaml b/kubernetes/apps/media/overseerr/app/helmrelease.yaml new file mode 100644 index 000000000..5292f8c16 --- /dev/null +++ b/kubernetes/apps/media/overseerr/app/helmrelease.yaml @@ -0,0 +1,109 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: &app overseerr +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + controllers: + overseerr: + containers: + app: + image: + repository: ghcr.io/sct/overseerr + tag: 1.33.2@sha256:714ea6db2bc007a2262d112bef7eec74972eb33d9c72bddb9cbd98b8742de950 + env: + LOG_LEVEL: info + PORT: &port 5055 + TZ: ${TIMEZONE} + probes: + liveness: &probes + enabled: true + custom: true + spec: + httpGet: + path: &path /api/v1/status + port: *port + initialDelaySeconds: 0 + periodSeconds: 10 + timeoutSeconds: 1 + failureThreshold: 3 + readiness: *probes + resources: + requests: + cpu: 10m + limits: + memory: 2Gi + securityContext: + allowPrivilegeEscalation: false + readOnlyRootFilesystem: true + capabilities: + drop: + - ALL + defaultPodOptions: + securityContext: + runAsNonRoot: true + runAsUser: 568 + runAsGroup: 568 + fsGroup: 568 + fsGroupChangePolicy: OnRootMismatch + ingress: + app: + className: external + annotations: + gatus.io/path: *path + hajimari.io/icon: mdi:eye-circle + hajimari.io/url: https://requests.${SECRET_DOMAIN} + hosts: + - host: &host "requests.${SECRET_DOMAIN}" + paths: + - path: / + service: + identifier: app + port: http + tls: + - hosts: + - *host + persistence: + config: + enabled: true + type: persistentVolumeClaim + accessMode: ReadWriteOnce + size: 5Gi + storageClass: ${MAIN_SC} + globalMounts: + - path: /app/config + config-cache: + enabled: true + type: persistentVolumeClaim + accessMode: ReadWriteOnce + size: 5Gi + storageClass: ${MAIN_SC} + logs: + type: emptyDir + globalMounts: + - path: /app/config/logs + tmp: + type: emptyDir + service: + app: + controller: *app + ports: + http: + port: *port diff --git a/kubernetes/apps/media/overseerr/app/kustomization.yaml b/kubernetes/apps/media/overseerr/app/kustomization.yaml new file mode 100644 index 000000000..5dd7baca7 --- /dev/null +++ b/kubernetes/apps/media/overseerr/app/kustomization.yaml @@ -0,0 +1,5 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml diff --git a/kubernetes/apps/media/overseerr/ks.yaml b/kubernetes/apps/media/overseerr/ks.yaml new file mode 100644 index 000000000..830d6e37e --- /dev/null +++ b/kubernetes/apps/media/overseerr/ks.yaml @@ -0,0 +1,19 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: overseerr + namespace: flux-system +spec: + targetNamespace: media + dependsOn: + - name: external-secrets-secretstores + path: ./kubernetes/apps/media/overseerr/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/media/plex-exporter/app/configmap.yaml b/kubernetes/apps/media/plex-exporter/app/configmap.yaml new file mode 100755 index 000000000..feae626af --- /dev/null +++ b/kubernetes/apps/media/plex-exporter/app/configmap.yaml @@ -0,0 +1,19 @@ +--- +apiVersion: v1 +data: + config.json: | + { + "exporter": { + "port": 9567 + }, + "server": { + "address": "10.20.30.40", + "port": 32400, + "token": "${SECRET_PLEXTOKEN}" + } + } +kind: ConfigMap +metadata: + labels: + app: plex-exporter + name: plex-exporter-config diff --git a/kubernetes/apps/media/plex-exporter/app/deployment.yaml b/kubernetes/apps/media/plex-exporter/app/deployment.yaml new file mode 100755 index 000000000..512cdc9e0 --- /dev/null +++ b/kubernetes/apps/media/plex-exporter/app/deployment.yaml @@ -0,0 +1,50 @@ +--- +apiVersion: apps/v1 +kind: Deployment +metadata: + annotations: + reloader.stakater.com/auto: "true" + labels: + app: plex-exporter + name: plex-exporter +spec: + replicas: 1 + selector: + matchLabels: + app: plex-exporter + template: + metadata: + labels: + app: plex-exporter + spec: + containers: + - image: registry.eighty-three.me/tuxpeople/plex-exporter:nightly + command: + - /plex_exporter + args: + - --config + - /config.json + imagePullPolicy: Always + name: plex-exporter + ports: + - containerPort: 9567 + protocol: TCP + resources: + requests: + cpu: 10m + memory: 50Mi + limits: + cpu: 500m + memory: 500Mi + volumeMounts: + - mountPath: /config.json + name: plex-exporter-config + subPath: config.json + volumes: + - configMap: + items: + - key: config.json + mode: 420 + path: config.json + name: plex-exporter-config + name: plex-exporter-config diff --git a/kubernetes/apps/media/plex-exporter/app/grafana-dashboard.yaml b/kubernetes/apps/media/plex-exporter/app/grafana-dashboard.yaml new file mode 100755 index 000000000..737b49d4e --- /dev/null +++ b/kubernetes/apps/media/plex-exporter/app/grafana-dashboard.yaml @@ -0,0 +1,477 @@ +--- +apiVersion: v1 +kind: ConfigMap +metadata: + name: plex-exporter-dashboard + labels: + grafana_dashboard: '1' + app: plex-exporter + namespace: media + annotations: + grafana_folder: Apps +data: + plex-exporter-dashboard.json: |- + { + "annotations": { + "list": [ + { + "builtIn": 1, + "datasource": "-- Grafana --", + "enable": true, + "hide": true, + "iconColor": "rgba(0, 211, 255, 1)", + "name": "Annotations & Alerts", + "target": { + "limit": 100, + "matchAny": false, + "tags": [], + "type": "dashboard" + }, + "type": "dashboard" + } + ] + }, + "editable": true, + "fiscalYearStartMonth": 0, + "gnetId": null, + "graphTooltip": 0, + "id": null, + "links": [], + "liveNow": false, + "panels": [ + { + "datasource": null, + "fieldConfig": { + "defaults": { + "color": { + "mode": "thresholds" + }, + "mappings": [], + "thresholds": { + "mode": "absolute", + "steps": [ + { + "color": "green", + "value": null + }, + { + "color": "red", + "value": 80 + } + ] + } + }, + "overrides": [] + }, + "gridPos": { + "h": 8, + "w": 12, + "x": 6, + "y": 0 + }, + "id": 12, + "options": { + "orientation": "auto", + "reduceOptions": { + "calcs": [ + "lastNotNull" + ], + "fields": "", + "values": false + }, + "showThresholdLabels": false, + "showThresholdMarkers": true, + "text": {} + }, + "pluginVersion": "8.2.1", + "targets": [ + { + "exemplar": true, + "expr": "sum(plex_transcode_sessions_active_count) by (container)", + "interval": "", + "legendFormat": "Plex sessions", + "refId": "A" + }, + { + "exemplar": true, + "expr": "sum(plex_transcode_sessions_active_count) by (container)", + "hide": false, + "interval": "", + "legendFormat": "Transcoding sessions", + "refId": "B" + } + ], + "title": "Current usage", + "type": "gauge" + }, + { + "collapsed": false, + "datasource": null, + "gridPos": { + "h": 1, + "w": 24, + "x": 0, + "y": 8 + }, + "id": 14, + "panels": [], + "title": "Sessions history", + "type": "row" + }, + { + "datasource": null, + "fieldConfig": { + "defaults": { + "color": { + "mode": "palette-classic" + }, + "custom": { + "axisLabel": "", + "axisPlacement": "auto", + "barAlignment": 0, + "drawStyle": "line", + "fillOpacity": 0, + "gradientMode": "none", + "hideFrom": { + "legend": false, + "tooltip": false, + "viz": false + }, + "lineInterpolation": "linear", + "lineWidth": 1, + "pointSize": 5, + "scaleDistribution": { + "type": "linear" + }, + "showPoints": "auto", + "spanNulls": false, + "stacking": { + "group": "A", + "mode": "none" + }, + "thresholdsStyle": { + "mode": "off" + } + }, + "mappings": [], + "thresholds": { + "mode": "absolute", + "steps": [ + { + "color": "green", + "value": null + }, + { + "color": "red", + "value": 80 + } + ] + } + }, + "overrides": [] + }, + "gridPos": { + "h": 8, + "w": 12, + "x": 0, + "y": 9 + }, + "id": 8, + "options": { + "legend": { + "calcs": [], + "displayMode": "list", + "placement": "bottom" + }, + "tooltip": { + "mode": "single" + } + }, + "targets": [ + { + "exemplar": true, + "expr": "sum(plex_transcode_sessions_active_count) by (container)", + "interval": "", + "legendFormat": "Active plex sessions", + "refId": "A" + } + ], + "title": "Active plex sessions", + "type": "timeseries" + }, + { + "datasource": null, + "fieldConfig": { + "defaults": { + "color": { + "mode": "palette-classic" + }, + "custom": { + "axisLabel": "", + "axisPlacement": "auto", + "barAlignment": 0, + "drawStyle": "line", + "fillOpacity": 0, + "gradientMode": "none", + "hideFrom": { + "legend": false, + "tooltip": false, + "viz": false + }, + "lineInterpolation": "linear", + "lineWidth": 1, + "pointSize": 5, + "scaleDistribution": { + "type": "linear" + }, + "showPoints": "auto", + "spanNulls": false, + "stacking": { + "group": "A", + "mode": "none" + }, + "thresholdsStyle": { + "mode": "off" + } + }, + "mappings": [], + "thresholds": { + "mode": "absolute", + "steps": [ + { + "color": "green", + "value": null + }, + { + "color": "red", + "value": 80 + } + ] + } + }, + "overrides": [] + }, + "gridPos": { + "h": 8, + "w": 12, + "x": 12, + "y": 9 + }, + "id": 10, + "options": { + "legend": { + "calcs": [], + "displayMode": "list", + "placement": "bottom" + }, + "tooltip": { + "mode": "single" + } + }, + "targets": [ + { + "exemplar": true, + "expr": "sum(plex_transcode_sessions_active_count) by (container)", + "interval": "", + "legendFormat": "Active transcode sessions", + "refId": "A" + } + ], + "title": "Active transcode sessions", + "type": "timeseries" + }, + { + "collapsed": false, + "datasource": null, + "gridPos": { + "h": 1, + "w": 24, + "x": 0, + "y": 17 + }, + "id": 6, + "panels": [], + "title": "Library content", + "type": "row" + }, + { + "datasource": null, + "description": "", + "fieldConfig": { + "defaults": { + "color": { + "mode": "palette-classic" + }, + "custom": { + "axisLabel": "", + "axisPlacement": "auto", + "barAlignment": 0, + "drawStyle": "line", + "fillOpacity": 0, + "gradientMode": "none", + "hideFrom": { + "legend": false, + "tooltip": false, + "viz": false + }, + "lineInterpolation": "linear", + "lineWidth": 1, + "pointSize": 5, + "scaleDistribution": { + "type": "linear" + }, + "showPoints": "auto", + "spanNulls": false, + "stacking": { + "group": "A", + "mode": "none" + }, + "thresholdsStyle": { + "mode": "off" + } + }, + "mappings": [], + "thresholds": { + "mode": "absolute", + "steps": [ + { + "color": "green", + "value": null + }, + { + "color": "red", + "value": 80 + } + ] + } + }, + "overrides": [] + }, + "gridPos": { + "h": 9, + "w": 12, + "x": 0, + "y": 18 + }, + "id": 4, + "options": { + "legend": { + "calcs": [], + "displayMode": "list", + "placement": "bottom" + }, + "tooltip": { + "mode": "single" + } + }, + "targets": [ + { + "exemplar": true, + "expr": "plex_media_server_library_media_count{type=\"show\"}", + "interval": "", + "legendFormat": "Library \"{{name}}\"", + "refId": "A" + } + ], + "title": "Numbers of TV shows", + "type": "timeseries" + }, + { + "datasource": null, + "description": "", + "fieldConfig": { + "defaults": { + "color": { + "mode": "palette-classic" + }, + "custom": { + "axisLabel": "", + "axisPlacement": "auto", + "barAlignment": 0, + "drawStyle": "line", + "fillOpacity": 0, + "gradientMode": "none", + "hideFrom": { + "legend": false, + "tooltip": false, + "viz": false + }, + "lineInterpolation": "linear", + "lineWidth": 1, + "pointSize": 5, + "scaleDistribution": { + "type": "linear" + }, + "showPoints": "auto", + "spanNulls": false, + "stacking": { + "group": "A", + "mode": "none" + }, + "thresholdsStyle": { + "mode": "off" + } + }, + "mappings": [], + "thresholds": { + "mode": "absolute", + "steps": [ + { + "color": "green", + "value": null + }, + { + "color": "red", + "value": 80 + } + ] + } + }, + "overrides": [] + }, + "gridPos": { + "h": 9, + "w": 12, + "x": 12, + "y": 18 + }, + "id": 2, + "options": { + "legend": { + "calcs": [], + "displayMode": "list", + "placement": "bottom" + }, + "tooltip": { + "mode": "single" + } + }, + "targets": [ + { + "exemplar": true, + "expr": "plex_media_server_library_media_count{type=\"movie\"}", + "interval": "", + "legendFormat": "Library \"{{name}}\"", + "refId": "A" + } + ], + "title": "Numbers of movies", + "type": "timeseries" + } + ], + "schemaVersion": 31, + "style": "dark", + "tags": [], + "templating": { + "list": [] + }, + "time": { + "from": "now-6h", + "to": "now" + }, + "timepicker": {}, + "timezone": "", + "title": "Plex Dashboard", + "uid": null, + "version": 0 + } diff --git a/kubernetes/apps/media/plex-exporter/app/kustomization.yaml b/kubernetes/apps/media/plex-exporter/app/kustomization.yaml new file mode 100755 index 000000000..e7fdf10f9 --- /dev/null +++ b/kubernetes/apps/media/plex-exporter/app/kustomization.yaml @@ -0,0 +1,11 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +namespace: media +resources: + - configmap.yaml + - deployment.yaml + - service.yaml + - service-monitor.yaml + - grafana-dashboard.yaml diff --git a/kubernetes/apps/media/plex-exporter/app/plex-exporter-grafana-dashboard.json b/kubernetes/apps/media/plex-exporter/app/plex-exporter-grafana-dashboard.json new file mode 100755 index 000000000..c7dcb5f10 --- /dev/null +++ b/kubernetes/apps/media/plex-exporter/app/plex-exporter-grafana-dashboard.json @@ -0,0 +1,464 @@ +{ + "annotations": { + "list": [ + { + "builtIn": 1, + "datasource": "-- Grafana --", + "enable": true, + "hide": true, + "iconColor": "rgba(0, 211, 255, 1)", + "name": "Annotations & Alerts", + "target": { + "limit": 100, + "matchAny": false, + "tags": [], + "type": "dashboard" + }, + "type": "dashboard" + } + ] + }, + "editable": true, + "fiscalYearStartMonth": 0, + "gnetId": null, + "graphTooltip": 0, + "id": null, + "links": [], + "liveNow": false, + "panels": [ + { + "datasource": null, + "fieldConfig": { + "defaults": { + "color": { + "mode": "thresholds" + }, + "mappings": [], + "thresholds": { + "mode": "absolute", + "steps": [ + { + "color": "green", + "value": null + }, + { + "color": "red", + "value": 80 + } + ] + } + }, + "overrides": [] + }, + "gridPos": { + "h": 8, + "w": 12, + "x": 6, + "y": 0 + }, + "id": 12, + "options": { + "orientation": "auto", + "reduceOptions": { + "calcs": [ + "lastNotNull" + ], + "fields": "", + "values": false + }, + "showThresholdLabels": false, + "showThresholdMarkers": true, + "text": {} + }, + "pluginVersion": "8.2.1", + "targets": [ + { + "exemplar": true, + "expr": "sum(plex_transcode_sessions_active_count) by (container)", + "interval": "", + "legendFormat": "Plex sessions", + "refId": "A" + }, + { + "exemplar": true, + "expr": "sum(plex_transcode_sessions_active_count) by (container)", + "hide": false, + "interval": "", + "legendFormat": "Transcoding sessions", + "refId": "B" + } + ], + "title": "Current usage", + "type": "gauge" + }, + { + "collapsed": false, + "datasource": null, + "gridPos": { + "h": 1, + "w": 24, + "x": 0, + "y": 8 + }, + "id": 14, + "panels": [], + "title": "Sessions history", + "type": "row" + }, + { + "datasource": null, + "fieldConfig": { + "defaults": { + "color": { + "mode": "palette-classic" + }, + "custom": { + "axisLabel": "", + "axisPlacement": "auto", + "barAlignment": 0, + "drawStyle": "line", + "fillOpacity": 0, + "gradientMode": "none", + "hideFrom": { + "legend": false, + "tooltip": false, + "viz": false + }, + "lineInterpolation": "linear", + "lineWidth": 1, + "pointSize": 5, + "scaleDistribution": { + "type": "linear" + }, + "showPoints": "auto", + "spanNulls": false, + "stacking": { + "group": "A", + "mode": "none" + }, + "thresholdsStyle": { + "mode": "off" + } + }, + "mappings": [], + "thresholds": { + "mode": "absolute", + "steps": [ + { + "color": "green", + "value": null + }, + { + "color": "red", + "value": 80 + } + ] + } + }, + "overrides": [] + }, + "gridPos": { + "h": 8, + "w": 12, + "x": 0, + "y": 9 + }, + "id": 8, + "options": { + "legend": { + "calcs": [], + "displayMode": "list", + "placement": "bottom" + }, + "tooltip": { + "mode": "single" + } + }, + "targets": [ + { + "exemplar": true, + "expr": "sum(plex_transcode_sessions_active_count) by (container)", + "interval": "", + "legendFormat": "Active plex sessions", + "refId": "A" + } + ], + "title": "Active plex sessions", + "type": "timeseries" + }, + { + "datasource": null, + "fieldConfig": { + "defaults": { + "color": { + "mode": "palette-classic" + }, + "custom": { + "axisLabel": "", + "axisPlacement": "auto", + "barAlignment": 0, + "drawStyle": "line", + "fillOpacity": 0, + "gradientMode": "none", + "hideFrom": { + "legend": false, + "tooltip": false, + "viz": false + }, + "lineInterpolation": "linear", + "lineWidth": 1, + "pointSize": 5, + "scaleDistribution": { + "type": "linear" + }, + "showPoints": "auto", + "spanNulls": false, + "stacking": { + "group": "A", + "mode": "none" + }, + "thresholdsStyle": { + "mode": "off" + } + }, + "mappings": [], + "thresholds": { + "mode": "absolute", + "steps": [ + { + "color": "green", + "value": null + }, + { + "color": "red", + "value": 80 + } + ] + } + }, + "overrides": [] + }, + "gridPos": { + "h": 8, + "w": 12, + "x": 12, + "y": 9 + }, + "id": 10, + "options": { + "legend": { + "calcs": [], + "displayMode": "list", + "placement": "bottom" + }, + "tooltip": { + "mode": "single" + } + }, + "targets": [ + { + "exemplar": true, + "expr": "sum(plex_transcode_sessions_active_count) by (container)", + "interval": "", + "legendFormat": "Active transcode sessions", + "refId": "A" + } + ], + "title": "Active transcode sessions", + "type": "timeseries" + }, + { + "collapsed": false, + "datasource": null, + "gridPos": { + "h": 1, + "w": 24, + "x": 0, + "y": 17 + }, + "id": 6, + "panels": [], + "title": "Library content", + "type": "row" + }, + { + "datasource": null, + "description": "", + "fieldConfig": { + "defaults": { + "color": { + "mode": "palette-classic" + }, + "custom": { + "axisLabel": "", + "axisPlacement": "auto", + "barAlignment": 0, + "drawStyle": "line", + "fillOpacity": 0, + "gradientMode": "none", + "hideFrom": { + "legend": false, + "tooltip": false, + "viz": false + }, + "lineInterpolation": "linear", + "lineWidth": 1, + "pointSize": 5, + "scaleDistribution": { + "type": "linear" + }, + "showPoints": "auto", + "spanNulls": false, + "stacking": { + "group": "A", + "mode": "none" + }, + "thresholdsStyle": { + "mode": "off" + } + }, + "mappings": [], + "thresholds": { + "mode": "absolute", + "steps": [ + { + "color": "green", + "value": null + }, + { + "color": "red", + "value": 80 + } + ] + } + }, + "overrides": [] + }, + "gridPos": { + "h": 9, + "w": 12, + "x": 0, + "y": 18 + }, + "id": 4, + "options": { + "legend": { + "calcs": [], + "displayMode": "list", + "placement": "bottom" + }, + "tooltip": { + "mode": "single" + } + }, + "targets": [ + { + "exemplar": true, + "expr": "plex_media_server_library_media_count{type=\"show\"}", + "interval": "", + "legendFormat": "Library \"{{name}}\"", + "refId": "A" + } + ], + "title": "Numbers of TV shows", + "type": "timeseries" + }, + { + "datasource": null, + "description": "", + "fieldConfig": { + "defaults": { + "color": { + "mode": "palette-classic" + }, + "custom": { + "axisLabel": "", + "axisPlacement": "auto", + "barAlignment": 0, + "drawStyle": "line", + "fillOpacity": 0, + "gradientMode": "none", + "hideFrom": { + "legend": false, + "tooltip": false, + "viz": false + }, + "lineInterpolation": "linear", + "lineWidth": 1, + "pointSize": 5, + "scaleDistribution": { + "type": "linear" + }, + "showPoints": "auto", + "spanNulls": false, + "stacking": { + "group": "A", + "mode": "none" + }, + "thresholdsStyle": { + "mode": "off" + } + }, + "mappings": [], + "thresholds": { + "mode": "absolute", + "steps": [ + { + "color": "green", + "value": null + }, + { + "color": "red", + "value": 80 + } + ] + } + }, + "overrides": [] + }, + "gridPos": { + "h": 9, + "w": 12, + "x": 12, + "y": 18 + }, + "id": 2, + "options": { + "legend": { + "calcs": [], + "displayMode": "list", + "placement": "bottom" + }, + "tooltip": { + "mode": "single" + } + }, + "targets": [ + { + "exemplar": true, + "expr": "plex_media_server_library_media_count{type=\"movie\"}", + "interval": "", + "legendFormat": "Library \"{{name}}\"", + "refId": "A" + } + ], + "title": "Numbers of movies", + "type": "timeseries" + } + ], + "schemaVersion": 31, + "style": "dark", + "tags": [], + "templating": { + "list": [] + }, + "time": { + "from": "now-6h", + "to": "now" + }, + "timepicker": {}, + "timezone": "", + "title": "Plex Dashboard", + "uid": null, + "version": 0 +} diff --git a/kubernetes/apps/media/plex-exporter/app/service-monitor.yaml b/kubernetes/apps/media/plex-exporter/app/service-monitor.yaml new file mode 100755 index 000000000..aeb22449d --- /dev/null +++ b/kubernetes/apps/media/plex-exporter/app/service-monitor.yaml @@ -0,0 +1,18 @@ +--- +apiVersion: monitoring.coreos.com/v1 +kind: ServiceMonitor +metadata: + name: prometheus-plex-exporter + labels: + release: prometheus +spec: + jobLabel: plex-exporter + selector: + matchExpressions: + - {key: app, operator: In, values: [plex-exporter]} + namespaceSelector: + matchNames: + - media + endpoints: + - port: metrics + interval: 30s diff --git a/kubernetes/apps/media/plex-exporter/app/service.yaml b/kubernetes/apps/media/plex-exporter/app/service.yaml new file mode 100755 index 000000000..821916b21 --- /dev/null +++ b/kubernetes/apps/media/plex-exporter/app/service.yaml @@ -0,0 +1,16 @@ +--- +apiVersion: v1 +kind: Service +metadata: + labels: + app: plex-exporter + name: plex-exporter-svc +spec: + ports: + - name: metrics + port: 9567 + protocol: TCP + targetPort: 9567 + selector: + app: plex-exporter + type: ClusterIP diff --git a/kubernetes/apps/media/plex-exporter/ks.yaml b/kubernetes/apps/media/plex-exporter/ks.yaml new file mode 100644 index 000000000..6d6ffab67 --- /dev/null +++ b/kubernetes/apps/media/plex-exporter/ks.yaml @@ -0,0 +1,21 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/kustomize.toolkit.fluxcd.io/kustomization_v1.json +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app plex-exporter + namespace: flux-system +spec: + commonMetadata: + labels: + app.kubernetes.io/name: *app + targetNamespace: media + path: ./kubernetes/apps/media/plex-exporter/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/media/plex-trakt-sync/app/config/config.yml b/kubernetes/apps/media/plex-trakt-sync/app/config/config.yml new file mode 100644 index 000000000..07de0ad3b --- /dev/null +++ b/kubernetes/apps/media/plex-trakt-sync/app/config/config.yml @@ -0,0 +1,34 @@ +cache: + path: $PTS_CACHE_DIR/trakt_cache + +excluded-libraries: + - Privat + +config: + dotenv_override: true + +logging: + append: false + debug: false + filename: plextraktsync.log + +sync: + plex_to_trakt: + collection: false + ratings: false + watched_status: true + trakt_to_plex: + liked_lists: false + ratings: false + watched_status: true + watchlist: false + +watch: + add_collection: false + remove_collection: false + scrobble_threshold: 90 + username_filter: true + +xbmc-providers: + movies: imdb + shows: tvdb diff --git a/kubernetes/apps/media/plex-trakt-sync/app/helmrelease.yaml b/kubernetes/apps/media/plex-trakt-sync/app/helmrelease.yaml new file mode 100644 index 000000000..5169ccaca --- /dev/null +++ b/kubernetes/apps/media/plex-trakt-sync/app/helmrelease.yaml @@ -0,0 +1,123 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: plex-trakt-sync + namespace: media +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + controllers: + app: + strategy: Recreate + annotations: + reloader.stakater.com/auto: "true" + pod: + enableServiceLinks: false + securityContext: + runAsUser: 1000 + runAsGroup: 1000 + fsGroup: 1000 + fsGroupChangePolicy: OnRootMismatch + + containers: + main: + image: + repository: ghcr.io/taxel/plextraktsync + tag: 0.30.11 + args: + - watch + env: + PLEX_BASEURL: http://10.20.30.40:32400 + PLEX_LOCALURL: http://10.20.30.40:32400 + PLEX_TOKEN: ${SECRET_PLEXTOKEN} + PLEX_USERNAME: ${SECRET_ACME_EMAIL} + TRAKT_USERNAME: ${SECRET_ACME_EMAIL} + probes: + liveness: + enabled: false + readiness: + enabled: false + startup: + enabled: false + resources: + requests: + cpu: 5m + memory: 101M + limits: + memory: 101M + + cronjob: + type: cronjob + cronjob: + concurrencyPolicy: Forbid + schedule: "@daily" + annotations: + reloader.stakater.com/auto: "true" + + pod: + enableServiceLinks: false + securityContext: + runAsUser: 1000 + runAsGroup: 1000 + fsGroup: 1000 + fsGroupChangePolicy: OnRootMismatch + + containers: + main: + image: + repository: ghcr.io/taxel/plextraktsync + tag: 0.30.11 + args: + - sync + env: + PLEX_BASEURL: http://10.20.30.40:32400 + PLEX_LOCALURL: http://10.20.30.40:32400 + PLEX_TOKEN: ${SECRET_PLEXTOKEN} + PLEX_USERNAME: ${SECRET_ACME_EMAIL} + TRAKT_USERNAME: ${SECRET_ACME_EMAIL} + probes: + liveness: + enabled: false + readiness: + enabled: false + startup: + enabled: false + resources: + requests: + cpu: 5m + memory: 101M + limits: + memory: 101M + + persistence: + config-yaml: + type: configMap + name: plex-tract-sync-configmap + globalMounts: + - path: /app/config/config.yml + subPath: config.yml + readOnly: true + config-pv: + enabled: true + type: persistentVolumeClaim + accessMode: ReadWriteOnce + size: 5Gi + storageClass: ${MAIN_SC} + globalMounts: + - path: /app/config diff --git a/kubernetes/apps/media/plex-trakt-sync/app/kustomization.yaml b/kubernetes/apps/media/plex-trakt-sync/app/kustomization.yaml new file mode 100644 index 000000000..c93f583aa --- /dev/null +++ b/kubernetes/apps/media/plex-trakt-sync/app/kustomization.yaml @@ -0,0 +1,20 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +namespace: media +resources: +- ./helmrelease.yaml +configMapGenerator: +- files: + - ./config/config.yml + name: plex-tract-sync-configmap +generatorOptions: + annotations: + kustomize.toolkit.fluxcd.io/substitute: disabled + disableNameSuffixHash: true +labels: +- includeSelectors: true + pairs: + app.kubernetes.io/instance: plex-trakt-sync + app.kubernetes.io/name: plex-trakt-sync diff --git a/kubernetes/apps/media/plex-trakt-sync/ks.yaml b/kubernetes/apps/media/plex-trakt-sync/ks.yaml new file mode 100644 index 000000000..10077d724 --- /dev/null +++ b/kubernetes/apps/media/plex-trakt-sync/ks.yaml @@ -0,0 +1,22 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/kustomize.toolkit.fluxcd.io/kustomization_v1.json +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app plex-trakt-sync + namespace: flux-system +spec: + commonMetadata: + labels: + app.kubernetes.io/name: *app + targetNamespace: media + dependsOn: + path: ./kubernetes/apps/media/plex-trakt-sync/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/media/podsync/app/config/config.toml b/kubernetes/apps/media/podsync/app/config/config.toml new file mode 100755 index 000000000..8c847e85f --- /dev/null +++ b/kubernetes/apps/media/podsync/app/config/config.toml @@ -0,0 +1,110 @@ +[server] +port = 8080 +hostname = "https://podsync.${SECRET_DOMAIN}" + +[storage] + [storage.local] + data_dir = "/data" + +[database] +badger = { truncate = true, file_io = true } + +[tokens] +youtube = "${SECRET_YOUTUBE_TOKEN}" + +[feeds] + [feeds.DevOpsToolkit] + url = "https://www.youtube.com/playlist?list=UUfz8x0lVzJpb_dgWm9kPVrw" + update_period = "8h" + format = "video" + quality = "high" + page_size = 15 + clean = { keep_last = 15 } + + [feeds.TechWorldWithNana] + url = "https://www.youtube.com/channel/UCdngmbVKX1Tgre699-XLlUA" + update_period = "8h" + format = "video" + quality = "high" + page_size = 15 + clean = { keep_last = 15 } + + [feeds.bares] + url = "https://www.youtube.com/channel/UC53bIpnef1pwAx69ERmmOLA" + update_period = "8h" + format = "video" + quality = "high" + page_size = 10 + clean = { keep_last = 10 } + + [feeds.headlock_breaking] + url = "https://www.youtube.com/channel/UC4A1tkY5mw9MWYa9SnDi3CQ" + filters = { title = "(B|b)(R|r)(E|e)(A|a)(K|k)(I|i)(N|n)(G|g)" } + custom = { title = "Headlock Breaking News" } + update_period = "6h" + format = "audio" + quality = "high" + page_size = 5 + clean = { keep_last = 5 } + + [feeds.lffs] + url = "https://www.youtube.com/playlist?list=PLDLU7Rp1Fecmx3mjQJU97rn5gfV8NH8AW" + update_period = "9h" + format = "video" + quality = "high" + page_size = 5 + clean = { keep_last = 5 } + + [feeds.mytowatch] + url = "https://youtube.com/playlist?list=PL7qBQ0Mi2xAp-alNW5mJ7z4X9Zko9rpWJ" + update_period = "7h" + format = "video" + quality = "high" + page_size = 30 + clean = { keep_last = 30 } + + [feeds.oralsessions] + url = "https://www.youtube.com/playlist?list=PLquP20HDxBb19HgiRawKoiTkHtHT473qG" + custom = { title = "The Sessions x AEW" } + update_period = "12h" + format = "video" + quality = "high" + page_size = 5 + clean = { keep_last = 5 } + + [feeds.spotfight_others] + url = "https://www.youtube.com/channel/UCROVkXXxpp_wisE7YyrTYyQ" + filters = { not_title = "(HAUPTKAMPF|Review)" } + custom = { title = "Spotfight Alles Andere" } + update_period = "12h" + format = "video" + quality = "high" + page_size = 15 + clean = { keep_last = 5 } + + [feeds.spotfightnews] + url = "https://www.youtube.com/channel/UCdsHMu1VHhZ8SlrdUQa457w" + update_period = "1h" + format = "audio" + quality = "high" + page_size = 13 + clean = { keep_last = 13 } + + [feeds.yt_fotografieren] + url = "https://www.youtube.com/playlist?list=PL7qBQ0Mi2xApoNGSCObcehoOnw9S2YTpc" + update_period = "7h" + format = "video" + quality = "high" + page_size = 30 + clean = { keep_last = 30 } + + [feeds.yt_kubernetes] + url = "https://www.youtube.com/playlist?list=PL7qBQ0Mi2xApcBPl9Ve3RVBD6CgQKaDY4" + update_period = "5h" + format = "video" + quality = "high" + page_size = 30 + clean = { keep_last = 30 } + +[downloader] +self_update = true diff --git a/kubernetes/apps/media/podsync/app/helmrelease.yaml b/kubernetes/apps/media/podsync/app/helmrelease.yaml new file mode 100644 index 000000000..0875634b1 --- /dev/null +++ b/kubernetes/apps/media/podsync/app/helmrelease.yaml @@ -0,0 +1,102 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: &app podsync +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + global: + nameOverride: *app + controllers: + app: + strategy: Recreate + annotations: + reloader.stakater.com/auto: "true" + containers: + main: + image: + repository: registry.eighty-three.me/tuxpeople/podsync + tag: v2.7.0 + env: + TZ: ${TIMEZONE} + resources: + requests: + cpu: 5m + memory: 60Mi + limits: + memory: 500Mi + probes: + liveness: + enabled: true + custom: true + spec: + httpGet: + path: / + port: &port 8080 + readiness: + enabled: true + custom: true + spec: + httpGet: + path: / + port: *port + startup: + enabled: true + custom: true + spec: + httpGet: + path: / + port: *port + # defaultPodOptions: + # securityContext: + # runAsUser: 1026 + # runAsGroup: 100 + service: + app: + ports: + http: + port: *port + ingress: + app: + enabled: true + ingressClassName: internal + hosts: + - host: &host podsync.${SECRET_DOMAIN} + paths: + - path: / + pathType: Prefix + service: + identifier: app + port: *port + tls: + - hosts: + - ${SECRET_DOMAIN/./-}-production-tls + persistence: + config-toml: + type: configMap + name: podsync-configmap + globalMounts: + - path: /app/config.toml + subPath: config.toml + readOnly: true + data: + enabled: true + type: nfs + server: 10.20.30.40 + path: /volume2/data/media/podcasts diff --git a/kubernetes/apps/media/podsync/app/kustomization.yaml b/kubernetes/apps/media/podsync/app/kustomization.yaml new file mode 100644 index 000000000..2d1c823d7 --- /dev/null +++ b/kubernetes/apps/media/podsync/app/kustomization.yaml @@ -0,0 +1,12 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml +configMapGenerator: + - name: podsync-configmap + files: + - ./config/config.toml +generatorOptions: + disableNameSuffixHash: true diff --git a/kubernetes/apps/media/podsync/ks.dis b/kubernetes/apps/media/podsync/ks.dis new file mode 100644 index 000000000..86af7a447 --- /dev/null +++ b/kubernetes/apps/media/podsync/ks.dis @@ -0,0 +1,21 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/kustomize.toolkit.fluxcd.io/kustomization_v1.json +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app podsync + namespace: flux-system +spec: + commonMetadata: + labels: + app.kubernetes.io/name: *app + targetNamespace: media + path: ./kubernetes/apps/media/podsync/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false # no flux ks dependents + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/media/readarr/app/externalsecret.yaml b/kubernetes/apps/media/readarr/app/externalsecret.yaml new file mode 100644 index 000000000..93d765677 --- /dev/null +++ b/kubernetes/apps/media/readarr/app/externalsecret.yaml @@ -0,0 +1,19 @@ +--- +apiVersion: external-secrets.io/v1beta1 +kind: ExternalSecret +metadata: + name: readarr +spec: + secretStoreRef: + kind: ClusterSecretStore + name: onepassword + target: + name: readarr-secret + creationPolicy: Owner + template: + engineVersion: v2 + data: + READARR__API_KEY: "{{ .READARR_API_KEY }}" + dataFrom: + - extract: + key: arr-apis diff --git a/kubernetes/apps/media/readarr/app/helmrelease.yaml b/kubernetes/apps/media/readarr/app/helmrelease.yaml new file mode 100644 index 000000000..8c8d2711f --- /dev/null +++ b/kubernetes/apps/media/readarr/app/helmrelease.yaml @@ -0,0 +1,118 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: &app readarr +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + controllers: + readarr: + annotations: + reloader.stakater.com/auto: "true" + containers: + app: + image: + repository: ghcr.io/onedr0p/readarr-develop + tag: 0.3.28.2554@sha256:4beda7d63d2cb014a860bf4f8fa367f9621e378675396b684d300f1e3a0380dc + env: + READARR__AUTHENTICATION_METHOD: External + READARR__AUTHENTICATION_REQUIRED: DisabledForLocalAddresses + READARR__INSTANCE_NAME: Readarr + READARR__APPLICATION_URL: "https://{{ .Release.Name }}.${SECRET_DOMAIN}" + READARR__LOG_LEVEL: info + READARR__PORT: &port 8787 + READARR__THEME: dark + TZ: ${TIMEZONE} + envFrom: &envFrom + - secretRef: + name: readarr-secret + probes: + liveness: &probes + enabled: true + custom: true + spec: + httpGet: + path: /ping + port: *port + initialDelaySeconds: 0 + periodSeconds: 10 + timeoutSeconds: 1 + failureThreshold: 3 + readiness: *probes + resources: + requests: + cpu: 10m + limits: + memory: 1Gi + securityContext: + allowPrivilegeEscalation: false + readOnlyRootFilesystem: true + capabilities: + drop: + - ALL + defaultPodOptions: + securityContext: + runAsNonRoot: true + runAsUser: 1027 + runAsGroup: 100 + fsGroup: 100 + fsGroupChangePolicy: OnRootMismatch + supplementalGroups: + - 65539 + ingress: + app: + className: internal + annotations: + hajimari.io/icon: mdi:filmstrip + hosts: + - host: &host "{{ .Release.Name }}.${SECRET_DOMAIN}" + paths: + - path: / + service: + identifier: app + port: http + tls: + - hosts: + - *host + persistence: + config: + enabled: true + type: persistentVolumeClaim + accessMode: ReadWriteOnce + size: 20Gi + storageClass: ${MAIN_SC} + logs: + type: emptyDir + globalMounts: + - path: /config/logs + data: + enabled: true + type: nfs + server: 10.20.30.40 + globalMounts: + - path: /data/media + path: /volume2/data/media + tmp: + type: emptyDir + service: + app: + controller: *app + ports: + http: + port: *port diff --git a/kubernetes/apps/media/readarr/app/kustomization.yaml b/kubernetes/apps/media/readarr/app/kustomization.yaml new file mode 100644 index 000000000..2708f09ee --- /dev/null +++ b/kubernetes/apps/media/readarr/app/kustomization.yaml @@ -0,0 +1,6 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./externalsecret.yaml + - ./helmrelease.yaml diff --git a/kubernetes/apps/media/readarr/ks.yaml b/kubernetes/apps/media/readarr/ks.yaml new file mode 100644 index 000000000..b3635dac7 --- /dev/null +++ b/kubernetes/apps/media/readarr/ks.yaml @@ -0,0 +1,21 @@ +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app readarr + namespace: flux-system +spec: + commonMetadata: + labels: + app.kubernetes.io/name: *app + dependsOn: + - name: external-secrets-secretstores + targetNamespace: media + path: ./kubernetes/apps/media/readarr/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/media/tautulli/app/helmrelease.yaml b/kubernetes/apps/media/tautulli/app/helmrelease.yaml new file mode 100644 index 000000000..d2f9e6591 --- /dev/null +++ b/kubernetes/apps/media/tautulli/app/helmrelease.yaml @@ -0,0 +1,108 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: tautulli + namespace: media +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + controllers: + app: + annotations: + reloader.stakater.com/auto: "true" + containers: + main: + image: + repository: ghcr.io/onedr0p/tautulli + tag: 2.13.4@sha256:633a57b2f8634feb67811064ec3fa52f40a70641be927fdfda6f5d91ebbd5d73 + env: + TZ: ${TIMEZONE} + probes: + liveness: &probes + enabled: true + custom: true + spec: + httpGet: + path: &path /status + port: &port 8181 + initialDelaySeconds: 0 + periodSeconds: 10 + timeoutSeconds: 1 + failureThreshold: 3 + readiness: *probes + startup: + enabled: false + resources: + requests: + cpu: 100m + memory: 128Mi + limits: + memory: 512Mi + jbops: + image: + repository: registry.k8s.io/git-sync/git-sync + tag: v4.2.3 + env: + GITSYNC_REPO: https://github.com/blacktwin/JBOPS + GITSYNC_REF: master + GITSYNC_PERIOD: 24h + GITSYNC_ROOT: /add-ons + resources: + requests: + cpu: 10m + memory: 10M + limits: + memory: 128M + pod: + securityContext: + runAsUser: 568 + runAsGroup: 568 + fsGroup: 568 + fsGroupChangePolicy: OnRootMismatch + service: + app: + controller: app + ports: + http: + port: *port + ingress: + app: + enabled: true + className: internal + annotations: + gatus.io/path: *path + hosts: + - host: &host "{{ .Release.Name }}.${SECRET_DOMAIN}" + paths: + - path: / + service: + identifier: app + port: *port + tls: + - hosts: + - *host + persistence: + config: + enabled: true + type: persistentVolumeClaim + accessMode: ReadWriteOnce + size: 5Gi + storageClass: ${MAIN_SC} + add-ons: + type: emptyDir diff --git a/kubernetes/apps/media/tautulli/app/kustomization.yaml b/kubernetes/apps/media/tautulli/app/kustomization.yaml new file mode 100644 index 000000000..94f7a6174 --- /dev/null +++ b/kubernetes/apps/media/tautulli/app/kustomization.yaml @@ -0,0 +1,7 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +namespace: media +resources: + - ./helmrelease.yaml diff --git a/kubernetes/apps/media/tautulli/exporter/helmrelease.yaml b/kubernetes/apps/media/tautulli/exporter/helmrelease.yaml new file mode 100644 index 000000000..d66caae36 --- /dev/null +++ b/kubernetes/apps/media/tautulli/exporter/helmrelease.yaml @@ -0,0 +1,68 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: tautulli-exporter +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + controllers: + app: + annotations: + reloader.stakater.com/auto: "true" + containers: + main: + image: + repository: registry.eighty-three.me/tuxpeople/tautulli-exporter + tag: 0.1.0 + env: + SERVE_PORT: &port 9487 + TAUTULLI_URI: ${SECRET_TAUTULLI_URL} + TAUTULLI_API_KEY: ${SECRET_TAUTULLI_API_KEY} + resources: + requests: + cpu: 5m + memory: 36M + limits: + memory: 128M + securityContext: + allowPrivilegeEscalation: false + readOnlyRootFilesystem: true + capabilities: + drop: + - ALL + pod: + securityContext: + runAsUser: 568 + runAsGroup: 568 + runAsNonRoot: true + service: + app: + controller: app + ports: + http: + port: *port + serviceMonitor: + main: + serviceName: main + endpoints: + - port: metrics + scheme: http + path: /metrics + interval: 1m + scrapeTimeout: 10s diff --git a/kubernetes/apps/media/tautulli/exporter/kustomization.yaml b/kubernetes/apps/media/tautulli/exporter/kustomization.yaml new file mode 100644 index 000000000..94f7a6174 --- /dev/null +++ b/kubernetes/apps/media/tautulli/exporter/kustomization.yaml @@ -0,0 +1,7 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +namespace: media +resources: + - ./helmrelease.yaml diff --git a/kubernetes/apps/media/tautulli/ks.yaml b/kubernetes/apps/media/tautulli/ks.yaml new file mode 100644 index 000000000..1f5188745 --- /dev/null +++ b/kubernetes/apps/media/tautulli/ks.yaml @@ -0,0 +1,44 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/kustomize.toolkit.fluxcd.io/kustomization_v1.json +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app tautulli + namespace: flux-system +spec: + commonMetadata: + labels: + app.kubernetes.io/name: *app + targetNamespace: media + path: ./kubernetes/apps/media/tautulli/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m +# --- +# # yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/kustomize.toolkit.fluxcd.io/kustomization_v1.json +# apiVersion: kustomize.toolkit.fluxcd.io/v1 +# kind: Kustomization +# metadata: +# name: &app tautulli-exporter +# namespace: flux-system +# spec: +# commonMetadata: +# labels: +# app.kubernetes.io/name: *app +# targetNamespace: media +# dependsOn: +# - name: tautulli +# path: ./kubernetes/apps/media/tautulli/exporter +# prune: true +# sourceRef: +# kind: GitRepository +# name: k8s-homelab +# wait: true +# interval: 30m +# retryInterval: 1m +# timeout: 5m diff --git a/kubernetes/apps/network/cloudflared/app/configs/config.yaml b/kubernetes/apps/network/cloudflared/app/configs/config.yaml new file mode 100644 index 000000000..05bcef5cf --- /dev/null +++ b/kubernetes/apps/network/cloudflared/app/configs/config.yaml @@ -0,0 +1,10 @@ +--- +originRequest: + originServerName: "external.${SECRET_DOMAIN}" + +ingress: + - hostname: "${SECRET_DOMAIN}" + service: https://ingress-nginx-external-controller.network.svc.cluster.local:443 + - hostname: "*.${SECRET_DOMAIN}" + service: https://ingress-nginx-external-controller.network.svc.cluster.local:443 + - service: http_status:404 diff --git a/kubernetes/apps/network/cloudflared/app/dnsendpoint.yaml b/kubernetes/apps/network/cloudflared/app/dnsendpoint.yaml new file mode 100644 index 000000000..43d7d7b29 --- /dev/null +++ b/kubernetes/apps/network/cloudflared/app/dnsendpoint.yaml @@ -0,0 +1,10 @@ +--- +apiVersion: externaldns.k8s.io/v1alpha1 +kind: DNSEndpoint +metadata: + name: cloudflared +spec: + endpoints: + - dnsName: "external.${SECRET_DOMAIN}" + recordType: CNAME + targets: ["${SECRET_CLOUDFLARE_TUNNEL_ID}.cfargotunnel.com"] diff --git a/kubernetes/apps/network/cloudflared/app/helmrelease.yaml b/kubernetes/apps/network/cloudflared/app/helmrelease.yaml new file mode 100644 index 000000000..50c0c5c31 --- /dev/null +++ b/kubernetes/apps/network/cloudflared/app/helmrelease.yaml @@ -0,0 +1,109 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: cloudflared +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + controllers: + cloudflared: + strategy: RollingUpdate + annotations: + reloader.stakater.com/auto: "true" + containers: + app: + image: + repository: docker.io/cloudflare/cloudflared + tag: 2024.6.0 + env: + NO_AUTOUPDATE: true + TUNNEL_CRED_FILE: /etc/cloudflared/creds/credentials.json + TUNNEL_METRICS: 0.0.0.0:8080 + TUNNEL_ORIGIN_ENABLE_HTTP2: true + TUNNEL_TRANSPORT_PROTOCOL: quic + TUNNEL_POST_QUANTUM: true + TUNNEL_ID: + valueFrom: + secretKeyRef: + name: cloudflared-secret + key: TUNNEL_ID + args: + - tunnel + - --config + - /etc/cloudflared/config/config.yaml + - run + - "$(TUNNEL_ID)" + probes: + liveness: &probes + enabled: true + custom: true + spec: + httpGet: + path: /ready + port: &port 8080 + initialDelaySeconds: 0 + periodSeconds: 10 + timeoutSeconds: 1 + failureThreshold: 3 + readiness: *probes + securityContext: + allowPrivilegeEscalation: false + readOnlyRootFilesystem: true + capabilities: { drop: ["ALL"] } + resources: + requests: + cpu: 10m + limits: + memory: 256Mi + defaultPodOptions: + securityContext: + runAsNonRoot: true + runAsUser: 65534 + runAsGroup: 65534 + seccompProfile: { type: RuntimeDefault } + service: + app: + controller: cloudflared + ports: + http: + port: *port + serviceMonitor: + app: + serviceName: cloudflared + endpoints: + - port: http + scheme: http + path: /metrics + interval: 1m + scrapeTimeout: 10s + persistence: + config: + type: configMap + name: cloudflared-configmap + globalMounts: + - path: /etc/cloudflared/config/config.yaml + subPath: config.yaml + readOnly: true + creds: + type: secret + name: cloudflared-secret + globalMounts: + - path: /etc/cloudflared/creds/credentials.json + subPath: credentials.json + readOnly: true diff --git a/kubernetes/apps/network/cloudflared/app/kustomization.yaml b/kubernetes/apps/network/cloudflared/app/kustomization.yaml new file mode 100644 index 000000000..891a864ad --- /dev/null +++ b/kubernetes/apps/network/cloudflared/app/kustomization.yaml @@ -0,0 +1,13 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./dnsendpoint.yaml + - ./secret.sops.yaml + - ./helmrelease.yaml +configMapGenerator: + - name: cloudflared-configmap + files: + - ./configs/config.yaml +generatorOptions: + disableNameSuffixHash: true diff --git a/kubernetes/apps/network/cloudflared/app/secret.sops.yaml b/kubernetes/apps/network/cloudflared/app/secret.sops.yaml new file mode 100644 index 000000000..0d0e3b9ae --- /dev/null +++ b/kubernetes/apps/network/cloudflared/app/secret.sops.yaml @@ -0,0 +1,27 @@ +apiVersion: v1 +kind: Secret +metadata: + name: cloudflared-secret +stringData: + TUNNEL_ID: ENC[AES256_GCM,data:4dguhd3VxFV83/W/lGuYraNlGgE9ev0JJAUknqqn42q2GsH7,iv:xi1ZljYkIebk8OjoZh3R7CrKtoZp5BdF5EwxOCRuaKU=,tag:u/wt3SKaZ/Jx9FkktA2+Ig==,type:str] + credentials.json: ENC[AES256_GCM,data:T3Cais2bI6iNyk+6OopjOhbZPLBBHoZBup6FaGMZuDA4KDRUvhunuCeTKyFh59ajl/Zh8LXOSrpqTnOLTjhqxyxp7QOy6g/zAQbDO732BmOYnDlAl3TT2pWbiEpzaSIr/Hy9K6sbpolaSld8SSvV7I/kNSgJGC5OSEzDdBfOymxp46NUD1S4Ut1RxoruehNv9ljKOR10g/NpMcyUhG6LUbCfnDCJL1jvyqd+3gtvCg==,iv:WdHtanSc7C37LqfMfHVUJFR/zxNFbVTRX4GVzcWHkJo=,tag:7tFfI2YjLjhXq+MFrLtlAw==,type:str] +sops: + kms: [] + gcp_kms: [] + azure_kv: [] + hc_vault: [] + age: + - recipient: age1y0kzuf0tn94a74whazwae4r9qal4snuqfuhl5jacscrpr7up5gts74fe5w + enc: | + -----BEGIN AGE ENCRYPTED FILE----- + YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSA4MU9WVW1tTFlac25WcXpT + c21uaFl1V2xUZDcrcEltTnNDUmIzVUJlU2hjCmREeVg4aEtPZmZKa2wwTlB0VVF6 + MXRvVVA3SFdzL0F6RVFXUk5jMVlSYkUKLS0tIFlDL0UxdkgwUWVnbmJyWVczSm54 + aVNDVWl5dXRWZ1JWdHlJQ2E5ckdXTHMK3IijAW6UUQVpvzJcW82AK0cSMx3A6d59 + JB3x4/D0zeWbGi3bS42Hb3J3CLs758hbmXl2B2b7+6kHGHhBBMlmnw== + -----END AGE ENCRYPTED FILE----- + lastmodified: "2024-06-06T09:08:40Z" + mac: ENC[AES256_GCM,data:mdw8exiya2PPcn0n14nglurnSu1FZ73K1KU0fGDDMJ+kvxlF23XY+rcDQQHn0WK+gjw6ULOE0H5e4D0bKONknWNAQHRWNSFASjLBIYTXvIx8CcS/0HAnNSNlxEcwcuZ/7pIB1cgLjTCfRTo3WG3lOSUreDqkta813QaNIv9LjiY=,iv:tl8xxZAIUB1kEZpBKyn+b6q+RVTU5TMXBWrfGd7cex0=,tag:csp3ngNow87AzCGf4mC/4Q==,type:str] + pgp: [] + encrypted_regex: ^(data|stringData)$ + version: 3.8.1 diff --git a/kubernetes/apps/network/cloudflared/ks.yaml b/kubernetes/apps/network/cloudflared/ks.yaml new file mode 100644 index 000000000..da98a0f78 --- /dev/null +++ b/kubernetes/apps/network/cloudflared/ks.yaml @@ -0,0 +1,22 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app cloudflared + namespace: flux-system +spec: + targetNamespace: network + commonMetadata: + labels: + app.kubernetes.io/name: *app + dependsOn: + - name: external-dns + path: ./kubernetes/apps/network/cloudflared/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/network/echo-server/app/helmrelease.yaml b/kubernetes/apps/network/echo-server/app/helmrelease.yaml new file mode 100644 index 000000000..c373ef0e1 --- /dev/null +++ b/kubernetes/apps/network/echo-server/app/helmrelease.yaml @@ -0,0 +1,91 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: echo-server +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + controllers: + echo-server: + strategy: RollingUpdate + containers: + app: + image: + repository: ghcr.io/mendhak/http-https-echo + tag: 33 + env: + HTTP_PORT: &port 8080 + LOG_WITHOUT_NEWLINE: true + LOG_IGNORE_PATH: /healthz + PROMETHEUS_ENABLED: true + probes: + liveness: &probes + enabled: true + custom: true + spec: + httpGet: + path: &paths /healthz + port: *port + initialDelaySeconds: 0 + periodSeconds: 10 + timeoutSeconds: 1 + failureThreshold: 3 + readiness: *probes + resources: + requests: + cpu: 10m + limits: + memory: 64Mi + securityContext: + allowPrivilegeEscalation: false + readOnlyRootFilesystem: true + capabilities: { drop: ["ALL"] } + defaultPodOptions: + securityContext: + runAsNonRoot: true + runAsUser: 65534 + runAsGroup: 65534 + seccompProfile: { type: RuntimeDefault } + service: + app: + controller: echo-server + ports: + http: + port: *port + serviceMonitor: + app: + serviceName: echo-server + endpoints: + - port: http + scheme: http + path: /metrics + interval: 1m + scrapeTimeout: 10s + ingress: + app: + className: external + annotations: + gatus.io/path: *paths + hosts: + - host: "{{ .Release.Name }}.${SECRET_DOMAIN}" + paths: + - path: / + service: + identifier: app + port: http diff --git a/kubernetes/apps/network/echo-server/app/kustomization.yaml b/kubernetes/apps/network/echo-server/app/kustomization.yaml new file mode 100644 index 000000000..5dd7baca7 --- /dev/null +++ b/kubernetes/apps/network/echo-server/app/kustomization.yaml @@ -0,0 +1,5 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml diff --git a/kubernetes/apps/network/echo-server/ks.yaml b/kubernetes/apps/network/echo-server/ks.yaml new file mode 100644 index 000000000..73aef89b6 --- /dev/null +++ b/kubernetes/apps/network/echo-server/ks.yaml @@ -0,0 +1,20 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app echo-server + namespace: flux-system +spec: + targetNamespace: network + commonMetadata: + labels: + app.kubernetes.io/name: *app + path: ./kubernetes/apps/network/echo-server/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/network/external-dns/app/helmrelease.yaml b/kubernetes/apps/network/external-dns/app/helmrelease.yaml new file mode 100644 index 000000000..3575fa45f --- /dev/null +++ b/kubernetes/apps/network/external-dns/app/helmrelease.yaml @@ -0,0 +1,48 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: &app external-dns +spec: + interval: 30m + chart: + spec: + chart: external-dns + version: 1.14.5 + sourceRef: + kind: HelmRepository + name: external-dns + namespace: flux-system + install: + crds: CreateReplace + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + crds: CreateReplace + remediation: + strategy: rollback + retries: 3 + values: + fullnameOverride: *app + provider: cloudflare + env: + - name: CF_API_TOKEN + valueFrom: + secretKeyRef: + name: external-dns-secret + key: api-token + extraArgs: + - --ingress-class=external + - --cloudflare-proxied + - --crd-source-apiversion=externaldns.k8s.io/v1alpha1 + - --crd-source-kind=DNSEndpoint + policy: sync + sources: ["crd", "ingress"] + txtPrefix: k8s. + txtOwnerId: default + domainFilters: ["${SECRET_DOMAIN}", "${SECRET_CH_DOMAIN}"] + serviceMonitor: + enabled: true + podAnnotations: + secret.reloader.stakater.com/reload: external-dns-secret diff --git a/kubernetes/apps/network/external-dns/app/kustomization.yaml b/kubernetes/apps/network/external-dns/app/kustomization.yaml new file mode 100644 index 000000000..95bf4747f --- /dev/null +++ b/kubernetes/apps/network/external-dns/app/kustomization.yaml @@ -0,0 +1,6 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./secret.sops.yaml + - ./helmrelease.yaml diff --git a/kubernetes/apps/network/external-dns/app/secret.sops.yaml b/kubernetes/apps/network/external-dns/app/secret.sops.yaml new file mode 100644 index 000000000..721282eff --- /dev/null +++ b/kubernetes/apps/network/external-dns/app/secret.sops.yaml @@ -0,0 +1,26 @@ +apiVersion: v1 +kind: Secret +metadata: + name: external-dns-secret +stringData: + api-token: ENC[AES256_GCM,data:dOW/EpSJzQCQ9r7dyTTWS+ulMvS9yHVsLo3eqoMo1iYkBJDcrfNHIQ==,iv:Vnh9K/P8niziwU4mIizBYttlCwasu0QKWz5kz+vLW2o=,tag:EtSmZvGRGNEEX9es87m6ZQ==,type:str] +sops: + kms: [] + gcp_kms: [] + azure_kv: [] + hc_vault: [] + age: + - recipient: age1y0kzuf0tn94a74whazwae4r9qal4snuqfuhl5jacscrpr7up5gts74fe5w + enc: | + -----BEGIN AGE ENCRYPTED FILE----- + YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBCU0Z6andZejNHSUZNNzVj + QzRjdTZvYUZ3QnZ1VWJkV0hTbXpHQkMrYlhrCmNHaVF3UXRpNGlMejFUbUp6c3Fj + WlMrbGZhOGtvVjlRbHFDY1JCMFR0MXcKLS0tIDY4akk4T2UvNitwZjBaQUZVQ25v + UzZ3WURLVlhRTzZXUmlQd3dBcnJPVk0KEfG2v02pW0yDEUUKp1jNlQzH9g5EC2wj + HAC/ig576UDuId4RTASDV3Lc0Re9neS5FN7zBm6EDI7fADgBYOm5jw== + -----END AGE ENCRYPTED FILE----- + lastmodified: "2024-06-06T09:08:40Z" + mac: ENC[AES256_GCM,data:5g+ctCbMNQbIe4o2t11KQXjShV0rdhTXUyZzp7sL0aYAbRrJSp9Iit9iogbc7ulTxgPpiFeKLrzNqHEeIsadSGAv0JkfHGIujAP+VYGMWFbe+Mq4jXnmZKtJIVmox5bMYveH5g7+fL9mUgxY6HiG4B3zl0w/SrR3npncm6aKHO4=,iv:T0YNXrBKtu+ETIkkQTNyZXzy/3j1priid0yAT4crYOg=,tag:5VvvR36r25DB0YBhKQqaQw==,type:str] + pgp: [] + encrypted_regex: ^(data|stringData)$ + version: 3.8.1 diff --git a/kubernetes/apps/network/external-dns/ks.yaml b/kubernetes/apps/network/external-dns/ks.yaml new file mode 100644 index 000000000..56b8ed00d --- /dev/null +++ b/kubernetes/apps/network/external-dns/ks.yaml @@ -0,0 +1,20 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app external-dns + namespace: flux-system +spec: + targetNamespace: network + commonMetadata: + labels: + app.kubernetes.io/name: *app + path: ./kubernetes/apps/network/external-dns/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/network/ingress-nginx/certificates/kustomization.yaml b/kubernetes/apps/network/ingress-nginx/certificates/kustomization.yaml new file mode 100644 index 000000000..76a6679e1 --- /dev/null +++ b/kubernetes/apps/network/ingress-nginx/certificates/kustomization.yaml @@ -0,0 +1,6 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + # - ./staging.yaml + - ./production.yaml diff --git a/kubernetes/apps/network/ingress-nginx/certificates/production.yaml b/kubernetes/apps/network/ingress-nginx/certificates/production.yaml new file mode 100644 index 000000000..b3f8a370a --- /dev/null +++ b/kubernetes/apps/network/ingress-nginx/certificates/production.yaml @@ -0,0 +1,34 @@ +--- +apiVersion: cert-manager.io/v1 +kind: Certificate +metadata: + name: "${SECRET_DOMAIN/./-}-production" +spec: + secretName: "${SECRET_DOMAIN/./-}-production-tls" + issuerRef: + name: letsencrypt-production + kind: ClusterIssuer + secretTemplate: + annotations: + replicator.v1.mittwald.de/replicate-to: ".*" + commonName: "${SECRET_DOMAIN}" + dnsNames: + - "${SECRET_DOMAIN}" + - "*.${SECRET_DOMAIN}" +--- +apiVersion: cert-manager.io/v1 +kind: Certificate +metadata: + name: "${SECRET_CH_DOMAIN/./-}-production" +spec: + secretName: "${SECRET_CH_DOMAIN/./-}-production-tls" + issuerRef: + name: letsencrypt-production + kind: ClusterIssuer + secretTemplate: + annotations: + replicator.v1.mittwald.de/replicate-to: ".*" + commonName: "${SECRET_CH_DOMAIN}" + dnsNames: + - "${SECRET_CH_DOMAIN}" + - "*.${SECRET_CH_DOMAIN}" diff --git a/kubernetes/apps/network/ingress-nginx/certificates/staging.yaml b/kubernetes/apps/network/ingress-nginx/certificates/staging.yaml new file mode 100644 index 000000000..688353000 --- /dev/null +++ b/kubernetes/apps/network/ingress-nginx/certificates/staging.yaml @@ -0,0 +1,34 @@ +--- +apiVersion: cert-manager.io/v1 +kind: Certificate +metadata: + name: "${SECRET_DOMAIN/./-}-staging" +spec: + secretName: "${SECRET_DOMAIN/./-}-staging-tls" + issuerRef: + name: letsencrypt-staging + kind: ClusterIssuer + secretTemplate: + annotations: + replicator.v1.mittwald.de/replicate-to: ".*" + commonName: "${SECRET_DOMAIN}" + dnsNames: + - "${SECRET_DOMAIN}" + - "*.${SECRET_DOMAIN}" +--- +apiVersion: cert-manager.io/v1 +kind: Certificate +metadata: + name: "${SECRET_CH_DOMAIN/./-}-staging" +spec: + secretName: "${SECRET_CH_DOMAIN/./-}-staging-tls" + issuerRef: + name: letsencrypt-staging + kind: ClusterIssuer + secretTemplate: + annotations: + replicator.v1.mittwald.de/replicate-to: ".*" + commonName: "${SECRET_CH_DOMAIN}" + dnsNames: + - "${SECRET_CH_DOMAIN}" + - "*.${SECRET_CH_DOMAIN}" diff --git a/kubernetes/apps/network/ingress-nginx/external/helmrelease.yaml b/kubernetes/apps/network/ingress-nginx/external/helmrelease.yaml new file mode 100644 index 000000000..3565765a0 --- /dev/null +++ b/kubernetes/apps/network/ingress-nginx/external/helmrelease.yaml @@ -0,0 +1,75 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: ingress-nginx-external +spec: + interval: 30m + chart: + spec: + chart: ingress-nginx + version: 4.10.1 + sourceRef: + kind: HelmRepository + name: ingress-nginx + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + dependsOn: + - name: cloudflared + namespace: network + values: + fullnameOverride: ingress-nginx-external + controller: + service: + annotations: + external-dns.alpha.kubernetes.io/hostname: "external.${SECRET_DOMAIN}" + io.cilium/lb-ipam-ips: "192.168.13.64" + externalTrafficPolicy: Cluster + ingressClassResource: + name: external + default: false + controllerValue: k8s.io/external + admissionWebhooks: + objectSelector: + matchExpressions: + - key: ingress-class + operator: In + values: ["external"] + config: + client-body-buffer-size: 100M + client-body-timeout: 120 + client-header-timeout: 120 + enable-brotli: "true" + enable-real-ip: "true" + hsts-max-age: 31449600 + keep-alive-requests: 10000 + keep-alive: 120 + log-format-escape-json: "true" + log-format-upstream: > + {"time": "$time_iso8601", "remote_addr": "$proxy_protocol_addr", "x_forwarded_for": "$proxy_add_x_forwarded_for", + "request_id": "$req_id", "remote_user": "$remote_user", "bytes_sent": $bytes_sent, "request_time": $request_time, + "status": $status, "vhost": "$host", "request_proto": "$server_protocol", "path": "$uri", "request_query": "$args", + "request_length": $request_length, "duration": $request_time, "method": "$request_method", "http_referrer": "$http_referer", + "http_user_agent": "$http_user_agent"} + proxy-body-size: 0 + proxy-buffer-size: 16k + ssl-protocols: TLSv1.3 TLSv1.2 + metrics: + enabled: true + serviceMonitor: + enabled: true + namespaceSelector: + any: true + extraArgs: + default-ssl-certificate: "network/${SECRET_DOMAIN/./-}-production-tls" + resources: + requests: + cpu: 100m + limits: + memory: 500Mi diff --git a/kubernetes/apps/network/ingress-nginx/external/kustomization.yaml b/kubernetes/apps/network/ingress-nginx/external/kustomization.yaml new file mode 100644 index 000000000..5dd7baca7 --- /dev/null +++ b/kubernetes/apps/network/ingress-nginx/external/kustomization.yaml @@ -0,0 +1,5 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml diff --git a/kubernetes/apps/network/ingress-nginx/internal/helmrelease.yaml b/kubernetes/apps/network/ingress-nginx/internal/helmrelease.yaml new file mode 100644 index 000000000..156319be8 --- /dev/null +++ b/kubernetes/apps/network/ingress-nginx/internal/helmrelease.yaml @@ -0,0 +1,72 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: ingress-nginx-internal + namespace: network +spec: + interval: 30m + chart: + spec: + chart: ingress-nginx + version: 4.10.1 + sourceRef: + kind: HelmRepository + name: ingress-nginx + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + fullnameOverride: ingress-nginx-internal + controller: + service: + annotations: + io.cilium/lb-ipam-ips: "192.168.13.66" + externalTrafficPolicy: Cluster + ingressClassResource: + name: internal + default: true + controllerValue: k8s.io/internal + admissionWebhooks: + objectSelector: + matchExpressions: + - key: ingress-class + operator: In + values: ["internal"] + config: + client-body-buffer-size: 100M + client-body-timeout: 120 + client-header-timeout: 120 + enable-brotli: "true" + enable-real-ip: "true" + hsts-max-age: 31449600 + keep-alive-requests: 10000 + keep-alive: 120 + log-format-escape-json: "true" + log-format-upstream: > + {"time": "$time_iso8601", "remote_addr": "$proxy_protocol_addr", "x_forwarded_for": "$proxy_add_x_forwarded_for", + "request_id": "$req_id", "remote_user": "$remote_user", "bytes_sent": $bytes_sent, "request_time": $request_time, + "status": $status, "vhost": "$host", "request_proto": "$server_protocol", "path": "$uri", "request_query": "$args", + "request_length": $request_length, "duration": $request_time, "method": "$request_method", "http_referrer": "$http_referer", + "http_user_agent": "$http_user_agent"} + proxy-body-size: 0 + proxy-buffer-size: 16k + ssl-protocols: TLSv1.3 TLSv1.2 + metrics: + enabled: true + serviceMonitor: + enabled: true + namespaceSelector: + any: true + extraArgs: + default-ssl-certificate: "network/${SECRET_DOMAIN/./-}-production-tls" + resources: + requests: + cpu: 100m + limits: + memory: 500Mi diff --git a/kubernetes/apps/network/ingress-nginx/internal/kustomization.yaml b/kubernetes/apps/network/ingress-nginx/internal/kustomization.yaml new file mode 100644 index 000000000..5dd7baca7 --- /dev/null +++ b/kubernetes/apps/network/ingress-nginx/internal/kustomization.yaml @@ -0,0 +1,5 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml diff --git a/kubernetes/apps/network/ingress-nginx/ks.yaml b/kubernetes/apps/network/ingress-nginx/ks.yaml new file mode 100644 index 000000000..570f91947 --- /dev/null +++ b/kubernetes/apps/network/ingress-nginx/ks.yaml @@ -0,0 +1,66 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app ingress-nginx-certificates + namespace: flux-system +spec: + targetNamespace: network + commonMetadata: + labels: + app.kubernetes.io/name: *app + dependsOn: + - name: cert-manager-issuers + path: ./kubernetes/apps/network/ingress-nginx/certificates + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app ingress-nginx-internal + namespace: flux-system +spec: + targetNamespace: network + commonMetadata: + labels: + app.kubernetes.io/name: *app + dependsOn: + - name: ingress-nginx-certificates + path: ./kubernetes/apps/network/ingress-nginx/internal + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false + interval: 30m + retryInterval: 1m + timeout: 5m +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app ingress-nginx-external + namespace: flux-system +spec: + targetNamespace: network + commonMetadata: + labels: + app.kubernetes.io/name: *app + dependsOn: + - name: ingress-nginx-certificates + path: ./kubernetes/apps/network/ingress-nginx/external + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/network/k8s-gateway/app/helmrelease.yaml b/kubernetes/apps/network/k8s-gateway/app/helmrelease.yaml new file mode 100644 index 000000000..63b2bc2fe --- /dev/null +++ b/kubernetes/apps/network/k8s-gateway/app/helmrelease.yaml @@ -0,0 +1,51 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: k8s-gateway +spec: + interval: 30m + chart: + spec: + chart: k8s-gateway + version: 2.4.0 + sourceRef: + kind: HelmRepository + name: k8s-gateway + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + fullnameOverride: k8s-gateway + domain: "${SECRET_DOMAIN}" + fallthrough: + enabled: true + ttl: 1 + service: + type: LoadBalancer + port: 53 + annotations: + io.cilium/lb-ipam-ips: "192.168.13.65" + externalTrafficPolicy: Cluster + watchedResources: ["Ingress", "Service"] + extraZonePlugins: + - name: log + - name: errors + - name: health + configBlock: |- + lameduck 5s + - name: ready + - name: prometheus + parameters: 0.0.0.0:9153 + - name: forward + parameters: . tls://1.1.1.1 tls://1.0.0.1 + configBlock: |- + tls_servername cloudflare-dns.com + - name: loop + - name: reload + - name: loadbalance diff --git a/kubernetes/apps/network/k8s-gateway/app/kustomization.yaml b/kubernetes/apps/network/k8s-gateway/app/kustomization.yaml new file mode 100644 index 000000000..5dd7baca7 --- /dev/null +++ b/kubernetes/apps/network/k8s-gateway/app/kustomization.yaml @@ -0,0 +1,5 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml diff --git a/kubernetes/apps/network/k8s-gateway/ks.yaml b/kubernetes/apps/network/k8s-gateway/ks.yaml new file mode 100644 index 000000000..2d4c643f2 --- /dev/null +++ b/kubernetes/apps/network/k8s-gateway/ks.yaml @@ -0,0 +1,20 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app k8s-gateway + namespace: flux-system +spec: + targetNamespace: network + commonMetadata: + labels: + app.kubernetes.io/name: *app + path: ./kubernetes/apps/network/k8s-gateway/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/network/kustomization.yaml b/kubernetes/apps/network/kustomization.yaml new file mode 100644 index 000000000..0d5721368 --- /dev/null +++ b/kubernetes/apps/network/kustomization.yaml @@ -0,0 +1,10 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - namespace.yaml + - cloudflared/ks.yaml + - echo-server/ks.yaml + - external-dns/ks.yaml + - ingress-nginx/ks.yaml + - k8s-gateway/ks.yaml diff --git a/kubernetes/apps/network/namespace.yaml b/kubernetes/apps/network/namespace.yaml new file mode 100644 index 000000000..4d78d7b11 --- /dev/null +++ b/kubernetes/apps/network/namespace.yaml @@ -0,0 +1,7 @@ +--- +apiVersion: v1 +kind: Namespace +metadata: + name: network + labels: + kustomize.toolkit.fluxcd.io/prune: disabled diff --git a/kubernetes/apps/observability/alertmanager-discord/app/alertmanager-discord-config.yaml b/kubernetes/apps/observability/alertmanager-discord/app/alertmanager-discord-config.yaml new file mode 100755 index 000000000..7a5c2bbd5 --- /dev/null +++ b/kubernetes/apps/observability/alertmanager-discord/app/alertmanager-discord-config.yaml @@ -0,0 +1,23 @@ +--- +apiVersion: monitoring.coreos.com/v1alpha1 +kind: AlertmanagerConfig +metadata: + name: discord + namespace: observability + labels: + alertmanagerConfig: discord +spec: + route: + groupBy: + - alertname + groupInterval: 10s + groupWait: 1s + repeatInterval: 30s + receiver: discord + routes: + - matchers: + - namespace: "*" + receivers: + - name: discord + webhookConfigs: + - url: http://alertmanager-discord:9094 diff --git a/kubernetes/apps/observability/alertmanager-discord/app/alertmanager-discord-deployment.yaml b/kubernetes/apps/observability/alertmanager-discord/app/alertmanager-discord-deployment.yaml new file mode 100755 index 000000000..174b31bc9 --- /dev/null +++ b/kubernetes/apps/observability/alertmanager-discord/app/alertmanager-discord-deployment.yaml @@ -0,0 +1,35 @@ +--- +apiVersion: apps/v1 +kind: Deployment +metadata: + name: alertmanager-discord + namespace: observability +spec: + selector: + matchLabels: + app: alertmanager-discord + template: + metadata: + labels: + app: alertmanager-discord + spec: + containers: + - image: registry.eighty-three.me/tuxpeople/alertmanager-discord:rolling + imagePullPolicy: Always + name: main + ports: + - containerPort: 9094 + name: http + resources: + requests: + cpu: 10m + memory: 10Mi + limits: + cpu: 20m + memory: 40Mi + env: + - name: DISCORD_WEBHOOK + valueFrom: + secretKeyRef: + key: ALERTMANAGER_DISCORD_WEBHOOK + name: alertmanager-discord-webhook-secret diff --git a/kubernetes/apps/observability/alertmanager-discord/app/alertmanager-discord-service.yaml b/kubernetes/apps/observability/alertmanager-discord/app/alertmanager-discord-service.yaml new file mode 100755 index 000000000..4fcf93148 --- /dev/null +++ b/kubernetes/apps/observability/alertmanager-discord/app/alertmanager-discord-service.yaml @@ -0,0 +1,15 @@ +--- +apiVersion: v1 +kind: Service +metadata: + labels: + app: alertmanager-discord + name: alertmanager-discord + namespace: observability +spec: + ports: + - name: http + port: 9094 + targetPort: http + selector: + app: alertmanager-discord diff --git a/kubernetes/apps/observability/alertmanager-discord/app/externalsecret.yaml b/kubernetes/apps/observability/alertmanager-discord/app/externalsecret.yaml new file mode 100644 index 000000000..81e0a62d1 --- /dev/null +++ b/kubernetes/apps/observability/alertmanager-discord/app/externalsecret.yaml @@ -0,0 +1,19 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/external-secrets.io/externalsecret_v1beta1.json +apiVersion: external-secrets.io/v1beta1 +kind: ExternalSecret +metadata: + name: alertmanager-discord-webhook +spec: + secretStoreRef: + kind: ClusterSecretStore + name: onepassword + target: + name: alertmanager-discord-webhook-secret + template: + engineVersion: v2 + data: + ALERTMANAGER_DISCORD_WEBHOOK: "{{ .ALERTMANAGER_DISCORD_WEBHOOK }}" + dataFrom: + - extract: + key: alertmanager-discord-webhook diff --git a/kubernetes/apps/observability/alertmanager-discord/app/kustomization.yaml b/kubernetes/apps/observability/alertmanager-discord/app/kustomization.yaml new file mode 100755 index 000000000..f70265c66 --- /dev/null +++ b/kubernetes/apps/observability/alertmanager-discord/app/kustomization.yaml @@ -0,0 +1,10 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +namespace: observability +resources: + - externalsecret.yaml + # - alertmanager-discord-config.yaml + - alertmanager-discord-deployment.yaml + - alertmanager-discord-service.yaml diff --git a/kubernetes/apps/observability/alertmanager-discord/ks.yaml b/kubernetes/apps/observability/alertmanager-discord/ks.yaml new file mode 100644 index 000000000..8baca3708 --- /dev/null +++ b/kubernetes/apps/observability/alertmanager-discord/ks.yaml @@ -0,0 +1,23 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/kustomize.toolkit.fluxcd.io/kustomization_v1.json +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app alertmanager-discord + namespace: flux-system +spec: + commonMetadata: + labels: + app.kubernetes.io/name: *app + targetNamespace: observability + dependsOn: + - name: external-secrets-secretstores + path: ./kubernetes/apps/observability/alertmanager-discord/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/observability/blackbox-exporter/app/helmrelease.yaml b/kubernetes/apps/observability/blackbox-exporter/app/helmrelease.yaml new file mode 100644 index 000000000..46018b1b9 --- /dev/null +++ b/kubernetes/apps/observability/blackbox-exporter/app/helmrelease.yaml @@ -0,0 +1,85 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: &app blackbox-exporter +spec: + interval: 30m + chart: + spec: + chart: prometheus-blackbox-exporter + version: 8.17.0 + sourceRef: + kind: HelmRepository + name: prometheus-community + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + fullnameOverride: *app + pspEnabled: false + ingress: + enabled: true + className: internal + annotations: + hajimari.io/enable: "false" + hosts: + - host: &host blackbox.${SECRET_DOMAIN} + paths: + - path: / + pathType: Prefix + tls: + - hosts: + - *host + securityContext: + readOnlyRootFilesystem: true + allowPrivilegeEscalation: false + capabilities: + add: + - NET_RAW + config: + modules: + http_2xx: + prober: http + timeout: 5s + http: + valid_http_versions: + - HTTP/1.1 + - HTTP/2.0 + follow_redirects: true + preferred_ip_protocol: ipv4 + icmp: + prober: icmp + timeout: 5s + icmp: + preferred_ip_protocol: ipv4 + tcp_connect: + prober: tcp + timeout: 5s + tcp: + preferred_ip_protocol: ipv4 + dnsConfig: + options: + - name: ndots + value: "1" + serviceMonitor: + enabled: true + defaults: + interval: 1m + scrapeTimeout: 10s + prometheusRule: + enabled: true + rules: + - alert: BlackboxProbeFailed + expr: probe_success == 0 + for: 15m + labels: + severity: critical + annotations: + description: |- + The host {{ $labels.instance }} is currently unreachable diff --git a/kubernetes/apps/observability/blackbox-exporter/app/kustomization.yaml b/kubernetes/apps/observability/blackbox-exporter/app/kustomization.yaml new file mode 100644 index 000000000..5dd7baca7 --- /dev/null +++ b/kubernetes/apps/observability/blackbox-exporter/app/kustomization.yaml @@ -0,0 +1,5 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml diff --git a/kubernetes/apps/observability/blackbox-exporter/ks.yaml b/kubernetes/apps/observability/blackbox-exporter/ks.yaml new file mode 100644 index 000000000..9afaa11c2 --- /dev/null +++ b/kubernetes/apps/observability/blackbox-exporter/ks.yaml @@ -0,0 +1,37 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: blackbox-exporter + namespace: flux-system +spec: + targetNamespace: observability + path: ./kubernetes/apps/observability/blackbox-exporter/app + dependsOn: + - name: prometheus-operator-crds + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: blackbox-exporter-probes + namespace: flux-system +spec: + targetNamespace: observability + dependsOn: + - name: blackbox-exporter + path: ./kubernetes/apps/observability/blackbox-exporter/probes + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/observability/blackbox-exporter/probes/homelab.yaml b/kubernetes/apps/observability/blackbox-exporter/probes/homelab.yaml new file mode 100644 index 000000000..2cef23e64 --- /dev/null +++ b/kubernetes/apps/observability/blackbox-exporter/probes/homelab.yaml @@ -0,0 +1,14 @@ +--- +kind: Probe +apiVersion: monitoring.coreos.com/v1 +metadata: + name: homelab +spec: + module: icmp + prober: + url: blackbox-exporter.observability.svc.cluster.local:9115 + targets: + staticConfig: + static: + - thiazi.${SECRET_PRIVATE_DOMAIN} + - router.${SECRET_PRIVATE_DOMAIN} diff --git a/kubernetes/apps/observability/blackbox-exporter/probes/kustomization.yaml b/kubernetes/apps/observability/blackbox-exporter/probes/kustomization.yaml new file mode 100644 index 000000000..e2990da68 --- /dev/null +++ b/kubernetes/apps/observability/blackbox-exporter/probes/kustomization.yaml @@ -0,0 +1,5 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./homelab.yaml diff --git a/kubernetes/apps/observability/gatus/app/config/config.yaml b/kubernetes/apps/observability/gatus/app/config/config.yaml new file mode 100644 index 000000000..15db62a47 --- /dev/null +++ b/kubernetes/apps/observability/gatus/app/config/config.yaml @@ -0,0 +1,51 @@ +--- +# Note: Gatus vars should be escaped with $${VAR_NAME} to avoid interpolation by Flux +web: + port: $${CUSTOM_WEB_PORT} +metrics: true +debug: true +storage: + type: sqlite + path: /data/data.db +ui: + title: Status | Gatus + header: Status +connectivity: + checker: + target: 1.1.1.1:53 + interval: 1m +remote: + instances: + - url: "http://status.home:8088/api/v1/endpoints/statuses" + # endpoint-prefix: "nonkubernetes-" +alerting: + discord: + webhook-url: $${GATUS_DISCORD_WEBHOOK} + default-alert: + # description: "health check failed" + send-on-resolved: true + failure-threshold: 2 + success-threshold: 2 +endpoints: + # - name: status + # group: external + # url: https://status.${SECRET_DOMAIN} + # interval: 1m + # ui: + # hide-hostname: true + # hide-url: true + # client: + # dns-resolver: tcp://1.1.1.1:53 + # conditions: + # - "[STATUS] == 200" + - name: flux-webhook + group: external-kubernetes + url: https://flux-webhook.${SECRET_DOMAIN} + interval: 1m + ui: + hide-hostname: true + hide-url: true + client: + dns-resolver: tcp://1.1.1.1:53 + conditions: + - "[STATUS] == 404" diff --git a/kubernetes/apps/observability/gatus/app/externalsecret.yaml b/kubernetes/apps/observability/gatus/app/externalsecret.yaml new file mode 100644 index 000000000..3aee670df --- /dev/null +++ b/kubernetes/apps/observability/gatus/app/externalsecret.yaml @@ -0,0 +1,19 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/external-secrets.io/externalsecret_v1beta1.json +apiVersion: external-secrets.io/v1beta1 +kind: ExternalSecret +metadata: + name: gatus-discord-webhook +spec: + secretStoreRef: + kind: ClusterSecretStore + name: onepassword + target: + name: gatus-discord-webhook-secret + template: + engineVersion: v2 + data: + GATUS_DISCORD_WEBHOOK: "{{ .WEBHOOK }}" + dataFrom: + - extract: + key: gatus-discord-webhook diff --git a/kubernetes/apps/observability/gatus/app/helmrelease.yaml b/kubernetes/apps/observability/gatus/app/helmrelease.yaml new file mode 100644 index 000000000..31bc9b3f7 --- /dev/null +++ b/kubernetes/apps/observability/gatus/app/helmrelease.yaml @@ -0,0 +1,128 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: gatus +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + controllers: + gatus: + annotations: + reloader.stakater.com/auto: "true" + initContainers: + init-config: + image: + repository: ghcr.io/kiwigrid/k8s-sidecar + tag: 1.27.4 + env: + FOLDER: /config + LABEL: gatus.io/enabled + NAMESPACE: ALL + RESOURCE: both + UNIQUE_FILENAMES: true + METHOD: WATCH + restartPolicy: Always + resources: &resources + requests: + cpu: 10m + limits: + memory: 256Mi + containers: + app: + image: + repository: ghcr.io/twin/gatus + tag: v5.11.0 + env: + TZ: Europe/Zurich + GATUS_CONFIG_PATH: /config + GATUS_DELAY_START_SECONDS: 5 + CUSTOM_WEB_PORT: &port 80 + envFrom: + - secretRef: + name: gatus-discord-webhook-secret + probes: + liveness: &probes + enabled: true + custom: true + spec: + httpGet: + path: &path /health + port: *port + initialDelaySeconds: 0 + periodSeconds: 10 + timeoutSeconds: 1 + failureThreshold: 3 + readiness: *probes + securityContext: + allowPrivilegeEscalation: false + readOnlyRootFilesystem: true + capabilities: { drop: ["ALL"] } + resources: *resources + service: + app: + controller: gatus + ports: + http: + port: *port + serviceMonitor: + app: + serviceName: gatus + endpoints: + - port: http + scheme: http + path: /metrics + interval: 1m + scrapeTimeout: 10s + ingress: + app: + className: external + annotations: + gatus.io/path: *path + hajimari.io/icon: simple-icons:statuspage + hajimari.io/url: https://status.${PUBLIC_DOMAIN} + hosts: + - host: &host "status.${SECRET_DOMAIN}" + paths: + - path: / + service: + identifier: app + port: http + tls: + - hosts: + - *host + secretName: ${SECRET_DOMAIN/./-}-production-tls + serviceAccount: + create: true + name: gatus + persistence: + config: + type: emptyDir + config-file: + type: configMap + name: gatus-configmap + globalMounts: + - path: /config/config.yaml + subPath: config.yaml + readOnly: true + data: + type: emptyDir + defaultPodOptions: + dnsConfig: + options: + - { name: ndots, value: "1" } diff --git a/kubernetes/apps/observability/gatus/app/kustomization.yaml b/kubernetes/apps/observability/gatus/app/kustomization.yaml new file mode 100644 index 000000000..d15eaef7a --- /dev/null +++ b/kubernetes/apps/observability/gatus/app/kustomization.yaml @@ -0,0 +1,14 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./rbac.yaml + - ./helmrelease.yaml + - ./externalsecret.yaml +configMapGenerator: + - name: gatus-configmap + files: + - config.yaml=./config/config.yaml +generatorOptions: + disableNameSuffixHash: true diff --git a/kubernetes/apps/observability/gatus/app/rbac.yaml b/kubernetes/apps/observability/gatus/app/rbac.yaml new file mode 100644 index 000000000..0f12c439b --- /dev/null +++ b/kubernetes/apps/observability/gatus/app/rbac.yaml @@ -0,0 +1,22 @@ +--- +apiVersion: rbac.authorization.k8s.io/v1 +kind: ClusterRole +metadata: + name: gatus +rules: + - apiGroups: [""] + resources: ["configmaps", "secrets"] + verbs: ["get", "watch", "list"] +--- +apiVersion: rbac.authorization.k8s.io/v1 +kind: ClusterRoleBinding +metadata: + name: gatus +roleRef: + apiGroup: rbac.authorization.k8s.io + kind: ClusterRole + name: gatus +subjects: + - kind: ServiceAccount + name: gatus + namespace: observability diff --git a/kubernetes/apps/observability/gatus/ks.yaml b/kubernetes/apps/observability/gatus/ks.yaml new file mode 100644 index 000000000..9d1a45c8d --- /dev/null +++ b/kubernetes/apps/observability/gatus/ks.yaml @@ -0,0 +1,23 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/kustomize.toolkit.fluxcd.io/kustomization_v1.json +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app gatus + namespace: flux-system +spec: + commonMetadata: + labels: + app.kubernetes.io/name: *app + dependsOn: + - name: external-secrets-secretstores + targetNamespace: observability + path: ./kubernetes/apps/observability/gatus/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/observability/kube-prometheus-stack/app/helmrelease.yaml b/kubernetes/apps/observability/kube-prometheus-stack/app/helmrelease.yaml new file mode 100644 index 000000000..acf0ada52 --- /dev/null +++ b/kubernetes/apps/observability/kube-prometheus-stack/app/helmrelease.yaml @@ -0,0 +1,452 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: kube-prometheus-stack + namespace: observability +spec: + interval: 30m + timeout: 15m + chart: + spec: + chart: kube-prometheus-stack + version: 60.1.0 + sourceRef: + kind: HelmRepository + name: prometheus-community + namespace: flux-system + install: + crds: Skip + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + crds: Skip + remediation: + strategy: rollback + retries: 3 + dependsOn: + - name: prometheus-operator-crds + namespace: observability + values: + crds: + enabled: false + cleanPrometheusOperatorObjectNames: true + alertmanager: + enabled: true + config: + global: + slack_api_url: ${SECRET_ALERT_MANAGER_DISCORD_WEBHOOK} + resolve_timeout: 5m + # smtp_smarthost: smtp.gmail.com:587 + # smtp_auth_username: you@gmail.com + # smtp_auth_password: yourapppassword # https://support.google.com/mail/answer/185833?hl=en-GB + # smtp_auth_identity: you@gmail.com + route: + group_by: + - alertname + - job + group_wait: 30s + group_interval: 5m + repeat_interval: 6h + receiver: discord + routes: + - receiver: "null" + match: + alertname: InfoInhibitor + - receiver: "null" + match: + alertname: CPUThrottlingHigh + - receiver: DeadMansSnitch + repeat_interval: 30m + match: + alertname: Watchdog + - receiver: discord + matchers: + - severity = "critical" + continue: true + # - receiver: discord + # group_wait: 10s + # match_re: + # issue: Portworx* + # continue: true + receivers: + - name: "null" + - name: email + email_configs: + - send_resolved: true + to: ${SECRET_ACME_EMAIL} + from: prometheus@tuxpeople.org + smarthost: smtp.utils.svc.cluster.local:25 + require_tls: false + - name: DeadMansSnitch + webhook_configs: + - url: https://nosnch.in/c15491ac44 + send_resolved: false + - name: discord + webhook_configs: + - send_resolved: true + url: http://alertmanager-discord:9094 + # title: |- + # [{{ .Status | toUpper }}{{ if eq .Status "firing" }}:{{ .Alerts.Firing | len }}{{ end }}] {{ if ne .CommonAnnotations.summary ""}}{{ .CommonAnnotations.summary }}{{ else }}{{ .CommonLabels.alertname }}{{ end }} + # text: >- + # {{ range .Alerts -}} + # **Alert:** {{ .Annotations.title }}{{ if .Labels.severity }} - `{{ .Labels.severity }}`{{ end }} + # **Description:** {{ if ne .Annotations.description ""}}{{ .Annotations.description }}{{else}}N/A{{ end }} + # **Details:** + # {{ range .Labels.SortedPairs }} • *{{ .Name }}:* `{{ .Value }}` + # {{ end }} + # {{ end }} + # - name: discord + # webhook_configs: + # - send_resolved: true + # url: 'http://alertmanager-discord:9094' + # Inhibition rules allow to mute a set of alerts given that another alert is firing. + # We use this to mute any warning-level notifications if the same alert is already critical. + inhibit_rules: + - source_matchers: + - severity = "critical" + target_matchers: + - severity = "warning" + equal: + - alertname + - namespace + alertmanagerSpec: + replicas: 1 + podAntiAffinity: hard + storage: + volumeClaimTemplate: + spec: + storageClassName: ${MAIN_SC} + accessModes: + - ReadWriteOnce + resources: + requests: + storage: 1Gi + resources: + limits: + cpu: 500m + memory: 400Mi + requests: + cpu: 5m + memory: 50Mi + # priorityClassName: high-priority + alertmanagerConfigSelector: + matchLabels: + alertmanagerConfig: homelab + ingress: + enabled: true + pathType: Prefix + ingressClassName: internal + annotations: + external-dns.alpha.kubernetes.io/target: "external.${SECRET_DOMAIN}" + hajimari.io/enable: "true" + hajimari.io/appName: Alertmanager + hajimari.io/icon: mdi:alert-decagram-outline + tls: + - secretName: ${SECRET_DOMAIN/./-}-production-tls + hosts: + - alertmanager.${SECRET_DOMAIN} + hosts: + - alertmanager.${SECRET_DOMAIN} + grafana: + enabled: false + forceDeployDashboards: true + sidecar: + dashboards: + multicluster: + etcd: + enabled: true + kubeStateMetrics: + enabled: true + kube-state-metrics: + metricLabelsAllowlist: + - pods=[*] + - deployments=[*] + - persistentvolumeclaims=[*] + prometheus: + monitor: + enabled: true + relabelings: + - action: replace + regex: (.*) + replacement: $1 + sourceLabels: [__meta_kubernetes_pod_node_name] + targetLabel: kubernetes_node + kubelet: + enabled: true + serviceMonitor: + metricRelabelings: + # Remove duplicate metrics + - sourceLabels: [__name__] + regex: (apiserver_audit|apiserver_client|apiserver_delegated|apiserver_envelope|apiserver_storage|apiserver_webhooks|authentication_token|cadvisor_version|container_blkio|container_cpu|container_fs|container_last|container_memory|container_network|container_oom|container_processes|container|csi_operations|disabled_metric|get_token|go|hidden_metric|kubelet_certificate|kubelet_cgroup|kubelet_container|kubelet_containers|kubelet_cpu|kubelet_device|kubelet_graceful|kubelet_http|kubelet_lifecycle|kubelet_managed|kubelet_node|kubelet_pleg|kubelet_pod|kubelet_run|kubelet_running|kubelet_runtime|kubelet_server|kubelet_started|kubelet_volume|kubernetes_build|kubernetes_feature|machine_cpu|machine_memory|machine_nvm|machine_scrape|node_namespace|plugin_manager|prober_probe|process_cpu|process_max|process_open|process_resident|process_start|process_virtual|registered_metric|rest_client|scrape_duration|scrape_samples|scrape_series|storage_operation|volume_manager|volume_operation|workqueue)_(.+) + action: keep + - sourceLabels: [node] + targetLabel: instance + action: replace + kubeApiServer: + enabled: true + serviceMonitor: + metricRelabelings: + # Remove duplicate metrics + - sourceLabels: [__name__] + regex: (aggregator_openapi|aggregator_unavailable|apiextensions_openapi|apiserver_admission|apiserver_audit|apiserver_cache|apiserver_cel|apiserver_client|apiserver_crd|apiserver_current|apiserver_envelope|apiserver_flowcontrol|apiserver_init|apiserver_kube|apiserver_longrunning|apiserver_request|apiserver_requested|apiserver_response|apiserver_selfrequest|apiserver_storage|apiserver_terminated|apiserver_tls|apiserver_watch|apiserver_webhooks|authenticated_user|authentication|disabled_metric|etcd_bookmark|etcd_lease|etcd_request|field_validation|get_token|go|grpc_client|hidden_metric|kube_apiserver|kubernetes_build|kubernetes_feature|node_authorizer|pod_security|process_cpu|process_max|process_open|process_resident|process_start|process_virtual|registered_metric|rest_client|scrape_duration|scrape_samples|scrape_series|serviceaccount_legacy|serviceaccount_stale|serviceaccount_valid|watch_cache|workqueue)_(.+) + action: keep + # Remove high cardinality metrics + - sourceLabels: [__name__] + regex: (apiserver|etcd|rest_client)_request(|_sli|_slo)_duration_seconds_bucket + action: drop + - sourceLabels: [__name__] + regex: (apiserver_response_sizes_bucket|apiserver_watch_events_sizes_bucket) + action: drop + kubeControllerManager: + enabled: true + endpoints: &cp + - 192.168.8.111 + - 192.168.8.112 + - 192.168.8.113 + serviceMonitor: + metricRelabelings: + # Remove duplicate metrics + - sourceLabels: [__name__] + regex: (apiserver_audit|apiserver_client|apiserver_delegated|apiserver_envelope|apiserver_storage|apiserver_webhooks|attachdetach_controller|authenticated_user|authentication|cronjob_controller|disabled_metric|endpoint_slice|ephemeral_volume|garbagecollector_controller|get_token|go|hidden_metric|job_controller|kubernetes_build|kubernetes_feature|leader_election|node_collector|node_ipam|process_cpu|process_max|process_open|process_resident|process_start|process_virtual|pv_collector|registered_metric|replicaset_controller|rest_client|retroactive_storageclass|root_ca|running_managed|scrape_duration|scrape_samples|scrape_series|service_controller|storage_count|storage_operation|ttl_after|volume_operation|workqueue)_(.+) + action: keep + kubeEtcd: + enabled: true + endpoints: *cp + kubeProxy: + enabled: false # Disabled because eBPF + kubeScheduler: + enabled: true + endpoints: *cp + serviceMonitor: + metricRelabelings: + # Remove duplicate metrics + - sourceLabels: [__name__] + regex: (apiserver_audit|apiserver_client|apiserver_delegated|apiserver_envelope|apiserver_storage|apiserver_webhooks|authenticated_user|authentication|disabled_metric|go|hidden_metric|kubernetes_build|kubernetes_feature|leader_election|process_cpu|process_max|process_open|process_resident|process_start|process_virtual|registered_metric|rest_client|scheduler|scrape_duration|scrape_samples|scrape_series|workqueue)_(.+) + action: keep + prometheus: + extraFlags: + - --web.enable-lifecycle + ingress: + enabled: true + ingressClassName: internal + annotations: + hajimari.io/appName: Prometheus + hajimari.io/icon: simple-icons:prometheus + nginx.ingress.kubernetes.io/ssl-redirect: "false" + pathType: Prefix + hosts: + - &host prometheus.${SECRET_DOMAIN} + tls: + - hosts: + - *host + prometheusSpec: + ruleSelectorNilUsesHelmValues: false + serviceMonitorSelectorNilUsesHelmValues: false + podMonitorSelectorNilUsesHelmValues: false + probeSelectorNilUsesHelmValues: false + enableAdminAPI: true + walCompression: true + retentionSize: 8GB + storageSpec: + volumeClaimTemplate: + spec: + storageClassName: ${MAIN_SC} + resources: + requests: + storage: 10Gi + # additionalScrapeConfigs: + # - job_name: node-exporter + # scrape_interval: 1m + # scrape_timeout: 30s + # honor_timestamps: true + # # basic_auth: + # # username: randomuser + # # password: examplepassword + # static_configs: + # - targets: # k3s-node1 + # - 192.168.8.111:9100 + # labels: + # node: "k3s-node1" + # - targets: # k3s-node2 + # - 192.168.8.112:9100 + # labels: + # node: "k3s-node2" + # - targets: # k3s-node3 + # - 192.168.8.113:9100 + # labels: + # node: "k3s-node3" + # - targets: # k3s-node4 + # - 192.168.8.114:9100 + # labels: + # node: "k3s-node4" + # - targets: # NAS + # - 10.20.30.40:9100 + # labels: + # node: "nas" + # - targets: # laptop2 + # - laptop2.home:9100 + # labels: + # node: "laptop-work" + prometheus-node-exporter: + extraArgs: + - --collector.filesystem.ignored-mount-points=^/(dev|proc|sys|var/lib/docker/.+|var/lib/kubelet/.+|boot/firmware)($|/) + # # From archive + # prometheus-node-exporter: + # fullnameOverride: node-exporter + # prometheus: + # monitor: + # enabled: true + # relabelings: + # - action: replace + # regex: (.*) + # replacement: $1 + # sourceLabels: + # - __meta_kubernetes_pod_node_name + # targetLabel: kubernetes_node + # prometheusOperator: + # prometheusConfigReloader: + # resources: + # requests: + # cpu: 100m + # memory: 50Mi + # limits: + # cpu: 200m + # memory: 100Mi + # prometheus: + # enabled: true + # persistentVolume: + # enabled: true + # size: 10Gi + # thanosService: + # enabled: true + # thanosServiceMonitor: + # enabled: true + # prometheusSpec: + # replicas: 1 + # externalLabels: + # cluster: homelab + # thanos: + # image: quay.io/thanos/thanos:v0.31.0 + # objectStorageConfig: + # name: thanos-objstore-secret + # key: objstore.yml + # retention: 12h + # retentionSize: 10GB + # podAntiAffinity: hard + # replicaExternalLabelName: __replica__ + # scrapeInterval: 1m + # ruleSelectorNilUsesHelmValues: false + # serviceMonitorSelectorNilUsesHelmValues: false + # podMonitorSelectorNilUsesHelmValues: false + # probeSelectorNilUsesHelmValues: false + # enableAdminAPI: true + # walCompression: true + # disableCompaction: true + # storageSpec: + # volumeClaimTemplate: + # spec: + # storageClassName: ${MAIN_SC} + # resources: + # requests: + # storage: 10Gi + # resources: + # requests: + # cpu: 10m + # memory: 2000Mi + # limits: + # memory: 8000Mi + # additionalScrapeConfigs: + # # - job_name: minio + # # honor_timestamps: true + # # metrics_path: /minio/v2/metrics/cluster + # # static_configs: + # # - targets: + # # - "minio.domain.com:9000" + # - job_name: octoprint + # scrape_interval: 1m + # metrics_path: /plugin/prometheus_exporter/metrics + # params: + # apikey: + # - ${SECRET_OCTOPRINTAPI} + # static_configs: + # - targets: + # - octopi.home:80 + # - job_name: speedtest-exporter + # scrape_interval: 1m + # scrape_timeout: 30s + # static_configs: + # - targets: + # - speedtest-exporter:9090 + # - job_name: minio-job + # bearer_token: ${SECRET_MINIO_BEARERTOKEN} + # metrics_path: /minio/v2/metrics/cluster + # scheme: http + # static_configs: + # - targets: + # - minio.lab.tdeutsch.ch:9091 + # - job_name: mystrom-exporter + # scrape_interval: 1m + # metrics_path: /device + # honor_labels: true + # static_configs: + # - targets: + # - 10.20.30.33 + # labels: + # alias: 3D Drucker + # relabel_configs: + # - source_labels: + # - __address__ + # target_label: __param_target + # - target_label: __address__ + # replacement: mystrom-3dprinter:9452 + # - job_name: prometheus-pushgateway + # scrape_interval: 1m + # scrape_timeout: 30s + # honor_labels: true + # static_configs: + # - targets: + # - prometheus-pushgateway:9091 + # - job_name: wireguard-exporter + # scrape_interval: 1m + # scrape_timeout: 30s + # metrics_path: /metrics + # static_configs: + # - targets: + # - 10.20.30.1:9586 + # - job_name: node-exporter + # scrape_interval: 1m + # scrape_timeout: 30s + # honor_timestamps: true + # # basic_auth: + # # username: randomuser + # # password: examplepassword + # static_configs: + # - targets: # k3s-node01 + # - 192.168.8.111:9100 + # - targets: # k3s-node02 + # - 192.168.8.112:9100 + # - targets: # k3s-node03 + # - 192.168.8.113:9100 + # - targets: # NAS + # - 10.20.30.40:9100 + # ingress: + # enabled: true + # pathType: Prefix + # ingressClassName: internal + # annotations: + # nginx.ingress.kubernetes.io/auth-method: 'GET' + nginx.ingress.kubernetes.io/auth-url: "https://auth.${SECRET_DOMAIN}/api/authz/auth-request" + nginx.ingress.kubernetes.io/auth-signin: "https://auth.${SECRET_DOMAIN}?rm=$request_method" + nginx.ingress.kubernetes.io/auth-response-headers: "Remote-User,Remote-Name,Remote-Groups,Remote-Email" + # hajimari.io/enable: "true" + # hajimari.io/appName: Prometheus + # hajimari.io/icon: mdi:fire + # external-dns.alpha.kubernetes.io/target: "external.${SECRET_DOMAIN}" + # tls: + # - secretName: ${SECRET_DOMAIN/./-}-production-tls + # hosts: + # - prometheus.${SECRET_DOMAIN} + # hosts: + # - prometheus.${SECRET_DOMAIN} diff --git a/kubernetes/apps/observability/kube-prometheus-stack/app/kustomization.yaml b/kubernetes/apps/observability/kube-prometheus-stack/app/kustomization.yaml new file mode 100644 index 000000000..1a892146a --- /dev/null +++ b/kubernetes/apps/observability/kube-prometheus-stack/app/kustomization.yaml @@ -0,0 +1,7 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +namespace: observability +resources: + - ./helmrelease.yaml diff --git a/kubernetes/apps/observability/kube-prometheus-stack/config/kustomization.yaml b/kubernetes/apps/observability/kube-prometheus-stack/config/kustomization.yaml new file mode 100644 index 000000000..4c6652242 --- /dev/null +++ b/kubernetes/apps/observability/kube-prometheus-stack/config/kustomization.yaml @@ -0,0 +1,8 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +namespace: observability +resources: + - ./prometheusrules.yaml + - ./scrapeconfigs.yaml diff --git a/kubernetes/apps/observability/kube-prometheus-stack/config/prometheusrules.yaml b/kubernetes/apps/observability/kube-prometheus-stack/config/prometheusrules.yaml new file mode 100644 index 000000000..ae12afd86 --- /dev/null +++ b/kubernetes/apps/observability/kube-prometheus-stack/config/prometheusrules.yaml @@ -0,0 +1,26 @@ +apiVersion: monitoring.coreos.com/v1 +kind: PrometheusRule +metadata: + name: homebrew-rules +spec: + groups: + - name: homebrew + rules: + - alert: homebrew_outdated_formulas + expr: | + homebrew_outdated_formulaes > 0 + for: 5m + labels: + severity: critical + annotations: + description: "There are upgradeable Homebrew formulas on {{$labels.instance}}" + summary: "Homebrew formulas can be upgraded" + - alert: homebrew_outdated_casks + expr: | + homebrew_outdated_casks > 0 + for: 5m + labels: + severity: critical + annotations: + description: "There are upgradeable Homebrew casks on {{$labels.instance}}" + summary: "Homebrew casks can be upgraded" diff --git a/kubernetes/apps/observability/kube-prometheus-stack/config/scrapeconfigs.yaml b/kubernetes/apps/observability/kube-prometheus-stack/config/scrapeconfigs.yaml new file mode 100644 index 000000000..29e3b104d --- /dev/null +++ b/kubernetes/apps/observability/kube-prometheus-stack/config/scrapeconfigs.yaml @@ -0,0 +1,35 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/monitoring.coreos.com/scrapeconfig_v1alpha1.json +apiVersion: monitoring.coreos.com/v1alpha1 +kind: ScrapeConfig +metadata: + name: &name weatherstation +spec: + staticConfigs: + - targets: + - weatherstation.home:80 + metricsPath: /metrics + relabelings: + - action: replace + targetLabel: job + replacement: *name +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/monitoring.coreos.com/scrapeconfig_v1alpha1.json +apiVersion: monitoring.coreos.com/v1alpha1 +kind: ScrapeConfig +metadata: + name: &name node-exporter +spec: + staticConfigs: + - targets: + - diskstation:9100 + - test-cluster-node01:9100 + - test-cluster-node02:9100 + - test-cluster-node03:9100 + - test-cluster-node04:9100 + - laptop2:9100 + metricsPath: /metrics + relabelings: + - action: replace + targetLabel: job + replacement: *name diff --git a/kubernetes/apps/observability/kube-prometheus-stack/ks.yaml b/kubernetes/apps/observability/kube-prometheus-stack/ks.yaml new file mode 100644 index 000000000..e353a3745 --- /dev/null +++ b/kubernetes/apps/observability/kube-prometheus-stack/ks.yaml @@ -0,0 +1,46 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/kustomize.toolkit.fluxcd.io/kustomization_v1.json +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app kube-prometheus-stack + namespace: flux-system +spec: + commonMetadata: + labels: + app.kubernetes.io/name: *app + targetNamespace: observability + dependsOn: + - name: alertmanager-discord + path: ./kubernetes/apps/observability/kube-prometheus-stack/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/kustomize.toolkit.fluxcd.io/kustomization_v1.json +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app kube-prometheus-config + namespace: flux-system +spec: + commonMetadata: + labels: + app.kubernetes.io/name: *app + targetNamespace: observability + dependsOn: + - name: kube-prometheus-stack + path: ./kubernetes/apps/observability/kube-prometheus-stack/config + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false # no flux ks dependents + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/observability/kustomization.yaml b/kubernetes/apps/observability/kustomization.yaml new file mode 100644 index 000000000..105ea822f --- /dev/null +++ b/kubernetes/apps/observability/kustomization.yaml @@ -0,0 +1,17 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - namespace.yaml + - alertmanager-discord/ks.yaml + - blackbox-exporter/ks.yaml + - gatus/ks.yaml + - kube-prometheus-stack/ks.yaml + - overseerr-exporter/ks.yaml + - prometheus-operator-crds/ks.yaml + - prowlarr-exporter/ks.yaml + - radarr-exporter/ks.yaml + - sabnzbd-exporter/ks.yaml + - sonarr-exporter/ks.yaml + - speedtest-exporter/ks.yaml + - tautulli-exporter/ks.yaml diff --git a/kubernetes/apps/observability/namespace.yaml b/kubernetes/apps/observability/namespace.yaml new file mode 100644 index 000000000..ce3a5bd22 --- /dev/null +++ b/kubernetes/apps/observability/namespace.yaml @@ -0,0 +1,7 @@ +--- +apiVersion: v1 +kind: Namespace +metadata: + name: observability + labels: + kustomize.toolkit.fluxcd.io/prune: disabled diff --git a/kubernetes/apps/observability/overseerr-exporter/app/externalsecret.yaml b/kubernetes/apps/observability/overseerr-exporter/app/externalsecret.yaml new file mode 100644 index 000000000..8b6370c8c --- /dev/null +++ b/kubernetes/apps/observability/overseerr-exporter/app/externalsecret.yaml @@ -0,0 +1,19 @@ +--- +apiVersion: external-secrets.io/v1beta1 +kind: ExternalSecret +metadata: + name: overseerr-exporter +spec: + secretStoreRef: + kind: ClusterSecretStore + name: onepassword + target: + name: overseerr-exporter-secret + creationPolicy: Owner + template: + engineVersion: v2 + data: + OVERSEERR_API_KEY: "{{ .OVERSEERR_API_KEY }}" + dataFrom: + - extract: + key: arr-apis diff --git a/kubernetes/apps/observability/overseerr-exporter/app/helmrelease.yaml b/kubernetes/apps/observability/overseerr-exporter/app/helmrelease.yaml new file mode 100644 index 000000000..e230de006 --- /dev/null +++ b/kubernetes/apps/observability/overseerr-exporter/app/helmrelease.yaml @@ -0,0 +1,80 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: &app overseerr-exporter +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + controllers: + overseerr-exporter: + annotations: + reloader.stakater.com/auto: "true" + containers: + app: + image: + repository: ghcr.io/willfantom/overseerr-exporter + tag: 1.2.1@sha256:b5cbff0fcd04a118190849b1ed92f51669109f766171106fc0b87f7a8562273b + args: + - --overseerr.address + - http://overseerr.media.svc.cluster.local:5055 + - --overseerr.api-key + - $(OVERSEERR_API_KEY) + envFrom: + - secretRef: + name: overseerr-exporter-secret + probes: + liveness: + enabled: true + readiness: + enabled: true + resources: + requests: + cpu: 10m + limits: + memory: 128Mi + securityContext: + allowPrivilegeEscalation: false + readOnlyRootFilesystem: true + capabilities: + drop: + - ALL + defaultPodOptions: + dnsConfig: + options: + - name: ndots + value: "1" + securityContext: + runAsNonRoot: true + runAsUser: 568 + runAsGroup: 568 + service: + app: + controller: *app + ports: + http: + port: 9850 + serviceMonitor: + app: + serviceName: *app + endpoints: + - port: http + scheme: http + path: /metrics + interval: 1h + scrapeTimeout: 1m diff --git a/kubernetes/apps/observability/overseerr-exporter/app/kustomization.yaml b/kubernetes/apps/observability/overseerr-exporter/app/kustomization.yaml new file mode 100644 index 000000000..2708f09ee --- /dev/null +++ b/kubernetes/apps/observability/overseerr-exporter/app/kustomization.yaml @@ -0,0 +1,6 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./externalsecret.yaml + - ./helmrelease.yaml diff --git a/kubernetes/apps/observability/overseerr-exporter/ks.yaml b/kubernetes/apps/observability/overseerr-exporter/ks.yaml new file mode 100644 index 000000000..debe01133 --- /dev/null +++ b/kubernetes/apps/observability/overseerr-exporter/ks.yaml @@ -0,0 +1,21 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: overseerr-exporter + namespace: flux-system +spec: + targetNamespace: observability + dependsOn: + - name: overseerr + - name: prometheus-operator-crds + - name: external-secrets-secretstores + path: ./kubernetes/apps/observability/overseerr-exporter/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/observability/prometheus-operator-crds/app/helmrelease.yaml b/kubernetes/apps/observability/prometheus-operator-crds/app/helmrelease.yaml new file mode 100644 index 000000000..1a8e3442f --- /dev/null +++ b/kubernetes/apps/observability/prometheus-operator-crds/app/helmrelease.yaml @@ -0,0 +1,22 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: prometheus-operator-crds +spec: + interval: 30m + chart: + spec: + chart: prometheus-operator-crds + version: 12.0.0 + sourceRef: + kind: HelmRepository + name: prometheus-community + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 diff --git a/kubernetes/apps/observability/prometheus-operator-crds/app/kustomization.yaml b/kubernetes/apps/observability/prometheus-operator-crds/app/kustomization.yaml new file mode 100644 index 000000000..5dd7baca7 --- /dev/null +++ b/kubernetes/apps/observability/prometheus-operator-crds/app/kustomization.yaml @@ -0,0 +1,5 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml diff --git a/kubernetes/apps/observability/prometheus-operator-crds/ks.yaml b/kubernetes/apps/observability/prometheus-operator-crds/ks.yaml new file mode 100644 index 000000000..19ed2ef9e --- /dev/null +++ b/kubernetes/apps/observability/prometheus-operator-crds/ks.yaml @@ -0,0 +1,20 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app prometheus-operator-crds + namespace: flux-system +spec: + targetNamespace: observability + commonMetadata: + labels: + app.kubernetes.io/name: *app + path: ./kubernetes/apps/observability/prometheus-operator-crds/app + prune: false # never should be deleted + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/observability/prowlarr-exporter/app/externalsecret.yaml b/kubernetes/apps/observability/prowlarr-exporter/app/externalsecret.yaml new file mode 100644 index 000000000..c6935b8aa --- /dev/null +++ b/kubernetes/apps/observability/prowlarr-exporter/app/externalsecret.yaml @@ -0,0 +1,19 @@ +--- +apiVersion: external-secrets.io/v1beta1 +kind: ExternalSecret +metadata: + name: prowlarr-exporter +spec: + secretStoreRef: + kind: ClusterSecretStore + name: onepassword + target: + name: prowlarr-exporter-secret + creationPolicy: Owner + template: + engineVersion: v2 + data: + APIKEY: "{{ .PROWLARR_API_KEY }}" + dataFrom: + - extract: + key: arr-apis diff --git a/kubernetes/apps/observability/prowlarr-exporter/app/helmrelease.yaml b/kubernetes/apps/observability/prowlarr-exporter/app/helmrelease.yaml new file mode 100644 index 000000000..5666759d7 --- /dev/null +++ b/kubernetes/apps/observability/prowlarr-exporter/app/helmrelease.yaml @@ -0,0 +1,81 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: &app prowlarr-exporter +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + controllers: + prowlarr-exporter: + annotations: + reloader.stakater.com/auto: "true" + containers: + app: + image: + repository: ghcr.io/onedr0p/exportarr + tag: v2.0.1@sha256:727e7bc8f2f0934a2117978c59f4476b954018b849a010ea6cfb380bd6539644 + args: + - prowlarr + - --enable-additional-metrics + env: + PORT: &port 9707 + URL: http://thiazi.home:9696 + envFrom: + - secretRef: + name: prowlarr-exporter-secret + probes: + liveness: + enabled: true + readiness: + enabled: true + resources: + requests: + cpu: 10m + limits: + memory: 128Mi + securityContext: + allowPrivilegeEscalation: false + readOnlyRootFilesystem: true + capabilities: + drop: + - ALL + defaultPodOptions: + dnsConfig: + options: + - name: ndots + value: "1" + securityContext: + runAsNonRoot: true + runAsUser: 568 + runAsGroup: 568 + service: + app: + controller: *app + ports: + http: + port: *port + serviceMonitor: + app: + serviceName: *app + endpoints: + - port: http + scheme: http + path: /metrics + interval: 1m + scrapeTimeout: 10s diff --git a/kubernetes/apps/observability/prowlarr-exporter/app/kustomization.yaml b/kubernetes/apps/observability/prowlarr-exporter/app/kustomization.yaml new file mode 100644 index 000000000..2708f09ee --- /dev/null +++ b/kubernetes/apps/observability/prowlarr-exporter/app/kustomization.yaml @@ -0,0 +1,6 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./externalsecret.yaml + - ./helmrelease.yaml diff --git a/kubernetes/apps/observability/prowlarr-exporter/ks.yaml b/kubernetes/apps/observability/prowlarr-exporter/ks.yaml new file mode 100644 index 000000000..a5b60571e --- /dev/null +++ b/kubernetes/apps/observability/prowlarr-exporter/ks.yaml @@ -0,0 +1,20 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: prowlarr-exporter + namespace: flux-system +spec: + targetNamespace: observability + dependsOn: + - name: prometheus-operator-crds + - name: external-secrets-secretstores + path: ./kubernetes/apps/observability/prowlarr-exporter/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/observability/radarr-exporter/app/externalsecret.yaml b/kubernetes/apps/observability/radarr-exporter/app/externalsecret.yaml new file mode 100644 index 000000000..5c3468f1f --- /dev/null +++ b/kubernetes/apps/observability/radarr-exporter/app/externalsecret.yaml @@ -0,0 +1,19 @@ +--- +apiVersion: external-secrets.io/v1beta1 +kind: ExternalSecret +metadata: + name: radarr-exporter +spec: + secretStoreRef: + kind: ClusterSecretStore + name: onepassword + target: + name: radarr-exporter-secret + creationPolicy: Owner + template: + engineVersion: v2 + data: + APIKEY: "{{ .RADARR_API_KEY }}" + dataFrom: + - extract: + key: arr-apis diff --git a/kubernetes/apps/observability/radarr-exporter/app/helmrelease.yaml b/kubernetes/apps/observability/radarr-exporter/app/helmrelease.yaml new file mode 100644 index 000000000..efa437528 --- /dev/null +++ b/kubernetes/apps/observability/radarr-exporter/app/helmrelease.yaml @@ -0,0 +1,82 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: &app radarr-exporter +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + controllers: + radarr-exporter: + annotations: + reloader.stakater.com/auto: "true" + containers: + app: + image: + repository: ghcr.io/onedr0p/exportarr + tag: v2.0.1@sha256:727e7bc8f2f0934a2117978c59f4476b954018b849a010ea6cfb380bd6539644 + args: + - radarr + - --enable-additional-metrics + - --enable-unknown-queue-items + env: + PORT: &port 9707 + URL: http://thiazi.home:7878 + envFrom: + - secretRef: + name: radarr-exporter-secret + probes: + liveness: + enabled: true + readiness: + enabled: true + resources: + requests: + cpu: 10m + limits: + memory: 128Mi + securityContext: + allowPrivilegeEscalation: false + readOnlyRootFilesystem: true + capabilities: + drop: + - ALL + defaultPodOptions: + dnsConfig: + options: + - name: ndots + value: "1" + securityContext: + runAsNonRoot: true + runAsUser: 568 + runAsGroup: 568 + service: + app: + controller: *app + ports: + http: + port: *port + serviceMonitor: + app: + serviceName: *app + endpoints: + - port: http + scheme: http + path: /metrics + interval: 1h + scrapeTimeout: 1m diff --git a/kubernetes/apps/observability/radarr-exporter/app/kustomization.yaml b/kubernetes/apps/observability/radarr-exporter/app/kustomization.yaml new file mode 100644 index 000000000..2708f09ee --- /dev/null +++ b/kubernetes/apps/observability/radarr-exporter/app/kustomization.yaml @@ -0,0 +1,6 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./externalsecret.yaml + - ./helmrelease.yaml diff --git a/kubernetes/apps/observability/radarr-exporter/ks.yaml b/kubernetes/apps/observability/radarr-exporter/ks.yaml new file mode 100644 index 000000000..96481f4a1 --- /dev/null +++ b/kubernetes/apps/observability/radarr-exporter/ks.yaml @@ -0,0 +1,20 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: radarr-exporter + namespace: flux-system +spec: + targetNamespace: observability + dependsOn: + - name: prometheus-operator-crds + - name: external-secrets-secretstores + path: ./kubernetes/apps/observability/radarr-exporter/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/observability/sabnzbd-exporter/app/externalsecret.yaml b/kubernetes/apps/observability/sabnzbd-exporter/app/externalsecret.yaml new file mode 100644 index 000000000..c2c97f3be --- /dev/null +++ b/kubernetes/apps/observability/sabnzbd-exporter/app/externalsecret.yaml @@ -0,0 +1,19 @@ +--- +apiVersion: external-secrets.io/v1beta1 +kind: ExternalSecret +metadata: + name: sabnzbd-exporter +spec: + secretStoreRef: + kind: ClusterSecretStore + name: onepassword + target: + name: sabnzbd-exporter-secret + creationPolicy: Owner + template: + engineVersion: v2 + data: + APIKEY: "{{ .SABNZBD_API_KEY }}" + dataFrom: + - extract: + key: arr-apis diff --git a/kubernetes/apps/observability/sabnzbd-exporter/app/helmrelease.yaml b/kubernetes/apps/observability/sabnzbd-exporter/app/helmrelease.yaml new file mode 100644 index 000000000..2dc1ce592 --- /dev/null +++ b/kubernetes/apps/observability/sabnzbd-exporter/app/helmrelease.yaml @@ -0,0 +1,80 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: &app sabnzbd-exporter +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + controllers: + sabnzbd-exporter: + annotations: + reloader.stakater.com/auto: "true" + containers: + app: + image: + repository: ghcr.io/onedr0p/exportarr + tag: v2.0.1@sha256:727e7bc8f2f0934a2117978c59f4476b954018b849a010ea6cfb380bd6539644 + args: + - sabnzbd + env: + PORT: &port 9712 + URL: http://thiazi.home:8080 + envFrom: + - secretRef: + name: sabnzbd-exporter-secret + probes: + liveness: + enabled: true + readiness: + enabled: true + resources: + requests: + cpu: 10m + limits: + memory: 128Mi + securityContext: + allowPrivilegeEscalation: false + readOnlyRootFilesystem: true + capabilities: + drop: + - ALL + defaultPodOptions: + dnsConfig: + options: + - name: ndots + value: "1" + securityContext: + runAsNonRoot: true + runAsUser: 568 + runAsGroup: 568 + service: + app: + controller: *app + ports: + http: + port: *port + serviceMonitor: + app: + serviceName: *app + endpoints: + - port: http + scheme: http + path: /metrics + interval: 30s + scrapeTimeout: 10s diff --git a/kubernetes/apps/observability/sabnzbd-exporter/app/kustomization.yaml b/kubernetes/apps/observability/sabnzbd-exporter/app/kustomization.yaml new file mode 100644 index 000000000..2708f09ee --- /dev/null +++ b/kubernetes/apps/observability/sabnzbd-exporter/app/kustomization.yaml @@ -0,0 +1,6 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./externalsecret.yaml + - ./helmrelease.yaml diff --git a/kubernetes/apps/observability/sabnzbd-exporter/ks.yaml b/kubernetes/apps/observability/sabnzbd-exporter/ks.yaml new file mode 100644 index 000000000..598b3f5ce --- /dev/null +++ b/kubernetes/apps/observability/sabnzbd-exporter/ks.yaml @@ -0,0 +1,20 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: sabnzbd-exporter + namespace: flux-system +spec: + targetNamespace: observability + dependsOn: + - name: prometheus-operator-crds + - name: external-secrets-secretstores + path: ./kubernetes/apps/observability/sabnzbd-exporter/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/observability/sonarr-exporter/app/externalsecret.yaml b/kubernetes/apps/observability/sonarr-exporter/app/externalsecret.yaml new file mode 100644 index 000000000..754279d88 --- /dev/null +++ b/kubernetes/apps/observability/sonarr-exporter/app/externalsecret.yaml @@ -0,0 +1,19 @@ +--- +apiVersion: external-secrets.io/v1beta1 +kind: ExternalSecret +metadata: + name: sonarr-exporter +spec: + secretStoreRef: + kind: ClusterSecretStore + name: onepassword + target: + name: sonarr-exporter-secret + creationPolicy: Owner + template: + engineVersion: v2 + data: + APIKEY: "{{ .SONARR_API_KEY }}" + dataFrom: + - extract: + key: arr-apis diff --git a/kubernetes/apps/observability/sonarr-exporter/app/helmrelease.yaml b/kubernetes/apps/observability/sonarr-exporter/app/helmrelease.yaml new file mode 100644 index 000000000..ba3dd26a3 --- /dev/null +++ b/kubernetes/apps/observability/sonarr-exporter/app/helmrelease.yaml @@ -0,0 +1,82 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: &app sonarr-exporter +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + controllers: + sonarr-exporter: + annotations: + reloader.stakater.com/auto: "true" + containers: + app: + image: + repository: ghcr.io/onedr0p/exportarr + tag: v2.0.1@sha256:727e7bc8f2f0934a2117978c59f4476b954018b849a010ea6cfb380bd6539644 + args: + - sonarr + - --enable-additional-metrics + - --enable-unknown-queue-items + env: + PORT: &port 9707 + URL: http://thiazi.home:8989 + envFrom: + - secretRef: + name: sonarr-exporter-secret + probes: + liveness: + enabled: true + readiness: + enabled: true + resources: + requests: + cpu: 10m + limits: + memory: 128Mi + securityContext: + allowPrivilegeEscalation: false + readOnlyRootFilesystem: true + capabilities: + drop: + - ALL + defaultPodOptions: + dnsConfig: + options: + - name: ndots + value: "1" + securityContext: + runAsNonRoot: true + runAsUser: 568 + runAsGroup: 568 + service: + app: + controller: *app + ports: + http: + port: *port + serviceMonitor: + app: + serviceName: *app + endpoints: + - port: http + scheme: http + path: /metrics + interval: 1h + scrapeTimeout: 1m diff --git a/kubernetes/apps/observability/sonarr-exporter/app/kustomization.yaml b/kubernetes/apps/observability/sonarr-exporter/app/kustomization.yaml new file mode 100644 index 000000000..2708f09ee --- /dev/null +++ b/kubernetes/apps/observability/sonarr-exporter/app/kustomization.yaml @@ -0,0 +1,6 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./externalsecret.yaml + - ./helmrelease.yaml diff --git a/kubernetes/apps/observability/sonarr-exporter/ks.yaml b/kubernetes/apps/observability/sonarr-exporter/ks.yaml new file mode 100644 index 000000000..21d922740 --- /dev/null +++ b/kubernetes/apps/observability/sonarr-exporter/ks.yaml @@ -0,0 +1,20 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: sonarr-exporter + namespace: flux-system +spec: + targetNamespace: observability + dependsOn: + - name: prometheus-operator-crds + - name: external-secrets-secretstores + path: ./kubernetes/apps/observability/sonarr-exporter/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/observability/speedtest-exporter/app/helmrelease.yaml b/kubernetes/apps/observability/speedtest-exporter/app/helmrelease.yaml new file mode 100644 index 000000000..1816a770d --- /dev/null +++ b/kubernetes/apps/observability/speedtest-exporter/app/helmrelease.yaml @@ -0,0 +1,77 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: &app speedtest-exporter +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + controllers: + speedtest-exporter: + containers: + app: + image: + repository: ghcr.io/miguelndecarvalho/speedtest-exporter + tag: v3.5.4@sha256:f1064d49124c7fc45faabb87c6c876a2fd04e92b3dc14d4b871301217ba30fed + env: + SPEEDTEST_PORT: &port 9798 + probes: + liveness: + enabled: true + readiness: + enabled: true + resources: + requests: + cpu: 10m + limits: + memory: 128Mi + securityContext: + allowPrivilegeEscalation: false + readOnlyRootFilesystem: true + capabilities: + drop: + - ALL + defaultPodOptions: + dnsConfig: + options: + - name: ndots + value: "1" + securityContext: + runAsNonRoot: true + runAsUser: 568 + runAsGroup: 568 + persistence: + config: + type: emptyDir + globalMounts: + - path: /.config + service: + app: + controller: *app + ports: + http: + port: *port + serviceMonitor: + app: + serviceName: *app + endpoints: + - port: http + scheme: http + path: /metrics + interval: 60m + scrapeTimeout: 5m diff --git a/kubernetes/apps/observability/speedtest-exporter/app/kustomization.yaml b/kubernetes/apps/observability/speedtest-exporter/app/kustomization.yaml new file mode 100644 index 000000000..5dd7baca7 --- /dev/null +++ b/kubernetes/apps/observability/speedtest-exporter/app/kustomization.yaml @@ -0,0 +1,5 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml diff --git a/kubernetes/apps/observability/speedtest-exporter/ks.yaml b/kubernetes/apps/observability/speedtest-exporter/ks.yaml new file mode 100644 index 000000000..088b40981 --- /dev/null +++ b/kubernetes/apps/observability/speedtest-exporter/ks.yaml @@ -0,0 +1,19 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: speedtest-exporter + namespace: flux-system +spec: + targetNamespace: observability + path: ./kubernetes/apps/observability/speedtest-exporter/app + dependsOn: + - name: prometheus-operator-crds + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/observability/tautulli-exporter/app/externalsecret.yaml b/kubernetes/apps/observability/tautulli-exporter/app/externalsecret.yaml new file mode 100644 index 000000000..c70250c9e --- /dev/null +++ b/kubernetes/apps/observability/tautulli-exporter/app/externalsecret.yaml @@ -0,0 +1,19 @@ +--- +apiVersion: external-secrets.io/v1beta1 +kind: ExternalSecret +metadata: + name: tautulli-exporter +spec: + secretStoreRef: + kind: ClusterSecretStore + name: onepassword + target: + name: tautulli-exporter-secret + creationPolicy: Owner + template: + engineVersion: v2 + data: + TAUTULLI_API_KEY: "{{ .TAUTULLI_API_KEY }}" + dataFrom: + - extract: + key: arr-apis diff --git a/kubernetes/apps/observability/tautulli-exporter/app/helmrelease.yaml b/kubernetes/apps/observability/tautulli-exporter/app/helmrelease.yaml new file mode 100644 index 000000000..50af6b6bc --- /dev/null +++ b/kubernetes/apps/observability/tautulli-exporter/app/helmrelease.yaml @@ -0,0 +1,78 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: &app tautulli-exporter +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + controllers: + tautulli-exporter: + annotations: + reloader.stakater.com/auto: "true" + containers: + app: + image: + repository: docker.io/nwalke/tautulli_exporter + tag: v0.1.0@sha256:36b53431ac19d8196e2b4431b98b221b3009c9d97dc3509bc229c7b569b23350 + env: + SERVE_PORT: &port 9487 + TAUTULLI_URI: http://thiazi.home:8181 + envFrom: + - secretRef: + name: tautulli-exporter-secret + probes: + liveness: + enabled: true + readiness: + enabled: true + resources: + requests: + cpu: 10m + limits: + memory: 128Mi + securityContext: + allowPrivilegeEscalation: false + readOnlyRootFilesystem: true + capabilities: + drop: + - ALL + defaultPodOptions: + dnsConfig: + options: + - name: ndots + value: "1" + securityContext: + runAsNonRoot: true + runAsUser: 568 + runAsGroup: 568 + service: + app: + controller: *app + ports: + http: + port: *port + serviceMonitor: + app: + serviceName: *app + endpoints: + - port: http + scheme: http + path: /metrics + interval: 1m + scrapeTimeout: 10s diff --git a/kubernetes/apps/observability/tautulli-exporter/app/kustomization.yaml b/kubernetes/apps/observability/tautulli-exporter/app/kustomization.yaml new file mode 100644 index 000000000..2708f09ee --- /dev/null +++ b/kubernetes/apps/observability/tautulli-exporter/app/kustomization.yaml @@ -0,0 +1,6 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./externalsecret.yaml + - ./helmrelease.yaml diff --git a/kubernetes/apps/observability/tautulli-exporter/ks.yaml b/kubernetes/apps/observability/tautulli-exporter/ks.yaml new file mode 100644 index 000000000..d6827054a --- /dev/null +++ b/kubernetes/apps/observability/tautulli-exporter/ks.yaml @@ -0,0 +1,21 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: tautulli-exporter + namespace: flux-system +spec: + targetNamespace: observability + dependsOn: + - name: tautulli + - name: prometheus-operator-crds + - name: external-secrets-secretstores + path: ./kubernetes/apps/observability/tautulli-exporter/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/openebs-system/kustomization.yaml b/kubernetes/apps/openebs-system/kustomization.yaml new file mode 100644 index 000000000..ca05ea8f4 --- /dev/null +++ b/kubernetes/apps/openebs-system/kustomization.yaml @@ -0,0 +1,6 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - namespace.yaml + - openebs/ks.yaml diff --git a/kubernetes/apps/openebs-system/namespace.yaml b/kubernetes/apps/openebs-system/namespace.yaml new file mode 100644 index 000000000..f173c6c9c --- /dev/null +++ b/kubernetes/apps/openebs-system/namespace.yaml @@ -0,0 +1,7 @@ +--- +apiVersion: v1 +kind: Namespace +metadata: + name: openebs-system + labels: + kustomize.toolkit.fluxcd.io/prune: disabled diff --git a/kubernetes/apps/openebs-system/openebs/app/helmrelease.yaml b/kubernetes/apps/openebs-system/openebs/app/helmrelease.yaml new file mode 100644 index 000000000..975bff303 --- /dev/null +++ b/kubernetes/apps/openebs-system/openebs/app/helmrelease.yaml @@ -0,0 +1,45 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: openebs +spec: + interval: 30m + chart: + spec: + chart: openebs + version: 4.0.1 + sourceRef: + kind: HelmRepository + name: openebs + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + engines: + local: + lvm: + enabled: false + zfs: + enabled: false + replicated: + mayastor: + enabled: false + openebs-crds: + csi: + volumeSnapshots: + enabled: false + localpv-provisioner: + localpv: + image: + registry: quay.io/ + hostpathClass: + enabled: true + name: openebs-hostpath + isDefaultClass: false + basePath: /var/openebs/local diff --git a/kubernetes/apps/openebs-system/openebs/app/kustomization.yaml b/kubernetes/apps/openebs-system/openebs/app/kustomization.yaml new file mode 100644 index 000000000..5dd7baca7 --- /dev/null +++ b/kubernetes/apps/openebs-system/openebs/app/kustomization.yaml @@ -0,0 +1,5 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml diff --git a/kubernetes/apps/openebs-system/openebs/ks.yaml b/kubernetes/apps/openebs-system/openebs/ks.yaml new file mode 100644 index 000000000..531f679ed --- /dev/null +++ b/kubernetes/apps/openebs-system/openebs/ks.yaml @@ -0,0 +1,20 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app openebs + namespace: flux-system +spec: + targetNamespace: openebs-system + commonMetadata: + labels: + app.kubernetes.io/name: *app + path: ./kubernetes/apps/openebs-system/openebs/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/productivity/kasm/app/ingress.yaml b/kubernetes/apps/productivity/kasm/app/ingress.yaml new file mode 100755 index 000000000..63df3e526 --- /dev/null +++ b/kubernetes/apps/productivity/kasm/app/ingress.yaml @@ -0,0 +1,35 @@ +--- +apiVersion: networking.k8s.io/v1 +kind: Ingress +metadata: + name: kasm + annotations: + external-dns.alpha.kubernetes.io/target: "external.${SECRET_DOMAIN}" + hajimari.io/enable: "true" + nginx.ingress.kubernetes.io/backend-protocol: "HTTPS" + nginx.ingress.kubernetes.io/proxy-ssl-verify: "off" + # hajimari.io/icon: printer-3d-nozzle + # nginx.ingress.kubernetes.io/auth-method: GET + # nginx.ingress.kubernetes.io/auth-url: https://auth.${SECRET_DOMAIN}/api/verify + # nginx.ingress.kubernetes.io/auth-signin: https://auth.${SECRET_DOMAIN}?rm=$request_method + # nginx.ingress.kubernetes.io/auth-response-headers: Remote-User,Remote-Name,Remote-Groups,Remote-Email + # nginx.ingress.kubernetes.io/auth-snippet: | + # proxy_set_header X-Forwarded-Method $request_method; + # proxy_set_header X-Forwarded-Scheme $scheme; +spec: + ingressClassName: external + tls: + - secretName: ${SECRET_DOMAIN/./-}-production-tls + hosts: + - kasm.${SECRET_DOMAIN} + rules: + - host: kasm.${SECRET_DOMAIN} + http: + paths: + - path: / + pathType: Prefix + backend: + service: + name: kasm + port: + number: 443 diff --git a/kubernetes/apps/productivity/kasm/app/kustomization.yaml b/kubernetes/apps/productivity/kasm/app/kustomization.yaml new file mode 100755 index 000000000..af1460d38 --- /dev/null +++ b/kubernetes/apps/productivity/kasm/app/kustomization.yaml @@ -0,0 +1,8 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +namespace: productivity +resources: + - ingress.yaml + - service.yaml diff --git a/kubernetes/apps/productivity/kasm/app/service.yaml b/kubernetes/apps/productivity/kasm/app/service.yaml new file mode 100755 index 000000000..b686313d0 --- /dev/null +++ b/kubernetes/apps/productivity/kasm/app/service.yaml @@ -0,0 +1,17 @@ +--- +apiVersion: v1 +kind: Service +metadata: + name: kasm + # annotations: + # traefik.ingress.kubernetes.io/service.serversscheme: https + # traefik.ingress.kubernetes.io/service.serverstransport: networking-insecureskipverify@kubernetescrd +spec: + externalName: kasm.vm.tdeutsch.ch + ports: + - name: https + port: 443 + protocol: TCP + targetPort: 443 + sessionAffinity: None + type: ExternalName diff --git a/kubernetes/apps/productivity/kasm/ks.yaml b/kubernetes/apps/productivity/kasm/ks.yaml new file mode 100644 index 000000000..4a348df6e --- /dev/null +++ b/kubernetes/apps/productivity/kasm/ks.yaml @@ -0,0 +1,21 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/kustomize.toolkit.fluxcd.io/kustomization_v1.json +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app kasm + namespace: flux-system +spec: + commonMetadata: + labels: + app.kubernetes.io/name: *app + targetNamespace: productivity + path: ./kubernetes/apps/productivity/kasm/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/productivity/kustomization.yaml b/kubernetes/apps/productivity/kustomization.yaml new file mode 100644 index 000000000..09e9eb089 --- /dev/null +++ b/kubernetes/apps/productivity/kustomization.yaml @@ -0,0 +1,10 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - namespace.yaml + - kasm/ks.yaml + - linkding/ks.yaml + - octoprint/ks.yaml + - paperless/ks.yaml + - webtrees/ks.yaml diff --git a/kubernetes/apps/productivity/linkding/app/externalsecret.yaml b/kubernetes/apps/productivity/linkding/app/externalsecret.yaml new file mode 100644 index 000000000..8997dc4b4 --- /dev/null +++ b/kubernetes/apps/productivity/linkding/app/externalsecret.yaml @@ -0,0 +1,27 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/external-secrets.io/externalsecret_v1beta1.json +apiVersion: external-secrets.io/v1beta1 +kind: ExternalSecret +metadata: + name: linkding-secrets +spec: + secretStoreRef: + kind: ClusterSecretStore + name: onepassword + target: + name: linkding-secrets + template: + engineVersion: v2 + data: + litestream-minio-id: "{{ .AWS_ACCESS_KEY_ID }}" + litestream-minio-key: "{{ .AWS_SECRET_ACCESS_KEY }}" + litestream-minio-endpoint: "http://{{ .BUCKET_HOST }}" + litestream-minio-bucket: "litestream" + litestream-age-pubkey: "{{ .LITESTREAM_AGE_PUBKEY }}" + litestream-age-secret: "{{ .LITESTREAM_AGE_SECRET }}" + + dataFrom: + - extract: + key: litestream-age + - extract: + key: minio-lab diff --git a/kubernetes/apps/productivity/linkding/app/helmrelease.yaml b/kubernetes/apps/productivity/linkding/app/helmrelease.yaml new file mode 100644 index 000000000..7e4492f40 --- /dev/null +++ b/kubernetes/apps/productivity/linkding/app/helmrelease.yaml @@ -0,0 +1,190 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: &app linkding +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + controllers: + app: + annotations: + reloader.stakater.com/auto: "true" + pod: + enableServiceLinks: false + containers: + main: + image: + repository: sissbruecker/linkding + tag: 1.30.0 + resources: + requests: + cpu: 12m + memory: 64M + limits: + memory: 256M + env: + TZ: ${TIMEZONE} + LD_SUPERUSER_NAME: tdeutsch + LD_ENABLE_AUTH_PROXY: "True" + LD_AUTH_PROXY_USERNAME_HEADER: "HTTP_REMOTE_USER" + LD_AUTH_PROXY_LOGOUT_URL: "https://auth.eighty-three.me/" + # to use a db see https://github.com/bjw-s/home-ops/blob/main/ kubernetes/apps/selfhosted/linkding/app/helmrelease.yaml + litestream: &ls + image: + repository: "docker.io/litestream/litestream" + tag: "0.3.13" + args: ["replicate"] + env: &lsenv + LITESTREAM_ACCESS_KEY_ID: + valueFrom: + secretKeyRef: + name: "linkding-secrets" + key: "litestream-minio-id" + LITESTREAM_SECRET_ACCESS_KEY: + valueFrom: + secretKeyRef: + name: "linkding-secrets" + key: "litestream-minio-key" + MINIO_ENDPOINT: + valueFrom: + secretKeyRef: + name: "linkding-secrets" + key: "litestream-minio-endpoint" + MINIO_BUCKET: + valueFrom: + secretKeyRef: + name: "linkding-secrets" + key: "litestream-minio-bucket" + AGE_PUBKEY: + valueFrom: + secretKeyRef: + name: "linkding-secrets" + key: "litestream-age-pubkey" + resources: + requests: + cpu: 10m + memory: 128Mi + limits: + memory: 1024Mi + initContainers: + 01-litestream-restore: + <<: *ls + args: + [ + "restore", + "-if-db-not-exists", + "-if-replica-exists", + "/etc/linkding/data/db.sqlite3", + ] + env: + <<: *lsenv + AGE_SECRET: + valueFrom: + secretKeyRef: + name: "linkding-secrets" + key: "litestream-age-secret" + service: + app: + controller: app + ports: + http: + port: &port 9090 + ingress: + app: + enabled: true + className: external + annotations: + nginx.ingress.kubernetes.io/auth-method: GET + nginx.ingress.kubernetes.io/auth-url: https://auth.${SECRET_DOMAIN}/api/verify + nginx.ingress.kubernetes.io/auth-signin: https://auth.${SECRET_DOMAIN}?rm=$request_method + nginx.ingress.kubernetes.io/auth-response-headers: Remote-User,Remote-Name,Remote-Groups,Remote-Email + nginx.ingress.kubernetes.io/auth-snippet: | + proxy_set_header X-Forwarded-Method $request_method; + proxy_set_header X-Forwarded-Scheme $scheme; + external-dns.alpha.kubernetes.io/target: "external.${SECRET_DOMAIN}" + hajimari.io/icon: "mdi:link-variant" + hosts: + - host: &host "{{ .Release.Name }}.${SECRET_DOMAIN}" + paths: + - path: / + pathType: Prefix + service: + identifier: app + port: *port + tls: + - hosts: + - *host + secretName: ${SECRET_DOMAIN/./-}-production-tls + persistence: + data: + enabled: true + type: persistentVolumeClaim + accessMode: ReadWriteOnce + size: 5Gi + storageClass: ${MAIN_SC} + globalMounts: + - path: /etc/linkding/data + config: + enabled: true + type: configMap + name: "linkding-config" + advancedMounts: + app: + litestream: + - &lsmnt + subPath: "litestream-replicate" + path: "/etc/litestream.yml" + readOnly: true + 01-litestream-restore: + - <<: *lsmnt + subPath: "litestream-restore" + configMaps: + config: + enabled: true + data: + litestream-replicate: | + dbs: + - path: /etc/linkding/data/db.sqlite3 + replicas: + - name: "minio" + type: "s3" + endpoint: "$${MINIO_ENDPOINT}" + bucket: "$${MINIO_BUCKET}" + path: "linkding" + force-path-style: true + retention: 168h + validation-interval: 24h + age: + recipients: + - $${AGE_PUBKEY} + litestream-restore: | + dbs: + - path: /etc/linkding/data/db.sqlite3 + replicas: + - name: "minio" + type: "s3" + endpoint: "$${MINIO_ENDPOINT}" + bucket: "$${MINIO_BUCKET}" + path: "linkding" + force-path-style: true + retention: 168h + validation-interval: 24h + age: + identities: + - $${AGE_SECRET} diff --git a/kubernetes/apps/productivity/linkding/app/kustomization.yaml b/kubernetes/apps/productivity/linkding/app/kustomization.yaml new file mode 100644 index 000000000..a530998cf --- /dev/null +++ b/kubernetes/apps/productivity/linkding/app/kustomization.yaml @@ -0,0 +1,7 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml + - ./externalsecret.yaml diff --git a/kubernetes/apps/productivity/linkding/ks.yaml b/kubernetes/apps/productivity/linkding/ks.yaml new file mode 100644 index 000000000..ec527f7b2 --- /dev/null +++ b/kubernetes/apps/productivity/linkding/ks.yaml @@ -0,0 +1,23 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/kustomize.toolkit.fluxcd.io/kustomization_v1.json +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app linkding + namespace: flux-system +spec: + commonMetadata: + labels: + app.kubernetes.io/name: *app + targetNamespace: productivity + dependsOn: + - name: external-secrets-secretstores + path: ./kubernetes/apps/productivity/linkding/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/productivity/namespace.yaml b/kubernetes/apps/productivity/namespace.yaml new file mode 100644 index 000000000..92638dea0 --- /dev/null +++ b/kubernetes/apps/productivity/namespace.yaml @@ -0,0 +1,7 @@ +--- +apiVersion: v1 +kind: Namespace +metadata: + name: productivity + labels: + kustomize.toolkit.fluxcd.io/prune: disabled diff --git a/kubernetes/apps/productivity/octoprint/app/ingress.yaml b/kubernetes/apps/productivity/octoprint/app/ingress.yaml new file mode 100755 index 000000000..9685b37e8 --- /dev/null +++ b/kubernetes/apps/productivity/octoprint/app/ingress.yaml @@ -0,0 +1,33 @@ +--- +apiVersion: networking.k8s.io/v1 +kind: Ingress +metadata: + name: octoprint + annotations: + external-dns.alpha.kubernetes.io/target: "external.${SECRET_DOMAIN}" + hajimari.io/enable: "true" + hajimari.io/icon: printer-3d-nozzle + # nginx.ingress.kubernetes.io/auth-method: GET + # nginx.ingress.kubernetes.io/auth-url: https://auth.${SECRET_DOMAIN}/api/verify + # nginx.ingress.kubernetes.io/auth-signin: https://auth.${SECRET_DOMAIN}?rm=$request_method + # nginx.ingress.kubernetes.io/auth-response-headers: Remote-User,Remote-Name,Remote-Groups,Remote-Email + # nginx.ingress.kubernetes.io/auth-snippet: | + # proxy_set_header X-Forwarded-Method $request_method; + # proxy_set_header X-Forwarded-Scheme $scheme; +spec: + ingressClassName: external + tls: + - secretName: ${SECRET_DOMAIN/./-}-production-tls + hosts: + - print.${SECRET_DOMAIN} + rules: + - host: print.${SECRET_DOMAIN} + http: + paths: + - path: / + pathType: Prefix + backend: + service: + name: octoprint + port: + number: 80 diff --git a/kubernetes/apps/productivity/octoprint/app/kustomization.yaml b/kubernetes/apps/productivity/octoprint/app/kustomization.yaml new file mode 100755 index 000000000..af1460d38 --- /dev/null +++ b/kubernetes/apps/productivity/octoprint/app/kustomization.yaml @@ -0,0 +1,8 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +namespace: productivity +resources: + - ingress.yaml + - service.yaml diff --git a/kubernetes/apps/productivity/octoprint/app/service.yaml b/kubernetes/apps/productivity/octoprint/app/service.yaml new file mode 100755 index 000000000..5f6664ab9 --- /dev/null +++ b/kubernetes/apps/productivity/octoprint/app/service.yaml @@ -0,0 +1,14 @@ +--- +apiVersion: v1 +kind: Service +metadata: + name: octoprint +spec: + externalName: octopi.home + ports: + - name: http + port: 80 + protocol: TCP + targetPort: 80 + sessionAffinity: None + type: ExternalName diff --git a/kubernetes/apps/productivity/octoprint/ks.yaml b/kubernetes/apps/productivity/octoprint/ks.yaml new file mode 100644 index 000000000..0f5126668 --- /dev/null +++ b/kubernetes/apps/productivity/octoprint/ks.yaml @@ -0,0 +1,21 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/kustomize.toolkit.fluxcd.io/kustomization_v1.json +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app octoprint + namespace: flux-system +spec: + commonMetadata: + labels: + app.kubernetes.io/name: *app + targetNamespace: productivity + path: ./kubernetes/apps/productivity/octoprint/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/productivity/paperless/app/helmrelease-gotenberg.yaml b/kubernetes/apps/productivity/paperless/app/helmrelease-gotenberg.yaml new file mode 100644 index 000000000..d86aa7a9b --- /dev/null +++ b/kubernetes/apps/productivity/paperless/app/helmrelease-gotenberg.yaml @@ -0,0 +1,40 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: paperless-gotenberg +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + controllers: + app: + annotations: + reloader.stakater.com/auto: "true" + containers: + main: + image: + repository: docker.io/gotenberg/gotenberg + tag: 8.6.0 + env: + DISABLE_GOOGLE_CHROME: "1" + service: + app: + controller: app + ports: + http: + port: 3000 diff --git a/kubernetes/apps/productivity/paperless/app/helmrelease-tika.yaml b/kubernetes/apps/productivity/paperless/app/helmrelease-tika.yaml new file mode 100644 index 000000000..91a8f0fac --- /dev/null +++ b/kubernetes/apps/productivity/paperless/app/helmrelease-tika.yaml @@ -0,0 +1,38 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: paperless-tika +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + controllers: + app: + annotations: + reloader.stakater.com/auto: "true" + containers: + main: + image: + repository: ghcr.io/paperless-ngx/tika + tag: 2.9.1-full + service: + app: + controller: app + ports: + http: + port: 9998 diff --git a/kubernetes/apps/productivity/paperless/app/helmrelease.yaml b/kubernetes/apps/productivity/paperless/app/helmrelease.yaml new file mode 100644 index 000000000..b98a35861 --- /dev/null +++ b/kubernetes/apps/productivity/paperless/app/helmrelease.yaml @@ -0,0 +1,143 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: paperless +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + dependsOn: + - name: paperless-gotenberg + namespace: productivity + - name: paperless-tika + namespace: productivity + values: + controllers: + app: + annotations: + reloader.stakater.com/auto: "true" + containers: + main: + image: + repository: ghcr.io/paperless-ngx/paperless-ngx + tag: 2.9.0 + env: + PAPERLESS_SECRET_KEY: + valueFrom: + secretKeyRef: + name: paperless-secret + key: PAPERLESS_SECRET_KEY + PAPERLESS_URL: https://{{ .Release.Name }}.${SECRET_DOMAIN} + PAPERLESS_PORT: "8080" + PAPERLESS_TIME_ZONE: ${TIMEZONE} + PAPERLESS_WEBSERVER_WORKERS: "1" + PAPERLESS_TASK_WORKERS: "1" + PAPERLESS_TIKA_ENABLED: "1" + PAPERLESS_TIKA_GOTENBERG_ENDPOINT: http://paperless-gotenberg:3000 + PAPERLESS_TIKA_ENDPOINT: http://paperless-tika:9998 + PAPERLESS_FILENAME_FORMAT: + "{created_year}/{correspondent}/{created_year}-{created_month}-{created_day} + {title}" + # Configure Remote User auth + PAPERLESS_ENABLE_HTTP_REMOTE_USER: "true" + # Configure folders + PAPERLESS_CONSUMPTION_DIR: /nfs/consume + PAPERLESS_DATA_DIR: /nfs/data + PAPERLESS_EXPORT_DIR: /nfs/export + PAPERLESS_MEDIA_ROOT: /nfs/media + # Configure folder importer + PAPERLESS_CONSUMER_POLLING: "60" + PAPERLESS_CONSUMER_RECURSIVE: "true" + PAPERLESS_CONSUMER_SUBDIRS_AS_TAGS: "true" + # Configure OCR + PAPERLESS_OCR_LANGUAGES: deu eng + PAPERLESS_OCR_LANGUAGE: deu+eng + PAPERLESS_OCR_MODE: skip + PAPERLESS_OCR_USER_ARGS: '{"invalidate_digital_signatures": true}' + #PAPERLESS_OCR_SKIP_ARCHIVE_FILE: with_text + # Configure redis integration + PAPERLESS_REDIS: redis://paperless-redis:6379 + # Configure admin user + PAPERLESS_ADMIN_USER: + valueFrom: + secretKeyRef: + name: paperless-secret + key: PAPERLESS_ADMIN_USER + PAPERLESS_ADMIN_PASSWORD: + valueFrom: + secretKeyRef: + name: paperless-secret + key: PAPERLESS_ADMIN_PASSWORD + resources: + requests: + cpu: 500m + memory: 700M + limits: + memory: 2000M + service: + app: + controller: app + ports: + http: + port: &port 8080 + ingress: + app: + enabled: true + className: internal + annotations: + hajimari.io/icon: material-symbols:scanner-outline + nginx.ingress.kubernetes.io/auth-method: GET + nginx.ingress.kubernetes.io/auth-url: https://auth.${SECRET_DOMAIN}/api/verify + nginx.ingress.kubernetes.io/auth-signin: https://auth.${SECRET_DOMAIN}?rm=$request_method + nginx.ingress.kubernetes.io/auth-response-headers: Remote-User,Remote-Name,Remote-Groups,Remote-Email + nginx.ingress.kubernetes.io/auth-snippet: | + proxy_set_header X-Forwarded-Method $request_method; + proxy_set_header X-Forwarded-Scheme $scheme; + hosts: + - host: &host "{{ .Release.Name }}.${SECRET_DOMAIN}" + paths: + - path: / + pathType: Prefix + service: + identifier: app + port: http + tls: + - hosts: + - *host + secretName: ${SECRET_DOMAIN/./-}-production-tls + public: + enabled: true + className: external + annotations: + gatus.io/enabled: "false" + hosts: + - host: &host2 "documents.${SECRET_CH_DOMAIN}" + paths: + - path: /share + pathType: Prefix + service: + identifier: app + port: http + tls: + - hosts: + - *host2 + secretName: ${SECRET_CH_DOMAIN/./-}-production-tls + persistence: + nfs: + type: nfs + server: 10.20.30.40 + path: /volume2/scanner diff --git a/kubernetes/apps/productivity/paperless/app/kustomization.yaml b/kubernetes/apps/productivity/paperless/app/kustomization.yaml new file mode 100644 index 000000000..35816c6f3 --- /dev/null +++ b/kubernetes/apps/productivity/paperless/app/kustomization.yaml @@ -0,0 +1,8 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./secret.sops.yaml + - ./helmrelease.yaml + - ./helmrelease-gotenberg.yaml + - ./helmrelease-tika.yaml diff --git a/kubernetes/apps/productivity/paperless/app/secret.sops.yaml b/kubernetes/apps/productivity/paperless/app/secret.sops.yaml new file mode 100644 index 000000000..96d7b5dd7 --- /dev/null +++ b/kubernetes/apps/productivity/paperless/app/secret.sops.yaml @@ -0,0 +1,28 @@ +apiVersion: v1 +kind: Secret +metadata: + name: paperless-secret +stringData: + PAPERLESS_ADMIN_USER: ENC[AES256_GCM,data:jwQRqR7sCy0=,iv:EiS5flZ7udBl43sMMinuBk19/rt611QxZOameKLxk+0=,tag:svdAj6UPnXYu4EnLnEntQg==,type:str] + PAPERLESS_ADMIN_PASSWORD: ENC[AES256_GCM,data:KOjXQVEjwD8G7wTOB7RjTAZIANUawJboywmq8mER/6x/XCYMrLj8Dtrype+H0o76lTQ=,iv:SYFJZ6rwgAtqZ07RA2ccEZJ/1GmevOVprsXUmbdIEKk=,tag:gaU5UYXlCYDuNlXFGrgbzg==,type:str] + PAPERLESS_SECRET_KEY: ENC[AES256_GCM,data:hIAQGN3TBy+aQRPZHJ91fIi0/ZlnzmUZJqpdGW7RcSEDEB+DsRWZGw==,iv:6rDWsj8ahc9tQnpjzSzVGPInsGVe323X7HCGg6TbOG8=,tag:46lD4l4Clx7+3WD2dA8QIg==,type:str] +sops: + kms: [] + gcp_kms: [] + azure_kv: [] + hc_vault: [] + age: + - recipient: age1y0kzuf0tn94a74whazwae4r9qal4snuqfuhl5jacscrpr7up5gts74fe5w + enc: | + -----BEGIN AGE ENCRYPTED FILE----- + YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBPOGRIQmNTZDJaNUpDbWVq + bkwvbklvbkRpVE9RQytkeUNWamFsWUFzRzJBCk1qek5ueFBWYUF4NmptRTBqekxr + VXZDazhreHB6UnhGNXZzMTZwV0xxWkkKLS0tIERUQkhOUEhDellUWjNZRU9WU1Z0 + bWZUWDR1SUwvVnJ1SDAydXV6YS9Db3cKEygUxkjdTZjA9y7i0CHSGdfCrgGOXhp3 + 6+67/ce4guTnhNIxux7dOARTg3gjp4lVAbR4SZFkAbEIMOq1JU63aQ== + -----END AGE ENCRYPTED FILE----- + lastmodified: "2023-12-12T10:36:29Z" + mac: ENC[AES256_GCM,data:M+XOPvMJJK0GIRtE7iFhK854sVTgH+QFzkgYma6UyXUeaQhXqyF1T0Ecs/fmBzpjQNrVVKhmgvREc7zOICHGXmPC6qs+WxXuNKNnWpnZhJm/8UdsuDFUW2ew9CahZZKAUDKKL/J56ND/GfKg6bGpMde+j1XuEOAVM4Z2B51j8Ho=,iv:CC523CMBJbMKq1fQ5yTyEYuIxiHOq+DURdHVsuOidlM=,tag:Hiw79sOFXOEgn6pd76pgXA==,type:str] + pgp: [] + encrypted_regex: ^(data|stringData)$ + version: 3.8.1 diff --git a/kubernetes/apps/productivity/paperless/ks.yaml b/kubernetes/apps/productivity/paperless/ks.yaml new file mode 100644 index 000000000..25b898de7 --- /dev/null +++ b/kubernetes/apps/productivity/paperless/ks.yaml @@ -0,0 +1,42 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app paperless-redis + namespace: flux-system +spec: + targetNamespace: productivity + commonMetadata: + labels: + app.kubernetes.io/name: *app + path: ./kubernetes/apps/productivity/paperless/redis + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app paperless + namespace: flux-system +spec: + targetNamespace: productivity + commonMetadata: + labels: + app.kubernetes.io/name: *app + dependsOn: + - name: paperless-redis + path: ./kubernetes/apps/productivity/paperless/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/productivity/paperless/redis/helmrelease.yaml b/kubernetes/apps/productivity/paperless/redis/helmrelease.yaml new file mode 100644 index 000000000..e29b5c94c --- /dev/null +++ b/kubernetes/apps/productivity/paperless/redis/helmrelease.yaml @@ -0,0 +1,43 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: paperless-redis +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + controllers: + app: + containers: + main: + image: + repository: public.ecr.aws/docker/library/redis + tag: 7.2.5 + resources: + requests: + cpu: 5m + memory: 32M + limits: + memory: 32M + service: + app: + controller: app + ports: + redis: + enabled: true + port: 6379 diff --git a/kubernetes/apps/productivity/paperless/redis/kustomization.yaml b/kubernetes/apps/productivity/paperless/redis/kustomization.yaml new file mode 100644 index 000000000..5dd7baca7 --- /dev/null +++ b/kubernetes/apps/productivity/paperless/redis/kustomization.yaml @@ -0,0 +1,5 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml diff --git a/kubernetes/apps/productivity/webtrees/app/helmrelease.yaml b/kubernetes/apps/productivity/webtrees/app/helmrelease.yaml new file mode 100644 index 000000000..9f6d2ce2f --- /dev/null +++ b/kubernetes/apps/productivity/webtrees/app/helmrelease.yaml @@ -0,0 +1,137 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: webtrees + namespace: productivity +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + maxHistory: 2 + install: + crds: CreateReplace + createNamespace: true + remediation: + retries: 3 + upgrade: + crds: CreateReplace + cleanupOnFail: true + remediation: + retries: 3 + uninstall: + keepHistory: false + dependsOn: + - name: webtrees-db + values: + controllers: + app: + strategy: Recreate + initContainers: + 01-init-modules: + image: + repository: busybox + pullPolicy: Always + tag: latest + command: [ + sh, + -c, + cd /var/www/html/modules_v4/; wget https://github.com/JesseWebDotCom/webtrees-theme-modern/releases/download/0.0.9/webtrees-theme-modern.0.0.9.zip + -O /tmp/webtrees-theme-modern.0.0.9.zip; unzip /tmp/webtrees-theme-modern.0.0.9.zip; + rm -f /tmp/webtrees-theme-modern.0.0.9.zip, + ] + containers: + main: + image: + repository: docker.io/dtjs48jkt/webtrees + tag: 2.1.20 + env: + DISABLE_SSL: "TRUE" + PRETTYURLSl: "TRUE" + ENABLE_REMOTE_USER: "TRUE" + HEADER_AUTH_VAR: Remote-User + PORT: "80" + BASE_URL: https://{{ .Release.Name }}.${SECRET_DOMAIN} + DB_HOST: webtrees-db-mariadb + DB_NAME: webtrees + DB_USER: webtrees + DB_PASSWORD: + valueFrom: + secretKeyRef: + name: mariadb-secret + key: mariadb-password + WT_ADMINPW: + valueFrom: + secretKeyRef: + name: webtrees-admin-pass + key: password + # probes: + # liveness: &probes + # enabled: true + # custom: true + # spec: + # httpGet: + # path: / + # port: *port + # initialDelaySeconds: 0 + # periodSeconds: 10 + # timeoutSeconds: 1 + # failureThreshold: 3 + # readiness: *probes + resources: + requests: + cpu: 5m + memory: 10Mi + limits: + memory: 500Mi + service: + app: + controller: app + ports: + http: + port: &port 80 + ingress: + app: + annotations: + nginx.ingress.kubernetes.io/auth-method: GET + nginx.ingress.kubernetes.io/auth-url: https://auth.${SECRET_DOMAIN}/api/verify + nginx.ingress.kubernetes.io/auth-signin: https://auth.${SECRET_DOMAIN}?rm=$request_method + nginx.ingress.kubernetes.io/auth-response-headers: Remote-User,Remote-Name,Remote-Groups,Remote-Email + nginx.ingress.kubernetes.io/auth-snippet: | + proxy_set_header X-Forwarded-Method $request_method; + proxy_set_header X-Forwarded-Scheme $scheme; + enabled: true + className: internal + hosts: + - host: &host "{{ .Release.Name }}.${SECRET_DOMAIN}" + paths: + - path: / + pathType: Prefix + service: + identifier: app + port: *port + tls: + - hosts: + - *host + persistence: + data: + enabled: true + type: persistentVolumeClaim + accessMode: ReadWriteOnce + size: 5Gi + storageClass: ${MAIN_SC} + globalMounts: + - path: /var/www/html/data + subPath: data + modules: + enabled: true + type: emptyDir + globalMounts: + - path: /var/www/html/modules_v4 + subPath: modules_v4 diff --git a/kubernetes/apps/productivity/webtrees/app/kustomization.yaml b/kubernetes/apps/productivity/webtrees/app/kustomization.yaml new file mode 100644 index 000000000..83346fd53 --- /dev/null +++ b/kubernetes/apps/productivity/webtrees/app/kustomization.yaml @@ -0,0 +1,8 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +namespace: productivity +resources: + - ./helmrelease.yaml + - secret.sops.yaml diff --git a/kubernetes/apps/productivity/webtrees/app/secret.sops.yaml b/kubernetes/apps/productivity/webtrees/app/secret.sops.yaml new file mode 100644 index 000000000..121d33319 --- /dev/null +++ b/kubernetes/apps/productivity/webtrees/app/secret.sops.yaml @@ -0,0 +1,26 @@ +apiVersion: v1 +kind: Secret +metadata: + name: webtrees-admin-pass +stringData: + password: ENC[AES256_GCM,data:6BRzjNC+WOZpG8s3,iv:UIpZKleh3hLQb9fPtjA8jz+YhD7e/Un7aOCoGQM0vzE=,tag:YJkW1/1Ea78JyF1q6qa66g==,type:str] +sops: + kms: [] + gcp_kms: [] + azure_kv: [] + hc_vault: [] + age: + - recipient: age1y0kzuf0tn94a74whazwae4r9qal4snuqfuhl5jacscrpr7up5gts74fe5w + enc: | + -----BEGIN AGE ENCRYPTED FILE----- + YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBPOGRIQmNTZDJaNUpDbWVq + bkwvbklvbkRpVE9RQytkeUNWamFsWUFzRzJBCk1qek5ueFBWYUF4NmptRTBqekxr + VXZDazhreHB6UnhGNXZzMTZwV0xxWkkKLS0tIERUQkhOUEhDellUWjNZRU9WU1Z0 + bWZUWDR1SUwvVnJ1SDAydXV6YS9Db3cKEygUxkjdTZjA9y7i0CHSGdfCrgGOXhp3 + 6+67/ce4guTnhNIxux7dOARTg3gjp4lVAbR4SZFkAbEIMOq1JU63aQ== + -----END AGE ENCRYPTED FILE----- + lastmodified: "2023-07-06T12:03:59Z" + mac: ENC[AES256_GCM,data:HgqRShiHLjWGG5qDgUQPe9Xu69YItk7i/g1qsYXm0XZcsgel/yu9YhhyxFyGcLOnS4W2c+jvvGfddExtZ2APVgenQfyGjhVCFkP7wkNCODkqR2c2xjnwoiHyyNGvHXazausdd/iILXjxIzUTe1oz8fxIGOocRAfpXt6HMCemRyk=,iv:69nAetjFY58TwI461MW28HbGC0raR9UidRc2+Uc+mxE=,tag:OEPsGnt9267aBPc+Ow+HEA==,type:str] + pgp: [] + encrypted_regex: ^(data|stringData)$ + version: 3.7.3 diff --git a/kubernetes/apps/productivity/webtrees/db/cronjob.yaml b/kubernetes/apps/productivity/webtrees/db/cronjob.yaml new file mode 100644 index 000000000..c6064194b --- /dev/null +++ b/kubernetes/apps/productivity/webtrees/db/cronjob.yaml @@ -0,0 +1,53 @@ +--- +apiVersion: batch/v1 +kind: CronJob +metadata: + name: webtrees-db-mariadb +spec: + suspend: false + schedule: "@daily" + concurrencyPolicy: Forbid + successfulJobsHistoryLimit: 1 + failedJobsHistoryLimit: 1 + jobTemplate: + spec: + template: + spec: + containers: + - name: alpine + image: alpine + env: + - name: DATABASES + value: webtrees + - name: MARIADB_HOST + value: webtrees-db-mariadb + - name: MARIADB_USER + value: root + - name: MYSQL_PWD + valueFrom: + secretKeyRef: + name: mariadb-secret + key: mariadb-root-password + command: + - /bin/sh + args: + - -c + - | + set -xe + DATE=$(date +%Y-%m-%d) + apk update + apk add mysql-client py-pip + mkdir -p /var/nfs/webtrees-db/$DATE + cd /var/nfs/webtrees-db + for DATABASE in $${DATABASES}; do + mysqldump -h $MARIADB_HOST -u $MARIADB_USER $DATABASE | gzip > $DATE/$DATABASE.sql.gz + done + volumeMounts: + - name: nfs-vol + mountPath: /var/nfs + restartPolicy: OnFailure + volumes: + - name: nfs-vol + nfs: + server: 10.20.30.40 + path: /volume2/data/backup/kubernetes diff --git a/kubernetes/apps/productivity/webtrees/db/helmrelease.yaml b/kubernetes/apps/productivity/webtrees/db/helmrelease.yaml new file mode 100644 index 000000000..b510a6cbe --- /dev/null +++ b/kubernetes/apps/productivity/webtrees/db/helmrelease.yaml @@ -0,0 +1,38 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: webtrees-db + namespace: productivity +spec: + interval: 30m + chart: + spec: + chart: mariadb + version: 18.2.2 + sourceRef: + kind: HelmRepository + name: bitnami + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + auth: + existingSecret: mariadb-secret + database: webtrees + username: webtrees + primary: + extraEnvVars: + - name: TZ + value: ${TIMEZONE} + - name: MYSQL_PASSWORD + value: $(MARIADB_ROOT_PASSWORD) + volumePermissions: + enabled: true + global: + storageClass: ${MAIN_SC} diff --git a/kubernetes/apps/productivity/webtrees/db/kustomization.yaml b/kubernetes/apps/productivity/webtrees/db/kustomization.yaml new file mode 100644 index 000000000..a20d4398a --- /dev/null +++ b/kubernetes/apps/productivity/webtrees/db/kustomization.yaml @@ -0,0 +1,9 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +namespace: productivity +resources: + - ./helmrelease.yaml + - cronjob.yaml + - secret.sops.yaml diff --git a/kubernetes/apps/productivity/webtrees/db/secret.sops.yaml b/kubernetes/apps/productivity/webtrees/db/secret.sops.yaml new file mode 100644 index 000000000..b04a00975 --- /dev/null +++ b/kubernetes/apps/productivity/webtrees/db/secret.sops.yaml @@ -0,0 +1,28 @@ +apiVersion: v1 +kind: Secret +metadata: + name: mariadb-secret +stringData: + mariadb-password: ENC[AES256_GCM,data:nNPB9rKCgg4TEt9T8KFk66wKV+bYkgNZSiZ/JB3U,iv:FTmlo2rrVvxsvlaMnwq4Uruu3C67TNBiPzNVmrkuqbU=,tag:PWPeoUwZN56egnCj3uUmmA==,type:str] + mariadb-root-password: ENC[AES256_GCM,data:A/wBQqbSJlEHngKw94VmFIqT7fI28q83L+Mwa/mP,iv:D6wGpLfhv2VYiZUa6SM7v/W5PL3mPwrp++DaRAUOJu4=,tag:q/L53cb3liEuLfa/IPS1Sw==,type:str] + mariadb-replication-password: ENC[AES256_GCM,data:vq/nUN/L3av+AUsJg1rs/7O7pUtbrLPXGrUS99Sr,iv:YshZjFEDUI2uejrUn+TtBoLmpfdJGJerYwat1H1XDFM=,tag:sO7py4jmlg0L/jPUQMU73g==,type:str] +sops: + kms: [] + gcp_kms: [] + azure_kv: [] + hc_vault: [] + age: + - recipient: age1y0kzuf0tn94a74whazwae4r9qal4snuqfuhl5jacscrpr7up5gts74fe5w + enc: | + -----BEGIN AGE ENCRYPTED FILE----- + YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBPOGRIQmNTZDJaNUpDbWVq + bkwvbklvbkRpVE9RQytkeUNWamFsWUFzRzJBCk1qek5ueFBWYUF4NmptRTBqekxr + VXZDazhreHB6UnhGNXZzMTZwV0xxWkkKLS0tIERUQkhOUEhDellUWjNZRU9WU1Z0 + bWZUWDR1SUwvVnJ1SDAydXV6YS9Db3cKEygUxkjdTZjA9y7i0CHSGdfCrgGOXhp3 + 6+67/ce4guTnhNIxux7dOARTg3gjp4lVAbR4SZFkAbEIMOq1JU63aQ== + -----END AGE ENCRYPTED FILE----- + lastmodified: "2023-07-06T17:00:15Z" + mac: ENC[AES256_GCM,data:H1Q4WDW2gkYUtqEARPCNEG0rNMI+ZZtIAoHYH7KSbi/s0esBFzRzPF6f6L1tU+C+Phhd73IKlmUY7XkkjZIZSsCMZh/X/gMlFIH9T7HZsCV8XhmXWPXwfXN1+HQp2wA6UxVq24BGV0r2ZXJmy5+HSanf90XGyRTPUlgmUE2j59A=,iv:R75EhMLD70DOjAmIBywChsl+bFvkC9Rp7ihUc6H2PAQ=,tag:km4UxZ1ZFwAHiBsH9nbrDg==,type:str] + pgp: [] + encrypted_regex: ^(data|stringData)$ + version: 3.7.3 diff --git a/kubernetes/apps/productivity/webtrees/ks.yaml b/kubernetes/apps/productivity/webtrees/ks.yaml new file mode 100644 index 000000000..1fd5c78b9 --- /dev/null +++ b/kubernetes/apps/productivity/webtrees/ks.yaml @@ -0,0 +1,46 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/kustomize.toolkit.fluxcd.io/kustomization_v1.json +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app webtrees + namespace: flux-system +spec: + commonMetadata: + labels: + app.kubernetes.io/name: *app + targetNamespace: productivity + dependsOn: + - name: webtrees-db + path: ./kubernetes/apps/productivity/webtrees/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false # no flux ks dependents + interval: 30m + retryInterval: 1m + timeout: 5m + +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/kustomize.toolkit.fluxcd.io/kustomization_v1.json +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app webtrees-db + namespace: flux-system +spec: + commonMetadata: + labels: + app.kubernetes.io/name: *app + targetNamespace: productivity + dependsOn: + path: ./kubernetes/apps/productivity/webtrees/db + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/security/external-secrets/ks.yaml b/kubernetes/apps/security/external-secrets/ks.yaml new file mode 100644 index 000000000..d96719fef --- /dev/null +++ b/kubernetes/apps/security/external-secrets/ks.yaml @@ -0,0 +1,44 @@ +--- +# yaml-language-server: $schema=https://raw.githubusercontent.com/fluxcd-community/flux2-schemas/main/kustomization-kustomize-v1.json +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app external-secrets-operator + namespace: flux-system +spec: + targetNamespace: security + commonMetadata: + labels: + app.kubernetes.io/name: *app + path: ./kubernetes/apps/security/external-secrets/operator + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m +--- +# yaml-language-server: $schema=https://raw.githubusercontent.com/fluxcd-community/flux2-schemas/main/kustomization-kustomize-v1.json +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app external-secrets-secretstores + namespace: flux-system +spec: + targetNamespace: security + commonMetadata: + labels: + app.kubernetes.io/name: *app + path: ./kubernetes/apps/security/external-secrets/secretstores + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + dependsOn: + - name: external-secrets-operator + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/security/external-secrets/operator/helmrelease.yaml b/kubernetes/apps/security/external-secrets/operator/helmrelease.yaml new file mode 100644 index 000000000..7b16cc974 --- /dev/null +++ b/kubernetes/apps/security/external-secrets/operator/helmrelease.yaml @@ -0,0 +1,33 @@ +--- +# yaml-language-server: $schema=https://raw.githubusercontent.com/fluxcd-community/flux2-schemas/main/helmrelease-helm-v2beta2.json +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: external-secrets +spec: + interval: 30m + chart: + spec: + chart: external-secrets + version: 0.9.19 + sourceRef: + kind: HelmRepository + name: external-secrets + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + installCRDs: true + serviceMonitor: + enabled: true + webhook: + serviceMonitor: + enabled: true + certController: + serviceMonitor: + enabled: true diff --git a/kubernetes/apps/security/external-secrets/operator/kustomization.yaml b/kubernetes/apps/security/external-secrets/operator/kustomization.yaml new file mode 100644 index 000000000..17cbc72b2 --- /dev/null +++ b/kubernetes/apps/security/external-secrets/operator/kustomization.yaml @@ -0,0 +1,6 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml diff --git a/kubernetes/apps/security/external-secrets/secretstores/doppler/kustomization.yaml b/kubernetes/apps/security/external-secrets/secretstores/doppler/kustomization.yaml new file mode 100644 index 000000000..0508dd04e --- /dev/null +++ b/kubernetes/apps/security/external-secrets/secretstores/doppler/kustomization.yaml @@ -0,0 +1,7 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./secret.sops.yaml + - ./secretstore.yaml diff --git a/kubernetes/apps/security/external-secrets/secretstores/doppler/secret.sops.yaml b/kubernetes/apps/security/external-secrets/secretstores/doppler/secret.sops.yaml new file mode 100644 index 000000000..cf5608600 --- /dev/null +++ b/kubernetes/apps/security/external-secrets/secretstores/doppler/secret.sops.yaml @@ -0,0 +1,26 @@ +apiVersion: v1 +stringData: + dopplerToken: ENC[AES256_GCM,data:g2iEL/9pvyVXWUkVYJYIEj3nmCZCaP2kMYqRmAfLPKgghoodu5CaaXENdIQIiUQ4GtUxDq08CXfyJs19mQ==,iv:6Y2p6v0szMQSGySlXKWNxf5gPIpPR1mHGhf4IV0JJl0=,tag:nDV7xs8vpmEKrixm/xrxHA==,type:str] +kind: Secret +metadata: + name: doppler-token-auth-api +sops: + kms: [] + gcp_kms: [] + azure_kv: [] + hc_vault: [] + age: + - recipient: age1y0kzuf0tn94a74whazwae4r9qal4snuqfuhl5jacscrpr7up5gts74fe5w + enc: | + -----BEGIN AGE ENCRYPTED FILE----- + YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSA2ek9hRUJHbk5OSVRtSkND + dWNZbG9uVlIzaUR0ekYrcFZScFEvQXo1aEFFCjlrR1lFSVlQWER2VmNYUkFhT21m + TXdZSkUrcm1ZUHQ0aEJ4SWwyZTdaWkkKLS0tIENVS09zaHRLYk55Mnl3bjE0eWNU + Z0RwQ3I5QXMvZWhzQW9hVW9nTE45YzgKlxbbjqihW8qoqWhrLCtzxfAMpXLRYzH7 + oq2Lab8rwhppqD28tiGknY61q82x/SaZNphYoXEAZKWEMKYo3lpX3A== + -----END AGE ENCRYPTED FILE----- + lastmodified: "2023-05-16T17:01:55Z" + mac: ENC[AES256_GCM,data:QE7nolYJJMAVdB3ZNaNCx6GyhigrcTlbglmGk857ojP02MS7WNcVpI64RbcG2HkGKjYpQiZ1QPRz5vKooSPQj7NNtzjpr9D6ChksVuEIC5x/8kotv5WmJAdYI7z8OGzJRM/XC8B8rqKOmEck1/zGU95/BYY3uA7hlJZ7/LpwmXA=,iv:mHbJ6vpICHAjPh/snpPjkDzWOp1/qH+rJ3wP8zlVExo=,tag:KHoJmvkufrMnPS3lm67Pmg==,type:str] + pgp: [] + encrypted_regex: ^(data|stringData)$ + version: 3.7.3 diff --git a/kubernetes/apps/security/external-secrets/secretstores/doppler/secretstore.yaml b/kubernetes/apps/security/external-secrets/secretstores/doppler/secretstore.yaml new file mode 100644 index 000000000..794cb3079 --- /dev/null +++ b/kubernetes/apps/security/external-secrets/secretstores/doppler/secretstore.yaml @@ -0,0 +1,14 @@ +--- +apiVersion: external-secrets.io/v1beta1 +kind: ClusterSecretStore +metadata: + name: doppler-auth-api +spec: + provider: + doppler: + auth: + secretRef: + dopplerToken: + name: doppler-token-auth-api + namespace: security + key: dopplerToken diff --git a/kubernetes/apps/security/external-secrets/secretstores/kustomization.yaml b/kubernetes/apps/security/external-secrets/secretstores/kustomization.yaml new file mode 100644 index 000000000..a41e314e2 --- /dev/null +++ b/kubernetes/apps/security/external-secrets/secretstores/kustomization.yaml @@ -0,0 +1,8 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +namespace: security +resources: + - ./onepassword + - ./doppler diff --git a/kubernetes/apps/security/external-secrets/secretstores/onepassword/helmrelease.yaml b/kubernetes/apps/security/external-secrets/secretstores/onepassword/helmrelease.yaml new file mode 100644 index 000000000..745ff7c37 --- /dev/null +++ b/kubernetes/apps/security/external-secrets/secretstores/onepassword/helmrelease.yaml @@ -0,0 +1,138 @@ +--- +# yaml-language-server: $schema=https://raw.githubusercontent.com/fluxcd-community/flux2-schemas/main/helmrelease-helm-v2beta2.json +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: onepassword-connect +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + controllers: + onepassword-connect: + strategy: RollingUpdate + annotations: + reloader.stakater.com/auto: "true" + containers: + api: + image: + repository: docker.io/1password/connect-api + tag: 1.7.2 + env: + XDG_DATA_HOME: &configDir /config + OP_HTTP_PORT: &apiPort 80 + OP_BUS_PORT: 11220 + OP_BUS_PEERS: localhost:11221 + OP_SESSION: + valueFrom: + secretKeyRef: + name: onepassword-connect-secret + key: 1password-credentials.json + probes: + liveness: + enabled: true + custom: true + spec: + httpGet: + path: /heartbeat + port: *apiPort + initialDelaySeconds: 15 + periodSeconds: 30 + failureThreshold: 3 + readiness: + enabled: true + custom: true + spec: + httpGet: + path: &path /health + port: *apiPort + initialDelaySeconds: 15 + securityContext: &securityContext + allowPrivilegeEscalation: false + readOnlyRootFilesystem: true + capabilities: { drop: ["ALL"] } + resources: &resources + requests: + cpu: 10m + limits: + memory: 256M + sync: + image: + repository: docker.io/1password/connect-sync + tag: 1.7.2 + env: + XDG_DATA_HOME: *configDir + OP_HTTP_PORT: &syncPort 8081 + OP_BUS_PORT: 11221 + OP_BUS_PEERS: localhost:11220 + OP_SESSION: + valueFrom: + secretKeyRef: + name: onepassword-connect-secret + key: 1password-credentials.json + probes: + liveness: + enabled: true + custom: true + spec: + httpGet: + path: /heartbeat + port: *syncPort + initialDelaySeconds: 15 + periodSeconds: 30 + failureThreshold: 3 + readiness: + enabled: true + custom: true + spec: + httpGet: + path: /health + port: *syncPort + initialDelaySeconds: 15 + securityContext: *securityContext + resources: *resources + defaultPodOptions: + securityContext: + runAsNonRoot: true + runAsUser: 999 + runAsGroup: 999 + fsGroup: 999 + fsGroupChangePolicy: OnRootMismatch + seccompProfile: { type: RuntimeDefault } + service: + app: + controller: onepassword-connect + ports: + http: + port: *apiPort + ingress: + app: + className: internal + annotations: + gatus.io/path: *path + hosts: + - host: "{{ .Release.Name }}.${SECRET_DOMAIN}" + paths: + - path: / + service: + identifier: app + port: http + persistence: + config: + type: emptyDir + globalMounts: + - path: *configDir diff --git a/kubernetes/apps/security/external-secrets/secretstores/onepassword/kustomization.yaml b/kubernetes/apps/security/external-secrets/secretstores/onepassword/kustomization.yaml new file mode 100644 index 000000000..8bd89645f --- /dev/null +++ b/kubernetes/apps/security/external-secrets/secretstores/onepassword/kustomization.yaml @@ -0,0 +1,8 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml + - ./secret.sops.yaml + - ./secretstore.yaml diff --git a/kubernetes/apps/security/external-secrets/secretstores/onepassword/secret.sops.yaml b/kubernetes/apps/security/external-secrets/secretstores/onepassword/secret.sops.yaml new file mode 100644 index 000000000..faba09623 --- /dev/null +++ b/kubernetes/apps/security/external-secrets/secretstores/onepassword/secret.sops.yaml @@ -0,0 +1,28 @@ +--- +apiVersion: v1 +stringData: + token: ENC[AES256_GCM,data:+yrrku0u+7eZfc5shry6J1CYtmNS/17TVqIpTmscy80KauEv+YA8/uu1KnWaQWWv1663FnfI8qXM12PNCSbHd0wLVRUT26YcnkEFx5lo+EbCJAiFXrJyMafWbn6OskRoWdQq7TodOQtjvYXsvzGEJ6IsUZz0JdAcBAohL0DkIiql97F4sGnXXWGRpZhvk6lkQDbWaX+djVAFjAfx2W+N5glzK8ESWX/nSBOnpTfPVosmL3aROA92ER7eQnuZgrz5HnHRuXwEtFIuPf9ykLc75bKxP6xlV6pQV30db5hGc1MISgUiqIIn9PDnMBG2H8Xj67+EsVRMzx5L1U/1yd0Lu8szZxvbR/6YlYyWfmkqG9Js7bYlfJg0xjJZE4sWaqF4TeWlJSmkpSvmL+zJ2/2pCWZTo4Op1ZfGRPaBxz+0kRIMdAbv3HZDBQiuD7mdSNvizbzQ/NYLod5N8aBRawDidLKMqGZZbN70bi2191OxQiJhFyA25trlTcmfZbw0cF6lSfPzS46NcoRl8F35O4jr+/pljbDcEoGuXJaKCxxWCn/e94re8hqLds8dEsqdevo93ahX18hGYLal5qDi0gXTZDgtC+q9mUB3xvgCNAge2DL/+vgZeAL+vYcp+Q2niIh6irWX9t+HAu13T4t18m0azfjgr2YDSyJoxdcj1ZHvt0Oy1m1Wd16ribw2LtcD+zRRreQMRIrEXpY1IN+gx2bMwWNWzku3d9pgAlkXyIx27V2kUNCJOY0kf5qJPyM5f+kaInFGoTgg8F1GLt27IxOW07WbjJXO/MabOs5h1jHF5QwY5//+nFGhdAqyr8KK922bnCBkW18OcxA+bkNH8kkqQbNR,iv:ifaiUGf2JGE26wItSPGtrkenPZQuM5omE8RXyml2qqY=,tag:WZyuZU0K4WJnJXVWL+27fg==,type:str] + 1password-credentials.json: ENC[AES256_GCM,data:0EpilwcQQ1mbuWBnopgRNT4Ra2ifVW4ddx9tBzWEM3Z5JkukOvToAiHUVDSYMFmn7mcu/E5Af4EXy4sQ80DVNkXv4YFLKsWtVD0Pjsm3dpLolQ8uAxhtuiTTF+KFkRA3s125pV/+KmTJ/A5NiTTeEtMBd8O1m01Sus3xVJS9fAlP/sY6/CBut4NGzdLTSTDNWZOJZfvK9lI9J40GT87JiGnhydHOU3WzwuHjjsm4IavgZC/BEAfvbpIzmEaPCMYYtD2SbwfUpJVh97EeBiNxpd8UO8RUStoUlvFLwqgipYCntfQRNhfFRoT19crYvhp83XRtk1v9H+75gJrS2AXZJ/niIBHZs9sSxpwbgqDJGBz/b7Nh0ShYdK0urJL4a6KT1NhbGCnbCqetb+0fki+XkynoafK15ihhHRqoJ0tNNn1/sSghVnfFUmc7gemXoxDpLWh2OmNNkwvs9eKDJlj4Ow1tXPswoUU6dXLNQfTtfU25SUkI5AQs3juwq+YJRTxTqFqf7AlsiKEMOBaHZnX8sa8FnIgpO5plFfApFmfhyGG6xDQxmEd6e3EUFSRDJvKW9+xy2Jwedl5LRyxwT2BAUZUVDIAU5foy4ktFRY+Ajb2PoqryqymV0R8B3gp86fJGNn0dj3U49BkLYDORvIjVU71NBGodCJxqVVbf1ZsgjD8U0vdvBknY1SpoLqXtCtbwzqMJHdaiza7T80X4IRNjJ1Kwb357GTLU81CE2Du9vmUw1+f6GKzqSEVgThHkdEnSX8LOMl6ZHQPU0k11vsnJ+7JCyNEs/8BEgoeBR9D9Cq8FUJQIndSb+Inj/YOZTBSekkHpqAvgzOmmmz74nC8e+CGJ2aEE5av3tagLLuVoOh2/iJtt1Qsz9YmogLmr9QP5GMBzfWceD8E74tcwWnPjLM6rZB5FIvyIPS3uKtcWZedkXHqYApzx8ebGCG7eMjJKoAzTSqeu1QTbNRv6BUdGWXfwH8sld+UtDFrOWa3KMgrYhisJyfDSPqMh/H6VgrmTxKYPt8NUYNLB+yAXt5jIb2Tb1jJm1cpmsCY+zjH4PBP78ri7YDI0BW9c2ZUSzBDSrBLbezz64u5AsURTM9rRFgvn+kJhtxOvJUm+MlSuioOZkI7NtwdN1xM67ntUrB+S8jz3VL52EK8ORA5mUPBIFAhXuTFqVqFMiuzs1LghNATjPEiigUukheGcx271otKVGn/9isko0hQpY33ZC9FTTWOhXZve/bpLaH8d8esonyca/nAOySO9WCb8/8mWEBv2uCDmngBsVbvN890s5XzK8VhUYLOF7xfRckCOqaBhVE8naKAqs9EcIHn5jaktiVkoGmaxs/7mFvqSVAMf8FbL95sWHw93JseNZmi2Im9vyfKqjwDl4XEi6Xbjhiev8zJOCdijW84UiwA1SUrmOkcBdGtRLi1TCsCQ4xiU51mC+qLnRg9KsfKj+4YlVDh6EAE+RfKwBJ6S75OeTrOTyGdN17f7ClvV20xlIUPJ0nkmIYk956uP9uTJS7m5esaEpgVv2Amr14gkITpsuY0brUba6MnUo68+w2lgV0amhGgR6RR79obKFICEpHn5NhfsvefyNcQTaEnGEy41HBrs0F//5xW4llZih8dEZPFoW12S1pIk1zcTRWHM8t9dJCB/M3UX8up+yKgW/uXgLorXk4fP5c2Zu5elXwkQa+Yey5MJuehtWnoF+eQORN8DCmfXVjb4XA0HyTjIySLh06ZUpRqdpAICPN//ZcV3HS+nxUEYSaHZqphwXaoYznPXDus3F6zAxUQLeE2rjJgPXDTeRUjiorw5WAo+viZlBa4RtD75akx3VAgUh88x6kfeocC+owsG0UfHG/ORO2Ce/u3rTYWO9vyD7pY6HS7jh4HAJP4x/RyVU/KMpUVw/dZx2XcegLN85z5WbsOVZ7Y7RwxU,iv:gtpdjyDGb0AKJ2S1snA1sESeqkesi8dLfIyTxEbw+TU=,tag:1u/yu3VIS4HHaGtqqJzquA==,type:str] +kind: Secret +metadata: + name: onepassword-connect-secret +sops: + kms: [] + gcp_kms: [] + azure_kv: [] + hc_vault: [] + age: + - recipient: age1y0kzuf0tn94a74whazwae4r9qal4snuqfuhl5jacscrpr7up5gts74fe5w + enc: | + -----BEGIN AGE ENCRYPTED FILE----- + YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBJVk5jeUQwT2oyMjlSV0t6 + NkpDWjlCaUFXdE9FeVl0bzh2M3Nia012TzJVCjlYUjlPMmVPdHdpT3hBTFRTQ0Y4 + KzFOSzFVQ2V2OEV4ZXdyQnNKYk1VRHcKLS0tIHVrdU51UHN2RWFyeTErQXdjdkwx + UzRycXl5SUhMNUx0a1F4VW16VndnaUkKln0lFslzjCU1LXVD86qytL/eSLPVYlGQ + eUf9aohlG+anEDqY2h/U3hIGnrrWaNEVteI8eXTNvO6AdnVa07RkSg== + -----END AGE ENCRYPTED FILE----- + lastmodified: '2023-03-03T20:04:50Z' + mac: ENC[AES256_GCM,data:aOBJcLG3gEPinMemD2faHVavdRe1fQf2tTgp7PlnOn1GgNvcFDu3FTbLCARU69l0AePrQrCq63qiNmO7N2k2a0l5sYPWDPvL2trJazwCoO9uNo0Dmw+DENMXszY+N2YuZRXBEiRzWITK9rqCCHiaSBRiJ6BICFkSGyYoPr6Pin4=,iv:se/PlganuFOf42TKInen2hyBTnBvOaJoTVNd3jeQttE=,tag:A3+M6q5+9cnbRSt1FOi9Cg==,type:str] + pgp: [] + encrypted_regex: ^(data|stringData)$ + version: 3.7.3 diff --git a/kubernetes/apps/security/external-secrets/secretstores/onepassword/secretstore.yaml b/kubernetes/apps/security/external-secrets/secretstores/onepassword/secretstore.yaml new file mode 100644 index 000000000..b9550d9fa --- /dev/null +++ b/kubernetes/apps/security/external-secrets/secretstores/onepassword/secretstore.yaml @@ -0,0 +1,17 @@ +--- +apiVersion: external-secrets.io/v1beta1 +kind: ClusterSecretStore +metadata: + name: onepassword +spec: + provider: + onepassword: + connectHost: http://onepassword-connect:80 + vaults: + Homelab: 1 + auth: + secretRef: + connectTokenSecretRef: + name: onepassword-connect-secret + namespace: security + key: token diff --git a/kubernetes/apps/security/kustomization.yaml b/kubernetes/apps/security/kustomization.yaml new file mode 100644 index 000000000..0132e37d4 --- /dev/null +++ b/kubernetes/apps/security/kustomization.yaml @@ -0,0 +1,7 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - namespace.yaml + - external-secrets/ks.yaml + - kyverno/ks.yaml diff --git a/kubernetes/apps/security/kyverno/app/helmrelease.yaml b/kubernetes/apps/security/kyverno/app/helmrelease.yaml new file mode 100644 index 000000000..83fa8e9de --- /dev/null +++ b/kubernetes/apps/security/kyverno/app/helmrelease.yaml @@ -0,0 +1,84 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: &app kyverno +spec: + interval: 30m + chart: + spec: + chart: kyverno + version: 3.2.4 + sourceRef: + kind: HelmRepository + name: kyverno-charts + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + crds: + install: true + grafana: + enabled: true + admissionController: + replicas: 3 + rbac: + clusterRole: + extraResources: + - apiGroups: + - "" + resources: + - pods + verbs: + - create + - update + - delete + topologySpreadConstraints: + - maxSkew: 1 + topologyKey: kubernetes.io/hostname + whenUnsatisfiable: DoNotSchedule + labelSelector: + matchLabels: + app.kubernetes.io/instance: *app + app.kubernetes.io/component: admission-controller + serviceMonitor: + enabled: true + backgroundController: + rbac: + clusterRole: + extraResources: + - apiGroups: + - "" + resources: + - pods + verbs: + - create + - update + - patch + - delete + - get + - list + resources: + requests: + cpu: 100m + limits: + memory: 1Gi + serviceMonitor: + enabled: true + cleanupController: + serviceMonitor: + enabled: true + reportsController: + serviceMonitor: + enabled: true + config: + webhooks: + - objectSelector: + matchExpressions: + - key: webhooks.kyverno.io/exclude + operator: DoesNotExist diff --git a/kubernetes/apps/security/kyverno/app/kustomization.yaml b/kubernetes/apps/security/kyverno/app/kustomization.yaml new file mode 100644 index 000000000..5dd7baca7 --- /dev/null +++ b/kubernetes/apps/security/kyverno/app/kustomization.yaml @@ -0,0 +1,5 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml diff --git a/kubernetes/apps/security/kyverno/ks.yaml b/kubernetes/apps/security/kyverno/ks.yaml new file mode 100644 index 000000000..c0c39bed8 --- /dev/null +++ b/kubernetes/apps/security/kyverno/ks.yaml @@ -0,0 +1,36 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: kyverno + namespace: flux-system +spec: + targetNamespace: security + path: ./kubernetes/apps/security/kyverno/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: kyverno-policies + namespace: flux-system +spec: + targetNamespace: security + dependsOn: + - name: kyverno + path: ./kubernetes/apps/security/kyverno/policies + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/security/kyverno/policies/gatus-external.yaml b/kubernetes/apps/security/kyverno/policies/gatus-external.yaml new file mode 100644 index 000000000..30a68a5b7 --- /dev/null +++ b/kubernetes/apps/security/kyverno/policies/gatus-external.yaml @@ -0,0 +1,77 @@ +--- +apiVersion: kyverno.io/v1 +kind: ClusterPolicy +metadata: + name: &name gatus-external + annotations: + policies.kyverno.io/title: Generate gatus endpoints + policies.kyverno.io/category: Monitoring + policies.kyverno.io/severity: low + policies.kyverno.io/subject: Ingress + policies.kyverno.io/description: >- + This policy will automatically generate gatus endpoints for + all Ingresses with the ingressClassName set to external. + pod-policies.kyverno.io/autogen-controllers: none +spec: + generateExisting: true + rules: + - name: *name + match: + any: + - resources: + kinds: + - Ingress + exclude: + any: + - resources: + kinds: + - Ingress + annotations: + gatus.io/enabled: "false" + preconditions: + all: + - key: "{{ request.object.spec.ingressClassName }}" + operator: Equals + value: external + context: + - name: GATUS_HOST + variable: + value: '{{ request.object.metadata.annotations."gatus.io/host" || request.object.spec.rules[0].host }}' + jmesPath: "to_string(@)" + - name: GATUS_NAME + variable: + value: '{{ request.object.metadata.annotations."gatus.io/name" || request.object.metadata.name }}' + jmesPath: "to_string(@)" + - name: GATUS_PATH + variable: + value: '{{ request.object.metadata.annotations."gatus.io/path" || request.object.spec.rules[0].http.paths[0].path }}' + jmesPath: "to_string(@)" + - name: GATUS_STATUS_CODE + variable: + value: '{{ request.object.metadata.annotations."gatus.io/status-code" || `200` }}' + jmesPath: "to_string(@)" + generate: + apiVersion: v1 + kind: ConfigMap + name: "{{ request.object.metadata.name }}-gatus-ep" + namespace: "{{ request.object.metadata.namespace }}" + synchronize: true + data: + kind: ConfigMap + metadata: + labels: + gatus.io/enabled: "true" + data: + config.yaml: |- + --- + endpoints: + - name: {{ GATUS_NAME }} + group: external-kubernetes + url: https://{{ GATUS_HOST }}{{ GATUS_PATH }} + interval: 2m + client: + dns-resolver: tcp://1.1.1.1:53 + conditions: + - "[STATUS] == {{ GATUS_STATUS_CODE }}" + alerts: + - type: discord diff --git a/kubernetes/apps/security/kyverno/policies/gatus-internal.yaml b/kubernetes/apps/security/kyverno/policies/gatus-internal.yaml new file mode 100644 index 000000000..3228ee792 --- /dev/null +++ b/kubernetes/apps/security/kyverno/policies/gatus-internal.yaml @@ -0,0 +1,77 @@ +--- +apiVersion: kyverno.io/v1 +kind: ClusterPolicy +metadata: + name: &name gatus-internal + annotations: + policies.kyverno.io/title: Generate gatus endpoints + policies.kyverno.io/category: Monitoring + policies.kyverno.io/severity: low + policies.kyverno.io/subject: Ingress + policies.kyverno.io/description: >- + This policy will automatically generate gatus endpoints for + all Ingresses with the ingressClassName set to internal. + pod-policies.kyverno.io/autogen-controllers: none +spec: + generateExisting: true + rules: + - name: *name + match: + any: + - resources: + kinds: + - Ingress + exclude: + any: + - resources: + kinds: + - Ingress + annotations: + gatus.io/enabled: "false" + preconditions: + all: + - key: "{{ request.object.spec.ingressClassName }}" + operator: Equals + value: internal + context: + - name: GATUS_HOST + variable: + value: '{{ request.object.metadata.annotations."gatus.io/host" || request.object.spec.rules[0].host }}' + jmesPath: "to_string(@)" + - name: GATUS_NAME + variable: + value: '{{ request.object.metadata.annotations."gatus.io/name" || request.object.metadata.name }}' + jmesPath: "to_string(@)" + - name: GATUS_PATH + variable: + value: '{{ request.object.metadata.annotations."gatus.io/path" || request.object.spec.rules[0].http.paths[0].path }}' + jmesPath: "to_string(@)" + - name: GATUS_STATUS_CODE + variable: + value: '{{ request.object.metadata.annotations."gatus.io/status-code" || `200` }}' + jmesPath: "to_string(@)" + generate: + apiVersion: v1 + kind: ConfigMap + name: "{{ request.object.metadata.name }}-gatus-ep" + namespace: "{{ request.object.metadata.namespace }}" + synchronize: true + data: + kind: ConfigMap + metadata: + labels: + gatus.io/enabled: "true" + data: + config.yaml: |- + --- + endpoints: + - name: {{ GATUS_NAME }} + group: internal-kubernetes + url: https://{{ GATUS_HOST }}{{ GATUS_PATH }} + interval: 2m + client: + dns-resolver: tcp://192.168.13.1:53 + conditions: + - "[STATUS] == {{ GATUS_STATUS_CODE }}" + alerts: + - type: discord diff --git a/kubernetes/apps/security/kyverno/policies/ingress.yaml b/kubernetes/apps/security/kyverno/policies/ingress.yaml new file mode 100644 index 000000000..1d88ae3ae --- /dev/null +++ b/kubernetes/apps/security/kyverno/policies/ingress.yaml @@ -0,0 +1,32 @@ +--- +apiVersion: kyverno.io/v1 +kind: ClusterPolicy +metadata: + name: &name ingress + annotations: + policies.kyverno.io/title: Add Ingress annotations + policies.kyverno.io/category: Ingress + policies.kyverno.io/severity: low + policies.kyverno.io/subject: Ingress + policies.kyverno.io/description: >- + This policy will automatically add external-dns annotations to Ingresses + with ingressClassName external. + pod-policies.kyverno.io/autogen-controllers: none +spec: + rules: + - name: *name + match: + any: + - resources: + kinds: + - Ingress + preconditions: + all: + - key: "{{ request.object.spec.ingressClassName }}" + operator: Equals + value: external + mutate: + patchStrategicMerge: + metadata: + annotations: + external-dns.alpha.kubernetes.io/target: "external.${SECRET_DOMAIN}" diff --git a/kubernetes/apps/security/kyverno/policies/kustomization.yaml b/kubernetes/apps/security/kyverno/policies/kustomization.yaml new file mode 100644 index 000000000..63a81a261 --- /dev/null +++ b/kubernetes/apps/security/kyverno/policies/kustomization.yaml @@ -0,0 +1,9 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./gatus-external.yaml + - ./gatus-internal.yaml + - ./ingress.yaml + - ./limits.yaml + - ./ndots.yaml diff --git a/kubernetes/apps/security/kyverno/policies/limits.yaml b/kubernetes/apps/security/kyverno/policies/limits.yaml new file mode 100644 index 000000000..1b9a1bf63 --- /dev/null +++ b/kubernetes/apps/security/kyverno/policies/limits.yaml @@ -0,0 +1,44 @@ +--- +apiVersion: kyverno.io/v1 +kind: ClusterPolicy +metadata: + name: limits + annotations: + policies.kyverno.io/title: Remove CPU limits + policies.kyverno.io/category: Best Practices + policies.kyverno.io/severity: medium + policies.kyverno.io/subject: Pod + policies.kyverno.io/description: >- + This policy removes CPU limits from all Pods. + pod-policies.kyverno.io/autogen-controllers: none +spec: + rules: + - name: remove-containers-cpu-limits + match: + any: + - resources: + kinds: + - Pod + mutate: + foreach: + - list: request.object.spec.containers + patchesJson6902: |- + - path: /spec/containers/{{elementIndex}}/resources/limits/cpu + op: remove + - name: delete-initcontainers-cpu-limits + match: + any: + - resources: + kinds: + - Pod + preconditions: + all: + - key: "{{ request.object.spec.initContainers[] || `[]` | length(@) }}" + operator: GreaterThanOrEquals + value: 1 + mutate: + foreach: + - list: request.object.spec.initContainers + patchesJson6902: |- + - path: /spec/initContainers/{{elementIndex}}/resources/limits/cpu + op: remove diff --git a/kubernetes/apps/security/kyverno/policies/ndots.yaml b/kubernetes/apps/security/kyverno/policies/ndots.yaml new file mode 100644 index 000000000..a6dd38d7a --- /dev/null +++ b/kubernetes/apps/security/kyverno/policies/ndots.yaml @@ -0,0 +1,41 @@ +--- +apiVersion: kyverno.io/v1 +kind: ClusterPolicy +metadata: + name: &name ndots + annotations: + policies.kyverno.io/title: Add ndots + policies.kyverno.io/category: DNS Optimization + policies.kyverno.io/severity: low + policies.kyverno.io/subject: Pod + policies.kyverno.io/description: >- + The ndots value controls where DNS lookups are first performed in a cluster + and needs to be set to a lower value than the default of 5 in some cases. + This policy mutates all Pods to add the ndots option with a value of 1. + pod-policies.kyverno.io/autogen-controllers: none +spec: + rules: + - name: *name + match: + any: + - resources: + kinds: + - Pod + namespaceSelector: + matchExpressions: + - key: kyverno.io/ndots + operator: Exists + exclude: + any: + - resources: + kinds: + - Pod + annotations: + kyverno.io/exclude: "true" + mutate: + patchStrategicMerge: + spec: + dnsConfig: + options: + - name: ndots + value: "1" diff --git a/kubernetes/apps/security/namespace.yaml b/kubernetes/apps/security/namespace.yaml new file mode 100644 index 000000000..397a2359d --- /dev/null +++ b/kubernetes/apps/security/namespace.yaml @@ -0,0 +1,7 @@ +--- +apiVersion: v1 +kind: Namespace +metadata: + name: security + labels: + kustomize.toolkit.fluxcd.io/prune: disabled diff --git a/kubernetes/apps/storage/kustomization.yaml b/kubernetes/apps/storage/kustomization.yaml new file mode 100644 index 000000000..5873c50d8 --- /dev/null +++ b/kubernetes/apps/storage/kustomization.yaml @@ -0,0 +1,6 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - namespace.yaml + - longhorn/ks.yaml diff --git a/kubernetes/apps/storage/longhorn/app/helm-release.yaml b/kubernetes/apps/storage/longhorn/app/helm-release.yaml new file mode 100644 index 000000000..a50c9d70d --- /dev/null +++ b/kubernetes/apps/storage/longhorn/app/helm-release.yaml @@ -0,0 +1,82 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: &app longhorn +spec: + interval: 30m + chart: + spec: + chart: longhorn + version: 1.6.2 + sourceRef: + kind: HelmRepository + name: longhorn + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + persistence: + defaultClass: true + defaultClassReplicaCount: 2 + defaultFsType: ext4 + reclaimPolicy: Delete + # recurringJobs: + # enable: true + # jobList: + # '[{"name":"daily", "task":"backup", "cron":"0 6 * * ?", "retain":3,"labels": + # {"interval":"daily"}}]' + defaultSettings: + backupstorePollInterval: 300 + backupTarget: nfs://10.20.30.40:/volume2/data/backup/kubernetes/longhorn-backup + snapshotDataIntegrity: "fast-check" + defaultDataPath: /var/lib/longhorn + defaultDataLocality: best-effort + replicaAutoBalance: best-effort + staleReplicaTimeout: "30" + defaultReplicaCount: 2 + defaultLonghornStaticStorageClass: longhorn + createDefaultDiskLabeledNodes: false + nodeDownPodDeletionPolicy: delete-both-statefulset-and-deployment-pod + concurrentAutomaticEngineUpgradePerNodeLimit: 1 + storageMinimalAvailablePercentage: 10 + StorageOverProvisioningPercentage: 110 + # taintToleration: "node-role.kubernetes.io/master=true:NoSchedule" + # upgradeChecker: true + ingress: + enabled: true + ingressClassName: internal + host: longhorn.${SECRET_DOMAIN} + tlsSecret: ${SECRET_DOMAIN/./-}-production-tls + tls: true + path: / + annotations: + hajimari.io/enable: "true" + hajimari.io/icon: cow + hajimari.io/appName: Longhorn + hajimari.io/group: "storage" + # hajimari.io/targetBlank: "true" + # hajimari.io/info: "Storage" + # longhornManager: + # tolerations: + # - key: node-role.kubernetes.io/master + # operator: Equal + # value: "true" + # effect: NoSchedule + # longhornDriver: + # tolerations: + # - key: node-role.kubernetes.io/master + # operator: Equal + # value: "true" + # effect: NoSchedule + # longhornUI: + # tolerations: + # - key: node-role.kubernetes.io/master + # operator: Equal + # value: "true" + # effect: NoSchedule diff --git a/kubernetes/apps/storage/longhorn/app/kustomization.yaml b/kubernetes/apps/storage/longhorn/app/kustomization.yaml new file mode 100755 index 000000000..064fe80f3 --- /dev/null +++ b/kubernetes/apps/storage/longhorn/app/kustomization.yaml @@ -0,0 +1,7 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +namespace: storage +resources: + - helm-release.yaml diff --git a/kubernetes/apps/storage/longhorn/conf/kustomization.yaml b/kubernetes/apps/storage/longhorn/conf/kustomization.yaml new file mode 100755 index 000000000..3c9449c26 --- /dev/null +++ b/kubernetes/apps/storage/longhorn/conf/kustomization.yaml @@ -0,0 +1,10 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +namespace: storage +resources: + - monitoring + - other + - recurringjobs + # - snap-class.yaml diff --git a/kubernetes/apps/storage/longhorn/conf/monitoring/kustomization.yaml b/kubernetes/apps/storage/longhorn/conf/monitoring/kustomization.yaml new file mode 100755 index 000000000..425e1e1c1 --- /dev/null +++ b/kubernetes/apps/storage/longhorn/conf/monitoring/kustomization.yaml @@ -0,0 +1,8 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +namespace: longhorn-system +resources: + - prometheusrule.yaml + - servicemonitor.yaml diff --git a/kubernetes/apps/storage/longhorn/conf/monitoring/prometheusrule.yaml b/kubernetes/apps/storage/longhorn/conf/monitoring/prometheusrule.yaml new file mode 100755 index 000000000..5f1296b4b --- /dev/null +++ b/kubernetes/apps/storage/longhorn/conf/monitoring/prometheusrule.yaml @@ -0,0 +1,110 @@ +apiVersion: monitoring.coreos.com/v1 +kind: PrometheusRule +metadata: + name: longhorn-rules + namespace: monitoring +spec: + groups: + - name: longhorn.rules + rules: + - alert: LonghornVolumeActualSpaceUsedWarning + annotations: + description: + The actual space used by Longhorn volume {{$labels.volume}} on {{$labels.node}} is at {{$value}}% capacity for + more than 5 minutes. + summary: The actual used space of Longhorn volume is over 90% of the capacity. + expr: (longhorn_volume_actual_size_bytes / longhorn_volume_capacity_bytes) * 100 > 90 + for: 5m + labels: + issue: The actual used space of Longhorn volume {{$labels.volume}} on {{$labels.node}} is high. + severity: warning + - alert: LonghornVolumeStatusCritical + annotations: + description: + Longhorn volume {{$labels.volume}} on {{$labels.node}} is Fault for + more than 2 minutes. + summary: Longhorn volume {{$labels.volume}} is Fault + expr: longhorn_volume_robustness == 3 + for: 5m + labels: + issue: Longhorn volume {{$labels.volume}} is Fault. + severity: critical + - alert: LonghornVolumeStatusWarning + annotations: + description: + Longhorn volume {{$labels.volume}} on {{$labels.node}} is Degraded for + more than 5 minutes. + summary: Longhorn volume {{$labels.volume}} is Degraded + expr: longhorn_volume_robustness == 2 + for: 5m + labels: + issue: Longhorn volume {{$labels.volume}} is Degraded. + severity: warning + - alert: LonghornNodeStorageWarning + annotations: + description: + The used storage of node {{$labels.node}} is at {{$value}}% capacity for + more than 5 minutes. + summary: The used storage of node is over 70% of the capacity. + expr: (longhorn_node_storage_usage_bytes / longhorn_node_storage_capacity_bytes) * 100 > 70 + for: 5m + labels: + issue: The used storage of node {{$labels.node}} is high. + severity: warning + - alert: LonghornDiskStorageWarning + annotations: + description: + The used storage of disk {{$labels.disk}} on node {{$labels.node}} is at {{$value}}% capacity for + more than 5 minutes. + summary: The used storage of disk is over 70% of the capacity. + expr: (longhorn_disk_usage_bytes / longhorn_disk_capacity_bytes) * 100 > 70 + for: 5m + labels: + issue: The used storage of disk {{$labels.disk}} on node {{$labels.node}} is high. + severity: warning + - alert: LonghornNodeDown + annotations: + description: There are {{$value}} Longhorn nodes which have been offline for more than 5 minutes. + summary: Longhorn nodes is offline + expr: (avg(longhorn_node_count_total) or on() vector(0)) - (count(longhorn_node_status{condition="ready"} == 1) or on() vector(0)) > 0 + for: 5m + labels: + issue: There are {{$value}} Longhorn nodes are offline + severity: warning + - alert: LonghornIntanceManagerCPUUsageWarning + annotations: + description: + Longhorn instance manager {{$labels.instance_manager}} on {{$labels.node}} has CPU Usage / CPU request is {{$value}}% for + more than 5 minutes. + summary: Longhorn instance manager {{$labels.instance_manager}} on {{$labels.node}} has CPU Usage / CPU request is over 300%. + expr: (longhorn_instance_manager_cpu_usage_millicpu/longhorn_instance_manager_cpu_requests_millicpu) * 100 > 300 + for: 5m + labels: + issue: Longhorn instance manager {{$labels.instance_manager}} on {{$labels.node}} consumes 3 times the CPU request. + severity: warning + - alert: LonghornNodeCPUUsageWarning + annotations: + description: + Longhorn node {{$labels.node}} has CPU Usage / CPU capacity is {{$value}}% for + more than 5 minutes. + summary: Longhorn node {{$labels.node}} experiences high CPU pressure for more than 5m. + expr: (longhorn_node_cpu_usage_millicpu / longhorn_node_cpu_capacity_millicpu) * 100 > 90 + for: 5m + labels: + issue: Longhorn node {{$labels.node}} experiences high CPU pressure. + severity: warning + - alert: LonghornVolumeBackupStuck + expr: count by (volume) (longhorn_backup_state < 2) + for: 8h + labels: + severity: warning + annotations: + description: There are {{$value}} longhorn backups of a volume {{$labels.volume}} stuck for at least 8h. + summary: Longhorn backups stuck. + - alert: LonghornVolumeBackupError + expr: count by (volume) (longhorn_backup_state > 3) + labels: + severity: warning + annotations: + description: There are {{$value}} longhorn backups of a volume {{$labels.volume}} which failed to complete. + summary: Longhorn backups failed. diff --git a/kubernetes/apps/storage/longhorn/conf/monitoring/servicemonitor.yaml b/kubernetes/apps/storage/longhorn/conf/monitoring/servicemonitor.yaml new file mode 100755 index 000000000..b670f9d73 --- /dev/null +++ b/kubernetes/apps/storage/longhorn/conf/monitoring/servicemonitor.yaml @@ -0,0 +1,16 @@ +--- +apiVersion: monitoring.coreos.com/v1 +kind: ServiceMonitor +metadata: + name: longhorn-prometheus-servicemonitor + labels: + name: longhorn-prometheus-servicemonitor +spec: + selector: + matchLabels: + app: longhorn-manager + namespaceSelector: + matchNames: + - longhorn-system + endpoints: + - port: manager diff --git a/kubernetes/apps/storage/longhorn/conf/other/kustomization.yaml b/kubernetes/apps/storage/longhorn/conf/other/kustomization.yaml new file mode 100755 index 000000000..df2944207 --- /dev/null +++ b/kubernetes/apps/storage/longhorn/conf/other/kustomization.yaml @@ -0,0 +1,7 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +namespace: longhorn-system +resources: + - systembackup.yaml diff --git a/kubernetes/apps/storage/longhorn/conf/other/systembackup.yaml b/kubernetes/apps/storage/longhorn/conf/other/systembackup.yaml new file mode 100644 index 000000000..7dab0e9b2 --- /dev/null +++ b/kubernetes/apps/storage/longhorn/conf/other/systembackup.yaml @@ -0,0 +1,7 @@ +--- +apiVersion: longhorn.io/v1beta2 +kind: SystemBackup +metadata: + name: system +spec: + volumeBackupPolicy: if-not-present diff --git a/kubernetes/apps/storage/longhorn/conf/recurringjobs/30min-snapshot.yaml b/kubernetes/apps/storage/longhorn/conf/recurringjobs/30min-snapshot.yaml new file mode 100755 index 000000000..e510408de --- /dev/null +++ b/kubernetes/apps/storage/longhorn/conf/recurringjobs/30min-snapshot.yaml @@ -0,0 +1,13 @@ +--- +apiVersion: longhorn.io/v1beta1 +kind: RecurringJob +metadata: + name: 30min-snapshot +spec: + name: 30min-snapshot + concurrency: 2 + cron: 0/30 * * * * + groups: + - normal + retain: 4 + task: snapshot diff --git a/kubernetes/apps/storage/longhorn/conf/recurringjobs/daily-backup.yaml b/kubernetes/apps/storage/longhorn/conf/recurringjobs/daily-backup.yaml new file mode 100755 index 000000000..7361e1bb8 --- /dev/null +++ b/kubernetes/apps/storage/longhorn/conf/recurringjobs/daily-backup.yaml @@ -0,0 +1,13 @@ +--- +apiVersion: longhorn.io/v1beta1 +kind: RecurringJob +metadata: + name: daily-backup +spec: + name: daily-backup + concurrency: 2 + cron: 45 0 * * * + groups: + - normal + retain: 7 + task: backup diff --git a/kubernetes/apps/storage/longhorn/conf/recurringjobs/daily-cleanup.yaml b/kubernetes/apps/storage/longhorn/conf/recurringjobs/daily-cleanup.yaml new file mode 100755 index 000000000..47656a4a9 --- /dev/null +++ b/kubernetes/apps/storage/longhorn/conf/recurringjobs/daily-cleanup.yaml @@ -0,0 +1,13 @@ +--- +apiVersion: longhorn.io/v1beta1 +kind: RecurringJob +metadata: + name: daily-cleanup +spec: + name: daily-cleanup + concurrency: 1 + cron: 45 4 * * * + groups: + - normal + retain: 1 + task: snapshot-cleanup diff --git a/kubernetes/apps/storage/longhorn/conf/recurringjobs/daily-delete.yaml b/kubernetes/apps/storage/longhorn/conf/recurringjobs/daily-delete.yaml new file mode 100755 index 000000000..56598cdc4 --- /dev/null +++ b/kubernetes/apps/storage/longhorn/conf/recurringjobs/daily-delete.yaml @@ -0,0 +1,13 @@ +--- +apiVersion: longhorn.io/v1beta1 +kind: RecurringJob +metadata: + name: daily-delete +spec: + name: daily-delete + concurrency: 1 + cron: 45 3 * * * + groups: + - normal + retain: 1 + task: snapshot-delete diff --git a/kubernetes/apps/storage/longhorn/conf/recurringjobs/daily-trim.yaml b/kubernetes/apps/storage/longhorn/conf/recurringjobs/daily-trim.yaml new file mode 100755 index 000000000..994896f31 --- /dev/null +++ b/kubernetes/apps/storage/longhorn/conf/recurringjobs/daily-trim.yaml @@ -0,0 +1,13 @@ +--- +apiVersion: longhorn.io/v1beta1 +kind: RecurringJob +metadata: + name: daily-trim +spec: + name: daily-trim + concurrency: 1 + cron: 45 22 * * * + groups: + - normal + retain: 1 + task: filesystem-trim diff --git a/kubernetes/apps/storage/longhorn/conf/recurringjobs/hourly-backup.yaml b/kubernetes/apps/storage/longhorn/conf/recurringjobs/hourly-backup.yaml new file mode 100755 index 000000000..ae5af79ab --- /dev/null +++ b/kubernetes/apps/storage/longhorn/conf/recurringjobs/hourly-backup.yaml @@ -0,0 +1,13 @@ +--- +apiVersion: longhorn.io/v1beta1 +kind: RecurringJob +metadata: + name: hourly-backup +spec: + name: hourly-backup + concurrency: 2 + cron: 15 * * * * + groups: + - normal + retain: 6 + task: backup diff --git a/kubernetes/apps/storage/longhorn/conf/recurringjobs/kustomization.yaml b/kubernetes/apps/storage/longhorn/conf/recurringjobs/kustomization.yaml new file mode 100755 index 000000000..cb90caf07 --- /dev/null +++ b/kubernetes/apps/storage/longhorn/conf/recurringjobs/kustomization.yaml @@ -0,0 +1,12 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +namespace: longhorn-system +resources: + - 30min-snapshot.yaml + - daily-backup.yaml + - daily-cleanup.yaml + - daily-delete.yaml + - daily-trim.yaml + - hourly-backup.yaml diff --git a/kubernetes/apps/storage/longhorn/conf/snap-class.yaml b/kubernetes/apps/storage/longhorn/conf/snap-class.yaml new file mode 100755 index 000000000..ae2f0ae0d --- /dev/null +++ b/kubernetes/apps/storage/longhorn/conf/snap-class.yaml @@ -0,0 +1,9 @@ +--- +kind: VolumeSnapshotClass +apiVersion: snapshot.storage.k8s.io/v1 +metadata: + name: longhorn + labels: + velero.io/csi-volumesnapshot-class: "true" +driver: driver.longhorn.io +deletionPolicy: Retain diff --git a/kubernetes/apps/storage/longhorn/ks.yaml b/kubernetes/apps/storage/longhorn/ks.yaml new file mode 100644 index 000000000..db27bd207 --- /dev/null +++ b/kubernetes/apps/storage/longhorn/ks.yaml @@ -0,0 +1,63 @@ +# --- +# # yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/kustomize.toolkit.fluxcd.io/kustomization_v1.json +# apiVersion: kustomize.toolkit.fluxcd.io/v1 +# kind: Kustomization +# metadata: +# name: longhorn-prereq +# namespace: flux-system +# spec: +# targetNamespace: storage +# path: ./kubernetes/apps/storage/longhorn/prereq +# prune: true +# sourceRef: +# kind: GitRepository +# name: k8s-homelab +# wait: true # no flux ks dependents +# interval: 30m +# retryInterval: 1m +# timeout: 5m +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/kustomize.toolkit.fluxcd.io/kustomization_v1.json +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app longhorn + namespace: flux-system +spec: + commonMetadata: + labels: + app.kubernetes.io/name: *app + targetNamespace: storage + # dependsOn: + # - name: longhorn-prereq + path: ./kubernetes/apps/storage/longhorn/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: true + interval: 30m + retryInterval: 1m + timeout: 5m +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/kustomize.toolkit.fluxcd.io/kustomization_v1.json +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app longhorn-conf + namespace: flux-system +spec: + commonMetadata: + labels: + app.kubernetes.io/name: *app + dependsOn: + - name: longhorn + path: ./kubernetes/apps/storage/longhorn/conf + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false # no flux ks dependents + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/apps/storage/longhorn/prereq/kustomization.yaml b/kubernetes/apps/storage/longhorn/prereq/kustomization.yaml new file mode 100644 index 000000000..aaae13c21 --- /dev/null +++ b/kubernetes/apps/storage/longhorn/prereq/kustomization.yaml @@ -0,0 +1,12 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +namespace: storage +resources: +- longhorn-iscsi-installation.yaml +labels: +- includeSelectors: true + pairs: + app.kubernetes.io/instance: longhorn + app.kubernetes.io/name: longhorn diff --git a/kubernetes/apps/storage/longhorn/prereq/longhorn-iscsi-installation.yaml b/kubernetes/apps/storage/longhorn/prereq/longhorn-iscsi-installation.yaml new file mode 100644 index 000000000..e8b1f4f29 --- /dev/null +++ b/kubernetes/apps/storage/longhorn/prereq/longhorn-iscsi-installation.yaml @@ -0,0 +1,40 @@ +--- +apiVersion: apps/v1 +kind: DaemonSet +metadata: + name: longhorn-iscsi-installation + labels: + app: longhorn-iscsi-installation + annotations: + command: &cmd sudo apt-get update -q -y && sudo apt-get install -q -y open-iscsi + && sudo systemctl -q enable iscsid && sudo systemctl start iscsid && sudo modprobe + iscsi_tcp && if [ $? -eq 0 ]; then echo "iscsi install successfully"; else echo + "iscsi install failed error code $?"; fi +spec: + selector: + matchLabels: + app: longhorn-iscsi-installation + template: + metadata: + labels: + app: longhorn-iscsi-installation + spec: + hostNetwork: true + hostPID: true + initContainers: + - name: iscsi-installation + command: + - nsenter + - --mount=/proc/1/ns/mnt + - -- + - bash + - -c + - *cmd + image: alpine:3.20 + securityContext: + privileged: true + containers: + - name: sleep + image: registry.k8s.io/pause:3.10 + updateStrategy: + type: RollingUpdate diff --git a/kubernetes/apps/storage/namespace.yaml b/kubernetes/apps/storage/namespace.yaml new file mode 100644 index 000000000..a8966521e --- /dev/null +++ b/kubernetes/apps/storage/namespace.yaml @@ -0,0 +1,7 @@ +--- +apiVersion: v1 +kind: Namespace +metadata: + name: storage + labels: + kustomize.toolkit.fluxcd.io/prune: disabled diff --git a/kubernetes/apps/tools/kustomization.yaml b/kubernetes/apps/tools/kustomization.yaml new file mode 100644 index 000000000..17b5a675d --- /dev/null +++ b/kubernetes/apps/tools/kustomization.yaml @@ -0,0 +1,6 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - namespace.yaml + - smtp-relay/ks.yaml diff --git a/kubernetes/apps/tools/namespace.yaml b/kubernetes/apps/tools/namespace.yaml new file mode 100644 index 000000000..29b15efa3 --- /dev/null +++ b/kubernetes/apps/tools/namespace.yaml @@ -0,0 +1,7 @@ +--- +apiVersion: v1 +kind: Namespace +metadata: + name: tools + labels: + kustomize.toolkit.fluxcd.io/prune: disabled diff --git a/kubernetes/apps/tools/smtp-relay/app/config/maddy.conf b/kubernetes/apps/tools/smtp-relay/app/config/maddy.conf new file mode 100644 index 000000000..7004b3c84 --- /dev/null +++ b/kubernetes/apps/tools/smtp-relay/app/config/maddy.conf @@ -0,0 +1,24 @@ +state_dir /cache/state +runtime_dir /cache/run + +openmetrics tcp://0.0.0.0:{env:SMTP_RELAY_METRICS_PORT} { } + +tls off +hostname {env:SMTP_RELAY_HOSTNAME} + +smtp tcp://0.0.0.0:{env:SMTP_RELAY_SMTP_PORT} { + default_source { + deliver_to &remote_queue + } +} + +target.queue remote_queue { + target &remote_smtp +} + +target.smtp remote_smtp { + attempt_starttls yes + require_tls yes + auth plain {env:SMTP_RELAY_USERNAME} {env:SMTP_RELAY_PASSWORD} + targets tls://{env:SMTP_RELAY_SERVER}:{env:SMTP_RELAY_SERVER_PORT} +} diff --git a/kubernetes/apps/tools/smtp-relay/app/externalsecret.yaml b/kubernetes/apps/tools/smtp-relay/app/externalsecret.yaml new file mode 100644 index 000000000..96eba21c1 --- /dev/null +++ b/kubernetes/apps/tools/smtp-relay/app/externalsecret.yaml @@ -0,0 +1,22 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/external-secrets.io/externalsecret_v1beta1.json +apiVersion: external-secrets.io/v1beta1 +kind: ExternalSecret +metadata: + name: smtp-relay +spec: + secretStoreRef: + kind: ClusterSecretStore + name: onepassword + target: + name: smtp-relay-secret + template: + engineVersion: v2 + data: + SMTP_RELAY_HOSTNAME: "{{ .SMTP_RELAY_HOSTNAME }}" + SMTP_RELAY_SERVER: "{{ .SMTP_RELAY_SERVER }}" + SMTP_RELAY_USERNAME: "{{ .SMTP_RELAY_USERNAME }}" + SMTP_RELAY_PASSWORD: "{{ .SMTP_RELAY_PASSWORD }}" + dataFrom: + - extract: + key: smtp-relay diff --git a/kubernetes/apps/tools/smtp-relay/app/helmrelease.yaml b/kubernetes/apps/tools/smtp-relay/app/helmrelease.yaml new file mode 100644 index 000000000..b8c9d5854 --- /dev/null +++ b/kubernetes/apps/tools/smtp-relay/app/helmrelease.yaml @@ -0,0 +1,98 @@ +--- +apiVersion: helm.toolkit.fluxcd.io/v2 +kind: HelmRelease +metadata: + name: &app smtp-relay +spec: + interval: 30m + chart: + spec: + chart: app-template + version: 3.2.1 + sourceRef: + kind: HelmRepository + name: bjw-s + namespace: flux-system + install: + remediation: + retries: 3 + upgrade: + cleanupOnFail: true + remediation: + retries: 3 + values: + controllers: + smtp-relay: + replicas: 1 + annotations: + reloader.stakater.com/auto: "true" + containers: + app: + image: + repository: ghcr.io/foxcpp/maddy + tag: 0.7.1 + env: + SMTP_RELAY_SMTP_PORT: &port 25 + SMTP_RELAY_METRICS_PORT: &metricsPort 8080 + SMTP_RELAY_SERVER_PORT: 465 + envFrom: + - secretRef: + name: smtp-relay-secret + probes: + liveness: + enabled: true + readiness: + enabled: true + securityContext: + allowPrivilegeEscalation: false + readOnlyRootFilesystem: true + capabilities: { drop: ["ALL"] } + resources: + requests: + cpu: 10m + limits: + memory: 128Mi + defaultPodOptions: + securityContext: + runAsNonRoot: true + runAsUser: 65534 + runAsGroup: 65534 + seccompProfile: { type: RuntimeDefault } + topologySpreadConstraints: + - maxSkew: 1 + topologyKey: kubernetes.io/hostname + whenUnsatisfiable: DoNotSchedule + labelSelector: + matchLabels: + app.kubernetes.io/name: *app + service: + app: + controller: smtp-relay + type: LoadBalancer + ports: + http: + primary: true + port: *metricsPort + smtp: + port: *port + serviceMonitor: + app: + serviceName: smtp-relay + endpoints: + - port: http + scheme: http + path: /metrics + interval: 1m + scrapeTimeout: 10s + persistence: + config: + type: configMap + name: smtp-relay-configmap + globalMounts: + - path: /data/maddy.conf + subPath: maddy.conf + readOnly: true + cache: + type: emptyDir + globalMounts: + - path: /cache diff --git a/kubernetes/apps/tools/smtp-relay/app/kustomization.yaml b/kubernetes/apps/tools/smtp-relay/app/kustomization.yaml new file mode 100644 index 000000000..65f6edd76 --- /dev/null +++ b/kubernetes/apps/tools/smtp-relay/app/kustomization.yaml @@ -0,0 +1,13 @@ +--- +# yaml-language-server: $schema=https://json.schemastore.org/kustomization +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./helmrelease.yaml + - ./externalsecret.yaml +configMapGenerator: + - name: smtp-relay-configmap + files: + - maddy.conf=./config/maddy.conf +generatorOptions: + disableNameSuffixHash: true diff --git a/kubernetes/apps/tools/smtp-relay/ks.yaml b/kubernetes/apps/tools/smtp-relay/ks.yaml new file mode 100644 index 000000000..d951fee5e --- /dev/null +++ b/kubernetes/apps/tools/smtp-relay/ks.yaml @@ -0,0 +1,24 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/kustomize.toolkit.fluxcd.io/kustomization_v1.json +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: &app smtp-relay + namespace: flux-system +spec: + commonMetadata: + labels: + app.kubernetes.io/name: *app + targetNamespace: tools + dependsOn: + - name: external-secrets-secretstores + - name: ingress-nginx-internal + path: ./kubernetes/apps/tools/smtp-relay/app + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + wait: false + interval: 30m + retryInterval: 1m + timeout: 5m diff --git a/kubernetes/bootstrap/flux/kustomization.yaml b/kubernetes/bootstrap/flux/kustomization.yaml new file mode 100644 index 000000000..4a669d63e --- /dev/null +++ b/kubernetes/bootstrap/flux/kustomization.yaml @@ -0,0 +1,61 @@ +# IMPORTANT: This file is not tracked by flux and should never be. Its +# purpose is to only install the Flux components and CRDs into your cluster. +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - github.com/fluxcd/flux2/manifests/install?ref=v2.3.0 +patches: + # Remove the default network policies + - patch: |- + $patch: delete + apiVersion: networking.k8s.io/v1 + kind: NetworkPolicy + metadata: + name: not-used + target: + group: networking.k8s.io + kind: NetworkPolicy + # Resources renamed to match those installed by oci://ghcr.io/fluxcd/flux-manifests + - target: + kind: ResourceQuota + name: critical-pods + patch: | + - op: replace + path: /metadata/name + value: critical-pods-flux-system + - target: + kind: ClusterRoleBinding + name: cluster-reconciler + patch: | + - op: replace + path: /metadata/name + value: cluster-reconciler-flux-system + - target: + kind: ClusterRoleBinding + name: crd-controller + patch: | + - op: replace + path: /metadata/name + value: crd-controller-flux-system + - target: + kind: ClusterRole + name: crd-controller + patch: | + - op: replace + path: /metadata/name + value: crd-controller-flux-system + - target: + kind: ClusterRole + name: flux-edit + patch: | + - op: replace + path: /metadata/name + value: flux-edit-flux-system + - target: + kind: ClusterRole + name: flux-view + patch: | + - op: replace + path: /metadata/name + value: flux-view-flux-system diff --git a/kubernetes/bootstrap/helmfile.yaml b/kubernetes/bootstrap/helmfile.yaml new file mode 100644 index 000000000..299267b0f --- /dev/null +++ b/kubernetes/bootstrap/helmfile.yaml @@ -0,0 +1,59 @@ +--- +helmDefaults: + wait: true + waitForJobs: true + timeout: 600 + recreatePods: true + force: true + +repositories: + - name: cilium + url: https://helm.cilium.io + - name: coredns + url: https://coredns.github.io/helm + - name: postfinance + url: https://postfinance.github.io/kubelet-csr-approver + +releases: + - name: prometheus-operator-crds + namespace: observability + chart: oci://ghcr.io/prometheus-community/charts/prometheus-operator-crds + version: 12.0.0 + - name: cilium + namespace: kube-system + chart: cilium/cilium + version: 1.15.6 + values: + - ../apps/kube-system/cilium/app/helm-values.yaml + needs: + - observability/prometheus-operator-crds + - name: coredns + namespace: kube-system + chart: coredns/coredns + version: 1.30.0 + values: + - ../apps/kube-system/coredns/app/helm-values.yaml + needs: + - observability/prometheus-operator-crds + - kube-system/cilium + - name: kubelet-csr-approver + namespace: kube-system + chart: postfinance/kubelet-csr-approver + version: 1.2.1 + values: + - ../apps/kube-system/kubelet-csr-approver/app/helm-values.yaml + needs: + - observability/prometheus-operator-crds + - kube-system/cilium + - kube-system/coredns + - name: spegel + namespace: kube-system + chart: oci://ghcr.io/spegel-org/helm-charts/spegel + version: v0.0.23 + values: + - ../apps/kube-system/spegel/app/helm-values.yaml + needs: + - observability/prometheus-operator-crds + - kube-system/cilium + - kube-system/coredns + - kube-system/kubelet-csr-approver diff --git a/kubernetes/bootstrap/talos/clusterconfig/.gitignore b/kubernetes/bootstrap/talos/clusterconfig/.gitignore new file mode 100644 index 000000000..abdc20ecb --- /dev/null +++ b/kubernetes/bootstrap/talos/clusterconfig/.gitignore @@ -0,0 +1,5 @@ +talos-test-talos-test01.yaml +talos-test-talos-test02.yaml +talos-test-talos-test03.yaml +talos-test-talos-test04.yaml +talosconfig diff --git a/kubernetes/bootstrap/talos/patches/README.md b/kubernetes/bootstrap/talos/patches/README.md new file mode 100644 index 000000000..b96818887 --- /dev/null +++ b/kubernetes/bootstrap/talos/patches/README.md @@ -0,0 +1,15 @@ +# Talos Patching + +This directory contains Kustomization patches that are added to the talhelper configuration file. + + + +## Patch Directories + +Under this `patches` directory, there are several sub-directories that can contain patches that are added to the talhelper configuration file. +Each directory is optional and therefore might not created by default. + +- `global/`: patches that are applied to both the controller and worker configurations +- `controller/`: patches that are applied to the controller configurations +- `worker/`: patches that are applied to the worker configurations +- `${node-hostname}/`: patches that are applied to the node with the specified name diff --git a/kubernetes/bootstrap/talos/patches/controller/api-access.yaml b/kubernetes/bootstrap/talos/patches/controller/api-access.yaml new file mode 100644 index 000000000..772328442 --- /dev/null +++ b/kubernetes/bootstrap/talos/patches/controller/api-access.yaml @@ -0,0 +1,8 @@ +machine: + features: + kubernetesTalosAPIAccess: + enabled: true + allowedRoles: + - os:admin + allowedKubernetesNamespaces: + - system-upgrade diff --git a/kubernetes/bootstrap/talos/patches/controller/cluster.yaml b/kubernetes/bootstrap/talos/patches/controller/cluster.yaml new file mode 100644 index 000000000..aa3a9f226 --- /dev/null +++ b/kubernetes/bootstrap/talos/patches/controller/cluster.yaml @@ -0,0 +1,12 @@ +cluster: + allowSchedulingOnControlPlanes: true + controllerManager: + extraArgs: + bind-address: 0.0.0.0 + coreDNS: + disabled: true + proxy: + disabled: true + scheduler: + extraArgs: + bind-address: 0.0.0.0 diff --git a/kubernetes/bootstrap/talos/patches/controller/disable-admission-controller.yaml b/kubernetes/bootstrap/talos/patches/controller/disable-admission-controller.yaml new file mode 100644 index 000000000..e311789f4 --- /dev/null +++ b/kubernetes/bootstrap/talos/patches/controller/disable-admission-controller.yaml @@ -0,0 +1,2 @@ +- op: remove + path: /cluster/apiServer/admissionControl diff --git a/kubernetes/bootstrap/talos/patches/controller/etcd.yaml b/kubernetes/bootstrap/talos/patches/controller/etcd.yaml new file mode 100644 index 000000000..9e27e9d6f --- /dev/null +++ b/kubernetes/bootstrap/talos/patches/controller/etcd.yaml @@ -0,0 +1,6 @@ +cluster: + etcd: + extraArgs: + listen-metrics-urls: http://0.0.0.0:2381 + advertisedSubnets: + - 192.168.13.0/24 diff --git a/kubernetes/bootstrap/talos/patches/global/cluster-discovery.yaml b/kubernetes/bootstrap/talos/patches/global/cluster-discovery.yaml new file mode 100644 index 000000000..586a07abb --- /dev/null +++ b/kubernetes/bootstrap/talos/patches/global/cluster-discovery.yaml @@ -0,0 +1,7 @@ +cluster: + discovery: + registries: + kubernetes: + disabled: false + service: + disabled: false diff --git a/kubernetes/bootstrap/talos/patches/global/containerd.yaml b/kubernetes/bootstrap/talos/patches/global/containerd.yaml new file mode 100644 index 000000000..2952d6b41 --- /dev/null +++ b/kubernetes/bootstrap/talos/patches/global/containerd.yaml @@ -0,0 +1,12 @@ +machine: + files: + - op: create + path: /etc/cri/conf.d/20-customization.part + content: |- + [plugins."io.containerd.grpc.v1.cri"] + enable_unprivileged_ports = true + enable_unprivileged_icmp = true + [plugins."io.containerd.grpc.v1.cri".containerd] + discard_unpacked_layers = false + [plugins."io.containerd.grpc.v1.cri".containerd.runtimes.runc] + discard_unpacked_layers = false diff --git a/kubernetes/bootstrap/talos/patches/global/disable-search-domain.yaml b/kubernetes/bootstrap/talos/patches/global/disable-search-domain.yaml new file mode 100644 index 000000000..8ba647c49 --- /dev/null +++ b/kubernetes/bootstrap/talos/patches/global/disable-search-domain.yaml @@ -0,0 +1,3 @@ +machine: + network: + disableSearchDomain: true diff --git a/kubernetes/bootstrap/talos/patches/global/hostdns.yaml b/kubernetes/bootstrap/talos/patches/global/hostdns.yaml new file mode 100644 index 000000000..36c5e94f7 --- /dev/null +++ b/kubernetes/bootstrap/talos/patches/global/hostdns.yaml @@ -0,0 +1,6 @@ +machine: + features: + hostDNS: + enabled: true + resolveMemberNames: true + forwardKubeDNSToHost: false diff --git a/kubernetes/bootstrap/talos/patches/global/kubelet.yaml b/kubernetes/bootstrap/talos/patches/global/kubelet.yaml new file mode 100644 index 000000000..d86fc9640 --- /dev/null +++ b/kubernetes/bootstrap/talos/patches/global/kubelet.yaml @@ -0,0 +1,7 @@ +machine: + kubelet: + extraArgs: + rotate-server-certificates: true + nodeIP: + validSubnets: + - 192.168.13.0/24 diff --git a/kubernetes/bootstrap/talos/patches/global/openebs-local.yaml b/kubernetes/bootstrap/talos/patches/global/openebs-local.yaml new file mode 100644 index 000000000..e4095d171 --- /dev/null +++ b/kubernetes/bootstrap/talos/patches/global/openebs-local.yaml @@ -0,0 +1,10 @@ +machine: + kubelet: + extraMounts: + - destination: /var/openebs/local + type: bind + source: /var/openebs/local + options: + - bind + - rshared + - rw diff --git a/kubernetes/bootstrap/talos/patches/global/sysctl.yaml b/kubernetes/bootstrap/talos/patches/global/sysctl.yaml new file mode 100644 index 000000000..90361d7bb --- /dev/null +++ b/kubernetes/bootstrap/talos/patches/global/sysctl.yaml @@ -0,0 +1,7 @@ +machine: + sysctls: + fs.inotify.max_queued_events: "65536" + fs.inotify.max_user_watches: "524288" + fs.inotify.max_user_instances: "8192" + net.core.rmem_max: "2500000" + net.core.wmem_max: "2500000" diff --git a/kubernetes/bootstrap/talos/talconfig.yaml b/kubernetes/bootstrap/talos/talconfig.yaml new file mode 100644 index 000000000..33f6757be --- /dev/null +++ b/kubernetes/bootstrap/talos/talconfig.yaml @@ -0,0 +1,114 @@ +# yaml-language-server: $schema=https://raw.githubusercontent.com/budimanjojo/talhelper/master/pkg/config/schemas/talconfig.json +--- +# renovate: datasource=docker depName=ghcr.io/siderolabs/installer +talosVersion: v1.7.4 +# renovate: datasource=docker depName=ghcr.io/siderolabs/kubelet +kubernetesVersion: v1.30.2 + +clusterName: "talos-test" +endpoint: https://192.168.13.10:6443 +clusterPodNets: + - "10.69.0.0/16" +clusterSvcNets: + - "10.96.0.0/16" +additionalApiServerCertSans: &sans + - "192.168.13.10" + - 127.0.0.1 # KubePrism +additionalMachineCertSans: *sans + +# Disable built-in Flannel to use Cilium +cniConfig: + name: none + +nodes: + - hostname: "talos-test01" + ipAddress: "192.168.13.11" + installDisk: "/dev/sda" + talosImageURL: factory.talos.dev/installer/a28d86375cf9debe952efbcbe8e2886cf0a174b1f4dd733512600a40334977d7 + controlPlane: true + networkInterfaces: + - deviceSelector: + hardwareAddr: "b2:46:57:e3:e4:52" + dhcp: false + addresses: + - "192.168.13.11/24" + routes: + - network: 0.0.0.0/0 + gateway: "192.168.13.1" + mtu: 1500 + vip: + ip: "192.168.13.10" + - hostname: "talos-test02" + ipAddress: "192.168.13.12" + installDisk: "/dev/sda" + talosImageURL: factory.talos.dev/installer/a28d86375cf9debe952efbcbe8e2886cf0a174b1f4dd733512600a40334977d7 + controlPlane: true + networkInterfaces: + - deviceSelector: + hardwareAddr: "5e:a2:56:18:3c:c8" + dhcp: false + addresses: + - "192.168.13.12/24" + routes: + - network: 0.0.0.0/0 + gateway: "192.168.13.1" + mtu: 1500 + vip: + ip: "192.168.13.10" + - hostname: "talos-test03" + ipAddress: "192.168.13.13" + installDisk: "/dev/sda" + talosImageURL: factory.talos.dev/installer/a28d86375cf9debe952efbcbe8e2886cf0a174b1f4dd733512600a40334977d7 + controlPlane: true + networkInterfaces: + - deviceSelector: + hardwareAddr: "9e:a9:2a:00:ab:4d" + dhcp: false + addresses: + - "192.168.13.13/24" + routes: + - network: 0.0.0.0/0 + gateway: "192.168.13.1" + mtu: 1500 + vip: + ip: "192.168.13.10" + - hostname: "talos-test04" + ipAddress: "192.168.13.14" + installDisk: "/dev/sda" + talosImageURL: factory.talos.dev/installer/a28d86375cf9debe952efbcbe8e2886cf0a174b1f4dd733512600a40334977d7 + controlPlane: false + networkInterfaces: + - deviceSelector: + hardwareAddr: "e6:e1:01:cb:6c:ee" + dhcp: false + addresses: + - "192.168.13.14/24" + routes: + - network: 0.0.0.0/0 + gateway: "192.168.13.1" + mtu: 1500 + +# Global patches +patches: + - # Force nameserver + |- + machine: + network: + nameservers: + - 192.168.13.1 + - "@./patches/global/cluster-discovery.yaml" + - "@./patches/global/containerd.yaml" + - "@./patches/global/disable-search-domain.yaml" + - "@./patches/global/hostdns.yaml" + - "@./patches/global/kubelet.yaml" + - "@./patches/global/openebs-local.yaml" + - "@./patches/global/sysctl.yaml" + +# Controller patches +controlPlane: + patches: + - "@./patches/controller/api-access.yaml" + - "@./patches/controller/cluster.yaml" + - "@./patches/controller/disable-admission-controller.yaml" + - "@./patches/controller/etcd.yaml" + diff --git a/kubernetes/bootstrap/talos/talsecret.sops.yaml b/kubernetes/bootstrap/talos/talsecret.sops.yaml new file mode 100644 index 000000000..8a3bc9e58 --- /dev/null +++ b/kubernetes/bootstrap/talos/talsecret.sops.yaml @@ -0,0 +1,43 @@ +cluster: + id: ENC[AES256_GCM,data:Na/opm9Ev3mlCNvTG4qeItC9n7I5M8xx/p9KtaWyZNVEMPBTw/yUClsUYOw=,iv:jOGmQ8YMeKHApST0W5x7T97CFAd78VinW/upkyXw3ME=,tag:QwTw5U4b28082hMJNW6QMQ==,type:str] + secret: ENC[AES256_GCM,data:SeEjhn50dsrlduNDateT16Kl/O+Eex+AngkfnFN/NtClTbbJrmQd3p7pth8=,iv:eIxa0hu7KedxClmh2LW8syhZ3qwR5xKjbOEl6fapIm8=,tag:k5wnxYVCP2KkKCmxqKtbvg==,type:str] +secrets: + bootstraptoken: ENC[AES256_GCM,data:L/+LSyWve+OHP5JnxPjNOmG/BQxamaQ=,iv:/g5S9mCl9l5+LQkcNaUGp//N+VIVfrAT+AglAOPlChA=,tag:tlH4x3Z39mwzRHZROYjzsQ==,type:str] + secretboxencryptionsecret: ENC[AES256_GCM,data:/KOxdMRBZmIbYUIRQEjD3kZvlBolVKYjxarOS1cyLMciUwzeSr1nUcU40I0=,iv:YyKkEhghk9g/cLWUsS9jkSoPZmoaIuThQbiVIZf25ko=,tag:tEVbUgIR2apZIMDF1Ue1IQ==,type:str] +trustdinfo: + token: ENC[AES256_GCM,data:u49VFg1PpYnXn0DVE6TxQob0tSJ5Zd4=,iv:3orj2CoYXnyTFWIRjOfUKySoh4qTOHPWagEin7JezwQ=,tag:a2qukyIQeO3a8QIOCEA6gQ==,type:str] +certs: + etcd: + crt: ENC[AES256_GCM,data:XL0XVUiIOPm9bOD3SW49TbMkpYunheQXcbNOq451kwKlF7Pm+Zvsppcaox7pMXbO3k/y8It+oiusf3ynw2znwKu52kkCKPQGg4qFCilsn8IAsY+Sm7Fs56wCnALN9dGb3ixgnMnPVl1hJWoTK+cMgc+FlTE8lTENf0EKKjKPmNybwrnZnqnQSLxD0qr8/p3XHfgGzXgCWBuWtkwTiZibsu+5XAmd6cKiR6MTv6faH/GaSJ7qPfKBqeenm7rGuaCBrWpu0eN+J4CafADmkrBrM0AOSdbThTCzzUFrA9+vw8RO4G3bEICj+GQuVmkhDhlkxbYwRSqx4VBsCca9wsnzOCZI2lR/zr7TeB9EPtyorj2Dqhqg5fJw6MFeUrdCizPFiQ4wpdgkjHQT2XgWafain5l7qk9WFPN2sgbUJ8vAioP+NA4u3U2WEh+fLUB6NVqt0n8LC8ti0WE95HffMEsnJ21XJzCrxRZBrQwV/vfxbPxtLad8/k2oZVxmAF0baOWNrYbuyVpxefOG9Acp62+KivtybNjO5b2tPpSYfuZvqtk1ufsm6YTKlUrz+ivHM037Yem3/aFxwcfzoW8D4H1FjMPBpNrg31n3Bv6R64zbCirGAWUywp3u4N3k9Qc7W4U8q9OmsGZq3bNTk/NO1OUbwBLjw0ZQJ9vfRglVuWwPAZqW+N6axKwZiYNyfYqKBDNEz4cIT8sNG/fZ6oPYwF8WJlsM5vA5P65UHP1IkDMrLOBcTKsDvF1593iVWiiVidkuBYm+WFvbp0AFc2KcAdHXD1W8Ze7s2soYrnC+Ugck+a97+YsTKQ/VsUZaUMDRFBNi9NZWpIy6D5DVT88gxDj1cgKo4kVq5r7IebNfUG+3J4YYmbE926UGTMgIfdSk7IIs1/k4mjbpii1i/8WIG4w8KqzXlE9g/1kg5kgQ4HjShj1cfAcYKxLEmKyKIkLcDyVVKtb/U8nMEMykvXSEEOAWHxKvvueDpMdsUA7WYGD8lC+F44Ffuo4bTwdvsSvFWRwzG4fjTQ==,iv:OWYyqszvXCsvy/2jovIaMjB51JpLK162t/2IgAicH/M=,tag:I9klN4vprUR+P9TMO9otzw==,type:str] + key: ENC[AES256_GCM,data:4SBy6qxkfGUj6yB5wuRArf1Mo6HOYE77cRydsl2IbOEquJijvRFHMEvP1ZDhySCAbUZoXjnVrKfoNKuiUhe7KV9RAsCJJSEnJKYdUUxcjmZKQ8uTyd4KUF4vV1qex4+ugfgkRakn3EXHWg656fwk36fvIFhU/hb4AkdovIjNCEa0dPCg5lHIQ2CnEzJ33/+p2M05pixg2Pfmdq/P8OvqfSBQZ+/mX6X4KQS5Hou/sH9nGJvYSS41PmttQZdDRM5kWWf9TDNFooIZMhgc1KZXRogGiPI5kucGSi9KiVypPy35jqP0TLCDcS/TnMgULBOCIM3hZrXBdtAkgctjV238htvKaL5QeHa0r2ZXXi8naGEoDfS7CSqNGZlACyMJlpzeXXOhDXRROBPkF5P/c9/asA==,iv:EHeUTQQ5nr3otksfx0UevnobGjw8RWhqChujNfzmlgo=,tag:vagapBWZl8dFpgOy0W2MCQ==,type:str] + k8s: + crt: ENC[AES256_GCM,data:GTNOdJbQjnE1I7pt4rkNrAdadVUXNPUlz5l6zAna4vQR5mpK9obLZCH+iBIYvh9FAwej0UDlLdvcZTmjcz8i2cnKuil1R9QPm4dqJFXAd3j1Mch3oBp8kT/Ay9Q1BFbwgDkApGDq0Rk2mEIQmrg8Oe59IaTMXvMVJZdd1A8ZkDFvaJmGGDhjpOeL6cEBXEYhM3Ur4Am/LtH4UdrO0qSfi17WiSw1/lHCGORFGLOn/hZI2HgdHvX6speuf5Mr4UttKGNbak/4aXESk5stoRrfbvSOMmq3Gvan4WnyTJUhzgINTs5BNslj9bcFm7ddf/R2wMDokoBBqex6zQxSblPISNTgJs+psu6WKzaKivbCvd017lI3F4+lIQPG2VmngkI9m+TP9/bnURcHm/ciCqszAyh6KkqSEeWEmfsxjqttw/ksKCmzp0LrfT9UjNfNrb0YXpVKOYAxMrcdMi7IXBJHPTbhbzhZdYHNojOsF011okIblpPqs00yVaXbt3y5Upgr/WSlzPznn45Ls+J5AhVXLfAbrCujfx+XmTAEh0th3ckULqs8wHa1hbS+A0i+ul+Jm6pUkNaWEMvpYdiNPn1fLozM+KaCj3F3ZDQSJJloZr2JBPlH+Y2NU1ZNw4qVvnqRaJ8O/7OPjO2v+WmKq2tPctBdEFgZuSiQ3j3KVdqmv/N3zdF9ioIf8zxO78Z4paoK4JLLBloyUKt8mnXcZnW5SGUxudMzHeaVDjt8O0YsS4JvVd1ZiT5ht/VnyYh9kWluYU/Peda/pZ69ih8Sn0t5u7C5A12wc8taLCidyIIG6/Dl/0g8TMjlKXtdez5Eu65+Aw/6at/Vk40fdiga7FczlCreQmjxxrPIzn60q/31+9daclFc23tx+824CCx2BX/EYHpI0pQM0gW5gpul/WDzk9E4qwfQN+afU7kcHb656LE2QAyc3YFWgEIRe30OmIzuw9KuL5bQeUkJ/x0mYKdcyi8dLuR9bIIFcg2saIk/+AHYJ0lJvgYAWlQgsYbW7xtchwFfEJ5TxlDI0WjA3ZHZuoiQ5T20RcyBRZxZmg==,iv:VANbOxCIDcCE6GH+I8AG/A+Uf7Mv0BweCZQTO7MgYaU=,tag:lwwOwq4fxKztBCVNPKbHbQ==,type:str] + key: ENC[AES256_GCM,data:GA4nnE9z6S9F9tYh8QltqV2Up6bNzu7OSF5PAmStDyQoatvp87RZK50WWKNtzIw/zoP+eQDPgccFduyAWFIDC/L8wZCxT6U8v4MYFpe9Yl/DCdo6Pca5W+gYiaYH0Nno4YA62PfLkr7MAwxUR2MCjJgUbo540dXpy9WX6ZN/fq+5WTNmXq1uSUwT8wTMXvRLwBa4TpKO/xudwMfMZ70o9kUxH2VTGf5pJfxWrc4BaG2gR1apMC8Et+FVQ6EB66iAxDghPwTks9mW8M5LxC9FxevnTUFHA9vM9tENmG6tqugJG+KliRYfB9hi0BgPW5oUB3zII05ACA7n0xm/8th1EazbYVeySfBouPg6tvMGjM8nNhF8VSVqbp6JYcEAcGA7hkoHPfH6W9E3feE/FLn2iw==,iv:FkwkSguzfFjG4khlSCRBMF8SXuf5gH+hiVllN0cIIns=,tag:1wcMfvmy7AhPIWhrJRDwdA==,type:str] + k8saggregator: + crt: ENC[AES256_GCM,data:KkZnPRD3jxddDyZh+mef9Oeru54s3HetKQ/J4dH+U3+DlxFQWmnJrhrxCt9Xf2k21gVPvSIsoceXZeZ8rhUvjZgOhGcV7CaUodl/17YAR8ArVeNL23dZ2FsfeYKV70FTswgHjhglmTZ4rX7W7E0joYWfu0GuykNOn6Vb3dfqDu5oS5iLpsM/oeL4lTUIPqbPbXp+eakW+EYrh8llB91XGCcLV/8spi+JRZiNHfIS3/wZ1lUklviKsQqXJaq5tXYbqE1psAIg4XDuFJFLzr6kvgSlUJKLpm/2n0ncWhUxaTeGvuMKPBjBmZA4r2J9MZ6rK8plP3T6/H0xqam565faQVV/ycIZfLq7cijBqCGTGDmGb6veil0obilV9x+duh0j6HWrYmSzuIaVqOj20HDEkJ4VOmFZdUTOxcGODf0TE7BoaaGCHiaOKrNq0iK922FiyO7v6IsGFGi6mUmSx2WMg7+UVl8szPXE664QRQIQF2mhTQUk14/L5Br7I4p24sfvj/RijLTzNj+Q6WbGXPW2UEmfWVnCE/mSH553qvFPE+VeUYzvaCQqkv9OK4fDJ/zsNd3o3qsrfgTuDMLYdKXLIZs49Swqv7sJxx430m1AqLMsa/9gUYUaEcacNVhWy9v2Wak0t4xhR48DHEOxXb1YVvoYavE2GYr8593w1So3/EQgvd7DgCP3vf7CkMvaguBvMKnTJFn3wcla/KB9HJazjNn6xx5IYh1SJsnhhTw98ZZVYolq+T9Src2nmr4u7tP4fWeDj3U6xBaFJoD3cFPtkvZRB38kcXzBq3IY7WViWhVnSmSxw3Un8Ij8Omz5AEcxsPLcowDPNm1zm4zMV+VfAwC8Y3xobDsPKVeRYnkHLPWsZfeYYqVzcTnCRPzCgwo0emnN1SEnCL64lEUvtxJgrvZRnjQFuHWb4A5hY1bDEU2W/WiavTmb9A==,iv:lPkiOJvsmC2JUlKlResHut+G/ecZVUi3RybMc1NrEYw=,tag:56GQjrdsIw+5TXAVwUCaRw==,type:str] + key: ENC[AES256_GCM,data:9f4gmDeiEgf7ysmlhDHA7w1CHM1xbluu6TwR8MrUSVn5PnvX6SwaQkEGUsCIQWOGN6t3Tl7FZdI6NKphyTRTkFWBnclK7Dsm+lmEU1cmFfCZCsNYptLjwtdMVYjS9120j4n1wq84+ZcUbLADabfAWazFZols11Gc7RiMDlVk7ozc6FO+JyD3NhadBAAtMsPZb/jZlfMQiXBA03VyCVX6VIc5INjzoH19K/LXxCu6UJ3sm6b4+wn5YlcHmde1BFpC1K9A0JDdJJ2Hf7XKm3KWbavZAY6+Hf/eNNHgJQEXOrsR6D4UyWOt2LzrymyK5SN09skzVRl3fSaOMbmYDwnS9z5qwOVTSuLfwxt8xYcV1XVAuIJebS/jBZYuOfQeQjO0wIDnCeGpgogDqraPfYRHXQ==,iv:E4CrC/y3+j/ZM3emOFA1X3e5+Ydz6iASSsmGQVv2jmY=,tag:+tqkSjnieezRcQOdF7QDvg==,type:str] + k8sserviceaccount: + key: ENC[AES256_GCM,data:YwyRpEz7MvF3mV9ISkiFFBcQdaGyLLiz4wvWM3OU+9TsdRGfNUGKed5SlGYVAB1nQFaT7afcx0WEwdrrP7kpDZwN1PeAzrdllT/1CBMg0LJKjBIK7d2DwtyfufNw9I/dKrOXfQPO3Sc199qQPQXYe4CTWjljOTTPNxMWRDXbnHvHmCjnJJOhzRIUZE4FfsX43L3IMoN4demA6I+DuUAkgOggTQQcjt1Z8RUuduX7lTSh3mVVl0cG0LU2Wb5yorhRcNcfYROOaP603nbHYg1PGgbQbIRvaxqFOEe6vA3HjrBtjxVhJOsLo1NF3+KNj3gWvhKtbFe3CPM3G20O2QjCxhfJO6/19GbuKqaochLi5jjwOO0wV18R8UfgR8vU+0B6PKxUdzRIBIn/kGU8bh38bHfxIPbQKwAu3F66ofO62lEeU3PuWghsUaaesvOx2IHugyqPpPzUzaKUckACF9Xv0MqO2AMYaSC6uHQMDyAUkx2xpThVG6fiOWf6dMhs/Q8FxI1k1umCzTwC27Brk+VEPvhGfRcVKXLLdiPjmT94HeU4FHQv9Tdkx2zb09stxMrK5qvwRj2OvcqWhbhTD+LXUZpGIr2YlZBYPNav+GmwxEaMkewVmfqtzCbpME9n4VlaXgLFuI1efl/OthUOA/7HEg8WyZCqAWIV8rAVSjg68EyWX+PH0VsaP4DZqPJaLgGXcT2KvkVXyF6gxY+YWlRl0pmtq5hArKxEJBPNVE4FN1N/dEFhLxuidfE1MRUBygZFN6DsaxKrDd+z0pezVDz2/YClnbKrnP5HIvRa8+NyZ2q+GFMUoljnHVnzCFARp6VD4o9xi+8GWbDa7jKG1muF2/KKwykZkwkq1Fpvx3Hy+a1uV+UNxNeA1Xdjgp5O5ifFC46ZFzqXf7YUB9n4JuDci6rg/rxjLLCbjUN5QdZjAbb+HXs+zaMGFK8omCw6ACbiMTPZZXHlvJ4wnhtto/8qWyNMaI2lfzB2SQb1jr6nZVEa6U3xJmPljE3dsYId/5cIEzPE+f6mCM1Aa8nkHb3AHtDPRnO3OYVHIrrKPObPSstePumLGS79fcVbN2dTgMXVwT1VVsggWD3K/QOz7XpAVHT/bTErHCCMrPV1PEvUXLahALgKJp97+8QXqEYjkVjL7PM966oCRdlO3PBIvF3SQYLoFEbQUzXEwJexwwXVzpZVXDI+0Kr/pCQUkNk9YAc2/e8m1MQLZ6L+1AHs4nTodyLYg5Cz/kwR9nJnqLRLKkw0lbb8D+VO5ZJXBdPWGdni6+eC+nHSv6ushBJ3oqfKVgIgPEphdrin7OAmkLTbWf0Qja47oXEWqhnuMsjKgHq4u/1hZ+v/9pQfRL2lUs5zOU4bD6IfdobRMf1qp//KJbn2B0LazKoNaojG1w1vzcpgh1gOuwW+L1i31L77+CpvfWRoyW2FDu+a6IhqyR/L5PDsHXqxoz2EXxkuytqeI3gJLgyQlgYvGbjO+WgsYONNe7ye1RTabXBqRzpZIzn4TlR2sq05DnqEaVNhVOssEwAeC/oABuuguD+A8oYLkKRTVkJiDq+cx9IQr8/yisnygT/oPqYDAvpQwa1EF8sXSehAzUl4PSCo9h1d/dub4DLbjwZmlhrGQWhbu8TVKcQ+uqO+MEFRH/FunhFmF0nplVzeQBMWaeHAVqSoKptpEFnhcKbzUxSEvk7nedJWWtZT2q+txCN5Jcu+8XfIwf7OH6+yJ82jWdbX6czjWqLYDyVzbc8s+VihPpmOikj6HKmHbpT16dXO40lfOi0nyw0IRXMZtekKkjxrnP/rPcgINl1il8o6dbwBdr5fRGikOttQ4MD5dNbJQ/FW9XcaeOg4gU6fDMI16QkCY/0Qv4Wq+mmBaC/xmZrrfNw+MPj/HD0tqboNkfyK00/ulMIysxh7G8hZQ1TuhmNQCuOlJBj5eBWtQijJqTi5Qi2c1YZnmp5ocgkQKLpaPAXhepwbdJaLvhx397wgMC91w8hW7FSF/ewOp4WHU479onu1HXXqbLoHTUDK1iM+4zj5AEzRO/typCFHhenilIkAOuVvgYhWtb5cFDl4Q9FstFJUI9V61YNi5SWKgyI2nG71L4/VTwu2nXdU5E0tgbIsvu8mSNxyn2R1eQFnOt438rtx2PgDYnKzrVeFK2aPiJwijbXa4zmCo2Xwa5SxPnwv4jc55kQpdRKV/rXGslzFKFzfPJFea4o6yGAucPBCapuaLER9Gz6Vj+KogQqF/lI07H7QFvlxcDiAJiEKtzd2aaKzY672ZAW6a/SxGQnbE7P2HDp+4MD+wur3fjvjhBTkiARgN6+QUnLrDL82UyqdqWD9b31NqRMX6gzNWDbN9GOAMzMFl5EQpyADBS/iPIYHjnnCDQRDkNpAlMdYpPfI0y5W5S08XTZlmaDtYH3aPkfO/2liQiEv1C6EGTQbfSXhj6sp2yunuSVCC8NSBy6NAs9K0yE1qWxj8hxBJbHfNPBApwqdThUN6KRJAr6iVbLO89K+fDvGbE2NVHx/3eHetcK9+tEiaHIiTxBJDKYcQvpjuQAiswJVvtcde/nDAWg2AbfsAwbNXVv/SA1mO3TL5a+OeqkF+WH3MgJaMkqjsmu6jeIyS5YBFHWN/bawNGO+OYIqUiGoSbCAE5skJlVqTNVXMe0EC034Tz5xaevNAL1lXTOE9iKE8Lg5qCiB8hh2nEaa0Ya8lzn6d7o7rDRGQx1EqzJH8yYYoJ2wFRXWpo49qjwYa8OeQEW8GCxPgNyLbbN674MDUro99HJhcaXMIixzSGsrtsq/ZUUJc/fSor3FVuIbgdnh6i7fPdCKv1ti5o1AdUunDwRo7K0Uv4z0N0BUawwrodrHOeinfwudH2YlvjtmNAePsND9MCbzo3mQkRbjj7MzD95gI5b+Cdp0/9imoTYT3G8UgZQ+3a0NhiCdYirzwkS8bU0xRi7A1klWNQwSXK5RNsI/pWj7/FS9nXwO3VMwuP0QUxsiWOceLItVtsICZcXT042hvzYWcKiELlZtKoGGhSG3EXkn8h37FJUIxV/I/HTamMfnA1IGh/pLEMwDmhoQEPHjkgYMP04igHT7jrrEGk5AVHA+1tyR2iOLiwew9IWVTPDxiPMhjArIFc0tM9cYWDdlOHEOmhrID+gqzeJz6zxvOdxGX4hBhIKQkwGeuPFhLUaCoUD4w8AAOWzM5br6f+Mrs8FQwxpM9bz7ipoU+YvergbEEUTVbLlcUnyJoQlOnvfSEcsF8vlaDcutFoL1Ru/EzIAidhwzis3KzORQFjOezXt/bBiI6UCZ8ELkRLC33st9oMx8C1N/IRBLKik3ilODsW+w+g2whpGR2uOwYgFlQlJhzsFbp8UslDGf5B91SIUIqRErs71vWwTN4H2jJJpIHYLCgd0TqmuNq2ZcdTexxRa9UEdpv/AIePGjCO1d41U60PQUOwVgv3xsQLsK7FO7vEgn2foWBN2tZgw4EwBUTYmjIMGokbLEFWRFNdoc/S6QQ/3VBY1neY8aS6n6X5j6SPgpsaKQ8B+A96DuyegEqCoH+5Bx2ZX8y6BcbwAW6xaFK5qG942QsisyRaPBUhxxn1mNLr1gtHV7By2QZtZV1OA2hdCxDjlv605rIT53dAptLUJbjExdqAcIpTB61eIe93kT0PTcqb0HgHq3yzpsrCKdXvOhIiejvZxS3TYSJ3xd6jbcJAX0BwU8y095BItToBQLY5HTRwNoYZalMF0QAA9s2lpzdchTv/RkGFuzlRTxcURpPzioE/FTZ5LJ/jV75MbrglDFXmvEshUTyRDJaldmsSVX0/0XmiaQ+eZx0ERdI+vIve/79s8qKHnluQnc5Z+z3jfcgsEqC4GnTyKoOmOGedkjOA8dMfptkNBgmtnBE+uX5gEVKZzXl21qj0q5J/nB3UWWIliZConWhq8dEHHM9cqykm06VECiH4XBqE8s7xRS3U5y0yjSzrzB+AtCaNcua2Zplr3nocknh0vRLax+qncLaW1mr+oyWzU2UIN8ot5cdbgHpBey8aVi4rLqNlMlp/gguEvLl6CvCzCvVCmqALUvhMlYgyIBcKC5UymQdvbwuKPdHbRpt9WI42Dd48HUPdQX39OjtTuULl7xZLLwjGQgiXc1OkQhhmjjUVCcWwyFMThsLaCidoFNNecmVfutfaM18Vd7xkcQCnOzVtVkIJtG3AYJdrAvqsKn7uUQviEwoOYsvmrt6IGeiEyD0ho2Aw3SUGXuEPom5wd3ItUB74twIVgugzqW4LWdvZQHQ2NvIfTF1GdfOTg+BDYwDzMOIPkTziHxeejenFwNC7+EYiY2/uORR4JpQhN7U8OtliCm8mENQAjVByV5BdunaSurT8H4/U5SSXTlzS/X08lVjv/jyHDDDBDiQc6ryQO7OZ5KYCXUw9EpMUS4+gUljLtEnal0N5MgCfdA765BnPBWxBnCxrPxMOzoiFpnHhIc8A94oRWuDtQ4coYGgSTSEsCUoy52Bi/ej8RNcH6VNOLV5ZLyreJGGifvdkQdH9eJwrH1sxzRRDWHzguYDr+8rYeevZFxBuikUsS5CAtzigoX+gQs5HeseAiROAbme9lC1SunL6QxKDZAXiIVO6W1JogTmrKlt0yBP2jxNqlHhShusBKs4531v6n+sBKdn3JqY/4AKqIqlU+7BLHBbdkfKWCtAtE6KnctL9wd1NkMtA9u/vu8qTeLMUlcCZJfoAPyzLSjrfMIGStNNljlW7pWQ9KAo82Gl4ZJX2ldVrI5bu3oufuMybJVBCiHM2K9Z4/DinBitSxFUZiztqcUAES+CJmT83CBOvKjb7K7nhJmXH2YpY0+kNfRRVoo4mfwJYr30ceFLsn4u7vcYRrTYrlYJ++mJFvhyAYv8PncpywWNtqk595+vg5EQ+3jcFHyB1atRezxnn9qSiGceONFbZ83XqpxrMBmlg0FgyyNaqA3PQ8zsDywuv3EvdW/kQicRgpRKLgo1dZQvQ7xWOxr9UIv5ul7wWim0Fo8jUFS16Dhk5u2oKukWreG6CHOeUuznatnR5Uuf47OHLhQne0azpWS9u4ufkHC9fyJ/ItJlmXVM9PJwaDClVG7dfln7vHYU1g6V+KiWavY3WIXjdKovzgxnFn2ZEpKHOH920K2r59mLSITLEVBIsNzRZ0Mtkj16XINnRRFC8LSOjosDdSXDQi7DkhlahXkY3nJmX1MCv0d8NqGzz1zvIdNfvtRIvRHe2A+WF1ZFkjLSYigC4oQ1QFYRW5Jsv+xxOTiL6PMXlalYZzeZxuPazek0sRCkHmrKqUAdNHs24TTTZDLYdU6SR31U647dgKfNmtyw6+xc11Vy52j0YEQFM0jPUb5riJBN7CXIYySRWVJGM5R42EWtgW/e8RfimnK9FtfED9qiI3DQYX/iJ8OT7cdlE+OCp6QSqTK9KtJ35NYIXJEEtywafKCnWom5+gEfxZtfBTQr0CNnX74+GqS50nX7zOLM0qkXvL+mJ7J/OTwK0aI/fa43TBc2rMtG4P74YbcCjBiEj73yKk3sSOKUKokhiPo0O0Ue/5XSvsMDTSfmTWhdick6PfqZJ2GsmZULZaDhL3i6IQvIUbgsTIghwdp6lX52ewJzlPxplc7wHrKCSL0KpFiw6XwnUeBf5UkjQ1GCa2ZRrgz4xSLqZl0f7vLBI6E7lGfmQ+Wh7yQAzoR/5nVvcLbvpEhhiBjwOwrfi3vzDEK21S9frCZ5ghyz/ytfmm1QUQwU82umuAnQm8e0K/Nf6+IJXNYU6vjfA==,iv:1XJVixfCQ6e01mePZ/amLTaj9N2uhbiyHnuTZdiGnB0=,tag:nNTr5SX88KRqnOUdvPUoLA==,type:str] + os: + crt: ENC[AES256_GCM,data:98x+xUdKQ3505hSEcIBEbR/Uf8Z99qb4o9jcfaq1AJ/vjx9yg9wM0CAt2ZQ3etaMC3TUaq0tnxUhiI855EYHbv5MWCUP1+ddmv/3R8+Ub/NDK1gDYU7Z0COsFOSzLf4cn4Ac3uSm9l/Hz7TNQ6vf7m+/CvugS1xM9GAa/no8bqhSWzzcBcOP5npfWd3bRO77ON/LxYyfru7Ix7Hh/+TjVzmYejwhyc9ge6DHQ9IKYyTFli8FmePDTLJgS4YqKV/IZOfeJWBo1i0n8ouPKwtamCSNQ+AU9AN35nsm5cz0s3AykUcOoqWQySWxfH+dTVlat02nxeoXU4H/rlgzj+a5WbZnAgvj09k5/84R8j+PFmP5AyiFMEgaGh4nKUNQMIb5EJ35Y06/+99V2C1LAGmr+PjuJGv1K9oqHjsEsHhhvcFSSzR60BJWgPm67cnHByWYbyCbakAqUQiWb9ThARA858PEFpvae3PL747HUbaqrCV1q+2KAn83myxqAbcqPDbyuCY9Ppgk+0Bz4b2WVL0hB+d7NtmOuNCZkNCMthDgyyqyUakf7wRi8/32QXGmrNEKC+WI3FmH+P0EQk/fvwKrk7WDt8sHZRyWnaFNk4IWju2TzKIAoMyPIX+TKjuY8P/KpmwJQNylZjGfZxWiyj9ejUwpMVlRtOr2wt7Vl1H/ETzFQDhdpsioV4GsWIYj9nFrYz6KJwP8vhnPZ2I8ImFqgEPsa7c+hVyt836WyRUE8YH/1zQPD7GMWnO/R85uXIJ7cUcCs4cDgspii3gZWN98kNSE7JB01IBOmQyMZlmdYiG1Ob6YlLoOrYjsT9I3HkB9HIpMuKoZSoZEqLkEEziFMYhOvoYQSuWLQyphoh8Elpr2gM8i,iv:gZen5SkrGhiM3xgCOskvSXe4xL1AP6cpVTZXwI+APs4=,tag:hNIeTLNlWo+LYBIt4+bSPg==,type:str] + key: ENC[AES256_GCM,data:q3+85cURMGPPulRuxMHeIA2BABiqBO4MSEb/fqKU15a+gQNEqECagshxtDa2M0fvx1xgmWtY/oK4AGJIxSIlX6zRnRKS3SCfYIc76mDEM5nUz7ulCAYOINOcEGLbnsRMZwEZb088OgH2fb6nilmjxNWqrcQVh9nEECr7s0r8NeLl1q6qPb5ZDO2oxRTtP2poj8x6dVTarRoqFOP45U2Le03L0TKiRS1BlIi/gncs8jjqSQFj,iv:cJUc2u6l67ZPYkfJHkInRJACCNmmvd9U74CNnxBIU34=,tag:TbQk002LZI+arBf+c0amxg==,type:str] +sops: + kms: [] + gcp_kms: [] + azure_kv: [] + hc_vault: [] + age: + - recipient: age1y0kzuf0tn94a74whazwae4r9qal4snuqfuhl5jacscrpr7up5gts74fe5w + enc: | + -----BEGIN AGE ENCRYPTED FILE----- + YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSB0dmFraWRzbEtQdDdPOUU3 + YXUzNjFNcTJvdXdUNUc5aTJXb2FmODBUcjBFCmd0ekRyYkh2R2NPc2J5THNmUVlT + WUxzTHhlVks0M0FoT21MTkxlMzJlK3MKLS0tIE1VN0JzUERPTGFQemplOUtWR2Ns + K2FYWURjUEVHU3dkUmQrVmpJS0QzZUEKgPuwlmCGHiCbx6oBOiic2Y0XIVsGVGPo + SHVmdAhQu+kLHxylcT0gqnXdGnexuBJaltKOMgSnsfRMnFI/s8MPUQ== + -----END AGE ENCRYPTED FILE----- + lastmodified: "2024-06-05T13:32:59Z" + mac: ENC[AES256_GCM,data:cAvu5yzKOPdxVeXdCrB8BGO5j2LhoEv0x9fJR8JpqTO3mJ6ijgCLco4FizKWST5CN3LAq9R5CR5u1GPwZqZfux2Bc4PqMmH6ZYntmWTZsLfb9jXZaV85xcaBCCas17wJM2bv9X9SzCIOQxFCX8zG3QX9z+mu3k765loiZ4wvWz8=,iv:LY3zuCnnxywVJY1ggD1DlyM/CMfh2HfopeTXD0xAOlo=,tag:xK1xC03xjuSoaeg8Ai8jFA==,type:str] + pgp: [] + unencrypted_suffix: _unencrypted + version: 3.8.1 diff --git a/kubernetes/flux/apps.yaml b/kubernetes/flux/apps.yaml new file mode 100644 index 000000000..408c48bff --- /dev/null +++ b/kubernetes/flux/apps.yaml @@ -0,0 +1,56 @@ +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: cluster-apps + namespace: flux-system +spec: + interval: 30m + path: ./kubernetes/apps + prune: true + sourceRef: + kind: GitRepository + name: k8s-homelab + decryption: + provider: sops + secretRef: + name: sops-age + postBuild: + substituteFrom: + - kind: ConfigMap + name: cluster-settings + - kind: Secret + name: cluster-secrets + - kind: ConfigMap + name: cluster-user-settings + optional: true + - kind: Secret + name: cluster-user-secrets + optional: true + patches: + - patch: |- + apiVersion: kustomize.toolkit.fluxcd.io/v1 + kind: Kustomization + metadata: + name: not-used + spec: + decryption: + provider: sops + secretRef: + name: sops-age + postBuild: + substituteFrom: + - kind: ConfigMap + name: cluster-settings + - kind: Secret + name: cluster-secrets + - kind: ConfigMap + name: cluster-user-settings + optional: true + - kind: Secret + name: cluster-user-secrets + optional: true + target: + group: kustomize.toolkit.fluxcd.io + kind: Kustomization + labelSelector: substitution.flux.home.arpa/disabled notin (true) diff --git a/kubernetes/flux/config/cluster.yaml b/kubernetes/flux/config/cluster.yaml new file mode 100644 index 000000000..e1712665a --- /dev/null +++ b/kubernetes/flux/config/cluster.yaml @@ -0,0 +1,40 @@ +--- +apiVersion: source.toolkit.fluxcd.io/v1 +kind: GitRepository +metadata: + name: k8s-homelab + namespace: flux-system +spec: + interval: 30m + url: "https://github.com/tuxpeople/k8s-homelab.git" + ref: + branch: "main" + ignore: | + # exclude all + /* + # include kubernetes directory + !/kubernetes +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: cluster + namespace: flux-system +spec: + interval: 30m + path: ./kubernetes/flux + prune: true + wait: false + sourceRef: + kind: GitRepository + name: k8s-homelab + decryption: + provider: sops + secretRef: + name: sops-age + postBuild: + substituteFrom: + - kind: ConfigMap + name: cluster-settings + - kind: Secret + name: cluster-secrets diff --git a/kubernetes/flux/config/flux.yaml b/kubernetes/flux/config/flux.yaml new file mode 100644 index 000000000..4f9bb975b --- /dev/null +++ b/kubernetes/flux/config/flux.yaml @@ -0,0 +1,86 @@ +--- +apiVersion: source.toolkit.fluxcd.io/v1beta2 +kind: OCIRepository +metadata: + name: flux-manifests + namespace: flux-system +spec: + interval: 10m + url: oci://ghcr.io/fluxcd/flux-manifests + ref: + tag: v2.3.0 +--- +apiVersion: kustomize.toolkit.fluxcd.io/v1 +kind: Kustomization +metadata: + name: flux + namespace: flux-system +spec: + interval: 10m + path: ./ + prune: true + wait: true + sourceRef: + kind: OCIRepository + name: flux-manifests + patches: + # Remove the network policies + - patch: | + $patch: delete + apiVersion: networking.k8s.io/v1 + kind: NetworkPolicy + metadata: + name: not-used + target: + group: networking.k8s.io + kind: NetworkPolicy + # Increase the number of reconciliations that can be performed in parallel and bump the resources limits + # https://fluxcd.io/flux/cheatsheets/bootstrap/#increase-the-number-of-workers + - patch: | + - op: add + path: /spec/template/spec/containers/0/args/- + value: --concurrent=8 + - op: add + path: /spec/template/spec/containers/0/args/- + value: --kube-api-qps=500 + - op: add + path: /spec/template/spec/containers/0/args/- + value: --kube-api-burst=1000 + - op: add + path: /spec/template/spec/containers/0/args/- + value: --requeue-dependency=5s + target: + kind: Deployment + name: (kustomize-controller|helm-controller|source-controller) + - patch: | + apiVersion: apps/v1 + kind: Deployment + metadata: + name: not-used + spec: + template: + spec: + containers: + - name: manager + resources: + limits: + cpu: 2000m + memory: 2Gi + target: + kind: Deployment + name: (kustomize-controller|helm-controller|source-controller) + # Enable Helm near OOM detection + # https://fluxcd.io/flux/cheatsheets/bootstrap/#enable-helm-near-oom-detection + - patch: | + - op: add + path: /spec/template/spec/containers/0/args/- + value: --feature-gates=OOMWatch=true + - op: add + path: /spec/template/spec/containers/0/args/- + value: --oom-watch-memory-threshold=95 + - op: add + path: /spec/template/spec/containers/0/args/- + value: --oom-watch-interval=500ms + target: + kind: Deployment + name: helm-controller diff --git a/kubernetes/flux/config/kustomization.yaml b/kubernetes/flux/config/kustomization.yaml new file mode 100644 index 000000000..ef231746a --- /dev/null +++ b/kubernetes/flux/config/kustomization.yaml @@ -0,0 +1,6 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./flux.yaml + - ./cluster.yaml diff --git a/kubernetes/flux/repositories/git/kustomization.yaml b/kubernetes/flux/repositories/git/kustomization.yaml new file mode 100644 index 000000000..fe0f332a9 --- /dev/null +++ b/kubernetes/flux/repositories/git/kustomization.yaml @@ -0,0 +1,4 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: [] diff --git a/kubernetes/flux/repositories/helm/bitnami.yaml b/kubernetes/flux/repositories/helm/bitnami.yaml new file mode 100644 index 000000000..1dcdba438 --- /dev/null +++ b/kubernetes/flux/repositories/helm/bitnami.yaml @@ -0,0 +1,11 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/source.toolkit.fluxcd.io/helmrepository_v1beta2.json +apiVersion: source.toolkit.fluxcd.io/v1 +kind: HelmRepository +metadata: + name: bitnami + namespace: flux-system +spec: + type: oci + interval: 1h + url: oci://registry-1.docker.io/bitnamicharts diff --git a/kubernetes/flux/repositories/helm/bjw-s.yaml b/kubernetes/flux/repositories/helm/bjw-s.yaml new file mode 100644 index 000000000..a40b5d778 --- /dev/null +++ b/kubernetes/flux/repositories/helm/bjw-s.yaml @@ -0,0 +1,10 @@ +--- +apiVersion: source.toolkit.fluxcd.io/v1 +kind: HelmRepository +metadata: + name: bjw-s + namespace: flux-system +spec: + type: oci + interval: 5m + url: oci://ghcr.io/bjw-s/helm diff --git a/kubernetes/flux/repositories/helm/cilium.yaml b/kubernetes/flux/repositories/helm/cilium.yaml new file mode 100644 index 000000000..3aee36788 --- /dev/null +++ b/kubernetes/flux/repositories/helm/cilium.yaml @@ -0,0 +1,9 @@ +--- +apiVersion: source.toolkit.fluxcd.io/v1 +kind: HelmRepository +metadata: + name: cilium + namespace: flux-system +spec: + interval: 1h + url: https://helm.cilium.io diff --git a/kubernetes/flux/repositories/helm/coredns.yaml b/kubernetes/flux/repositories/helm/coredns.yaml new file mode 100644 index 000000000..3bdbbafbe --- /dev/null +++ b/kubernetes/flux/repositories/helm/coredns.yaml @@ -0,0 +1,9 @@ +--- +apiVersion: source.toolkit.fluxcd.io/v1 +kind: HelmRepository +metadata: + name: coredns + namespace: flux-system +spec: + interval: 1h + url: https://coredns.github.io/helm diff --git a/kubernetes/flux/repositories/helm/external-dns.yaml b/kubernetes/flux/repositories/helm/external-dns.yaml new file mode 100644 index 000000000..a44512667 --- /dev/null +++ b/kubernetes/flux/repositories/helm/external-dns.yaml @@ -0,0 +1,9 @@ +--- +apiVersion: source.toolkit.fluxcd.io/v1 +kind: HelmRepository +metadata: + name: external-dns + namespace: flux-system +spec: + interval: 1h + url: https://kubernetes-sigs.github.io/external-dns diff --git a/kubernetes/flux/repositories/helm/external-secrets.yaml b/kubernetes/flux/repositories/helm/external-secrets.yaml new file mode 100644 index 000000000..bcf54eb5e --- /dev/null +++ b/kubernetes/flux/repositories/helm/external-secrets.yaml @@ -0,0 +1,10 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/source.toolkit.fluxcd.io/helmrepository_v1beta2.json +apiVersion: source.toolkit.fluxcd.io/v1 +kind: HelmRepository +metadata: + name: external-secrets + namespace: flux-system +spec: + interval: 1h + url: https://charts.external-secrets.io diff --git a/kubernetes/flux/repositories/helm/ingress-nginx.yaml b/kubernetes/flux/repositories/helm/ingress-nginx.yaml new file mode 100644 index 000000000..82a0d0fff --- /dev/null +++ b/kubernetes/flux/repositories/helm/ingress-nginx.yaml @@ -0,0 +1,9 @@ +--- +apiVersion: source.toolkit.fluxcd.io/v1 +kind: HelmRepository +metadata: + name: ingress-nginx + namespace: flux-system +spec: + interval: 1h + url: https://kubernetes.github.io/ingress-nginx diff --git a/kubernetes/flux/repositories/helm/jetstack.yaml b/kubernetes/flux/repositories/helm/jetstack.yaml new file mode 100644 index 000000000..737e06af0 --- /dev/null +++ b/kubernetes/flux/repositories/helm/jetstack.yaml @@ -0,0 +1,9 @@ +--- +apiVersion: source.toolkit.fluxcd.io/v1 +kind: HelmRepository +metadata: + name: jetstack + namespace: flux-system +spec: + interval: 1h + url: https://charts.jetstack.io diff --git a/kubernetes/flux/repositories/helm/k8s-gateway.yaml b/kubernetes/flux/repositories/helm/k8s-gateway.yaml new file mode 100644 index 000000000..63a90615e --- /dev/null +++ b/kubernetes/flux/repositories/helm/k8s-gateway.yaml @@ -0,0 +1,9 @@ +--- +apiVersion: source.toolkit.fluxcd.io/v1 +kind: HelmRepository +metadata: + name: k8s-gateway + namespace: flux-system +spec: + interval: 1h + url: https://ori-edge.github.io/k8s_gateway diff --git a/kubernetes/flux/repositories/helm/kustomization.yaml b/kubernetes/flux/repositories/helm/kustomization.yaml new file mode 100644 index 000000000..0f2ad1ca3 --- /dev/null +++ b/kubernetes/flux/repositories/helm/kustomization.yaml @@ -0,0 +1,23 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - bitnami.yaml + - bjw-s.yaml + - cilium.yaml + - coredns.yaml + - external-dns.yaml + - external-secrets.yaml + - ingress-nginx.yaml + - jetstack.yaml + - k8s-gateway.yaml + - kyverno-charts.yaml + - longhorn.yaml + - metrics-server.yaml + - mittwald-charts.yaml + - openebs.yaml + - postfinance.yaml + - prometheus-community.yaml + - spegel.yaml + - stakater.yaml + - weave-gitops.yaml diff --git a/kubernetes/flux/repositories/helm/kyverno-charts.yaml b/kubernetes/flux/repositories/helm/kyverno-charts.yaml new file mode 100644 index 000000000..dbcf2f51b --- /dev/null +++ b/kubernetes/flux/repositories/helm/kyverno-charts.yaml @@ -0,0 +1,10 @@ +--- +apiVersion: source.toolkit.fluxcd.io/v1 +kind: HelmRepository +metadata: + name: kyverno-charts + namespace: flux-system +spec: + type: oci + interval: 5m + url: oci://ghcr.io/kyverno/charts diff --git a/kubernetes/flux/repositories/helm/longhorn.yaml b/kubernetes/flux/repositories/helm/longhorn.yaml new file mode 100755 index 000000000..d9c4116dc --- /dev/null +++ b/kubernetes/flux/repositories/helm/longhorn.yaml @@ -0,0 +1,10 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/source.toolkit.fluxcd.io/helmrepository_v1beta2.json +apiVersion: source.toolkit.fluxcd.io/v1 +kind: HelmRepository +metadata: + name: longhorn + namespace: flux-system +spec: + interval: 1h + url: https://charts.longhorn.io diff --git a/kubernetes/flux/repositories/helm/metrics-server.yaml b/kubernetes/flux/repositories/helm/metrics-server.yaml new file mode 100644 index 000000000..27a44828a --- /dev/null +++ b/kubernetes/flux/repositories/helm/metrics-server.yaml @@ -0,0 +1,9 @@ +--- +apiVersion: source.toolkit.fluxcd.io/v1 +kind: HelmRepository +metadata: + name: metrics-server + namespace: flux-system +spec: + interval: 1h + url: https://kubernetes-sigs.github.io/metrics-server diff --git a/kubernetes/flux/repositories/helm/mittwald-charts.yaml b/kubernetes/flux/repositories/helm/mittwald-charts.yaml new file mode 100755 index 000000000..d501dbe7e --- /dev/null +++ b/kubernetes/flux/repositories/helm/mittwald-charts.yaml @@ -0,0 +1,10 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/source.toolkit.fluxcd.io/helmrepository_v1beta2.json +apiVersion: source.toolkit.fluxcd.io/v1 +kind: HelmRepository +metadata: + name: mittwald-charts + namespace: flux-system +spec: + interval: 1h + url: https://helm.mittwald.de diff --git a/kubernetes/flux/repositories/helm/openebs.yaml b/kubernetes/flux/repositories/helm/openebs.yaml new file mode 100644 index 000000000..4f48013ee --- /dev/null +++ b/kubernetes/flux/repositories/helm/openebs.yaml @@ -0,0 +1,9 @@ +--- +apiVersion: source.toolkit.fluxcd.io/v1 +kind: HelmRepository +metadata: + name: openebs + namespace: flux-system +spec: + interval: 1h + url: https://openebs.github.io/openebs diff --git a/kubernetes/flux/repositories/helm/postfinance.yaml b/kubernetes/flux/repositories/helm/postfinance.yaml new file mode 100644 index 000000000..b14a64d8e --- /dev/null +++ b/kubernetes/flux/repositories/helm/postfinance.yaml @@ -0,0 +1,9 @@ +--- +apiVersion: source.toolkit.fluxcd.io/v1 +kind: HelmRepository +metadata: + name: postfinance + namespace: flux-system +spec: + interval: 1h + url: https://postfinance.github.io/kubelet-csr-approver diff --git a/kubernetes/flux/repositories/helm/prometheus-community.yaml b/kubernetes/flux/repositories/helm/prometheus-community.yaml new file mode 100644 index 000000000..318a1a514 --- /dev/null +++ b/kubernetes/flux/repositories/helm/prometheus-community.yaml @@ -0,0 +1,10 @@ +--- +apiVersion: source.toolkit.fluxcd.io/v1 +kind: HelmRepository +metadata: + name: prometheus-community + namespace: flux-system +spec: + type: oci + interval: 5m + url: oci://ghcr.io/prometheus-community/charts diff --git a/kubernetes/flux/repositories/helm/spegel.yaml b/kubernetes/flux/repositories/helm/spegel.yaml new file mode 100644 index 000000000..d9a8b2cd3 --- /dev/null +++ b/kubernetes/flux/repositories/helm/spegel.yaml @@ -0,0 +1,10 @@ +--- +apiVersion: source.toolkit.fluxcd.io/v1 +kind: HelmRepository +metadata: + name: spegel + namespace: flux-system +spec: + type: oci + interval: 5m + url: oci://ghcr.io/spegel-org/helm-charts diff --git a/kubernetes/flux/repositories/helm/stakater.yaml b/kubernetes/flux/repositories/helm/stakater.yaml new file mode 100644 index 000000000..98a3f6455 --- /dev/null +++ b/kubernetes/flux/repositories/helm/stakater.yaml @@ -0,0 +1,9 @@ +--- +apiVersion: source.toolkit.fluxcd.io/v1 +kind: HelmRepository +metadata: + name: stakater + namespace: flux-system +spec: + interval: 1h + url: https://stakater.github.io/stakater-charts diff --git a/kubernetes/flux/repositories/helm/weave-gitops.yaml b/kubernetes/flux/repositories/helm/weave-gitops.yaml new file mode 100644 index 000000000..49362c1d8 --- /dev/null +++ b/kubernetes/flux/repositories/helm/weave-gitops.yaml @@ -0,0 +1,11 @@ +--- +# yaml-language-server: $schema=https://kubernetes-schemas.pages.dev/source.toolkit.fluxcd.io/helmrepository_v1beta2.json +apiVersion: source.toolkit.fluxcd.io/v1 +kind: HelmRepository +metadata: + name: weave-gitops + namespace: flux-system +spec: + type: oci + interval: 1h + url: oci://ghcr.io/weaveworks/charts diff --git a/kubernetes/flux/repositories/kustomization.yaml b/kubernetes/flux/repositories/kustomization.yaml new file mode 100644 index 000000000..d158d426e --- /dev/null +++ b/kubernetes/flux/repositories/kustomization.yaml @@ -0,0 +1,7 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./git + - ./helm + - ./oci diff --git a/kubernetes/flux/repositories/oci/kustomization.yaml b/kubernetes/flux/repositories/oci/kustomization.yaml new file mode 100644 index 000000000..fe0f332a9 --- /dev/null +++ b/kubernetes/flux/repositories/oci/kustomization.yaml @@ -0,0 +1,4 @@ +--- +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: [] diff --git a/kubernetes/flux/vars/cluster-secrets.sops.yaml b/kubernetes/flux/vars/cluster-secrets.sops.yaml new file mode 100644 index 000000000..acd80cf84 --- /dev/null +++ b/kubernetes/flux/vars/cluster-secrets.sops.yaml @@ -0,0 +1,47 @@ +apiVersion: v1 +kind: Secret +metadata: + name: cluster-secrets + namespace: flux-system +stringData: + SECRET_PRIVATE_DOMAIN: ENC[AES256_GCM,data:COCK8A==,iv:YPYEGGqqDrIMeUX0FbStWD4jmQ9ExTfSPtyn4Qy7uZA=,tag:vyn3CqoW5FLqcHVVZv6RdA==,type:str] + SECRET_DOMAIN: ENC[AES256_GCM,data:HD2+IYTT1NYLy8P0r9b0,iv:4Au1eHFDF2Hvf5ulOS5PdfK4HRbvepJfKsrsLXK5pHA=,tag:gK8oz6RbICG8cGC9PkstBQ==,type:str] + SECRET_CH_DOMAIN: ENC[AES256_GCM,data:OiXW1ncVmlX4Wa8=,iv:Eoh8KbbtEBuYR8KrTbEKPasWZoX2yPLLi7I9jBK4HDY=,tag:0pDUvuRVT/zx20nnpNSM1w==,type:str] + SECRET_ACME_EMAIL: ENC[AES256_GCM,data:sBMQkxk0JKmfd2hyXe+cUIVG56s=,iv:VG1mU8InYp9Rmc7RND4+1irYWW7z/BgkqPSM7UF7mOo=,tag:QNFcui7oWUhyzSC9UpYRkw==,type:str] + SECRET_CLOUDFLARE_TUNNEL_ID: ENC[AES256_GCM,data:VJVigXU8YnnD7IlBpVruPk00WTNsAtrfM6HVaqCxZ3K5/jOj,iv:rspNCQYW7oxa44qWidGebFKdmuY6uHjwPT1x/MaLX1k=,tag:sVCnjhEexxd6sq68tougIg==,type:str] + #ENC[AES256_GCM,data:ywv/N6Rv,iv:fRH8YMj1C4zISA3roX2p8MH9snV1toX1NBXhQSvNW9c=,tag:8QRAHb2FTh3ArRAJ6sLxow==,type:comment] + SECRET_MINIO_BEARERTOKEN: ENC[AES256_GCM,data:03nx9nZQtVqsYW3BTjGqyN9lyHfHQRKcv1GsvoxsEDXPrniq7V8Jstqu+IQMNNkv/dOyxJQ33MmCjIsbTTMort8j/hGoPBJ1YFxNnkz+zxLM9vIcDNk4LzfN+uQaOD8a7WMl2Z+2MOTF6eqeTbs5U/w5PqSpmLqnXqHZZy2rVNUPnveLia+FqmEeEIVCJL5PCoI5ykceyCs0mgz8hVOVImLsJ0ecUSnvj0RaH6hSgTSIptC52TMymLOupjhCo8uF,iv:WsFTXI1h78xThvggo+Fsjj7QM4ylk1IMFfOiAY7PDHI=,tag:yX5B5qX1f3aSLmUV6O0T+w==,type:str] + #ENC[AES256_GCM,data:/vTntgGpTGHTG4Q=,iv:ia/tLuhey8RGt/JQ2BAHJY4T3/IZk15I9/9H8qZlIY0=,tag:DxmWxLCOJnO92aQuppRM6A==,type:comment] + SECRET_ALERT_MANAGER_DISCORD_WEBHOOK: ENC[AES256_GCM,data:Fc/8+wmOTy5fBx6abKhXmUItKIRNIrRmzl+Qzx/gu+9GX5Ril2U5iPmyiKX7EzaHzq6gyliRj6miW4wlOxSM0GkXwsto0CufEetC7us2N/Pd4RisUCgISrAHlGfYndcOJ3Dx+7Y92/p6WHyOpqiXUlOacQOy0+u30j4=,iv:FOWLuki3FuY4J3dSTpuyW7c0Qwdui0GGK6/nHDPQ11Q=,tag:WGVn2u3R2/ukfBWw5KVD6A==,type:str] + #ENC[AES256_GCM,data:4EC/oOxC45B5,iv:cBBrEvAosviU9VnsSmSMkxyYGEUkXgtUMlzAr2Jxr58=,tag:Y1vSWz6RQBrQPqy7b/DRpg==,type:comment] + SECRET_PLEXTOKEN: ENC[AES256_GCM,data:R3V6YFNsyZ9wLZgB8K89T2tNMBc=,iv:s1p8qSkSQivGyfuCHsJ8DbY528ElcRS8nwWEu4Xhwtk=,tag:EHwYyVmMiWacK8gn6Vg2wQ==,type:str] + SECRET_SONARR_URL: ENC[AES256_GCM,data:J4cZ1L8hda+kCqgiWoUj9xZjiG8SYqg=,iv:qKBbH4+82UZuH3j/NLt+M25BdzMW6e9TcE0TRrTFbhg=,tag:fBmBhDh+FXFHvuL7HAy9kQ==,type:str] + SECRET_SONARR_API_KEY: ENC[AES256_GCM,data:I11goqwjUchQgJypjH4CKGNztNwR3YJxY3Xu5IPYpzw=,iv:pJ8TBEIeI5M7b5KRw5cmQr7v60/4lfMQstrMVL1eW88=,tag:ye1xN07obAzqPPFsIhBu9Q==,type:str] + SECRET_RADARR_URL: ENC[AES256_GCM,data:35PnVcsHzGLGyKT1BlxuUsd6Sb1tqUM=,iv:3XW/uDyf6tD91kRsFB/Ql6NO9E8CrnKGUPpifrAq4Ko=,tag:tAz0IPp6VIeTQxnaDEz1jg==,type:str] + SECRET_RADARR_API_KEY: ENC[AES256_GCM,data:azSW9joHc1gdDrguntMkYaF6XvWtw9rtcBfN1pkYgaY=,iv:07pORlBnWlQUhVo64o1amDrNdUe+cLSXoyszovMS/H8=,tag:veD3LMyo1abGqIni8j4gpw==,type:str] + SECRET_TAUTULLI_URL: ENC[AES256_GCM,data:MYEA+aTazCuoYCuA2sab7TcbTv4n2rSXRb8VTkifaAN1AGePideAKcZASzo=,iv:k2ryKDGPzqXCXAvwgIzxauKSXAUR3LmXNCGzMpLh+0c=,tag:9q8zx48psuJwzrugR5wIZQ==,type:str] + SECRET_TAUTULLI_API_KEY: ENC[AES256_GCM,data:r04w84Bi6MjyCLcCJtxkQGdUMmC0xUajlqYTNGCqJAQ=,iv:9UuQu8lp0I4nAX/f9MsZaYwmmZYMzahsUKWLDoRoIA4=,tag:OQj9uZNt6kkydoyRgPAPIQ==,type:str] + SECRET_PROWLARR_URL: ENC[AES256_GCM,data:tX0H4NH+/N3xzN8c8u/C0jXqfi+x158=,iv:Lka+R1n720ka/POIEUDXRzUJgHntL87NokKby9QqqKg=,tag:qdv514L0dYvajKsOOy+kuA==,type:str] + SECRET_PROWLARR_API_KEY: ENC[AES256_GCM,data:l4BT7qluGPmWc970fryd86wUigCliiGTXJGPj5TtXRs=,iv:h15UohQUJcLakpFHfygHHSLgFRjPsmvF4Ei7EbJL64k=,tag:XnDJgfRcyykZUBLzRqW0lQ==,type:str] + #ENC[AES256_GCM,data:L3utkl/lQPQ=,iv:OnYd2zjfqEhwvw6SaLa1Q7Cn+NuN79XmyZ0O2TNVx1U=,tag:xWOP2XT8TwQbCSUjlL849g==,type:comment] + SECRET_YOUTUBE_TOKEN: ENC[AES256_GCM,data:4Fk+AV92SmT72m5Obe94kaU9lNgDpbcyF7zid9l1U9PHepNA6FcX,iv:d0OGqp7HPp11uoIRj+ZMKIjLZLimzsMXJ7sqGoHheoM=,tag:aUSyV8TNjsFCZV+3+9Vjsg==,type:str] +sops: + kms: [] + gcp_kms: [] + azure_kv: [] + hc_vault: [] + age: + - recipient: age1y0kzuf0tn94a74whazwae4r9qal4snuqfuhl5jacscrpr7up5gts74fe5w + enc: | + -----BEGIN AGE ENCRYPTED FILE----- + YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBmYmhiZ0llMG52ejgxQnk5 + OTMwanhxQU51dngyTGUxUDVGTWVvN1F6c240ClRDMFR1YmpXc1pBOTVBZGFZay81 + MnlETWQ5RzdzL1U0ZG50WStNS2tPNmsKLS0tIFJYbHFMSWwzU3dKcmx0MFpCMVNY + SWRQZ2p4OUNSeTMyRnVNUWdmR3B2cTQK7LMzvv7DygENOwcwdv95kL9L7ohUzW/B + FESqyAt3DdZD/uvxVViM0KJ2Ktfugi3HP0jOCKWNBchps+mn8qdoWQ== + -----END AGE ENCRYPTED FILE----- + lastmodified: "2024-06-07T06:37:11Z" + mac: ENC[AES256_GCM,data:6iyDHjBh3xxD3BUxzPVsfwSzvNxPCTOJMyyKLaXcYgkZEtp5817HOJPuUYz+/cJFpI+Csjrw0bNdDZ5Cb3SECGfSPp9iiMe5THkJ29snSXFdbeu4DVtKlPjzfdK1vBhzqC++VDANlm8lk9E18qwFuY12p5Si0iYRMF2+BzISx3g=,iv:bIBekPp0+qzufTS5CNmjXm3ZqsALP0q2tYDZgJ1lbgM=,tag:kT23gq8/DPjYfkuBy5dSaw==,type:str] + pgp: [] + encrypted_regex: ^(data|stringData)$ + version: 3.8.1 diff --git a/kubernetes/flux/vars/cluster-settings.yaml b/kubernetes/flux/vars/cluster-settings.yaml new file mode 100644 index 000000000..4c7f910fc --- /dev/null +++ b/kubernetes/flux/vars/cluster-settings.yaml @@ -0,0 +1,9 @@ +--- +apiVersion: v1 +kind: ConfigMap +metadata: + name: cluster-settings + namespace: flux-system +data: + TIMEZONE: Europe/Zurich + MAIN_SC: longhorn diff --git a/kubernetes/flux/vars/kustomization.yaml b/kubernetes/flux/vars/kustomization.yaml new file mode 100644 index 000000000..8db2fe911 --- /dev/null +++ b/kubernetes/flux/vars/kustomization.yaml @@ -0,0 +1,5 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - ./cluster-settings.yaml + - ./cluster-secrets.sops.yaml diff --git a/scripts/rebuild-kustomizations.sh b/scripts/rebuild-kustomizations.sh new file mode 100755 index 000000000..bc33f6c5c --- /dev/null +++ b/scripts/rebuild-kustomizations.sh @@ -0,0 +1,39 @@ +#!/usr/bin/env bash + +FOLDERS="kubernetes/flux/repositories/oci kubernetes/flux/repositories/helm kubernetes/flux/repositories/git" + +_pwd="$(pwd)" +_basedir="${_pwd}/$(dirname $(which ${0}))" + +cd ${_basedir} && cd $(git rev-parse --show-toplevel) + +_gitdir="$(git rev-parse --show-toplevel)" + +# https://github.com/lyz-code/yamlfix/blob/main/docs/index.md#configure-environment-prefix +export YAMLFIX_SEQUENCE_STYLE="block_style" + +for i in ${FOLDERS}; do + cd ${i} + f=$(ls -1 | grep -v kustomization.yaml) + if [[ ! -z "${f}" ]]; then + rm -f kustomization.yaml + kustomize create --autodetect + #gawk -i inplace 'NR==1{print "# yaml-language-server: $schema=https://json.schemastore.org/kustomization"}1' kustomization.yaml + yamlfix kustomization.yaml + fi + cd ${_gitdir} +done + +cd ${_gitdir} + +for d in $(for i in $(find kubernetes -name ks.yaml); do echo $i | rev | cut -d/ -f3- | rev; done | sort -u); do + cd ${d} + rm -f kustomization.yaml + kustomize create --autodetect + for k in */ks.yaml; do + kustomize edit add resource ${k} + done + #gawk -i inplace 'NR==1{print "# yaml-language-server: $schema=https://json.schemastore.org/kustomization"}1' kustomization.yaml + yamlfix kustomization.yaml + cd ${_gitdir} +done