Commit 53797061 authored by JINMEI Tatuya's avatar JINMEI Tatuya
Browse files

[2911] refactoring: extract _get_zone_soa from XfrinConnection as free func.

This change will be helpful for later part of this branch.
parent c612e8e2
......@@ -850,7 +850,9 @@ class TestXfrinConnection(unittest.TestCase):
'''
self.conn._zone_name = zone_name
self.conn._zone_soa = self.conn._get_zone_soa()
self.conn._zone_soa = xfrin._get_zone_soa(self.conn._datasrc_client,
zone_name,
self.conn._rrclass)
class TestAXFR(TestXfrinConnection):
def setUp(self):
......@@ -974,7 +976,9 @@ class TestAXFR(TestXfrinConnection):
RRType.IXFR)
self._set_test_zone(Name('dup-soa.example'))
self.conn._zone_soa = self.conn._get_zone_soa()
self.conn._zone_soa = xfrin._get_zone_soa(self.conn._datasrc_client,
self.conn._zone_name,
self.conn._rrclass)
self.assertRaises(XfrinException, self.conn._create_query,
RRType.IXFR)
......
......@@ -593,7 +593,8 @@ class XfrinConnection(asyncore.dispatcher):
# Data source handler
self._datasrc_client = datasrc_client
self._zone_soa = self._get_zone_soa()
self._zone_soa = _get_zone_soa(self._datasrc_client, zone_name,
rrclass)
self._sock_map = sock_map
self._soa_rr_count = 0
......@@ -622,54 +623,6 @@ class XfrinConnection(asyncore.dispatcher):
self.create_socket(self._master_addrinfo[0], self._master_addrinfo[1])
self.socket.setblocking(1)
def _get_zone_soa(self):
'''Retrieve the current SOA RR of the zone to be transferred.
It will be used for various purposes in subsequent xfr protocol
processing. It is validly possible that the zone is currently
empty and therefore doesn't have an SOA, so this method doesn't
consider it an error and returns None in such a case. It may or
may not result in failure in the actual processing depending on
how the SOA is used.
When the zone has an SOA RR, this method makes sure that it's
valid, i.e., it has exactly one RDATA; if it is not the case
this method returns None.
If the underlying data source doesn't even know the zone, this method
tries to provide backward compatible behavior where xfrin is
responsible for creating zone in the corresponding DB table.
For a longer term we should deprecate this behavior by introducing
more generic zone management framework, but at the moment we try
to not surprise existing users. (Note also that the part of
providing the compatible behavior uses the old data source API.
We'll deprecate this API in a near future, too).
'''
# get the zone finder. this must be SUCCESS (not even
# PARTIALMATCH) because we are specifying the zone origin name.
result, finder = self._datasrc_client.find_zone(self._zone_name)
if result != DataSourceClient.SUCCESS:
# The data source doesn't know the zone. For now, we provide
# backward compatibility and creates a new one ourselves.
# For longer term, we should probably separate this level of zone
# management outside of xfrin.
self._datasrc_client.create_zone(self._zone_name)
logger.warn(XFRIN_ZONE_CREATED, self.zone_str())
# try again
result, finder = self._datasrc_client.find_zone(self._zone_name)
if result != DataSourceClient.SUCCESS:
return None
result, soa_rrset, _ = finder.find(self._zone_name, RRType.SOA)
if result != ZoneFinder.SUCCESS:
logger.info(XFRIN_ZONE_NO_SOA, self.zone_str())
return None
if soa_rrset.get_rdata_count() != 1:
logger.warn(XFRIN_ZONE_MULTIPLE_SOA, self.zone_str(),
soa_rrset.get_rdata_count())
return None
return soa_rrset
def __set_xfrstate(self, new_state):
self.__state = new_state
......@@ -1110,6 +1063,58 @@ class XfrinConnection(asyncore.dispatcher):
return False
def _get_zone_soa(datasrc_client, zone_name, zone_class):
"""Retrieve the current SOA RR of the zone to be transferred.
This function is essentially private to the module, but will also
be called from tests; no one else should use this function directly.
It will be used for various purposes in subsequent xfr protocol
processing. It is validly possible that the zone is currently
empty and therefore doesn't have an SOA, so this method doesn't
consider it an error and returns None in such a case. It may or
may not result in failure in the actual processing depending on
how the SOA is used.
When the zone has an SOA RR, this method makes sure that it's
valid, i.e., it has exactly one RDATA; if it is not the case
this method returns None.
If the underlying data source doesn't even know the zone, this method
tries to provide backward compatible behavior where xfrin is
responsible for creating zone in the corresponding DB table.
For a longer term we should deprecate this behavior by introducing
more generic zone management framework, but at the moment we try
to not surprise existing users. (Note also that the part of
providing the compatible behavior uses the old data source API.
We'll deprecate this API in a near future, too).
"""
# get the zone finder. this must be SUCCESS (not even
# PARTIALMATCH) because we are specifying the zone origin name.
result, finder = datasrc_client.find_zone(zone_name)
if result != DataSourceClient.SUCCESS:
# The data source doesn't know the zone. For now, we provide
# backward compatibility and creates a new one ourselves.
# For longer term, we should probably separate this level of zone
# management outside of xfrin.
datasrc_client.create_zone(zone_name)
logger.warn(XFRIN_ZONE_CREATED, format_zone_str(zone_name, zone_class))
# try again
result, finder = datasrc_client.find_zone(zone_name)
if result != DataSourceClient.SUCCESS:
return None
result, soa_rrset, _ = finder.find(zone_name, RRType.SOA)
if result != ZoneFinder.SUCCESS:
logger.info(XFRIN_ZONE_NO_SOA, format_zone_str(zone_name, zone_class))
return None
if soa_rrset.get_rdata_count() != 1:
logger.warn(XFRIN_ZONE_MULTIPLE_SOA,
format_zone_str(zone_name, zone_class),
soa_rrset.get_rdata_count())
return None
return soa_rrset
def __process_xfrin(server, zone_name, rrclass, db_file,
shutdown_event, master_addrinfo, check_soa, tsig_key,
request_type, conn_class):
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment