Gate Prometheus behind Authentik #147
@@ -545,6 +545,88 @@ data:
|
||||
kubernetes_ingress_secret_name: "authentik-outpost-tls"
|
||||
kubernetes_json_patches: null
|
||||
|
||||
# ------------------------------------------------------------------
|
||||
# prometheus gate
|
||||
#
|
||||
# Prometheus (prometheus.renner.uno, monitoring ns, :9090) had no auth
|
||||
# of its own. Its admin API is disabled (read-only), but the full 90d
|
||||
# metrics DB is an infra-recon oracle — hostnames, IPs, service
|
||||
# inventory (2026-07-10 audit). Same proxy-outpost pattern as
|
||||
# alertmanager-gate above; reuses the shared "Monitoring Access" group
|
||||
# (created generically for exactly this). Grafana is unaffected — it
|
||||
# queries the ClusterIP Service, not this ingress.
|
||||
- id: prometheus-gate-provider
|
||||
model: authentik_providers_proxy.proxyprovider
|
||||
identifiers:
|
||||
name: prometheus-gate
|
||||
state: present
|
||||
attrs:
|
||||
authorization_flow: !Find [authentik_flows.flow, [slug, default-provider-authorization-implicit-consent]]
|
||||
invalidation_flow: !Find [authentik_flows.flow, [slug, default-provider-invalidation-flow]]
|
||||
mode: proxy
|
||||
internal_host: http://kube-prometheus-stack-prometheus.monitoring.svc.cluster.local:9090
|
||||
internal_host_ssl_validation: false
|
||||
external_host: https://prometheus.renner.uno
|
||||
cookie_domain: renner.uno
|
||||
access_token_validity: hours=24
|
||||
refresh_token_validity: days=30
|
||||
intercept_header_auth: true
|
||||
# No skip_path_regex: the Prometheus UI is a plain React SPA with no
|
||||
# service worker and no manifest (verified 2026-07-10 — index.html
|
||||
# has no serviceWorker/manifest/webmanifest refs), same as the
|
||||
# Alertmanager UI, so no credentials:'omit' PWA fetches to carve out.
|
||||
|
||||
- model: authentik_core.application
|
||||
identifiers:
|
||||
slug: prometheus-gate
|
||||
state: present
|
||||
attrs:
|
||||
name: Prometheus (Gate)
|
||||
slug: prometheus-gate
|
||||
provider: !KeyOf prometheus-gate-provider
|
||||
meta_launch_url: https://prometheus.renner.uno
|
||||
meta_description: "Authentik-gated Prometheus"
|
||||
|
||||
# Only the Monitoring Access group passes the gate (shared with
|
||||
# alertmanager-gate).
|
||||
- model: authentik_policies.policybinding
|
||||
identifiers:
|
||||
target: !Find [authentik_core.application, [slug, prometheus-gate]]
|
||||
group: !KeyOf monitoring-access-group
|
||||
order: 0
|
||||
state: present
|
||||
attrs:
|
||||
enabled: true
|
||||
negate: false
|
||||
failure_result: false
|
||||
|
||||
- model: authentik_outposts.outpost
|
||||
identifiers:
|
||||
name: prometheus-gate
|
||||
state: present
|
||||
attrs:
|
||||
type: proxy
|
||||
service_connection: !KeyOf k8s-conn
|
||||
providers:
|
||||
- !KeyOf prometheus-gate-provider
|
||||
config:
|
||||
log_level: info
|
||||
authentik_host: "http://authentik-server.authentik.svc.cluster.local"
|
||||
authentik_host_insecure: false
|
||||
authentik_host_browser: "https://auth.renner.uno/"
|
||||
refresh_interval: "minutes=5"
|
||||
container_image: null
|
||||
object_naming_template: "ak-outpost-%(name)s"
|
||||
kubernetes_namespace: authentik
|
||||
kubernetes_replicas: 1
|
||||
kubernetes_service_type: ClusterIP
|
||||
kubernetes_disabled_components: ["ingress"]
|
||||
kubernetes_image_pull_secrets: []
|
||||
kubernetes_ingress_annotations: {}
|
||||
kubernetes_ingress_class_name: null
|
||||
kubernetes_ingress_secret_name: "authentik-outpost-tls"
|
||||
kubernetes_json_patches: null
|
||||
|
||||
- model: authentik_outposts.outpost
|
||||
identifiers:
|
||||
name: authentik Embedded Outpost
|
||||
|
||||
@@ -10,6 +10,7 @@ resources:
|
||||
- vscode-gate-egress.yaml
|
||||
- shelly-manager-gate-egress.yaml
|
||||
- alertmanager-gate-egress.yaml
|
||||
- prometheus-gate-egress.yaml
|
||||
- outpost-servicemonitors.yaml
|
||||
- ldap-outpost-cert.yaml
|
||||
- ldap-outpost-lb.yaml
|
||||
|
||||
@@ -0,0 +1,24 @@
|
||||
---
|
||||
# Allow the dedicated prometheus-gate outpost to egress into the monitoring
|
||||
# namespace and reach Prometheus (:9090). Without this, the authentik
|
||||
# baseline CNP has no egress rule to monitoring, so the gate outpost's
|
||||
# forwarded requests are dropped. Scoped to the gate outpost's pod label.
|
||||
# Mirrors alertmanager-gate-egress.yaml.
|
||||
apiVersion: cilium.io/v2
|
||||
kind: CiliumNetworkPolicy
|
||||
metadata:
|
||||
name: prometheus-gate-egress
|
||||
namespace: authentik
|
||||
spec:
|
||||
endpointSelector:
|
||||
matchLabels:
|
||||
goauthentik.io/outpost-name: prometheus-gate
|
||||
egress:
|
||||
- toEndpoints:
|
||||
- matchLabels:
|
||||
"k8s:io.kubernetes.pod.namespace": monitoring
|
||||
app.kubernetes.io/name: prometheus
|
||||
toPorts:
|
||||
- ports:
|
||||
- port: "9090"
|
||||
protocol: TCP
|
||||
@@ -33,21 +33,24 @@ spec:
|
||||
values:
|
||||
# Prometheus
|
||||
prometheus:
|
||||
# LAN-only ingress at prometheus.renner.uno. No
|
||||
# external-dns/cloudflare label, so only external-dns-unifi
|
||||
# publishes the hostname — resolves on LAN, NXDOMAIN from the
|
||||
# public internet.
|
||||
# prometheus.renner.uno is served by a standalone, Authentik-gated
|
||||
# Ingress (prometheus-gate-ingress.yaml), NOT this Helm-generated one.
|
||||
# Prometheus had no auth of its own — its full 90d metrics DB is an
|
||||
# infra-recon oracle (hostnames, IPs, service inventory). Gated behind
|
||||
# the prometheus-gate proxy outpost, same as alertmanager-gate (#146).
|
||||
# The chart Ingress is disabled here — two Ingresses for one host would
|
||||
# conflict. tls (prometheus-tls) and externalUrl below are unchanged;
|
||||
# the standalone Ingress reuses the same secret.
|
||||
#
|
||||
# Grafana is unaffected: its datasource targets the ClusterIP Service
|
||||
# (kube-prometheus-stack-prometheus.monitoring:9090), not this ingress.
|
||||
# Blackbox uptime probes that target https://prometheus.renner.uno
|
||||
# follow the gate's 302 to the Authentik login (200), so they stay
|
||||
# green — but now measure Authentik reachability, not Prometheus. Same
|
||||
# already-true for alerts.renner.uno since #146. Repointing those probes
|
||||
# to an internal endpoint is a separate follow-up.
|
||||
ingress:
|
||||
enabled: true
|
||||
ingressClassName: traefik
|
||||
annotations:
|
||||
cert-manager.io/cluster-issuer: letsencrypt-cluster
|
||||
hosts:
|
||||
- prometheus.renner.uno
|
||||
tls:
|
||||
- secretName: prometheus-tls
|
||||
hosts:
|
||||
- prometheus.renner.uno
|
||||
enabled: false
|
||||
prometheusSpec:
|
||||
# Rewrites the in-cluster URL embedded in alert generatorURLs and
|
||||
# status pages so click-through from emails works.
|
||||
|
||||
@@ -14,6 +14,8 @@ resources:
|
||||
- loki-ingress.yaml
|
||||
- alertmanager-gate-service.yaml
|
||||
- alertmanager-gate-ingress.yaml
|
||||
- prometheus-gate-service.yaml
|
||||
- prometheus-gate-ingress.yaml
|
||||
- dashboards/
|
||||
# prometheusrule-garage.yaml lives in ./monitoring-rules/ and is applied by a
|
||||
# separate Flux Kustomization that dependsOn `monitoring` — otherwise the
|
||||
|
||||
@@ -0,0 +1,39 @@
|
||||
---
|
||||
# prometheus.renner.uno — Prometheus, gated behind Authentik.
|
||||
#
|
||||
# Prometheus has no auth of its own; its admin API is disabled (read-only),
|
||||
# but the full 90d metrics DB exposes hostnames, IPs and service inventory
|
||||
# to any unauthenticated LAN client. This Ingress backends the Authentik
|
||||
# prometheus-gate proxy outpost (ExternalName → authentik ns); the
|
||||
# monitoring CNP allows only that outpost to reach :9090. Replaces the
|
||||
# Helm-chart-generated Prometheus Ingress (disabled via
|
||||
# prometheus.ingress.enabled=false in helmrelease-prometheus.yaml) — two
|
||||
# Ingresses for the same host would conflict. Mirrors
|
||||
# alertmanager-gate-ingress.yaml.
|
||||
#
|
||||
# Grafana is unaffected: its datasource targets the ClusterIP Service
|
||||
# (kube-prometheus-stack-prometheus:9090), not this hostname.
|
||||
apiVersion: networking.k8s.io/v1
|
||||
kind: Ingress
|
||||
metadata:
|
||||
name: prometheus-gate
|
||||
namespace: monitoring
|
||||
annotations:
|
||||
cert-manager.io/cluster-issuer: letsencrypt-cluster
|
||||
spec:
|
||||
ingressClassName: traefik
|
||||
rules:
|
||||
- host: prometheus.renner.uno
|
||||
http:
|
||||
paths:
|
||||
- path: /
|
||||
pathType: Prefix
|
||||
backend:
|
||||
service:
|
||||
name: ak-outpost-prometheus-gate
|
||||
port:
|
||||
number: 9000
|
||||
tls:
|
||||
- secretName: prometheus-tls
|
||||
hosts:
|
||||
- prometheus.renner.uno
|
||||
@@ -0,0 +1,22 @@
|
||||
---
|
||||
# ExternalName mirror so the monitoring-namespace Prometheus gate Ingress
|
||||
# can backend to the prometheus-gate outpost that Authentik deploys into the
|
||||
# authentik namespace (cross-namespace Service refs aren't supported in a
|
||||
# standard Ingress). Mirrors ak-outpost-alertmanager-gate.
|
||||
#
|
||||
# Traffic path:
|
||||
# browser → traefik (prometheus.renner.uno)
|
||||
# → ak-outpost-prometheus-gate (ExternalName → authentik ns)
|
||||
# → outpost validates the Authentik session
|
||||
# → http://kube-prometheus-stack-prometheus.monitoring.svc:9090
|
||||
apiVersion: v1
|
||||
kind: Service
|
||||
metadata:
|
||||
name: ak-outpost-prometheus-gate
|
||||
namespace: monitoring
|
||||
spec:
|
||||
type: ExternalName
|
||||
externalName: ak-outpost-prometheus-gate.authentik.svc.cluster.local
|
||||
ports:
|
||||
- port: 9000
|
||||
targetPort: 9000
|
||||
@@ -39,6 +39,17 @@ spec:
|
||||
- ports:
|
||||
- port: "9093"
|
||||
protocol: TCP
|
||||
# The Authentik prometheus-gate outpost forwards gated browser traffic
|
||||
# to Prometheus :9090. Same scoping as alertmanager-gate above. Matching
|
||||
# egress: authentik/prometheus-gate-egress.yaml.
|
||||
- fromEndpoints:
|
||||
- matchLabels:
|
||||
"k8s:io.kubernetes.pod.namespace": authentik
|
||||
goauthentik.io/outpost-name: prometheus-gate
|
||||
toPorts:
|
||||
- ports:
|
||||
- port: "9090"
|
||||
protocol: TCP
|
||||
# Kubelet probes + control-plane (PrometheusRule/ServiceMonitor admission
|
||||
# webhooks via kube-prometheus-stack-operator are called by kube-apiserver).
|
||||
# Also covers external alloy-syslog traffic — ETP=Cluster on the LB SNATs
|
||||
|
||||
Reference in New Issue
Block a user