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

resource/aws_route_table: Add documentation/warnings for import behavior #5715

Merged
merged 1 commit into from
Aug 30, 2018

Conversation

YakDriver
Copy link
Member

This adds warnings and work around information related to the bug
detailed in #5631.

Changes proposed in this pull request:

Related #5657

@YakDriver
Copy link
Member Author

YakDriver commented Aug 28, 2018

See comment from @bflad here regarding this PR.

Create a separate PR to document the upcoming change in the Version 2 Upgrade Guide and provide [WARN] logs indicating the change of behavior. We may also want to consider properly documenting the existing behavior and available workaround(s) in the aws_route_table resource documentation, even if we are deprecating it.


### Import Change

Importing a VPC route table will result in a state having a single `aws_route_table` resource with inline routes.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This section seems wordy. I think instead we should just state something like:

Previously, importing this resource resulted in an aws_route_table resource and an aws_route resource for each route in the table in the Terraform state. Support for importing aws_route resources has been added, so now this resource will only import the aws_route_table resource itself.

@@ -85,8 +85,19 @@ attribute once the route resource is created.

## Import

Route Tables can be imported using the `route table id`, e.g.
~> **NOTE on Importing Routes:** Currently, importing an `aws_route_table` and then
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The two new paragraphs here seem wordy as well. Instead, we should probably just state the potential problem, its workaround, and the upcoming change in a single callout box:

NOTE: Importing this resource currently imports an aws_route_table resource and aws_route resources for each route. If you intend to manage routes within the aws_route_table resource (using the route argument), you must use terraform state rm to delete the imported aws_route resources or Terraform will delete the routes. The behavior of importing aws_route resources with the aws_route_table resource will be removed in the next major version.

@bflad bflad added documentation Introduces or discusses updates to documentation. service/ec2 Issues and PRs that pertain to the ec2 service. labels Aug 29, 2018
@YakDriver YakDriver force-pushed the route-table-bug-docs branch from 137e7e8 to b255e9e Compare August 29, 2018 14:05
@ghost ghost removed the documentation Introduces or discusses updates to documentation. label Aug 29, 2018
@YakDriver
Copy link
Member Author

@bflad It's much better less wordy. I tweaked a little to further clarify.

@@ -85,8 +85,11 @@ attribute once the route resource is created.

## Import

Route Tables can be imported using the `route table id`, e.g.
~> **NOTE:** Importing this resource currently imports an `aws_route` resource for each route in addition to the `aws_route_table` resource. You must use `terraform state rm` to delete the imported `aws_route` resources if you plan on applying the imported configuration or Terraform will delete the actual routes. The behavior of importing `aws_route` resources with the `aws_route_table` resource will be removed in the next major version.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You must use terraform state rm to delete the imported aws_route resources if you plan on applying the imported configuration or Terraform will delete the actual routes.

This verbiage is not accurate if you add the aws_route configurations before applying. The distinction I made in my original ask was intentional:

If you intend to manage routes within the aws_route_table resource (using the route argument), you must use terraform state rm to delete the imported aws_route resources or Terraform will delete the routes.

Please feel free to reconcile the difference as you see appropriate, but I think its incorrect to say "You must use terraform state rm" as this is not a requirement in all situations and could cause confusion.

@YakDriver YakDriver force-pushed the route-table-bug-docs branch 2 times, most recently from a11e200 to 6d13716 Compare August 29, 2018 18:12
@YakDriver
Copy link
Member Author

@bflad I've changed the language and believe it is accurate. Even if you add the aws_route configuration before the apply, the actual route is still deleted on apply:

resource "aws_route_table" "route_table2" {
  vpc_id = "${var.vpc_id}"
}

resource "aws_route" "route1" {
  route_table_id = "${aws_route_table.route_table2.id}"
  destination_cidr_block = "${var.destination_cidr_ipv4}"
  vpc_peering_connection_id = "${var.vpc_peering_conn_2}"
}

Assuming the resources were previously created, if you do the following, the actual AWS route (addressed as aws_route.route1) will be deleted.

