Skip to content

Instantly share code, notes, and snippets.

@jacoor
Created August 19, 2021 07:48
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save jacoor/e6b90dc1f6a0e204b792855825a18c70 to your computer and use it in GitHub Desktop.
Save jacoor/e6b90dc1f6a0e204b792855825a18c70 to your computer and use it in GitHub Desktop.
Generate zone records file (terraform) from AWS Route53 zone dump.
"""
Generate zone records file (terraform) from zone dump.
To get zone dump:
aws route53 list-resource-record-sets --hosted-zone-id ZONE ID > records.json
Example usage:
ZONE_FILE=records.json TERRAFORM_DIR=zone_name python generate_zone_records_from_json.py
Based on:
https://mrkaran.dev/posts/terraform-route53-import/
"""
import json
from os import getenv, path
from string import Template
from subprocess import run
from sys import exit
# terraform resource path of the zone to add resource to.
ZONE_ID = "aws_route53_zone.main.zone_id"
ZONE_FILE = getenv("ZONE_FILE")
TERRAFORM_DIR = getenv("TERRAFORM_DIR")
RECORDS_FILE_PATH = path.join(TERRAFORM_DIR, "records.tf")
def check_env_vars():
if not ZONE_FILE:
return "$ZONE_FILE"
if not TERRAFORM_DIR:
return "$TERRAFORM_DIR"
return ""
# Loads the zone records in a dict
def load_records(zone_file=ZONE_FILE):
with open(zone_file) as record_file:
data = json.load(record_file)
return data
# Creates the Terraform template
def template_records_file(resource_safe_name, resource_name, resource_type, resource_values=None, alias_values=None, resource_ttl=60):
if resource_values:
add_records_record = Template(
"""
resource "aws_route53_record" "$resource_safe_name" {
zone_id = $zone_id
name = "$resource_name"
type = "$resource_type"
ttl = "$resource_ttl"
records = $resource_values
}
"""
)
if alias_values:
add_records_record = Template(
"""
resource "aws_route53_record" "$resource_safe_name" {
zone_id = $zone_id
name = "$resource_name"
type = "$resource_type"
alias {
name = "$aliasTarget_DNSName"
zone_id = "$aliasTarget_HostedZoneId"
evaluate_target_health = $aliasTarget_EvaluateTargetHealth
}
}
"""
)
with open(RECORDS_FILE_PATH, "a") as f:
f.write(add_records_record.safe_substitute(
zone_id=ZONE_ID,
resource_name=resource_name,
resource_safe_name=resource_safe_name,
resource_type=resource_type,
resource_ttl=resource_ttl,
resource_values=resource_values,
aliasTarget_DNSName=alias_values.get("DNSName"),
aliasTarget_HostedZoneId=alias_values.get("HostedZoneId"),
aliasTarget_EvaluateTargetHealth="true" if alias_values.get(
"EvaluateTargetHealth") else "false"
))
if __name__ == "__main__":
missing = check_env_vars()
if missing:
exit(f"Required env variable {missing} is missing.")
with open(RECORDS_FILE_PATH, "w") as f:
# just clear the file
pass
records = load_records()
for i in records.get("ResourceRecordSets"):
resource_name = i.get("Name")
resource_type = i.get("Type")
resource_safe_name = resource_name.replace(".", "__")[:-2]
resource_safe_name = f"{resource_type}_{resource_safe_name}"
resource_ttl = i.get("TTL")
alias_values = i.get("AliasTarget", {})
resource_values = json.dumps(
[record.get("Value").replace("\"", "") for record in i.get("ResourceRecords", [])])
template_records_file(resource_safe_name, resource_name,
resource_type, resource_values, alias_values, resource_ttl)
print(f"Imported {resource_name} {resource_type}")
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment