Skip to content

Commit ae59b13

Browse files
committed
daemon: update reconciler tests for StatusWatcher cache
Each unit test creates its own watcher with a fresh cache via newTestEnv() to avoid test pollution. Assisted-by: AI Signed-off-by: Alice Frosi <afrosi@redhat.com>
1 parent 35d2f5d commit ae59b13

3 files changed

Lines changed: 44 additions & 27 deletions

File tree

cmd/daemon/main.go

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -70,12 +70,12 @@ func main() {
7070
executor := bootc.NewHostExecutor()
7171

7272
watcher := &daemon.StatusWatcher{
73-
PollInterval: pollInterval,
73+
PollInterval: pollInterval,
7474
OstreePath: daemon.DefaultOstreePath,
7575
ComposefsPath: daemon.DefaultComposefsPath,
76-
Events: make(chan event.GenericEvent, 1),
77-
NodeName: nodeName,
78-
Executor: executor,
76+
Events: make(chan event.GenericEvent, 1),
77+
NodeName: nodeName,
78+
Executor: executor,
7979
}
8080
if err := mgr.Add(watcher); err != nil {
8181
setupLog.Error(err, "Failed to add status watcher")

internal/daemon/reconciler_test.go

Lines changed: 9 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,8 @@ func TestReconcilePopulatesStatus(t *testing.T) {
3232
g.SetDefaultEventuallyPollingInterval(pollInterval)
3333
ctx := context.Background()
3434

35+
fake := newTestEnv()
36+
3537
v1 := "v1"
3638
v2 := "v2"
3739
v3 := "v3"
@@ -99,7 +101,7 @@ func TestReconcileBootcStatusError(t *testing.T) {
99101
g.SetDefaultEventuallyPollingInterval(pollInterval)
100102
ctx := context.Background()
101103

102-
resetDaemon()
104+
fake := newTestEnv()
103105
fake.setStatusErr(errors.New(bootcStatusErrMsg))
104106

105107
bn := testutil.NewNode(testNodeName, testutil.ImageDigestRefA)
@@ -126,7 +128,7 @@ func TestStagingTriggered(t *testing.T) {
126128
g.SetDefaultEventuallyPollingInterval(pollInterval)
127129
ctx := context.Background()
128130

129-
resetDaemon()
131+
fake := newTestEnv()
130132
fake.status = newBootcStatus(testutil.DigestA)
131133

132134
bn := testutil.NewNode(testNodeName, testutil.ImageDigestRefB)
@@ -163,7 +165,7 @@ func TestStagingError(t *testing.T) {
163165
g.SetDefaultEventuallyPollingInterval(pollInterval)
164166
ctx := context.Background()
165167

166-
resetDaemon()
168+
fake := newTestEnv()
167169
fake.status = newBootcStatus(testutil.DigestA)
168170
fake.setStageErr(errors.New(stageErrMsg))
169171

@@ -196,7 +198,7 @@ func TestAlreadyStaged(t *testing.T) {
196198
g.SetDefaultEventuallyPollingInterval(pollInterval)
197199
ctx := context.Background()
198200

199-
resetDaemon()
201+
fake := newTestEnv()
200202
fake.status = newBootcStatus(testutil.DigestA)
201203
fake.status.Status.Staged = newBootEntry(testutil.ImageDigestRefB, testutil.DigestB)
202204

@@ -225,7 +227,7 @@ func TestRebootingSet(t *testing.T) {
225227
g.SetDefaultEventuallyPollingInterval(pollInterval)
226228
ctx := context.Background()
227229

228-
resetDaemon()
230+
fake := newTestEnv()
229231
fake.status = newBootcStatus(testutil.DigestA)
230232
fake.status.Status.Staged = newBootEntry(testutil.ImageDigestRefB, testutil.DigestB)
231233

@@ -254,7 +256,7 @@ func TestRollback(t *testing.T) {
254256
g.SetDefaultEventuallyPollingInterval(pollInterval)
255257
ctx := context.Background()
256258

257-
resetDaemon()
259+
fake := newTestEnv()
258260
fake.status = newBootcStatus(testutil.DigestA)
259261
fake.status.Status.Staged = newBootEntry(testutil.ImageDigestRefB, testutil.DigestB)
260262

@@ -285,7 +287,7 @@ func TestCancelInflightStage(t *testing.T) {
285287
g.SetDefaultEventuallyPollingInterval(pollInterval)
286288
ctx := context.Background()
287289

288-
resetDaemon()
290+
fake := newTestEnv()
289291
fake.status = newBootcStatus(testutil.DigestA)
290292

291293
firstBlock := make(chan struct{})

internal/daemon/suite_test.go

Lines changed: 31 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ import (
1313
ctrl "sigs.k8s.io/controller-runtime"
1414
"sigs.k8s.io/controller-runtime/pkg/client"
1515
"sigs.k8s.io/controller-runtime/pkg/envtest"
16+
"sigs.k8s.io/controller-runtime/pkg/event"
1617
"sigs.k8s.io/controller-runtime/pkg/log/zap"
1718
metricsserver "sigs.k8s.io/controller-runtime/pkg/metrics/server"
1819

@@ -22,20 +23,11 @@ import (
2223
const testNodeName = "test-node"
2324

2425
var (
25-
testEnv *envtest.Environment
26-
k8sClient client.Client
27-
fake *fakeExecutor
28-
reconciler *BootcNodeReconciler
26+
testEnv *envtest.Environment
27+
k8sClient client.Client
28+
testReconciler *BootcNodeReconciler
2929
)
3030

31-
// resetDaemon resets all volatile state on the shared reconciler and
32-
// fake executor so each test starts from a clean slate.
33-
func resetDaemon() {
34-
fake.reset()
35-
reconciler.rebootIssued = false
36-
reconciler.inflight.reset()
37-
}
38-
3931
func TestMain(m *testing.M) {
4032
ctrl.SetLogger(zap.New(zap.UseDevMode(true)))
4133

@@ -61,8 +53,6 @@ func TestMain(m *testing.M) {
6153
os.Exit(1)
6254
}
6355

64-
fake = &fakeExecutor{}
65-
6656
mgr, err := ctrl.NewManager(cfg, ctrl.Options{
6757
Scheme: scheme.Scheme,
6858
Metrics: metricsserver.Options{
@@ -74,13 +64,23 @@ func TestMain(m *testing.M) {
7464
os.Exit(1)
7565
}
7666

77-
reconciler = &BootcNodeReconciler{
67+
fake := &fakeExecutor{}
68+
testReconciler = &BootcNodeReconciler{
7869
Client: mgr.GetClient(),
7970
Scheme: mgr.GetScheme(),
8071
NodeName: testNodeName,
8172
Executor: fake,
73+
StatusWatcher: &StatusWatcher{
74+
Events: make(chan event.GenericEvent, 1),
75+
NodeName: testNodeName,
76+
Executor: fake,
77+
},
78+
}
79+
if err := mgr.Add(testReconciler.StatusWatcher); err != nil {
80+
fmt.Fprintf(os.Stderr, "Failed to add status watcher: %v\n", err)
81+
os.Exit(1)
8282
}
83-
if err := reconciler.SetupWithManager(mgr); err != nil {
83+
if err := testReconciler.SetupWithManager(mgr); err != nil {
8484
fmt.Fprintf(os.Stderr, "Failed to setup reconciler: %v\n", err)
8585
os.Exit(1)
8686
}
@@ -107,3 +107,18 @@ func TestMain(m *testing.M) {
107107

108108
os.Exit(code)
109109
}
110+
111+
// newTestEnv creates a fresh fakeExecutor and StatusWatcher for a test,
112+
// wiring them into the shared reconciler. Each test gets its own cache.
113+
func newTestEnv() *fakeExecutor {
114+
fake := &fakeExecutor{}
115+
testReconciler.Executor = fake
116+
testReconciler.rebootIssued = false
117+
testReconciler.inflight.reset()
118+
testReconciler.StatusWatcher = &StatusWatcher{
119+
Events: testReconciler.StatusWatcher.Events,
120+
NodeName: testNodeName,
121+
Executor: fake,
122+
}
123+
return fake
124+
}

0 commit comments

Comments
 (0)