From 46486ce47ae5233ccb5c6788362fe7b5aedc6deb Mon Sep 17 00:00:00 2001 From: Glenn <31919569+GlennChia@users.noreply.github.com> Date: Tue, 11 Jan 2022 23:16:10 +0800 Subject: [PATCH] r/aws_connect_quick_connect (#22250) * feat(connect): add QuickConnect schema * feat(connect): add aws_connect_quick_connect * feat(connect): add QuickConnect expand, flatten condition on QuickConnectType that has values USER, QUEUE, PHONE_NUMBER * feat(connect): add QuickConnect ParseID func * feat(connect): add QuickConnect read DescribeQuickConnectWithContext api * feat(connect): add QuickConnect create CreateQuickConnectWithContext api * feat(connect): add QuickConnect update QuickConnect has 2 update APIs UpdateQuickConnectConfigWithContext: for configuration settings UpdateQuickConnectNameWithContext for name and description * feat(connect): add QuickConnect delete DeleteQuickConnectWithContext api * test(connect): config for instance, QuickConnect * test(connect): serialise tests * test(connect): check QuickConnect exists * test(connect): check QuickConnect destroy * test(connect): QuickConnect create and update update description field * test(connect): QuickConnect disappear * fix(connect): update for name req name or desc * test(connect): QuickConnect change phone number * docs(connect): add aws_connect_quick_connect * ci(connect): add CHANGELOG entry * style(connect): fix terrafmt errors * refactor(connect): many HasChange to 1 HasChanges * refactor(connect): rename quick_connect_arn to arn * style(connect): reorder comments for update * refactor(connect): remove quickConnect timeouts * chore(connect): remove unused variables --- .changelog/22250.txt | 3 + internal/provider/provider.go | 1 + internal/service/connect/quick_connect.go | 416 ++++++++++++++++++ .../service/connect/quick_connect_test.go | 234 ++++++++++ .../r/connect_quick_connect.html.markdown | 82 ++++ 5 files changed, 736 insertions(+) create mode 100644 .changelog/22250.txt create mode 100644 internal/service/connect/quick_connect.go create mode 100644 internal/service/connect/quick_connect_test.go create mode 100644 website/docs/r/connect_quick_connect.html.markdown diff --git a/.changelog/22250.txt b/.changelog/22250.txt new file mode 100644 index 00000000000..ec6ee130817 --- /dev/null +++ b/.changelog/22250.txt @@ -0,0 +1,3 @@ +```release-note:new-resource +aws_connect_quick_connect +``` \ No newline at end of file diff --git a/internal/provider/provider.go b/internal/provider/provider.go index 7d8ea622abc..0af4c95ad87 100644 --- a/internal/provider/provider.go +++ b/internal/provider/provider.go @@ -981,6 +981,7 @@ func Provider() *schema.Provider { "aws_connect_instance": connect.ResourceInstance(), "aws_connect_hours_of_operation": connect.ResourceHoursOfOperation(), "aws_connect_lambda_function_association": connect.ResourceLambdaFunctionAssociation(), + "aws_connect_quick_connect": connect.ResourceQuickConnect(), "aws_cur_report_definition": cur.ResourceReportDefinition(), diff --git a/internal/service/connect/quick_connect.go b/internal/service/connect/quick_connect.go new file mode 100644 index 00000000000..f90c59c300f --- /dev/null +++ b/internal/service/connect/quick_connect.go @@ -0,0 +1,416 @@ +package connect + +import ( + "context" + "fmt" + "log" + "strings" + + "github.com/aws/aws-sdk-go/aws" + "github.com/aws/aws-sdk-go/service/connect" + "github.com/hashicorp/aws-sdk-go-base/tfawserr" + "github.com/hashicorp/terraform-plugin-sdk/v2/diag" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/validation" + "github.com/hashicorp/terraform-provider-aws/internal/conns" + tftags "github.com/hashicorp/terraform-provider-aws/internal/tags" +) + +func ResourceQuickConnect() *schema.Resource { + return &schema.Resource{ + CreateContext: resourceQuickConnectCreate, + ReadContext: resourceQuickConnectRead, + UpdateContext: resourceQuickConnectUpdate, + DeleteContext: resourceQuickConnectDelete, + Importer: &schema.ResourceImporter{ + StateContext: schema.ImportStatePassthroughContext, + }, + Schema: map[string]*schema.Schema{ + "description": { + Type: schema.TypeString, + Optional: true, + ValidateFunc: validation.StringLenBetween(1, 250), + }, + "arn": { + Type: schema.TypeString, + Computed: true, + }, + "quick_connect_id": { + Type: schema.TypeString, + Computed: true, + }, + "instance_id": { + Type: schema.TypeString, + Required: true, + }, + "name": { + Type: schema.TypeString, + Required: true, + ValidateFunc: validation.StringLenBetween(1, 127), + }, + "quick_connect_config": { + Type: schema.TypeList, + Required: true, + MaxItems: 1, + Elem: &schema.Resource{ + Schema: map[string]*schema.Schema{ + "phone_config": { + Type: schema.TypeList, + Optional: true, + Elem: &schema.Resource{ + Schema: map[string]*schema.Schema{ + "phone_number": { + Type: schema.TypeString, + Required: true, + }, + }, + }, + DiffSuppressFunc: func(k, old, new string, d *schema.ResourceData) bool { + if v := d.Get("quick_connect_config.0.quick_connect_type").(string); v == connect.QuickConnectTypePhoneNumber { + return false + } + return true + }, + }, + "queue_config": { + Type: schema.TypeList, + Optional: true, + Elem: &schema.Resource{ + Schema: map[string]*schema.Schema{ + "contact_flow_id": { + Type: schema.TypeString, + Required: true, + }, + "queue_id": { + Type: schema.TypeString, + Required: true, + }, + }, + }, + DiffSuppressFunc: func(k, old, new string, d *schema.ResourceData) bool { + if v := d.Get("quick_connect_config.0.quick_connect_type").(string); v == connect.QuickConnectTypeQueue { + return false + } + return true + }, + }, + "quick_connect_type": { + Type: schema.TypeString, + Required: true, + ValidateFunc: validation.StringInSlice(connect.QuickConnectType_Values(), false), + }, + "user_config": { + Type: schema.TypeList, + Optional: true, + Elem: &schema.Resource{ + Schema: map[string]*schema.Schema{ + "contact_flow_id": { + Type: schema.TypeString, + Required: true, + }, + "user_id": { + Type: schema.TypeString, + Required: true, + }, + }, + }, + DiffSuppressFunc: func(k, old, new string, d *schema.ResourceData) bool { + if v := d.Get("quick_connect_config.0.quick_connect_type").(string); v == connect.QuickConnectTypeUser { + return false + } + return true + }, + }, + }, + }, + }, + "tags": tftags.TagsSchema(), + "tags_all": tftags.TagsSchemaComputed(), + }, + } +} + +func resourceQuickConnectCreate(ctx context.Context, d *schema.ResourceData, meta interface{}) diag.Diagnostics { + conn := meta.(*conns.AWSClient).ConnectConn + defaultTagsConfig := meta.(*conns.AWSClient).DefaultTagsConfig + tags := defaultTagsConfig.MergeTags(tftags.New(d.Get("tags").(map[string]interface{}))) + + instanceID := d.Get("instance_id").(string) + name := d.Get("name").(string) + + quickConnectConfig := expandQuickConnectConfig(d.Get("quick_connect_config").([]interface{})) + + input := &connect.CreateQuickConnectInput{ + QuickConnectConfig: quickConnectConfig, + InstanceId: aws.String(instanceID), + Name: aws.String(name), + } + + if v, ok := d.GetOk("description"); ok { + input.Description = aws.String(v.(string)) + } + + if len(tags) > 0 { + input.Tags = Tags(tags.IgnoreAWS()) + } + + log.Printf("[DEBUG] Creating Connect Quick Connect %s", input) + output, err := conn.CreateQuickConnectWithContext(ctx, input) + + if err != nil { + return diag.FromErr(fmt.Errorf("error creating Connect Quick Connect (%s): %w", name, err)) + } + + if output == nil { + return diag.FromErr(fmt.Errorf("error creating Connect Quick Connect (%s): empty output", name)) + } + + d.SetId(fmt.Sprintf("%s:%s", instanceID, aws.StringValue(output.QuickConnectId))) + + return resourceQuickConnectRead(ctx, d, meta) +} + +func resourceQuickConnectRead(ctx context.Context, d *schema.ResourceData, meta interface{}) diag.Diagnostics { + conn := meta.(*conns.AWSClient).ConnectConn + defaultTagsConfig := meta.(*conns.AWSClient).DefaultTagsConfig + ignoreTagsConfig := meta.(*conns.AWSClient).IgnoreTagsConfig + + instanceID, quickConnectID, err := QuickConnectParseID(d.Id()) + + if err != nil { + return diag.FromErr(err) + } + + resp, err := conn.DescribeQuickConnectWithContext(ctx, &connect.DescribeQuickConnectInput{ + InstanceId: aws.String(instanceID), + QuickConnectId: aws.String(quickConnectID), + }) + + if !d.IsNewResource() && tfawserr.ErrMessageContains(err, connect.ErrCodeResourceNotFoundException, "") { + log.Printf("[WARN] Connect Quick Connect (%s) not found, removing from state", d.Id()) + d.SetId("") + return nil + } + + if err != nil { + return diag.FromErr(fmt.Errorf("error getting Connect Quick Connect (%s): %w", d.Id(), err)) + } + + if resp == nil || resp.QuickConnect == nil { + return diag.FromErr(fmt.Errorf("error getting Connect Quick Connect (%s): empty response", d.Id())) + } + + if err := d.Set("quick_connect_config", flattenQuickConnectConfig(resp.QuickConnect.QuickConnectConfig)); err != nil { + return diag.FromErr(err) + } + + d.Set("instance_id", instanceID) + d.Set("description", resp.QuickConnect.Description) + d.Set("name", resp.QuickConnect.Name) + d.Set("arn", resp.QuickConnect.QuickConnectARN) + d.Set("quick_connect_id", resp.QuickConnect.QuickConnectId) + + tags := KeyValueTags(resp.QuickConnect.Tags).IgnoreAWS().IgnoreConfig(ignoreTagsConfig) + + //lintignore:AWSR002 + if err := d.Set("tags", tags.RemoveDefaultConfig(defaultTagsConfig).Map()); err != nil { + return diag.FromErr(fmt.Errorf("error setting tags: %w", err)) + } + + if err := d.Set("tags_all", tags.Map()); err != nil { + return diag.FromErr(fmt.Errorf("error setting tags_all: %w", err)) + } + + return nil +} + +func resourceQuickConnectUpdate(ctx context.Context, d *schema.ResourceData, meta interface{}) diag.Diagnostics { + conn := meta.(*conns.AWSClient).ConnectConn + + instanceID, quickConnectID, err := QuickConnectParseID(d.Id()) + + if err != nil { + return diag.FromErr(err) + } + + // QuickConnect has 2 update APIs + // UpdateQuickConnectNameWithContext: Updates the name and description of a quick connect. + // UpdateQuickConnectConfigWithContext: Updates the configuration settings for the specified quick connect. + + // updates to name and/or description + inputNameDesc := &connect.UpdateQuickConnectNameInput{ + InstanceId: aws.String(instanceID), + QuickConnectId: aws.String(quickConnectID), + } + + // Either QuickConnectName or QuickConnectDescription must be specified. Both cannot be null or empty + if d.HasChanges("name", "description") { + inputNameDesc.Name = aws.String(d.Get("name").(string)) + inputNameDesc.Description = aws.String(d.Get("description").(string)) + _, err = conn.UpdateQuickConnectNameWithContext(ctx, inputNameDesc) + + if err != nil { + return diag.FromErr(fmt.Errorf("[ERROR] Error updating QuickConnect Name (%s): %w", d.Id(), err)) + } + } + + // updates to configuration settings + inputConfig := &connect.UpdateQuickConnectConfigInput{ + InstanceId: aws.String(instanceID), + QuickConnectId: aws.String(quickConnectID), + } + + // QuickConnectConfig is a required field but does not require update if it is unchanged + if d.HasChange("quick_connect_config") { + quickConnectConfig := expandQuickConnectConfig(d.Get("quick_connect_config").([]interface{})) + inputConfig.QuickConnectConfig = quickConnectConfig + _, err = conn.UpdateQuickConnectConfigWithContext(ctx, inputConfig) + if err != nil { + return diag.FromErr(fmt.Errorf("[ERROR] Error updating QuickConnect (%s): %w", d.Id(), err)) + } + } + + // updates to tags + if d.HasChange("tags_all") { + o, n := d.GetChange("tags_all") + if err := UpdateTags(conn, d.Id(), o, n); err != nil { + return diag.FromErr(fmt.Errorf("error updating tags: %w", err)) + } + } + + return resourceQuickConnectRead(ctx, d, meta) +} + +func resourceQuickConnectDelete(ctx context.Context, d *schema.ResourceData, meta interface{}) diag.Diagnostics { + conn := meta.(*conns.AWSClient).ConnectConn + + instanceID, quickConnectID, err := QuickConnectParseID(d.Id()) + + if err != nil { + return diag.FromErr(err) + } + + _, err = conn.DeleteQuickConnectWithContext(ctx, &connect.DeleteQuickConnectInput{ + InstanceId: aws.String(instanceID), + QuickConnectId: aws.String(quickConnectID), + }) + + if err != nil { + return diag.FromErr(fmt.Errorf("error deleting QuickConnect (%s): %w", d.Id(), err)) + } + + return nil +} + +func expandQuickConnectConfig(quickConnectConfig []interface{}) *connect.QuickConnectConfig { + if len(quickConnectConfig) == 0 || quickConnectConfig[0] == nil { + return nil + } + + tfMap, ok := quickConnectConfig[0].(map[string]interface{}) + if !ok { + return nil + } + + quickConnectType := tfMap["quick_connect_type"].(string) + + result := &connect.QuickConnectConfig{ + QuickConnectType: aws.String(quickConnectType), + } + + switch quickConnectType { + case connect.QuickConnectTypePhoneNumber: + tpc := tfMap["phone_config"].([]interface{}) + if len(tpc) == 0 || tpc[0] == nil { + log.Printf("[ERR] 'phone_config' must be set when 'quick_connect_type' is '%s'", quickConnectType) + return nil + } + vpc := tpc[0].(map[string]interface{}) + pc := connect.PhoneNumberQuickConnectConfig{ + PhoneNumber: aws.String(vpc["phone_number"].(string)), + } + result.PhoneConfig = &pc + + case connect.QuickConnectTypeQueue: + tqc := tfMap["queue_config"].([]interface{}) + if len(tqc) == 0 || tqc[0] == nil { + log.Printf("[ERR] 'queue_config' must be set when 'quick_connect_type' is '%s'", quickConnectType) + return nil + } + vqc := tqc[0].(map[string]interface{}) + qc := connect.QueueQuickConnectConfig{ + ContactFlowId: aws.String(vqc["contact_flow_id"].(string)), + QueueId: aws.String(vqc["queue_id"].(string)), + } + result.QueueConfig = &qc + + case connect.QuickConnectTypeUser: + tuc := tfMap["user_config"].([]interface{}) + if len(tuc) == 0 || tuc[0] == nil { + log.Printf("[ERR] 'user_config' must be set when 'quick_connect_type' is '%s'", quickConnectType) + return nil + } + vuc := tuc[0].(map[string]interface{}) + uc := connect.UserQuickConnectConfig{ + ContactFlowId: aws.String(vuc["contact_flow_id"].(string)), + UserId: aws.String(vuc["user_id"].(string)), + } + result.UserConfig = &uc + + default: + log.Printf("[ERR] quick_connect_type is invalid") + return nil + } + + return result +} + +func flattenQuickConnectConfig(quickConnectConfig *connect.QuickConnectConfig) []interface{} { + if quickConnectConfig == nil { + return []interface{}{} + } + + quickConnectType := aws.StringValue(quickConnectConfig.QuickConnectType) + + values := map[string]interface{}{ + "quick_connect_type": quickConnectType, + } + + switch quickConnectType { + case connect.QuickConnectTypePhoneNumber: + pc := map[string]interface{}{ + "phone_number": aws.StringValue(quickConnectConfig.PhoneConfig.PhoneNumber), + } + values["phone_config"] = []interface{}{pc} + + case connect.QuickConnectTypeQueue: + qc := map[string]interface{}{ + "contact_flow_id": aws.StringValue(quickConnectConfig.QueueConfig.ContactFlowId), + "queue_id": aws.StringValue(quickConnectConfig.QueueConfig.QueueId), + } + values["queue_config"] = []interface{}{qc} + + case connect.QuickConnectTypeUser: + uc := map[string]interface{}{ + "contact_flow_id": aws.StringValue(quickConnectConfig.UserConfig.ContactFlowId), + "user_id": aws.StringValue(quickConnectConfig.UserConfig.UserId), + } + values["user_config"] = []interface{}{uc} + + default: + log.Printf("[ERR] quick_connect_type is invalid") + return nil + } + + return []interface{}{values} +} + +func QuickConnectParseID(id string) (string, string, error) { + parts := strings.SplitN(id, ":", 2) + + if len(parts) != 2 || parts[0] == "" || parts[1] == "" { + return "", "", fmt.Errorf("unexpected format of ID (%s), expected instanceID:quickConnectID", id) + } + + return parts[0], parts[1], nil +} diff --git a/internal/service/connect/quick_connect_test.go b/internal/service/connect/quick_connect_test.go new file mode 100644 index 00000000000..75fbf7cd294 --- /dev/null +++ b/internal/service/connect/quick_connect_test.go @@ -0,0 +1,234 @@ +package connect_test + +import ( + "fmt" + "testing" + + "github.com/aws/aws-sdk-go/aws" + "github.com/aws/aws-sdk-go/aws/awserr" + "github.com/aws/aws-sdk-go/service/connect" + sdkacctest "github.com/hashicorp/terraform-plugin-sdk/v2/helper/acctest" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-provider-aws/internal/acctest" + "github.com/hashicorp/terraform-provider-aws/internal/conns" + tfconnect "github.com/hashicorp/terraform-provider-aws/internal/service/connect" +) + +//Serialized acceptance tests due to Connect account limits (max 2 parallel tests) +func TestAccConnectQuickConnect_serial(t *testing.T) { + testCases := map[string]func(t *testing.T){ + "basic": testAccQuickConnect_phoneNumber, + "disappears": testAccQuickConnect_disappears, + } + + for name, tc := range testCases { + tc := tc + t.Run(name, func(t *testing.T) { + tc(t) + }) + } +} + +func testAccQuickConnect_phoneNumber(t *testing.T) { + var v connect.DescribeQuickConnectOutput + rName := sdkacctest.RandomWithPrefix("resource-test-terraform") + rName2 := sdkacctest.RandomWithPrefix("resource-test-terraform") + resourceName := "aws_connect_quick_connect.test" + + resource.Test(t, resource.TestCase{ + PreCheck: func() { acctest.PreCheck(t) }, + ErrorCheck: acctest.ErrorCheck(t, connect.EndpointsID), + Providers: acctest.Providers, + CheckDestroy: testAccCheckQuickConnectDestroy, + Steps: []resource.TestStep{ + { + Config: testAccQuickConnectPhoneNumberConfig(rName, rName2, "Created", "+12345678912"), + Check: resource.ComposeTestCheckFunc( + testAccCheckQuickConnectExists(resourceName, &v), + resource.TestCheckResourceAttrSet(resourceName, "instance_id"), + resource.TestCheckResourceAttrSet(resourceName, "name"), + resource.TestCheckResourceAttrSet(resourceName, "description"), + resource.TestCheckResourceAttrSet(resourceName, "arn"), + resource.TestCheckResourceAttrSet(resourceName, "quick_connect_id"), + resource.TestCheckResourceAttr(resourceName, "quick_connect_config.#", "1"), + resource.TestCheckResourceAttr(resourceName, "quick_connect_config.0.quick_connect_type", "PHONE_NUMBER"), + resource.TestCheckResourceAttr(resourceName, "quick_connect_config.0.phone_config.#", "1"), + resource.TestCheckResourceAttr(resourceName, "quick_connect_config.0.phone_config.0.phone_number", "+12345678912"), + + resource.TestCheckResourceAttr(resourceName, "tags.%", "1"), + ), + }, + { + ResourceName: resourceName, + ImportState: true, + ImportStateVerify: true, + }, + { + // update description + Config: testAccQuickConnectPhoneNumberConfig(rName, rName2, "Updated", "+12345678912"), + Check: resource.ComposeAggregateTestCheckFunc( + testAccCheckQuickConnectExists(resourceName, &v), + resource.TestCheckResourceAttrSet(resourceName, "instance_id"), + resource.TestCheckResourceAttrSet(resourceName, "name"), + resource.TestCheckResourceAttr(resourceName, "description", "Updated"), + resource.TestCheckResourceAttrSet(resourceName, "arn"), + resource.TestCheckResourceAttrSet(resourceName, "quick_connect_id"), + resource.TestCheckResourceAttr(resourceName, "quick_connect_config.#", "1"), + resource.TestCheckResourceAttr(resourceName, "quick_connect_config.0.quick_connect_type", "PHONE_NUMBER"), + resource.TestCheckResourceAttr(resourceName, "quick_connect_config.0.phone_config.#", "1"), + resource.TestCheckResourceAttr(resourceName, "quick_connect_config.0.phone_config.0.phone_number", "+12345678912"), + + resource.TestCheckResourceAttr(resourceName, "tags.%", "1"), + ), + }, + { + ResourceName: resourceName, + ImportState: true, + ImportStateVerify: true, + }, + { + // update phone number + Config: testAccQuickConnectPhoneNumberConfig(rName, rName2, "Updated", "+12345678913"), + Check: resource.ComposeAggregateTestCheckFunc( + testAccCheckQuickConnectExists(resourceName, &v), + resource.TestCheckResourceAttrSet(resourceName, "instance_id"), + resource.TestCheckResourceAttrSet(resourceName, "name"), + resource.TestCheckResourceAttr(resourceName, "description", "Updated"), + resource.TestCheckResourceAttrSet(resourceName, "arn"), + resource.TestCheckResourceAttrSet(resourceName, "quick_connect_id"), + resource.TestCheckResourceAttr(resourceName, "quick_connect_config.#", "1"), + resource.TestCheckResourceAttr(resourceName, "quick_connect_config.0.quick_connect_type", "PHONE_NUMBER"), + resource.TestCheckResourceAttr(resourceName, "quick_connect_config.0.phone_config.#", "1"), + resource.TestCheckResourceAttr(resourceName, "quick_connect_config.0.phone_config.0.phone_number", "+12345678913"), + + resource.TestCheckResourceAttr(resourceName, "tags.%", "1"), + ), + }, + }, + }) +} + +func testAccQuickConnect_disappears(t *testing.T) { + var v connect.DescribeQuickConnectOutput + rName := sdkacctest.RandomWithPrefix("resource-test-terraform") + rName2 := sdkacctest.RandomWithPrefix("resource-test-terraform") + resourceName := "aws_connect_quick_connect.test" + + resource.Test(t, resource.TestCase{ + PreCheck: func() { acctest.PreCheck(t) }, + ErrorCheck: acctest.ErrorCheck(t, connect.EndpointsID), + Providers: acctest.Providers, + CheckDestroy: testAccCheckQuickConnectDestroy, + Steps: []resource.TestStep{ + { + Config: testAccQuickConnectPhoneNumberConfig(rName, rName2, "Disappear", "+12345678912"), + Check: resource.ComposeTestCheckFunc( + testAccCheckQuickConnectExists(resourceName, &v), + acctest.CheckResourceDisappears(acctest.Provider, tfconnect.ResourceQuickConnect(), resourceName), + ), + ExpectNonEmptyPlan: true, + }, + }, + }) +} + +func testAccCheckQuickConnectExists(resourceName string, function *connect.DescribeQuickConnectOutput) resource.TestCheckFunc { + return func(s *terraform.State) error { + rs, ok := s.RootModule().Resources[resourceName] + if !ok { + return fmt.Errorf("Connect Quick Connect not found: %s", resourceName) + } + + if rs.Primary.ID == "" { + return fmt.Errorf("Connect Quick Connect ID not set") + } + instanceID, quickConnectID, err := tfconnect.QuickConnectParseID(rs.Primary.ID) + + if err != nil { + return err + } + + conn := acctest.Provider.Meta().(*conns.AWSClient).ConnectConn + + params := &connect.DescribeQuickConnectInput{ + QuickConnectId: aws.String(quickConnectID), + InstanceId: aws.String(instanceID), + } + + getFunction, err := conn.DescribeQuickConnect(params) + if err != nil { + return err + } + + *function = *getFunction + + return nil + } +} + +func testAccCheckQuickConnectDestroy(s *terraform.State) error { + for _, rs := range s.RootModule().Resources { + if rs.Type != "aws_connect_quick_connect" { + continue + } + + conn := acctest.Provider.Meta().(*conns.AWSClient).ConnectConn + + instanceID, quickConnectID, err := tfconnect.QuickConnectParseID(rs.Primary.ID) + + if err != nil { + return err + } + + params := &connect.DescribeQuickConnectInput{ + QuickConnectId: aws.String(quickConnectID), + InstanceId: aws.String(instanceID), + } + + _, experr := conn.DescribeQuickConnect(params) + // Verify the error is what we want + if experr != nil { + if awsErr, ok := experr.(awserr.Error); ok && awsErr.Code() == "ResourceNotFoundException" { + continue + } + return experr + } + } + return nil +} + +func testAccQuickConnectBaseConfig(rName string) string { + return fmt.Sprintf(` +resource "aws_connect_instance" "test" { + identity_management_type = "CONNECT_MANAGED" + inbound_calls_enabled = true + instance_alias = %[1]q + outbound_calls_enabled = true +} +`, rName) +} + +func testAccQuickConnectPhoneNumberConfig(rName, rName2, label string, phoneNumber string) string { + return acctest.ConfigCompose( + testAccQuickConnectBaseConfig(rName), + fmt.Sprintf(` +resource "aws_connect_quick_connect" "test" { + instance_id = aws_connect_instance.test.id + name = %[1]q + description = %[2]q + + quick_connect_config { + quick_connect_type = "PHONE_NUMBER" + + phone_config { + phone_number = %[3]q + } + } + + tags = { + "Name" = "Test Quick Connect" + } +} +`, rName2, label, phoneNumber)) +} diff --git a/website/docs/r/connect_quick_connect.html.markdown b/website/docs/r/connect_quick_connect.html.markdown new file mode 100644 index 00000000000..9f5271100e2 --- /dev/null +++ b/website/docs/r/connect_quick_connect.html.markdown @@ -0,0 +1,82 @@ +--- +subcategory: "Connect" +layout: "aws" +page_title: "AWS: aws_connect_quick_connect" +description: |- + Provides details about a specific Amazon Quick Connect +--- + +# Resource: aws_connect_quick_connect + +Provides an Amazon Connect Quick Connect resource. For more information see +[Amazon Connect: Getting Started](https://docs.aws.amazon.com/connect/latest/adminguide/amazon-connect-get-started.html) + +## Example Usage + +```terraform +resource "aws_connect_quick_connect" "test" { + instance_id = "aaaaaaaa-bbbb-cccc-dddd-111111111111" + name = "Example Name" + description = "quick connect phone number" + + quick_connect_config { + quick_connect_type = "PHONE_NUMBER" + + phone_config { + phone_number = "+12345678912" + } + } + + tags = { + "Name" = "Example Quick Connect" + } +} +``` + +## Argument Reference + +The following arguments are supported: + +* `description` - (Optional) Specifies the description of the Quick Connect. +* `instance_id` - (Required) Specifies the identifier of the hosting Amazon Connect Instance. +* `name` - (Required) Specifies the name of the Quick Connect. +* `quick_connect_config` - (Required) A block that defines the configuration information for the Quick Connect: `quick_connect_type` and one of `phone_config`, `queue_config`, `user_config` . The Quick Connect Config block is documented below. +* `tags` - (Optional) Tags to apply to the Quick Connect. If configured with a provider [`default_tags` configuration block](/docs/providers/aws/index.html#default_tags-configuration-block) present, tags with matching keys will overwrite those defined at the provider-level. + +A `quick_connect_config` block supports the following arguments: + +* `quick_connect_type` - (Required) Specifies the configuration type of the quick connect. valid values are `PHONE_NUMBER`, `QUEUE`, `USER`. +* `phone_config` - (Optional) Specifies the phone configuration of the Quick Connect. This is required only if `quick_connect_type` is `PHONE_NUMBER`. The `phone_config` block is documented below. +* `queue_config` - (Optional) Specifies the queue configuration of the Quick Connect. This is required only if `quick_connect_type` is `QUEUE`. The `queue_config` block is documented below. +* `user_config` - (Optional) Specifies the user configuration of the Quick Connect. This is required only if `quick_connect_type` is `USER`. The `user_config` block is documented below. + +A `phone_config` block supports the following arguments: + +* `phone_number` - (Required) Specifies the phone number in in E.164 format. + +A `queue_config` block supports the following arguments: + +* `contact_flow_id` - (Required) Specifies the identifier of the contact flow. +* `queue_id` - (Required) Specifies the identifier for the queue. + +A `user_config` block supports the following arguments: + +* `contact_flow_id` - (Required) Specifies the identifier of the contact flow. +* `user_id` - (Required) Specifies the identifier for the user. + +## Attributes Reference + +In addition to all arguments above, the following attributes are exported: + +* `arn` - The Amazon Resource Name (ARN) of the Quick Connect. +* `quick_connect_id` - The identifier for the Quick Connect. +* `id` - The identifier of the hosting Amazon Connect Instance and identifier of the Quick Connect separated by a colon (`:`). +* `tags_all` - A map of tags assigned to the resource, including those inherited from the provider [`default_tags` configuration block](/docs/providers/aws/index.html#default_tags-configuration-block). + +## Import + +Amazon Connect Quick Connects can be imported using the `instance_id` and `quick_connect_id` separated by a colon (`:`), e.g., + +``` +$ terraform import aws_connect_quick_connect.example f1288a1f-6193-445a-b47e-af739b2:c1d4e5f6-1b3c-1b3c-1b3c-c1d4e5f6c1d4e5 +```