8 bpav1alpha1 "github.com/bpa-operator/pkg/apis/bpa/v1alpha1"
9 metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
10 "k8s.io/apimachinery/pkg/apis/meta/v1/unstructured"
11 "k8s.io/apimachinery/pkg/runtime"
12 "k8s.io/apimachinery/pkg/types"
13 fakedynamic "k8s.io/client-go/dynamic/fake"
14 fakeclientset "k8s.io/client-go/kubernetes/fake"
15 "k8s.io/client-go/kubernetes/scheme"
16 "sigs.k8s.io/controller-runtime/pkg/client/fake"
17 "sigs.k8s.io/controller-runtime/pkg/reconcile"
18 logf "sigs.k8s.io/controller-runtime/pkg/runtime/log"
21 func TestProvisioningController(t *testing.T) {
23 logf.SetLogger(logf.ZapLogger(true))
24 bpaName1 := "bpa-test-cr"
25 bpaName2 := "bpa-test-2"
26 bpaName3 := "bpa-test-3"
27 namespace := "default"
28 clusterName := "test-cluster"
29 clusterName2 := "test-cluster-2"
30 clusterName3 := "test-cluster-3"
31 macAddress1 := "08:00:27:00:ab:2c"
32 macAddress2 := "08:00:27:00:ab:3d"
33 macAddress3 := "08:00:27:00:ab:1c"
35 // Create Fake DHCP file
36 err := createFakeDHCP()
38 t.Fatalf("Cannot create Fake DHCP file for testing\n")
41 // Create Fake baremetalhost
42 bmhList := newBMList()
44 // Create Fake Provisioning CR
45 provisioning := newBPA(bpaName1, namespace, clusterName, macAddress1)
46 provisioning2 := newBPA(bpaName2, namespace, clusterName2, macAddress2)
47 provisioning3 := newBPA(bpaName3, namespace, clusterName3, macAddress3)
49 // Objects to track in the fake Client
50 objs := []runtime.Object{provisioning, provisioning2, provisioning3}
52 // Register operator types with the runtime scheme
55 sc.AddKnownTypes(bpav1alpha1.SchemeGroupVersion, provisioning, provisioning2, provisioning3)
57 // Create Fake Clients and Clientset
58 fakeClient := fake.NewFakeClient(objs...)
59 fakeDyn := fakedynamic.NewSimpleDynamicClient(sc, bmhList)
60 fakeClientSet := fakeclientset.NewSimpleClientset()
62 r := &ReconcileProvisioning{client: fakeClient, scheme: sc, clientset: fakeClientSet, bmhClient: fakeDyn}
64 // Mock request to simulate Reconcile() being called on an event for a watched resource
65 req := simulateRequest(provisioning)
66 _, err = r.Reconcile(req)
68 t.Fatalf("reconcile: (%v)", err)
71 // Test 1: Check the job was created with the expected name
72 jobClient := r.clientset.BatchV1().Jobs(namespace)
73 job, err := jobClient.Get("kud-test-cluster", metav1.GetOptions{})
76 t.Fatalf("Error occured while getting job: (%v)", err)
79 // Test 2: Check that cluster name metadata in job is the expected cluster name
80 jobClusterName := job.Labels["cluster"]
81 if jobClusterName != clusterName {
82 t.Fatalf("Job cluster Name is wrong")
85 // Test 3: Check that the right error is produced when host with MAC address does not exist
86 req = simulateRequest(provisioning2)
87 _, err = r.Reconcile(req)
88 expectedErr := "Host with MAC Address " + macAddress2 + " not found\n"
89 if err.Error() != expectedErr {
90 t.Fatalf("Failed, Unexpected error occured %v\n", err)
93 // Test 4: Check that the right error is produced when MAC address is not found in the DHCP lease file
94 req = simulateRequest(provisioning3)
95 _, err = r.Reconcile(req)
96 expectedErr = "IP address not found for host with MAC address " + macAddress3 + " \n"
97 if err.Error() != expectedErr {
98 t.Fatalf("Failed, Unexpected error occured %v\n", err)
101 // Delete Fake DHCP file and cluster directories
102 err = os.Remove("/var/lib/dhcp/dhcpd.leases")
104 t.Logf("\nUnable to delete fake DHCP file\n")
106 err = os.RemoveAll("/multi-cluster/" + clusterName)
108 t.Logf("\nUnable to delete cluster directory %s\n", clusterName)
110 err = os.RemoveAll("/multi-cluster/" + clusterName2)
112 t.Logf("\nUnable to delete cluster directory %s\n", clusterName2)
114 err = os.RemoveAll("/multi-cluster/" + clusterName3)
116 t.Logf("\nUnable to delete cluster directory %s\n", clusterName3)
121 func simulateRequest(bpaCR *bpav1alpha1.Provisioning) reconcile.Request {
122 namespacedName := types.NamespacedName{
123 Name: bpaCR.ObjectMeta.Name,
124 Namespace: bpaCR.ObjectMeta.Namespace,
126 return reconcile.Request{NamespacedName: namespacedName}
129 func newBPA(name, namespace, clusterName, macAddress string) *bpav1alpha1.Provisioning {
131 provisioningCR := &bpav1alpha1.Provisioning{
132 ObjectMeta: metav1.ObjectMeta{
134 Namespace: namespace,
135 Labels: map[string]string{
136 "cluster": clusterName,
139 Spec: bpav1alpha1.ProvisioningSpec{
140 Masters: []map[string]bpav1alpha1.Master{
141 map[string]bpav1alpha1.Master{
142 "test-master": bpav1alpha1.Master{
143 MACaddress: macAddress,
149 return provisioningCR
152 func newBMList() *unstructured.UnstructuredList {
154 bmMap := map[string]interface{}{
155 "apiVersion": "metal3.io/v1alpha1",
156 "kind": "BareMetalHostList",
157 "metaData": map[string]interface{}{
159 "resourceVersion": "11830058",
160 "selfLink": "/apis/metal3.io/v1alpha1/baremetalhosts",
164 metaData := map[string]interface{}{
165 "creationTimestamp": "2019-10-24T04:51:15Z",
167 "name": "fake-test-bmh",
168 "namespace": "default",
169 "resourceVersion": "11829263",
170 "selfLink": "/apis/metal3.io/v1alpha1/namespaces/default/baremetalhosts/bpa-test-bmh",
171 "uid": "e92cb312-f619-11e9-90bc-00219ba0c77a",
174 nicMap1 := map[string]interface{}{
176 "mac": "08:00:27:00:ab:2c",
177 "model": "0x8086 0x1572",
184 nicMap2 := map[string]interface{}{
186 "mac": "08:00:27:00:ab:1c",
187 "model": "0x8086 0x1572",
194 specMap := map[string]interface{}{
195 "status": map[string]interface{}{
197 "hardware": map[string]interface{}{
198 "nics": map[string]interface{}{
206 itemMap := map[string]interface{}{
207 "apiVersion": "metal3.io/v1alpha1",
208 "kind": "BareMetalHost",
209 "metadata": metaData,
212 itemU := unstructured.Unstructured{
216 itemsList := []unstructured.Unstructured{itemU}
218 bmhList := &unstructured.UnstructuredList{
226 // Create DHCP file for testing
227 func createFakeDHCP() error {
229 dhcpData := []byte(`lease 192.168.50.63 {
230 starts 4 2019/08/08 22:32:49;
231 ends 4 2019/08/08 23:52:49;
232 cltt 4 2019/08/08 22:32:49;
233 binding state active;
234 next binding state free;
235 rewind binding state free;
236 hardware ethernet 08:00:27:00:ab:2c;
237 client-hostname "fake-test-bmh"";
239 err := ioutil.WriteFile("/var/lib/dhcp/dhcpd.leases", dhcpData, 0777)