27bb82767b
1: Script had AAAA hardcoded, this would've changed all records to AAAA. 2: Script was not saving the DNS Records ids, only their names this would've made it impossible to actually edit the DNS Record 3: Lowered the amount of printing going on, removed irrelevant information such as zoneid from the print statements, also removed most printing during the update phase
97 lines
3.3 KiB
Python
97 lines
3.3 KiB
Python
import sys
|
|
import ipaddress
|
|
from configparser import ConfigParser
|
|
import json
|
|
import copy
|
|
import CloudFlare
|
|
|
|
|
|
class DNSUpdater:
|
|
def __init__(self, args):
|
|
# Parse config
|
|
config = ConfigParser()
|
|
config.read('config.ini')
|
|
|
|
self.HOSTNAME = config['server']['HOSTNAME']
|
|
__TOKEN = config['cloudflare']['TOKEN']
|
|
|
|
# Parse args
|
|
try:
|
|
ipversion = args[1].lstrip('-')
|
|
ipaddress_new = args[2]
|
|
except IndexError:
|
|
ipaddress_new = ''
|
|
ipversion = 'skip'
|
|
|
|
match ipversion:
|
|
case '4': self.IPVER = 'ipv4'
|
|
case '6': self.IPVER = 'ipv6'
|
|
case 'skip': self.IPVER = ipversion
|
|
case other: raise ValueError(f"Wrong IP Address version given: {ipversion}")
|
|
|
|
self.IPNEW = ipaddress_new
|
|
|
|
# Cloudflare class
|
|
self._cloudflare = CloudFlare.CloudFlare(token=__TOKEN)
|
|
|
|
with open('cloudflare.json', 'r') as file:
|
|
self.dns_replacements = json.load(file)
|
|
|
|
def get_zones(self):
|
|
# Cloudflare get zones from API token
|
|
zones = self._cloudflare.zones.get()
|
|
for zone in zones:
|
|
self.zone_id = zone['id']
|
|
self.zone_name = zone['name']
|
|
print(f"Zone ID: {zone['id']} | Zone Name: {zone['name']}")
|
|
|
|
def get_dns_records(self, log=False):
|
|
dns_records_all = self._cloudflare.zones.dns_records.get(self.zone_id)
|
|
|
|
dns_records_to_update = {'A' : [], 'AAAA' : []}
|
|
for dnsrecord in dns_records_all:
|
|
if dnsrecord['type'] in ['A', 'AAAA']:
|
|
if log:
|
|
print(f"DNS Name: {dnsrecord['name']} | Type : {dnsrecord['type']} | IP: {dnsrecord['content']}")
|
|
dns_records_to_update[dnsrecord['type']].append(dnsrecord)
|
|
else:
|
|
if log:
|
|
print(f"| Unknow DNS | Type: {dnsrecord['type']} | Zone: {dnsrecord['name']}")
|
|
|
|
self.DNSRECORDS = copy.deepcopy(dns_records_to_update)
|
|
|
|
def update_records(self):
|
|
if self.IPVER == 'skip':
|
|
self.get_dns_records(log=True)
|
|
return
|
|
|
|
self.get_dns_records()
|
|
|
|
ipinformation = {
|
|
'ipv4': [ipaddress.IPv4Address, 'A'],
|
|
'ipv6': [ipaddress.IPv6Address, 'AAAA']
|
|
}
|
|
|
|
print(f"Updating IP of version {self.IPVER}")
|
|
assert isinstance(ipaddress.ip_address(self.IPNEW), ipinformation[self.IPVER][0]), f'IP {self.IPNEW} is not a valid IPv6 address'
|
|
dnstype = ipinformation[self.IPVER][1]
|
|
|
|
names_replace = self.dns_replacements[dnstype]
|
|
print(names_replace)
|
|
for name in names_replace:
|
|
fullname = f"{name}.{self.HOSTNAME}"
|
|
|
|
for record in self.DNSRECORDS[dnstype]:
|
|
if record['name'] == fullname:
|
|
new_dnsrecord = {"name": fullname, "type": dnstype, "content": self.IPNEW}
|
|
print(f"Sending request {new_dnsrecord}")
|
|
res = self._cloudflare.zones.dns_records.patch(self.zone_id, record['id'], data=new_dnsrecord)
|
|
if res['content'] != new_dnsrecord['content']:
|
|
print(res)
|
|
|
|
|
|
|
|
if __name__ == '__main__':
|
|
dnsupdate = DNSUpdater(sys.argv)
|
|
dnsupdate.get_zones()
|
|
dnsupdate.update_records() |