2
votes

I have an issue where my terraform is somehow not the same as what is deployed though I don't know why. According to my git history, the file that manages Cognito User Pools hasn't changed since it was deployed, but terraform thinks it has and complains changes need to force a new resource.

terraform version : 0.11.7

AWS Provider Version : 1.14.1

My Terraform code :

resource "aws_cognito_user_pool" "my_app" {
  name                          = "My App Pool"

  /* Fields that can work as aliases */
  alias_attributes              = [
    "email"
  ]

  /* Auto-verify these fields */
  auto_verified_attributes      = [
    "email"
  ]

  /* This is the template used to verify addresses / accounts */
  verification_message_template {
    default_email_option        = "CONFIRM_WITH_CODE"
  }

  admin_create_user_config {
    allow_admin_create_user_only = false
    invite_message_template {
      email_message             = <<EOF    
  {####}
  EOF

      email_subject             = "MyApp"
      sms_message               = "Welcome to MyApp.  Your username: {username} and password: {####}  Thank you!"
    }
  }

  email_verification_subject    = "MyApp's Confirmation Code"
  email_verification_message    = "Your confirmation code: {####}   Thank you."

password_policy {
    minimum_length              = 8
    require_lowercase           = true
    require_numbers             = true
    require_symbols             = true
    require_uppercase           = true
}

  schema {
    attribute_data_type         = "String"
    developer_only_attribute    = false
    mutable                     = true
    name                        = "email"
    required                    = true
  }

  schema {
    attribute_data_type         = "String"
    developer_only_attribute    = false
    mutable                     = true
    name                        = "custom1"
    required                    = false
  }

  schema {
    attribute_data_type         = "String"
    developer_only_attribute    = false
    mutable                     = true
    name                        = "custom2"
    required                    = false
  }

  tags {
    "name"                      = "MyApp"
    "Project"                   = "Terraform"
  }
}

I get the following result :

  schema.3021841581.attribute_data_type:                              "String" => "" (forces new resource)
  schema.3021841581.developer_only_attribute:                         "false" => "false"
  schema.3021841581.mutable:                                          "true" => "false" (forces new resource)
  schema.3021841581.name:                                             "custom1" => "" (forces new resource)
  schema.3021841581.number_attribute_constraints.#:                   "0" => "0"
  schema.3021841581.required:                                         "false" => "false"
  schema.3021841581.string_attribute_constraints.#:                   "1" => "0" (forces new resource)
  schema.3021841581.string_attribute_constraints.0.max_length:        "" => ""
  schema.3021841581.string_attribute_constraints.0.min_length:        "" => ""

I tried terraform refresh and it didn't work.

Showing what's in the state by doing terraform state show gives this

 schema.3021841581.attribute_data_type                              = String
 schema.3021841581.developer_only_attribute                         = false
 schema.3021841581.mutable                                          = true
 schema.3021841581.name                                             = custom1
 schema.3021841581.number_attribute_constraints.#                   = 0
 schema.3021841581.required                                         = false
 schema.3021841581.string_attribute_constraints.#                   = 1

So, my question :

  1. I know it's probably not ideal, but is there any way to ignore or skip over Cognito? I don't want to change anything on that service, and need to protect it due to our users.

  2. Is there any way to figure out why it thinks there's a difference and resolve it without destroying my pool?

1

1 Answers

3
votes
  1. You can use the option -target in your plan/apply operations. You should pass here the resource you want to update/create. Terraform will restrict the operation to that resource. If you have dependencies or you are going to update/create multiple resources, you can use that option as many times as you like.
  2. If for some reason it is out of sync, maybe you can use terraform import command targeting the problematic resource(es). That will try to bring the current configuration you have deployed, but this approach have some limitations and not everything is imported.