Refactor notify logic into backends
The idea here is, like many things, the time and frequency of sending NOTIFYs is not the same for every backend. So we let the backends decide when to send their NOTIFYs. Ideally this makes the Pool Manager code simpler and the backend code easier to understand, and avoids sending some unnecessary NOTIFYs. This requires a change to MiniDNS' rpcapi to make notify_zone_changed and get_serial_number take a host and port, instead of a nameserver object. Change-Id: I8d67cebeecc8261e715849aefeafd20f0d60d304
This commit is contained in:
parent
bf8431728e
commit
520c32e514
contrib/devstack/lib/designate_plugins
designate
backend
mdns
pool_manager
tests
@ -77,7 +77,7 @@ EOF
|
||||
function configure_designate_backend {
|
||||
iniset $DESIGNATE_CONF pool_target:$DESIGNATE_TARGET_ID type bind9
|
||||
iniset $DESIGNATE_CONF pool_target:$DESIGNATE_TARGET_ID masters $DESIGNATE_SERVICE_HOST:$DESIGNATE_SERVICE_PORT_MDNS
|
||||
iniset $DESIGNATE_CONF pool_target:$DESIGNATE_TARGET_ID options "rndc_host: $DESIGNATE_SERVICE_HOST, rndc_port: $DESIGNATE_SERVICE_PORT_RNDC, rndc_config_file: $BIND_CFG_DIR/rndc.conf, rndc_key_file: $BIND_CFG_DIR/rndc.key"
|
||||
iniset $DESIGNATE_CONF pool_target:$DESIGNATE_TARGET_ID options "rndc_host: $DESIGNATE_SERVICE_HOST, rndc_port: $DESIGNATE_SERVICE_PORT_RNDC, rndc_config_file: $BIND_CFG_DIR/rndc.conf, rndc_key_file: $BIND_CFG_DIR/rndc.key, host: $DESIGNATE_SERVICE_HOST, port: $DESIGNATE_SERVICE_PORT_DNS"
|
||||
|
||||
# DevStack Managed BIND NameServer
|
||||
local nameserver_id=`uuidgen`
|
||||
|
@ -56,6 +56,7 @@ function install_designate_backend {
|
||||
function configure_designate_backend {
|
||||
iniset $DESIGNATE_CONF pool_target:$DESIGNATE_TARGET_ID type infoblox
|
||||
iniset $DESIGNATE_CONF pool_target:$DESIGNATE_TARGET_ID masters $DESIGNATE_SERVICE_HOST:$DESIGNATE_SERVICE_PORT_MDNS
|
||||
iniset $DESIGNATE_CONF pool_target:$DESIGNATE_TARGET_ID options "host: $DESIGNATE_INFOBLOX_NAMESERVER_IP, port: $DESIGNATE_SERVICE_PORT_DNS"
|
||||
|
||||
local nameserver_id=`uuidgen`
|
||||
iniset $DESIGNATE_CONF pool:$DESIGNATE_POOL_ID nameservers $nameserver_id
|
||||
|
@ -56,7 +56,7 @@ function install_designate_backend {
|
||||
function configure_designate_backend {
|
||||
iniset $DESIGNATE_CONF pool_target:$DESIGNATE_TARGET_ID type powerdns
|
||||
iniset $DESIGNATE_CONF pool_target:$DESIGNATE_TARGET_ID masters $DESIGNATE_SERVICE_HOST:$DESIGNATE_SERVICE_PORT_MDNS
|
||||
iniset $DESIGNATE_CONF pool_target:$DESIGNATE_TARGET_ID options "connection: `database_connection_url designate_pdns`"
|
||||
iniset $DESIGNATE_CONF pool_target:$DESIGNATE_TARGET_ID options "connection: `database_connection_url designate_pdns`, host: $DESIGNATE_SERVICE_HOST, port: $DESIGNATE_SERVICE_PORT_DNS"
|
||||
|
||||
# DevStack Managed PDNS NameServer
|
||||
local nameserver_id=`uuidgen`
|
||||
|
@ -30,7 +30,6 @@ from designate.i18n import _LW
|
||||
from designate.backend import base
|
||||
from designate import exceptions
|
||||
from designate.mdns import rpcapi as mdns_api
|
||||
from designate import objects
|
||||
|
||||
|
||||
dns_query = eventlet.import_patched('dns.query')
|
||||
@ -38,6 +37,18 @@ dns_query = eventlet.import_patched('dns.query')
|
||||
LOG = logging.getLogger(__name__)
|
||||
CONF = cfg.CONF
|
||||
|
||||
# Command and Control OPCODE
|
||||
CC = 14
|
||||
|
||||
# Private DNS CLASS Uses
|
||||
CLASSCC = 65280
|
||||
|
||||
# Private RR Code Uses
|
||||
SUCCESS = 65280
|
||||
FAILURE = 65281
|
||||
CREATE = 65282
|
||||
DELETE = 65283
|
||||
|
||||
|
||||
class AgentPoolBackend(base.Backend):
|
||||
__plugin_name__ = 'agent'
|
||||
@ -46,8 +57,8 @@ class AgentPoolBackend(base.Backend):
|
||||
|
||||
def __init__(self, target):
|
||||
super(AgentPoolBackend, self).__init__(target)
|
||||
self.host = self.options.get('host')
|
||||
self.port = int(self.options.get('port'))
|
||||
self.host = self.options.get('host', '127.0.0.1')
|
||||
self.port = int(self.options.get('port', 53))
|
||||
self.timeout = CONF['service:pool_manager'].poll_timeout
|
||||
self.retry_interval = CONF['service:pool_manager'].poll_retry_interval
|
||||
self.max_retries = CONF['service:pool_manager'].poll_max_retries
|
||||
@ -58,29 +69,43 @@ class AgentPoolBackend(base.Backend):
|
||||
|
||||
def create_domain(self, context, domain):
|
||||
LOG.debug('Create Domain')
|
||||
response, retry = self._make_and_send_dns_message(domain.name, 15, 14,
|
||||
65282, 65280, self.host, self.port)
|
||||
response, retry = self._make_and_send_dns_message(
|
||||
domain.name,
|
||||
self.timeout,
|
||||
CC,
|
||||
CREATE,
|
||||
CLASSCC,
|
||||
self.host,
|
||||
self.port
|
||||
)
|
||||
if response is None:
|
||||
raise exceptions.Backend()
|
||||
|
||||
def update_domain(self, context, domain):
|
||||
LOG.debug('Update Domain')
|
||||
|
||||
values = {
|
||||
'host': self.host,
|
||||
'port': self.port,
|
||||
'pool_id': CONF['service:central'].default_pool_id
|
||||
}
|
||||
nameserver = objects.PoolNameserver(**values)
|
||||
|
||||
self.mdns_api.notify_zone_changed(
|
||||
context, domain, nameserver, self.timeout,
|
||||
self.retry_interval, self.max_retries, 0)
|
||||
context,
|
||||
domain,
|
||||
self.host,
|
||||
self.port,
|
||||
self.timeout,
|
||||
self.retry_interval,
|
||||
self.max_retries,
|
||||
self.delay
|
||||
)
|
||||
|
||||
def delete_domain(self, context, domain):
|
||||
LOG.debug('Delete Domain')
|
||||
response, retry = self._make_and_send_dns_message(domain.name, 15, 14,
|
||||
65283, 65280, self.host, self.port)
|
||||
response, retry = self._make_and_send_dns_message(
|
||||
domain.name,
|
||||
self.timeout,
|
||||
CC,
|
||||
DELETE,
|
||||
CLASSCC,
|
||||
self.host,
|
||||
self.port
|
||||
)
|
||||
if response is None:
|
||||
raise exceptions.Backend()
|
||||
|
||||
|
@ -21,6 +21,7 @@ from oslo_log import log as logging
|
||||
from designate.i18n import _LI
|
||||
from designate.context import DesignateContext
|
||||
from designate.plugin import DriverPlugin
|
||||
from designate.mdns import rpcapi as mdns_api
|
||||
|
||||
|
||||
LOG = logging.getLogger(__name__)
|
||||
@ -41,17 +42,29 @@ class Backend(DriverPlugin):
|
||||
self.target = target
|
||||
self.options = target.options
|
||||
self.masters = target.masters
|
||||
self.host = self.options.get('host', '127.0.0.1')
|
||||
self.port = int(self.options.get('port', 53))
|
||||
|
||||
# TODO(kiall): Context's should never be shared accross requests.
|
||||
self.admin_context = DesignateContext.get_admin_context()
|
||||
self.admin_context.all_tenants = True
|
||||
|
||||
# Options for sending NOTIFYs
|
||||
self.timeout = CONF['service:pool_manager'].poll_timeout
|
||||
self.retry_interval = CONF['service:pool_manager'].poll_retry_interval
|
||||
self.max_retries = CONF['service:pool_manager'].poll_max_retries
|
||||
self.delay = CONF['service:pool_manager'].poll_delay
|
||||
|
||||
def start(self):
|
||||
LOG.info(_LI('Starting %s backend'), self.get_canonical_name())
|
||||
|
||||
def stop(self):
|
||||
LOG.info(_LI('Stopped %s backend'), self.get_canonical_name())
|
||||
|
||||
@property
|
||||
def mdns_api(self):
|
||||
return mdns_api.MdnsAPI.get_instance()
|
||||
|
||||
# Core Backend Interface
|
||||
@abc.abstractmethod
|
||||
def create_domain(self, context, domain):
|
||||
@ -69,6 +82,11 @@ class Backend(DriverPlugin):
|
||||
:param context: Security context information.
|
||||
:param domain: the DNS domain.
|
||||
"""
|
||||
LOG.debug('Update Domain')
|
||||
|
||||
self.mdns_api.notify_zone_changed(
|
||||
context, domain, self.host, self.port, self.timeout,
|
||||
self.retry_interval, self.max_retries, self.delay)
|
||||
|
||||
@abc.abstractmethod
|
||||
def delete_domain(self, context, domain):
|
||||
|
@ -35,6 +35,8 @@ class Bind9Backend(base.Backend):
|
||||
def __init__(self, target):
|
||||
super(Bind9Backend, self).__init__(target)
|
||||
|
||||
self.host = self.options.get('host', '127.0.0.1')
|
||||
self.port = int(self.options.get('port', 53))
|
||||
self.rndc_host = self.options.get('rndc_host', '127.0.0.1')
|
||||
self.rndc_port = int(self.options.get('rndc_port', 953))
|
||||
self.rndc_config_file = self.options.get('rndc_config_file')
|
||||
@ -65,6 +67,10 @@ class Bind9Backend(base.Backend):
|
||||
if "already exists" not in six.text_type(e):
|
||||
raise
|
||||
|
||||
self.mdns_api.notify_zone_changed(
|
||||
context, domain, self.host, self.port, self.timeout,
|
||||
self.retry_interval, self.max_retries, self.delay)
|
||||
|
||||
def delete_domain(self, context, domain):
|
||||
LOG.debug('Delete Domain')
|
||||
rndc_op = [
|
||||
|
@ -377,9 +377,6 @@ class DynECTBackend(base.Backend):
|
||||
client.put(url, data={'activate': True})
|
||||
client.logout()
|
||||
|
||||
def update_domain(self, context, domain):
|
||||
LOG.debug('Discarding update_domain call, not-applicable')
|
||||
|
||||
def delete_domain(self, context, domain):
|
||||
LOG.info(_LI('Deleting domain %(d_id)s / %(d_name)s') %
|
||||
{'d_id': domain['id'], 'd_name': domain['name']})
|
||||
|
@ -51,10 +51,6 @@ class InfobloxBackend(base.Backend):
|
||||
dns_view=dns_net_view
|
||||
)
|
||||
|
||||
def update_domain(self, context, domain):
|
||||
# Since all updates are done via zone transfer, there is nothing to do
|
||||
LOG.info(_LI('Update Domain %r') % domain)
|
||||
|
||||
def delete_domain(self, context, domain):
|
||||
LOG.info(_LI('Delete Domain %r') % domain)
|
||||
self.infoblox.delete_zone_auth(domain['name'][0:-1])
|
||||
|
@ -55,6 +55,8 @@ class PowerDNSBackend(base.Backend):
|
||||
def __init__(self, target):
|
||||
super(PowerDNSBackend, self).__init__(target)
|
||||
|
||||
self.host = self.options.get('host', '127.0.0.1')
|
||||
self.port = int(self.options.get('port', 53))
|
||||
self.local_store = threading.local()
|
||||
|
||||
default_connection = 'sqlite:///%(state_path)s/powerdns.sqlite' % {
|
||||
@ -140,6 +142,10 @@ class PowerDNSBackend(base.Backend):
|
||||
else:
|
||||
self.session.commit()
|
||||
|
||||
self.mdns_api.notify_zone_changed(
|
||||
context, domain, self.host, self.port, self.timeout,
|
||||
self.retry_interval, self.max_retries, self.delay)
|
||||
|
||||
def delete_domain(self, context, domain):
|
||||
# TODO(kiall): We should make this match create_domain with regard to
|
||||
# transactions.
|
||||
|
@ -37,16 +37,17 @@ CONF = cfg.CONF
|
||||
|
||||
|
||||
class NotifyEndpoint(base.BaseEndpoint):
|
||||
RPC_API_VERSION = '1.1'
|
||||
RPC_API_VERSION = '2.0'
|
||||
RPC_API_NAMESPACE = 'notify'
|
||||
|
||||
def notify_zone_changed(self, context, domain, nameserver, timeout,
|
||||
def notify_zone_changed(self, context, domain, host, port, timeout,
|
||||
retry_interval, max_retries, delay):
|
||||
"""
|
||||
:param context: The user context.
|
||||
:param domain: The designate domain object. This contains the domain
|
||||
name.
|
||||
:param nameserver: A notify is sent to nameserver.host:nameserver.port.
|
||||
:param host: A notify is sent to this host.
|
||||
:param port: A notify is sent to this port.
|
||||
:param timeout: The time (in seconds) to wait for a NOTIFY response
|
||||
from server.
|
||||
:param retry_interval: The time (in seconds) between retries.
|
||||
@ -60,7 +61,7 @@ class NotifyEndpoint(base.BaseEndpoint):
|
||||
"""
|
||||
time.sleep(delay)
|
||||
return self._make_and_send_dns_message(
|
||||
domain, nameserver, timeout, retry_interval, max_retries,
|
||||
domain, host, port, timeout, retry_interval, max_retries,
|
||||
notify=True)
|
||||
|
||||
def poll_for_serial_number(self, context, domain, nameserver, timeout,
|
||||
@ -69,8 +70,7 @@ class NotifyEndpoint(base.BaseEndpoint):
|
||||
:param context: The user context.
|
||||
:param domain: The designate domain object. This contains the domain
|
||||
name. domain.serial = expected_serial
|
||||
:param nameserver: nameserver.host:nameserver.port is checked for an
|
||||
updated serial number.
|
||||
:param nameserver: Destination for the poll
|
||||
:param timeout: The time (in seconds) to wait for a SOA response from
|
||||
nameserver.
|
||||
:param retry_interval: The time (in seconds) between retries.
|
||||
@ -81,19 +81,19 @@ class NotifyEndpoint(base.BaseEndpoint):
|
||||
:return: The pool manager is informed of the status with update_status.
|
||||
"""
|
||||
(status, actual_serial, retries) = self.get_serial_number(
|
||||
context, domain, nameserver, timeout, retry_interval, max_retries,
|
||||
delay)
|
||||
context, domain, nameserver.host, nameserver.port, timeout,
|
||||
retry_interval, max_retries, delay)
|
||||
self.pool_manager_api.update_status(
|
||||
context, domain, nameserver, status, actual_serial)
|
||||
|
||||
def get_serial_number(self, context, domain, nameserver, timeout,
|
||||
def get_serial_number(self, context, domain, host, port, timeout,
|
||||
retry_interval, max_retries, delay):
|
||||
"""
|
||||
:param context: The user context.
|
||||
:param domain: The designate domain object. This contains the domain
|
||||
name. domain.serial = expected_serial
|
||||
:param nameserver: nameserver.host:nameserver.port is checked for an
|
||||
updated serial number.
|
||||
:param host: A notify is sent to this host.
|
||||
:param port: A notify is sent to this port.
|
||||
:param timeout: The time (in seconds) to wait for a SOA response from
|
||||
nameserver.
|
||||
:param retry_interval: The time (in seconds) between retries.
|
||||
@ -115,7 +115,7 @@ class NotifyEndpoint(base.BaseEndpoint):
|
||||
time.sleep(delay)
|
||||
while (True):
|
||||
(response, retry) = self._make_and_send_dns_message(
|
||||
domain, nameserver, timeout, retry_interval, retries)
|
||||
domain, host, port, timeout, retry_interval, retries)
|
||||
if response and response.rcode() in (
|
||||
dns.rcode.NXDOMAIN, dns.rcode.REFUSED, dns.rcode.SERVFAIL):
|
||||
status = 'NO_DOMAIN'
|
||||
@ -133,8 +133,8 @@ class NotifyEndpoint(base.BaseEndpoint):
|
||||
LOG.warn(_LW("Got lower serial for '%(zone)s' to '%(host)s:"
|
||||
"%(port)s'. Expected:'%(es)d'. Got:'%(as)s'."
|
||||
"Retries left='%(retries)d'") %
|
||||
{'zone': domain.name, 'host': nameserver.host,
|
||||
'port': nameserver.port, 'es': domain.serial,
|
||||
{'zone': domain.name, 'host': host,
|
||||
'port': port, 'es': domain.serial,
|
||||
'as': actual_serial, 'retries': retries})
|
||||
if retries > 0:
|
||||
# retry again
|
||||
@ -150,13 +150,13 @@ class NotifyEndpoint(base.BaseEndpoint):
|
||||
# Return retries for testing purposes.
|
||||
return (status, actual_serial, retries)
|
||||
|
||||
def _make_and_send_dns_message(self, domain, nameserver, timeout,
|
||||
def _make_and_send_dns_message(self, domain, host, port, timeout,
|
||||
retry_interval, max_retries, notify=False):
|
||||
"""
|
||||
:param domain: The designate domain object. This contains the domain
|
||||
name.
|
||||
:param server: The destination for the dns message is
|
||||
server.host:server.port.
|
||||
:param host: The destination host for the dns message.
|
||||
:param port: The destination port for the dns message.
|
||||
:param timeout: The time (in seconds) to wait for a response from
|
||||
destination.
|
||||
:param retry_interval: The time (in seconds) between retries.
|
||||
@ -168,9 +168,6 @@ class NotifyEndpoint(base.BaseEndpoint):
|
||||
response is the response on success or None on failure.
|
||||
current_retry is the current retry number
|
||||
"""
|
||||
dest_ip = nameserver.host
|
||||
dest_port = nameserver.port
|
||||
|
||||
dns_message = self._make_dns_message(domain.name, notify=notify)
|
||||
|
||||
retry = 0
|
||||
@ -181,18 +178,18 @@ class NotifyEndpoint(base.BaseEndpoint):
|
||||
LOG.info(_LI("Sending '%(msg)s' for '%(zone)s' to '%(server)s:"
|
||||
"%(port)d'.") %
|
||||
{'msg': 'NOTIFY' if notify else 'SOA',
|
||||
'zone': domain.name, 'server': dest_ip,
|
||||
'port': dest_port})
|
||||
'zone': domain.name, 'server': host,
|
||||
'port': port})
|
||||
response = self._send_dns_message(
|
||||
dns_message, dest_ip, dest_port, timeout)
|
||||
dns_message, host, port, timeout)
|
||||
|
||||
if isinstance(response, dns.exception.Timeout):
|
||||
LOG.warn(_LW("Got Timeout while trying to send '%(msg)s' for "
|
||||
"'%(zone)s' to '%(server)s:%(port)d'. Timeout="
|
||||
"'%(timeout)d' seconds. Retry='%(retry)d'") %
|
||||
{'msg': 'NOTIFY' if notify else 'SOA',
|
||||
'zone': domain.name, 'server': dest_ip,
|
||||
'port': dest_port, 'timeout': timeout,
|
||||
'zone': domain.name, 'server': host,
|
||||
'port': port, 'timeout': timeout,
|
||||
'retry': retry})
|
||||
response = None
|
||||
# retry sending the message if we get a Timeout.
|
||||
@ -203,8 +200,8 @@ class NotifyEndpoint(base.BaseEndpoint):
|
||||
"for '%(zone)s' to '%(server)s:%(port)d'. Timeout"
|
||||
"='%(timeout)d' seconds. Retry='%(retry)d'") %
|
||||
{'msg': 'NOTIFY' if notify else 'SOA',
|
||||
'zone': domain.name, 'server': dest_ip,
|
||||
'port': dest_port, 'timeout': timeout,
|
||||
'zone': domain.name, 'server': host,
|
||||
'port': port, 'timeout': timeout,
|
||||
'retry': retry})
|
||||
response = None
|
||||
break
|
||||
@ -213,8 +210,8 @@ class NotifyEndpoint(base.BaseEndpoint):
|
||||
elif response.rcode() in (dns.rcode.NXDOMAIN, dns.rcode.REFUSED,
|
||||
dns.rcode.SERVFAIL):
|
||||
LOG.info(_LI("%(zone)s not found on %(server)s:%(port)d") %
|
||||
{'zone': domain.name, 'server': dest_ip,
|
||||
'port': dest_port})
|
||||
{'zone': domain.name, 'server': host,
|
||||
'port': port})
|
||||
break
|
||||
elif not (response.flags & dns.flags.AA) or dns.rcode.from_flags(
|
||||
response.flags, response.ednsflags) != dns.rcode.NOERROR:
|
||||
@ -222,8 +219,8 @@ class NotifyEndpoint(base.BaseEndpoint):
|
||||
"send '%(msg)s' for '%(zone)s' to '%(server)s:"
|
||||
"%(port)d'.\nResponse message:\n%(resp)s\n") %
|
||||
{'msg': 'NOTIFY' if notify else 'SOA',
|
||||
'zone': domain.name, 'server': dest_ip,
|
||||
'port': dest_port, 'resp': str(response)})
|
||||
'zone': domain.name, 'server': host,
|
||||
'port': port, 'resp': str(response)})
|
||||
response = None
|
||||
break
|
||||
else:
|
||||
@ -252,21 +249,21 @@ class NotifyEndpoint(base.BaseEndpoint):
|
||||
|
||||
return dns_message
|
||||
|
||||
def _send_dns_message(self, dns_message, dest_ip, dest_port, timeout):
|
||||
def _send_dns_message(self, dns_message, host, port, timeout):
|
||||
"""
|
||||
:param dns_message: The dns message that needs to be sent.
|
||||
:param dest_ip: The destination ip of dns_message.
|
||||
:param dest_port: The destination port of dns_message.
|
||||
:param host: The destination ip of dns_message.
|
||||
:param port: The destination port of dns_message.
|
||||
:param timeout: The timeout in seconds to wait for a response.
|
||||
:return: response or dns.exception.Timeout or dns_query.BadResponse
|
||||
"""
|
||||
try:
|
||||
if not CONF['service:mdns'].all_tcp:
|
||||
response = dns_query.udp(
|
||||
dns_message, dest_ip, port=dest_port, timeout=timeout)
|
||||
dns_message, host, port=port, timeout=timeout)
|
||||
else:
|
||||
response = dns_query.tcp(
|
||||
dns_message, dest_ip, port=dest_port, timeout=timeout)
|
||||
dns_message, host, port=port, timeout=timeout)
|
||||
return response
|
||||
except dns.exception.Timeout as timeout:
|
||||
return timeout
|
||||
|
@ -34,11 +34,12 @@ class MdnsAPI(object):
|
||||
|
||||
1.0 - Added notify_zone_changed and poll_for_serial_number.
|
||||
1.1 - Added get_serial_number.
|
||||
2.0 - Changed method signatures
|
||||
|
||||
XFR API version history:
|
||||
1.0 - Added perform_zone_xfr.
|
||||
"""
|
||||
RPC_NOTIFY_API_VERSION = '1.1'
|
||||
RPC_NOTIFY_API_VERSION = '2.0'
|
||||
RPC_XFR_API_VERSION = '1.0'
|
||||
|
||||
def __init__(self, topic=None):
|
||||
@ -47,7 +48,7 @@ class MdnsAPI(object):
|
||||
notify_target = messaging.Target(topic=topic,
|
||||
namespace='notify',
|
||||
version=self.RPC_NOTIFY_API_VERSION)
|
||||
self.notify_client = rpc.get_client(notify_target, version_cap='1.1')
|
||||
self.notify_client = rpc.get_client(notify_target, version_cap='2.0')
|
||||
|
||||
xfr_target = messaging.Target(topic=topic,
|
||||
namespace='xfr',
|
||||
@ -68,17 +69,17 @@ class MdnsAPI(object):
|
||||
MDNS_API = cls()
|
||||
return MDNS_API
|
||||
|
||||
def notify_zone_changed(self, context, domain, nameserver, timeout,
|
||||
def notify_zone_changed(self, context, domain, host, port, timeout,
|
||||
retry_interval, max_retries, delay):
|
||||
LOG.info(_LI("notify_zone_changed: Calling mdns for zone '%(zone)s', "
|
||||
"serial '%(serial)s' to nameserver '%(host)s:%(port)s'") %
|
||||
{'zone': domain.name, 'serial': domain.serial,
|
||||
'host': nameserver.host, 'port': nameserver.port})
|
||||
'host': host, 'port': port})
|
||||
# The notify_zone_changed method is a cast rather than a call since the
|
||||
# caller need not wait for the notify to complete.
|
||||
return self.notify_client.cast(
|
||||
context, 'notify_zone_changed', domain=domain,
|
||||
nameserver=nameserver, timeout=timeout,
|
||||
host=host, port=port, timeout=timeout,
|
||||
retry_interval=retry_interval, max_retries=max_retries,
|
||||
delay=delay)
|
||||
|
||||
@ -98,17 +99,17 @@ class MdnsAPI(object):
|
||||
retry_interval=retry_interval, max_retries=max_retries,
|
||||
delay=delay)
|
||||
|
||||
def get_serial_number(self, context, domain, nameserver, timeout,
|
||||
def get_serial_number(self, context, domain, host, port, timeout,
|
||||
retry_interval, max_retries, delay):
|
||||
LOG.info(
|
||||
_LI("get_serial_number: Calling mdns for zone '%(zone)s', serial "
|
||||
"%(serial)s' on nameserver '%(host)s:%(port)s'") %
|
||||
{'zone': domain.name, 'serial': domain.serial,
|
||||
'host': nameserver.host, 'port': nameserver.port})
|
||||
cctxt = self.notify_client.prepare(version='1.1')
|
||||
'host': host, 'port': port})
|
||||
cctxt = self.notify_client.prepare()
|
||||
return cctxt.call(
|
||||
context, 'get_serial_number', domain=domain,
|
||||
nameserver=nameserver, timeout=timeout,
|
||||
host=host, port=port, timeout=timeout,
|
||||
retry_interval=retry_interval, max_retries=max_retries,
|
||||
delay=delay)
|
||||
|
||||
|
@ -277,7 +277,9 @@ class Service(service.RPCService, coordination.CoordinationMixin,
|
||||
nameserver, domain, CREATE_ACTION)
|
||||
self.cache.store(context, create_status)
|
||||
|
||||
self._update_domain_on_nameserver(context, nameserver, domain)
|
||||
self.mdns_api.poll_for_serial_number(
|
||||
context, domain, nameserver, self.timeout,
|
||||
self.retry_interval, self.max_retries, self.delay)
|
||||
|
||||
def _create_domain_on_target(self, context, target, domain):
|
||||
"""
|
||||
@ -332,7 +334,7 @@ class Service(service.RPCService, coordination.CoordinationMixin,
|
||||
for also_notify in self.pool.also_notifies:
|
||||
self._update_domain_on_also_notify(context, also_notify, domain)
|
||||
|
||||
# Send a NOTIFY to each nameserver
|
||||
# Ensure the change has propogated to each nameserver
|
||||
for nameserver in self.pool.nameservers:
|
||||
# See if there is already another update in progress
|
||||
try:
|
||||
@ -343,7 +345,9 @@ class Service(service.RPCService, coordination.CoordinationMixin,
|
||||
nameserver, domain, UPDATE_ACTION)
|
||||
self.cache.store(context, update_status)
|
||||
|
||||
self._update_domain_on_nameserver(context, nameserver, domain)
|
||||
self.mdns_api.poll_for_serial_number(
|
||||
context, domain, nameserver, self.timeout,
|
||||
self.retry_interval, self.max_retries, self.delay)
|
||||
|
||||
def _update_domain_on_target(self, context, target, domain):
|
||||
"""
|
||||
@ -372,20 +376,8 @@ class Service(service.RPCService, coordination.CoordinationMixin,
|
||||
'server': self._get_destination(also_notify)})
|
||||
|
||||
self.mdns_api.notify_zone_changed(
|
||||
context, domain, also_notify, self.timeout, self.retry_interval,
|
||||
self.max_retries, 0)
|
||||
|
||||
def _update_domain_on_nameserver(self, context, nameserver, domain):
|
||||
LOG.info(_LI('Updating domain %(domain)s on nameserver %(server)s.') %
|
||||
{'domain': domain.name,
|
||||
'server': self._get_destination(nameserver)})
|
||||
|
||||
self.mdns_api.notify_zone_changed(
|
||||
context, domain, nameserver, self.timeout, self.retry_interval,
|
||||
self.max_retries, 0)
|
||||
self.mdns_api.poll_for_serial_number(
|
||||
context, domain, nameserver, self.timeout, self.retry_interval,
|
||||
self.max_retries, self.delay)
|
||||
context, domain, also_notify.host, also_notify.port, self.timeout,
|
||||
self.retry_interval, self.max_retries, 0)
|
||||
|
||||
def delete_domain(self, context, domain):
|
||||
"""
|
||||
@ -628,8 +620,9 @@ class Service(service.RPCService, coordination.CoordinationMixin,
|
||||
try:
|
||||
(status, actual_serial, retries) = \
|
||||
self.mdns_api.get_serial_number(
|
||||
context, domain, nameserver, self.timeout,
|
||||
self.retry_interval, self.max_retries, self.delay)
|
||||
context, domain, nameserver.host, nameserver.port,
|
||||
self.timeout, self.retry_interval, self.max_retries,
|
||||
self.delay)
|
||||
except messaging.MessagingException as msg_ex:
|
||||
LOG.debug('Could not retrieve status and serial for domain %s on '
|
||||
'nameserver %s with action %s (%s: %s)' %
|
||||
|
@ -78,7 +78,7 @@ class InfobloxBackendTestCase(BackendTestCase):
|
||||
def test_update_domain(self):
|
||||
self.set_up_backend()
|
||||
context = self.get_context()
|
||||
domain = self.get_domain_fixture()
|
||||
domain = objects.Domain().from_dict(self.get_domain_fixture())
|
||||
self.backend.update_domain(context, domain)
|
||||
|
||||
def test_delete_domain(self):
|
||||
|
@ -37,7 +37,9 @@ class PowerDNSBackendTestCase(BackendTestCase):
|
||||
'type': 'powerdns',
|
||||
'masters': [{'host': '192.0.2.1', 'port': 53},
|
||||
{'host': '192.0.2.2', 'port': 35}],
|
||||
'options': [{'key': 'connection', 'value': 'memory://'}],
|
||||
'options': [{'key': 'connection', 'value': 'memory://',
|
||||
'key': 'host', 'value': '192.0.2.3',
|
||||
'key': 'port', 'value': 53}],
|
||||
})
|
||||
|
||||
self.backend = impl_powerdns.PowerDNSBackend(self.target)
|
||||
|
@ -61,7 +61,7 @@ class MdnsNotifyTest(MdnsTestCase):
|
||||
binascii.a2b_hex(expected_notify_response))):
|
||||
response, retry = self.notify.notify_zone_changed(
|
||||
context, objects.Domain.from_dict(self.test_domain),
|
||||
self.nameserver, 0, 0, 2, 0)
|
||||
self.nameserver.host, self.nameserver.port, 0, 0, 2, 0)
|
||||
self.assertEqual(response, dns.message.from_wire(
|
||||
binascii.a2b_hex(expected_notify_response)))
|
||||
self.assertEqual(retry, 1)
|
||||
@ -83,7 +83,7 @@ class MdnsNotifyTest(MdnsTestCase):
|
||||
binascii.a2b_hex(non_auth_notify_response))):
|
||||
response, retry = self.notify.notify_zone_changed(
|
||||
context, objects.Domain.from_dict(self.test_domain),
|
||||
self.nameserver, 0, 0, 2, 0)
|
||||
self.nameserver.host, self.nameserver.port, 0, 0, 2, 0)
|
||||
self.assertEqual(response, None)
|
||||
self.assertEqual(retry, 1)
|
||||
|
||||
@ -92,7 +92,7 @@ class MdnsNotifyTest(MdnsTestCase):
|
||||
context = self.get_context()
|
||||
response, retry = self.notify.notify_zone_changed(
|
||||
context, objects.Domain.from_dict(self.test_domain),
|
||||
self.nameserver, 0, 0, 2, 0)
|
||||
self.nameserver.host, self.nameserver.port, 0, 0, 2, 0)
|
||||
self.assertEqual(response, None)
|
||||
self.assertEqual(retry, 2)
|
||||
|
||||
@ -101,7 +101,7 @@ class MdnsNotifyTest(MdnsTestCase):
|
||||
context = self.get_context()
|
||||
response, retry = self.notify.notify_zone_changed(
|
||||
context, objects.Domain.from_dict(self.test_domain),
|
||||
self.nameserver, 0, 0, 2, 0)
|
||||
self.nameserver.host, self.nameserver.port, 0, 0, 2, 0)
|
||||
self.assertEqual(response, None)
|
||||
self.assertEqual(retry, 1)
|
||||
|
||||
@ -126,7 +126,7 @@ class MdnsNotifyTest(MdnsTestCase):
|
||||
binascii.a2b_hex(poll_response))):
|
||||
status, serial, retries = self.notify.get_serial_number(
|
||||
context, objects.Domain.from_dict(self.test_domain),
|
||||
self.nameserver, 0, 0, 2, 0)
|
||||
self.nameserver.host, self.nameserver.port, 0, 0, 2, 0)
|
||||
self.assertEqual(status, 'SUCCESS')
|
||||
self.assertEqual(serial, self.test_domain['serial'])
|
||||
self.assertEqual(retries, 2)
|
||||
@ -152,7 +152,7 @@ class MdnsNotifyTest(MdnsTestCase):
|
||||
binascii.a2b_hex(poll_response))):
|
||||
status, serial, retries = self.notify.get_serial_number(
|
||||
context, objects.Domain.from_dict(self.test_domain),
|
||||
self.nameserver, 0, 0, 2, 0)
|
||||
self.nameserver.host, self.nameserver.port, 0, 0, 2, 0)
|
||||
self.assertEqual(status, 'ERROR')
|
||||
self.assertEqual(serial, 99)
|
||||
self.assertEqual(retries, 0)
|
||||
@ -178,7 +178,7 @@ class MdnsNotifyTest(MdnsTestCase):
|
||||
binascii.a2b_hex(poll_response))):
|
||||
status, serial, retries = self.notify.get_serial_number(
|
||||
context, objects.Domain.from_dict(self.test_domain),
|
||||
self.nameserver, 0, 0, 2, 0)
|
||||
self.nameserver.host, self.nameserver.port, 0, 0, 2, 0)
|
||||
self.assertEqual(status, 'SUCCESS')
|
||||
self.assertEqual(serial, 101)
|
||||
self.assertEqual(retries, 2)
|
||||
@ -188,7 +188,7 @@ class MdnsNotifyTest(MdnsTestCase):
|
||||
context = self.get_context()
|
||||
status, serial, retries = self.notify.get_serial_number(
|
||||
context, objects.Domain.from_dict(self.test_domain),
|
||||
self.nameserver, 0, 0, 2, 0)
|
||||
self.nameserver.host, self.nameserver.port, 0, 0, 2, 0)
|
||||
self.assertEqual(status, 'ERROR')
|
||||
self.assertEqual(serial, None)
|
||||
self.assertEqual(retries, 0)
|
||||
@ -203,8 +203,10 @@ class MdnsNotifyTest(MdnsTestCase):
|
||||
context = self.get_context()
|
||||
test_domain = objects.Domain.from_dict(self.test_domain)
|
||||
status, serial, retries = self.notify.get_serial_number(
|
||||
context, test_domain, self.nameserver, 0, 0, 2, 0)
|
||||
context, test_domain, self.nameserver.host,
|
||||
self.nameserver.port, 0, 0, 2, 0)
|
||||
response, retry = self.notify.notify_zone_changed(
|
||||
context, test_domain, self.nameserver, 0, 0, 2, 0)
|
||||
context, test_domain, self.nameserver.host,
|
||||
self.nameserver.port, 0, 0, 2, 0)
|
||||
assert not udp.called
|
||||
assert tcp.called
|
||||
|
@ -131,15 +131,7 @@ class PoolManagerServiceNoopTest(PoolManagerTestCase):
|
||||
# not return any status
|
||||
self.assertEqual(0, len(create_statuses))
|
||||
|
||||
# Ensure notify_zone_changed and poll_for_serial_number
|
||||
# was called for each nameserver.
|
||||
self.assertEqual(2, mock_notify_zone_changed.call_count)
|
||||
self.assertEqual(
|
||||
[call(self.admin_context, domain,
|
||||
self.service.pool.nameservers[0], 30, 15, 10, 0),
|
||||
call(self.admin_context, domain,
|
||||
self.service.pool.nameservers[1], 30, 15, 10, 0)],
|
||||
mock_notify_zone_changed.call_args_list)
|
||||
# Ensure poll_for_serial_number was called for each nameserver.
|
||||
self.assertEqual(2, mock_poll_for_serial_number.call_count)
|
||||
self.assertEqual(
|
||||
[call(self.admin_context, domain,
|
||||
@ -231,16 +223,7 @@ class PoolManagerServiceNoopTest(PoolManagerTestCase):
|
||||
self.admin_context, domain, 'CREATE')
|
||||
self.assertEqual(0, len(create_statuses))
|
||||
|
||||
# Ensure notify_zone_changed and poll_for_serial_number
|
||||
# was called for each nameserver.
|
||||
self.assertEqual(2, mock_notify_zone_changed.call_count)
|
||||
self.assertEqual(
|
||||
[call(self.admin_context, domain,
|
||||
self.service.pool.nameservers[0], 30, 15, 10, 0),
|
||||
call(self.admin_context, domain,
|
||||
self.service.pool.nameservers[1], 30, 15, 10, 0)],
|
||||
mock_notify_zone_changed.call_args_list)
|
||||
self.assertEqual(2, mock_poll_for_serial_number.call_count)
|
||||
# Ensure poll_for_serial_number was called for each nameserver.
|
||||
self.assertEqual(
|
||||
[call(self.admin_context, domain,
|
||||
self.service.pool.nameservers[0], 30, 15, 10, 5),
|
||||
|
Loading…
x
Reference in New Issue
Block a user