Skip to content

Instantly share code, notes, and snippets.

@kjkuan
Created December 31, 2025 03:42
Show Gist options
  • Select an option

  • Save kjkuan/abe71b978b4d34d1f0f099abee883e19 to your computer and use it in GitHub Desktop.

Select an option

Save kjkuan/abe71b978b4d34d1f0f099abee883e19 to your computer and use it in GitHub Desktop.
A script that generates terraform import blocks from existing terraform resource states
#!/usr/bin/env bash
declare -A resource_id_map=( # terraform resource type -> jq expression for its import id
[aws_lb]=.arn
[aws_lb_listener]=.arn
[aws_lb_target_group]=.arn
[aws_security_group]=.id
[aws_vpc_security_group_ingress_rule]=.security_group_rule_id
[aws_vpc_security_group_egress_rule]=.security_group_rule_id
[aws_iam_role]=.name
[aws_iam_role_policy]='"\(.role):\(.name)"'
[aws_ecs_cluster]=.name
[aws_ecs_cluster_capacity_providers]=.cluster_name
[aws_ecs_service]='"\(.cluster|sub("^.*/"; ""))/\(.name)"'
[aws_ecs_task_definition]=.arn
[aws_kms_key]=.id
[aws_kms_alias]=.name
[aws_route53_record]=.id
[aws_secretsmanager_secret]=.arn
[aws_secretsmanager_secret_version]=.id
# Feel free to look up the documentation and add the jq expression for the import id
# For example, according to https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/s3_bucket#import
# the import id for 'aws_s3_bucket' is the bucket name, which is available from the terraform state (
# made available via "$state_attributes_json" in 'generate-imports' below), so you would add an entry here like so:
#
# [aws_s3_bucket]=.id
#
# to teach the script how to get the import id for any aws_s3_bucket resources.
#
)
generate-imports () {
local state_attributes_json; state_attributes_json=$(
terraform state pull | jq '
[
.resources[]
| select(.mode == "managed")
| (if .module then "\(.module)." else "" end) as $module
| .instances[] as $inst
| (if $inst.index_key then "[\($inst.index_key|tojson)]" else "" end) as $index
| {
"key": "\($module)\(.type).\(.name)\($index)",
"value": $inst.attributes
}
] | from_entries
' # | tee state_attributes.json
# NOTE: Uncomment to see the json that can be used for mapping a resource type to
# its import id used in the resource_id_map above.
)
local source_state_name
while read -r source_state_name; do
resource_type=${source_state_name#module.*.}
resource_type=${resource_type%%.*}
cat <<EOF
import {
id = $(jq --arg key "$source_state_name" ".[\$key] | ${resource_id_map[$resource_type]:?}" <<<"$state_attributes_json")
to = $(map-tf-state-name)
}
EOF
done
}
map-tf-state-name () {
: TODO: implement your mapping logic here and output the target resource id
# NOTE: You are free to reference variables (e.g., $source_state_name or even $state_attributes_json)
# in the call chain.
}
terraform state list | egrep -v 'data\.' \
|
generate-imports
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment