Skip to content

Repository files navigation

Fleetsweeper: the fleet is the policy

The cluster that drifted is the one that pages you at 3am.
Fleetsweeper finds it before it does.

Release Go reference License: MIT

Fleetsweeper flags the one cluster that drifted from the fleet norm


You run twelve clusters. Or fifty. Or two hundred. They started identical and they did not stay that way. Versions skew. Admission policies drift. Service accounts get patched at 3am and nobody writes it down. Every cluster is "healthy" on its own, so every tool you already own stays quiet. Fleetsweeper finds the one cluster that wandered off the herd.

The fleet itself is the baseline. No rulebook. No rules to write. The modified z-score across your own clusters does the work.

What you walk away with after one scan

  • A Fleet Score from 0 to 100 with a one-line headline you can put on a status TV.
  • The cluster that is most unlike the rest, plus the exact fields that flagged it.
  • Ranked, leverage-weighted recommendations. The fix that takes ten clusters from drifted to clean ranks ahead of the same fix on one.
  • An optional admission webhook that flags pods deviating from your fleet's actual norm, not from a static checklist. It warns by default and never denies until you have read the warnings and opted into enforcement; the rollout path is warn first, enforce on purpose.
  • One unified stream for inbound signal: scan findings, AlertManager, Falco, Trivy CVEs, Kyverno and Gatekeeper PolicyReports.

How scoring works

A scan scores your fleet in two steps.

1. Find the clusters that differ from the rest. Every scanner reports fields per cluster, and each field is compared across the fleet and across each tagged cohort.

  • Numbers (privileged containers, CRD count, pod restarts) use the modified z-score, 0.6745 * (value - median) / MAD. A cluster is flagged when that score passes 3.5 in either direction. The median and MAD come from your own clusters, so one broken cluster cannot widen the band that is meant to catch it.
  • Strings (PSA mode, ingress class) flag every cluster off the most common value, once that value holds at least 60% of the fleet.
  • Lists (installed CRDs) flag a cluster missing any item that at least 60% of the fleet has.

What moves the result:

  • Fleet size. The z-score needs 8 or more clusters. Fleets of 3 to 7 use a stricter leave-one-out rule that flags at most one cluster per field and caps it at warning. Under 3 clusters nothing is flagged, and the report says why.
  • Agreement. A number most clusters share exactly (MAD of zero) is judged like a string. Once one value holds at least 60% of the fleet, every cluster off it is flagged, and the finding reads "every other cluster in the fleet reports exactly 0" instead of quoting a score. A field where no value reaches 60% is skipped. There is no norm to break.
  • Cohorts. A cluster that matches its own tagged cohort (edge sites, say) is not charged for differing from the rest of the fleet.
  • Sensitivity. scan --outlier-threshold and ?threshold= on /api/outliers change the 3.5 cutoff. Lower flags more.

2. Turn what was found into a score. A flagged field becomes a finding. Its severity comes from which field drifted, not from how far. Privileged containers or cluster-admin bindings are critical, node counts are a warning, and most other fields are info. Direction counts too. A cluster on the better side of a field where only one direction is bad (fewer privileged containers than the fleet) is info, titled better than the norm. A finding that restates another one on the same cluster is dropped, so one fact is charged once. The Fleet Score starts at 100 and subtracts:

Cost Points
Each critical, warning, info finding 6, 1.5, 0.25 (capped at 36, 24, 5)
Share of clusters in critical status Up to 20
Share of clusters degraded or strained Up to 10
Kubernetes minor version skew 10 for two or more, 3 for one
Unhealthy nodes in the worst cluster Up to 10

The three largest costs come back as the score's drivers, so the number always arrives with the reason for it.

The details are in Outliers for the detection math, Fleet Score for every cost and cap, and Findings for how severity is chosen.

Consistency is not correctness

The Fleet Score measures one thing: how much your clusters deviate from each other. It is a consistency number, not a correctness number.

That has a specific failure mode, and you should know it before you put the number on a TV. If all fifty of your clusters allow privileged pods, skip resource limits, and run the same end-of-life Kubernetes version, there is no deviation to find. The fleet agrees with itself, so it scores well. A uniformly misconfigured fleet looks the same as a uniformly well-configured one, because the baseline is the fleet, not a standard.

So a Fleet Score of 87 means your clusters mostly agree with each other, and the drivers name the few places they do not. It does not mean they are secure, patched, or compliant with anything. Every score also carries its provenance: how many clusters and scan dimensions produced it, and how many clusters were excluded for insufficient data. A score built from six clusters is a weaker claim than one built from sixty, and the report says which one you are looking at.

A score is also only as good as what the scan could see. A scan that could not observe a cluster says so and is not graded, and a finding is never produced from a read that failed.

Fleetsweeper is therefore not a replacement for policy engines, CIS benchmarks, or vulnerability scanning. Those check clusters against absolute rules, and they are the tools that catch the failure mode above. What they cannot catch is the drift and the one-off snowflake cluster that fleetsweeper exists to find, because nobody wrote a rule for it. Run both: Kyverno or Gatekeeper for the rules you can write down, Fleetsweeper for the anomalies you did not know to write a rule for. The PolicyReport integration feeds their violations into the same finding stream, so the pairing is already wired in.

See it in 30 seconds

go install github.com/dcadolph/fleetsweeper@latest
fleetsweeper serve --demo --addr :8080

Open http://localhost:8080. A synthetic 26-cluster fleet with six days of scan history renders with a 3D globe, findings, drift, outliers, capacity, and a guided tour. No kubeconfig required. The demo is real scan data run through the real engine, so every number on screen is one the engine computed. Auth is off in the demo, so the scan trigger, acks, and tags all work. Real data needs --auth-token. The pulsing red dot is the cinematic part. The outlier detection under it is the real part.

Install for real

helm install fleetsweeper deploy/helm/fleetsweeper \
  --set auth.token=$(openssl rand -hex 32) \
  --set controller.enabled=true
kubectl apply -f deploy/examples/clusterscan-prod.yaml

The controller reconciles ClusterScan resources and writes outcomes back to .status. Full installation paths in docs/operator/helm.md. Scoped API keys for pipelines in docs/operator/rbac.md.

Why this and not what you already have

You already use What it tells you What Fleetsweeper adds
kubectl, k9s The state of one cluster, right now. A fleet-wide comparison across 24 dimensions. Names the outlier.
Argo CD, Flux Whether each cluster matches its manifest. Drift across clusters even when every cluster matches its own source of truth.
Prometheus, Grafana Time series for what you remembered to instrument. Statistical baselines derived from the fleet, with no rules to write.
OPA, Kyverno Violations against rules you authored. Detects drift you forgot to write a rule for. Complements, does not replace.

Production-ready out of the box

HA backends, leader election, scoped RBAC, audit log, declarative CRDs, Prometheus and OpenTelemetry, signed reports, backups, GitOps integrations, admission webhook, and supply-chain signed images. Full checklist: docs/production-readiness.md.

Where to go next

Start here

Concepts

Operator

Integrations

Reference

Contributing

Issues and PRs welcome. Start with CONTRIBUTING.md and the code of conduct. Security disclosures go through SECURITY.md.

License

MIT. See LICENSE.

Releases

Packages

Contributors

Languages