Skip to content

Commit 3f21042

Browse files
authored
Merge pull request #10951 from dlipovetsky/fix-applymutators-nil-mutator
🐛 Handle a nil mutator by returning an error, not panicking
2 parents c0c7cdf + 12b0d07 commit 3f21042

File tree

2 files changed

+54
-3
lines changed

2 files changed

+54
-3
lines changed

cmd/clusterctl/client/cluster/mover.go

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1329,7 +1329,13 @@ func applyMutators(object client.Object, mutators ...ResourceMutatorFunc) (*unst
13291329
}
13301330
u.SetUnstructuredContent(to)
13311331
for _, mutator := range mutators {
1332-
if err := mutator(u); err != nil {
1332+
var err error
1333+
if mutator != nil {
1334+
err = mutator(u)
1335+
} else {
1336+
err = errors.New("mutator is nil")
1337+
}
1338+
if err != nil {
13331339
return nil, errors.Wrapf(err, "error applying resource mutator to %q %s/%s",
13341340
u.GroupVersionKind(), object.GetNamespace(), object.GetName())
13351341
}

cmd/clusterctl/client/cluster/mover_test.go

Lines changed: 47 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,7 @@ import (
3030
apierrors "k8s.io/apimachinery/pkg/api/errors"
3131
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
3232
"k8s.io/apimachinery/pkg/apis/meta/v1/unstructured"
33+
"k8s.io/apimachinery/pkg/runtime"
3334
"k8s.io/apimachinery/pkg/types"
3435
"k8s.io/apimachinery/pkg/util/sets"
3536
"k8s.io/apimachinery/pkg/util/wait"
@@ -1202,7 +1203,7 @@ func Test_objectMover_move_dryRun(t *testing.T) {
12021203
dryRun: true,
12031204
}
12041205

1205-
err := mover.move(ctx, graph, toProxy, nil)
1206+
err := mover.move(ctx, graph, toProxy)
12061207
if tt.wantErr {
12071208
g.Expect(err).To(HaveOccurred())
12081209
return
@@ -1876,7 +1877,6 @@ func Test_objectMoverService_ensureNamespaces(t *testing.T) {
18761877
expectedNamespaces: []string{"namespace-1", "namespace-2"},
18771878
},
18781879
{
1879-
18801880
name: "ensureNamespaces moves namespace-2 to target which already has namespace-1",
18811881
fields: fields{
18821882
objs: cluster2.Objs(),
@@ -2408,3 +2408,48 @@ func TestWaitReadyForMove(t *testing.T) {
24082408
})
24092409
}
24102410
}
2411+
2412+
func Test_applyMutators(t *testing.T) {
2413+
tests := []struct {
2414+
name string
2415+
object client.Object
2416+
mutators []ResourceMutatorFunc
2417+
want *unstructured.Unstructured
2418+
wantErr bool
2419+
}{
2420+
{
2421+
name: "do nothing if object is nil",
2422+
},
2423+
{
2424+
name: "do nothing if mutators is a nil slice",
2425+
object: test.NewFakeCluster("example", "example").Objs()[0],
2426+
want: func() *unstructured.Unstructured {
2427+
g := NewWithT(t)
2428+
obj := test.NewFakeCluster("example", "example").Objs()[0]
2429+
u := &unstructured.Unstructured{}
2430+
to, err := runtime.DefaultUnstructuredConverter.ToUnstructured(obj)
2431+
g.Expect(err).NotTo(HaveOccurred())
2432+
u.SetUnstructuredContent(to)
2433+
return u
2434+
}(),
2435+
},
2436+
{
2437+
name: "return error if any element in mutators slice is nil",
2438+
mutators: []ResourceMutatorFunc{nil},
2439+
object: test.NewFakeCluster("example", "example").Objs()[0],
2440+
wantErr: true,
2441+
},
2442+
}
2443+
for _, tt := range tests {
2444+
t.Run(tt.name, func(t *testing.T) {
2445+
g := NewWithT(t)
2446+
got, err := applyMutators(tt.object, tt.mutators...)
2447+
g.Expect(got).To(Equal(tt.want))
2448+
if tt.wantErr {
2449+
g.Expect(err).To(HaveOccurred())
2450+
} else {
2451+
g.Expect(err).NotTo(HaveOccurred())
2452+
}
2453+
})
2454+
}
2455+
}

0 commit comments

Comments
 (0)