Merge pull request #10093 from ufukty/digitalocean-connect-with-private-ip

Adds the capability of provisioning with private ip for digitalocean
This commit is contained in:
Megan Marsh 2020-11-20 14:33:03 -08:00 committed by GitHub
commit 8ec7ee0ab7
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
6 changed files with 90 additions and 2 deletions

View File

@ -362,3 +362,55 @@ func TestBuilderPrepare_DropletName(t *testing.T) {
}
}
func TestBuilderPrepare_VPCUUID(t *testing.T) {
var b Builder
config := testConfig()
// Test with the case vpc_uuid is defined but private_networking is not enabled
config["vpc_uuid"] = "554c41b3-425f-5403-8860-7f24fb108098"
_, warnings, err := b.Prepare(config)
if len(warnings) > 0 {
t.Fatalf("bad: %#v", warnings)
}
if err == nil {
t.Fatalf("should have error: 'private networking should be enabled to use vpc_uuid'")
}
// Test with the case both vpc_uuid and private_networking are defined/enabled
config["private_networking"] = true
b = Builder{}
_, warnings, err = b.Prepare(config)
if len(warnings) > 0 {
t.Fatalf("bad: %#v", warnings)
}
if err != nil {
t.Fatal("should not have error")
}
}
func TestBuilderPrepare_ConnectWithPrivateIP(t *testing.T) {
var b Builder
config := testConfig()
// Test with the case connect_with_private_ip is defined but private_networking is not enabled
config["connect_with_private_ip"] = true
_, warnings, err := b.Prepare(config)
if len(warnings) > 0 {
t.Fatalf("bad: %#v", warnings)
}
if err == nil {
t.Fatalf("should have error: 'private networking should be enabled to use connect_with_private_ip'")
}
// Test with the case both connect_with_private_ip and private_networking are enabled
config["private_networking"] = true
b = Builder{}
_, warnings, err = b.Prepare(config)
if len(warnings) > 0 {
t.Fatalf("bad: %#v", warnings)
}
if err != nil {
t.Fatal("should not have error")
}
}

View File

@ -85,6 +85,14 @@ type Config struct {
UserDataFile string `mapstructure:"user_data_file" required:"false"`
// Tags to apply to the droplet when it is created
Tags []string `mapstructure:"tags" required:"false"`
// UUID of the VPC which the droplet will be created in. Before using this,
// private_networking should be enabled.
VPCUUID string `mapstructure:"vpc_uuid" required:"false"`
// Wheter the communicators should use private IP or not (public IP in that case).
// If the droplet is or going to be accessible only from the local network because
// it is at behind a firewall, then communicators should use the private IP
// instead of the public IP. Before using this, private_networking should be enabled.
ConnectWithPrivateIP bool `mapstructure:"connect_with_private_ip" required:"false"`
ctx interpolate.Context
}
@ -187,6 +195,20 @@ func (c *Config) Prepare(raws ...interface{}) ([]string, error) {
}
}
// Check if the PrivateNetworking is enabled by user before use VPC UUID
if c.VPCUUID != "" {
if c.PrivateNetworking != true {
errs = packer.MultiErrorAppend(errs, errors.New("private networking should be enabled to use vpc_uuid"))
}
}
// Check if the PrivateNetworking is enabled by user before use ConnectWithPrivateIP
if c.ConnectWithPrivateIP == true {
if c.PrivateNetworking != true {
errs = packer.MultiErrorAppend(errs, errors.New("private networking should be enabled to use connect_with_private_ip"))
}
}
if errs != nil && len(errs.Errors) > 0 {
return nil, errs
}

View File

@ -82,6 +82,8 @@ type FlatConfig struct {
UserData *string `mapstructure:"user_data" required:"false" cty:"user_data" hcl:"user_data"`
UserDataFile *string `mapstructure:"user_data_file" required:"false" cty:"user_data_file" hcl:"user_data_file"`
Tags []string `mapstructure:"tags" required:"false" cty:"tags" hcl:"tags"`
VPCUUID *string `mapstructure:"vpc_uuid" required:"false" cty:"vpc_uuid" hcl:"vpc_uuid"`
ConnectWithPrivateIP *bool `mapstructure:"connect_with_private_ip" required:"false" cty:"connect_with_private_ip" hcl:"connect_with_private_ip"`
}
// FlatMapstructure returns a new FlatConfig.
@ -169,6 +171,8 @@ func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
"user_data": &hcldec.AttrSpec{Name: "user_data", Type: cty.String, Required: false},
"user_data_file": &hcldec.AttrSpec{Name: "user_data_file", Type: cty.String, Required: false},
"tags": &hcldec.AttrSpec{Name: "tags", Type: cty.List(cty.String), Required: false},
"vpc_uuid": &hcldec.AttrSpec{Name: "vpc_uuid", Type: cty.String, Required: false},
"connect_with_private_ip": &hcldec.AttrSpec{Name: "connect_with_private_ip", Type: cty.Bool, Required: false},
}
return s
}

View File

@ -52,6 +52,7 @@ func (s *stepCreateDroplet) Run(ctx context.Context, state multistep.StateBag) m
IPv6: c.IPv6,
UserData: userData,
Tags: c.Tags,
VPCUUID: c.VPCUUID,
}
log.Printf("[DEBUG] Droplet create paramaters: %s", godo.Stringify(dropletCreateReq))

View File

@ -46,10 +46,11 @@ func (s *stepDropletInfo) Run(ctx context.Context, state multistep.StateBag) mul
return multistep.ActionHalt
}
// Find a public IPv4 network
// Find the ip address which will be used by communicator
foundNetwork := false
for _, network := range droplet.Networks.V4 {
if network.Type == "public" {
if (c.ConnectWithPrivateIP && network.Type == "private") ||
(!(c.ConnectWithPrivateIP) && network.Type == "public") {
state.Put("droplet_ip", network.IPAddress)
foundNetwork = true
break

View File

@ -43,3 +43,11 @@
data when launching the Droplet.
- `tags` ([]string) - Tags to apply to the droplet when it is created
- `vpc_uuid` (string) - UUID of the VPC which the droplet will be created in. Before using this,
private_networking should be enabled.
- `connect_with_private_ip` (bool) - Wheter the communicators should use private IP or not (public IP in that case).
If the droplet is or going to be accessible only from the local network because
it is at behind a firewall, then communicators should use the private IP
instead of the public IP. Before using this, private_networking should be enabled.