From 317d7ea2f3d6383fd518f27acc2c73dbc4be5522 Mon Sep 17 00:00:00 2001 From: Dave DeRicco <30156588+ddericco@users.noreply.github.com> Date: Wed, 25 Oct 2023 11:10:28 -0400 Subject: [PATCH 1/9] Add support for NO_ENCAP protocol --- .../networkmanager/connect_attachment.go | 2 +- .../networkmanager/connect_attachment_test.go | 76 +++++++++++++++++++ 2 files changed, 77 insertions(+), 1 deletion(-) diff --git a/internal/service/networkmanager/connect_attachment.go b/internal/service/networkmanager/connect_attachment.go index 6f4937f32076..665572814b55 100644 --- a/internal/service/networkmanager/connect_attachment.go +++ b/internal/service/networkmanager/connect_attachment.go @@ -93,7 +93,7 @@ func ResourceConnectAttachment() *schema.Resource { "protocol": { Type: schema.TypeString, Optional: true, - ValidateFunc: validation.StringInSlice([]string{"GRE"}, false), + ValidateFunc: validation.StringInSlice([]string{"GRE", "NO_ENCAP"}, false), }, }, }, diff --git a/internal/service/networkmanager/connect_attachment_test.go b/internal/service/networkmanager/connect_attachment_test.go index d8a84839b151..fc12393296b8 100644 --- a/internal/service/networkmanager/connect_attachment_test.go +++ b/internal/service/networkmanager/connect_attachment_test.go @@ -39,6 +39,7 @@ func TestAccNetworkManagerConnectAttachment_basic(t *testing.T) { resource.TestCheckResourceAttr(resourceName, "attachment_type", "CONNECT"), resource.TestCheckResourceAttrSet(resourceName, "core_network_id"), resource.TestCheckResourceAttr(resourceName, "edge_location", acctest.Region()), + resource.TestCheckResourceAttr(resourceName, "options.0.protocol", "GRE"), acctest.CheckResourceAttrAccountID(resourceName, "owner_account_id"), resource.TestCheckResourceAttr(resourceName, "segment_name", "shared"), resource.TestCheckResourceAttrSet(resourceName, "state"), @@ -74,6 +75,7 @@ func TestAccNetworkManagerConnectAttachment_basic_NoDependsOn(t *testing.T) { resource.TestCheckResourceAttr(resourceName, "attachment_type", "CONNECT"), resource.TestCheckResourceAttrSet(resourceName, "core_network_id"), resource.TestCheckResourceAttr(resourceName, "edge_location", acctest.Region()), + resource.TestCheckResourceAttr(resourceName, "options.0.protocol", "GRE"), acctest.CheckResourceAttrAccountID(resourceName, "owner_account_id"), resource.TestCheckResourceAttr(resourceName, "segment_name", "shared"), resource.TestCheckResourceAttrSet(resourceName, "state"), @@ -113,6 +115,42 @@ func TestAccNetworkManagerConnectAttachment_disappears(t *testing.T) { }) } +func TestAccNetworkManagerConnectAttachment_protocolNoEncap(t *testing.T) { + ctx := acctest.Context(t) + var v networkmanager.ConnectAttachment + resourceName := "aws_networkmanager_connect_attachment.test" + rName := sdkacctest.RandomWithPrefix(acctest.ResourcePrefix) + + resource.ParallelTest(t, resource.TestCase{ + PreCheck: func() { acctest.PreCheck(ctx, t) }, + ErrorCheck: acctest.ErrorCheck(t, networkmanager.EndpointsID), + ProtoV5ProviderFactories: acctest.ProtoV5ProviderFactories, + CheckDestroy: testAccCheckConnectAttachmentDestroy(ctx), + Steps: []resource.TestStep{ + { + Config: testAccConnectAttachmentConfig_protocolNoEncap(rName), + Check: resource.ComposeAggregateTestCheckFunc( + testAccCheckConnectAttachmentExists(ctx, resourceName, &v), + acctest.MatchResourceAttrGlobalARN(resourceName, "arn", "networkmanager", regexache.MustCompile(`attachment/.+`)), + resource.TestCheckResourceAttr(resourceName, "attachment_type", "CONNECT"), + resource.TestCheckResourceAttrSet(resourceName, "core_network_id"), + resource.TestCheckResourceAttr(resourceName, "edge_location", acctest.Region()), + resource.TestCheckResourceAttr(resourceName, "options.0.protocol", "NO_ENCAP"), + acctest.CheckResourceAttrAccountID(resourceName, "owner_account_id"), + resource.TestCheckResourceAttr(resourceName, "segment_name", "shared"), + resource.TestCheckResourceAttrSet(resourceName, "state"), + resource.TestCheckResourceAttr(resourceName, "tags.%", "1"), + ), + }, + { + ResourceName: resourceName, + ImportState: true, + ImportStateVerify: true, + }, + }, + }) +} + func TestAccNetworkManagerConnectAttachment_tags(t *testing.T) { ctx := acctest.Context(t) var v networkmanager.ConnectAttachment @@ -370,6 +408,44 @@ resource "aws_networkmanager_attachment_accepter" "test2" { `) } +func testAccConnectAttachmentConfig_protocolNoEncap(rName string) string { + return acctest.ConfigCompose(testAccConnectAttachmentConfig_base(rName), ` +resource "aws_networkmanager_vpc_attachment" "test" { + subnet_arns = aws_subnet.test[*].arn + core_network_id = aws_networkmanager_core_network_policy_attachment.test.core_network_id + vpc_arn = aws_vpc.test.arn + tags = { + segment = "shared" + } +} + +resource "aws_networkmanager_attachment_accepter" "test" { + attachment_id = aws_networkmanager_vpc_attachment.test.id + attachment_type = aws_networkmanager_vpc_attachment.test.attachment_type +} + +resource "aws_networkmanager_connect_attachment" "test" { + core_network_id = aws_networkmanager_core_network.test.id + transport_attachment_id = aws_networkmanager_vpc_attachment.test.id + edge_location = aws_networkmanager_vpc_attachment.test.edge_location + options { + protocol = "NO_ENCAP" + } + tags = { + segment = "shared" + } + depends_on = [ + "aws_networkmanager_attachment_accepter.test" + ] +} + +resource "aws_networkmanager_attachment_accepter" "test2" { + attachment_id = aws_networkmanager_connect_attachment.test.id + attachment_type = aws_networkmanager_connect_attachment.test.attachment_type +} +`) +} + func testAccConnectAttachmentConfig_tags1(rName, tagKey1, tagValue1 string) string { return acctest.ConfigCompose(testAccConnectAttachmentConfig_base(rName), fmt.Sprintf(` resource "aws_networkmanager_vpc_attachment" "test" { From 541ab2eba6d213113947f01e0ee0539357cb2d32 Mon Sep 17 00:00:00 2001 From: Dave DeRicco <30156588+ddericco@users.noreply.github.com> Date: Wed, 25 Oct 2023 11:23:55 -0400 Subject: [PATCH 2/9] Update docs --- .../docs/r/networkmanager_connect_attachment.html.markdown | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/website/docs/r/networkmanager_connect_attachment.html.markdown b/website/docs/r/networkmanager_connect_attachment.html.markdown index 61bfff429173..10beee0dfcd5 100644 --- a/website/docs/r/networkmanager_connect_attachment.html.markdown +++ b/website/docs/r/networkmanager_connect_attachment.html.markdown @@ -70,12 +70,16 @@ The following arguments are required: - `core_network_id` - (Required) The ID of a core network where you want to create the attachment. - `transport_attachment_id` - (Required) The ID of the attachment between the two connections. - `edge_location` - (Required) The Region where the edge is located. -- `options` - (Required) Options for creating an attachment. +- `options` - (Required) Options block. See [options](#options) for more information. The following arguments are optional: - `tags` - (Optional) Key-value tags for the attachment. If configured with a provider [`default_tags` configuration block](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#default_tags-configuration-block) present, tags with matching keys will overwrite those defined at the provider-level. +### options + +* `protocol` - (Required) The protocol used for the attachment connection. Possible values are `GRE` and `NO_ENCAP`. + ## Attribute Reference This resource exports the following attributes in addition to the arguments above: From af55fc65010cebadc9300d372edb8a27369a047e Mon Sep 17 00:00:00 2001 From: Dave DeRicco <30156588+ddericco@users.noreply.github.com> Date: Wed, 25 Oct 2023 11:32:19 -0400 Subject: [PATCH 3/9] Add changelog --- .changelog/34109.txt | 3 +++ 1 file changed, 3 insertions(+) create mode 100644 .changelog/34109.txt diff --git a/.changelog/34109.txt b/.changelog/34109.txt new file mode 100644 index 000000000000..508d5506842e --- /dev/null +++ b/.changelog/34109.txt @@ -0,0 +1,3 @@ +```release-note:enhancement +resource/aws_networkmanager_connect_attachment: Add support for tunnel-less connect `NO_ENCAP` in `protocol` attribute +``` \ No newline at end of file From 07850f07fef32061152bc1d34a75a82011ab7ef8 Mon Sep 17 00:00:00 2001 From: Dave DeRicco <30156588+ddericco@users.noreply.github.com> Date: Wed, 25 Oct 2023 20:19:41 -0400 Subject: [PATCH 4/9] [WIP] Add subnet_arn attribute to connect_peer --- .../service/networkmanager/connect_peer.go | 28 ++++- .../networkmanager/connect_peer_test.go | 102 +++++++++++++++--- 2 files changed, 109 insertions(+), 21 deletions(-) diff --git a/internal/service/networkmanager/connect_peer.go b/internal/service/networkmanager/connect_peer.go index 68e4a98240fb..ecb5b0810055 100644 --- a/internal/service/networkmanager/connect_peer.go +++ b/internal/service/networkmanager/connect_peer.go @@ -153,7 +153,7 @@ func ResourceConnectPeer() *schema.Resource { }, "inside_cidr_blocks": { Type: schema.TypeList, - Required: true, + Optional: true, ForceNew: true, MaxItems: 2, Elem: &schema.Schema{ @@ -170,6 +170,14 @@ func ResourceConnectPeer() *schema.Resource { validation.StringMatch(regexache.MustCompile(`[\s\S]*`), "Anything but whitespace"), ), }, + "subnet_arn": { + Type: schema.TypeString, + Optional: true, + ValidateFunc: validation.All( + validation.StringLenBetween(0, 500), + validation.StringMatch(regexache.MustCompile(`^arn:[^:]{1,63}:ec2:[^:]{0,63}:[^:]{0,63}:subnet\/subnet-[0-9a-f]{8,17}$|^$`), "Must be a valid subnet ARN"), + ), + }, "state": { Type: schema.TypeString, Computed: true, @@ -184,13 +192,13 @@ func resourceConnectPeerCreate(ctx context.Context, d *schema.ResourceData, meta conn := meta.(*conns.AWSClient).NetworkManagerConn(ctx) connectAttachmentID := d.Get("connect_attachment_id").(string) - insideCIDRBlocks := flex.ExpandStringList(d.Get("inside_cidr_blocks").([]interface{})) + // insideCIDRBlocks := flex.ExpandStringList(d.Get("inside_cidr_blocks").([]interface{})) peerAddress := d.Get("peer_address").(string) input := &networkmanager.CreateConnectPeerInput{ ConnectAttachmentId: aws.String(connectAttachmentID), - InsideCidrBlocks: insideCIDRBlocks, - PeerAddress: aws.String(peerAddress), - Tags: getTagsIn(ctx), + // InsideCidrBlocks: insideCIDRBlocks, + PeerAddress: aws.String(peerAddress), + Tags: getTagsIn(ctx), } if v, ok := d.GetOk("bgp_options"); ok && len(v.([]interface{})) > 0 { @@ -201,6 +209,15 @@ func resourceConnectPeerCreate(ctx context.Context, d *schema.ResourceData, meta input.CoreNetworkAddress = aws.String(v.(string)) } + if v, ok := d.GetOk("inside_cidr_blocks"); ok { + insideCIDRBlocks := flex.ExpandStringList(v.([]interface{})) + input.InsideCidrBlocks = insideCIDRBlocks + } + + if v, ok := d.GetOk("subnet_arn"); ok { + input.SubnetArn = aws.String(v.(string)) + } + outputRaw, err := tfresource.RetryWhen(ctx, d.Timeout(schema.TimeoutCreate), func() (interface{}, error) { return conn.CreateConnectPeerWithContext(ctx, input) @@ -277,6 +294,7 @@ func resourceConnectPeerRead(ctx context.Context, d *schema.ResourceData, meta i d.Set("connect_attachment_id", connectPeer.ConnectAttachmentId) d.Set("inside_cidr_blocks", connectPeer.Configuration.InsideCidrBlocks) d.Set("peer_address", connectPeer.Configuration.PeerAddress) + d.Set("subnet_arn", connectPeer.SubnetArn) d.Set("state", connectPeer.State) setTagsOut(ctx, connectPeer.Tags) diff --git a/internal/service/networkmanager/connect_peer_test.go b/internal/service/networkmanager/connect_peer_test.go index 4c7808b70e0b..104dbcfedbb2 100644 --- a/internal/service/networkmanager/connect_peer_test.go +++ b/internal/service/networkmanager/connect_peer_test.go @@ -26,6 +26,7 @@ func TestAccNetworkManagerConnectPeer_basic(t *testing.T) { rName := sdkacctest.RandomWithPrefix(acctest.ResourcePrefix) insideCidrBlocksv4 := "169.254.10.0/29" peerAddress := "1.1.1.1" + protocol := "GRE" asn := "65501" resource.ParallelTest(t, resource.TestCase{ @@ -35,7 +36,7 @@ func TestAccNetworkManagerConnectPeer_basic(t *testing.T) { CheckDestroy: testAccCheckConnectPeerDestroy(ctx), Steps: []resource.TestStep{ { - Config: testAccConnectPeerConfig_basic(rName, insideCidrBlocksv4, peerAddress, asn), + Config: testAccConnectPeerConfig_basic(rName, insideCidrBlocksv4, peerAddress, asn, protocol), Check: resource.ComposeAggregateTestCheckFunc( testAccCheckConnectPeerExists(ctx, resourceName, &v), acctest.MatchResourceAttrGlobalARN(resourceName, "arn", "networkmanager", regexache.MustCompile(`connect-peer/.+`)), @@ -70,6 +71,7 @@ func TestAccNetworkManagerConnectPeer_noDependsOn(t *testing.T) { rName := sdkacctest.RandomWithPrefix(acctest.ResourcePrefix) insideCidrBlocksv4 := "169.254.10.0/29" peerAddress := "1.1.1.1" + protocol := "GRE" asn := "65501" resource.ParallelTest(t, resource.TestCase{ @@ -79,7 +81,7 @@ func TestAccNetworkManagerConnectPeer_noDependsOn(t *testing.T) { CheckDestroy: testAccCheckConnectPeerDestroy(ctx), Steps: []resource.TestStep{ { - Config: testAccConnectPeerConfig_noDependsOn(rName, insideCidrBlocksv4, peerAddress, asn), + Config: testAccConnectPeerConfig_noDependsOn(rName, insideCidrBlocksv4, peerAddress, asn, protocol), Check: resource.ComposeAggregateTestCheckFunc( testAccCheckConnectPeerExists(ctx, resourceName, &v), acctest.MatchResourceAttrGlobalARN(resourceName, "arn", "networkmanager", regexache.MustCompile(`connect-peer/.+`)), @@ -107,6 +109,49 @@ func TestAccNetworkManagerConnectPeer_noDependsOn(t *testing.T) { }) } +func TestAccNetworkManagerConnectPeer_subnetArn(t *testing.T) { + ctx := acctest.Context(t) + var v networkmanager.ConnectPeer + resourceName := "aws_networkmanager_connect_peer.test" + subnetResourceName := "aws_subnet.test2" + rName := sdkacctest.RandomWithPrefix(acctest.ResourcePrefix) + peerAddress := "1.1.1.1" + protocol := "NO_ENCAP" + asn := "65501" + + resource.ParallelTest(t, resource.TestCase{ + PreCheck: func() { acctest.PreCheck(ctx, t) }, + ErrorCheck: acctest.ErrorCheck(t, networkmanager.EndpointsID), + ProtoV5ProviderFactories: acctest.ProtoV5ProviderFactories, + CheckDestroy: testAccCheckConnectPeerDestroy(ctx), + Steps: []resource.TestStep{ + { + Config: testAccConnectPeerConfig_subnetArn(rName, peerAddress, asn, protocol), + Check: resource.ComposeAggregateTestCheckFunc( + testAccCheckConnectPeerExists(ctx, resourceName, &v), + acctest.MatchResourceAttrGlobalARN(resourceName, "arn", "networkmanager", regexache.MustCompile(`connect-peer/.+`)), + resource.TestCheckResourceAttr(resourceName, "configuration.#", "1"), + resource.TestCheckResourceAttr(resourceName, "configuration.0.peer_address", peerAddress), + resource.TestCheckResourceAttr(resourceName, "configuration.0.protocol", "NO_ENCAP"), + resource.TestCheckResourceAttr(resourceName, "configuration.0.bgp_configurations.#", "1"), + resource.TestCheckResourceAttrSet(resourceName, "connect_attachment_id"), + resource.TestCheckResourceAttr(resourceName, "peer_address", peerAddress), + resource.TestCheckResourceAttr(resourceName, "edge_location", acctest.Region()), + resource.TestCheckResourceAttrSet(resourceName, "connect_attachment_id"), + resource.TestCheckResourceAttrPair(resourceName, "subnet_arn", subnetResourceName, "arn"), + resource.TestCheckResourceAttrSet(resourceName, "state"), + resource.TestCheckResourceAttr(resourceName, "tags.%", "1"), + ), + }, + { + ResourceName: resourceName, + ImportState: true, + ImportStateVerify: true, + }, + }, + }) +} + func TestAccNetworkManagerConnectPeer_tags(t *testing.T) { ctx := acctest.Context(t) var v networkmanager.ConnectPeer @@ -114,6 +159,7 @@ func TestAccNetworkManagerConnectPeer_tags(t *testing.T) { rName := sdkacctest.RandomWithPrefix(acctest.ResourcePrefix) insideCidrBlocksv4 := "169.254.10.0/29" peerAddress := "1.1.1.1" + protocol := "GRE" asn := "65501" resource.ParallelTest(t, resource.TestCase{ @@ -123,7 +169,7 @@ func TestAccNetworkManagerConnectPeer_tags(t *testing.T) { CheckDestroy: testAccCheckConnectPeerDestroy(ctx), Steps: []resource.TestStep{ { - Config: testAccConnectPeerConfig_tags1(rName, "Name", "test", insideCidrBlocksv4, peerAddress, asn), + Config: testAccConnectPeerConfig_tags1(rName, "Name", "test", insideCidrBlocksv4, peerAddress, asn, protocol), Check: resource.ComposeTestCheckFunc( testAccCheckConnectPeerExists(ctx, resourceName, &v), resource.TestCheckResourceAttr(resourceName, "tags.%", "1"), @@ -131,7 +177,7 @@ func TestAccNetworkManagerConnectPeer_tags(t *testing.T) { ), }, { - Config: testAccConnectPeerConfig_tags2(rName, "Name", "test", "env", "test", insideCidrBlocksv4, peerAddress, asn), + Config: testAccConnectPeerConfig_tags2(rName, "Name", "test", "env", "test", insideCidrBlocksv4, peerAddress, asn, protocol), Check: resource.ComposeTestCheckFunc( testAccCheckConnectPeerExists(ctx, resourceName, &v), resource.TestCheckResourceAttr(resourceName, "tags.%", "2"), @@ -140,7 +186,7 @@ func TestAccNetworkManagerConnectPeer_tags(t *testing.T) { ), }, { - Config: testAccConnectPeerConfig_tags1(rName, "Name", "test", insideCidrBlocksv4, peerAddress, asn), + Config: testAccConnectPeerConfig_tags1(rName, "Name", "test", insideCidrBlocksv4, peerAddress, asn, protocol), Check: resource.ComposeTestCheckFunc( testAccCheckConnectPeerExists(ctx, resourceName, &v), resource.TestCheckResourceAttr(resourceName, "tags.%", "1"), @@ -206,7 +252,7 @@ func testAccCheckConnectPeerDestroy(ctx context.Context) resource.TestCheckFunc } } -func testAccConnectPeerConfig_base(rName string) string { +func testAccConnectPeerConfig_base(rName string, protocol string) string { return acctest.ConfigCompose(acctest.ConfigAvailableAZsNoOptIn(), fmt.Sprintf(` data "aws_region" "current" {} @@ -306,7 +352,7 @@ resource "aws_networkmanager_connect_attachment" "test" { transport_attachment_id = aws_networkmanager_vpc_attachment.test.id edge_location = aws_networkmanager_vpc_attachment.test.edge_location options { - protocol = "GRE" + protocol = %[2]q } tags = { segment = "shared" @@ -320,11 +366,11 @@ resource "aws_networkmanager_attachment_accepter" "test2" { attachment_id = aws_networkmanager_connect_attachment.test.id attachment_type = aws_networkmanager_connect_attachment.test.attachment_type } -`, rName)) +`, rName, protocol)) } -func testAccConnectPeerConfig_basic(rName string, insideCidrBlocks string, peerAddress string, asn string) string { - return acctest.ConfigCompose(testAccConnectPeerConfig_base(rName), fmt.Sprintf(` +func testAccConnectPeerConfig_basic(rName string, insideCidrBlocks string, peerAddress string, asn string, protocol string) string { + return acctest.ConfigCompose(testAccConnectPeerConfig_base(rName, protocol), fmt.Sprintf(` resource "aws_networkmanager_connect_peer" "test" { connect_attachment_id = aws_networkmanager_connect_attachment.test.id peer_address = %[3]q @@ -344,8 +390,8 @@ resource "aws_networkmanager_connect_peer" "test" { `, rName, insideCidrBlocks, peerAddress, asn)) } -func testAccConnectPeerConfig_noDependsOn(rName string, insideCidrBlocks string, peerAddress string, asn string) string { - return acctest.ConfigCompose(testAccConnectPeerConfig_base(rName), fmt.Sprintf(` +func testAccConnectPeerConfig_noDependsOn(rName string, insideCidrBlocks string, peerAddress string, asn string, protocol string) string { + return acctest.ConfigCompose(testAccConnectPeerConfig_base(rName, protocol), fmt.Sprintf(` resource "aws_networkmanager_connect_peer" "test" { connect_attachment_id = aws_networkmanager_connect_attachment.test.id peer_address = %[3]q @@ -362,8 +408,32 @@ resource "aws_networkmanager_connect_peer" "test" { `, rName, insideCidrBlocks, peerAddress, asn)) } -func testAccConnectPeerConfig_tags1(rName, tagKey1, tagValue1 string, insideCidrBlocks string, peerAddress string, asn string) string { - return acctest.ConfigCompose(testAccConnectPeerConfig_base(rName), fmt.Sprintf(` +func testAccConnectPeerConfig_subnetArn(rName string, peerAddress string, asn string, protocol string) string { + return acctest.ConfigCompose(testAccConnectPeerConfig_base(rName, protocol), fmt.Sprintf(` +resource "aws_networkmanager_connect_peer" "test" { + connect_attachment_id = aws_networkmanager_connect_attachment.test.id + peer_address = %[2]q + bgp_options { + peer_asn = %[3]q + } + subnet_arn = aws_subnet.test2.arn + tags = { + Name = %[1]q + } + depends_on = [ + "aws_networkmanager_attachment_accepter.test" + ] +} + +resource "aws_subnet" "test2" { + vpc_id = aws_vpc.test.id + cidr_block = cidrsubnet(aws_vpc.test.cidr_block, 8, 2) +} +`, rName, peerAddress, asn)) +} + +func testAccConnectPeerConfig_tags1(rName, tagKey1, tagValue1 string, insideCidrBlocks string, peerAddress string, asn string, protocol string) string { + return acctest.ConfigCompose(testAccConnectPeerConfig_base(rName, protocol), fmt.Sprintf(` resource "aws_networkmanager_connect_peer" "test" { connect_attachment_id = aws_networkmanager_connect_attachment.test.id peer_address = %[4]q @@ -380,8 +450,8 @@ resource "aws_networkmanager_connect_peer" "test" { `, tagKey1, tagValue1, insideCidrBlocks, peerAddress, asn)) } -func testAccConnectPeerConfig_tags2(rName, tagKey1, tagValue1, tagKey2, tagValue2 string, insideCidrBlocks string, peerAddress string, asn string) string { - return acctest.ConfigCompose(testAccConnectPeerConfig_base(rName), fmt.Sprintf(` +func testAccConnectPeerConfig_tags2(rName, tagKey1, tagValue1, tagKey2, tagValue2 string, insideCidrBlocks string, peerAddress string, asn string, protocol string) string { + return acctest.ConfigCompose(testAccConnectPeerConfig_base(rName, protocol), fmt.Sprintf(` resource "aws_networkmanager_connect_peer" "test" { connect_attachment_id = aws_networkmanager_connect_attachment.test.id peer_address = %[6]q From 93e0eaab1aed93217688df99b30dad30456a0f6e Mon Sep 17 00:00:00 2001 From: Dave DeRicco <30156588+ddericco@users.noreply.github.com> Date: Thu, 26 Oct 2023 11:54:24 -0400 Subject: [PATCH 5/9] Update connect_peer docs --- .../networkmanager_connect_peer.html.markdown | 31 ++++++++++++++++++- 1 file changed, 30 insertions(+), 1 deletion(-) diff --git a/website/docs/r/networkmanager_connect_peer.html.markdown b/website/docs/r/networkmanager_connect_peer.html.markdown index 6930fb41df46..91a942a9ff62 100644 --- a/website/docs/r/networkmanager_connect_peer.html.markdown +++ b/website/docs/r/networkmanager_connect_peer.html.markdown @@ -84,18 +84,47 @@ resource "aws_networkmanager_connect_peer" "example" { } ``` +### Usage with a Tunnel-less Connect attachment + +```terraform +resource "aws_networkmanager_vpc_attachment" "example" { + subnet_arns = aws_subnet.example[*].arn + core_network_id = awscc_networkmanager_core_network.example.id + vpc_arn = aws_vpc.example.arn +} + +resource "aws_networkmanager_connect_attachment" "example" { + core_network_id = awscc_networkmanager_core_network.example.id + transport_attachment_id = aws_networkmanager_vpc_attachment.example.id + edge_location = aws_networkmanager_vpc_attachment.example.edge_location + options { + protocol = "NO_ENCAP" + } +} + +resource "aws_networkmanager_connect_peer" "example" { + connect_attachment_id = aws_networkmanager_connect_attachment.example.id + peer_address = "127.0.0.1" + bgp_options { + peer_asn = 65000 + } + subnet_arn = aws_subnet.test2.arn +} +``` + ## Argument Reference The following arguments are required: - `connect_attachment_id` - (Required) The ID of the connection attachment. -- `inside_cidr_blocks` - (Required) The inside IP addresses used for BGP peering. - `peer_address` - (Required) The Connect peer address. The following arguments are optional: - `bgp_options` (Optional) The Connect peer BGP options. - `core_network_address` (Optional) A Connect peer core network address. +- `inside_cidr_blocks` - (Optional) The inside IP addresses used for BGP peering. Required when the Connect attachment protocol is `GRE`. See [`aws_networkmanager_connect_attachment`](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/networkmanager_connect_attachment) for details. +- `subnet_arn` - (Optional) The subnet ARN for the Connect peer. Required when the Connect attachment protocol is `NO_ENCAP`. See [`aws_networkmanager_connect_attachment`](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/networkmanager_connect_attachment) for details. - `tags` - (Optional) Key-value tags for the attachment. If configured with a provider [`default_tags` configuration block](https://registry.terraform.io/providers/hashicorp/aws/latest/docs#default_tags-configuration-block) present, tags with matching keys will overwrite those defined at the provider-level. ## Attribute Reference From e57c2a75942d0a1ae5e39f7460b180d366ac3dcf Mon Sep 17 00:00:00 2001 From: Dave DeRicco <30156588+ddericco@users.noreply.github.com> Date: Thu, 26 Oct 2023 11:59:54 -0400 Subject: [PATCH 6/9] Update changelog --- .changelog/34109.txt | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/.changelog/34109.txt b/.changelog/34109.txt index 508d5506842e..35dfb12ec261 100644 --- a/.changelog/34109.txt +++ b/.changelog/34109.txt @@ -1,3 +1,11 @@ ```release-note:enhancement resource/aws_networkmanager_connect_attachment: Add support for tunnel-less connect `NO_ENCAP` in `protocol` attribute +``` + +```release-note:enhancement +resource/aws_networkmanager_connect_peer: Add `subnet_arn` attribute to support tunnel-less Connect attachments +``` + +```release-note:enhancement +resource/aws_networkmanager_connect_peer: Mark `inside_cidr_blocks` argument as optional to support tunnel-less Connect attachments ``` \ No newline at end of file From a3cd81ef9b5ffc8629ef97b228181b5599adc049 Mon Sep 17 00:00:00 2001 From: Dave DeRicco <30156588+ddericco@users.noreply.github.com> Date: Thu, 26 Oct 2023 12:27:42 -0400 Subject: [PATCH 7/9] Fix semgrep issues --- internal/service/networkmanager/connect_peer_test.go | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/internal/service/networkmanager/connect_peer_test.go b/internal/service/networkmanager/connect_peer_test.go index 104dbcfedbb2..160be16297e3 100644 --- a/internal/service/networkmanager/connect_peer_test.go +++ b/internal/service/networkmanager/connect_peer_test.go @@ -109,7 +109,7 @@ func TestAccNetworkManagerConnectPeer_noDependsOn(t *testing.T) { }) } -func TestAccNetworkManagerConnectPeer_subnetArn(t *testing.T) { +func TestAccNetworkManagerConnectPeer_subnetARN(t *testing.T) { ctx := acctest.Context(t) var v networkmanager.ConnectPeer resourceName := "aws_networkmanager_connect_peer.test" @@ -126,7 +126,7 @@ func TestAccNetworkManagerConnectPeer_subnetArn(t *testing.T) { CheckDestroy: testAccCheckConnectPeerDestroy(ctx), Steps: []resource.TestStep{ { - Config: testAccConnectPeerConfig_subnetArn(rName, peerAddress, asn, protocol), + Config: testAccConnectPeerConfig_subnetARN(rName, peerAddress, asn, protocol), Check: resource.ComposeAggregateTestCheckFunc( testAccCheckConnectPeerExists(ctx, resourceName, &v), acctest.MatchResourceAttrGlobalARN(resourceName, "arn", "networkmanager", regexache.MustCompile(`connect-peer/.+`)), @@ -408,7 +408,7 @@ resource "aws_networkmanager_connect_peer" "test" { `, rName, insideCidrBlocks, peerAddress, asn)) } -func testAccConnectPeerConfig_subnetArn(rName string, peerAddress string, asn string, protocol string) string { +func testAccConnectPeerConfig_subnetARN(rName string, peerAddress string, asn string, protocol string) string { return acctest.ConfigCompose(testAccConnectPeerConfig_base(rName, protocol), fmt.Sprintf(` resource "aws_networkmanager_connect_peer" "test" { connect_attachment_id = aws_networkmanager_connect_attachment.test.id From d7c0fbf88c7b80c22b26249ceca169558f97e35b Mon Sep 17 00:00:00 2001 From: Kit Ewbank Date: Fri, 27 Oct 2023 10:29:05 -0400 Subject: [PATCH 8/9] r/aws_networkmanager_connect_attachment: Use 'networkmanager.TunnelProtocol_Values()' in validation. --- internal/service/networkmanager/connect_attachment.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/internal/service/networkmanager/connect_attachment.go b/internal/service/networkmanager/connect_attachment.go index 665572814b55..9fdd16a05976 100644 --- a/internal/service/networkmanager/connect_attachment.go +++ b/internal/service/networkmanager/connect_attachment.go @@ -93,7 +93,7 @@ func ResourceConnectAttachment() *schema.Resource { "protocol": { Type: schema.TypeString, Optional: true, - ValidateFunc: validation.StringInSlice([]string{"GRE", "NO_ENCAP"}, false), + ValidateFunc: validation.StringInSlice(networkmanager.TunnelProtocol_Values(), false), }, }, }, From c720787d4d4bc0ba8d71fd1ce95ff9ddff79c12c Mon Sep 17 00:00:00 2001 From: Kit Ewbank Date: Fri, 27 Oct 2023 10:34:56 -0400 Subject: [PATCH 9/9] Tweak CHANGELOG entries. --- .changelog/34109.txt | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/.changelog/34109.txt b/.changelog/34109.txt index 35dfb12ec261..30a4fe1af047 100644 --- a/.changelog/34109.txt +++ b/.changelog/34109.txt @@ -1,11 +1,11 @@ ```release-note:enhancement -resource/aws_networkmanager_connect_attachment: Add support for tunnel-less connect `NO_ENCAP` in `protocol` attribute +resource/aws_networkmanager_connect_attachment: Add `NO_ENCAP` as a valid `options.protocol` value ``` ```release-note:enhancement -resource/aws_networkmanager_connect_peer: Add `subnet_arn` attribute to support tunnel-less Connect attachments +resource/aws_networkmanager_connect_peer: Add `subnet_arn` argument to support [Tunnel-less Connect attachments](https://docs.aws.amazon.com/network-manager/latest/cloudwan/cloudwan-connect-attachment.html#cloudwan-connect-tlc) ``` ```release-note:enhancement -resource/aws_networkmanager_connect_peer: Mark `inside_cidr_blocks` argument as optional to support tunnel-less Connect attachments +resource/aws_networkmanager_connect_peer: `inside_cidr_blocks` is Optional ``` \ No newline at end of file