diff --git a/netbox_ddns/background_tasks.py b/netbox_ddns/background_tasks.py index 5f5c5e5..4299495 100644 --- a/netbox_ddns/background_tasks.py +++ b/netbox_ddns/background_tasks.py @@ -9,7 +9,7 @@ from django_rq import job from dns import rcode from netaddr import ip -from netbox_ddns.models import ACTION_CREATE, ACTION_DELETE, DNSStatus, ReverseZone, Zone +from netbox_ddns.models import ACTION_CREATE, ACTION_DELETE, DNSStatus, RCODE_NO_ZONE, ReverseZone, Zone from netbox_ddns.utils import get_soa logger = logging.getLogger('netbox_ddns') @@ -29,11 +29,12 @@ def status_update(output: List[str], operation: str, response) -> None: def create_forward(dns_name: str, address: ip.IPAddress, status: Optional[DNSStatus], output: List[str]): + if status: + status.forward_action = ACTION_CREATE + zone = Zone.objects.find_for_dns_name(dns_name) if zone: logger.debug(f"Found zone {zone.name} for {dns_name}") - if status: - status.forward_action = ACTION_CREATE # Check the SOA, we don't want to write to a parent zone if it has delegated authority soa = get_soa(dns_name) @@ -57,14 +58,17 @@ def create_forward(dns_name: str, address: ip.IPAddress, status: Optional[DNSSta status.forward_rcode = rcode.NOTAUTH else: logger.debug(f"No zone found for {dns_name}") + if status: + status.forward_rcode = RCODE_NO_ZONE def delete_forward(dns_name: str, address: ip.IPAddress, status: Optional[DNSStatus], output: List[str]): + if status: + status.forward_action = ACTION_DELETE + zone = Zone.objects.find_for_dns_name(dns_name) if zone: logger.debug(f"Found zone {zone.name} for {dns_name}") - if status: - status.forward_action = ACTION_DELETE # Check the SOA, we don't want to write to a parent zone if it has delegated authority soa = get_soa(dns_name) @@ -87,15 +91,18 @@ def delete_forward(dns_name: str, address: ip.IPAddress, status: Optional[DNSSta status.forward_rcode = rcode.NOTAUTH else: logger.debug(f"No zone found for {dns_name}") + if status: + status.forward_rcode = RCODE_NO_ZONE def create_reverse(dns_name: str, address: ip.IPAddress, status: Optional[DNSStatus], output: List[str]): + if status: + status.reverse_action = ACTION_CREATE + zone = ReverseZone.objects.find_for_address(address) - if zone and dns_name: + if zone: record_name = zone.record_name(address) logger.debug(f"Found zone {zone.name} for {record_name}") - if status: - status.reverse_action = ACTION_CREATE # Check the SOA, we don't want to write to a parent zone if it has delegated authority soa = get_soa(record_name) @@ -118,15 +125,18 @@ def create_reverse(dns_name: str, address: ip.IPAddress, status: Optional[DNSSta status.reverse_rcode = rcode.NOTAUTH else: logger.debug(f"No zone found for {address}") + if status: + status.reverse_rcode = RCODE_NO_ZONE def delete_reverse(dns_name: str, address: ip.IPAddress, status: Optional[DNSStatus], output: List[str]): + if status: + status.reverse_action = ACTION_DELETE + zone = ReverseZone.objects.find_for_address(address) - if zone and dns_name: + if zone: record_name = zone.record_name(address) logger.debug(f"Found zone {zone.name} for {record_name}") - if status: - status.reverse_action = ACTION_DELETE # Check the SOA, we don't want to write to a parent zone if it has delegated authority soa = get_soa(record_name) @@ -148,6 +158,8 @@ def delete_reverse(dns_name: str, address: ip.IPAddress, status: Optional[DNSSta status.reverse_rcode = rcode.NOTAUTH else: logger.debug(f"No zone found for {address}") + if status: + status.reverse_rcode = RCODE_NO_ZONE @job diff --git a/netbox_ddns/models.py b/netbox_ddns/models.py index 7a66168..801a20b 100644 --- a/netbox_ddns/models.py +++ b/netbox_ddns/models.py @@ -37,6 +37,9 @@ ACTION_CHOICES = ( (ACTION_DELETE, 'Delete'), ) +# Use a private rcode for internal errors +RCODE_NO_ZONE = 4095 + def get_rcode_display(code): if code is None: @@ -53,6 +56,8 @@ def get_rcode_display(code): return _('Refused') elif code == rcode.NOTAUTH: return _('Server not authoritative') + elif code == RCODE_NO_ZONE: + return _('No zone configured') else: return _('Unknown response: {}').format(code) diff --git a/netbox_ddns/views.py b/netbox_ddns/views.py index d91cc3c..b554f20 100644 --- a/netbox_ddns/views.py +++ b/netbox_ddns/views.py @@ -67,9 +67,8 @@ class IPAddressDNSNameRecreateView(PermissionRequiredMixin, View): new_dns_name = normalize_fqdn(ip_address.dns_name) updated_names = [] - zoneless_names = [] - if new_dns_name and Zone.objects.find_for_dns_name(new_dns_name): + if new_dns_name: status, created = DNSStatus.objects.get_or_create(ip_address=ip_address) dns_create.delay( @@ -79,28 +78,21 @@ class IPAddressDNSNameRecreateView(PermissionRequiredMixin, View): ) updated_names.append(new_dns_name) - else: - zoneless_names.append(new_dns_name) for extra in ip_address.extradnsname_set.all(): new_address = extra.ip_address.address.ip new_dns_name = extra.name - if Zone.objects.find_for_dns_name(new_dns_name): - dns_create.delay( - dns_name=new_dns_name, - address=new_address, - status=extra, - reverse=False, - ) + dns_create.delay( + dns_name=new_dns_name, + address=new_address, + status=extra, + reverse=False, + ) - updated_names.append(new_dns_name) - else: - zoneless_names.append(new_dns_name) + updated_names.append(new_dns_name) if updated_names: messages.info(request, _("Updating DNS for {names}").format(names=', '.join(updated_names))) - if zoneless_names: - messages.warning(request, _("No DNS zone configured for {names}").format(names=', '.join(zoneless_names))) return redirect('ipam:ipaddress', pk=ip_address.pk)