@@ -169,16 +169,74 @@ func TestAddSnatForDns(t *testing.T) {
169169 }
170170}
171171
172+ // linux swiftv2 example
173+ func GetTestCNSResponseSecondaryLinux (macAddress string ) map [string ]network.InterfaceInfo {
174+ parsedMAC , _ := net .ParseMAC (macAddress )
175+ return map [string ]network.InterfaceInfo {
176+ string (cns .InfraNIC ): {
177+ IPConfigs : []* network.IPConfig {
178+ {
179+ Address : * getCIDRNotationForAddress ("20.241.0.35/16" ),
180+ Gateway : net .ParseIP ("20.241.0.35" ), // actual scenario doesn't have a gateway
181+ },
182+ },
183+ Routes : []network.RouteInfo {
184+ {
185+ Dst : * getCIDRNotationForAddress ("169.254.2.1/16" ),
186+ Gw : net .ParseIP ("10.244.2.1" ),
187+ },
188+ {
189+ Dst : * getCIDRNotationForAddress ("0.0.0.0/32" ),
190+ Gw : net .ParseIP ("169.254.2.1" ),
191+ },
192+ },
193+ NICType : cns .InfraNIC ,
194+ SkipDefaultRoutes : true ,
195+ HostSubnetPrefix : * getCIDRNotationForAddress ("10.224.0.0/16" ),
196+ },
197+ macAddress : {
198+ MacAddress : parsedMAC ,
199+ IPConfigs : []* network.IPConfig {
200+ {
201+ Address : * getCIDRNotationForAddress ("10.241.0.35/32" ),
202+ Gateway : net .ParseIP ("10.241.0.35" ), // actual scenario doesn't have a gateway
203+ },
204+ },
205+ Routes : []network.RouteInfo {
206+ {
207+ Dst : * getCIDRNotationForAddress ("169.254.2.1/32" ),
208+ Gw : net .ParseIP ("10.244.2.1" ),
209+ },
210+ {
211+ Dst : * getCIDRNotationForAddress ("0.0.0.0/0" ),
212+ Gw : net .ParseIP ("169.254.2.1" ),
213+ },
214+ },
215+ NICType : cns .NodeNetworkInterfaceFrontendNIC ,
216+ SkipDefaultRoutes : false ,
217+ },
218+ }
219+ }
220+
172221// Happy path scenario for add and delete
173222func TestPluginLinuxAdd (t * testing.T ) {
174223 resources := GetTestResources ()
175- localNwCfg := cni.NetworkConfig {
224+ mulNwCfg := cni.NetworkConfig {
176225 CNIVersion : "0.3.0" ,
177226 Name : "mulnet" ,
178227 MultiTenancy : true ,
179228 EnableExactMatchForPodName : true ,
180229 Master : "eth0" ,
181230 }
231+ nwCfg := cni.NetworkConfig {
232+ CNIVersion : "0.3.0" ,
233+ Name : "net" ,
234+ MultiTenancy : false ,
235+ EnableExactMatchForPodName : true ,
236+ // test auto finding master interface
237+ }
238+ macAddress := "60:45:bd76:f6:44"
239+ parsedMACAddress , _ := net .ParseMAC (macAddress )
182240 type endpointEntry struct {
183241 epInfo * network.EndpointInfo
184242 epIDRegex string
@@ -202,7 +260,7 @@ func TestPluginLinuxAdd(t *testing.T) {
202260 multitenancyClient : NewMockMultitenancy (false , []* cns.GetNetworkContainerResponse {GetTestCNSResponse3 ()}),
203261 },
204262 args : & cniSkel.CmdArgs {
205- StdinData : localNwCfg .Serialize (),
263+ StdinData : mulNwCfg .Serialize (),
206264 ContainerID : "test-container" ,
207265 Netns : "bc526fae-4ba0-4e80-bc90-ad721e5850bf" ,
208266 Args : fmt .Sprintf ("K8S_POD_NAME=%v;K8S_POD_NAMESPACE=%v" , "test-pod" , "test-pod-ns" ),
@@ -271,6 +329,145 @@ func TestPluginLinuxAdd(t *testing.T) {
271329 },
272330 },
273331 },
332+ {
333+ // Based on a live swiftv2 linux cluster's cns invoker response
334+ name : "Add Happy Path Swiftv2" ,
335+ plugin : & NetPlugin {
336+ Plugin : resources .Plugin ,
337+ nm : network .NewMockNetworkmanager (network .NewMockEndpointClient (nil )),
338+ tb : & telemetry.TelemetryBuffer {},
339+ report : & telemetry.CNIReport {},
340+ ipamInvoker : NewCustomMockIpamInvoker (GetTestCNSResponseSecondaryLinux (macAddress )),
341+ netClient : & InterfaceGetterMock {
342+ // used in secondary find master interface
343+ interfaces : []net.Interface {
344+ {
345+ Name : "secondary" ,
346+ HardwareAddr : parsedMACAddress ,
347+ },
348+ {
349+ Name : "primary" ,
350+ HardwareAddr : net.HardwareAddr {},
351+ },
352+ },
353+ // used in primary find master interface
354+ interfaceAddrs : map [string ][]net.Addr {
355+ "primary" : {
356+ // match with the host subnet prefix to know that this ip belongs to the host
357+ getCIDRNotationForAddress ("10.224.0.0/16" ),
358+ },
359+ },
360+ },
361+ },
362+ args : & cniSkel.CmdArgs {
363+ StdinData : nwCfg .Serialize (),
364+ ContainerID : "test-container" ,
365+ Netns : "bc526fae-4ba0-4e80-bc90-ad721e5850bf" ,
366+ Args : fmt .Sprintf ("K8S_POD_NAME=%v;K8S_POD_NAMESPACE=%v" , "test-pod" , "test-pod-ns" ),
367+ IfName : eth0IfName ,
368+ },
369+ match : func (ei1 , ei2 * network.EndpointInfo ) bool {
370+ return ei1 .NICType == ei2 .NICType
371+ },
372+ want : []endpointEntry {
373+ // should match infra
374+ {
375+ epInfo : & network.EndpointInfo {
376+ ContainerID : "test-container" ,
377+ Data : map [string ]interface {}{
378+ "vethname" : "nettest-containereth0" ,
379+ },
380+ Routes : []network.RouteInfo {
381+ {
382+ Dst : * getCIDRNotationForAddress ("169.254.2.1/16" ),
383+ Gw : net .ParseIP ("10.244.2.1" ),
384+ },
385+ {
386+ Dst : * getCIDRNotationForAddress ("0.0.0.0/32" ),
387+ Gw : net .ParseIP ("169.254.2.1" ),
388+ },
389+ },
390+ PODName : "test-pod" ,
391+ PODNameSpace : "test-pod-ns" ,
392+ NICType : cns .InfraNIC ,
393+ SkipDefaultRoutes : true ,
394+ MasterIfName : "primary" ,
395+ NetworkID : "net" ,
396+ NetNsPath : "bc526fae-4ba0-4e80-bc90-ad721e5850bf" ,
397+ NetNs : "bc526fae-4ba0-4e80-bc90-ad721e5850bf" ,
398+ HostSubnetPrefix : "10.224.0.0/16" ,
399+ Options : map [string ]interface {}{},
400+ // matches with cns ip configuration
401+ IPAddresses : []net.IPNet {
402+ {
403+ IP : net .ParseIP ("20.241.0.35" ),
404+ Mask : getIPNetWithString ("20.241.0.35/16" ).Mask ,
405+ },
406+ },
407+ NATInfo : nil ,
408+ // ip config pod ip + mask(s) from cns > interface info > subnet info
409+ Subnets : []network.SubnetInfo {
410+ {
411+ Family : platform .AfINET ,
412+ // matches cns ip configuration (20.241.0.0/16 == 20.241.0.35/16)
413+ Prefix : * getIPNetWithString ("20.241.0.0/16" ),
414+ // matches cns ip configuration gateway ip address
415+ Gateway : net .ParseIP ("20.241.0.35" ),
416+ },
417+ },
418+ },
419+ epIDRegex : `.*` ,
420+ },
421+ // should match secondary
422+ {
423+ epInfo : & network.EndpointInfo {
424+ MacAddress : parsedMACAddress ,
425+ ContainerID : "test-container" ,
426+ Data : map [string ]interface {}{
427+ "vethname" : "nettest-containereth0" ,
428+ },
429+ Routes : []network.RouteInfo {
430+ {
431+ Dst : * getCIDRNotationForAddress ("169.254.2.1/32" ),
432+ Gw : net .ParseIP ("10.244.2.1" ),
433+ },
434+ {
435+ Dst : * getCIDRNotationForAddress ("0.0.0.0/0" ),
436+ Gw : net .ParseIP ("169.254.2.1" ),
437+ },
438+ },
439+ PODName : "test-pod" ,
440+ PODNameSpace : "test-pod-ns" ,
441+ NICType : cns .NodeNetworkInterfaceFrontendNIC ,
442+ SkipDefaultRoutes : false ,
443+ MasterIfName : "secondary" ,
444+ NetworkID : "net" ,
445+ NetNsPath : "bc526fae-4ba0-4e80-bc90-ad721e5850bf" ,
446+ NetNs : "bc526fae-4ba0-4e80-bc90-ad721e5850bf" ,
447+ HostSubnetPrefix : "<nil>" ,
448+ Options : map [string ]interface {}{},
449+ // matches with cns ip configuration
450+ IPAddresses : []net.IPNet {
451+ {
452+ IP : net .ParseIP ("10.241.0.35" ),
453+ Mask : getIPNetWithString ("10.241.0.35/32" ).Mask ,
454+ },
455+ },
456+ NATInfo : nil ,
457+ // ip config pod ip + mask(s) from cns > interface info > subnet info
458+ Subnets : []network.SubnetInfo {
459+ {
460+ Family : platform .AfINET ,
461+ Prefix : * getIPNetWithString ("10.241.0.35/32" ),
462+ // matches cns ip configuration gateway ip address
463+ Gateway : net .ParseIP ("10.241.0.35" ),
464+ },
465+ },
466+ },
467+ epIDRegex : `.*` ,
468+ },
469+ },
470+ },
274471 }
275472
276473 for _ , tt := range tests {
0 commit comments