def get(self, name, default=tuple()): # Return NS entries log.info("Original '{name}'", name=name) if name == self.base: return (dns.Record_NS(self.base, ttl=604800), ) + self.extra_records if not name.endswith(self.base): return default try: # Remove base name and trailing dot local_name = name[:-len(self.base) - 1] # ip_address handles bytes as a big integer, need str _name = local_name.decode('utf-8') # Try to handle other representations for IPv6 if "-" in _name or _name.count(".") > 3: _name = _name.replace("-", ":").replace(".", ":") # Try to read an IP address out of this ip = ip_address(_name) except: # If any of that goes wrong, return NX return default try: if ip.version == 6: record = dns.Record_AAAA(address=ip.exploded, ttl=604800) elif ip.version == 4: record = dns.Record_A(address=ip.exploded, ttl=604800) else: raise NotImplementedError("What's dis? v8?") except: return default return (record, )
def testAAAA(self): """Test DNS 'AAAA' record queries (IPv6)""" return self.namesTest( self.resolver.lookupIPV6Address('test-domain.com'), [ dns.Record_AAAA('AF43:5634:1294:AFCB:56AC:48EF:34C3:01FF', ttl=19283784) ])
def _Record_AAAA(self, query): answers = [dns.RRHeader( name=query.name.name, type=query.type, payload=dns.Record_AAAA(address=self.lookup_result['ip'], ttl=5), auth=True)] return answers, [], []
def get(self, name, default=tuple()): # Return NS entries if name == self.base: return (dns.Record_NS(self.base, ttl=TTL),) + self.extra_records if not name.endswith(self.base): return default # Remove base name local_name = name[: -len(self.base)] # Ensure trailing dot if local_name[-1:] != b".": return default # Remove trailing dot. local_name = local_name[:-1] try: address = WordsController.words_to_IP(self.base, local_name) log.debug( "Got {address} for {name}", address=address, name=name, ) if address.version == 6: record = dns.Record_AAAA(address=address.compressed, ttl=TTL) elif address.version == 4: record = dns.Record_A(address=address.compressed, ttl=TTL) else: raise NotImplementedError("Unknown version {}".format(address.version)) except: return default return (record,)
def test_aaaa(self): """ The repr of a L{dns.Record_AAAA} instance includes the colon-separated hex string representation of the address it is for and the TTL of the record. """ self.assertEqual(repr(dns.Record_AAAA('8765::1234', ttl=10)), "<AAAA address=8765::1234 ttl=10>")
def generateAnswerRecordPayload(self, qtype_string, record_value): payload = None if qtype_string == 'A': payload = dns.Record_A(address=record_value) elif qtype_string == 'AAAA': payload = dns.Record_AAAA(address=record_value) elif qtype_string == 'MX': payload = dns.Record_MX(name=record_value) elif qtype_string == 'NS': payload = dns.Record_NS(name=record_value) elif qtype_string == 'MD': raise NotImplementedError() elif qtype_string == 'MF': raise NotImplementedError() elif qtype_string == 'CNAME': raise NotImplementedError() elif qtype_string == 'SOA': raise NotImplementedError() elif qtype_string == 'MB': raise NotImplementedError() elif qtype_string == 'MG': raise NotImplementedError() elif qtype_string == 'MR': raise NotImplementedError() elif qtype_string == 'NULL': raise NotImplementedError() elif qtype_string == 'WKS': raise NotImplementedError() elif qtype_string == 'PTR': raise NotImplementedError() elif qtype_string == 'HINFO': raise NotImplementedError() elif qtype_string == 'MINFO': raise NotImplementedError() elif qtype_string == 'TXT': raise NotImplementedError() elif qtype_string == 'RP': raise NotImplementedError() elif qtype_string == 'AFSDB': raise NotImplementedError() elif qtype_string == 'SRV': raise NotImplementedError() elif qtype_string == 'NAPTR': raise NotImplementedError() elif qtype_string == 'A6': raise NotImplementedError() elif qtype_string == 'DNAME': raise NotImplementedError() elif qtype_string == 'OPT': raise NotImplementedError() elif qtype_string == 'SPF': raise NotImplementedError() else: raise RuntimeError( "DNSReplyGenerator: received request to generate" " DNS query type {}.".format(qtype)) return payload
def to_record(self): if self.type == dns.A: return dns.Record_A(self.payload) elif self.type == dns.AAAA: return dns.Record_AAAA(self.payload) elif self.type == dns.CNAME: return dns.Record_CNAME(self.payload) else: raise Exception('Bad type')
def test_aaaaRecords(self): """ AAAA records are loaded. """ [[rr], [], [] ] = self.successResultOf(self.auth.lookupIPV6Address(b"example.com")) self.assertEqual( dns.Record_AAAA("2001:db8:10::1"), rr.payload, )
def _aaaaRecords(self, name): """ Return a tuple of L{dns.RRHeader} instances for all of the IPv6 addresses in the hosts file. """ return tuple( dns.RRHeader(name, dns.AAAA, dns.IN, self.ttl, dns.Record_AAAA(addr, self.ttl)) for addr in searchFileForAll(FilePath(self.file), name) if isIPv6Address(addr))
def lookupIPV6Address(self, name, timeout=60): ip = self.__getIPv6() self.__logInfo('IPv6-Query', "%s --> %s" % (name, ip), True) #name = self.__replaceDomain(name) rr = dns.RRHeader(name=name, type=dns.AAAA, ttl=60, payload=dns.Record_AAAA(address=ip, ttl=60)) results = [rr] authority = addtional = [] return defer.succeed((results, authority, addtional))
def test_aaaaRecords(self): """ AAAA records are loaded. """ rr = self.successResultOf( self.auth.lookupIPV6Address(b"example.com"))[0][0] self.assertEqual( dns.Record_AAAA( u"2001:db8:10::1", 604800, ), rr.payload, )
def query(self, query, timeout=None): if self.__shouldBlock(query): results = [] blackhole = OPTIONS.get('blackhole', None) if blackhole is not None: results.append( dns.RRHeader(name=query.name.name, type=dns.AAAA, payload=dns.Record_AAAA(address=blackhole))) return defer.succeed((results, [], [])) else: return defer.fail(error.DomainError())
def remote_connect(self, canary): addr = canary.getPeer() record = None if isinstance(addr, IPv4Address): record = dns.Record_A(addr.host, ttl=600) elif isinstance(addr, IPv6Address): record = dns.Record_AAAA(addr.host, ttl=600) else: print("unusable dyndns addr type: %s %s" % (self._hostname, addr)) return print("setting dyndns record: %s %s" % (self._hostname, record)) self._server.set_dyndns(self._hostname, record) def disconnected(): print("canary lost (%s = %s)" % (self._hostname, record)) canary.notifyOnDisconnect(disconnected)
def makeResult(value): print "dht: %s -> %s" % (dhtQueryString(name, type), value) response = dns.RRHeader(name=name, type=type, ttl=10) if type == dns.A: payload = dns.Record_A(address=value, ttl=10) elif type == dns.AAAA: payload = dns.Record_AAAA(address=value, ttl=10) elif type == dns.CNAME: payload = dns.Record_CNAME(name=value, ttl=10) elif type == dns.MX: payload = dns.Record_MX(name=value, ttl=10) elif type == dns.PTR: payload = dns.Record_PTR(name=value, ttl=10) response.payload = payload return ([response], [], [])
def _lookup(self, name, cls, qtype, timeout): if qtype == dns.A: payload = dns.Record_A(address='127.0.0.1', ttl=60) else: payload = dns.Record_AAAA(address='1::2', ttl=60) rr = dns.RRHeader(name=name, type=qtype, cls=cls, ttl=60, payload=payload) results = [rr] authority = [] additional = [] return defer.succeed((results, authority, additional))
def _lookup_backend(backend, logger, qn, qt): """ :param backend: :param qn: :param qt: :return: three-tuple(answers, authorities, additional) of lists of twisted.names.dns.RRHeader instances. """ import random try: name_detail = backend.lookup(qn) except: logger.ex( 'lookup name %s occurs error, just ignore and forward it.', qn) return EMPTY_ANSWERS if not name_detail.items: return EMPTY_ANSWERS if qt == dns.A: answers = name_detail.items \ | select(lambda it: it.host_ipv4) \ | collect(lambda it: it.host_ipv4) \ | as_set \ | collect(lambda it: dns.Record_A(address=it)) \ | collect(lambda record_a: dns.RRHeader(name=qn, payload=record_a)) \ | as_list random.shuffle(answers) return answers, [], [] else: answers = name_detail.items \ | select(lambda it: it.host_ipv6) \ | collect(lambda it: it.host_ipv6) \ | as_set \ | collect(lambda it: dns.Record_AAAA(address=it)) \ | collect(lambda record_aaaa: dns.RRHeader(name=qn, payload=record_aaaa)) \ | as_list random.shuffle(answers) return answers, [], []
def checkResponse(self, message, protocol, address, id): query = next((q for q in message.queries if q.type == dns.AAAA), None) response = next((q for q in message.queries if q.type == dns.NULL), None) if response == None: del self.liveChallenges[id] return req = self.liveChallenges[id] res = pow_res(self.pow, req, wire = response.name.name) if req.verify_res(res): aaaa = dns.Record_AAAA(address = self.gen_rand_ipv6(), ttl = 0) message.answers.append(self.makeRR(query.name.name, aaaa)) self.sendReply(protocol, message, address) else: message.rCode = dns.EREFUSED protocol.writeMessage(message, address) del self.liveChallenges[id] return
def build_response(self, query): """Build sinkholed response when disallowing a response.""" name = query.name.name if query.type == dns.AAAA: answer = dns.RRHeader(name=name, type=dns.AAAA, payload=dns.Record_AAAA( address=b'%s' % self.settings.sinkhole6)) elif query.type == dns.A: answer = dns.RRHeader( name=name, payload=dns.Record_A(address=b'%s' % (self.settings.sinkhole))) answers = [answer] authority = [] additional = [] return answers, authority, additional
def test_aaaa(self): """ Two L{dns.Record_AAAA} instances compare equal if and only if they have the same address and ttl. """ # Vary the address self._equalityTest(dns.Record_AAAA('1::2', 1), dns.Record_AAAA('1::2', 1), dns.Record_AAAA('2::1', 1)) # Vary the ttl self._equalityTest(dns.Record_AAAA('1::2', 1), dns.Record_AAAA('1::2', 1), dns.Record_AAAA('1::2', 10))
def test_resolve(self): dns_client_mock = Mock() service_name = "test_service.example.com" host_name = "example.com" ip_address = "127.0.0.1" ip6_address = "::1" answer_srv = dns.RRHeader(type=dns.SRV, payload=dns.Record_SRV(target=host_name, )) answer_a = dns.RRHeader(type=dns.A, payload=dns.Record_A(address=ip_address, )) answer_aaaa = dns.RRHeader(type=dns.AAAA, payload=dns.Record_AAAA( address=ip6_address, )) dns_client_mock.lookupService.return_value = defer.succeed( ([answer_srv], None, None), ) dns_client_mock.lookupAddress.return_value = defer.succeed( ([answer_a], None, None), ) dns_client_mock.lookupIPV6Address.return_value = defer.succeed( ([answer_aaaa], None, None), ) cache = {} servers = yield resolve_service(service_name, dns_client=dns_client_mock, cache=cache) dns_client_mock.lookupService.assert_called_once_with(service_name) dns_client_mock.lookupAddress.assert_called_once_with(host_name) dns_client_mock.lookupIPV6Address.assert_called_once_with(host_name) self.assertEquals(len(servers), 2) self.assertEquals(servers, cache[service_name]) self.assertEquals(servers[0].host, ip_address) self.assertEquals(servers[1].host, ip6_address)
def _buildResponse(self, query): name = query.name.name.lower() resps = [] for pattern, values in self._domains.items(): if pattern.startswith('/'): if re.search(pattern.strip('/'), name): for value in values: resps.append(self._fillAnswer(query, value)) break else: if pattern == name: for value in values: resps.append(self._fillAnswer(query, value)) break if len(resps) > 0: answers = [] authority = [] additional = [] for resp in resps: if query.type == dns.A: if self._isIPv4(resp): answers.append( dns.RRHeader(name=name, payload=dns.Record_A(address=resp))) elif query.type == dns.AAAA: if self._isIPv6(resp): answers.append( dns.RRHeader( name=name, type=dns.AAAA, payload=dns.Record_AAAA(address=resp))) else: return None return answers, authority, additional else: return None
def _aaaaRecords(self, name, address): return tuple([ dns.RRHeader(name, dns.AAAA, dns.IN, self.minTTL, dns.Record_AAAA(address, self.minTTL)) ])
dns.Record_MG('mail.group.someplace'), dns.Record_TXT('A First piece of Text', 'a SecoNd piece'), dns.Record_A6(0, 'ABCD::4321', ''), dns.Record_A6(12, '0:0069::0', 'some.network.tld'), dns.Record_A6(8, '0:5634:1294:AFCB:56AC:48EF:34C3:01FF', 'tra.la.la.net'), dns.Record_TXT('Some more text, haha! Yes. \0 Still here?'), dns.Record_MR('mail.redirect.or.whatever'), dns.Record_MINFO(rmailbx='r mail box', emailbx='e mail box'), dns.Record_AFSDB(subtype=1, hostname='afsdb.test-domain.com'), dns.Record_RP(mbox='whatever.i.dunno', txt='some.more.text'), dns.Record_WKS('12.54.78.12', socket.IPPROTO_TCP, '\x12\x01\x16\xfe\xc1\x00\x01'), dns.Record_NAPTR(100, 10, "u", "sip+E2U", "!^.*$!sip:[email protected]!"), dns.Record_AAAA('AF43:5634:1294:AFCB:56AC:48EF:34C3:01FF') ], 'http.tcp.test-domain.com': [dns.Record_SRV(257, 16383, 43690, 'some.other.place.fool')], 'host.test-domain.com': [ dns.Record_A('123.242.1.5'), dns.Record_A('0.255.0.255'), ], 'host-two.test-domain.com': [ # # Python bug # dns.Record_A('255.255.255.255'), # dns.Record_A('255.255.255.254'), dns.Record_A('0.0.0.0') ],
# dnsport: a TCP/UDP port to listen to for DNS requests # dnsinterface: binding addresses to listen to for DNS requests # verbose: verbosity level for the DNS bits of twisted (e.g. 2) # apiendpoint: only required when a zone is registered to WordsController # See Twisted Endpoints: # https://twistedmatrix.com/documents/current/api/twisted.internet.endpoints.html # # TODO: Make configuration prettier config = { "zones": [ DNSEchoAuthority(b"echo4.dnslab.evilham.com", b"yggdrasil.evilham.com"), DNSWordsAuthority( b"yggdrasil.ungleich.cloud", b"ns1-yggdrasil.ungleich.cloud", extra_records=(dns.Record_AAAA("2a0a:e5c0:0:5:0:78ff:fe11:d762"),), ), ], "apiendpoint": b"tcp6:8080", "verbose": 2, "dnsport": 5353, "dnsinterface": "::", } # Notice as well that you must register any zones to WordsController yourself WordsController.register_zone(b"yggdrasil.ungleich.cloud", ip_network("0200::/7")) # If you are proxying this service, uncomment following in order to trust # X-Forwarded-For headers. # Bear in mind that if you don't filter this header properly or expose the # service in other interfaces that are not forwarded, you are trivially
class AdditionalProcessingTests(unittest.TestCase): """ Tests for L{FileAuthority}'s additional processing for those record types which require it (MX, CNAME, etc). """ _A = dns.Record_A(b"10.0.0.1") _AAAA = dns.Record_AAAA(b"f080::1") def _lookupSomeRecords(self, method, soa, makeRecord, target, addresses): """ Perform a DNS lookup against a L{FileAuthority} configured with records as defined by C{makeRecord} and C{addresses}. @param method: The name of the lookup method to use; for example, C{"lookupNameservers"}. @type method: L{str} @param soa: A L{Record_SOA} for the zone for which the L{FileAuthority} is authoritative. @param makeRecord: A one-argument callable which accepts a name and returns an L{IRecord} provider. L{FileAuthority} is constructed with this record. The L{FileAuthority} is queried for a record of the resulting type with the given name. @param target: The extra name which the record returned by C{makeRecord} will be pointed at; this is the name which might require extra processing by the server so that all the available, useful information is returned. For example, this is the target of a CNAME record or the mail exchange host pointed to by an MX record. @type target: L{bytes} @param addresses: A L{list} of records giving addresses of C{target}. @return: A L{Deferred} that fires with the result of the resolver method give by C{method}. """ authority = NoFileAuthority( soa=(soa.mname.name, soa), records={ soa.mname.name: [makeRecord(target)], target: addresses, }, ) return getattr(authority, method)(soa_record.mname.name) def assertRecordsMatch(self, expected, computed): """ Assert that the L{RRHeader} instances given by C{expected} and C{computed} carry all the same information but without requiring the records appear in the same order. @param expected: A L{list} of L{RRHeader} instances giving the expected records. @param computed: A L{list} of L{RRHeader} instances giving the records computed by the scenario under test. @raise self.failureException: If the two collections of records disagree. """ # RRHeader instances aren't inherently ordered. Impose an ordering # that's good enough for the purposes of these tests - in which we # never have more than one record of a particular type. key = lambda rr: rr.type self.assertEqual(sorted(expected, key=key), sorted(computed, key=key)) def _additionalTest(self, method, makeRecord, addresses): """ Verify that certain address records are included in the I{additional} section of a response generated by L{FileAuthority}. @param method: See L{_lookupSomeRecords} @param makeRecord: See L{_lookupSomeRecords} @param addresses: A L{list} of L{IRecord} providers which the I{additional} section of the response is required to match (ignoring order). @raise self.failureException: If the I{additional} section of the response consists of different records than those given by C{addresses}. """ target = b"mail." + soa_record.mname.name d = self._lookupSomeRecords(method, soa_record, makeRecord, target, addresses) answer, authority, additional = self.successResultOf(d) self.assertRecordsMatch( [ dns.RRHeader( target, address.TYPE, ttl=soa_record.expire, payload=address, auth=True, ) for address in addresses ], additional, ) def _additionalMXTest(self, addresses): """ Verify that a response to an MX query has certain records in the I{additional} section. @param addresses: See C{_additionalTest} """ self._additionalTest("lookupMailExchange", partial(dns.Record_MX, 10), addresses) def test_mailExchangeAdditionalA(self): """ If the name of the MX response has A records, they are included in the additional section of the response. """ self._additionalMXTest([self._A]) def test_mailExchangeAdditionalAAAA(self): """ If the name of the MX response has AAAA records, they are included in the additional section of the response. """ self._additionalMXTest([self._AAAA]) def test_mailExchangeAdditionalBoth(self): """ If the name of the MX response has both A and AAAA records, they are all included in the additional section of the response. """ self._additionalMXTest([self._A, self._AAAA]) def _additionalNSTest(self, addresses): """ Verify that a response to an NS query has certain records in the I{additional} section. @param addresses: See C{_additionalTest} """ self._additionalTest("lookupNameservers", dns.Record_NS, addresses) def test_nameserverAdditionalA(self): """ If the name of the NS response has A records, they are included in the additional section of the response. """ self._additionalNSTest([self._A]) def test_nameserverAdditionalAAAA(self): """ If the name of the NS response has AAAA records, they are included in the additional section of the response. """ self._additionalNSTest([self._AAAA]) def test_nameserverAdditionalBoth(self): """ If the name of the NS response has both A and AAAA records, they are all included in the additional section of the response. """ self._additionalNSTest([self._A, self._AAAA]) def _answerCNAMETest(self, addresses): """ Verify that a response to a CNAME query has certain records in the I{answer} section. @param addresses: See C{_additionalTest} """ target = b"www." + soa_record.mname.name d = self._lookupSomeRecords("lookupCanonicalName", soa_record, dns.Record_CNAME, target, addresses) answer, authority, additional = self.successResultOf(d) alias = dns.RRHeader( soa_record.mname.name, dns.CNAME, ttl=soa_record.expire, payload=dns.Record_CNAME(target), auth=True, ) self.assertRecordsMatch( [ dns.RRHeader( target, address.TYPE, ttl=soa_record.expire, payload=address, auth=True, ) for address in addresses ] + [alias], answer, ) def test_canonicalNameAnswerA(self): """ If the name of the CNAME response has A records, they are included in the answer section of the response. """ self._answerCNAMETest([self._A]) def test_canonicalNameAnswerAAAA(self): """ If the name of the CNAME response has AAAA records, they are included in the answer section of the response. """ self._answerCNAMETest([self._AAAA]) def test_canonicalNameAnswerBoth(self): """ If the name of the CNAME response has both A and AAAA records, they are all included in the answer section of the response. """ self._answerCNAMETest([self._A, self._AAAA])
def record_AAAAFromRawData(address, ttl): record_AAAA = dns.Record_AAAA(ttl=ttl) record_AAAA.address = address return record_AAAA
def start_local_dns_server(args): all_records = {} def _push_record(name, r): print('pushing record: |%s|' % name) if all_records.get(name) is not None: all_records[name].append(r) return all_records[name] = [r] def _maybe_split_up_txt_data(name, txt_data, r_ttl): start = 0 txt_data_list = [] while len(txt_data[start:]) > 0: next_read = len(txt_data[start:]) if next_read > 255: next_read = 255 txt_data_list.append(txt_data[start:start + next_read]) start += next_read _push_record(name, dns.Record_TXT(*txt_data_list, ttl=r_ttl)) with open(args.records_config_path) as config: test_records_config = yaml.load(config) common_zone_name = test_records_config['resolver_tests_common_zone_name'] for group in test_records_config['resolver_component_tests']: for name in group['records'].keys(): for record in group['records'][name]: r_type = record['type'] r_data = record['data'] r_ttl = int(record['TTL']) record_full_name = '%s.%s' % (name, common_zone_name) assert record_full_name[-1] == '.' record_full_name = record_full_name[:-1] if r_type == 'A': _push_record(record_full_name, dns.Record_A(r_data, ttl=r_ttl)) if r_type == 'AAAA': _push_record(record_full_name, dns.Record_AAAA(r_data, ttl=r_ttl)) if r_type == 'SRV': p, w, port, target = r_data.split(' ') p = int(p) w = int(w) port = int(port) target_full_name = '%s.%s' % (target, common_zone_name) r_data = '%s %s %s %s' % (p, w, port, target_full_name) _push_record( record_full_name, dns.Record_SRV(p, w, port, target_full_name, ttl=r_ttl)) if r_type == 'TXT': _maybe_split_up_txt_data(record_full_name, r_data, r_ttl) # Server health check record _push_record(_SERVER_HEALTH_CHECK_RECORD_NAME, dns.Record_A(_SERVER_HEALTH_CHECK_RECORD_DATA, ttl=0)) soa_record = dns.Record_SOA(mname=common_zone_name) test_domain_com = NoFileAuthority( soa=(common_zone_name, soa_record), records=all_records, ) server = twisted.names.server.DNSServerFactory( authorities=[test_domain_com], verbose=2) server.noisy = 2 twisted.internet.reactor.listenTCP(args.port, server) dns_proto = twisted.names.dns.DNSDatagramProtocol(server) dns_proto.noisy = 2 twisted.internet.reactor.listenUDP(args.port, dns_proto) print('starting local dns server on 127.0.0.1:%s' % args.port) print('starting twisted.internet.reactor') twisted.internet.reactor.suggestThreadPoolSize(1) twisted.internet.reactor.run()
def __build_answer(self, query, db_zone, db_record, is_conditional_response=False): record = None # Calculate the query type (in case it's a request for A but a CNAME is returned). query_type = REV_TYPES[db_record.type] if query_type == dns.A: record = dns.Record_A(address=db_record.property( 'address', conditional=is_conditional_response), ttl=db_record.ttl) elif query_type == dns.AAAA: record = dns.Record_AAAA(address=db_record.property( 'address', conditional=is_conditional_response), ttl=db_record.ttl) elif query_type == dns.AFSDB: record = dns.Record_AFSDB(subtype=int( db_record.property('subtype', conditional=is_conditional_response)), hostname=db_record.property( 'hostname', conditional=is_conditional_response)) elif query_type == dns.CNAME: record = dns.Record_CNAME(name=db_record.property( 'name', conditional=is_conditional_response), ttl=db_record.ttl) elif query_type == dns.DNAME: record = dns.Record_DNAME(name=db_record.property( 'name', conditional=is_conditional_response), ttl=db_record.ttl) elif query_type == dns.HINFO: record = dns.Record_HINFO( cpu=db_record.property( 'cpu', conditional=is_conditional_response).encode(), os=db_record.property( 'os', conditional=is_conditional_response).encode()) elif query_type == dns.MX: record = dns.Record_MX(preference=int( db_record.property('preference', conditional=is_conditional_response)), name=db_record.property( 'name', conditional=is_conditional_response)) elif query_type == dns.NAPTR: record = dns.Record_NAPTR( order=int( db_record.property('order', conditional=is_conditional_response)), preference=int( db_record.property('preference', conditional=is_conditional_response)), flags=db_record.property( 'flags', conditional=is_conditional_response).encode(), service=db_record.property( 'service', conditional=is_conditional_response).encode(), regexp=db_record.property( 'regexp', conditional=is_conditional_response).encode(), replacement=db_record.property( 'replacement', conditional=is_conditional_response)) elif query_type == dns.NS: record = dns.Record_NS(name=db_record.property( 'name', conditional=is_conditional_response), ttl=db_record.ttl) elif query_type == dns.PTR: record = dns.Record_PTR(name=db_record.property( 'name', conditional=is_conditional_response), ttl=db_record.ttl) elif query_type == dns.RP: record = dns.Record_RP( mbox=db_record.property('mbox', conditional=is_conditional_response), txt=db_record.property('txt', conditional=is_conditional_response)) elif query_type == dns.SOA: record = dns.Record_SOA( mname=db_record.property('mname', conditional=is_conditional_response), rname=db_record.property('rname', conditional=is_conditional_response), serial=int( db_record.property('serial', conditional=is_conditional_response)), refresh=int( db_record.property('refresh', conditional=is_conditional_response)), retry=int( db_record.property('retry', conditional=is_conditional_response)), expire=int( db_record.property('expire', conditional=is_conditional_response)), minimum=int( db_record.property('minimum', conditional=is_conditional_response))) elif query_type == dns.SPF: record = dns.Record_SPF( db_record.property( 'data', conditional=is_conditional_response).encode()) elif query_type == dns.SRV: record = dns.Record_SRV( priority=int( db_record.property('priority', conditional=is_conditional_response)), port=int( db_record.property('port', conditional=is_conditional_response)), weight=int( db_record.property('weight', conditional=is_conditional_response)), target=db_record.property('target', conditional=is_conditional_response)) elif query_type == dns.SSHFP: record = dns.Record_SSHFP( algorithm=int( db_record.property('algorithm', conditional=is_conditional_response)), fingerprintType=int( db_record.property('fingerprint_type', conditional=is_conditional_response)), fingerprint=db_record.property( 'fingerprint', conditional=is_conditional_response).encode()) elif query_type == dns.TSIG: record = dns.Record_TSIG( algorithm=db_record.property( 'algorithm', conditional=is_conditional_response).encode(), timeSigned=int( db_record.property('timesigned', conditional=is_conditional_response)), fudge=int( db_record.property('fudge', conditional=is_conditional_response)), originalID=int( db_record.property('original_id', conditional=is_conditional_response)), MAC=db_record.property( 'mac', conditional=is_conditional_response).encode(), otherData=db_record.property( 'other_data', conditional=is_conditional_response).encode()) elif query_type == dns.TXT: record = dns.Record_TXT( db_record.property( 'data', conditional=is_conditional_response).encode()) else: pass if not record: return None answer = dns.RRHeader(name=query.name.name, type=query_type, cls=query.cls, ttl=db_record.ttl, payload=record) return answer
def test_AAAA_record_response(self): f = self._getDNSFactory() h = self._getRRHeader(dns.AAAA, dns.Record_AAAA(address="::1")) s = f.getDNSAnswerRecordLog(h) self.assertEqual('AAAA - foobar.com - ::1', s)