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

r/ecr_replication_configuration - new resource #16853

Merged
merged 15 commits into from
Apr 5, 2021
3 changes: 3 additions & 0 deletions .changelog/16853.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
```release-note:new-resource
aws_ecr_replication_configuration
```
1 change: 1 addition & 0 deletions aws/provider.go
Original file line number Diff line number Diff line change
Expand Up @@ -667,6 +667,7 @@ func Provider() *schema.Provider {
"aws_ec2_transit_gateway_vpc_attachment_accepter": resourceAwsEc2TransitGatewayVpcAttachmentAccepter(),
"aws_ecr_lifecycle_policy": resourceAwsEcrLifecyclePolicy(),
"aws_ecrpublic_repository": resourceAwsEcrPublicRepository(),
"aws_ecr_replication_configuration": resourceAwsEcrReplicationConfiguration(),
"aws_ecr_repository": resourceAwsEcrRepository(),
"aws_ecr_repository_policy": resourceAwsEcrRepositoryPolicy(),
"aws_ecs_capacity_provider": resourceAwsEcsCapacityProvider(),
Expand Down
200 changes: 200 additions & 0 deletions aws/resource_aws_ecr_replication_configuration.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,200 @@
package aws

import (
"fmt"
"log"

"github.com/aws/aws-sdk-go/aws"
"github.com/aws/aws-sdk-go/service/ecr"
"github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema"
)

func resourceAwsEcrReplicationConfiguration() *schema.Resource {
return &schema.Resource{
Create: resourceAwsEcrReplicationConfigurationPut,
Read: resourceAwsEcrReplicationConfigurationRead,
Update: resourceAwsEcrReplicationConfigurationPut,
Delete: schema.Noop,
Importer: &schema.ResourceImporter{
State: schema.ImportStatePassthrough,
},

Schema: map[string]*schema.Schema{
"registry_id": {
Type: schema.TypeString,
Computed: true,
},
"replication_configuration": {
Type: schema.TypeList,
Optional: true,
MaxItems: 1,
Elem: &schema.Resource{
Schema: map[string]*schema.Schema{
"rule": {
Type: schema.TypeList,
Required: true,
MaxItems: 1,
Elem: &schema.Resource{
Schema: map[string]*schema.Schema{
"destination": {
Type: schema.TypeList,
Required: true,
Elem: &schema.Resource{
Schema: map[string]*schema.Schema{
"region": {
Type: schema.TypeString,
Required: true,
},
"registry_id": {
Type: schema.TypeString,
Required: true,
ValidateFunc: validateAwsAccountId,
},
},
},
},
},
},
},
},
},
},
},
}
}

func resourceAwsEcrReplicationConfigurationPut(d *schema.ResourceData, meta interface{}) error {
conn := meta.(*AWSClient).ecrconn

input := ecr.PutReplicationConfigurationInput{
ReplicationConfiguration: expandEcrReplicationConfigurationReplicationConfiguration(d.Get("replication_configuration").([]interface{})),
}

_, err := conn.PutReplicationConfiguration(&input)
if err != nil {
return fmt.Errorf("error creating ECR Replication Configuration: %w", err)
}

d.SetId(meta.(*AWSClient).accountid)

return resourceAwsEcrReplicationConfigurationRead(d, meta)
}

func resourceAwsEcrReplicationConfigurationRead(d *schema.ResourceData, meta interface{}) error {
conn := meta.(*AWSClient).ecrconn

log.Printf("[DEBUG] Reading ECR Replication Configuration %s", d.Id())
out, err := conn.DescribeRegistry(&ecr.DescribeRegistryInput{})
if err != nil {
return fmt.Errorf("error reading ECR Replication Configuration: %w", err)
}

d.Set("registry_id", out.RegistryId)

if err := d.Set("replication_configuration", flattenEcrReplicationConfigurationReplicationConfiguration(out.ReplicationConfiguration)); err != nil {
return fmt.Errorf("error setting replication_configuration for ECR Replication Configuration: %w", err)
}

return nil
}

func expandEcrReplicationConfigurationReplicationConfiguration(data []interface{}) *ecr.ReplicationConfiguration {
if len(data) == 0 || data[0] == nil {
return nil
}

ec := data[0].(map[string]interface{})
config := &ecr.ReplicationConfiguration{
Rules: expandEcrReplicationConfigurationReplicationConfigurationRules(ec["rule"].([]interface{})),
}
return config
}

func flattenEcrReplicationConfigurationReplicationConfiguration(ec *ecr.ReplicationConfiguration) []map[string]interface{} {
if ec == nil {
return nil
}

config := map[string]interface{}{
"rule": flattenEcrReplicationConfigurationReplicationConfigurationRules(ec.Rules),
}

return []map[string]interface{}{
config,
}
}

func expandEcrReplicationConfigurationReplicationConfigurationRules(data []interface{}) []*ecr.ReplicationRule {
if len(data) == 0 || data[0] == nil {
return nil
}

var rules []*ecr.ReplicationRule

for _, rule := range data {
ec := rule.(map[string]interface{})
config := &ecr.ReplicationRule{
Destinations: expandEcrReplicationConfigurationReplicationConfigurationRulesDestinations(ec["destination"].([]interface{})),
}

rules = append(rules, config)

}
return rules
}

func flattenEcrReplicationConfigurationReplicationConfigurationRules(ec []*ecr.ReplicationRule) []interface{} {
if len(ec) == 0 {
return nil
}

var tfList []interface{}

for _, apiObject := range ec {
tfMap := map[string]interface{}{
"destination": flattenEcrReplicationConfigurationReplicationConfigurationRulesDestinations(apiObject.Destinations),
}

tfList = append(tfList, tfMap)
}

return tfList
}

func expandEcrReplicationConfigurationReplicationConfigurationRulesDestinations(data []interface{}) []*ecr.ReplicationDestination {
if len(data) == 0 || data[0] == nil {
return nil
}

var dests []*ecr.ReplicationDestination

for _, dest := range data {
ec := dest.(map[string]interface{})
config := &ecr.ReplicationDestination{
Region: aws.String(ec["region"].(string)),
RegistryId: aws.String(ec["registry_id"].(string)),
}

dests = append(dests, config)
}
return dests
}

func flattenEcrReplicationConfigurationReplicationConfigurationRulesDestinations(ec []*ecr.ReplicationDestination) []interface{} {
if len(ec) == 0 {
return nil
}

var tfList []interface{}

for _, apiObject := range ec {
tfMap := map[string]interface{}{
"region": aws.StringValue(apiObject.Region),
"registry_id": aws.StringValue(apiObject.RegistryId),
}

tfList = append(tfList, tfMap)
}

return tfList
}
68 changes: 68 additions & 0 deletions aws/resource_aws_ecr_replication_configuration_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
package aws

import (
"fmt"
"testing"

"github.com/aws/aws-sdk-go/service/ecr"
"github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource"
"github.com/hashicorp/terraform-plugin-sdk/v2/terraform"
)

func TestAccAWSEcrReplicationConfiguration_basic(t *testing.T) {
resourceName := "aws_ecr_replication_configuration.test"

resource.ParallelTest(t, resource.TestCase{
PreCheck: func() { testAccPreCheck(t) },
ErrorCheck: testAccErrorCheck(t, ecr.EndpointsID),
Providers: testAccProviders,
CheckDestroy: nil,
Steps: []resource.TestStep{
{
Config: testAccAWSEcrReplicationConfiguration(testAccGetAlternateRegion()),
Check: resource.ComposeTestCheckFunc(
testAccCheckAWSEcrReplicationConfigurationExists(resourceName),
testAccCheckResourceAttrAccountID(resourceName, "registry_id"),
resource.TestCheckResourceAttr(resourceName, "replication_configuration.#", "1"),
resource.TestCheckResourceAttr(resourceName, "replication_configuration.0.rule.#", "1"),
resource.TestCheckResourceAttr(resourceName, "replication_configuration.0.rule.0.destination.#", "1"),
resource.TestCheckResourceAttr(resourceName, "replication_configuration.0.rule.0.destination.0.region", testAccGetAlternateRegion()),
testAccCheckResourceAttrAccountID(resourceName, "replication_configuration.0.rule.0.destination.0.registry_id"),
),
DrFaust92 marked this conversation as resolved.
Show resolved Hide resolved
},
{
ResourceName: resourceName,
ImportState: true,
ImportStateVerify: true,
},
},
})
}

func testAccCheckAWSEcrReplicationConfigurationExists(name string) resource.TestCheckFunc {
return func(s *terraform.State) error {
_, ok := s.RootModule().Resources[name]
if !ok {
return fmt.Errorf("Not found: %s", name)
}

return nil
}
}

func testAccAWSEcrReplicationConfiguration(region string) string {
return fmt.Sprintf(`
data "aws_caller_identity" "current" {}

resource "aws_ecr_replication_configuration" "test" {
replication_configuration {
rule {
destination {
region = %[1]q
registry_id = data.aws_caller_identity.current.account_id
}
}
}
}
`, region)
}
63 changes: 63 additions & 0 deletions website/docs/r/ecr_replication_configuration.html.markdown
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
---
subcategory: "ECR"
layout: "aws"
page_title: "AWS: aws_ecr_replication_configuration"
description: |-
Provides an Elastic Container Registry Replication Configuration.
---

# Resource: aws_ecr_replication_configuration

Provides an Elastic Container Registry Replication Configuration.

## Example Usage

```terraform
data "aws_caller_identity" "current" {}

data "aws_regions" "example" {}

resource "aws_ecr_replication_configuration" "example" {
replication_configuration {
rule {
destination {
region = data.aws_regions.example.names[0]
registry_id = data.aws_caller_identity.current.account_id
}
}
}
}
```

## Argument Reference

The following arguments are supported:

* `replication_configuration` - (Required) Replication configuration for a registry. See [Replication Configuration](#encryption-configuration).

### Replication Configuration

* `rule` - (Required) The replication rules for a replication configuration. See [Rule](#rule).

### Rule

* `destination` - (Required) the details of a replication destination. See [Destination](#destination).

### Destination

* `region` - (Required) A Region to replicate to.
* `registry_id` - (Required) The account ID of the destination registry to replicate to.

## Attributes Reference

In addition to all arguments above, the following attributes are exported:

* `registry_id` - The registry ID where the replication configuration was created.

## Import

ECR Replication Configuration can be imported using the `registry_id`, e.g.

```
$ terraform import aws_ecr_replication_configuration.service 012345678912
```