From 57776776d4b639c0356d58277307d18d0123742a Mon Sep 17 00:00:00 2001 From: Adit Sarfaty Date: Thu, 6 Dec 2018 13:54:56 +0200 Subject: [PATCH] Policy plugin: Add devstack/admin-utils for client auth Adding devstack support for policy plugin with certificate and the certificate admin utilis which are needed for the devstack support. Change-Id: I5c9d23c7f0a83cbf4cb71fed4da488bafa230be4 --- devstack/lib/vmware_nsx_p | 7 + doc/source/admin_util.rst | 23 ++ vmware_nsx/plugins/nsx_v3/utils.py | 27 +- .../admin/plugins/common/v3_common_cert.py | 250 ++++++++++++++++++ .../plugins/nsxp/resources/certificates.py | 73 +++++ .../plugins/nsxv3/resources/certificates.py | 216 +-------------- .../admin/plugins/nsxv3/resources/utils.py | 14 +- vmware_nsx/shell/resources.py | 6 + 8 files changed, 389 insertions(+), 227 deletions(-) create mode 100644 vmware_nsx/shell/admin/plugins/common/v3_common_cert.py create mode 100644 vmware_nsx/shell/admin/plugins/nsxp/resources/certificates.py diff --git a/devstack/lib/vmware_nsx_p b/devstack/lib/vmware_nsx_p index 30cc749de5..738f490797 100644 --- a/devstack/lib/vmware_nsx_p +++ b/devstack/lib/vmware_nsx_p @@ -201,6 +201,13 @@ function nsxp_configure_service { _nsxp_ini_set retries $NSX_RETRIES _nsxp_ini_set insecure $NSX_INSECURE _nsxp_ini_set ca_file $NSX_CA_FILE + + if [[ "$NSX_USE_CLIENT_CERT_AUTH" == "True" ]]; then + _nsxp_ini_set nsx_use_client_auth "True" + _nsxp_ini_set nsx_client_cert_file "$CLIENT_CERT_FILE" + _nsxp_ini_set nsx_client_cert_storage "nsx-db" + _nsxp_ini_set nsx_client_cert_pk_password "openstack" + fi } function init_vmware_nsx_p { diff --git a/doc/source/admin_util.rst b/doc/source/admin_util.rst index 12bfd7e95e..92ec730471 100644 --- a/doc/source/admin_util.rst +++ b/doc/source/admin_util.rst @@ -597,6 +597,29 @@ NSX Policy Plugin nsxadmin -r routers -o list +Client Certificate +~~~~~~~~~~~~~~~~~~ + +- Generate new client certificate (this command will delete previous certificate if exists):: + + nsxadmin -r certificate -o generate [--property username= --property password= --property key-size= --property sig-alg= --property valid-days= --property country= --property state= --property org= --property unit= --property host=] + +- Delete client certificate:: + + nsxadmin -r certificate -o clean + +- Show client certificate details:: + + nsxadmin -r certificate -o show + +- Import external certificate to NSX:: + + nsxadmin -r certificate -o import [--property username= --property password= --property filename=] + +- List certificates associated with openstack principal identity in NSX:: + + nsxadmin -r certificate -o nsx-list + Upgrade Steps (NSX-T Version 1.0.0 to Version 1.1.0) ---------------------------------------------------- diff --git a/vmware_nsx/plugins/nsx_v3/utils.py b/vmware_nsx/plugins/nsx_v3/utils.py index e320bebbec..3ad33f490e 100644 --- a/vmware_nsx/plugins/nsx_v3/utils.py +++ b/vmware_nsx/plugins/nsx_v3/utils.py @@ -137,26 +137,29 @@ def get_client_cert_provider(conf_path=cfg.CONF.nsx_v3): return DbCertProvider -def get_nsxlib_wrapper(nsx_username=None, nsx_password=None, basic_auth=False): +def get_nsxlib_wrapper(nsx_username=None, nsx_password=None, basic_auth=False, + plugin_conf=None): client_cert_provider = None if not basic_auth: # if basic auth requested, dont use cert file even if provided client_cert_provider = get_client_cert_provider() + if not plugin_conf: + plugin_conf = cfg.CONF.nsx_v3 nsxlib_config = config.NsxLibConfig( - username=nsx_username or cfg.CONF.nsx_v3.nsx_api_user, - password=nsx_password or cfg.CONF.nsx_v3.nsx_api_password, + username=nsx_username or plugin_conf.nsx_api_user, + password=nsx_password or plugin_conf.nsx_api_password, client_cert_provider=client_cert_provider, - retries=cfg.CONF.nsx_v3.http_retries, - insecure=cfg.CONF.nsx_v3.insecure, - ca_file=cfg.CONF.nsx_v3.ca_file, - concurrent_connections=cfg.CONF.nsx_v3.concurrent_connections, - http_timeout=cfg.CONF.nsx_v3.http_timeout, - http_read_timeout=cfg.CONF.nsx_v3.http_read_timeout, - conn_idle_timeout=cfg.CONF.nsx_v3.conn_idle_timeout, + retries=plugin_conf.http_retries, + insecure=plugin_conf.insecure, + ca_file=plugin_conf.ca_file, + concurrent_connections=plugin_conf.concurrent_connections, + http_timeout=plugin_conf.http_timeout, + http_read_timeout=plugin_conf.http_read_timeout, + conn_idle_timeout=plugin_conf.conn_idle_timeout, http_provider=None, - max_attempts=cfg.CONF.nsx_v3.retries, - nsx_api_managers=cfg.CONF.nsx_v3.nsx_api_managers, + max_attempts=plugin_conf.retries, + nsx_api_managers=plugin_conf.nsx_api_managers, plugin_scope=OS_NEUTRON_ID_SCOPE, plugin_tag=NSX_NEUTRON_PLUGIN, plugin_ver=n_version.version_info.release_string(), diff --git a/vmware_nsx/shell/admin/plugins/common/v3_common_cert.py b/vmware_nsx/shell/admin/plugins/common/v3_common_cert.py new file mode 100644 index 0000000000..55431bb33f --- /dev/null +++ b/vmware_nsx/shell/admin/plugins/common/v3_common_cert.py @@ -0,0 +1,250 @@ +# Copyright 2018 VMware, Inc. All rights reserved. +# +# 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 + +from neutron_lib import context + +from vmware_nsx.plugins.nsx_v3 import cert_utils +from vmware_nsx.shell.admin.plugins.common import utils as admin_utils +from vmware_nsx.shell.admin.plugins.nsxv3.resources import utils +from vmware_nsxlib.v3 import client_cert +from vmware_nsxlib.v3 import exceptions +from vmware_nsxlib.v3 import trust_management + + +LOG = logging.getLogger(__name__) + +CERT_DEFAULTS = {'key-size': 2048, + 'sig-alg': 'sha256', + 'valid-days': 3650, + 'country': 'US', + 'state': 'California', + 'org': 'default org', + 'unit': 'default unit', + 'host': 'defaulthost.org'} + + +def get_nsx_trust_management(plugin_conf, **kwargs): + username, password = None, None + if kwargs.get('property'): + properties = admin_utils.parse_multi_keyval_opt(kwargs['property']) + username = properties.get('user') + password = properties.get('password') + + nsx_client = utils.get_nsxv3_client(username, password, True, + plugin_conf=plugin_conf) + nsx_trust = trust_management.NsxLibTrustManagement(nsx_client, {}) + return nsx_trust + + +def get_certificate_manager(plugin_conf, **kwargs): + storage_driver_type = plugin_conf.nsx_client_cert_storage.lower() + LOG.info("Certificate storage is %s", storage_driver_type) + if storage_driver_type == 'nsx-db': + storage_driver = cert_utils.DbCertificateStorageDriver( + context.get_admin_context()) + elif storage_driver_type == 'none': + storage_driver = cert_utils.DummyCertificateStorageDriver() + # TODO(annak) - add support for barbican storage driver + + return client_cert.ClientCertificateManager( + cert_utils.NSX_OPENSTACK_IDENTITY, + get_nsx_trust_management(plugin_conf, **kwargs), + storage_driver) + + +def verify_client_cert_on(plugin_conf): + if plugin_conf.nsx_use_client_auth: + return True + + LOG.info("Operation not applicable since client authentication " + "is disabled") + return False + + +def generate_cert(plugin_conf, **kwargs): + """Generate self signed client certificate and private key + """ + + if not verify_client_cert_on(plugin_conf): + return + + if plugin_conf.nsx_client_cert_storage.lower() == "none": + LOG.info("Generate operation is not supported " + "with storage type 'none'") + return + + # update cert defaults based on user input + properties = CERT_DEFAULTS.copy() + if kwargs.get('property'): + properties.update(admin_utils.parse_multi_keyval_opt( + kwargs['property'])) + + try: + prop = 'key-size' + key_size = int(properties.get(prop)) + prop = 'valid-days' + valid_for_days = int(properties.get(prop)) + except ValueError: + LOG.info("%s property must be a number", prop) + return + + signature_alg = properties.get('sig-alg') + subject = {} + subject[client_cert.CERT_SUBJECT_COUNTRY] = properties.get('country') + subject[client_cert.CERT_SUBJECT_STATE] = properties.get('state') + subject[client_cert.CERT_SUBJECT_ORG] = properties.get('org') + subject[client_cert.CERT_SUBJECT_UNIT] = properties.get('org') + subject[client_cert.CERT_SUBJECT_HOST] = properties.get('host') + + regenerate = False + with get_certificate_manager(plugin_conf, **kwargs) as cert: + if cert.exists(): + LOG.info("Deleting existing certificate") + # Need to delete cert first + cert.delete() + regenerate = True + + try: + cert.generate(subject, key_size, valid_for_days, signature_alg) + except exceptions.NsxLibInvalidInput as e: + LOG.info(e) + return + + LOG.info("Client certificate generated successfully") + if not regenerate: + # No certificate existed, so client authentication service was likely + # changed to true just now. The user must restart neutron to avoid + # failures. + LOG.info("Please restart neutron service") + + +def delete_cert(plugin_conf, **kwargs): + """Delete client certificate and private key """ + if not verify_client_cert_on(plugin_conf): + return + + with get_certificate_manager(plugin_conf, **kwargs) as cert: + if plugin_conf.nsx_client_cert_storage.lower() == "none": + filename = get_cert_filename(plugin_conf, **kwargs) + if not filename: + LOG.info("Please specify file containing the certificate " + "using filename property") + return + cert.delete_pem(filename) + else: + if not cert.exists(): + LOG.info("Nothing to clean") + return + + cert.delete() + LOG.info("Client certificate deleted successfully") + + +def show_cert(plugin_conf, **kwargs): + """Show client certificate details """ + + if not verify_client_cert_on(plugin_conf): + return + + with get_certificate_manager(plugin_conf, **kwargs) as cert: + if cert.exists(): + cert_pem, key_pem = cert.get_pem() + expires_on = cert.expires_on() + expires_in_days = cert.expires_in_days() + cert_data = cert.get_subject() + cert_data['alg'] = cert.get_signature_alg() + cert_data['key_size'] = cert.get_key_size() + if expires_in_days >= 0: + LOG.info("Client certificate is valid. " + "Expires on %(date)s UTC (in %(days)d days).", + {'date': expires_on, + 'days': expires_in_days}) + + else: + LOG.info("Client certificate expired on %s.", expires_on) + + LOG.info("Key Size %(key_size)s, " + "Signature Algorithm %(alg)s\n" + "Subject: Country %(country)s, State %(state)s, " + "Organization %(organization)s, Unit %(unit)s, " + "Common Name %(hostname)s", cert_data) + + LOG.info(cert_pem) + else: + LOG.info("Client certificate is not registered " + "in storage") + + +def get_cert_filename(plugin_conf, **kwargs): + filename = plugin_conf.nsx_client_cert_file + if kwargs.get('property'): + properties = admin_utils.parse_multi_keyval_opt(kwargs['property']) + filename = properties.get('filename', filename) + + if not filename: + LOG.info("Please specify file containing the certificate " + "using filename property") + return filename + + +def import_cert(plugin_conf, **kwargs): + """Import client certificate that was generated externally""" + if not verify_client_cert_on(plugin_conf): + return + + if plugin_conf.nsx_client_cert_storage.lower() != "none": + LOG.info("Import operation is supported " + "with storage type 'none' only") + return + + with get_certificate_manager(plugin_conf, **kwargs) as cert: + if cert.exists(): + LOG.info("Deleting existing certificate") + cert.delete() + + filename = get_cert_filename(plugin_conf, **kwargs) + if not filename: + return + cert.import_pem(filename) + + LOG.info("Client certificate imported successfully") + + +def show_nsx_certs(plugin_conf, **kwargs): + """Show client certificates associated with openstack identity in NSX""" + + # Note - this operation is supported even if the feature is disabled + nsx_trust = get_nsx_trust_management(plugin_conf, **kwargs) + + ids = nsx_trust.get_identities(cert_utils.NSX_OPENSTACK_IDENTITY) + if not ids: + LOG.info("Principal identity %s not found", + cert_utils.NSX_OPENSTACK_IDENTITY) + return + + LOG.info("Certificate(s) associated with principal identity %s\n", + cert_utils.NSX_OPENSTACK_IDENTITY) + + cert = None + for identity in ids: + if 'certificate_id' in identity: + cert = nsx_trust.get_cert(identity['certificate_id']) + + LOG.info(cert['pem_encoded']) + + if not cert: + LOG.info("No certificates found") diff --git a/vmware_nsx/shell/admin/plugins/nsxp/resources/certificates.py b/vmware_nsx/shell/admin/plugins/nsxp/resources/certificates.py new file mode 100644 index 0000000000..f714d8d2b3 --- /dev/null +++ b/vmware_nsx/shell/admin/plugins/nsxp/resources/certificates.py @@ -0,0 +1,73 @@ +# Copyright 2018 VMware, Inc. All rights reserved. +# +# 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 vmware_nsx.shell.admin.plugins.common import constants +from vmware_nsx.shell.admin.plugins.common import utils as admin_utils +from vmware_nsx.shell.admin.plugins.common import v3_common_cert +from vmware_nsx.shell import resources as shell + +from neutron_lib.callbacks import registry +from oslo_config import cfg + + +@admin_utils.output_header +def generate_cert(resource, event, trigger, **kwargs): + """Generate self signed client certificate and private key + """ + return v3_common_cert.generate_cert(cfg.CONF.nsx_p, **kwargs) + + +@admin_utils.output_header +def delete_cert(resource, event, trigger, **kwargs): + """Delete client certificate and private key """ + return v3_common_cert.delete_cert(cfg.CONF.nsx_p, **kwargs) + + +@admin_utils.output_header +def show_cert(resource, event, trigger, **kwargs): + """Show client certificate details """ + return v3_common_cert.show_cert(cfg.CONF.nsx_p, **kwargs) + + +@admin_utils.output_header +def import_cert(resource, event, trigger, **kwargs): + """Import client certificate that was generated externally""" + return v3_common_cert.import_cert(cfg.CONF.nsx_p, **kwargs) + + +@admin_utils.output_header +def show_nsx_certs(resource, event, trigger, **kwargs): + """Show client certificates associated with openstack identity in NSX""" + return v3_common_cert.show_nsx_certs(cfg.CONF.nsx_p, **kwargs) + + +registry.subscribe(generate_cert, + constants.CERTIFICATE, + shell.Operations.GENERATE.value) + +registry.subscribe(show_cert, + constants.CERTIFICATE, + shell.Operations.SHOW.value) + +registry.subscribe(delete_cert, + constants.CERTIFICATE, + shell.Operations.CLEAN.value) + +registry.subscribe(import_cert, + constants.CERTIFICATE, + shell.Operations.IMPORT.value) + +registry.subscribe(show_nsx_certs, + constants.CERTIFICATE, + shell.Operations.NSX_LIST.value) diff --git a/vmware_nsx/shell/admin/plugins/nsxv3/resources/certificates.py b/vmware_nsx/shell/admin/plugins/nsxv3/resources/certificates.py index 84fa21a56b..b561ea9426 100644 --- a/vmware_nsx/shell/admin/plugins/nsxv3/resources/certificates.py +++ b/vmware_nsx/shell/admin/plugins/nsxv3/resources/certificates.py @@ -13,248 +13,44 @@ # under the License. -from oslo_log import log as logging - -from vmware_nsx.plugins.nsx_v3 import cert_utils from vmware_nsx.shell.admin.plugins.common import constants from vmware_nsx.shell.admin.plugins.common import utils as admin_utils -from vmware_nsx.shell.admin.plugins.nsxv3.resources import utils +from vmware_nsx.shell.admin.plugins.common import v3_common_cert from vmware_nsx.shell import resources as shell -from vmware_nsxlib.v3 import client_cert -from vmware_nsxlib.v3 import exceptions -from vmware_nsxlib.v3 import trust_management from neutron_lib.callbacks import registry -from neutron_lib import context from oslo_config import cfg -LOG = logging.getLogger(__name__) - -CERT_DEFAULTS = {'key-size': 2048, - 'sig-alg': 'sha256', - 'valid-days': 3650, - 'country': 'US', - 'state': 'California', - 'org': 'default org', - 'unit': 'default unit', - 'host': 'defaulthost.org'} - - -def get_nsx_trust_management(**kwargs): - username, password = None, None - if kwargs.get('property'): - properties = admin_utils.parse_multi_keyval_opt(kwargs['property']) - username = properties.get('user') - password = properties.get('password') - - nsx_client = utils.get_nsxv3_client(username, password, True) - nsx_trust = trust_management.NsxLibTrustManagement(nsx_client, {}) - return nsx_trust - - -def get_certificate_manager(**kwargs): - storage_driver_type = cfg.CONF.nsx_v3.nsx_client_cert_storage.lower() - LOG.info("Certificate storage is %s", storage_driver_type) - if storage_driver_type == 'nsx-db': - storage_driver = cert_utils.DbCertificateStorageDriver( - context.get_admin_context()) - elif storage_driver_type == 'none': - storage_driver = cert_utils.DummyCertificateStorageDriver() - # TODO(annak) - add support for barbican storage driver - - return client_cert.ClientCertificateManager( - cert_utils.NSX_OPENSTACK_IDENTITY, - get_nsx_trust_management(**kwargs), - storage_driver) - - -def verify_client_cert_on(): - if cfg.CONF.nsx_v3.nsx_use_client_auth: - return True - - LOG.info("Operation not applicable since client authentication " - "is disabled") - return False - @admin_utils.output_header def generate_cert(resource, event, trigger, **kwargs): """Generate self signed client certificate and private key """ - - if not verify_client_cert_on(): - return - - if cfg.CONF.nsx_v3.nsx_client_cert_storage.lower() == "none": - LOG.info("Generate operation is not supported " - "with storage type 'none'") - return - - # update cert defaults based on user input - properties = CERT_DEFAULTS.copy() - if kwargs.get('property'): - properties.update(admin_utils.parse_multi_keyval_opt( - kwargs['property'])) - - try: - prop = 'key-size' - key_size = int(properties.get(prop)) - prop = 'valid-days' - valid_for_days = int(properties.get(prop)) - except ValueError: - LOG.info("%s property must be a number", prop) - return - - signature_alg = properties.get('sig-alg') - subject = {} - subject[client_cert.CERT_SUBJECT_COUNTRY] = properties.get('country') - subject[client_cert.CERT_SUBJECT_STATE] = properties.get('state') - subject[client_cert.CERT_SUBJECT_ORG] = properties.get('org') - subject[client_cert.CERT_SUBJECT_UNIT] = properties.get('org') - subject[client_cert.CERT_SUBJECT_HOST] = properties.get('host') - - regenerate = False - with get_certificate_manager(**kwargs) as cert: - if cert.exists(): - LOG.info("Deleting existing certificate") - # Need to delete cert first - cert.delete() - regenerate = True - - try: - cert.generate(subject, key_size, valid_for_days, signature_alg) - except exceptions.NsxLibInvalidInput as e: - LOG.info(e) - return - - LOG.info("Client certificate generated successfully") - if not regenerate: - # No certificate existed, so client authentication service was likely - # changed to true just now. The user must restart neutron to avoid - # failures. - LOG.info("Please restart neutron service") + return v3_common_cert.generate_cert(cfg.CONF.nsx_v3, **kwargs) @admin_utils.output_header def delete_cert(resource, event, trigger, **kwargs): """Delete client certificate and private key """ - if not verify_client_cert_on(): - return - - with get_certificate_manager(**kwargs) as cert: - if cfg.CONF.nsx_v3.nsx_client_cert_storage.lower() == "none": - filename = get_cert_filename(**kwargs) - if not filename: - LOG.info("Please specify file containing the certificate " - "using filename property") - return - cert.delete_pem(filename) - else: - if not cert.exists(): - LOG.info("Nothing to clean") - return - - cert.delete() - LOG.info("Client certificate deleted successfully") + return v3_common_cert.delete_cert(cfg.CONF.nsx_v3, **kwargs) @admin_utils.output_header def show_cert(resource, event, trigger, **kwargs): """Show client certificate details """ - - if not verify_client_cert_on(): - return - - with get_certificate_manager(**kwargs) as cert: - if cert.exists(): - cert_pem, key_pem = cert.get_pem() - expires_on = cert.expires_on() - expires_in_days = cert.expires_in_days() - cert_data = cert.get_subject() - cert_data['alg'] = cert.get_signature_alg() - cert_data['key_size'] = cert.get_key_size() - if expires_in_days >= 0: - LOG.info("Client certificate is valid. " - "Expires on %(date)s UTC (in %(days)d days).", - {'date': expires_on, - 'days': expires_in_days}) - - else: - LOG.info("Client certificate expired on %s.", expires_on) - - LOG.info("Key Size %(key_size)s, " - "Signature Algorithm %(alg)s\n" - "Subject: Country %(country)s, State %(state)s, " - "Organization %(organization)s, Unit %(unit)s, " - "Common Name %(hostname)s", cert_data) - - LOG.info(cert_pem) - else: - LOG.info("Client certificate is not registered " - "in storage") - - -def get_cert_filename(**kwargs): - filename = cfg.CONF.nsx_v3.nsx_client_cert_file - if kwargs.get('property'): - properties = admin_utils.parse_multi_keyval_opt(kwargs['property']) - filename = properties.get('filename', filename) - - if not filename: - LOG.info("Please specify file containing the certificate " - "using filename property") - return filename + return v3_common_cert.show_cert(cfg.CONF.nsx_v3, **kwargs) @admin_utils.output_header def import_cert(resource, event, trigger, **kwargs): """Import client certificate that was generated externally""" - if not verify_client_cert_on(): - return - - if cfg.CONF.nsx_v3.nsx_client_cert_storage.lower() != "none": - LOG.info("Import operation is supported " - "with storage type 'none' only") - return - - with get_certificate_manager(**kwargs) as cert: - if cert.exists(): - LOG.info("Deleting existing certificate") - cert.delete() - - filename = get_cert_filename(**kwargs) - if not filename: - return - cert.import_pem(filename) - - LOG.info("Client certificate imported successfully") + return v3_common_cert.import_cert(cfg.CONF.nsx_v3, **kwargs) @admin_utils.output_header def show_nsx_certs(resource, event, trigger, **kwargs): """Show client certificates associated with openstack identity in NSX""" - - # Note - this operation is supported even if the feature is disabled - nsx_trust = get_nsx_trust_management(**kwargs) - - ids = nsx_trust.get_identities(cert_utils.NSX_OPENSTACK_IDENTITY) - if not ids: - LOG.info("Principal identity %s not found", - cert_utils.NSX_OPENSTACK_IDENTITY) - return - - LOG.info("Certificate(s) associated with principal identity %s\n", - cert_utils.NSX_OPENSTACK_IDENTITY) - - cert = None - for identity in ids: - if 'certificate_id' in identity: - cert = nsx_trust.get_cert(identity['certificate_id']) - - LOG.info(cert['pem_encoded']) - - if not cert: - LOG.info("No certificates found") + return v3_common_cert.show_nsx_certs(cfg.CONF.nsx_v3, **kwargs) registry.subscribe(generate_cert, diff --git a/vmware_nsx/shell/admin/plugins/nsxv3/resources/utils.py b/vmware_nsx/shell/admin/plugins/nsxv3/resources/utils.py index d27f5be025..f3e59d2fa3 100644 --- a/vmware_nsx/shell/admin/plugins/nsxv3/resources/utils.py +++ b/vmware_nsx/shell/admin/plugins/nsxv3/resources/utils.py @@ -44,24 +44,28 @@ _NSXLIB = None def get_nsxv3_client(nsx_username=None, nsx_password=None, - use_basic_auth=False): + use_basic_auth=False, + plugin_conf=None): return get_connected_nsxlib(nsx_username, nsx_password, - use_basic_auth).client + use_basic_auth, + plugin_conf).client def get_connected_nsxlib(nsx_username=None, nsx_password=None, - use_basic_auth=False): + use_basic_auth=False, + plugin_conf=None): global _NSXLIB # for non-default agruments, initiate new lib if nsx_username or use_basic_auth: return v3_utils.get_nsxlib_wrapper(nsx_username, nsx_password, - use_basic_auth) + use_basic_auth, + plugin_conf) if _NSXLIB is None: - _NSXLIB = v3_utils.get_nsxlib_wrapper() + _NSXLIB = v3_utils.get_nsxlib_wrapper(plugin_conf=plugin_conf) return _NSXLIB diff --git a/vmware_nsx/shell/resources.py b/vmware_nsx/shell/resources.py index ec4997dd3f..033bf33318 100644 --- a/vmware_nsx/shell/resources.py +++ b/vmware_nsx/shell/resources.py @@ -248,6 +248,12 @@ nsxp_resources = { [Operations.LIST.value]), constants.ROUTERS: Resource(constants.ROUTERS, [Operations.LIST.value]), + constants.CERTIFICATE: Resource(constants.CERTIFICATE, + [Operations.GENERATE.value, + Operations.SHOW.value, + Operations.CLEAN.value, + Operations.IMPORT.value, + Operations.NSX_LIST.value]), } nsxv3_resources_names = list(nsxv3_resources.keys())