Documentation
¶
Overview ¶
Package gitops provides Flux CD graph discovery, change impact analysis, and reconciliation coordination.
Core rule: if Flux already knows it, StageFreight discovers it — never asks for it. No duplicated topology config. No declared kustomization lists. Flux is truth. StageFreight is the intelligence + evidence layer.
Index ¶
- func BuildKubeconfig(ctx context.Context, cfg config.ClusterConfig, rctx *runtime.RuntimeContext, ...) error
- func BuildRoots(graph *FluxGraph) []string
- func CycleNodes(graph *FluxGraph) map[KustomizationKey]bool
- func DanglingDeps(graph *FluxGraph) map[KustomizationKey][]KustomizationKey
- func DuplicatePaths(graph *FluxGraph) map[string][]KustomizationKey
- func GetChangedFiles(repoDir, base, head string) ([]string, error)
- func NormalizePath(p string) string
- func SortKeys(keys []KustomizationKey)
- func SortedKinds(m map[string]int) []string
- type BootstrapState
- type Finding
- type FluxBackend
- func (f *FluxBackend) Capabilities() []runtime.Capability
- func (f *FluxBackend) Cleanup(rctx *runtime.RuntimeContext)
- func (f *FluxBackend) Execute(ctx context.Context, plan *runtime.LifecyclePlan, rctx *runtime.RuntimeContext) (*runtime.LifecycleResult, error)
- func (f *FluxBackend) Name() string
- func (f *FluxBackend) Plan(ctx context.Context, cfg *config.Config, rctx *runtime.RuntimeContext) (*runtime.LifecyclePlan, error)
- func (f *FluxBackend) Prepare(ctx context.Context, cfg *config.Config, rctx *runtime.RuntimeContext) error
- func (f *FluxBackend) Validate(ctx context.Context, cfg *config.Config, rctx *runtime.RuntimeContext) error
- type FluxGraph
- type FluxReconcileResult
- type ImpactResult
- type KustomizationKey
- type KustomizationNode
- type SchemaFinding
- type Status
- type ValidationMeta
- type Verdict
Constants ¶
This section is empty.
Variables ¶
This section is empty.
Functions ¶
func BuildKubeconfig ¶
func BuildKubeconfig(ctx context.Context, cfg config.ClusterConfig, rctx *runtime.RuntimeContext, desired map[string]config.ToolConstraint) error
BuildKubeconfig creates an isolated kubeconfig for the target cluster. CA is resolved from environment: <PREFIX>_CA_FILE or <PREFIX>_CA_B64. OIDC token is resolved from STAGEFREIGHT_OIDC. All ephemeral files are registered for cleanup on rctx.Resolved.
func BuildRoots ¶ added in v0.7.0
BuildRoots returns the unique, normalized, non-empty kustomization paths in the graph — the set of directories to `kustomize build` exactly once. Multiple Flux Kustomizations pointing at the same path collapse to a single root, so shared manifests are not rendered (and re-validated) once per owner. Deterministic: lexically sorted.
func CycleNodes ¶ added in v0.7.0
func CycleNodes(graph *FluxGraph) map[KustomizationKey]bool
CycleNodes returns the set of kustomizations that cannot be topologically placed — those in, or downstream of, a dependency cycle. These are the keys a validation verdict marks as failed with a cycle reason: the dependency intent is incoherent and Flux itself would deadlock on them.
func DanglingDeps ¶ added in v0.7.0
func DanglingDeps(graph *FluxGraph) map[KustomizationKey][]KustomizationKey
DanglingDeps returns, per kustomization, the dependsOn references that point at a kustomization not present in the discovered graph. The referrer is the key a validation verdict marks — its declared dependency cannot be satisfied from this repository.
func DuplicatePaths ¶
func DuplicatePaths(graph *FluxGraph) map[string][]KustomizationKey
DuplicatePaths returns paths owned by multiple kustomizations.
func GetChangedFiles ¶
GetChangedFiles returns files changed between two refs using three-dot (merge-base) diff semantics, with two-dot fallback if merge-base fails.
func NormalizePath ¶
NormalizePath cleans a path for consistent matching.
func SortKeys ¶
func SortKeys(keys []KustomizationKey)
SortKeys sorts kustomization keys lexically by namespace/name.
func SortedKinds ¶ added in v0.7.0
SortedKinds returns the kinds of a count map in descending count, then name.
Types ¶
type BootstrapState ¶
BootstrapState indicates whether Flux bootstrapping is needed.
func DetectBootstrapRequired ¶
func DetectBootstrapRequired(graph *FluxGraph) BootstrapState
DetectBootstrapRequired checks if Flux bootstrapping is needed. Stub for now — returns false. Hook wired for future extension.
type Finding ¶ added in v0.7.0
type Finding struct {
Severity Status
Source string
Message string
// Schema carries the normalized, provenance-bearing form of a schema-validation
// finding (core-schema / crd-catalog): the offending field, interpreted rule, and
// the raw validator transcript for the escape hatch. Nil for non-schema findings
// (graph/render) — those use Message directly.
Schema *SchemaFinding
}
Finding is one piece of evidence against a Kustomization. Severity carries its authority class and Source its provenance, so operators can distinguish "Kubernetes will reject this" (authoritative) from "a community catalog thinks this might be wrong" (heuristic). Sources: "graph" (dependsOn integrity), "render" (kustomize build / raw-manifest stream), "core-schema" (built-in Kubernetes schemas — authoritative), "crd-catalog" (datreeio CRD catalog — advisory; see docs/architecture/gitops-fluxcd-validation.md).
type FluxBackend ¶
type FluxBackend struct {
// contains filtered or unexported fields
}
FluxBackend implements runtime.LifecycleBackend for Flux CD reconciliation.
func (*FluxBackend) Capabilities ¶
func (f *FluxBackend) Capabilities() []runtime.Capability
func (*FluxBackend) Cleanup ¶
func (f *FluxBackend) Cleanup(rctx *runtime.RuntimeContext)
Cleanup is handled by rctx.Resolved cleanup funcs registered in Prepare.
func (*FluxBackend) Execute ¶
func (f *FluxBackend) Execute(ctx context.Context, plan *runtime.LifecyclePlan, rctx *runtime.RuntimeContext) (*runtime.LifecycleResult, error)
Execute runs flux reconcile on the planned set. Idempotent: repeated execution converges to the same state.
func (*FluxBackend) Name ¶
func (f *FluxBackend) Name() string
func (*FluxBackend) Plan ¶
func (f *FluxBackend) Plan(ctx context.Context, cfg *config.Config, rctx *runtime.RuntimeContext) (*runtime.LifecyclePlan, error)
Plan discovers the Flux graph, computes impact, and builds the reconcile set. Deterministic: identical config + inputs → identical output.
func (*FluxBackend) Prepare ¶
func (f *FluxBackend) Prepare(ctx context.Context, cfg *config.Config, rctx *runtime.RuntimeContext) error
Prepare builds an isolated kubeconfig for the target cluster. Skipped if no cluster config is present (local dev).
func (*FluxBackend) Validate ¶
func (f *FluxBackend) Validate(ctx context.Context, cfg *config.Config, rctx *runtime.RuntimeContext) error
Validate checks that the flux CLI is available and cluster config is complete.
type FluxGraph ¶
type FluxGraph struct {
Kustomizations map[KustomizationKey]KustomizationNode
ReverseDeps map[KustomizationKey][]KustomizationKey
}
FluxGraph is the discovered dependency graph of Flux Kustomizations.
func DiscoverFluxGraph ¶
DiscoverFluxGraph walks the repo and discovers all Flux Kustomization objects. Builds forward and reverse dependency graphs. No config needed — everything is derived from the actual manifests.
type FluxReconcileResult ¶
type FluxReconcileResult struct {
Kustomization string
Namespace string
Attempted bool
Success bool
Duration time.Duration
Ready bool
Message string
}
FluxReconcileResult reports the outcome of reconciling one kustomization. Kept for backward compatibility with existing CLI output rendering.
func Reconcile ¶
func Reconcile(rootDir string, keys []KustomizationKey, dryRun bool) []FluxReconcileResult
Reconcile executes flux reconcile on the given kustomizations in order. Legacy function — new code should use FluxBackend via the runtime.
type ImpactResult ¶
type ImpactResult struct {
ChangedFiles []string
DirectlyAffected []KustomizationKey
TransitivelyAffected []KustomizationKey
ReconcileSet []KustomizationKey // topologically sorted
UnmappedFiles []string // changed files not under any kustomization path
}
ImpactResult describes which kustomizations are affected by a set of changes.
func ComputeImpact ¶
func ComputeImpact(graph *FluxGraph, files []string) ImpactResult
ComputeImpact determines which kustomizations are affected by changed files. Walks the reverse dependency graph to find transitive dependents.
type KustomizationKey ¶
KustomizationKey uniquely identifies a Flux Kustomization. Identity is (namespace, name) — never bare name alone.
func Orphans ¶
func Orphans(graph *FluxGraph) []KustomizationKey
Orphans returns kustomizations with no dependents and no dependencies.
func ReconcileOrder ¶ added in v0.7.0
func ReconcileOrder(graph *FluxGraph) []KustomizationKey
ReconcileOrder returns the kustomizations in dependency order: a kustomization's dependencies always appear before it. This is what Flux's own controller honors via spec.dependsOn — reconciling in this order accelerates convergence and makes the reconcile output read top-down instead of randomly.
Order is by dependency DEPTH (longest path from a root), then lexically within a depth — a wavefront that mirrors how Flux actually reconciles: Flux runs every kustomization concurrently and gates each on its deps being Ready, so the nodes sharing a depth are exactly the ones Flux fires together. Depth-first (not a greedy lexical walk) is what keeps a shallow leaf — e.g. a bootstrap Job that only dependsOn an early phase — in its own early wave instead of being pushed to the end just because a deeper node sorts before it lexically. Still a valid topological order (a node's depth is always strictly greater than any dep's) and deterministic (identical graphs → identical sequences).
DependsOn edges to kustomizations not present in the graph are ignored (Flux tolerates cross-source dependencies). Cycles are broken deterministically: any nodes that cannot be topologically placed are appended in lexical order so reconcile still covers the whole estate rather than silently dropping them.
func TopoSort ¶
func TopoSort(graph *FluxGraph, subset []KustomizationKey) []KustomizationKey
TopoSort produces a deterministic topological order for a subset of the graph. Dependencies come before dependents. Ties broken by namespace/name sort.
func (KustomizationKey) String ¶
func (k KustomizationKey) String() string
type KustomizationNode ¶
type KustomizationNode struct {
Key KustomizationKey
Path string // normalized, repo-root relative
DependsOn []KustomizationKey
SourceRef string
}
KustomizationNode is a discovered Flux Kustomization with its dependencies.
type SchemaFinding ¶ added in v0.7.0
type SchemaFinding struct {
Kind string
Name string
Version string
Field string // dotted instance path incl. the offending property; "" if unparsed
Rule string // interpreted violation, phrased operator-side; "" if unparsed
SchemaURL string // the schema authority the check ran against; "" if absent
Raw string // original validator message, verbatim (escape hatch)
}
SchemaFinding is the structured, provenance-carrying form of a schema-validation finding. It separates what we can MECHANICALLY DERIVE from the validator output (kind, name, the offending field, the violated rule) from the raw validator transcript (the escape hatch). Field and Rule are best-effort: when the message can't be parsed with confidence they stay empty and the renderer falls back to Raw. The renderer must never synthesize meaning the transcript doesn't support — no operator folklore, only statements derivable from schema + manifest + result.
func (SchemaFinding) Parsed ¶ added in v0.7.0
func (s SchemaFinding) Parsed() bool
Parsed reports whether the violation was understood well enough to render an interpreted line. When false, callers show Raw rather than inventing meaning.
type ValidationMeta ¶ added in v0.7.0
type ValidationMeta struct {
Roots int
Skipped string // non-empty: validation could not run (e.g. tool unavailable)
KustomizeVer string
KubeconformVer string
Validated map[string]int // kind -> count checked against a known schema
NoSchema map[string]int // kind -> count with no available schema
}
ValidationMeta carries repository-scoped facts that are not per-Kustomization verdicts: tool versions, a skip reason, and schema coverage (kinds checked vs kinds with no available schema). Coverage gaps are reported, never failed.
func ValidateManifests ¶ added in v0.7.0
func ValidateManifests(ctx context.Context, rootDir string, desired map[string]config.ToolConstraint) (map[KustomizationKey]Verdict, *ValidationMeta, error)
ValidateManifests discovers the Flux graph and returns a verdict per Kustomization plus repository-scoped meta. The error return is reserved for infrastructure failures (graph discovery, pinned tool resolution); a repo with no Flux content returns an empty map and zero-roots meta.