kimbo [Thu, 7 May 2020 14:27:00 +0000 (08:27 -0600)]
make dnspython installable with pip
I tried installing dnspython from the master branch and it did not work.
The error I got was
"poetry.masonry.utils.module.ModuleOrPackageNotFound: No file/folder
found for package dnspython".
Turns out there have been some changes made to pip involving the build
system (see https://www.python.org/dev/peps/pep-0517).
Basically pip is using poetry to install your package.
Poetry has some requirements about how you structure your project (see
https://python-poetry.org/docs/basic-usage/#project-setup and
https://python-poetry.org/docs/pyproject/#packages).
This change allows you to install dnspython without running into that
particular issue.
This zone was copied from a zone file in BIND long ago. BIND contains
both sample zone files and a script to generate sample zone files, but
the committed files appear to have been generated by a broken version of
the script.
This updates the TXT records to what the script would have generated,
which is far more complete.
Bob Halley [Mon, 4 May 2020 15:00:33 +0000 (08:00 -0700)]
Grealy simplify our getaddrinfo() implementation by calling the
system's version when we have an address literal for the host. This
also avoids infinite loops as dns.query.* needs to call getaddrinfo()
to handle scoping correctly.
Bob Halley [Mon, 4 May 2020 14:17:11 +0000 (07:17 -0700)]
In cases where we care that something is just an IPv4 or IPv6 address,
without any extras like IPv6 scope, explicitly use dns.ipv4 and dns.ipv6
instead of dns.inet. This will let us be tolerant of scopes in other
cases (e.g. ordinary network connections).
Simplify code using try/finally to use context managers.
In some cases, contextlib.ExitStack() is used; this could probably be
further simplified to use contextlib.nullcontext() once Python 3.7+ is a
requirement.
This changes the internal implementation from a list to an ordered
dictionary (dict or collections.OrderedDict, depending on Python
version). This is possible now that Rdata are immutable.
Now that Rdata instances are immutable, there needs to be a way to make
a new Rdata based on an existing one. replace() creates a clone of the
current Rdata, overriding fields with the specified parameters.
When we find a class-independent type, cache it for both class ANY and
the requested type, to avoid an extra dict lookup the next time. If we
don't find anything, cache GenericRdata, to avoid extra module loads the
next time.
This replaces the module cache with a class cache, so that the getattr()
call to retrieve the class happens only when a new type module is
loaded, not in the common case. This also allows avoiding the calls to
dns.rdataclass.to_text() and dns.rdatatype.to_text() in the common case.
Previously, repr() of rdataset/rrset looked like this:
<DNS IN A rdataset>
<DNS IN TXT rdataset>
<DNS IN RRSIG rdataset>
<DNS example. IN A RRset>
<DNS example. IN TXT RRset>
<DNS example. IN RRSIG(NSEC) RRset>
With this patch, it they look like:
<DNS IN A rdataset: [<1.2.3.4>, <5.6.7.8>]>
<DNS IN TXT rdataset: [<"foo" "bar">, <"baz">]>
<DNS IN RRSIG(NSEC) rdataset: [<NSEC 1 3 3600 2020010100000020030101000000 2143 foo MxFcby9k/yvedMfQgKzhH5er0Mu/vILz 45IkskceFGgiWC...>]>
<DNS example. IN A RRset: [<1.2.3.4>, <5.6.7.8>]>
<DNS example. IN TXT RRset: [<"foo" "bar">, <"baz">]>
<DNS example. IN RRSIG(NSEC) RRset: [<NSEC 1 3 3600 2020010100000020030101000000 2143 foo MxFcby9k/yvedMfQgKzhH5er0Mu/vILz 45IkskceFGgiWC...>]>
Note that each rdata is truncated to 100 characters.
Brian Wellington [Tue, 31 Mar 2020 20:45:20 +0000 (13:45 -0700)]
Remove dns.rdata.choose_relativity().
This method changes rdata in place, so prevents rdata from becoming
immutable. There are no in-tree users, and if there are out of tree
users, they are rate and hard to find.
Brian Wellington [Fri, 20 Mar 2020 20:58:02 +0000 (13:58 -0700)]
zone.to_text() should return a string.
As part of the Python 3 conversion, the result of dns.zone.to_text()
changed from str to bytes. This was likely unintentional, as a method
with text in its name should be returning text.
Brian Wellington [Wed, 18 Mar 2020 23:44:09 +0000 (16:44 -0700)]
Add relativize_to to from_text().
When calling from_text, the zone code needs to apply the current origin
(which may or may not be the zone origin, if sub-zone $ORIGIN statements
are present), and may also want to relativize the contents to the zone
origin.
Previously, this was done by explicitly reading records as absolute, and
then relativizing them laster. With this change, the work is moved to
the tokenizer.
This gets rid of the remaining internal uses of
dns.rdata.choose_relativity(), which prevents rdata from being
immutable.
Brian Wellington [Wed, 18 Mar 2020 21:56:58 +0000 (14:56 -0700)]
Remove choose_relativity() from zone.from_xfr()
The comment states that relativize must be consistent between
dns.query.xfr() and dns.zone.from_xfr(), and the code fails if they're
not (if check_origin is True, at least). This means that the rdata is
already correctly relativized (or not).
This also adds a test of creating zones from xfrs, both relativized and
not.