Skip to content

Commit 08e8d0d

Browse files
Use Subresource to mutate NamespacedCloudProfile status (gardener#11036)
1 parent d898b88 commit 08e8d0d

File tree

2 files changed

+54
-10
lines changed

2 files changed

+54
-10
lines changed

pkg/provider-local/admission/mutator/webhook.go

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ package mutator
66

77
import (
88
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
9+
"k8s.io/utils/ptr"
910
"sigs.k8s.io/controller-runtime/pkg/log"
1011
"sigs.k8s.io/controller-runtime/pkg/manager"
1112

@@ -31,7 +32,7 @@ func New(mgr manager.Manager) (*extensionswebhook.Webhook, error) {
3132
Path: "/webhooks/mutate",
3233
Mutators: map[extensionswebhook.Mutator][]extensionswebhook.Type{
3334
NewShootMutator(mgr): {{Obj: &gardencorev1beta1.Shoot{}}},
34-
NewNamespacedCloudProfileMutator(mgr): {{Obj: &gardencorev1beta1.NamespacedCloudProfile{}}},
35+
NewNamespacedCloudProfileMutator(mgr): {{Obj: &gardencorev1beta1.NamespacedCloudProfile{}, Subresource: ptr.To("status")}},
3536
},
3637
Target: extensionswebhook.TargetSeed,
3738
ObjectSelector: &metav1.LabelSelector{

test/e2e/gardener/shoot/create_hibernate_wakeup_delete.go

Lines changed: 52 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -11,10 +11,18 @@ import (
1111

1212
. "github.com/onsi/ginkgo/v2"
1313
. "github.com/onsi/gomega"
14+
. "github.com/onsi/gomega/gstruct"
15+
"k8s.io/apimachinery/pkg/runtime"
16+
"k8s.io/apimachinery/pkg/runtime/serializer"
17+
utilruntime "k8s.io/apimachinery/pkg/util/runtime"
18+
"k8s.io/utils/ptr"
1419
k8sclient "sigs.k8s.io/controller-runtime/pkg/client"
1520

21+
"github.com/gardener/gardener/extensions/pkg/util"
1622
gardencorev1beta1 "github.com/gardener/gardener/pkg/apis/core/v1beta1"
1723
v1beta1helper "github.com/gardener/gardener/pkg/apis/core/v1beta1/helper"
24+
api "github.com/gardener/gardener/pkg/provider-local/apis/local"
25+
"github.com/gardener/gardener/pkg/provider-local/apis/local/install"
1826
"github.com/gardener/gardener/pkg/utils/retry"
1927
. "github.com/gardener/gardener/pkg/utils/test/matchers"
2028
e2e "github.com/gardener/gardener/test/e2e/gardener"
@@ -32,12 +40,18 @@ var _ = Describe("Shoot Tests", Label("Shoot", "default"), func() {
3240

3341
if shoot.Spec.CloudProfileName == nil && shoot.Spec.CloudProfile != nil && shoot.Spec.CloudProfile.Kind == "NamespacedCloudProfile" {
3442
By("Create NamespacedCloudProfile")
35-
Expect(f.GardenClient.Client().Create(ctx, e2e.DefaultNamespacedCloudProfile())).To(Or(Succeed(), BeAlreadyExistsError()))
43+
namespacedCloudProfile := addCustomMachineImage(e2e.DefaultNamespacedCloudProfile())
44+
Expect(f.GardenClient.Client().Create(ctx, namespacedCloudProfile)).To(Or(Succeed()))
45+
DeferCleanup(func() {
46+
By("Delete NamespacedCloudProfile")
47+
ctx, cancel = context.WithTimeout(parentCtx, 15*time.Minute)
48+
defer cancel()
49+
Expect(f.GardenClient.Client().Delete(ctx, namespacedCloudProfile)).To(Or(Succeed(), BeNotFoundError()))
50+
})
3651

3752
By("Wait for new NamespacedCloudProfile to be reconciled")
3853
Expect(retry.UntilTimeout(ctx, 10*time.Second, 60*time.Second, func(ctx context.Context) (done bool, err error) {
39-
namespacedCloudProfile := &gardencorev1beta1.NamespacedCloudProfile{}
40-
err = f.GardenClient.Client().Get(ctx, k8sclient.ObjectKeyFromObject(e2e.DefaultNamespacedCloudProfile()), namespacedCloudProfile)
54+
err = f.GardenClient.Client().Get(ctx, k8sclient.ObjectKeyFromObject(namespacedCloudProfile), namespacedCloudProfile)
4155
if err != nil {
4256
return retry.SevereError(err)
4357
}
@@ -47,12 +61,20 @@ var _ = Describe("Shoot Tests", Label("Shoot", "default"), func() {
4761
return retry.Ok()
4862
})).To(Succeed())
4963

50-
DeferCleanup(func() {
51-
By("Delete NamespacedCloudProfile")
52-
ctx, cancel = context.WithTimeout(parentCtx, 15*time.Minute)
53-
defer cancel()
54-
Expect(f.GardenClient.Client().Delete(ctx, e2e.DefaultNamespacedCloudProfile())).To(Or(Succeed(), BeNotFoundError()))
55-
})
64+
By("Check for correct mutation of the status provider config")
65+
scheme := f.GardenClient.Client().Scheme()
66+
utilruntime.Must(install.AddToScheme(scheme))
67+
68+
cloudProfileConfig := &api.CloudProfileConfig{}
69+
decoder := serializer.NewCodecFactory(scheme, serializer.EnableStrict).UniversalDecoder()
70+
Expect(namespacedCloudProfile.Status.CloudProfileSpec.ProviderConfig).To(Not(BeNil()))
71+
Expect(util.Decode(decoder, namespacedCloudProfile.Status.CloudProfileSpec.ProviderConfig.Raw, cloudProfileConfig)).To(Succeed())
72+
Expect(cloudProfileConfig.MachineImages).To(ContainElement(MatchFields(IgnoreExtras, Fields{
73+
"Name": Equal("nscpfl-machine-image-1"),
74+
"Versions": ContainElements(
75+
api.MachineImageVersion{Version: "1.1", Image: "local/image:1.1"},
76+
),
77+
})))
5678
}
5779

5880
By("Create Shoot")
@@ -103,3 +125,24 @@ var _ = Describe("Shoot Tests", Label("Shoot", "default"), func() {
103125
test(shoot)
104126
})
105127
})
128+
129+
func addCustomMachineImage(namespacedCloudProfile *gardencorev1beta1.NamespacedCloudProfile) *gardencorev1beta1.NamespacedCloudProfile {
130+
namespacedCloudProfile.Spec.MachineImages = []gardencorev1beta1.MachineImage{
131+
{
132+
Name: "nscpfl-machine-image-1",
133+
UpdateStrategy: ptr.To(gardencorev1beta1.UpdateStrategyMinor),
134+
Versions: []gardencorev1beta1.MachineImageVersion{
135+
{ExpirableVersion: gardencorev1beta1.ExpirableVersion{Version: "1.1"}, Architectures: []string{"amd64"}, CRI: []gardencorev1beta1.CRI{{Name: "containerd"}}},
136+
},
137+
},
138+
}
139+
namespacedCloudProfile.Spec.ProviderConfig = &runtime.RawExtension{
140+
Raw: []byte(`{
141+
"apiVersion":"local.provider.extensions.gardener.cloud/v1alpha1",
142+
"kind":"CloudProfileConfig",
143+
"machineImages":[
144+
{"name":"nscpfl-machine-image-1","versions":[{"version":"1.1","image":"local/image:1.1"}]}
145+
]}`),
146+
}
147+
return namespacedCloudProfile
148+
}

0 commit comments

Comments
 (0)