Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(flexibleip): add support for IPv6 #2104

Merged
merged 4 commits into from
Aug 22, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
26 changes: 19 additions & 7 deletions docs/resources/flexible_ip.md
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,14 @@ resource "scaleway_flexible_ip" "main" {
}
```

### With IPv6

```hcl
resource "scaleway_flexible_ip" "main" {
is_ipv6 = "true"
}
```

### With baremetal server

```hcl
Expand Down Expand Up @@ -62,9 +70,10 @@ resource "scaleway_flexible_ip" "main" {

The following arguments are supported:

- `description`: (Optional) A description of the flexible IP.
- `tags`: (Optional) A list of tags to apply to the flexible IP.
- `description` - (Optional) A description of the flexible IP.
- `tags` - (Optional) A list of tags to apply to the flexible IP.
- `reverse` - (Optional) The reverse domain associated with this flexible IP.
- `is_ipv6` - (Optional) Defines whether the flexible IP has an IPv6 address.

## Attributes Reference

Expand All @@ -74,11 +83,14 @@ In addition to all arguments above, the following attributes are exported:

~> **Important:** Flexible IPs' IDs are [zoned](../guides/regions_and_zones.md#resource-ids), which means they are of the form `{zone}/{id}`, e.g. `fr-par-1/11111111-1111-1111-1111-111111111111`

- `ip_address` - The IPv4 address of the Flexible IP
- `zone` - The zone of the Flexible IP
- `organization_id` - The organization of the Flexible IP
- `project_id` - The project of the Flexible IP
- `server_id` - The ID of the associated server
- `ip_address` - The IP address of the Flexible IP.
- `server_id` - The ID of the associated server.
- `status` - The status of the flexible IP.
- `created_at` - The date and time of the creation of the Flexible IP (Format ISO 8601).
- `updated_at` - The date and time of the last update of the Flexible IP (Format ISO 8601).
- `zone` - The zone of the Flexible IP.
- `organization_id` - The organization of the Flexible IP.
- `project_id` - The project of the Flexible IP.

## Import

Expand Down
23 changes: 19 additions & 4 deletions scaleway/resource_flexible_ip.go
Original file line number Diff line number Diff line change
Expand Up @@ -32,10 +32,12 @@ func resourceScalewayFlexibleIP() *schema.Resource {
Optional: true,
Description: "Description of the flexible IP",
},
"ip_address": {
Type: schema.TypeString,
Computed: true,
Description: "The IPv4 address of the flexible IP",
"is_ipv6": {
Type: schema.TypeBool,
Optional: true,
ForceNew: true,
Default: false,
Description: "Defines whether the flexible IP has an IPv6 address",
},
"reverse": {
Type: schema.TypeString,
Expand All @@ -59,6 +61,16 @@ func resourceScalewayFlexibleIP() *schema.Resource {
"zone": zoneSchema(),
"organization_id": organizationIDSchema(),
"project_id": projectIDSchema(),
"ip_address": {
Type: schema.TypeString,
Computed: true,
Description: "The IP address of the flexible IP",
},
"status": {
Type: schema.TypeString,
Computed: true,
Description: "The status of the flexible IP",
},
"created_at": {
Type: schema.TypeString,
Computed: true,
Expand Down Expand Up @@ -87,6 +99,7 @@ func resourceScalewayFlexibleIPCreate(ctx context.Context, d *schema.ResourceDat
Tags: expandStrings(d.Get("tags")),
ServerID: expandStringPtr(expandID(d.Get("server_id"))),
Reverse: expandStringPtr(d.Get("reverse")),
IsIPv6: d.Get("is_ipv6").(bool),
}, scw.WithContext(ctx))
if err != nil {
return diag.FromErr(err)
Expand Down Expand Up @@ -133,6 +146,8 @@ func resourceScalewayFlexibleIPRead(ctx context.Context, d *schema.ResourceData,
_ = d.Set("reverse", flexibleIP.Reverse)
_ = d.Set("created_at", flattenTime(flexibleIP.CreatedAt))
_ = d.Set("updated_at", flattenTime(flexibleIP.UpdatedAt))
_ = d.Set("tags", flexibleIP.Tags)
_ = d.Set("status", flexibleIP.Status.String())

if flexibleIP.ServerID != nil {
_ = d.Set("server_id", newZonedIDString(zone, *flexibleIP.ServerID))
Expand Down
59 changes: 56 additions & 3 deletions scaleway/resource_flexible_ip_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ package scaleway

import (
"fmt"
"net"
"testing"

"github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource"
Expand Down Expand Up @@ -60,9 +61,10 @@ func TestAccScalewayFlexibleIP_Basic(t *testing.T) {
),
},
{
ResourceName: "scaleway_flexible_ip.main",
ImportState: true,
ImportStateVerify: true,
ResourceName: "scaleway_flexible_ip.main",
ImportState: true,
ImportStateVerify: true,
ImportStateVerifyIgnore: []string{"is_ipv6"},
},
},
})
Expand Down Expand Up @@ -99,6 +101,29 @@ func TestAccScalewayFlexibleIP_WithZone(t *testing.T) {
})
}

func TestAccScalewayFlexibleIP_IPv6(t *testing.T) {
tt := NewTestTools(t)
defer tt.Cleanup()
resource.ParallelTest(t, resource.TestCase{
ProviderFactories: tt.ProviderFactories,
CheckDestroy: testAccCheckScalewayFlexibleIPDestroy(tt),
Steps: []resource.TestStep{
{
Config: `
resource "scaleway_flexible_ip" "main" {
is_ipv6 = true
}
`,
Check: resource.ComposeTestCheckFunc(
testAccCheckScalewayFlexibleIPExists(tt, "scaleway_flexible_ip.main"),
resource.TestCheckResourceAttr("scaleway_flexible_ip.main", "is_ipv6", "true"),
testAccCheckScalewayFlexibleIPIsIPv6(tt, "scaleway_flexible_ip.main"),
),
},
},
})
}

func TestAccScalewayFlexibleIP_CreateAndAttachToBaremetalServer(t *testing.T) {
tt := NewTestTools(t)
defer tt.Cleanup()
Expand Down Expand Up @@ -400,3 +425,31 @@ func testAccCheckScalewayFlexibleIPAttachedToBaremetalServer(tt *TestTools, ipRe
return nil
}
}

func testAccCheckScalewayFlexibleIPIsIPv6(tt *TestTools, resourceName string) resource.TestCheckFunc {
return func(s *terraform.State) error {
rs, ok := s.RootModule().Resources[resourceName]
if !ok {
return fmt.Errorf("resource not found: %s", resourceName)
}

fipAPI, zone, ID, err := fipAPIWithZoneAndID(tt.Meta, rs.Primary.ID)
if err != nil {
return err
}

flexibleIP, err := fipAPI.GetFlexibleIP(&flexibleip.GetFlexibleIPRequest{
Zone: zone,
FipID: ID,
})
if err != nil {
return err
}

if len(flexibleIP.IPAddress.IP.To16()) != net.IPv6len {
return fmt.Errorf("expected an IPv6 address but got: %s", flexibleIP.IPAddress.String())
}

return nil
}
}
Loading