Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
13 changes: 12 additions & 1 deletion bin/update-gcloud-dns
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
#!/usr/bin/env python3
import argparse
import socket

from gcloud_dynamic_dns.dns import update_dns

Expand All @@ -9,7 +10,17 @@ parser.add_argument("dns_name", help="the DNS name to update")
parser.add_argument("--ttl", help="TTL of the update record", default=60)
parser.add_argument("--project_id", default=None, help="name of the GCP project")
parser.add_argument("--force_update", action="store_true", default=False, help="force the DNS update even if the record hasn't changed")
parser.add_argument("--ipv4", action="store_true", default=False, help="updates IPv4 A record, if both ipv4 and ipv6 are not specified both will be updated")
parser.add_argument("--ipv6", action="store_true", default=False, help="updates IPv6 AAAA record, if both ipv4 and ipv6 are not specified both will be updated")

if __name__ == "__main__":
args = parser.parse_args()
update_dns(args.zone_name, args.dns_name, args.ttl, args.force_update, args.project_id)

if (not args.ipv4 and not args.ipv6) or (args.ipv4 and args.ipv6):
ip_kind = (socket.AddressFamily.AF_INET, socket.AddressFamily.AF_INET6)
elif args.ipv4:
ip_kind = (socket.AddressFamily.AF_INET,)
else:
ip_kind = (socket.AddressFamily.AF_INET6,)

update_dns(args.zone_name, args.dns_name, args.ttl, args.force_update, args.project_id, ip_kind)
7 changes: 4 additions & 3 deletions gcloud_dynamic_dns/dns.py
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ def my_ip(kind: Iterable[socket.AddressFamily] = IPV4_6, query_host: str = "ifco


def update_dns(zone_name: str, dns_name: str, ttl: int = 60, force_update: bool = False,
project_id: Optional[str] = None):
project_id: Optional[str] = None, ip_kind: Iterable[socket.AddressFamily] = (socket.AddressFamily.AF_INET, socket.AddressFamily.AF_INET6)):
"""
Updates a GCP Cloud DNS zone with the host's current IP as it appears from the internet
:param zone_name: the name of the zone in your GCP project
Expand All @@ -53,10 +53,12 @@ def update_dns(zone_name: str, dns_name: str, ttl: int = 60, force_update: bool
:return: the applied change set
"""

addresses = my_ip(ip_kind)

if not dns_name.endswith("."):
dns_name = "%s." % dns_name

if len(resolve_addresses(dns_name).symmetric_difference(my_ip())) == 0 and not force_update:
if len(resolve_addresses(dns_name).symmetric_difference(addresses)) == 0 and not force_update:
return

if project_id:
Expand All @@ -65,7 +67,6 @@ def update_dns(zone_name: str, dns_name: str, ttl: int = 60, force_update: bool
client = dns.Client()
zone = client.zone(zone_name)

addresses = my_ip()
ipv4_addresses = set(filter(lambda _ip: len(_ip.split(".")) == 4, addresses))
ipv6_addresses = addresses - ipv4_addresses

Expand Down