Merge "Check TXT/SPF records for RFC1035 sec. 5.1"

This commit is contained in:
Zuul 2019-05-20 04:18:20 +00:00 committed by Gerrit Code Review
commit 64c09e015b
6 changed files with 111 additions and 4 deletions

View File

@ -187,10 +187,8 @@ class RecordSet(base.DesignateObject, base.DictObjectMixin,
error_indexes.append(i)
except Exception as e:
error_message = str.format(
'Provided object is not valid. '
'Got a %s error with message %s' %
(type(e).__name__, six.text_type(e)))
error_message = ('Provided object is not valid. Got a %s error'
' with message %s' % (type(e).__name__, six.text_type(e)))
raise exceptions.InvalidObject(error_message)
else:

View File

@ -16,6 +16,7 @@ from designate.objects.record import Record
from designate.objects.record import RecordList
from designate.objects import base
from designate.objects import fields
from designate.exceptions import InvalidObject
@base.DesignateRegistry.register
@ -32,6 +33,23 @@ class SPF(Record):
return self.txt_data
def _from_string(self, value):
if (not value.startswith('"') and not value.endswith('"')):
# value with spaces should be quoted as per RFC1035 5.1
for element in value:
if element.isspace():
err = ("Empty spaces are not allowed in SPF record, "
"unless wrapped in double quotes.")
raise InvalidObject(err)
else:
# quotes within value should be escaped with backslash
strip_value = value.strip('"')
for index, char in enumerate(strip_value):
if char == '"':
if strip_value[index - 1] != "\\":
err = ("Quotation marks should be escaped with "
"backslash.")
raise InvalidObject(err)
self.txt_data = value
# The record type is defined in the RFC. This will be used when the record

View File

@ -16,6 +16,7 @@ from designate.objects.record import Record
from designate.objects.record import RecordList
from designate.objects import base
from designate.objects import fields
from designate.exceptions import InvalidObject
@base.DesignateRegistry.register
@ -32,6 +33,23 @@ class TXT(Record):
return self.txt_data
def _from_string(self, value):
if (not value.startswith('"') and not value.endswith('"')):
# value with spaces should be quoted as per RFC1035 5.1
for element in value:
if element.isspace():
err = ("Empty spaces are not allowed in TXT record, "
"unless wrapped in double quotes.")
raise InvalidObject(err)
else:
# quotes within value should be escaped with backslash
strip_value = value.strip('"')
for index, char in enumerate(strip_value):
if char == '"':
if strip_value[index - 1] != "\\":
err = ("Quotation marks should be escaped with "
"backslash.")
raise InvalidObject(err)
self.txt_data = value
# The record type is defined in the RFC. This will be used when the record

View File

@ -0,0 +1,33 @@
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
# a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations
# under the License.
from oslo_log import log as logging
import oslotest.base
import testtools
from designate import exceptions
from designate import objects
LOG = logging.getLogger(__name__)
class RRDataSPFTest(oslotest.base.BaseTestCase):
def test_reject_non_quoted_spaces(self):
record = objects.SPF(data='foo bar')
with testtools.ExpectedException(exceptions.InvalidObject):
record.validate()
def test_reject_non_escaped_quotes(self):
record = objects.SPF(data='foo"bar')
with testtools.ExpectedException(exceptions.InvalidObject):
record.validate()

View File

@ -0,0 +1,33 @@
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
# a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations
# under the License.
from oslo_log import log as logging
import oslotest.base
import testtools
from designate import exceptions
from designate import objects
LOG = logging.getLogger(__name__)
class RRDataTXTTest(oslotest.base.BaseTestCase):
def test_reject_non_quoted_spaces(self):
record = objects.TXT(data='foo bar')
with testtools.ExpectedException(exceptions.InvalidObject):
record.validate()
def test_reject_non_escaped_quotes(self):
record = objects.TXT(data='foo"bar')
with testtools.ExpectedException(exceptions.InvalidObject):
record.validate()

View File

@ -0,0 +1,7 @@
---
fixes:
- |
TXT and SPF records are now validated for empty spaces in the values.
If record value has empty space it should use "" quotation according to
RFC-1035 section 5.1. Use of single quotation mark within record value
requires quote symbol to be escaped with backslash. Bug-1755788