github.com/axw/juju@v0.0.0-20161005053422-4bd6544d08d4/provider/maas/interfaces_test.go (about) 1 // Copyright 2015 Canonical Ltd. 2 // Licensed under the AGPLv3, see LICENCE file for details. 3 4 package maas 5 6 import ( 7 "bytes" 8 "fmt" 9 "text/template" 10 11 "github.com/juju/errors" 12 "github.com/juju/gomaasapi" 13 jc "github.com/juju/testing/checkers" 14 gc "gopkg.in/check.v1" 15 16 "github.com/juju/juju/network" 17 ) 18 19 //////////////////////////////////////////////////////////////////////////////// 20 // New (1.9 and later) environs.NetworkInterfaces() implementation tests follow. 21 22 type interfacesSuite struct { 23 providerSuite 24 } 25 26 var _ = gc.Suite(&interfacesSuite{}) 27 28 func newAddressOnSpaceWithId(space string, id network.Id, address string) network.Address { 29 newAddress := network.NewAddressOnSpace(space, address) 30 newAddress.SpaceProviderId = id 31 return newAddress 32 } 33 34 const exampleInterfaceSetJSON = ` 35 [ 36 { 37 "name": "eth0", 38 "links": [ 39 { 40 "subnet": { 41 "dns_servers": ["10.20.19.2", "10.20.19.3"], 42 "name": "pxe", 43 "space": "default", 44 "vlan": { 45 "name": "untagged", 46 "vid": 0, 47 "mtu": 1500, 48 "fabric": "managed", 49 "id": 5001, 50 "resource_uri": "/MAAS/api/1.0/vlans/5001/" 51 }, 52 "gateway_ip": "10.20.19.2", 53 "cidr": "10.20.19.0/24", 54 "id": 3, 55 "resource_uri": "/MAAS/api/1.0/subnets/3/" 56 }, 57 "ip_address": "10.20.19.103", 58 "id": 436, 59 "mode": "static" 60 }, 61 { 62 "subnet": { 63 "dns_servers": ["10.20.19.2", "10.20.19.3"], 64 "name": "pxe", 65 "space": "default", 66 "vlan": { 67 "name": "untagged", 68 "vid": 0, 69 "mtu": 1500, 70 "fabric": "managed", 71 "id": 5001, 72 "resource_uri": "/MAAS/api/1.0/vlans/5001/" 73 }, 74 "gateway_ip": "10.20.19.2", 75 "cidr": "10.20.19.0/24", 76 "id": 3, 77 "resource_uri": "/MAAS/api/1.0/subnets/3/" 78 }, 79 "ip_address": "10.20.19.104", 80 "id": 437, 81 "mode": "static" 82 } 83 ], 84 "tags": [], 85 "vlan": { 86 "name": "untagged", 87 "vid": 0, 88 "mtu": 1500, 89 "fabric": "managed", 90 "id": 5001, 91 "resource_uri": "/MAAS/api/1.0/vlans/5001/" 92 }, 93 "enabled": true, 94 "id": 91, 95 "discovered": [ 96 { 97 "subnet": { 98 "dns_servers": [], 99 "name": "pxe", 100 "space": "default", 101 "vlan": { 102 "name": "untagged", 103 "vid": 0, 104 "mtu": 1500, 105 "fabric": "managed", 106 "id": 5001, 107 "resource_uri": "/MAAS/api/1.0/vlans/5001/" 108 }, 109 "gateway_ip": "10.20.19.2", 110 "cidr": "10.20.19.0/24", 111 "id": 3, 112 "resource_uri": "/MAAS/api/1.0/subnets/3/" 113 }, 114 "ip_address": "10.20.19.20" 115 } 116 ], 117 "mac_address": "52:54:00:70:9b:fe", 118 "parents": [], 119 "effective_mtu": 1500, 120 "params": {}, 121 "type": "physical", 122 "children": [ 123 "eth0.100", 124 "eth0.250", 125 "eth0.50" 126 ], 127 "resource_uri": "/MAAS/api/1.0/nodes/node-18489434-9eb0-11e5-bdef-00163e40c3b6/interfaces/91/" 128 }, 129 { 130 "name": "eth0.50", 131 "links": [ 132 { 133 "subnet": { 134 "dns_servers": [], 135 "name": "admin", 136 "space": "admin", 137 "vlan": { 138 "name": "admin", 139 "vid": 50, 140 "mtu": 1500, 141 "fabric": "managed", 142 "id": 5004, 143 "resource_uri": "/MAAS/api/1.0/vlans/5004/" 144 }, 145 "gateway_ip": "10.50.19.2", 146 "cidr": "10.50.19.0/24", 147 "id": 5, 148 "resource_uri": "/MAAS/api/1.0/subnets/5/" 149 }, 150 "ip_address": "10.50.19.103", 151 "id": 517, 152 "mode": "static" 153 } 154 ], 155 "tags": [], 156 "vlan": { 157 "name": "admin", 158 "vid": 50, 159 "mtu": 1500, 160 "fabric": "managed", 161 "id": 5004, 162 "resource_uri": "/MAAS/api/1.0/vlans/5004/" 163 }, 164 "enabled": true, 165 "id": 150, 166 "discovered": null, 167 "mac_address": "52:54:00:70:9b:fe", 168 "parents": [ 169 "eth0" 170 ], 171 "effective_mtu": 1500, 172 "params": {}, 173 "type": "vlan", 174 "children": [], 175 "resource_uri": "/MAAS/api/1.0/nodes/node-18489434-9eb0-11e5-bdef-00163e40c3b6/interfaces/150/" 176 }, 177 { 178 "name": "eth0.100", 179 "links": [ 180 { 181 "subnet": { 182 "dns_servers": [], 183 "name": "public", 184 "space": "public", 185 "vlan": { 186 "name": "public", 187 "vid": 100, 188 "mtu": 1500, 189 "fabric": "managed", 190 "id": 5005, 191 "resource_uri": "/MAAS/api/1.0/vlans/5005/" 192 }, 193 "gateway_ip": "10.100.19.2", 194 "cidr": "10.100.19.0/24", 195 "id": 6, 196 "resource_uri": "/MAAS/api/1.0/subnets/6/" 197 }, 198 "ip_address": "10.100.19.103", 199 "id": 519, 200 "mode": "static" 201 } 202 ], 203 "tags": [], 204 "vlan": { 205 "name": "public", 206 "vid": 100, 207 "mtu": 1500, 208 "fabric": "managed", 209 "id": 5005, 210 "resource_uri": "/MAAS/api/1.0/vlans/5005/" 211 }, 212 "enabled": true, 213 "id": 151, 214 "discovered": null, 215 "mac_address": "52:54:00:70:9b:fe", 216 "parents": [ 217 "eth0" 218 ], 219 "effective_mtu": 1500, 220 "params": {}, 221 "type": "vlan", 222 "children": [], 223 "resource_uri": "/MAAS/api/1.0/nodes/node-18489434-9eb0-11e5-bdef-00163e40c3b6/interfaces/151/" 224 }, 225 { 226 "name": "eth0.250", 227 "links": [ 228 { 229 "subnet": { 230 "dns_servers": [], 231 "name": "storage", 232 "space": "storage", 233 "vlan": { 234 "name": "storage", 235 "vid": 250, 236 "mtu": 1500, 237 "fabric": "managed", 238 "id": 5008, 239 "resource_uri": "/MAAS/api/1.0/vlans/5008/" 240 }, 241 "gateway_ip": "10.250.19.2", 242 "cidr": "10.250.19.0/24", 243 "id": 8, 244 "resource_uri": "/MAAS/api/1.0/subnets/8/" 245 }, 246 "ip_address": "10.250.19.103", 247 "id": 523, 248 "mode": "static" 249 } 250 ], 251 "tags": [], 252 "vlan": { 253 "name": "storage", 254 "vid": 250, 255 "mtu": 1500, 256 "fabric": "managed", 257 "id": 5008, 258 "resource_uri": "/MAAS/api/1.0/vlans/5008/" 259 }, 260 "enabled": true, 261 "id": 152, 262 "discovered": null, 263 "mac_address": "52:54:00:70:9b:fe", 264 "parents": [ 265 "eth0" 266 ], 267 "effective_mtu": 1500, 268 "params": {}, 269 "type": "vlan", 270 "children": [], 271 "resource_uri": "/MAAS/api/1.0/nodes/node-18489434-9eb0-11e5-bdef-00163e40c3b6/interfaces/152/" 272 } 273 ]` 274 275 var exampleParsedInterfaceSetJSON = []network.InterfaceInfo{{ 276 DeviceIndex: 0, 277 MACAddress: "52:54:00:70:9b:fe", 278 CIDR: "10.20.19.0/24", 279 ProviderId: "91", 280 ProviderSubnetId: "3", 281 AvailabilityZones: nil, 282 VLANTag: 0, 283 ProviderVLANId: "5001", 284 ProviderAddressId: "436", 285 InterfaceName: "eth0", 286 InterfaceType: "ethernet", 287 Disabled: false, 288 NoAutoStart: false, 289 ConfigType: "static", 290 Address: network.NewAddressOnSpace("default", "10.20.19.103"), 291 DNSServers: network.NewAddressesOnSpace("default", "10.20.19.2", "10.20.19.3"), 292 DNSSearchDomains: nil, 293 MTU: 1500, 294 GatewayAddress: network.NewAddressOnSpace("default", "10.20.19.2"), 295 }, { 296 DeviceIndex: 0, 297 MACAddress: "52:54:00:70:9b:fe", 298 CIDR: "10.20.19.0/24", 299 ProviderId: "91", 300 ProviderSubnetId: "3", 301 AvailabilityZones: nil, 302 VLANTag: 0, 303 ProviderVLANId: "5001", 304 ProviderAddressId: "437", 305 InterfaceName: "eth0", 306 InterfaceType: "ethernet", 307 Disabled: false, 308 NoAutoStart: false, 309 ConfigType: "static", 310 Address: network.NewAddressOnSpace("default", "10.20.19.104"), 311 DNSServers: network.NewAddressesOnSpace("default", "10.20.19.2", "10.20.19.3"), 312 DNSSearchDomains: nil, 313 MTU: 1500, 314 GatewayAddress: network.NewAddressOnSpace("default", "10.20.19.2"), 315 }, { 316 DeviceIndex: 1, 317 MACAddress: "52:54:00:70:9b:fe", 318 CIDR: "10.50.19.0/24", 319 ProviderId: "150", 320 ProviderSubnetId: "5", 321 AvailabilityZones: nil, 322 VLANTag: 50, 323 ProviderVLANId: "5004", 324 ProviderAddressId: "517", 325 InterfaceName: "eth0.50", 326 ParentInterfaceName: "eth0", 327 InterfaceType: "802.1q", 328 Disabled: false, 329 NoAutoStart: false, 330 ConfigType: "static", 331 Address: network.NewAddressOnSpace("admin", "10.50.19.103"), 332 DNSServers: nil, 333 DNSSearchDomains: nil, 334 MTU: 1500, 335 GatewayAddress: network.NewAddressOnSpace("admin", "10.50.19.2"), 336 }, { 337 DeviceIndex: 2, 338 MACAddress: "52:54:00:70:9b:fe", 339 CIDR: "10.100.19.0/24", 340 ProviderId: "151", 341 ProviderSubnetId: "6", 342 AvailabilityZones: nil, 343 VLANTag: 100, 344 ProviderVLANId: "5005", 345 ProviderAddressId: "519", 346 InterfaceName: "eth0.100", 347 ParentInterfaceName: "eth0", 348 InterfaceType: "802.1q", 349 Disabled: false, 350 NoAutoStart: false, 351 ConfigType: "static", 352 Address: network.NewAddressOnSpace("public", "10.100.19.103"), 353 DNSServers: nil, 354 DNSSearchDomains: nil, 355 MTU: 1500, 356 GatewayAddress: network.NewAddressOnSpace("public", "10.100.19.2"), 357 }, { 358 DeviceIndex: 3, 359 MACAddress: "52:54:00:70:9b:fe", 360 CIDR: "10.250.19.0/24", 361 ProviderId: "152", 362 ProviderSubnetId: "8", 363 AvailabilityZones: nil, 364 VLANTag: 250, 365 ProviderVLANId: "5008", 366 ProviderAddressId: "523", 367 ProviderSpaceId: "3", 368 InterfaceName: "eth0.250", 369 ParentInterfaceName: "eth0", 370 InterfaceType: "802.1q", 371 Disabled: false, 372 NoAutoStart: false, 373 ConfigType: "static", 374 Address: newAddressOnSpaceWithId("storage", network.Id("3"), "10.250.19.103"), 375 DNSServers: nil, 376 DNSSearchDomains: nil, 377 MTU: 1500, 378 GatewayAddress: newAddressOnSpaceWithId("storage", network.Id("3"), "10.250.19.2"), 379 }} 380 381 func (s *interfacesSuite) TestParseInterfacesNoJSON(c *gc.C) { 382 result, err := parseInterfaces(nil) 383 c.Check(err, gc.ErrorMatches, "parsing interfaces: unexpected end of JSON input") 384 c.Check(result, gc.IsNil) 385 } 386 387 func (s *interfacesSuite) TestParseInterfacesBadJSON(c *gc.C) { 388 result, err := parseInterfaces([]byte("$bad")) 389 c.Check(err, gc.ErrorMatches, `parsing interfaces: invalid character '\$' .*`) 390 c.Check(result, gc.IsNil) 391 } 392 393 func (s *interfacesSuite) TestParseInterfacesExampleJSON(c *gc.C) { 394 395 vlan0 := maasVLAN{ 396 ID: 5001, 397 Name: "untagged", 398 VID: 0, 399 MTU: 1500, 400 Fabric: "managed", 401 ResourceURI: "/MAAS/api/1.0/vlans/5001/", 402 } 403 404 vlan50 := maasVLAN{ 405 ID: 5004, 406 Name: "admin", 407 VID: 50, 408 MTU: 1500, 409 Fabric: "managed", 410 ResourceURI: "/MAAS/api/1.0/vlans/5004/", 411 } 412 413 vlan100 := maasVLAN{ 414 ID: 5005, 415 Name: "public", 416 VID: 100, 417 MTU: 1500, 418 Fabric: "managed", 419 ResourceURI: "/MAAS/api/1.0/vlans/5005/", 420 } 421 422 vlan250 := maasVLAN{ 423 ID: 5008, 424 Name: "storage", 425 VID: 250, 426 MTU: 1500, 427 Fabric: "managed", 428 ResourceURI: "/MAAS/api/1.0/vlans/5008/", 429 } 430 431 subnetPXE := maasSubnet{ 432 ID: 3, 433 Name: "pxe", 434 Space: "default", 435 VLAN: vlan0, 436 GatewayIP: "10.20.19.2", 437 DNSServers: []string{"10.20.19.2", "10.20.19.3"}, 438 CIDR: "10.20.19.0/24", 439 ResourceURI: "/MAAS/api/1.0/subnets/3/", 440 } 441 442 expected := []maasInterface{{ 443 ID: 91, 444 Name: "eth0", 445 Type: "physical", 446 Enabled: true, 447 MACAddress: "52:54:00:70:9b:fe", 448 VLAN: vlan0, 449 EffectveMTU: 1500, 450 Links: []maasInterfaceLink{{ 451 ID: 436, 452 Subnet: &subnetPXE, 453 IPAddress: "10.20.19.103", 454 Mode: "static", 455 }, { 456 ID: 437, 457 Subnet: &subnetPXE, 458 IPAddress: "10.20.19.104", 459 Mode: "static", 460 }}, 461 Parents: []string{}, 462 Children: []string{"eth0.100", "eth0.250", "eth0.50"}, 463 ResourceURI: "/MAAS/api/1.0/nodes/node-18489434-9eb0-11e5-bdef-00163e40c3b6/interfaces/91/", 464 }, { 465 ID: 150, 466 Name: "eth0.50", 467 Type: "vlan", 468 Enabled: true, 469 MACAddress: "52:54:00:70:9b:fe", 470 VLAN: vlan50, 471 EffectveMTU: 1500, 472 Links: []maasInterfaceLink{{ 473 ID: 517, 474 Subnet: &maasSubnet{ 475 ID: 5, 476 Name: "admin", 477 Space: "admin", 478 VLAN: vlan50, 479 GatewayIP: "10.50.19.2", 480 DNSServers: []string{}, 481 CIDR: "10.50.19.0/24", 482 ResourceURI: "/MAAS/api/1.0/subnets/5/", 483 }, 484 IPAddress: "10.50.19.103", 485 Mode: "static", 486 }}, 487 Parents: []string{"eth0"}, 488 Children: []string{}, 489 ResourceURI: "/MAAS/api/1.0/nodes/node-18489434-9eb0-11e5-bdef-00163e40c3b6/interfaces/150/", 490 }, { 491 ID: 151, 492 Name: "eth0.100", 493 Type: "vlan", 494 Enabled: true, 495 MACAddress: "52:54:00:70:9b:fe", 496 VLAN: vlan100, 497 EffectveMTU: 1500, 498 Links: []maasInterfaceLink{{ 499 ID: 519, 500 Subnet: &maasSubnet{ 501 ID: 6, 502 Name: "public", 503 Space: "public", 504 VLAN: vlan100, 505 GatewayIP: "10.100.19.2", 506 DNSServers: []string{}, 507 CIDR: "10.100.19.0/24", 508 ResourceURI: "/MAAS/api/1.0/subnets/6/", 509 }, 510 IPAddress: "10.100.19.103", 511 Mode: "static", 512 }}, 513 Parents: []string{"eth0"}, 514 Children: []string{}, 515 ResourceURI: "/MAAS/api/1.0/nodes/node-18489434-9eb0-11e5-bdef-00163e40c3b6/interfaces/151/", 516 }, { 517 ID: 152, 518 Name: "eth0.250", 519 Type: "vlan", 520 Enabled: true, 521 MACAddress: "52:54:00:70:9b:fe", 522 VLAN: vlan250, 523 EffectveMTU: 1500, 524 Links: []maasInterfaceLink{{ 525 ID: 523, 526 Subnet: &maasSubnet{ 527 ID: 8, 528 Name: "storage", 529 Space: "storage", 530 VLAN: vlan250, 531 GatewayIP: "10.250.19.2", 532 DNSServers: []string{}, 533 CIDR: "10.250.19.0/24", 534 ResourceURI: "/MAAS/api/1.0/subnets/8/", 535 }, 536 IPAddress: "10.250.19.103", 537 Mode: "static", 538 }}, 539 Parents: []string{"eth0"}, 540 Children: []string{}, 541 ResourceURI: "/MAAS/api/1.0/nodes/node-18489434-9eb0-11e5-bdef-00163e40c3b6/interfaces/152/", 542 }} 543 544 result, err := parseInterfaces([]byte(exampleInterfaceSetJSON)) 545 c.Check(err, jc.ErrorIsNil) 546 c.Check(result, jc.DeepEquals, expected) 547 } 548 549 func (s *interfacesSuite) TestMAASObjectNetworkInterfaces(c *gc.C) { 550 nodeJSON := fmt.Sprintf(`{ 551 "system_id": "foo", 552 "interface_set": %s 553 }`, exampleInterfaceSetJSON) 554 obj := s.testMAASObject.TestServer.NewNode(nodeJSON) 555 subnetsMap := make(map[string]network.Id) 556 subnetsMap["10.250.19.0/24"] = network.Id("3") 557 subnetsMap["192.168.1.0/24"] = network.Id("0") 558 559 infos, err := maasObjectNetworkInterfaces(&obj, subnetsMap) 560 c.Assert(err, jc.ErrorIsNil) 561 c.Check(infos, jc.DeepEquals, exampleParsedInterfaceSetJSON) 562 } 563 564 const ( 565 notUsingMAAS2 = false 566 notUsingMAAS1 = true 567 ) 568 569 func (s *interfacesSuite) TestInstanceConfiguredInterfaceNamesWithExampleMAAS1InterfaceSet(c *gc.C) { 570 nodeJSON := fmt.Sprintf(`{ 571 "system_id": "foo", 572 "interface_set": %s 573 }`, exampleInterfaceSetJSON) 574 obj := s.testMAASObject.TestServer.NewNode(nodeJSON) 575 576 inst := &maas1Instance{maasObject: &obj} 577 names, err := instanceConfiguredInterfaceNames(notUsingMAAS2, inst, nil) 578 c.Assert(err, jc.ErrorIsNil) 579 c.Check(names, jc.DeepEquals, []string{"eth0", "eth0:1", "eth0.50", "eth0.100", "eth0.250"}) 580 } 581 582 func (s *interfacesSuite) TestInstanceConfiguredNamesWithoutInterfaceSetMAAS1(c *gc.C) { 583 nodeJSON := `{"system_id": "foo"}` 584 obj := s.testMAASObject.TestServer.NewNode(nodeJSON) 585 586 inst := &maas1Instance{maasObject: &obj} 587 names, err := instanceConfiguredInterfaceNames(notUsingMAAS2, inst, nil) 588 c.Assert(err, gc.ErrorMatches, "interface_set not supported") 589 c.Check(err, jc.Satisfies, errors.IsNotSupported) 590 c.Check(names, gc.HasLen, 0) 591 } 592 593 func (s *interfacesSuite) TestInstanceConfiguredInterfaceNamesPartiallyConfiguredMAAS1(c *gc.C) { 594 nodeJSON := `{ 595 "system_id": "foo", 596 "interface_set": [{ 597 "name": "eth0", 598 "links": [ 599 {"subnet": {"cidr": "1.2.3.4/5"}, "mode": "static", "ip_address": "1.2.3.4"}, 600 {"subnet": {"cidr": "1.2.3.4/5"}, "mode": "auto"}, 601 {"subnet": {"cidr": "1.2.3.4/5"}, "mode": "dhcp"} 602 ] 603 }, { 604 "name": "eth1", 605 "links": [{"mode": "link_up"}] 606 }, { 607 "name": "eth1.99", 608 "links": [{"subnet": {"cidr": "192.168.99.0/24"}, "mode": "auto"}] 609 }]}` 610 obj := s.testMAASObject.TestServer.NewNode(nodeJSON) 611 612 inst := &maas1Instance{maasObject: &obj} 613 names, err := instanceConfiguredInterfaceNames(notUsingMAAS2, inst, nil) 614 c.Assert(err, jc.ErrorIsNil) 615 c.Check(names, jc.DeepEquals, []string{"eth0", "eth0:1", "eth0:2", "eth1.99"}) 616 } 617 618 func (s *interfacesSuite) TestInstanceConfiguredInterfaceNamesWithoutInterfaceSetMAAS2(c *gc.C) { 619 inst := &maas2Instance{machine: &fakeMachine{interfaceSet: nil}} 620 621 names, err := instanceConfiguredInterfaceNames(notUsingMAAS1, inst, nil) 622 c.Assert(err, jc.ErrorIsNil) 623 c.Check(names, gc.HasLen, 0) 624 } 625 626 func (s *interfacesSuite) TestInstanceConfiguredInterfaceNamesPartiallyConfiguredMAAS2(c *gc.C) { 627 628 subnet50 := &fakeSubnet{ 629 cidr: "10.50.19.0/24", 630 vlan: &fakeVLAN{id: 5050}, 631 } 632 subnet250 := &fakeSubnet{ 633 cidr: "10.250.19.0/24", 634 vlan: &fakeVLAN{id: 5250}, 635 } 636 637 interfaces := []gomaasapi.Interface{ 638 &fakeInterface{ 639 name: "eth0", 640 links: []gomaasapi.Link{ 641 &fakeLink{mode: "link_up"}, 642 }, 643 }, 644 &fakeInterface{ 645 name: "eth0.50", 646 links: []gomaasapi.Link{ 647 &fakeLink{ 648 subnet: subnet50, 649 ipAddress: "10.50.19.103", 650 mode: "static", 651 }, 652 &fakeLink{ // alias :1 653 subnet: subnet50, 654 mode: "auto", // no address yet, but will have at startNode time 655 }, 656 &fakeLink{ // alias :2 657 subnet: subnet50, 658 mode: "dhcp", // will get address at boot via DHCP 659 }, 660 }, 661 }, 662 &fakeInterface{name: "eth0.100", links: nil}, 663 &fakeInterface{ 664 name: "eth0.250", 665 links: []gomaasapi.Link{ 666 &fakeLink{ 667 subnet: subnet250, 668 mode: "auto", 669 }, 670 }, 671 }, 672 } 673 674 inst := &maas2Instance{machine: &fakeMachine{interfaceSet: interfaces}} 675 676 names, err := instanceConfiguredInterfaceNames(notUsingMAAS1, inst, nil) 677 c.Assert(err, jc.ErrorIsNil) 678 c.Check(names, jc.DeepEquals, []string{"eth0.50", "eth0.50:1", "eth0.50:2", "eth0.250"}) 679 } 680 681 func (s *interfacesSuite) TestMAAS2NetworkInterfaces(c *gc.C) { 682 vlan0 := fakeVLAN{ 683 id: 5001, 684 vid: 0, 685 mtu: 1500, 686 } 687 688 vlan50 := fakeVLAN{ 689 id: 5004, 690 vid: 50, 691 mtu: 1500, 692 } 693 694 vlan100 := fakeVLAN{ 695 id: 5005, 696 vid: 100, 697 mtu: 1500, 698 } 699 700 vlan250 := fakeVLAN{ 701 id: 5008, 702 vid: 250, 703 mtu: 1500, 704 } 705 706 subnetPXE := fakeSubnet{ 707 id: 3, 708 space: "default", 709 vlan: vlan0, 710 gateway: "10.20.19.2", 711 cidr: "10.20.19.0/24", 712 dnsServers: []string{"10.20.19.2", "10.20.19.3"}, 713 } 714 715 exampleInterfaces := []gomaasapi.Interface{ 716 &fakeInterface{ 717 id: 91, 718 name: "eth0", 719 type_: "physical", 720 enabled: true, 721 macAddress: "52:54:00:70:9b:fe", 722 vlan: vlan0, 723 links: []gomaasapi.Link{ 724 &fakeLink{ 725 id: 436, 726 subnet: &subnetPXE, 727 ipAddress: "10.20.19.103", 728 mode: "static", 729 }, 730 &fakeLink{ 731 id: 437, 732 subnet: &subnetPXE, 733 ipAddress: "10.20.19.104", 734 mode: "static", 735 }, 736 }, 737 parents: []string{}, 738 children: []string{"eth0.100", "eth0.250", "eth0.50"}, 739 }, 740 &fakeInterface{ 741 id: 150, 742 name: "eth0.50", 743 type_: "vlan", 744 enabled: true, 745 macAddress: "52:54:00:70:9b:fe", 746 vlan: vlan50, 747 links: []gomaasapi.Link{ 748 &fakeLink{ 749 id: 517, 750 subnet: &fakeSubnet{ 751 id: 5, 752 space: "admin", 753 vlan: vlan50, 754 gateway: "10.50.19.2", 755 cidr: "10.50.19.0/24", 756 dnsServers: []string{}, 757 }, 758 ipAddress: "10.50.19.103", 759 mode: "static", 760 }, 761 }, 762 parents: []string{"eth0"}, 763 children: []string{}, 764 }, 765 &fakeInterface{ 766 id: 151, 767 name: "eth0.100", 768 type_: "vlan", 769 enabled: true, 770 macAddress: "52:54:00:70:9b:fe", 771 vlan: vlan100, 772 links: []gomaasapi.Link{ 773 &fakeLink{ 774 id: 519, 775 subnet: &fakeSubnet{ 776 id: 6, 777 space: "public", 778 vlan: vlan100, 779 gateway: "10.100.19.2", 780 cidr: "10.100.19.0/24", 781 dnsServers: []string{}, 782 }, 783 ipAddress: "10.100.19.103", 784 mode: "static", 785 }, 786 }, 787 parents: []string{"eth0"}, 788 children: []string{}, 789 }, 790 &fakeInterface{ 791 id: 152, 792 name: "eth0.250", 793 type_: "vlan", 794 enabled: true, 795 macAddress: "52:54:00:70:9b:fe", 796 vlan: vlan250, 797 links: []gomaasapi.Link{ 798 &fakeLink{ 799 id: 523, 800 subnet: &fakeSubnet{ 801 id: 8, 802 space: "storage", 803 vlan: vlan250, 804 gateway: "10.250.19.2", 805 cidr: "10.250.19.0/24", 806 dnsServers: []string{}, 807 }, 808 ipAddress: "10.250.19.103", 809 mode: "static", 810 }, 811 }, 812 parents: []string{"eth0"}, 813 children: []string{}, 814 }, 815 } 816 817 subnetsMap := make(map[string]network.Id) 818 subnetsMap["10.250.19.0/24"] = network.Id("3") 819 subnetsMap["192.168.1.0/24"] = network.Id("0") 820 821 expected := []network.InterfaceInfo{{ 822 DeviceIndex: 0, 823 MACAddress: "52:54:00:70:9b:fe", 824 CIDR: "10.20.19.0/24", 825 ProviderId: "91", 826 ProviderSubnetId: "3", 827 AvailabilityZones: nil, 828 VLANTag: 0, 829 ProviderVLANId: "5001", 830 ProviderAddressId: "436", 831 InterfaceName: "eth0", 832 InterfaceType: "ethernet", 833 Disabled: false, 834 NoAutoStart: false, 835 ConfigType: "static", 836 Address: network.NewAddressOnSpace("default", "10.20.19.103"), 837 DNSServers: network.NewAddressesOnSpace("default", "10.20.19.2", "10.20.19.3"), 838 DNSSearchDomains: nil, 839 MTU: 1500, 840 GatewayAddress: network.NewAddressOnSpace("default", "10.20.19.2"), 841 }, { 842 DeviceIndex: 0, 843 MACAddress: "52:54:00:70:9b:fe", 844 CIDR: "10.20.19.0/24", 845 ProviderId: "91", 846 ProviderSubnetId: "3", 847 AvailabilityZones: nil, 848 VLANTag: 0, 849 ProviderVLANId: "5001", 850 ProviderAddressId: "437", 851 InterfaceName: "eth0", 852 InterfaceType: "ethernet", 853 Disabled: false, 854 NoAutoStart: false, 855 ConfigType: "static", 856 Address: network.NewAddressOnSpace("default", "10.20.19.104"), 857 DNSServers: network.NewAddressesOnSpace("default", "10.20.19.2", "10.20.19.3"), 858 DNSSearchDomains: nil, 859 MTU: 1500, 860 GatewayAddress: network.NewAddressOnSpace("default", "10.20.19.2"), 861 }, { 862 DeviceIndex: 1, 863 MACAddress: "52:54:00:70:9b:fe", 864 CIDR: "10.50.19.0/24", 865 ProviderId: "150", 866 ProviderSubnetId: "5", 867 AvailabilityZones: nil, 868 VLANTag: 50, 869 ProviderVLANId: "5004", 870 ProviderAddressId: "517", 871 InterfaceName: "eth0.50", 872 ParentInterfaceName: "eth0", 873 InterfaceType: "802.1q", 874 Disabled: false, 875 NoAutoStart: false, 876 ConfigType: "static", 877 Address: network.NewAddressOnSpace("admin", "10.50.19.103"), 878 DNSServers: nil, 879 DNSSearchDomains: nil, 880 MTU: 1500, 881 GatewayAddress: network.NewAddressOnSpace("admin", "10.50.19.2"), 882 }, { 883 DeviceIndex: 2, 884 MACAddress: "52:54:00:70:9b:fe", 885 CIDR: "10.100.19.0/24", 886 ProviderId: "151", 887 ProviderSubnetId: "6", 888 AvailabilityZones: nil, 889 VLANTag: 100, 890 ProviderVLANId: "5005", 891 ProviderAddressId: "519", 892 InterfaceName: "eth0.100", 893 ParentInterfaceName: "eth0", 894 InterfaceType: "802.1q", 895 Disabled: false, 896 NoAutoStart: false, 897 ConfigType: "static", 898 Address: network.NewAddressOnSpace("public", "10.100.19.103"), 899 DNSServers: nil, 900 DNSSearchDomains: nil, 901 MTU: 1500, 902 GatewayAddress: network.NewAddressOnSpace("public", "10.100.19.2"), 903 }, { 904 DeviceIndex: 3, 905 MACAddress: "52:54:00:70:9b:fe", 906 CIDR: "10.250.19.0/24", 907 ProviderId: "152", 908 ProviderSubnetId: "8", 909 AvailabilityZones: nil, 910 VLANTag: 250, 911 ProviderVLANId: "5008", 912 ProviderAddressId: "523", 913 ProviderSpaceId: "3", 914 InterfaceName: "eth0.250", 915 ParentInterfaceName: "eth0", 916 InterfaceType: "802.1q", 917 Disabled: false, 918 NoAutoStart: false, 919 ConfigType: "static", 920 Address: newAddressOnSpaceWithId("storage", network.Id("3"), "10.250.19.103"), 921 DNSServers: nil, 922 DNSSearchDomains: nil, 923 MTU: 1500, 924 GatewayAddress: newAddressOnSpaceWithId("storage", network.Id("3"), "10.250.19.2"), 925 }} 926 927 instance := &maas2Instance{machine: &fakeMachine{interfaceSet: exampleInterfaces}} 928 929 infos, err := maas2NetworkInterfaces(instance, subnetsMap) 930 c.Assert(err, jc.ErrorIsNil) 931 c.Check(infos, jc.DeepEquals, expected) 932 } 933 934 func (s *interfacesSuite) TestMAAS2InterfacesNilVLAN(c *gc.C) { 935 vlan0 := fakeVLAN{ 936 id: 5001, 937 vid: 0, 938 mtu: 1500, 939 } 940 941 subnetPXE := fakeSubnet{ 942 id: 3, 943 space: "default", 944 vlan: vlan0, 945 gateway: "10.20.19.2", 946 cidr: "10.20.19.0/24", 947 dnsServers: []string{"10.20.19.2", "10.20.19.3"}, 948 } 949 950 exampleInterfaces := []gomaasapi.Interface{ 951 &fakeInterface{ 952 id: 91, 953 name: "eth0", 954 type_: "physical", 955 enabled: true, 956 macAddress: "52:54:00:70:9b:fe", 957 vlan: nil, 958 links: []gomaasapi.Link{&fakeLink{ 959 id: 436, 960 subnet: &subnetPXE, 961 ipAddress: "10.20.19.103", 962 mode: "static", 963 }}, 964 parents: []string{}, 965 children: []string{"eth0.100", "eth0.250", "eth0.50"}, 966 }, 967 } 968 969 instance := &maas2Instance{machine: &fakeMachine{interfaceSet: exampleInterfaces}} 970 971 expected := []network.InterfaceInfo{{ 972 DeviceIndex: 0, 973 MACAddress: "52:54:00:70:9b:fe", 974 CIDR: "10.20.19.0/24", 975 ProviderId: "91", 976 ProviderSubnetId: "3", 977 AvailabilityZones: nil, 978 VLANTag: 0, 979 ProviderVLANId: "5001", 980 ProviderAddressId: "436", 981 InterfaceName: "eth0", 982 InterfaceType: "ethernet", 983 Disabled: false, 984 NoAutoStart: false, 985 ConfigType: "static", 986 Address: network.NewAddressOnSpace("default", "10.20.19.103"), 987 DNSServers: network.NewAddressesOnSpace("default", "10.20.19.2", "10.20.19.3"), 988 DNSSearchDomains: nil, 989 MTU: 1500, 990 GatewayAddress: network.NewAddressOnSpace("default", "10.20.19.2"), 991 }} 992 993 infos, err := maas2NetworkInterfaces(instance, map[string]network.Id{}) 994 c.Assert(err, jc.ErrorIsNil) 995 c.Check(infos, jc.DeepEquals, expected) 996 } 997 998 const lshwXMLTemplate = ` 999 <?xml version="1.0" standalone="yes" ?> 1000 <!-- generated by lshw-B.02.16 --> 1001 <list> 1002 <node id="node1" claimed="true" class="system" handle="DMI:0001"> 1003 <description>Computer</description> 1004 <product>VirtualBox ()</product> 1005 <width units="bits">64</width> 1006 <node id="core" claimed="true" class="bus" handle="DMI:0008"> 1007 <description>Motherboard</description> 1008 <node id="pci" claimed="true" class="bridge" handle="PCIBUS:0000:00"> 1009 <description>Host bridge</description>{{$list := .}}{{range $mac, $ifi := $list}} 1010 <node id="network{{if gt (len $list) 1}}:{{$ifi.DeviceIndex}}{{end}}"{{if $ifi.Disabled}} disabled="true"{{end}} claimed="true" class="network" handle="PCI:0000:00:03.0"> 1011 <description>Ethernet interface</description> 1012 <product>82540EM Gigabit Ethernet Controller</product> 1013 <logicalname>{{$ifi.InterfaceName}}</logicalname> 1014 <serial>{{$mac}}</serial> 1015 </node>{{end}} 1016 </node> 1017 </node> 1018 </node> 1019 </list> 1020 ` 1021 1022 func (suite *environSuite) generateHWTemplate(netMacs map[string]ifaceInfo) (string, error) { 1023 tmpl, err := template.New("test").Parse(lshwXMLTemplate) 1024 if err != nil { 1025 return "", err 1026 } 1027 var buf bytes.Buffer 1028 err = tmpl.Execute(&buf, netMacs) 1029 if err != nil { 1030 return "", err 1031 } 1032 return string(buf.Bytes()), nil 1033 }