Skip to content

Commit 7d15514

Browse files
kvapsclaude
andcommitted
feat(satellite/controllers): wire StoragePoolReconciler.Reconcile body (Phase 10.1)
StoragePool reconciler now actually registers providers — the same dynamic path Phase 10.5's `ApplyStoragePools` opened, but driven by CRD watches instead of gRPC pushes. Reconcile body: - DeletionTimestamp set → RegisterProvider(name, nil) which deregisters. The destructive teardown (vgremove --force / zpool destroy) lives behind the Phase 10.8 finalizer. - Otherwise → `satellite.NewProviderFromKind(kind, props, exec)` builds the matching Provider; `RegisterProvider(name, p)` adds it to the in-memory pool map. Idempotent re-runs replace the entry, which is the desired behaviour after a pool config edit. Config gains an `Exec storage.Exec` field — handed to NewProviderFromKind so the same fake/real switch the rest of the satellite uses applies here. Per-pool failures log without failing the reconcile so controller-runtime's back-off handles retries. Co-Authored-By: Claude <noreply@anthropic.com> Signed-off-by: Andrei Kvapil <kvapss@gmail.com>
1 parent 33c69d6 commit 7d15514

2 files changed

Lines changed: 35 additions & 7 deletions

File tree

pkg/satellite/controllers/config.go

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@ package controllers
1818

1919
import (
2020
"github.com/cozystack/blockstor/pkg/satellite"
21+
"github.com/cozystack/blockstor/pkg/storage"
2122
)
2223

2324
// Config carries the bits the four reconcilers need beyond what
@@ -38,4 +39,10 @@ type Config struct {
3839
// the storage + DRBD + LUKS chain. Phase 10.1 reuses it so
3940
// the controller-runtime path doesn't duplicate logic.
4041
Apply *satellite.Reconciler
42+
43+
// Exec is the shell-out interface the StoragePool reconciler
44+
// hands to `satellite.NewProviderFromKind` when materialising
45+
// a Provider instance from a StoragePool CRD. Production
46+
// wires `storage.RealExec{}`; tests inject `storage.FakeExec`.
47+
Exec storage.Exec
4148
}

pkg/satellite/controllers/storagepool.go

Lines changed: 28 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@ import (
2727
"sigs.k8s.io/controller-runtime/pkg/log"
2828

2929
blockstoriov1alpha1 "github.com/cozystack/blockstor/api/v1alpha1"
30+
"github.com/cozystack/blockstor/pkg/satellite"
3031
)
3132

3233
// StoragePoolReconciler watches StoragePool CRDs filtered to
@@ -68,13 +69,33 @@ func (r *StoragePoolReconciler) Reconcile(ctx context.Context, req ctrl.Request)
6869
"kind", pool.Spec.ProviderKind,
6970
"deletionTimestamp", pool.DeletionTimestamp)
7071

71-
// Phase 10.1 follow-up: instantiate via
72-
// `satellite.NewProviderFromKind(pool.Spec.ProviderKind,
73-
// pool.Spec.Props, exec)` and call
74-
// `Config.Apply.RegisterProvider(poolName, provider)`. The
75-
// per-pool capacity reporting (Status writes) flips to a
76-
// periodic loop here too — Phase 10.5's stub gets replaced
77-
// with the c-r-driven real path.
72+
// On delete: deregister the provider (its in-memory
73+
// instance goes away). The actual on-disk teardown
74+
// (`vgremove --force` / `zpool destroy`) is a Phase 10.8
75+
// finalizer that runs separately when
76+
// `Spec.DestroyOnDelete=true`.
77+
if !pool.DeletionTimestamp.IsZero() {
78+
r.Config.Apply.RegisterProvider(pool.Spec.PoolName, nil)
79+
80+
return ctrl.Result{}, nil
81+
}
82+
83+
provider, err := satellite.NewProviderFromKind(pool.Spec.ProviderKind, pool.Spec.Props, r.Config.Exec)
84+
if err != nil {
85+
// Per-pool failure: log and let the next reconcile
86+
// retry (controller-runtime back-off handles the
87+
// retry cadence). The pool stays unavailable until
88+
// the operator fixes the config — same semantic the
89+
// gRPC `ApplyStoragePools` path had via Ok=false.
90+
logger.Info("NewProviderFromKind failed", "kind", pool.Spec.ProviderKind, "err", err)
91+
92+
return ctrl.Result{}, nil
93+
}
94+
95+
// nil provider = DISKLESS kind; RegisterProvider's nil path
96+
// deregisters, which is the right semantic.
97+
r.Config.Apply.RegisterProvider(pool.Spec.PoolName, provider)
98+
7899
return ctrl.Result{}, nil
79100
}
80101

0 commit comments

Comments
 (0)