From 9e1656c23fd4ef4b45ef791982ed66a39d995d44 Mon Sep 17 00:00:00 2001 From: Radek Simko Date: Sat, 3 Sep 2016 14:16:33 +0100 Subject: [PATCH] provider/aws: Add aws_elasticsearch_domain_policy --- builtin/providers/aws/provider.go | 1 + .../aws/resource_aws_elasticsearch_domain.go | 1 + ...esource_aws_elasticsearch_domain_policy.go | 127 ++++++++++++++++++ ...ce_aws_elasticsearch_domain_policy_test.go | 62 +++++++++ .../elasticsearch_domain_policy.html.markdown | 47 +++++++ website/source/layouts/aws.erb | 4 + 6 files changed, 242 insertions(+) create mode 100644 builtin/providers/aws/resource_aws_elasticsearch_domain_policy.go create mode 100644 builtin/providers/aws/resource_aws_elasticsearch_domain_policy_test.go create mode 100644 website/source/docs/providers/aws/r/elasticsearch_domain_policy.html.markdown diff --git a/builtin/providers/aws/provider.go b/builtin/providers/aws/provider.go index 655c88fc457f..4185d2ae09cc 100644 --- a/builtin/providers/aws/provider.go +++ b/builtin/providers/aws/provider.go @@ -228,6 +228,7 @@ func Provider() terraform.ResourceProvider { "aws_elastic_beanstalk_configuration_template": resourceAwsElasticBeanstalkConfigurationTemplate(), "aws_elastic_beanstalk_environment": resourceAwsElasticBeanstalkEnvironment(), "aws_elasticsearch_domain": resourceAwsElasticSearchDomain(), + "aws_elasticsearch_domain_policy": resourceAwsElasticSearchDomainPolicy(), "aws_elastictranscoder_pipeline": resourceAwsElasticTranscoderPipeline(), "aws_elastictranscoder_preset": resourceAwsElasticTranscoderPreset(), "aws_elb": resourceAwsElb(), diff --git a/builtin/providers/aws/resource_aws_elasticsearch_domain.go b/builtin/providers/aws/resource_aws_elasticsearch_domain.go index 9b9adfaa8bc7..294716b41937 100644 --- a/builtin/providers/aws/resource_aws_elasticsearch_domain.go +++ b/builtin/providers/aws/resource_aws_elasticsearch_domain.go @@ -24,6 +24,7 @@ func resourceAwsElasticSearchDomain() *schema.Resource { "access_policies": &schema.Schema{ Type: schema.TypeString, StateFunc: normalizeJson, + Computed: true, Optional: true, }, "advanced_options": &schema.Schema{ diff --git a/builtin/providers/aws/resource_aws_elasticsearch_domain_policy.go b/builtin/providers/aws/resource_aws_elasticsearch_domain_policy.go new file mode 100644 index 000000000000..dfb22c64d12f --- /dev/null +++ b/builtin/providers/aws/resource_aws_elasticsearch_domain_policy.go @@ -0,0 +1,127 @@ +package aws + +import ( + "fmt" + "log" + "time" + + "github.com/aws/aws-sdk-go/aws" + "github.com/aws/aws-sdk-go/aws/awserr" + elasticsearch "github.com/aws/aws-sdk-go/service/elasticsearchservice" + "github.com/hashicorp/terraform/helper/resource" + "github.com/hashicorp/terraform/helper/schema" +) + +func resourceAwsElasticSearchDomainPolicy() *schema.Resource { + return &schema.Resource{ + Create: resourceAwsElasticSearchDomainPolicyUpsert, + Read: resourceAwsElasticSearchDomainPolicyRead, + Update: resourceAwsElasticSearchDomainPolicyUpsert, + Delete: resourceAwsElasticSearchDomainPolicyDelete, + + Schema: map[string]*schema.Schema{ + "domain_name": { + Type: schema.TypeString, + Required: true, + }, + "access_policies": { + Type: schema.TypeString, + Required: true, + DiffSuppressFunc: suppressEquivalentAwsPolicyDiffs, + }, + }, + } +} + +func resourceAwsElasticSearchDomainPolicyRead(d *schema.ResourceData, meta interface{}) error { + conn := meta.(*AWSClient).esconn + name := d.Get("domain_name").(string) + out, err := conn.DescribeElasticsearchDomain(&elasticsearch.DescribeElasticsearchDomainInput{ + DomainName: aws.String(name), + }) + if err != nil { + if awsErr, ok := err.(awserr.Error); ok && awsErr.Code() == "ResourceNotFound" { + log.Printf("[WARN] ElasticSearch Domain %q not found, removing", name) + d.SetId("") + return nil + } + return err + } + + log.Printf("[DEBUG] Received ElasticSearch domain: %s", out) + + ds := out.DomainStatus + d.Set("access_policies", ds.AccessPolicies) + + return nil +} + +func resourceAwsElasticSearchDomainPolicyUpsert(d *schema.ResourceData, meta interface{}) error { + conn := meta.(*AWSClient).esconn + domainName := d.Get("domain_name").(string) + _, err := conn.UpdateElasticsearchDomainConfig(&elasticsearch.UpdateElasticsearchDomainConfigInput{ + DomainName: aws.String(domainName), + AccessPolicies: aws.String(d.Get("access_policies").(string)), + }) + if err != nil { + return err + } + + d.SetId("esd-policy-" + domainName) + + err = resource.Retry(50*time.Minute, func() *resource.RetryError { + out, err := conn.DescribeElasticsearchDomain(&elasticsearch.DescribeElasticsearchDomainInput{ + DomainName: aws.String(d.Get("domain_name").(string)), + }) + if err != nil { + return resource.NonRetryableError(err) + } + + if *out.DomainStatus.Processing == false { + return nil + } + + return resource.RetryableError( + fmt.Errorf("%q: Timeout while waiting for changes to be processed", d.Id())) + }) + if err != nil { + return err + } + + return resourceAwsElasticSearchDomainPolicyRead(d, meta) +} + +func resourceAwsElasticSearchDomainPolicyDelete(d *schema.ResourceData, meta interface{}) error { + conn := meta.(*AWSClient).esconn + + _, err := conn.UpdateElasticsearchDomainConfig(&elasticsearch.UpdateElasticsearchDomainConfigInput{ + DomainName: aws.String(d.Get("domain_name").(string)), + AccessPolicies: aws.String(""), + }) + if err != nil { + return err + } + + log.Printf("[DEBUG] Waiting for ElasticSearch domain policy %q to be deleted", d.Get("domain_name").(string)) + err = resource.Retry(60*time.Minute, func() *resource.RetryError { + out, err := conn.DescribeElasticsearchDomain(&elasticsearch.DescribeElasticsearchDomainInput{ + DomainName: aws.String(d.Get("domain_name").(string)), + }) + if err != nil { + return resource.NonRetryableError(err) + } + + if *out.DomainStatus.Processing == false { + return nil + } + + return resource.RetryableError( + fmt.Errorf("%q: Timeout while waiting for policy to be deleted", d.Id())) + }) + if err != nil { + return err + } + + d.SetId("") + return nil +} diff --git a/builtin/providers/aws/resource_aws_elasticsearch_domain_policy_test.go b/builtin/providers/aws/resource_aws_elasticsearch_domain_policy_test.go new file mode 100644 index 000000000000..c27aad041931 --- /dev/null +++ b/builtin/providers/aws/resource_aws_elasticsearch_domain_policy_test.go @@ -0,0 +1,62 @@ +package aws + +import ( + "fmt" + "regexp" + "testing" + + elasticsearch "github.com/aws/aws-sdk-go/service/elasticsearchservice" + "github.com/hashicorp/terraform/helper/acctest" + "github.com/hashicorp/terraform/helper/resource" +) + +func TestAccAWSElasticSearchDomainPolicy_basic(t *testing.T) { + var domain elasticsearch.ElasticsearchDomainStatus + ri := acctest.RandInt() + + resource.Test(t, resource.TestCase{ + PreCheck: func() { testAccPreCheck(t) }, + Providers: testAccProviders, + CheckDestroy: testAccCheckESDomainDestroy, + Steps: []resource.TestStep{ + resource.TestStep{ + Config: testAccESDomainPolicyConfig(ri), + Check: resource.ComposeTestCheckFunc( + testAccCheckESDomainExists("aws_elasticsearch_domain.example", &domain), + resource.TestCheckResourceAttr("aws_elasticsearch_domain.example", "elasticsearch_version", "2.3"), + resource.TestMatchResourceAttr("aws_elasticsearch_domain_policy.main", "access_policies", + regexp.MustCompile("^{\"Statement\":.+")), + ), + }, + }, + }) +} + +func testAccESDomainPolicyConfig(randInt int) string { + return fmt.Sprintf(` +resource "aws_elasticsearch_domain" "example" { + domain_name = "tf-test-%d" + elasticsearch_version = "2.3" +} + +resource "aws_elasticsearch_domain_policy" "main" { + domain_name = "${aws_elasticsearch_domain.example.domain_name}" + access_policies = <aws_elasticsearch_domain + > + aws_elasticsearch_domain_policy + +