forked from scaleway/scaleway-cli
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat: add scaleway_compute_instance_ip resource (scaleway#161)
- Loading branch information
1 parent
3dcde13
commit 255c239
Showing
12 changed files
with
4,338 additions
and
4 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,155 @@ | ||
package scaleway | ||
|
||
import ( | ||
"github.com/hashicorp/terraform/helper/schema" | ||
"github.com/scaleway/scaleway-sdk-go/api/instance/v1" | ||
) | ||
|
||
func resourceScalewayComputeInstanceIP() *schema.Resource { | ||
return &schema.Resource{ | ||
Create: resourceScalewayComputeInstanceIPCreate, | ||
Read: resourceScalewayComputeInstanceIPRead, | ||
Update: resourceScalewayComputeInstanceIPUpdate, | ||
Delete: resourceScalewayComputeInstanceIPDelete, | ||
Importer: &schema.ResourceImporter{ | ||
State: schema.ImportStatePassthrough, | ||
}, | ||
SchemaVersion: 0, | ||
Schema: map[string]*schema.Schema{ | ||
"address": { | ||
Type: schema.TypeString, | ||
Computed: true, | ||
Description: "The ip address", | ||
}, | ||
"reverse": { | ||
Type: schema.TypeString, | ||
Optional: true, | ||
Description: "The reverse dns for this IP", | ||
}, | ||
"server_id": { | ||
Type: schema.TypeString, | ||
Computed: true, | ||
Description: "The server associated with this ip", | ||
}, | ||
"zone": zoneSchema(), | ||
"project_id": projectIDSchema(), | ||
}, | ||
} | ||
} | ||
|
||
func resourceScalewayComputeInstanceIPCreate(d *schema.ResourceData, m interface{}) error { | ||
meta := m.(*Meta) | ||
instanceApi := instance.NewAPI(meta.scwClient) | ||
|
||
zone, err := getZone(d, meta) | ||
if err != nil { | ||
return err | ||
} | ||
|
||
res, err := instanceApi.CreateIP(&instance.CreateIPRequest{ | ||
Zone: zone, | ||
Organization: d.Get("project_id").(string), | ||
}) | ||
if err != nil { | ||
return err | ||
} | ||
|
||
reverse := d.Get("reverse").(string) | ||
if reverse != "" { | ||
_, err = instanceApi.UpdateIP(&instance.UpdateIPRequest{ | ||
Zone: zone, | ||
IPID: res.IP.ID, | ||
Reverse: &reverse, | ||
}) | ||
if err != nil { | ||
return err | ||
} | ||
} | ||
|
||
d.SetId(newZonedId(zone, res.IP.ID)) | ||
return resourceScalewayComputeInstanceIPRead(d, m) | ||
} | ||
|
||
func resourceScalewayComputeInstanceIPRead(d *schema.ResourceData, m interface{}) error { | ||
meta := m.(*Meta) | ||
instanceApi := instance.NewAPI(meta.scwClient) | ||
|
||
zone, ID, err := parseZonedID(d.Id()) | ||
if err != nil { | ||
return err | ||
} | ||
|
||
res, err := instanceApi.GetIP(&instance.GetIPRequest{ | ||
IPID: ID, | ||
Zone: zone, | ||
}) | ||
|
||
if err != nil { | ||
// We check for 403 because instance API returns 403 for a deleted IP | ||
if is404Error(err) || is403Error(err) { | ||
d.SetId("") | ||
return nil | ||
} | ||
return err | ||
} | ||
|
||
d.Set("address", res.IP.Address) | ||
d.Set("zone", string(zone)) | ||
d.Set("project_id", res.IP.Organization) | ||
d.Set("reverse", res.IP.Reverse) | ||
|
||
if res.IP.Server != nil { | ||
d.Set("server_id", res.IP.Server.ID) | ||
} else { | ||
d.Set("server_id", nil) | ||
} | ||
|
||
return nil | ||
} | ||
|
||
func resourceScalewayComputeInstanceIPUpdate(d *schema.ResourceData, m interface{}) error { | ||
meta := m.(*Meta) | ||
instanceApi := instance.NewAPI(meta.scwClient) | ||
|
||
zone, ID, err := parseZonedID(d.Id()) | ||
if err != nil { | ||
return err | ||
} | ||
|
||
if d.HasChange("reverse") { | ||
l.Debugf("updating IP %q reverse to %q\n", d.Id(), d.Get("reverse")) | ||
|
||
reverse := d.Get("reverse").(string) | ||
_, err = instanceApi.UpdateIP(&instance.UpdateIPRequest{ | ||
Zone: zone, | ||
IPID: ID, | ||
Reverse: &reverse, | ||
}) | ||
if err != nil { | ||
return err | ||
} | ||
} | ||
|
||
return resourceScalewayComputeInstanceIPRead(d, m) | ||
} | ||
|
||
func resourceScalewayComputeInstanceIPDelete(d *schema.ResourceData, m interface{}) error { | ||
meta := m.(*Meta) | ||
instanceApi := instance.NewAPI(meta.scwClient) | ||
|
||
zone, ID, err := parseZonedID(d.Id()) | ||
if err != nil { | ||
return err | ||
} | ||
|
||
err = instanceApi.DeleteIP(&instance.DeleteIPRequest{ | ||
IPID: ID, | ||
Zone: zone, | ||
}) | ||
|
||
if err != nil && !is404Error(err) { | ||
return err | ||
} | ||
|
||
return nil | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,154 @@ | ||
package scaleway | ||
|
||
import ( | ||
"fmt" | ||
"testing" | ||
|
||
"github.com/hashicorp/terraform/helper/resource" | ||
"github.com/hashicorp/terraform/terraform" | ||
"github.com/scaleway/scaleway-sdk-go/api/instance/v1" | ||
) | ||
|
||
// Check that reverse is handled at creation and update time | ||
var testAccScalewayComputeInstanceIPConfig = []string{ | ||
` | ||
resource "scaleway_compute_instance_ip" "base" {} | ||
resource "scaleway_compute_instance_ip" "scaleway" { | ||
reverse = "www.scaleway.com" | ||
} | ||
`, | ||
` | ||
resource "scaleway_compute_instance_ip" "base" { | ||
reverse = "www.scaleway.com" | ||
} | ||
resource "scaleway_compute_instance_ip" "scaleway" {} | ||
`, | ||
} | ||
|
||
// Check that we can change the zone of an ip (delete + create) | ||
var testAccScalewayComputeInstanceIPZoneConfig = []string{ | ||
` | ||
resource "scaleway_compute_instance_ip" "base" {} | ||
`, | ||
` | ||
resource "scaleway_compute_instance_ip" "base" { | ||
zone = "nl-ams-1" | ||
} | ||
`, | ||
} | ||
|
||
func TestAccScalewayComputeInstanceIP(t *testing.T) { | ||
|
||
resource.Test(t, resource.TestCase{ | ||
PreCheck: func() { testAccPreCheck(t) }, | ||
Providers: testAccProviders, | ||
CheckDestroy: testAccCheckScalewayComputeInstanceIPDestroy, | ||
Steps: []resource.TestStep{ | ||
{ | ||
Config: testAccScalewayComputeInstanceIPConfig[0], | ||
Check: resource.ComposeTestCheckFunc( | ||
testAccCheckScalewayComputeInstanceIPExists("scaleway_compute_instance_ip.base"), | ||
testAccCheckScalewayComputeInstanceIPExists("scaleway_compute_instance_ip.scaleway"), | ||
resource.TestCheckResourceAttr("scaleway_compute_instance_ip.base", "reverse", ""), | ||
resource.TestCheckResourceAttr("scaleway_compute_instance_ip.scaleway", "reverse", "www.scaleway.com"), | ||
), | ||
}, | ||
{ | ||
Config: testAccScalewayComputeInstanceIPConfig[1], | ||
Check: resource.ComposeTestCheckFunc( | ||
testAccCheckScalewayComputeInstanceIPExists("scaleway_compute_instance_ip.base"), | ||
testAccCheckScalewayComputeInstanceIPExists("scaleway_compute_instance_ip.scaleway"), | ||
resource.TestCheckResourceAttr("scaleway_compute_instance_ip.base", "reverse", "www.scaleway.com"), | ||
resource.TestCheckResourceAttr("scaleway_compute_instance_ip.scaleway", "reverse", ""), | ||
), | ||
}, | ||
}, | ||
}) | ||
} | ||
|
||
func TestAccScalewayComputeInstanceIP_Zone(t *testing.T) { | ||
|
||
resource.Test(t, resource.TestCase{ | ||
PreCheck: func() { testAccPreCheck(t) }, | ||
Providers: testAccProviders, | ||
CheckDestroy: testAccCheckScalewayComputeInstanceIPDestroy, | ||
Steps: []resource.TestStep{ | ||
{ | ||
Config: testAccScalewayComputeInstanceIPZoneConfig[0], | ||
Check: resource.ComposeTestCheckFunc( | ||
testAccCheckScalewayComputeInstanceIPExists("scaleway_compute_instance_ip.base"), | ||
resource.TestCheckResourceAttr("scaleway_compute_instance_ip.base", "zone", "fr-par-1"), | ||
), | ||
}, | ||
{ | ||
Config: testAccScalewayComputeInstanceIPZoneConfig[1], | ||
Check: resource.ComposeTestCheckFunc( | ||
testAccCheckScalewayComputeInstanceIPExists("scaleway_compute_instance_ip.base"), | ||
resource.TestCheckResourceAttr("scaleway_compute_instance_ip.base", "zone", "nl-ams-1"), | ||
), | ||
}, | ||
}, | ||
}) | ||
} | ||
|
||
func testAccCheckScalewayComputeInstanceIPExists(n string) resource.TestCheckFunc { | ||
return func(s *terraform.State) error { | ||
rs, ok := s.RootModule().Resources[n] | ||
|
||
if !ok { | ||
return fmt.Errorf("not found: %s", n) | ||
} | ||
|
||
zone, ID, err := parseZonedID(rs.Primary.ID) | ||
if err != nil { | ||
return err | ||
} | ||
|
||
meta := testAccProvider.Meta().(*Meta) | ||
instanceApi := instance.NewAPI(meta.scwClient) | ||
_, err = instanceApi.GetIP(&instance.GetIPRequest{ | ||
IPID: ID, | ||
Zone: zone, | ||
}) | ||
|
||
if err != nil { | ||
return err | ||
} | ||
|
||
return nil | ||
} | ||
} | ||
|
||
func testAccCheckScalewayComputeInstanceIPDestroy(s *terraform.State) error { | ||
meta := testAccProvider.Meta().(*Meta) | ||
instanceApi := instance.NewAPI(meta.scwClient) | ||
|
||
for _, rs := range s.RootModule().Resources { | ||
if rs.Type != "scaleway_compute_instance_ip" { | ||
continue | ||
} | ||
|
||
zone, ID, err := parseZonedID(rs.Primary.ID) | ||
if err != nil { | ||
return err | ||
} | ||
|
||
_, err = instanceApi.GetIP(&instance.GetIPRequest{ | ||
Zone: zone, | ||
IPID: ID, | ||
}) | ||
|
||
// If no error resource still exist | ||
if err == nil { | ||
return fmt.Errorf("IP (%s) still exists", rs.Primary.ID) | ||
} | ||
|
||
// Unexpected api error we return it | ||
// We check for 403 because instance API return 403 for deleted IP | ||
if !is404Error(err) && !is403Error(err) { | ||
return err | ||
} | ||
} | ||
|
||
return nil | ||
} |
Oops, something went wrong.