diff --git a/README.md b/README.md index 3a59c94..504c310 100644 --- a/README.md +++ b/README.md @@ -74,6 +74,23 @@ The generated CSV includes the following columns: - Redirect Chain - HTTP Error +## Parked Domain CSV Generator + +The `scripts/parked_domain_csv.py` helper script creates DNS change records for +locking down parked or non-mailing domains. Provide a text file of domains and +an output CSV path: + +```bash +python scripts/parked_domain_csv.py domains.txt parked_domains.csv +``` + +Each domain receives the following DNS entries: + +- SPF record with `-all` +- Null MX record +- DKIM wildcard with an empty key +- DMARC CNAME pointing to a reject policy + ## License This project is released under the MIT License. See [LICENSE](LICENSE) for details. diff --git a/scripts/parked_domain_csv.py b/scripts/parked_domain_csv.py new file mode 100644 index 0000000..7ee6fc5 --- /dev/null +++ b/scripts/parked_domain_csv.py @@ -0,0 +1,58 @@ +import csv +import sys + +HEADER = [ + "Action", + "Zone", + "Record Name", + "Record Type", + "TTL", + "Value", + "Comments", +] + +RECORD_TEMPLATE = [ + ["REMOVE", "{domain}", "@", "MX", "", "10 custmx.cscdns.net.", "Remove existing MX record"], + ["ADD", "{domain}", "@", "TXT", "3600", "v=spf1 -all", "SPF hard fail"], + ["ADD", "{domain}", "@", "MX", "3600", "0 .", "Null MX (RFC 7505)"], + ["ADD", "{domain}", "*._domainkey", "TXT", "3600", "v=DKIM1; p=", "DKIM wildcard with empty key"], + ["ADD", "{domain}", "_dmarc", "CNAME", "3600", "reject.dmarc.fabrikam.com.", "DMARC reject policy via CNAME"], +] + + +def generate_records(domain: str): + records = [[f"--- {domain} ---", "", "", "", "", "", "Domain configuration"]] + for template in RECORD_TEMPLATE: + records.append([ + template[0], + domain, + template[2], + template[3], + template[4], + template[5], + template[6], + ]) + return records + + +def main(): + if len(sys.argv) != 3: + print("Usage: python parked_domain_csv.py domains.txt output.csv") + sys.exit(1) + + domain_file = sys.argv[1] + output_csv = sys.argv[2] + + with open(domain_file, "r", encoding="utf-8") as f: + domains = [line.strip() for line in f if line.strip()] + + with open(output_csv, "w", newline="", encoding="utf-8") as csvfile: + writer = csv.writer(csvfile) + writer.writerow(HEADER) + for domain in domains: + for row in generate_records(domain): + writer.writerow(row) + + +if __name__ == "__main__": + main()