$ terraform import -input=false aws_route_table.route_table2 "${route_table2_id}"
$ terraform plan -input=false -out=newplan
$ terraform apply -input=false newplan

I've updated issue #5631 to show that regardless, your routes are deleted.

@YakDriver YakDriver force-pushed the route-table-bug-docs branch from 6d13716 to 158abbc Compare August 29, 2018 18:26
@bflad
Copy link
Contributor

bflad commented Aug 29, 2018

If the aws_route resource naming matches the aws_route_table resource name, it imports correctly and does not delete routes.

Given this configuration:

terraform {
  required_version = "0.11.8"
}

provider "aws" {
  region  = "us-east-1"
  version = "1.33.0"
}

resource "aws_vpc" "test" {
  cidr_block = "10.0.0.0/16"

  tags {
    Name = "bflad-testing"
  }
}

resource "aws_internet_gateway" "test" {
  vpc_id = "${aws_vpc.test.id}"

  tags {
    Name = "bflad-testing"
  }
}

resource "aws_route_table" "test" {
  vpc_id = "${aws_vpc.test.id}"

  tags {
    Name = "bflad-testing"
  }
}

resource "aws_route" "test" {
  destination_cidr_block = "0.0.0.0/0"
  gateway_id             = "${aws_internet_gateway.test.id}"
  route_table_id         = "${aws_route_table.test.id}"
}
$ terraform apply

An execution plan has been generated and is shown below.
Resource actions are indicated with the following symbols:
  + create

Terraform will perform the following actions:

  + aws_internet_gateway.test
      id:                               <computed>
      tags.%:                           "1"
      tags.Name:                        "bflad-testing"
      vpc_id:                           "${aws_vpc.test.id}"

  + aws_route.test
      id:                               <computed>
      destination_cidr_block:           "0.0.0.0/0"
      destination_prefix_list_id:       <computed>
      egress_only_gateway_id:           <computed>
      gateway_id:                       "${aws_internet_gateway.test.id}"
      instance_id:                      <computed>
      instance_owner_id:                <computed>
      nat_gateway_id:                   <computed>
      network_interface_id:             <computed>
      origin:                           <computed>
      route_table_id:                   "${aws_route_table.test.id}"
      state:                            <computed>

  + aws_route_table.test
      id:                               <computed>
      propagating_vgws.#:               <computed>
      route.#:                          <computed>
      tags.%:                           "1"
      tags.Name:                        "bflad-testing"
      vpc_id:                           "${aws_vpc.test.id}"

  + aws_vpc.test
      id:                               <computed>
      arn:                              <computed>
      assign_generated_ipv6_cidr_block: "false"
      cidr_block:                       "10.0.0.0/16"
      default_network_acl_id:           <computed>
      default_route_table_id:           <computed>
      default_security_group_id:        <computed>
      dhcp_options_id:                  <computed>
      enable_classiclink:               <computed>
      enable_classiclink_dns_support:   <computed>
      enable_dns_hostnames:             <computed>
      enable_dns_support:               "true"
      instance_tenancy:                 "default"
      ipv6_association_id:              <computed>
      ipv6_cidr_block:                  <computed>
      main_route_table_id:              <computed>
      tags.%:                           "1"
      tags.Name:                        "bflad-testing"


Plan: 4 to add, 0 to change, 0 to destroy.

Do you want to perform these actions?
  Terraform will perform the actions described above.
  Only 'yes' will be accepted to approve.

  Enter a value: yes

aws_vpc.test: Creating...
  arn:                              "" => "<computed>"
  assign_generated_ipv6_cidr_block: "" => "false"
  cidr_block:                       "" => "10.0.0.0/16"
  default_network_acl_id:           "" => "<computed>"
  default_route_table_id:           "" => "<computed>"
  default_security_group_id:        "" => "<computed>"
  dhcp_options_id:                  "" => "<computed>"
  enable_classiclink:               "" => "<computed>"
  enable_classiclink_dns_support:   "" => "<computed>"
  enable_dns_hostnames:             "" => "<computed>"
  enable_dns_support:               "" => "true"
  instance_tenancy:                 "" => "default"
  ipv6_association_id:              "" => "<computed>"
  ipv6_cidr_block:                  "" => "<computed>"
  main_route_table_id:              "" => "<computed>"
  tags.%:                           "" => "1"
  tags.Name:                        "" => "bflad-testing"
