diff --git a/aws/resource_aws_cloudwatch_event_target.go b/aws/resource_aws_cloudwatch_event_target.go index 28e6ff5199c..efc714509f6 100644 --- a/aws/resource_aws_cloudwatch_event_target.go +++ b/aws/resource_aws_cloudwatch_event_target.go @@ -248,6 +248,41 @@ func resourceAwsCloudWatchEventTarget() *schema.Resource { }, }, }, + + "dead_letter_config": { + Type: schema.TypeList, + Optional: true, + MaxItems: 1, + Elem: &schema.Resource{ + Schema: map[string]*schema.Schema{ + "arn": { + Type: schema.TypeString, + Optional: true, + }, + }, + }, + }, + "retry_policy": { + Type: schema.TypeList, + Optional: true, + MaxItems: 1, + Elem: &schema.Resource{ + Schema: map[string]*schema.Schema{ + "maximum_retry_attempts": { + Type: schema.TypeInt, + Optional: true, + ValidateFunc: validation.IntBetween(0, 185), + Default: 185, + }, + "maximum_event_age_in_seconds": { + Type: schema.TypeInt, + Optional: true, + ValidateFunc: validation.IntBetween(60, 86400), + Default: 86400, + }, + }, + }, + }, }, } } @@ -350,6 +385,18 @@ func resourceAwsCloudWatchEventTargetRead(d *schema.ResourceData, meta interface } } + if t.RetryPolicy != nil { + if err := d.Set("retry_policy", flattenAwsCloudWatchEventTargetRetryPolicyParameters(t.RetryPolicy)); err != nil { + return fmt.Errorf("Error setting retry_policy error: %#v", err) + } + } + + if t.DeadLetterConfig != nil { + if err := d.Set("dead_letter_config", flattenAwsCloudWatchEventTargetDeadLetterConfigParameters(t.DeadLetterConfig)); err != nil { + return fmt.Errorf("Error setting dead_letter_config error: %#v", err) + } + } + return nil } @@ -434,6 +481,14 @@ func buildPutTargetInputStruct(d *schema.ResourceData) *events.PutTargetsInput { e.InputTransformer = expandAwsCloudWatchEventTransformerParameters(v.([]interface{})) } + if v, ok := d.GetOk("retry_policy"); ok { + e.RetryPolicy = expandAwsCloudWatchEventRetryPolicyParameters(v.([]interface{})) + } + + if v, ok := d.GetOk("dead_letter_config"); ok { + e.DeadLetterConfig = expandAwsCloudWatchEventDeadLetterConfigParameters(v.([]interface{})) + } + input := events.PutTargetsInput{ Rule: aws.String(d.Get("rule").(string)), Targets: []*events.Target{e}, @@ -550,6 +605,31 @@ func expandAwsCloudWatchEventTargetSqsParameters(config []interface{}) *events.S return sqsParameters } +func expandAwsCloudWatchEventRetryPolicyParameters(config []interface{}) *events.RetryPolicy { + retryPolicyParameters := &events.RetryPolicy{} + for _, c := range config { + param := c.(map[string]interface{}) + if v, ok := param["maximum_event_age_in_seconds"].(int); ok { + retryPolicyParameters.MaximumEventAgeInSeconds = aws.Int64(int64(v)) + } + if v, ok := param["maximum_retry_attempts"].(int); ok { + retryPolicyParameters.MaximumRetryAttempts = aws.Int64(int64(v)) + } + } + return retryPolicyParameters +} + +func expandAwsCloudWatchEventDeadLetterConfigParameters(config []interface{}) *events.DeadLetterConfig { + deadLetterConfigParameters := &events.DeadLetterConfig{} + for _, c := range config { + param := c.(map[string]interface{}) + if v, ok := param["arn"].(string); ok && v != "" { + deadLetterConfigParameters.Arn = aws.String(v) + } + } + return deadLetterConfigParameters +} + func expandAwsCloudWatchEventTransformerParameters(config []interface{}) *events.InputTransformer { transformerParameters := &events.InputTransformer{} @@ -638,6 +718,21 @@ func flattenAwsCloudWatchEventTargetKinesisParameters(kinesisParameters *events. return result } +func flattenAwsCloudWatchEventTargetRetryPolicyParameters(retryPolicy *events.RetryPolicy) []map[string]interface{} { + config := make(map[string]interface{}) + config["maximum_event_age_in_seconds"] = int(aws.Int64Value(retryPolicy.MaximumEventAgeInSeconds)) + config["maximum_retry_attempts"] = int(aws.Int64Value(retryPolicy.MaximumRetryAttempts)) + result := []map[string]interface{}{config} + return result +} + +func flattenAwsCloudWatchEventTargetDeadLetterConfigParameters(deadLetterConfig *events.DeadLetterConfig) []map[string]interface{} { + config := make(map[string]interface{}) + config["arn"] = aws.StringValue(deadLetterConfig.Arn) + result := []map[string]interface{}{config} + return result +} + func flattenAwsCloudWatchEventTargetSqsParameters(sqsParameters *events.SqsParameters) []map[string]interface{} { config := make(map[string]interface{}) config["message_group_id"] = aws.StringValue(sqsParameters.MessageGroupId) diff --git a/aws/resource_aws_cloudwatch_event_target_test.go b/aws/resource_aws_cloudwatch_event_target_test.go index c6d3e17a84e..7e810a049d9 100644 --- a/aws/resource_aws_cloudwatch_event_target_test.go +++ b/aws/resource_aws_cloudwatch_event_target_test.go @@ -139,6 +139,8 @@ func TestAccAWSCloudWatchEventTarget_basic(t *testing.T) { resource.TestCheckResourceAttr(resourceName, "kinesis_target.#", "0"), resource.TestCheckResourceAttr(resourceName, "sqs_target.#", "0"), resource.TestCheckResourceAttr(resourceName, "input_transformer.#", "0"), + resource.TestCheckResourceAttr(resourceName, "retry_policy.#", "0"), + resource.TestCheckResourceAttr(resourceName, "dead_letter_config.#", "0"), ), }, { @@ -250,19 +252,24 @@ func TestAccAWSCloudWatchEventTarget_GeneratedTargetId(t *testing.T) { func TestAccAWSCloudWatchEventTarget_full(t *testing.T) { resourceName := "aws_cloudwatch_event_target.test" kinesisStreamResourceName := "aws_kinesis_stream.test" + deadLetterSQSResourceName := "aws_sqs_queue.test" + var v events.Target ruleName := acctest.RandomWithPrefix("tf-acc-cw-event-rule-full") ssmDocumentName := acctest.RandomWithPrefix("tf_ssm_Document") targetID := acctest.RandomWithPrefix("tf-acc-cw-target-full") + maximumRetryAttempts := acctest.RandIntRange(1, 10) + maximumEventAgeInSeconds := acctest.RandIntRange(60, 360) + resource.ParallelTest(t, resource.TestCase{ PreCheck: func() { testAccPreCheck(t) }, Providers: testAccProviders, CheckDestroy: testAccCheckAWSCloudWatchEventTargetDestroy, Steps: []resource.TestStep{ { - Config: testAccAWSCloudWatchEventTargetConfig_full(ruleName, targetID, ssmDocumentName), + Config: testAccAWSCloudWatchEventTargetConfig_full(ruleName, targetID, ssmDocumentName, maximumRetryAttempts, maximumEventAgeInSeconds), Check: resource.ComposeTestCheckFunc( testAccCheckCloudWatchEventTargetExists(resourceName, &v), resource.TestCheckResourceAttr(resourceName, "rule", ruleName), @@ -270,6 +277,9 @@ func TestAccAWSCloudWatchEventTarget_full(t *testing.T) { resource.TestCheckResourceAttrPair(resourceName, "arn", kinesisStreamResourceName, "arn"), testAccCheckResourceAttrEquivalentJSON(resourceName, "input", `{"source": ["aws.cloudtrail"]}`), resource.TestCheckResourceAttr(resourceName, "input_path", ""), + resource.TestCheckResourceAttrPair(resourceName, "dead_letter_config.0.arn", deadLetterSQSResourceName, "arn"), + resource.TestCheckResourceAttr(resourceName, "retry_policy.0.maximum_retry_attempts", fmt.Sprint(maximumRetryAttempts)), + resource.TestCheckResourceAttr(resourceName, "retry_policy.0.maximum_event_age_in_seconds", fmt.Sprint(maximumEventAgeInSeconds)), ), }, { @@ -730,7 +740,7 @@ resource "aws_sns_topic" "test" { `, ruleName, snsTopicName) } -func testAccAWSCloudWatchEventTargetConfig_full(ruleName, targetName, rName string) string { +func testAccAWSCloudWatchEventTargetConfig_full(ruleName, targetName, rName string, maximumRetryAttempts int, maximumEventAgeInSeconds int) string { return fmt.Sprintf(` resource "aws_cloudwatch_event_rule" "test" { name = %[1]q @@ -784,7 +794,13 @@ EOF resource "aws_cloudwatch_event_target" "test" { rule = aws_cloudwatch_event_rule.test.name target_id = %[3]q - + dead_letter_config { + arn = aws_sqs_queue.test.arn + } + retry_policy { + maximum_retry_attempts = %[4]d + maximum_event_age_in_seconds = %[5]d + } input = <