github.com/k8snetworkplumbingwg/sriov-network-operator@v1.2.1-0.20240408194816-2d2e5a45d453/cmd/sriov-network-config-daemon/service_test.go (about) 1 package main 2 3 import ( 4 "fmt" 5 6 "github.com/golang/mock/gomock" 7 "github.com/spf13/cobra" 8 "gopkg.in/yaml.v3" 9 10 . "github.com/onsi/ginkgo/v2" 11 . "github.com/onsi/gomega" 12 13 sriovnetworkv1 "github.com/k8snetworkplumbingwg/sriov-network-operator/api/v1" 14 "github.com/k8snetworkplumbingwg/sriov-network-operator/pkg/helper" 15 helperMock "github.com/k8snetworkplumbingwg/sriov-network-operator/pkg/helper/mock" 16 "github.com/k8snetworkplumbingwg/sriov-network-operator/pkg/platforms" 17 platformsMock "github.com/k8snetworkplumbingwg/sriov-network-operator/pkg/platforms/mock" 18 plugin "github.com/k8snetworkplumbingwg/sriov-network-operator/pkg/plugins" 19 "github.com/k8snetworkplumbingwg/sriov-network-operator/pkg/plugins/generic" 20 pluginsMock "github.com/k8snetworkplumbingwg/sriov-network-operator/pkg/plugins/mock" 21 "github.com/k8snetworkplumbingwg/sriov-network-operator/pkg/systemd" 22 "github.com/k8snetworkplumbingwg/sriov-network-operator/test/util/fakefilesystem" 23 testHelpers "github.com/k8snetworkplumbingwg/sriov-network-operator/test/util/helpers" 24 ) 25 26 func restoreOrigFuncs() { 27 origNewGenericPluginFunc := newGenericPluginFunc 28 origNewVirtualPluginFunc := newVirtualPluginFunc 29 origNewHostHelpersFunc := newHostHelpersFunc 30 origNewPlatformHelperFunc := newPlatformHelperFunc 31 DeferCleanup(func() { 32 newGenericPluginFunc = origNewGenericPluginFunc 33 newVirtualPluginFunc = origNewVirtualPluginFunc 34 newHostHelpersFunc = origNewHostHelpersFunc 35 newPlatformHelperFunc = origNewPlatformHelperFunc 36 }) 37 } 38 39 func getTestSriovInterfaceConfig(platform int) []byte { 40 return []byte(fmt.Sprintf(`spec: 41 dpconfigversion: "" 42 interfaces: 43 - pciaddress: 0000:d8:00.0 44 numvfs: 4 45 mtu: 1500 46 name: enp216s0f0np0 47 linktype: "" 48 eswitchmode: legacy 49 vfgroups: 50 - resourcename: legacy 51 devicetype: "" 52 vfrange: 0-3 53 policyname: test-legacy 54 mtu: 1500 55 isrdma: false 56 vdpatype: "" 57 externallymanaged: false 58 unsupportedNics: false 59 platformType: %d 60 `, platform)) 61 } 62 63 var testSriovSupportedNicIDs = `8086 1583 154c 64 8086 0d58 154c 65 8086 10c9 10ca 66 ` 67 68 func getTestResultFileContent(syncStatus, errMsg string) []byte { 69 data, err := yaml.Marshal(systemd.SriovResult{SyncStatus: syncStatus, LastSyncError: errMsg}) 70 ExpectWithOffset(1, err).NotTo(HaveOccurred()) 71 return data 72 } 73 74 // checks if NodeState contains deviceName in spec and status fields 75 func newNodeStateContainsDeviceMatcher(deviceName string) gomock.Matcher { 76 return &nodeStateContainsDeviceMatcher{deviceName: deviceName} 77 } 78 79 type nodeStateContainsDeviceMatcher struct { 80 deviceName string 81 } 82 83 func (ns *nodeStateContainsDeviceMatcher) Matches(x interface{}) bool { 84 s, ok := x.(*sriovnetworkv1.SriovNetworkNodeState) 85 if !ok { 86 return false 87 } 88 specFound := false 89 for _, i := range s.Spec.Interfaces { 90 if i.Name == ns.deviceName { 91 specFound = true 92 break 93 } 94 } 95 if !specFound { 96 return false 97 } 98 statusFound := false 99 for _, i := range s.Status.Interfaces { 100 if i.Name == ns.deviceName { 101 statusFound = true 102 break 103 } 104 } 105 return statusFound 106 } 107 108 func (ns *nodeStateContainsDeviceMatcher) String() string { 109 return "node state contains match: " + ns.deviceName 110 } 111 112 var _ = Describe("Service", func() { 113 var ( 114 hostHelpers *helperMock.MockHostHelpersInterface 115 platformHelper *platformsMock.MockInterface 116 genericPlugin *pluginsMock.MockVendorPlugin 117 virtualPlugin *pluginsMock.MockVendorPlugin 118 119 testCtrl *gomock.Controller 120 testError = fmt.Errorf("test") 121 ) 122 123 BeforeEach(func() { 124 restoreOrigFuncs() 125 126 testCtrl = gomock.NewController(GinkgoT()) 127 hostHelpers = helperMock.NewMockHostHelpersInterface(testCtrl) 128 platformHelper = platformsMock.NewMockInterface(testCtrl) 129 genericPlugin = pluginsMock.NewMockVendorPlugin(testCtrl) 130 virtualPlugin = pluginsMock.NewMockVendorPlugin(testCtrl) 131 132 newGenericPluginFunc = func(_ helper.HostHelpersInterface, _ ...generic.Option) (plugin.VendorPlugin, error) { 133 return genericPlugin, nil 134 } 135 newVirtualPluginFunc = func(_ helper.HostHelpersInterface) (plugin.VendorPlugin, error) { 136 return virtualPlugin, nil 137 } 138 newHostHelpersFunc = func() (helper.HostHelpersInterface, error) { 139 return hostHelpers, nil 140 } 141 newPlatformHelperFunc = func() (platforms.Interface, error) { 142 return platformHelper, nil 143 } 144 145 }) 146 AfterEach(func() { 147 phaseArg = "" 148 testCtrl.Finish() 149 }) 150 151 It("Pre phase - baremetal cluster", func() { 152 phaseArg = PhasePre 153 testHelpers.GinkgoConfigureFakeFS(&fakefilesystem.FS{ 154 Dirs: []string{"/etc/sriov-operator"}, 155 Files: map[string][]byte{ 156 "/etc/sriov-operator/sriov-supported-nics-ids.yaml": []byte(testSriovSupportedNicIDs), 157 "/etc/sriov-operator/sriov-interface-config.yaml": getTestSriovInterfaceConfig(0), 158 "/etc/sriov-operator/sriov-interface-result.yaml": []byte("something"), 159 }, 160 }) 161 hostHelpers.EXPECT().TryEnableRdma().Return(true, nil) 162 hostHelpers.EXPECT().TryEnableTun().Return() 163 hostHelpers.EXPECT().TryEnableVhostNet().Return() 164 hostHelpers.EXPECT().DiscoverSriovDevices(hostHelpers).Return([]sriovnetworkv1.InterfaceExt{{ 165 Name: "enp216s0f0np0", 166 }}, nil) 167 genericPlugin.EXPECT().OnNodeStateChange(newNodeStateContainsDeviceMatcher("enp216s0f0np0")).Return(true, false, nil) 168 genericPlugin.EXPECT().Apply().Return(nil) 169 170 Expect(runServiceCmd(&cobra.Command{}, []string{})).NotTo(HaveOccurred()) 171 172 testHelpers.GinkgoAssertFileContentsEquals("/etc/sriov-operator/sriov-interface-result.yaml", 173 string(getTestResultFileContent("InProgress", ""))) 174 }) 175 176 It("Pre phase - virtual cluster", func() { 177 phaseArg = PhasePre 178 testHelpers.GinkgoConfigureFakeFS(&fakefilesystem.FS{ 179 Dirs: []string{"/etc/sriov-operator"}, 180 Files: map[string][]byte{ 181 "/etc/sriov-operator/sriov-supported-nics-ids.yaml": []byte(testSriovSupportedNicIDs), 182 "/etc/sriov-operator/sriov-interface-config.yaml": getTestSriovInterfaceConfig(1), 183 "/etc/sriov-operator/sriov-interface-result.yaml": []byte("something"), 184 }, 185 }) 186 hostHelpers.EXPECT().TryEnableRdma().Return(true, nil) 187 hostHelpers.EXPECT().TryEnableTun().Return() 188 hostHelpers.EXPECT().TryEnableVhostNet().Return() 189 190 platformHelper.EXPECT().CreateOpenstackDevicesInfo().Return(nil) 191 platformHelper.EXPECT().DiscoverSriovDevicesVirtual().Return([]sriovnetworkv1.InterfaceExt{{ 192 Name: "enp216s0f0np0", 193 }}, nil) 194 195 virtualPlugin.EXPECT().OnNodeStateChange(newNodeStateContainsDeviceMatcher("enp216s0f0np0")).Return(true, false, nil) 196 virtualPlugin.EXPECT().Apply().Return(nil) 197 198 Expect(runServiceCmd(&cobra.Command{}, []string{})).NotTo(HaveOccurred()) 199 200 testHelpers.GinkgoAssertFileContentsEquals("/etc/sriov-operator/sriov-interface-result.yaml", 201 string(getTestResultFileContent("InProgress", ""))) 202 }) 203 204 It("Pre phase - apply failed", func() { 205 phaseArg = PhasePre 206 testHelpers.GinkgoConfigureFakeFS(&fakefilesystem.FS{ 207 Dirs: []string{"/etc/sriov-operator"}, 208 Files: map[string][]byte{ 209 "/etc/sriov-operator/sriov-supported-nics-ids.yaml": []byte(testSriovSupportedNicIDs), 210 "/etc/sriov-operator/sriov-interface-config.yaml": getTestSriovInterfaceConfig(0), 211 "/etc/sriov-operator/sriov-interface-result.yaml": []byte("something"), 212 }, 213 }) 214 hostHelpers.EXPECT().TryEnableRdma().Return(true, nil) 215 hostHelpers.EXPECT().TryEnableTun().Return() 216 hostHelpers.EXPECT().TryEnableVhostNet().Return() 217 hostHelpers.EXPECT().DiscoverSriovDevices(hostHelpers).Return([]sriovnetworkv1.InterfaceExt{{ 218 Name: "enp216s0f0np0", 219 }}, nil) 220 genericPlugin.EXPECT().OnNodeStateChange(newNodeStateContainsDeviceMatcher("enp216s0f0np0")).Return(true, false, nil) 221 genericPlugin.EXPECT().Apply().Return(testError) 222 223 Expect(runServiceCmd(&cobra.Command{}, []string{})).To(MatchError(ContainSubstring("test"))) 224 225 testHelpers.GinkgoAssertFileContentsEquals("/etc/sriov-operator/sriov-interface-result.yaml", 226 string(getTestResultFileContent("Failed", "pre: failed to apply configuration: test"))) 227 }) 228 229 It("Post phase - baremetal cluster", func() { 230 phaseArg = PhasePost 231 testHelpers.GinkgoConfigureFakeFS(&fakefilesystem.FS{ 232 Dirs: []string{"/etc/sriov-operator"}, 233 Files: map[string][]byte{ 234 "/etc/sriov-operator/sriov-supported-nics-ids.yaml": []byte(testSriovSupportedNicIDs), 235 "/etc/sriov-operator/sriov-interface-config.yaml": getTestSriovInterfaceConfig(0), 236 "/etc/sriov-operator/sriov-interface-result.yaml": getTestResultFileContent("InProgress", ""), 237 }, 238 }) 239 hostHelpers.EXPECT().DiscoverSriovDevices(hostHelpers).Return([]sriovnetworkv1.InterfaceExt{{ 240 Name: "enp216s0f0np0", 241 }}, nil) 242 genericPlugin.EXPECT().OnNodeStateChange(newNodeStateContainsDeviceMatcher("enp216s0f0np0")).Return(true, false, nil) 243 genericPlugin.EXPECT().Apply().Return(nil) 244 Expect(runServiceCmd(&cobra.Command{}, []string{})).NotTo(HaveOccurred()) 245 testHelpers.GinkgoAssertFileContentsEquals("/etc/sriov-operator/sriov-interface-result.yaml", 246 string(getTestResultFileContent("Succeeded", ""))) 247 }) 248 249 It("Post phase - virtual cluster", func() { 250 phaseArg = PhasePost 251 testHelpers.GinkgoConfigureFakeFS(&fakefilesystem.FS{ 252 Dirs: []string{"/etc/sriov-operator"}, 253 Files: map[string][]byte{ 254 "/etc/sriov-operator/sriov-supported-nics-ids.yaml": []byte(testSriovSupportedNicIDs), 255 "/etc/sriov-operator/sriov-interface-config.yaml": getTestSriovInterfaceConfig(1), 256 "/etc/sriov-operator/sriov-interface-result.yaml": getTestResultFileContent("InProgress", ""), 257 }, 258 }) 259 Expect(runServiceCmd(&cobra.Command{}, []string{})).NotTo(HaveOccurred()) 260 testHelpers.GinkgoAssertFileContentsEquals("/etc/sriov-operator/sriov-interface-result.yaml", 261 string(getTestResultFileContent("Succeeded", ""))) 262 }) 263 264 It("Post phase - wrong result of the pre phase", func() { 265 phaseArg = PhasePost 266 testHelpers.GinkgoConfigureFakeFS(&fakefilesystem.FS{ 267 Dirs: []string{"/etc/sriov-operator"}, 268 Files: map[string][]byte{ 269 "/etc/sriov-operator/sriov-supported-nics-ids.yaml": []byte(testSriovSupportedNicIDs), 270 "/etc/sriov-operator/sriov-interface-config.yaml": getTestSriovInterfaceConfig(1), 271 "/etc/sriov-operator/sriov-interface-result.yaml": getTestResultFileContent("Failed", "pretest"), 272 }, 273 }) 274 Expect(runServiceCmd(&cobra.Command{}, []string{})).To(HaveOccurred()) 275 testHelpers.GinkgoAssertFileContentsEquals("/etc/sriov-operator/sriov-interface-result.yaml", 276 string(getTestResultFileContent("Failed", "post: unexpected result of the pre phase: Failed, syncError: pretest"))) 277 }) 278 })