aws_vpc.test: Creation complete after 2s (ID: vpc-0b06332a6d7204b98)
aws_internet_gateway.test: Creating...
  tags.%:    "0" => "1"
  tags.Name: "" => "bflad-testing"
  vpc_id:    "" => "vpc-0b06332a6d7204b98"
aws_route_table.test: Creating...
  propagating_vgws.#: "" => "<computed>"
  route.#:            "" => "<computed>"
  tags.%:             "" => "1"
  tags.Name:          "" => "bflad-testing"
  vpc_id:             "" => "vpc-0b06332a6d7204b98"
aws_route_table.test: Creation complete after 0s (ID: rtb-03b09f66fed5a0013)
aws_internet_gateway.test: Creation complete after 0s (ID: igw-07f2f4fe32b2c9375)
aws_route.test: Creating...
  destination_cidr_block:     "" => "0.0.0.0/0"
  destination_prefix_list_id: "" => "<computed>"
  egress_only_gateway_id:     "" => "<computed>"
  gateway_id:                 "" => "igw-07f2f4fe32b2c9375"
  instance_id:                "" => "<computed>"
  instance_owner_id:          "" => "<computed>"
  nat_gateway_id:             "" => "<computed>"
  network_interface_id:       "" => "<computed>"
  origin:                     "" => "<computed>"
  route_table_id:             "" => "rtb-03b09f66fed5a0013"
  state:                      "" => "<computed>"
aws_route.test: Creation complete after 1s (ID: r-rtb-03b09f66fed5a00131080289494)

Apply complete! Resources: 4 added, 0 changed, 0 destroyed.

$ terraform state rm aws_route.test
1 items removed.
Item removal successful.

$ terraform state rm aws_route_table.test
1 items removed.
Item removal successful.

$ terraform state list
aws_internet_gateway.test
aws_vpc.test

$ terraform import aws_route_table.test rtb-03b09f66fed5a0013
aws_route_table.test: Importing from ID "rtb-03b09f66fed5a0013"...
aws_route_table.test: Import complete!
  Imported aws_route_table (ID: rtb-03b09f66fed5a0013)
  Imported aws_route (ID: r-rtb-03b09f66fed5a00131080289494)
aws_route_table.test: Refreshing state... (ID: rtb-03b09f66fed5a0013)
aws_route.test: Refreshing state... (ID: r-rtb-03b09f66fed5a00131080289494)

Import successful!

The resources that were imported are shown above. These resources are now in
your Terraform state and will henceforth be managed by Terraform.

$ terraform plan
Refreshing Terraform state in-memory prior to plan...
The refreshed state will be used to calculate this plan, but will not be
persisted to local or remote state storage.

aws_vpc.test: Refreshing state... (ID: vpc-0b06332a6d7204b98)
aws_route_table.test: Refreshing state... (ID: rtb-03b09f66fed5a0013)
aws_internet_gateway.test: Refreshing state... (ID: igw-07f2f4fe32b2c9375)
aws_route.test: Refreshing state... (ID: r-rtb-03b09f66fed5a00131080289494)

------------------------------------------------------------------------

No changes. Infrastructure is up-to-date.

This means that Terraform did not detect any differences between your
configuration and real physical resources that exist. As a result, no
actions need to be performed.

If instead your configuration has the route defined as:

resource "aws_route" "randomname" {
  destination_cidr_block = "0.0.0.0/0"
  gateway_id             = "${aws_internet_gateway.test.id}"
  route_table_id         = "${aws_route_table.test.id}"
}

It will report the destruction after import:

$ terraform plan
Refreshing Terraform state in-memory prior to plan...
The refreshed state will be used to calculate this plan, but will not be
persisted to local or remote state storage.

