net-dnsserver/dns/resolver.py

73 lines
2.1 KiB
Python

#!/usr/bin/env python2
""" DNS Resolver
This module contains a class for resolving hostnames. You will have to implement
things in this module. This resolver will be both used by the DNS client and the
DNS server, but with a different list of servers.
"""
import socket
from dns.classes import Class
from dns.types import Type
import dns.cache
import dns.message
import dns.rcodes
class Resolver(object):
""" DNS resolver """
def __init__(self, caching, ttl):
""" Initialize the resolver
Args:
caching (bool): caching is enabled if True
ttl (int): ttl of cache entries (if > 0)
"""
self.caching = caching
self.ttl = ttl
def gethostbyname(self, hostname):
""" Translate a host name to IPv4 address.
Currently this method contains an example. You will have to replace
this example with example with the algorithm described in section
5.3.3 in RFC 1034.
Args:
hostname (str): the hostname to resolve
Returns:
(str, [str], [str]): (hostname, aliaslist, ipaddrlist)
"""
timeout = 2
sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
sock.settimeout(timeout)
# Create and send query
question = dns.message.Question(hostname, Type.A, Class.IN)
header = dns.message.Header(9001, 0, 1, 0, 0, 0)
header.qr = 0
header.opcode = 0
header.rd = 1
query = dns.message.Message(header, [question])
sock.sendto(query.to_bytes(), ("8.8.8.8", 53))
# Receive response
data = sock.recv(512)
response = dns.message.Message.from_bytes(data)
# Get data
aliases = []
for additional in response.additionals:
if additional.type_ == Type.CNAME:
aliases.append(additional.rdata.data)
addresses = []
for answer in response.answers:
if answer.type_ == Type.A:
addresses.append(answer.rdata.data)
return hostname, aliases, addresses