Bump dnspython from 2.2.1 to 2.3.0 (#1975)

* Bump dnspython from 2.2.1 to 2.3.0

Bumps [dnspython](https://github.com/rthalley/dnspython) from 2.2.1 to 2.3.0.
- [Release notes](https://github.com/rthalley/dnspython/releases)
- [Changelog](https://github.com/rthalley/dnspython/blob/master/doc/whatsnew.rst)
- [Commits](https://github.com/rthalley/dnspython/compare/v2.2.1...v2.3.0)

---
updated-dependencies:
- dependency-name: dnspython
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>

* Update dnspython==2.3.0

---------

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Co-authored-by: JonnyWong16 <9099342+JonnyWong16@users.noreply.github.com>

[skip ci]
This commit is contained in:
dependabot[bot] 2023-03-02 20:54:32 -08:00 committed by GitHub
parent 6910079330
commit 32c06a8b72
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
137 changed files with 7699 additions and 4277 deletions

View file

@ -17,6 +17,8 @@
"""DNS rdata."""
from typing import Any, Dict, Optional, Tuple, Union
from importlib import import_module
import base64
import binascii
@ -55,21 +57,22 @@ class NoRelativeRdataOrdering(dns.exception.DNSException):
"""
def _wordbreak(data, chunksize=_chunksize, separator=b' '):
def _wordbreak(data, chunksize=_chunksize, separator=b" "):
"""Break a binary string into chunks of chunksize characters separated by
a space.
"""
if not chunksize:
return data.decode()
return separator.join([data[i:i + chunksize]
for i
in range(0, len(data), chunksize)]).decode()
return separator.join(
[data[i : i + chunksize] for i in range(0, len(data), chunksize)]
).decode()
# pylint: disable=unused-argument
def _hexify(data, chunksize=_chunksize, separator=b' ', **kw):
def _hexify(data, chunksize=_chunksize, separator=b" ", **kw):
"""Convert a binary string into its hex encoding, broken up into chunks
of chunksize characters separated by a separator.
"""
@ -77,17 +80,19 @@ def _hexify(data, chunksize=_chunksize, separator=b' ', **kw):
return _wordbreak(binascii.hexlify(data), chunksize, separator)
def _base64ify(data, chunksize=_chunksize, separator=b' ', **kw):
def _base64ify(data, chunksize=_chunksize, separator=b" ", **kw):
"""Convert a binary string into its base64 encoding, broken up into chunks
of chunksize characters separated by a separator.
"""
return _wordbreak(base64.b64encode(data), chunksize, separator)
# pylint: enable=unused-argument
__escaped = b'"\\'
def _escapify(qstring):
"""Escape the characters in a quoted string which need it."""
@ -96,14 +101,14 @@ def _escapify(qstring):
if not isinstance(qstring, bytearray):
qstring = bytearray(qstring)
text = ''
text = ""
for c in qstring:
if c in __escaped:
text += '\\' + chr(c)
text += "\\" + chr(c)
elif c >= 0x20 and c < 0x7F:
text += chr(c)
else:
text += '\\%03d' % c
text += "\\%03d" % c
return text
@ -114,9 +119,10 @@ def _truncate_bitmap(what):
for i in range(len(what) - 1, -1, -1):
if what[i] != 0:
return what[0: i + 1]
return what[0 : i + 1]
return what[0:1]
# So we don't have to edit all the rdata classes...
_constify = dns.immutable.constify
@ -125,7 +131,7 @@ _constify = dns.immutable.constify
class Rdata:
"""Base class for all DNS rdata types."""
__slots__ = ['rdclass', 'rdtype', 'rdcomment']
__slots__ = ["rdclass", "rdtype", "rdcomment"]
def __init__(self, rdclass, rdtype):
"""Initialize an rdata.
@ -140,8 +146,9 @@ class Rdata:
self.rdcomment = None
def _get_all_slots(self):
return itertools.chain.from_iterable(getattr(cls, '__slots__', [])
for cls in self.__class__.__mro__)
return itertools.chain.from_iterable(
getattr(cls, "__slots__", []) for cls in self.__class__.__mro__
)
def __getstate__(self):
# We used to try to do a tuple of all slots here, but it
@ -160,12 +167,12 @@ class Rdata:
def __setstate__(self, state):
for slot, val in state.items():
object.__setattr__(self, slot, val)
if not hasattr(self, 'rdcomment'):
if not hasattr(self, "rdcomment"):
# Pickled rdata from 2.0.x might not have a rdcomment, so add
# it if needed.
object.__setattr__(self, 'rdcomment', None)
object.__setattr__(self, "rdcomment", None)
def covers(self):
def covers(self) -> dns.rdatatype.RdataType:
"""Return the type a Rdata covers.
DNS SIG/RRSIG rdatas apply to a specific type; this type is
@ -174,12 +181,12 @@ class Rdata:
creating rdatasets, allowing the rdataset to contain only RRSIGs
of a particular type, e.g. RRSIG(NS).
Returns an ``int``.
Returns a ``dns.rdatatype.RdataType``.
"""
return dns.rdatatype.NONE
def extended_rdatatype(self):
def extended_rdatatype(self) -> int:
"""Return a 32-bit type value, the least significant 16 bits of
which are the ordinary DNS type, and the upper 16 bits of which are
the "covered" type, if any.
@ -189,7 +196,12 @@ class Rdata:
return self.covers() << 16 | self.rdtype
def to_text(self, origin=None, relativize=True, **kw):
def to_text(
self,
origin: Optional[dns.name.Name] = None,
relativize: bool = True,
**kw: Dict[str, Any]
) -> str:
"""Convert an rdata to text format.
Returns a ``str``.
@ -197,11 +209,22 @@ class Rdata:
raise NotImplementedError # pragma: no cover
def _to_wire(self, file, compress=None, origin=None, canonicalize=False):
def _to_wire(
self,
file: Optional[Any],
compress: Optional[dns.name.CompressType] = None,
origin: Optional[dns.name.Name] = None,
canonicalize: bool = False,
) -> bytes:
raise NotImplementedError # pragma: no cover
def to_wire(self, file=None, compress=None, origin=None,
canonicalize=False):
def to_wire(
self,
file: Optional[Any] = None,
compress: Optional[dns.name.CompressType] = None,
origin: Optional[dns.name.Name] = None,
canonicalize: bool = False,
) -> bytes:
"""Convert an rdata to wire format.
Returns a ``bytes`` or ``None``.
@ -214,15 +237,18 @@ class Rdata:
self._to_wire(f, compress, origin, canonicalize)
return f.getvalue()
def to_generic(self, origin=None):
def to_generic(
self, origin: Optional[dns.name.Name] = None
) -> "dns.rdata.GenericRdata":
"""Creates a dns.rdata.GenericRdata equivalent of this rdata.
Returns a ``dns.rdata.GenericRdata``.
"""
return dns.rdata.GenericRdata(self.rdclass, self.rdtype,
self.to_wire(origin=origin))
return dns.rdata.GenericRdata(
self.rdclass, self.rdtype, self.to_wire(origin=origin)
)
def to_digestable(self, origin=None):
def to_digestable(self, origin: Optional[dns.name.Name] = None) -> bytes:
"""Convert rdata to a format suitable for digesting in hashes. This
is also the DNSSEC canonical form.
@ -234,12 +260,19 @@ class Rdata:
def __repr__(self):
covers = self.covers()
if covers == dns.rdatatype.NONE:
ctext = ''
ctext = ""
else:
ctext = '(' + dns.rdatatype.to_text(covers) + ')'
return '<DNS ' + dns.rdataclass.to_text(self.rdclass) + ' ' + \
dns.rdatatype.to_text(self.rdtype) + ctext + ' rdata: ' + \
str(self) + '>'
ctext = "(" + dns.rdatatype.to_text(covers) + ")"
return (
"<DNS "
+ dns.rdataclass.to_text(self.rdclass)
+ " "
+ dns.rdatatype.to_text(self.rdtype)
+ ctext
+ " rdata: "
+ str(self)
+ ">"
)
def __str__(self):
return self.to_text()
@ -320,27 +353,39 @@ class Rdata:
return not self.__eq__(other)
def __lt__(self, other):
if not isinstance(other, Rdata) or \
self.rdclass != other.rdclass or self.rdtype != other.rdtype:
if (
not isinstance(other, Rdata)
or self.rdclass != other.rdclass
or self.rdtype != other.rdtype
):
return NotImplemented
return self._cmp(other) < 0
def __le__(self, other):
if not isinstance(other, Rdata) or \
self.rdclass != other.rdclass or self.rdtype != other.rdtype:
if (
not isinstance(other, Rdata)
or self.rdclass != other.rdclass
or self.rdtype != other.rdtype
):
return NotImplemented
return self._cmp(other) <= 0
def __ge__(self, other):
if not isinstance(other, Rdata) or \
self.rdclass != other.rdclass or self.rdtype != other.rdtype:
if (
not isinstance(other, Rdata)
or self.rdclass != other.rdclass
or self.rdtype != other.rdtype
):
return NotImplemented
return self._cmp(other) >= 0
def __gt__(self, other):
if not isinstance(other, Rdata) or \
self.rdclass != other.rdclass or self.rdtype != other.rdtype:
if (
not isinstance(other, Rdata)
or self.rdclass != other.rdclass
or self.rdtype != other.rdtype
):
return NotImplemented
return self._cmp(other) > 0
@ -348,15 +393,28 @@ class Rdata:
return hash(self.to_digestable(dns.name.root))
@classmethod
def from_text(cls, rdclass, rdtype, tok, origin=None, relativize=True,
relativize_to=None):
def from_text(
cls,
rdclass: dns.rdataclass.RdataClass,
rdtype: dns.rdatatype.RdataType,
tok: dns.tokenizer.Tokenizer,
origin: Optional[dns.name.Name] = None,
relativize: bool = True,
relativize_to: Optional[dns.name.Name] = None,
) -> "Rdata":
raise NotImplementedError # pragma: no cover
@classmethod
def from_wire_parser(cls, rdclass, rdtype, parser, origin=None):
def from_wire_parser(
cls,
rdclass: dns.rdataclass.RdataClass,
rdtype: dns.rdatatype.RdataType,
parser: dns.wire.Parser,
origin: Optional[dns.name.Name] = None,
) -> "Rdata":
raise NotImplementedError # pragma: no cover
def replace(self, **kwargs):
def replace(self, **kwargs: Any) -> "Rdata":
"""
Create a new Rdata instance based on the instance replace was
invoked on. It is possible to pass different parameters to
@ -369,19 +427,25 @@ class Rdata:
"""
# Get the constructor parameters.
parameters = inspect.signature(self.__init__).parameters
parameters = inspect.signature(self.__init__).parameters # type: ignore
# Ensure that all of the arguments correspond to valid fields.
# Don't allow rdclass or rdtype to be changed, though.
for key in kwargs:
if key == 'rdcomment':
if key == "rdcomment":
continue
if key not in parameters:
raise AttributeError("'{}' object has no attribute '{}'"
.format(self.__class__.__name__, key))
if key in ('rdclass', 'rdtype'):
raise AttributeError("Cannot overwrite '{}' attribute '{}'"
.format(self.__class__.__name__, key))
raise AttributeError(
"'{}' object has no attribute '{}'".format(
self.__class__.__name__, key
)
)
if key in ("rdclass", "rdtype"):
raise AttributeError(
"Cannot overwrite '{}' attribute '{}'".format(
self.__class__.__name__, key
)
)
# Construct the parameter list. For each field, use the value in
# kwargs if present, and the current value otherwise.
@ -391,9 +455,9 @@ class Rdata:
rd = self.__class__(*args)
# The comment is not set in the constructor, so give it special
# handling.
rdcomment = kwargs.get('rdcomment', self.rdcomment)
rdcomment = kwargs.get("rdcomment", self.rdcomment)
if rdcomment is not None:
object.__setattr__(rd, 'rdcomment', rdcomment)
object.__setattr__(rd, "rdcomment", rdcomment)
return rd
# Type checking and conversion helpers. These are class methods as
@ -408,18 +472,26 @@ class Rdata:
return dns.rdatatype.RdataType.make(value)
@classmethod
def _as_bytes(cls, value, encode=False, max_length=None, empty_ok=True):
def _as_bytes(
cls,
value: Any,
encode: bool = False,
max_length: Optional[int] = None,
empty_ok: bool = True,
) -> bytes:
if encode and isinstance(value, str):
value = value.encode()
bvalue = value.encode()
elif isinstance(value, bytearray):
value = bytes(value)
elif not isinstance(value, bytes):
raise ValueError('not bytes')
if max_length is not None and len(value) > max_length:
raise ValueError('too long')
if not empty_ok and len(value) == 0:
raise ValueError('empty bytes not allowed')
return value
bvalue = bytes(value)
elif isinstance(value, bytes):
bvalue = value
else:
raise ValueError("not bytes")
if max_length is not None and len(bvalue) > max_length:
raise ValueError("too long")
if not empty_ok and len(bvalue) == 0:
raise ValueError("empty bytes not allowed")
return bvalue
@classmethod
def _as_name(cls, value):
@ -429,49 +501,49 @@ class Rdata:
if isinstance(value, str):
return dns.name.from_text(value)
elif not isinstance(value, dns.name.Name):
raise ValueError('not a name')
raise ValueError("not a name")
return value
@classmethod
def _as_uint8(cls, value):
if not isinstance(value, int):
raise ValueError('not an integer')
raise ValueError("not an integer")
if value < 0 or value > 255:
raise ValueError('not a uint8')
raise ValueError("not a uint8")
return value
@classmethod
def _as_uint16(cls, value):
if not isinstance(value, int):
raise ValueError('not an integer')
raise ValueError("not an integer")
if value < 0 or value > 65535:
raise ValueError('not a uint16')
raise ValueError("not a uint16")
return value
@classmethod
def _as_uint32(cls, value):
if not isinstance(value, int):
raise ValueError('not an integer')
raise ValueError("not an integer")
if value < 0 or value > 4294967295:
raise ValueError('not a uint32')
raise ValueError("not a uint32")
return value
@classmethod
def _as_uint48(cls, value):
if not isinstance(value, int):
raise ValueError('not an integer')
raise ValueError("not an integer")
if value < 0 or value > 281474976710655:
raise ValueError('not a uint48')
raise ValueError("not a uint48")
return value
@classmethod
def _as_int(cls, value, low=None, high=None):
if not isinstance(value, int):
raise ValueError('not an integer')
raise ValueError("not an integer")
if low is not None and value < low:
raise ValueError('value too small')
raise ValueError("value too small")
if high is not None and value > high:
raise ValueError('value too large')
raise ValueError("value too large")
return value
@classmethod
@ -483,7 +555,7 @@ class Rdata:
elif isinstance(value, bytes):
return dns.ipv4.inet_ntoa(value)
else:
raise ValueError('not an IPv4 address')
raise ValueError("not an IPv4 address")
@classmethod
def _as_ipv6_address(cls, value):
@ -494,14 +566,14 @@ class Rdata:
elif isinstance(value, bytes):
return dns.ipv6.inet_ntoa(value)
else:
raise ValueError('not an IPv6 address')
raise ValueError("not an IPv6 address")
@classmethod
def _as_bool(cls, value):
if isinstance(value, bool):
return value
else:
raise ValueError('not a boolean')
raise ValueError("not a boolean")
@classmethod
def _as_ttl(cls, value):
@ -510,7 +582,7 @@ class Rdata:
elif isinstance(value, str):
return dns.ttl.from_text(value)
else:
raise ValueError('not a TTL')
raise ValueError("not a TTL")
@classmethod
def _as_tuple(cls, value, as_value):
@ -532,6 +604,7 @@ class Rdata:
return items
@dns.immutable.immutable
class GenericRdata(Rdata):
"""Generic Rdata Class
@ -540,28 +613,32 @@ class GenericRdata(Rdata):
implementation. It implements the DNS "unknown RRs" scheme.
"""
__slots__ = ['data']
__slots__ = ["data"]
def __init__(self, rdclass, rdtype, data):
super().__init__(rdclass, rdtype)
object.__setattr__(self, 'data', data)
self.data = data
def to_text(self, origin=None, relativize=True, **kw):
return r'\# %d ' % len(self.data) + _hexify(self.data, **kw)
def to_text(
self,
origin: Optional[dns.name.Name] = None,
relativize: bool = True,
**kw: Dict[str, Any]
) -> str:
return r"\# %d " % len(self.data) + _hexify(self.data, **kw)
@classmethod
def from_text(cls, rdclass, rdtype, tok, origin=None, relativize=True,
relativize_to=None):
def from_text(
cls, rdclass, rdtype, tok, origin=None, relativize=True, relativize_to=None
):
token = tok.get()
if not token.is_identifier() or token.value != r'\#':
raise dns.exception.SyntaxError(
r'generic rdata does not start with \#')
if not token.is_identifier() or token.value != r"\#":
raise dns.exception.SyntaxError(r"generic rdata does not start with \#")
length = tok.get_int()
hex = tok.concatenate_remaining_identifiers(True).encode()
data = binascii.unhexlify(hex)
if len(data) != length:
raise dns.exception.SyntaxError(
'generic rdata hex data has wrong length')
raise dns.exception.SyntaxError("generic rdata hex data has wrong length")
return cls(rdclass, rdtype, data)
def _to_wire(self, file, compress=None, origin=None, canonicalize=False):
@ -571,8 +648,12 @@ class GenericRdata(Rdata):
def from_wire_parser(cls, rdclass, rdtype, parser, origin=None):
return cls(rdclass, rdtype, parser.get_remaining())
_rdata_classes = {}
_module_prefix = 'dns.rdtypes'
_rdata_classes: Dict[
Tuple[dns.rdataclass.RdataClass, dns.rdatatype.RdataType], Any
] = {}
_module_prefix = "dns.rdtypes"
def get_rdata_class(rdclass, rdtype):
cls = _rdata_classes.get((rdclass, rdtype))
@ -581,16 +662,16 @@ def get_rdata_class(rdclass, rdtype):
if not cls:
rdclass_text = dns.rdataclass.to_text(rdclass)
rdtype_text = dns.rdatatype.to_text(rdtype)
rdtype_text = rdtype_text.replace('-', '_')
rdtype_text = rdtype_text.replace("-", "_")
try:
mod = import_module('.'.join([_module_prefix,
rdclass_text, rdtype_text]))
mod = import_module(
".".join([_module_prefix, rdclass_text, rdtype_text])
)
cls = getattr(mod, rdtype_text)
_rdata_classes[(rdclass, rdtype)] = cls
except ImportError:
try:
mod = import_module('.'.join([_module_prefix,
'ANY', rdtype_text]))
mod = import_module(".".join([_module_prefix, "ANY", rdtype_text]))
cls = getattr(mod, rdtype_text)
_rdata_classes[(dns.rdataclass.ANY, rdtype)] = cls
_rdata_classes[(rdclass, rdtype)] = cls
@ -602,8 +683,15 @@ def get_rdata_class(rdclass, rdtype):
return cls
def from_text(rdclass, rdtype, tok, origin=None, relativize=True,
relativize_to=None, idna_codec=None):
def from_text(
rdclass: Union[dns.rdataclass.RdataClass, str],
rdtype: Union[dns.rdatatype.RdataType, str],
tok: Union[dns.tokenizer.Tokenizer, str],
origin: Optional[dns.name.Name] = None,
relativize: bool = True,
relativize_to: Optional[dns.name.Name] = None,
idna_codec: Optional[dns.name.IDNACodec] = None,
) -> Rdata:
"""Build an rdata object from text format.
This function attempts to dynamically load a class which
@ -617,9 +705,9 @@ def from_text(rdclass, rdtype, tok, origin=None, relativize=True,
If *tok* is a ``str``, then a tokenizer is created and the string
is used as its input.
*rdclass*, an ``int``, the rdataclass.
*rdclass*, a ``dns.rdataclass.RdataClass`` or ``str``, the rdataclass.
*rdtype*, an ``int``, the rdatatype.
*rdtype*, a ``dns.rdatatype.RdataType`` or ``str``, the rdatatype.
*tok*, a ``dns.tokenizer.Tokenizer`` or a ``str``.
@ -651,17 +739,18 @@ def from_text(rdclass, rdtype, tok, origin=None, relativize=True,
# peek at first token
token = tok.get()
tok.unget(token)
if token.is_identifier() and \
token.value == r'\#':
if token.is_identifier() and token.value == r"\#":
#
# Known type using the generic syntax. Extract the
# wire form from the generic syntax, and then run
# from_wire on it.
#
grdata = GenericRdata.from_text(rdclass, rdtype, tok, origin,
relativize, relativize_to)
rdata = from_wire(rdclass, rdtype, grdata.data, 0,
len(grdata.data), origin)
grdata = GenericRdata.from_text(
rdclass, rdtype, tok, origin, relativize, relativize_to
)
rdata = from_wire(
rdclass, rdtype, grdata.data, 0, len(grdata.data), origin
)
#
# If this comparison isn't equal, then there must have been
# compressed names in the wire format, which is an error,
@ -669,19 +758,27 @@ def from_text(rdclass, rdtype, tok, origin=None, relativize=True,
#
rwire = rdata.to_wire()
if rwire != grdata.data:
raise dns.exception.SyntaxError('compressed data in '
'generic syntax form '
'of known rdatatype')
raise dns.exception.SyntaxError(
"compressed data in "
"generic syntax form "
"of known rdatatype"
)
if rdata is None:
rdata = cls.from_text(rdclass, rdtype, tok, origin, relativize,
relativize_to)
rdata = cls.from_text(
rdclass, rdtype, tok, origin, relativize, relativize_to
)
token = tok.get_eol_as_token()
if token.comment is not None:
object.__setattr__(rdata, 'rdcomment', token.comment)
object.__setattr__(rdata, "rdcomment", token.comment)
return rdata
def from_wire_parser(rdclass, rdtype, parser, origin=None):
def from_wire_parser(
rdclass: Union[dns.rdataclass.RdataClass, str],
rdtype: Union[dns.rdatatype.RdataType, str],
parser: dns.wire.Parser,
origin: Optional[dns.name.Name] = None,
) -> Rdata:
"""Build an rdata object from wire format
This function attempts to dynamically load a class which
@ -692,9 +789,9 @@ def from_wire_parser(rdclass, rdtype, parser, origin=None):
Once a class is chosen, its from_wire() class method is called
with the parameters to this function.
*rdclass*, an ``int``, the rdataclass.
*rdclass*, a ``dns.rdataclass.RdataClass`` or ``str``, the rdataclass.
*rdtype*, an ``int``, the rdatatype.
*rdtype*, a ``dns.rdatatype.RdataType`` or ``str``, the rdatatype.
*parser*, a ``dns.wire.Parser``, the parser, which should be
restricted to the rdata length.
@ -712,7 +809,14 @@ def from_wire_parser(rdclass, rdtype, parser, origin=None):
return cls.from_wire_parser(rdclass, rdtype, parser, origin)
def from_wire(rdclass, rdtype, wire, current, rdlen, origin=None):
def from_wire(
rdclass: Union[dns.rdataclass.RdataClass, str],
rdtype: Union[dns.rdatatype.RdataType, str],
wire: bytes,
current: int,
rdlen: int,
origin: Optional[dns.name.Name] = None,
) -> Rdata:
"""Build an rdata object from wire format
This function attempts to dynamically load a class which
@ -746,13 +850,21 @@ def from_wire(rdclass, rdtype, wire, current, rdlen, origin=None):
class RdatatypeExists(dns.exception.DNSException):
"""DNS rdatatype already exists."""
supp_kwargs = {'rdclass', 'rdtype'}
fmt = "The rdata type with class {rdclass:d} and rdtype {rdtype:d} " + \
"already exists."
supp_kwargs = {"rdclass", "rdtype"}
fmt = (
"The rdata type with class {rdclass:d} and rdtype {rdtype:d} "
+ "already exists."
)
def register_type(implementation, rdtype, rdtype_text, is_singleton=False,
rdclass=dns.rdataclass.IN):
def register_type(
implementation: Any,
rdtype: int,
rdtype_text: str,
is_singleton: bool = False,
rdclass: dns.rdataclass.RdataClass = dns.rdataclass.IN,
) -> None:
"""Dynamically register a module to handle an rdatatype.
*implementation*, a module implementing the type in the usual dnspython
@ -769,14 +881,16 @@ def register_type(implementation, rdtype, rdtype_text, is_singleton=False,
it applies to all classes.
"""
existing_cls = get_rdata_class(rdclass, rdtype)
if existing_cls != GenericRdata or dns.rdatatype.is_metatype(rdtype):
raise RdatatypeExists(rdclass=rdclass, rdtype=rdtype)
the_rdtype = dns.rdatatype.RdataType.make(rdtype)
existing_cls = get_rdata_class(rdclass, the_rdtype)
if existing_cls != GenericRdata or dns.rdatatype.is_metatype(the_rdtype):
raise RdatatypeExists(rdclass=rdclass, rdtype=the_rdtype)
try:
if dns.rdatatype.RdataType(rdtype).name != rdtype_text:
raise RdatatypeExists(rdclass=rdclass, rdtype=rdtype)
if dns.rdatatype.RdataType(the_rdtype).name != rdtype_text:
raise RdatatypeExists(rdclass=rdclass, rdtype=the_rdtype)
except ValueError:
pass
_rdata_classes[(rdclass, rdtype)] = getattr(implementation,
rdtype_text.replace('-', '_'))
dns.rdatatype.register_type(rdtype, rdtype_text, is_singleton)
_rdata_classes[(rdclass, the_rdtype)] = getattr(
implementation, rdtype_text.replace("-", "_")
)
dns.rdatatype.register_type(the_rdtype, rdtype_text, is_singleton)