diff --git a/devstack/plugin.sh b/devstack/plugin.sh index 578edf6a..3e3fccc1 100644 --- a/devstack/plugin.sh +++ b/devstack/plugin.sh @@ -59,6 +59,7 @@ function configure_kuryr { configure_auth_token_middleware "$KURYR_CONFIG" kuryr \ "$KURYR_AUTH_CACHE_DIR" neutron iniset $KURYR_CONFIG DEFAULT capability_scope $KURYR_CAPABILITY_SCOPE + iniset $KURYR_CONFIG DEFAULT process_external_connectivity $KURYR_PROCESS_EXTERNAL_CONNECTIVITY fi if [[ "$ENABLE_PLUGINV2" == "True" ]]; then diff --git a/devstack/settings b/devstack/settings index 8004bc46..ce23e60a 100644 --- a/devstack/settings +++ b/devstack/settings @@ -20,6 +20,7 @@ KURYR_POOL_PREFIX=${KURYR_POOL_PREFIX:-10.10.0.0/16} KURYR_POOL_PREFIX_LEN=${KURYR_POOL_PREFIX_LEN:-24} KURYR_CAPABILITY_SCOPE=${KURYR_CAPABILITY_SCOPE:-local} +KURYR_PROCESS_EXTERNAL_CONNECTIVITY=${KURYR_PROCESS_EXTERNAL_CONNECTIVITY:-True} KURYR_DOCKER_ENGINE_PORT=${KURYR_DOCKER_ENGINE_PORT:-2375} DOCKER_CLUSTER_STORE=${DOCKER_CLUSTER_STORE:-etcd://$SERVICE_HOST:$ETCD_PORT} diff --git a/kuryr_libnetwork/config.py b/kuryr_libnetwork/config.py index bc6d37a2..641cd7ce 100644 --- a/kuryr_libnetwork/config.py +++ b/kuryr_libnetwork/config.py @@ -52,6 +52,9 @@ core_opts = [ cfg.ListOpt('enabled_port_drivers', default=['kuryr_libnetwork.port_driver.drivers.veth'], help=_('Available port drivers')), + cfg.BoolOpt('process_external_connectivity', + default=True, + help=_('Do processing external connectivity')), cfg.StrOpt('ssl_cert_file', default='/var/lib/kuryr/certs/cert.pem', help=_('This option allows setting absolute path' diff --git a/kuryr_libnetwork/controllers.py b/kuryr_libnetwork/controllers.py index 7bfd318d..6d23d657 100644 --- a/kuryr_libnetwork/controllers.py +++ b/kuryr_libnetwork/controllers.py @@ -1437,6 +1437,9 @@ def network_driver_program_external_connectivity(): json_data = flask.request.get_json(force=True) LOG.debug("Received JSON data %s for" " /NetworkDriver.ProgramExternalConnectivity", json_data) + if not cfg.CONF.process_external_connectivity: + return flask.jsonify(const.SCHEMA['SUCCESS']) + # TODO(banix): Add support for exposed ports port = _get_neutron_port_from_docker_endpoint(json_data['EndpointID']) if port: @@ -1459,6 +1462,9 @@ def network_driver_revoke_external_connectivity(): json_data = flask.request.get_json(force=True) LOG.debug("Received JSON data %s for" " /NetworkDriver.RevokeExternalConnectivity", json_data) + if not cfg.CONF.process_external_connectivity: + return flask.jsonify(const.SCHEMA['SUCCESS']) + # TODO(banix): Add support for removal of exposed ports port = _get_neutron_port_from_docker_endpoint(json_data['EndpointID']) if port: diff --git a/kuryr_libnetwork/tests/unit/test_external_connectivity.py b/kuryr_libnetwork/tests/unit/test_external_connectivity.py index aef3214b..f9059251 100644 --- a/kuryr_libnetwork/tests/unit/test_external_connectivity.py +++ b/kuryr_libnetwork/tests/unit/test_external_connectivity.py @@ -21,6 +21,7 @@ from oslo_utils import uuidutils from kuryr.lib import constants as lib_const from kuryr.lib import utils as lib_utils +from kuryr_libnetwork import config from kuryr_libnetwork import constants from kuryr_libnetwork.tests.unit import base from kuryr_libnetwork import utils @@ -55,6 +56,7 @@ class TestExternalConnectivityKuryr(base.TestKuryrBase): num_ports, mock_list_ports, mock_create_security_group, mock_create_security_group_rule, mock_show_port, mock_update_port): + config.CONF.set_override('process_external_connectivity', True) fake_docker_net_id = lib_utils.get_hash() fake_docker_endpoint_id = lib_utils.get_hash() @@ -142,6 +144,51 @@ class TestExternalConnectivityKuryr(base.TestKuryrBase): decoded_json = jsonutils.loads(response.data) self.assertEqual(constants.SCHEMA['SUCCESS'], decoded_json) + @mock.patch('kuryr_libnetwork.controllers.app.neutron.update_port') + @mock.patch('kuryr_libnetwork.controllers.app.neutron.show_port') + @mock.patch( + 'kuryr_libnetwork.controllers.app.neutron.create_security_group_rule') + @mock.patch( + 'kuryr_libnetwork.controllers.app.neutron.create_security_group') + @mock.patch('kuryr_libnetwork.controllers.app.neutron.list_ports') + @ddt.data((False, 1), (True, 1), (False, 2), (True, 2)) + @ddt.unpack + def test_network_driver_program_external_connectivity_disabled( + self, existing_sg, + num_ports, mock_list_ports, mock_create_security_group, + mock_create_security_group_rule, mock_show_port, + mock_update_port): + config.CONF.set_override('process_external_connectivity', False) + fake_docker_net_id = lib_utils.get_hash() + fake_docker_endpoint_id = lib_utils.get_hash() + + port_opt = [] + for i in range(num_ports): + port_opt.append({u'Port': PORT + i, u'Proto': PROTOCOL_TCP}) + port_opt.append({u'Port': PORT + i, u'Proto': PROTOCOL_UDP}) + port_opt.append({u'Port': SINGLE_PORT, u'Proto': PROTOCOL_UDP}) + options = {'com.docker.network.endpoint.exposedports': + port_opt, + 'com.docker.network.portmap': + []} + data = { + 'NetworkID': fake_docker_net_id, + 'EndpointID': fake_docker_endpoint_id, + 'Options': options, + } + response = self.app.post('/NetworkDriver.ProgramExternalConnectivity', + content_type='application/json', + data=jsonutils.dumps(data)) + + self.assertEqual(200, response.status_code) + mock_update_port.assert_not_called() + mock_show_port.assert_not_called() + mock_create_security_group_rule.assert_not_called() + mock_create_security_group.assert_not_called() + mock_list_ports.assert_not_called() + decoded_json = jsonutils.loads(response.data) + self.assertEqual(constants.SCHEMA['SUCCESS'], decoded_json) + @mock.patch('kuryr_libnetwork.controllers.app.neutron.update_port') @mock.patch('kuryr_libnetwork.controllers.app.neutron.show_port') @mock.patch( @@ -155,6 +202,7 @@ class TestExternalConnectivityKuryr(base.TestKuryrBase): removing_sg, mock_list_ports, mock_list_security_groups, mock_delete_security_groups, mock_show_port, mock_update_port): + config.CONF.set_override('process_external_connectivity', True) fake_docker_net_id = lib_utils.get_hash() fake_docker_endpoint_id = lib_utils.get_hash() @@ -219,3 +267,38 @@ class TestExternalConnectivityKuryr(base.TestKuryrBase): mock_update_port.assert_not_called() decoded_json = jsonutils.loads(response.data) self.assertEqual(constants.SCHEMA['SUCCESS'], decoded_json) + + @mock.patch('kuryr_libnetwork.controllers.app.neutron.update_port') + @mock.patch('kuryr_libnetwork.controllers.app.neutron.show_port') + @mock.patch( + 'kuryr_libnetwork.controllers.app.neutron.delete_security_group') + @mock.patch( + 'kuryr_libnetwork.controllers.app.neutron.list_security_groups') + @mock.patch('kuryr_libnetwork.controllers.app.neutron.list_ports') + @ddt.data((False, False), (False, True), (True, False), (True, True)) + @ddt.unpack + def test_network_driver_revoke_external_connectivity_disabled( + self, existing_sg, + removing_sg, mock_list_ports, mock_list_security_groups, + mock_delete_security_groups, mock_show_port, + mock_update_port): + config.CONF.set_override('process_external_connectivity', False) + fake_docker_net_id = lib_utils.get_hash() + fake_docker_endpoint_id = lib_utils.get_hash() + + data = { + 'NetworkID': fake_docker_net_id, + 'EndpointID': fake_docker_endpoint_id, + } + response = self.app.post('/NetworkDriver.RevokeExternalConnectivity', + content_type='application/json', + data=jsonutils.dumps(data)) + + self.assertEqual(200, response.status_code) + mock_list_ports.assert_not_called() + mock_list_security_groups.assert_not_called() + mock_delete_security_groups.assert_not_called() + mock_show_port.assert_not_called() + mock_update_port.assert_not_called() + decoded_json = jsonutils.loads(response.data) + self.assertEqual(constants.SCHEMA['SUCCESS'], decoded_json)