Skip to content

Commit 35cc2f1

Browse files
authored
Merge pull request kubernetes-sigs#273 from davidvossel/add-more-failure-conditions-v1
Add condition to KubeVirtMachine when VM Creation Fails
2 parents c2cd191 + e1faf70 commit 35cc2f1

File tree

3 files changed

+53
-3
lines changed

3 files changed

+53
-3
lines changed

api/v1alpha1/condition_consts.go

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,10 @@ const (
3333
// WaitingForBootstrapDataReason (Severity=Info) documents a KubevirtMachine waiting for the bootstrap
3434
// script to be ready before starting to create the VM that provides the KubevirtMachine infrastructure.
3535
WaitingForBootstrapDataReason = "WaitingForBootstrapData"
36+
37+
// VMCreateFailed (Severity=Error) documents a KubevirtMachine that is unable to create the
38+
// corresponding VM object.
39+
VMCreateFailedReason = "VMCreateFailed"
3640
)
3741

3842
const (

controllers/kubevirtmachine_controller.go

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,9 +20,10 @@ import (
2020
gocontext "context"
2121
"fmt"
2222
"regexp"
23-
"sigs.k8s.io/controller-runtime/pkg/builder"
2423
"time"
2524

25+
"sigs.k8s.io/controller-runtime/pkg/builder"
26+
2627
"github.com/pkg/errors"
2728
"gopkg.in/yaml.v3"
2829
corev1 "k8s.io/api/core/v1"
@@ -264,6 +265,7 @@ func (r *KubevirtMachineReconciler) reconcileNormal(ctx *context.MachineContext)
264265
if !isTerminal && !externalMachine.Exists() {
265266
ctx.KubevirtMachine.Status.Ready = false
266267
if err := externalMachine.Create(ctx.Context); err != nil {
268+
conditions.MarkFalse(ctx.KubevirtMachine, infrav1.VMProvisionedCondition, infrav1.VMCreateFailedReason, clusterv1.ConditionSeverityError, fmt.Sprintf("Failed vm creation: %v", err))
267269
return ctrl.Result{}, errors.Wrap(err, "failed to create VM instance")
268270
}
269271
ctx.Logger.Info("VM Created, waiting on vm to be provisioned.")

controllers/kubevirtmachine_controller_test.go

Lines changed: 46 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,7 @@ import (
3838
ctrl "sigs.k8s.io/controller-runtime"
3939
"sigs.k8s.io/controller-runtime/pkg/client"
4040
"sigs.k8s.io/controller-runtime/pkg/client/fake"
41+
"sigs.k8s.io/controller-runtime/pkg/client/interceptor"
4142
"sigs.k8s.io/controller-runtime/pkg/controller/controllerutil"
4243

4344
machinemocks "sigs.k8s.io/cluster-api-provider-kubevirt/pkg/kubevirt/mock"
@@ -318,7 +319,7 @@ var _ = Describe("reconcile a kubevirt machine", func() {
318319

319320
})
320321

321-
setupClient := func(machineFactory kubevirt.MachineFactory, objects []client.Object) {
322+
setupClientWithInterceptors := func(machineFactory kubevirt.MachineFactory, objects []client.Object, interceptorFuncs interceptor.Funcs) {
322323
machineContext = &context.MachineContext{
323324
Context: gocontext.Background(),
324325
Cluster: cluster,
@@ -328,15 +329,21 @@ var _ = Describe("reconcile a kubevirt machine", func() {
328329
Logger: testLogger,
329330
}
330331

331-
fakeClient = fake.NewClientBuilder().WithScheme(testing.SetupScheme()).WithObjects(objects...).WithStatusSubresource(objects...).Build()
332+
fakeClient = fake.NewClientBuilder().WithScheme(testing.SetupScheme()).WithObjects(objects...).WithStatusSubresource(objects...).WithInterceptorFuncs(interceptorFuncs).Build()
332333
kubevirtMachineReconciler = KubevirtMachineReconciler{
333334
Client: fakeClient,
334335
WorkloadCluster: workloadClusterMock,
335336
InfraCluster: infraClusterMock,
336337
MachineFactory: machineFactory,
337338
}
339+
}
340+
341+
setupClient := func(machineFactory kubevirt.MachineFactory, objects []client.Object) {
342+
343+
setupClientWithInterceptors(machineFactory, objects, interceptor.Funcs{})
338344

339345
}
346+
340347
AfterEach(func() {})
341348

342349
It("should create KubeVirt VM", func() {
@@ -879,6 +886,43 @@ var _ = Describe("reconcile a kubevirt machine", func() {
879886
Expect(conditions[0].Type).To(Equal(infrav1.VMProvisionedCondition))
880887
Expect(conditions[0].Reason).To(Equal(infrav1.WaitingForBootstrapDataReason))
881888
})
889+
890+
It("adds a failed VMProvisionedCondition with reason VMCreateFailed when failng to create VM", func() {
891+
objects := []client.Object{
892+
cluster,
893+
kubevirtCluster,
894+
machine,
895+
kubevirtMachine,
896+
sshKeySecret,
897+
bootstrapSecret,
898+
}
899+
900+
injectErr := interceptor.Funcs{
901+
Create: func(ctx gocontext.Context, client client.WithWatch, obj client.Object, opts ...client.CreateOption) error {
902+
903+
_, ok := obj.(*kubevirtv1.VirtualMachine)
904+
if ok {
905+
return errors.New("vm create error")
906+
}
907+
return nil
908+
},
909+
}
910+
911+
setupClientWithInterceptors(kubevirt.DefaultMachineFactory{}, objects, injectErr)
912+
913+
infraClusterMock.EXPECT().GenerateInfraClusterClient(kubevirtMachine.Spec.InfraClusterSecretRef, kubevirtMachine.Namespace, machineContext.Context).Return(fakeClient, kubevirtMachine.Namespace, nil)
914+
915+
_, err := kubevirtMachineReconciler.reconcileNormal(machineContext)
916+
917+
Expect(err).Should(HaveOccurred())
918+
919+
// should expect condition
920+
conditions := machineContext.KubevirtMachine.GetConditions()
921+
Expect(conditions[0].Type).To(Equal(infrav1.VMProvisionedCondition))
922+
Expect(conditions[0].Status).To(Equal(corev1.ConditionFalse))
923+
Expect(conditions[0].Reason).To(Equal(infrav1.VMCreateFailedReason))
924+
})
925+
882926
It("adds a succeeded VMProvisionedCondition", func() {
883927
vmiReadyCondition := kubevirtv1.VirtualMachineInstanceCondition{
884928
Type: kubevirtv1.VirtualMachineInstanceReady,

0 commit comments

Comments
 (0)