aws_route.test: Refreshing state... (ID: r-rtb-0171a2cd5e15c60e91080289494)
aws_vpc.test: Refreshing state... (ID: vpc-0afc44982875d9c93)
aws_internet_gateway.test: Refreshing state... (ID: igw-0927460c696a87e43)
aws_route_table.test: Refreshing state... (ID: rtb-0171a2cd5e15c60e9)

------------------------------------------------------------------------

An execution plan has been generated and is shown below.
Resource actions are indicated with the following symbols:
  + create
  - destroy

Terraform will perform the following actions:

  + aws_route.randomname
      id:                         <computed>
      destination_cidr_block:     "0.0.0.0/0"
      destination_prefix_list_id: <computed>
      egress_only_gateway_id:     <computed>
      gateway_id:                 "igw-0927460c696a87e43"
      instance_id:                <computed>
      instance_owner_id:          <computed>
      nat_gateway_id:             <computed>
      network_interface_id:       <computed>
      origin:                     <computed>
      route_table_id:             "rtb-0171a2cd5e15c60e9"
      state:                      <computed>

  - aws_route.test


Plan: 1 to add, 0 to change, 1 to destroy.

------------------------------------------------------------------------

Note: You didn't specify an "-out" parameter to save this plan, so Terraform
can't guarantee that exactly these actions will be performed if
"terraform apply" is subsequently run.

If you then fix your configuration to:

resource "aws_route" "test" {
  destination_cidr_block = "0.0.0.0/0"
  gateway_id             = "${aws_internet_gateway.test.id}"
  route_table_id         = "${aws_route_table.test.id}"
}

It will again report no differences:

$ terraform plan
Refreshing Terraform state in-memory prior to plan...
The refreshed state will be used to calculate this plan, but will not be
persisted to local or remote state storage.

aws_vpc.test: Refreshing state... (ID: vpc-0afc44982875d9c93)
aws_route_table.test: Refreshing state... (ID: rtb-0171a2cd5e15c60e9)
aws_internet_gateway.test: Refreshing state... (ID: igw-0927460c696a87e43)
aws_route.test: Refreshing state... (ID: r-rtb-0171a2cd5e15c60e91080289494)

------------------------------------------------------------------------

No changes. Infrastructure is up-to-date.

This means that Terraform did not detect any differences between your
configuration and real physical resources that exist. As a result, no
actions need to be performed.

@YakDriver
Copy link
Member Author

@bflad After a few hours of trying many scenarios, here is what I've come up with. Would you agree with this? Your routes will be deleted if you import/apply and either:

  1. the route reference address in the config is not aligned with the automagically created route reference address, OR
  2. your config has inline routes.

@YakDriver YakDriver force-pushed the route-table-bug-docs branch from 158abbc to dd3392a Compare August 30, 2018 00:00
This adds warnings and work around information related to the bug
detailed in hashicorp#5631.
@YakDriver YakDriver force-pushed the route-table-bug-docs branch from dd3392a to 4a3e1a6 Compare August 30, 2018 00:12
@YakDriver
Copy link
Member Author

@bflad I updated the verbiage.

Copy link
Contributor

@bflad bflad left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM -- thank you so much for working through this @YakDriver and sorry for being so particular about the phrasing. 🚀

@bflad bflad added the documentation Introduces or discusses updates to documentation. label Aug 30, 2018
@bflad bflad added this to the v1.34.0 milestone Aug 30, 2018
@bflad bflad merged commit a718d95 into hashicorp:master Aug 30, 2018
@YakDriver
Copy link
Member Author

@bflad No, no, I'm glad that you are particular. I rather be corrected when I misunderstand than endure the shame of submitting something that's wrong! It's pretty amazing the level of understanding you have over so many details.

@ghost
Copy link

ghost commented Apr 3, 2020

I'm going to lock this issue because it has been closed for 30 days ⏳. This helps our maintainers find and focus on the active issues.

If you feel this issue should be reopened, we encourage creating a new issue linking back to this one for added context. Thanks!

@ghost ghost locked and limited conversation to collaborators Apr 3, 2020
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
documentation Introduces or discusses updates to documentation. service/ec2 Issues and PRs that pertain to the ec2 service.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants