[OVN] Allow to execute ``MetadataProxyHandler`` in a local thread
If configuration option "metadata_workers=0", the OVN metadata agent
will try to spawn the ``MetadataProxyHandler`` instance inside a local
thread, instead of creating a new process. In this case, the method
``MetadataProxyHandler.post_fork_initialize`` is never called and the
SB IDL is never created.
This patch passes the OVN metadata agent SB IDL instance to the proxy
handler instance. This also reduces the number of OVN database active
connections.
Closes-Bug: #1993181
Change-Id: If9d827228002de7e3a55be660da266b60b0dfb79
(cherry picked from commit f43891bf86
)
This commit is contained in:
parent
dd7fc47684
commit
c8409a33d9
|
@ -242,11 +242,6 @@ class MetadataAgent(object):
|
|||
self.ovs_idl = ovsdb.MetadataAgentOvsIdl().start()
|
||||
self._load_config()
|
||||
|
||||
# Launch the server that will act as a proxy between the VM's and Nova.
|
||||
proxy = metadata_server.UnixDomainMetadataProxy(self.conf,
|
||||
self.chassis)
|
||||
proxy.run()
|
||||
|
||||
tables = ('Encap', 'Port_Binding', 'Datapath_Binding', 'SB_Global',
|
||||
'Chassis')
|
||||
events = (PortBindingChassisCreatedEvent(self),
|
||||
|
@ -272,13 +267,18 @@ class MetadataAgent(object):
|
|||
# Now IDL connections can be safely used.
|
||||
self._post_fork_event.set()
|
||||
|
||||
# Launch the server that will act as a proxy between the VM's and Nova.
|
||||
self._proxy = metadata_server.UnixDomainMetadataProxy(
|
||||
self.conf, self.chassis, sb_idl=self.sb_idl)
|
||||
self._proxy.run()
|
||||
|
||||
# Do the initial sync.
|
||||
self.sync()
|
||||
|
||||
# Register the agent with its corresponding Chassis
|
||||
self.register_metadata_agent()
|
||||
|
||||
proxy.wait()
|
||||
self._proxy.wait()
|
||||
|
||||
@tenacity.retry(
|
||||
wait=tenacity.wait_exponential(
|
||||
|
|
|
@ -44,10 +44,10 @@ MODE_MAP = {
|
|||
|
||||
class MetadataProxyHandler(object):
|
||||
|
||||
def __init__(self, conf, chassis):
|
||||
def __init__(self, conf, chassis, sb_idl):
|
||||
self.conf = conf
|
||||
self.chassis = chassis
|
||||
self._sb_idl = None
|
||||
self._sb_idl = sb_idl
|
||||
self._post_fork_event = threading.Event()
|
||||
self.subscribe()
|
||||
|
||||
|
@ -193,9 +193,10 @@ class MetadataProxyHandler(object):
|
|||
|
||||
class UnixDomainMetadataProxy(object):
|
||||
|
||||
def __init__(self, conf, chassis):
|
||||
def __init__(self, conf, chassis, sb_idl=None):
|
||||
self.conf = conf
|
||||
self.chassis = chassis
|
||||
self.sb_idl = sb_idl
|
||||
agent_utils.ensure_directory_exists_without_file(
|
||||
cfg.CONF.metadata_proxy_socket)
|
||||
|
||||
|
@ -224,7 +225,9 @@ class UnixDomainMetadataProxy(object):
|
|||
md_workers = self.conf.metadata_workers
|
||||
if md_workers is None:
|
||||
md_workers = 2
|
||||
self.server.start(MetadataProxyHandler(self.conf, self.chassis),
|
||||
sb_idl = self.sb_idl if md_workers == 0 else None
|
||||
self.server.start(MetadataProxyHandler(self.conf, self.chassis,
|
||||
sb_idl),
|
||||
self.conf.metadata_proxy_socket,
|
||||
workers=md_workers,
|
||||
backlog=self.conf.metadata_backlog,
|
||||
|
|
|
@ -87,18 +87,17 @@ class TestMetadataAgent(base.TestOVNFunctionalBase):
|
|||
|
||||
ovn_sb_db = self.ovsdb_server_mgr.get_ovsdb_connection_path('sb')
|
||||
conf.set_override('ovn_sb_connection', ovn_sb_db, group='ovn')
|
||||
|
||||
# We don't need the HA proxy server running for now
|
||||
p = mock.patch.object(metadata_server, 'UnixDomainMetadataProxy')
|
||||
p.start()
|
||||
self.addCleanup(p.stop)
|
||||
conf.set_override('metadata_workers', '0')
|
||||
|
||||
self.chassis_name = self.add_fake_chassis(self.FAKE_CHASSIS_HOST)
|
||||
mock.patch.object(agent.MetadataAgent,
|
||||
'_get_own_chassis_name',
|
||||
return_value=self.chassis_name).start()
|
||||
agt = agent.MetadataAgent(conf)
|
||||
with mock.patch.object(metadata_server.UnixDomainMetadataProxy,
|
||||
'wait'):
|
||||
agt.start()
|
||||
|
||||
# Metadata agent will open connections to OVS and SB databases.
|
||||
# Close connections to them when the test ends,
|
||||
self.addCleanup(agt.ovs_idl.ovsdb_connection.stop)
|
||||
|
@ -338,3 +337,9 @@ class TestMetadataAgent(base.TestOVNFunctionalBase):
|
|||
else:
|
||||
self.fail('Rule not found in "mangle" table, in namespace %s' %
|
||||
namespace)
|
||||
|
||||
def test_metadata_proxy_handler_idl(self):
|
||||
# This test relies on the configuration option metadata_workers=0
|
||||
proxy_sb_idl = self.agent._proxy.server._server._application.sb_idl
|
||||
agent_sb_idl = self.agent.sb_idl
|
||||
self.assertEqual(agent_sb_idl, proxy_sb_idl)
|
||||
|
|
|
@ -55,8 +55,8 @@ class TestMetadataProxyHandler(base.BaseTestCase):
|
|||
self.useFixture(self.fake_conf_fixture)
|
||||
self.log_p = mock.patch.object(agent, 'LOG')
|
||||
self.log = self.log_p.start()
|
||||
self.handler = agent.MetadataProxyHandler(self.fake_conf, 'chassis1')
|
||||
self.handler.sb_idl = mock.Mock()
|
||||
self.handler = agent.MetadataProxyHandler(self.fake_conf, 'chassis1',
|
||||
mock.Mock())
|
||||
self.handler._post_fork_event.set()
|
||||
|
||||
def test_call(self):
|
||||
|
|
Loading…
Reference in New Issue