def test_parse_zone(self): zone_file = self.get_zonefile_fixture() dnspython_zone = dnszone.from_text( zone_file, # Don't relativize, otherwise we end up with '@' record names. relativize=False, # Dont check origin, we allow missing NS records (missing SOA # records are taken care of in _create_zone). check_origin=False) zone = dnsutils.from_dnspython_zone(dnspython_zone) for rrset in zone.recordsets: k = (rrset.name, rrset.type) self.assertIn(k, SAMPLES) sample_ttl = SAMPLES[k].get('ttl', None) if rrset.obj_attr_is_set('ttl') or sample_ttl is not None: self.assertEqual(rrset.ttl, sample_ttl) self.assertEqual(len(SAMPLES[k]['records']), len(rrset.records)) for r in rrset.records: self.assertIn(r.data, SAMPLES[k]['records']) self.assertEqual(len(SAMPLES), len(zone.recordsets)) self.assertEqual('example.com.', zone.name)
def test_parse_zone(self): zone_file = self.get_zonefile_fixture() dnspython_zone = dnszone.from_text( zone_file, # Don't relativize, otherwise we end up with '@' record names. relativize=False, # Dont check origin, we allow missing NS records (missing SOA # records are taken care of in _create_zone). check_origin=False) zone = dnsutils.from_dnspython_zone(dnspython_zone) for rrset in zone.recordsets: k = (rrset.name, rrset.type) self.assertIn(k, SAMPLES) sample_ttl = SAMPLES[k].get('ttl', None) if rrset.obj_attr_is_set('ttl') or sample_ttl is not None: self.assertEqual(sample_ttl, rrset.ttl) self.assertEqual(len(rrset.records), len(SAMPLES[k]['records'])) for record in rrset.records: self.assertIn(record.data, SAMPLES[k]['records']) self.assertEqual(len(SAMPLES), len(zone.recordsets)) self.assertEqual('example.com.', zone.name)
def _post_zonefile(self, request, response, context): """Import Zone""" try: dnspython_zone = dnszone.from_text( request.body, # Don't relativize, otherwise we end up with '@' record names. relativize=False, # Dont check origin, we allow missing NS records (missing SOA # records are taken care of in _create_zone). check_origin=False) domain = dnsutils.from_dnspython_zone(dnspython_zone) for rrset in domain.recordsets: if rrset.type in ('NS', 'SOA'): domain.recordsets.remove(rrset) except dnszone.UnknownOrigin: raise exceptions.BadRequest('The $ORIGIN statement is required and' ' must be the first statement in the' ' zonefile.') except dnsexception.SyntaxError: raise exceptions.BadRequest('Malformed zonefile.') zone = self.central_api.create_domain(context, domain) if zone['status'] == 'PENDING': response.status_int = 202 else: response.status_int = 201 response.headers['Location'] = self._view._get_resource_href(request, zone) return self._view.show(context, request, zone)
def _post_zonefile(self, request, response, context): """Import Zone""" try: dnspython_zone = dnszone.from_text( request.body, # Don't relativize, otherwise we end up with '@' record names. relativize=False, # Dont check origin, we allow missing NS records (missing SOA # records are taken care of in _create_zone). check_origin=False) domain = dnsutils.from_dnspython_zone(dnspython_zone) domain.type = 'PRIMARY' for rrset in list(domain.recordsets): if rrset.type in ('NS', 'SOA'): domain.recordsets.remove(rrset) except dnszone.UnknownOrigin: raise exceptions.BadRequest('The $ORIGIN statement is required and' ' must be the first statement in the' ' zonefile.') except dnsexception.SyntaxError: raise exceptions.BadRequest('Malformed zonefile.') zone = self.central_api.create_domain(context, domain) if zone['status'] == 'PENDING': response.status_int = 202 else: response.status_int = 201 response.headers['Location'] = self._view._get_resource_href( request, zone) return self._view.show(context, request, zone)
def test_from_dnspython_zone(self): zone_file = self.get_zonefile_fixture() dnspython_zone = dnszone.from_text(zone_file, relativize=False, check_origin=False) zone = dnsutils.from_dnspython_zone(dnspython_zone) self.assertIsInstance(zone, objects.zone.Zone)
def post_all(self): request = pecan.request response = pecan.response context = pecan.request.environ['context'] policy.check('zone_import', context) if request.content_type != 'text/dns': raise exceptions.UnsupportedContentType( 'Content-type must be text/dns') try: dnspython_zone = dnszone.from_text( request.body, # Don't relativize, otherwise we end up with '@' record names. relativize=False, # Dont check origin, we allow missing NS records (missing SOA # records are taken care of in _create_zone). check_origin=False) domain = dnsutils.from_dnspython_zone(dnspython_zone) domain.type = 'PRIMARY' for rrset in list(domain.recordsets): if rrset.type in ('NS', 'SOA'): domain.recordsets.remove(rrset) except dnszone.UnknownOrigin: raise exceptions.BadRequest('The $ORIGIN statement is required and' ' must be the first statement in the' ' zonefile.') except dnsexception.SyntaxError: raise exceptions.BadRequest('Malformed zonefile.') zone = self.central_api.create_domain(context, domain) if zone['status'] == 'PENDING': response.status_int = 202 else: response.status_int = 201 zone = DesignateAdapter.render('API_v2', zone, request=request) zone['links']['self'] = '%s/%s/%s' % (self.BASE_URI, 'v2/zones', zone['id']) response.headers['Location'] = zone['links']['self'] return zone
def post_all(self): request = pecan.request response = pecan.response context = pecan.request.environ['context'] policy.check('zone_import', context) if request.content_type != 'text/dns': raise exceptions.UnsupportedContentType( 'Content-type must be text/dns') try: dnspython_zone = dnszone.from_text( request.body, # Don't relativize, otherwise we end up with '@' record names. relativize=False, # Dont check origin, we allow missing NS records (missing SOA # records are taken care of in _create_zone). check_origin=False) domain = dnsutils.from_dnspython_zone(dnspython_zone) domain.type = 'PRIMARY' for rrset in list(domain.recordsets): if rrset.type in ('NS', 'SOA'): domain.recordsets.remove(rrset) except dnszone.UnknownOrigin: raise exceptions.BadRequest('The $ORIGIN statement is required and' ' must be the first statement in the' ' zonefile.') except dnsexception.SyntaxError: raise exceptions.BadRequest('Malformed zonefile.') zone = self.central_api.create_domain(context, domain) if zone['status'] == 'PENDING': response.status_int = 202 else: response.status_int = 201 zone = DesignateAdapter.render('API_v2', zone, request=request) zone['links']['self'] = '%s/%s/%s' % ( self.BASE_URI, 'v2/zones', zone['id']) response.headers['Location'] = zone['links']['self'] return zone
def zone_sync(self, context, zone, servers=None): servers = servers or zone.masters servers = servers.to_list() timeout = cfg.CONF["service:mdns"].xfr_timeout try: dnspython_zone = dnsutils.do_axfr(zone.name, servers, timeout=timeout) except exceptions.XFRFailure as e: LOG.warning(e) return zone.update(dnsutils.from_dnspython_zone(dnspython_zone)) zone.transferred_at = timeutils.utcnow() self.central_api.update_zone(context, zone, increment_serial=False)
def domain_sync(self, context, domain, servers=None): servers = servers or domain.masters servers = dnsutils.expand_servers(servers) timeout = cfg.CONF["service:mdns"].xfr_timeout try: dnspython_zone = dnsutils.do_axfr(domain.name, servers, timeout=timeout) except exceptions.XFRFailure as e: LOG.warning(e.message) return zone = dnsutils.from_dnspython_zone(dnspython_zone) domain.update(zone) domain.transferred_at = timeutils.utcnow() self.central_api.update_domain(context, domain, increment_serial=False)
def zone_sync(self, context, zone, servers=None): start_time = time.time() try: servers = servers or zone.masters servers = servers.to_list() timeout = cfg.CONF["service:mdns"].xfr_timeout try: dnspython_zone = dnsutils.do_axfr(zone.name, servers, timeout=timeout) except exceptions.XFRFailure as e: LOG.warning(e) return zone.update(dnsutils.from_dnspython_zone(dnspython_zone)) zone.transferred_at = timeutils.utcnow() zone.obj_reset_changes(["name"]) self.central_api.update_zone(context, zone, increment_serial=False) finally: metrics.timing('mdns.xfr.zone_sync', time.time() - start_time)