Improve NAPTR support
This patchset adds support for fields (e.g flags, services, regexp) to be quoted and empty as described in RFC 2915. While unquoted fields are NOT optional, the previous behaviour remains for backward compatibility. The regular expressions have been adjusted to allow empty string values for quoted fields. Additional tests added to cover more cases. https://datatracker.ietf.org/doc/html/rfc2915 https://github.com/isc-projects/bind9/blob/main/bin/tests/system/xfer/dig1.good Change-Id: I44bc7d2a231ed8d63cba69ec95f06358687aa914
This commit is contained in:
parent
590064e8d9
commit
aa151b4d00
@ -96,9 +96,9 @@ class StringFields(ovoo_fields.StringField):
|
|||||||
RE_SRV_HOST_NAME = r'^(?:(?!\-)(?:\_[A-Za-z0-9_\-]{1,63}\.){2})(?!.{255,})(?:(?!\-)[A-Za-z0-9_\-]{1,63}(?<!\-)\.)+\Z' # noqa
|
RE_SRV_HOST_NAME = r'^(?:(?!\-)(?:\_[A-Za-z0-9_\-]{1,63}\.){2})(?!.{255,})(?:(?!\-)[A-Za-z0-9_\-]{1,63}(?<!\-)\.)+\Z' # noqa
|
||||||
RE_SSHFP_FINGERPRINT = r'^([0-9A-Fa-f]{10,40}|[0-9A-Fa-f]{64})\Z'
|
RE_SSHFP_FINGERPRINT = r'^([0-9A-Fa-f]{10,40}|[0-9A-Fa-f]{64})\Z'
|
||||||
RE_TLDNAME = r'^(?!.{255,})(?:(?!\-)[A-Za-z0-9_\-]{1,63}(?<!\-))(?:\.(?:(?!\-)[A-Za-z0-9_\-]{1,63}(?<!\-)))*\Z' # noqa
|
RE_TLDNAME = r'^(?!.{255,})(?:(?!\-)[A-Za-z0-9_\-]{1,63}(?<!\-))(?:\.(?:(?!\-)[A-Za-z0-9_\-]{1,63}(?<!\-)))*\Z' # noqa
|
||||||
RE_NAPTR_FLAGS = r'^(?!.*(.).*\1)[APSU]+$'
|
RE_NAPTR_FLAGS = r'^[APSUapsu]*$'
|
||||||
RE_NAPTR_SERVICE = r'^([A-Za-z]([A-Za-z0-9]*)(\+[A-Za-z]([A-Za-z0-9]{0,31}))*)?' # noqa
|
RE_NAPTR_SERVICE = r'^([A-Za-z]([A-Za-z0-9]*)(\+[A-Za-z]([A-Za-z0-9]{0,31}))*)?$' # noqa
|
||||||
RE_NAPTR_REGEXP = r'^([^0-9i\\])(.*)\1((.+)|(\\[1-9]))\1(i?)'
|
RE_NAPTR_REGEXP = r'^(([^0-9i\\])(.*)\2((.+)|(\\[1-9]))?\2(i?))?$'
|
||||||
RE_KVP = r'^\s[A-Za-z0-9]+=[A-Za-z0-9]+'
|
RE_KVP = r'^\s[A-Za-z0-9]+=[A-Za-z0-9]+'
|
||||||
RE_URL_MAIL = r'^mailto:[A-Za-z0-9_\-]+(\+[A-Za-z0-9_\-]+)?@.*'
|
RE_URL_MAIL = r'^mailto:[A-Za-z0-9_\-]+(\+[A-Za-z0-9_\-]+)?@.*'
|
||||||
RE_URL_HTTP = r'^http(s)?://.*/'
|
RE_URL_HTTP = r'^http(s)?://.*/'
|
||||||
|
@ -35,15 +35,22 @@ class NAPTR(Record):
|
|||||||
'replacement': fields.DomainField(maxLength=255)
|
'replacement': fields.DomainField(maxLength=255)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def _strip_double_quotes(value):
|
||||||
|
if value.startswith('"') and value.endswith('"'):
|
||||||
|
return value[1:-1]
|
||||||
|
else:
|
||||||
|
return value
|
||||||
|
|
||||||
def from_string(self, value):
|
def from_string(self, value):
|
||||||
order, preference, flags, service, regexp, replacement = (
|
order, preference, flags, service, regexp, replacement = (
|
||||||
value.split(' ')
|
value.split(' ')
|
||||||
)
|
)
|
||||||
self.order = int(order)
|
self.order = int(order)
|
||||||
self.preference = int(preference)
|
self.preference = int(preference)
|
||||||
self.flags = flags
|
self.flags = self._strip_double_quotes(flags)
|
||||||
self.service = service
|
self.service = self._strip_double_quotes(service)
|
||||||
self.regexp = regexp
|
self.regexp = self._strip_double_quotes(regexp)
|
||||||
self.replacement = replacement
|
self.replacement = replacement
|
||||||
|
|
||||||
# The record type is defined in the RFC. This will be used when the record
|
# The record type is defined in the RFC. This will be used when the record
|
||||||
|
@ -34,3 +34,40 @@ class RRDataNAPTRTest(oslotest.base.BaseTestCase):
|
|||||||
self.assertEqual('!^.*$!sip:customer-service@example.com!',
|
self.assertEqual('!^.*$!sip:customer-service@example.com!',
|
||||||
naptr_record.regexp)
|
naptr_record.regexp)
|
||||||
self.assertEqual('_sip._udp.example.com.', naptr_record.replacement)
|
self.assertEqual('_sip._udp.example.com.', naptr_record.replacement)
|
||||||
|
|
||||||
|
def test_parse_naptr_quoted(self):
|
||||||
|
naptr_record = objects.NAPTR()
|
||||||
|
naptr_record.from_string(
|
||||||
|
'0 0 "S" "SIP+D2U" "!^.*$!sip:support@example.com!" _sip._udp.example.com.') # noqa
|
||||||
|
|
||||||
|
self.assertEqual(0, naptr_record.order)
|
||||||
|
self.assertEqual(0, naptr_record.preference)
|
||||||
|
self.assertEqual('S', naptr_record.flags)
|
||||||
|
self.assertEqual('SIP+D2U', naptr_record.service)
|
||||||
|
self.assertEqual('!^.*$!sip:support@example.com!',
|
||||||
|
naptr_record.regexp)
|
||||||
|
self.assertEqual('_sip._udp.example.com.', naptr_record.replacement)
|
||||||
|
|
||||||
|
def test_parse_naptr_empty_fields(self):
|
||||||
|
naptr_record = objects.NAPTR()
|
||||||
|
naptr_record.from_string('0 0 "" "" "" test.') # noqa
|
||||||
|
|
||||||
|
self.assertEqual(0, naptr_record.order)
|
||||||
|
self.assertEqual(0, naptr_record.preference)
|
||||||
|
self.assertEqual('', naptr_record.flags)
|
||||||
|
self.assertEqual('', naptr_record.service)
|
||||||
|
self.assertEqual('',
|
||||||
|
naptr_record.regexp)
|
||||||
|
self.assertEqual('test.', naptr_record.replacement)
|
||||||
|
|
||||||
|
def test_parse_naptr_valid_exampe1(self):
|
||||||
|
naptr_record = objects.NAPTR()
|
||||||
|
naptr_record.from_string('65535 65535 "SAUP" "bloop" ":beep::" test.') # noqa
|
||||||
|
|
||||||
|
self.assertEqual(65535, naptr_record.order)
|
||||||
|
self.assertEqual(65535, naptr_record.preference)
|
||||||
|
self.assertEqual('SAUP', naptr_record.flags)
|
||||||
|
self.assertEqual('bloop', naptr_record.service)
|
||||||
|
self.assertEqual(':beep::',
|
||||||
|
naptr_record.regexp)
|
||||||
|
self.assertEqual('test.', naptr_record.replacement)
|
||||||
|
Loading…
Reference in New Issue
Block a user