Documentation
¶
Index ¶
Constants ¶
This section is empty.
Variables ¶
This section is empty.
Functions ¶
This section is empty.
Types ¶
type ClusterProjectionReconciler ¶ added in v0.3.0
type ClusterProjectionReconciler struct {
*ControllerDeps
// SourceMode is the cluster-admin-configured policy for which source
// objects are projectable. Empty string defaults to SourceModeAllowlist.
// Mirrors the namespaced reconciler's flag — both honor the same
// projectable-annotation veto and the same allowlist/permissive modes.
SourceMode SourceMode
// RequeueInterval controls how long the reconciler sleeps before
// retrying after a failed reconcile. Defaults to 30 seconds when unset
// (filled by SetupWithManager).
RequeueInterval time.Duration
// SelectorWriteConcurrency caps the number of in-flight destination
// writes during selector-based fan-out. Bounded so a CR matching
// thousands of namespaces doesn't burst the apiserver. Defaults to
// 16 when SetupWithManager runs against a zero value.
SelectorWriteConcurrency int
// Controller and Cache are captured by SetupWithManager so Reconcile
// can lazily register source / destination watches as new GVKs appear.
// Both are nil in unit-test paths that call Reconcile directly without
// SetupWithManager — the watch helpers no-op in that mode.
Controller controller.Controller
Cache cache.Cache
// contains filtered or unexported fields
}
ClusterProjectionReconciler reconciles cluster-scoped ClusterProjection objects: a single source object is fanned out to many destination namespaces selected either by an explicit list or a label selector.
State separated from ProjectionReconciler because the two reconcilers must not contend on the same source-watch and dest-watch maps — distinct ownership tiers, distinct enqueue paths, distinct cleanup semantics. Apiserver-facing dependencies are shared via *ControllerDeps.
func (*ClusterProjectionReconciler) SetupWithManager ¶ added in v0.3.0
func (r *ClusterProjectionReconciler) SetupWithManager(mgr ctrl.Manager) error
SetupWithManager wires the cluster reconciler to the manager.
Three things happen here that Reconcile relies on:
- A field indexer on ClusterProjection.spec indexes each CR by the canonical sourceKey of its source ref (mapSource resolves source events through this).
- A field indexer on ClusterProjection.metadata.uid indexes each CR by UID (ensureClusterDestWatch resolves dest events through this in O(1)).
- A namespace watch is registered on the builder so a namespace gaining or losing a selector label re-enqueues every affected ClusterProjection — without this, the only catch-up path would be the periodic resync.
We use .Build(r) (not .Complete(r)) to capture the controller.Controller so Reconcile can lazily register source / destination watches.
type ControllerDeps ¶ added in v0.3.0
type ControllerDeps struct {
client.Client
Scheme *runtime.Scheme
DynamicClient dynamic.Interface
RESTMapper apimeta.RESTMapper
Recorder events.EventRecorder
}
ControllerDeps bundles dependencies shared by every projection reconciler (namespaced and cluster-scoped). Each reconciler embeds one. Reconciler- specific state (the watched-sources map, the controller handle, requeue interval, source mode, …) lives on the reconciler itself, not here.
Exported so cmd/main.go can construct it. Field names match the historical ProjectionReconciler shape so existing callers (cmd/main.go, tests) keep compiling with only the construction-shape change of wrapping the apiserver dependencies in `ControllerDeps: &ControllerDeps{...}`.
type ProjectionReconciler ¶
type ProjectionReconciler struct {
// ControllerDeps bundles the apiserver-facing dependencies shared with
// ClusterProjectionReconciler (Client, Scheme, DynamicClient,
// RESTMapper, Recorder). Embedded so `r.Client`, `r.Scheme`, etc. continue
// to resolve via promotion and existing callsites read unchanged. Pointer
// embedding lets cmd/main.go and tests build the reconciler with a single
// composite literal where the apiserver dependencies live behind one field.
*ControllerDeps
// SourceMode is the cluster-admin-configured policy for which source
// objects are projectable. Empty string defaults to SourceModeAllowlist.
SourceMode SourceMode
// RequeueInterval controls how long the reconciler sleeps before
// retrying after a successful or failed reconcile. Configured via the
// --requeue-interval CLI flag. Defaults to 30 seconds when unset
// (SetupWithManager fills the zero value so unit-test constructions
// don't need to set it explicitly).
RequeueInterval time.Duration
// Controller is the underlying controller.Controller we built in
// SetupWithManager. We need it so Reconcile can register new source
// watches lazily as previously-unseen source GVKs show up. It is nil
// in unit tests that call Reconcile directly without SetupWithManager.
Controller controller.Controller
// Cache is the manager's cache, used as the source for dynamic watches.
// Also nil in direct-reconcile unit tests.
Cache cache.Cache
// contains filtered or unexported fields
}
ProjectionReconciler reconciles a (namespaced) Projection object. The Projection mirrors a single source object into the Projection's own namespace; cross-namespace fan-out lives on the cluster-scoped sibling (ClusterProjection) and its dedicated reconciler.
func (*ProjectionReconciler) SetupWithManager ¶
func (r *ProjectionReconciler) SetupWithManager(mgr ctrl.Manager) error
SetupWithManager sets up the controller with the Manager.
Three things happen here that Reconcile relies on:
- A field indexer on Projection.spec indexes each CR by the canonical sourceKey of its source ref, so mapSource can list all projections referencing a changed source via a single cached List.
- A field indexer on Projection.metadata.uid lets ensureDestWatch's handler resolve a destination's UID-label value back to its owner in O(1) (single cached List, no full-cluster scan).
- We use .Build(r) (not .Complete(r)) to capture the controller.Controller so Reconcile can lazily register source / destination watches as previously-unseen GVKs appear. No up-front watches — Reconcile adds them on demand.
type SourceMode ¶
type SourceMode string
SourceMode controls which source objects the operator is willing to project. Configured once per controller via the --source-mode flag.
const ( // SourceModePermissive allows any source object to be projected. Source // owners can still veto individual objects with the // projection.sh/projectable="false" annotation. SourceModePermissive SourceMode = "permissive" // SourceModeAllowlist requires every source object to carry the // projection.sh/projectable="true" annotation before it can be // mirrored. This is the default — Kubernetes convention favors // opt-in for cluster-scoped operators with broad read RBAC. SourceModeAllowlist SourceMode = "allowlist" )