Make _discover_extensions public

Heat uses `novaclient.shell.OpenStackComputeShell._discover_extensions`
function, which is private currently. It's better to change this method
to public for public use.

Change-Id: I15879d56db2ec88a9bef99b6af8924ebd4ad169b
Closes-bug: #1440779
This commit is contained in:
kylin7-sg 2015-04-07 15:23:14 +08:00
parent 2a7c2f14c2
commit 02c04c5658
3 changed files with 73 additions and 66 deletions

View File

@ -22,8 +22,12 @@ OpenStack Client interface. Handles the REST calls and responses.
import copy import copy
import functools import functools
import glob
import hashlib import hashlib
import imp
import itertools
import logging import logging
import os
import pkgutil import pkgutil
import re import re
import socket import socket
@ -32,6 +36,7 @@ import warnings
from keystoneclient import adapter from keystoneclient import adapter
from oslo_utils import importutils from oslo_utils import importutils
from oslo_utils import netutils from oslo_utils import netutils
import pkg_resources
import requests import requests
from requests import adapters from requests import adapters
@ -43,6 +48,7 @@ except ImportError:
from six.moves.urllib import parse from six.moves.urllib import parse
from novaclient import exceptions from novaclient import exceptions
from novaclient import extension as ext
from novaclient.i18n import _, _LW from novaclient.i18n import _, _LW
from novaclient import service_catalog from novaclient import service_catalog
from novaclient import utils from novaclient import utils
@ -713,6 +719,61 @@ def _construct_http_client(username=None, password=None, project_id=None,
connection_pool=connection_pool) connection_pool=connection_pool)
def discover_extensions(version):
extensions = []
for name, module in itertools.chain(
_discover_via_python_path(),
_discover_via_contrib_path(version),
_discover_via_entry_points()):
extension = ext.Extension(name, module)
extensions.append(extension)
return extensions
def _discover_via_python_path():
for (module_loader, name, _ispkg) in pkgutil.iter_modules():
if name.endswith('_python_novaclient_ext'):
if not hasattr(module_loader, 'load_module'):
# Python 2.6 compat: actually get an ImpImporter obj
module_loader = module_loader.find_module(name)
module = module_loader.load_module(name)
if hasattr(module, 'extension_name'):
name = module.extension_name
yield name, module
def _discover_via_contrib_path(version):
module_path = os.path.dirname(os.path.abspath(__file__))
version_str = "v%s" % version.replace('.', '_')
# NOTE(andreykurilin): v1.1 uses implementation of v2, so we should
# discover contrib modules in novaclient.v2 dir.
if version_str == "v1_1":
version_str = "v2"
ext_path = os.path.join(module_path, version_str, 'contrib')
ext_glob = os.path.join(ext_path, "*.py")
for ext_path in glob.iglob(ext_glob):
name = os.path.basename(ext_path)[:-3]
if name == "__init__":
continue
module = imp.load_source(name, ext_path)
yield name, module
def _discover_via_entry_points():
for ep in pkg_resources.iter_entry_points('novaclient.extension'):
name = ep.name
module = ep.load()
yield name, module
def get_client_class(version): def get_client_class(version):
version = str(version) version = str(version)
if version in DEPRECATED_VERSIONS: if version in DEPRECATED_VERSIONS:

View File

@ -21,12 +21,7 @@ Command-line interface to the OpenStack Nova API.
from __future__ import print_function from __future__ import print_function
import argparse import argparse
import getpass import getpass
import glob
import imp
import itertools
import logging import logging
import os
import pkgutil
import sys import sys
from keystoneclient.auth.identity.generic import password from keystoneclient.auth.identity.generic import password
@ -35,7 +30,6 @@ from keystoneclient.auth.identity import v3 as identity
from keystoneclient import session as ksession from keystoneclient import session as ksession
from oslo_utils import encodeutils from oslo_utils import encodeutils
from oslo_utils import strutils from oslo_utils import strutils
import pkg_resources
import six import six
HAS_KEYRING = False HAS_KEYRING = False
@ -456,56 +450,10 @@ class OpenStackComputeShell(object):
return parser return parser
# TODO(lyj): Delete this method after heat patched to use
# client.discover_extensions
def _discover_extensions(self, version): def _discover_extensions(self, version):
extensions = [] return client.discover_extensions(version)
for name, module in itertools.chain(
self._discover_via_python_path(),
self._discover_via_contrib_path(version),
self._discover_via_entry_points()):
extension = novaclient.extension.Extension(name, module)
extensions.append(extension)
return extensions
def _discover_via_python_path(self):
for (module_loader, name, _ispkg) in pkgutil.iter_modules():
if name.endswith('_python_novaclient_ext'):
if not hasattr(module_loader, 'load_module'):
# Python 2.6 compat: actually get an ImpImporter obj
module_loader = module_loader.find_module(name)
module = module_loader.load_module(name)
if hasattr(module, 'extension_name'):
name = module.extension_name
yield name, module
def _discover_via_contrib_path(self, version):
module_path = os.path.dirname(os.path.abspath(__file__))
version_str = "v%s" % version.replace('.', '_')
# NOTE(andreykurilin): v1.1 uses implementation of v2, so we should
# discover contrib modules in novaclient.v2 dir.
if version_str == "v1_1":
version_str = "v2"
ext_path = os.path.join(module_path, version_str, 'contrib')
ext_glob = os.path.join(ext_path, "*.py")
for ext_path in glob.iglob(ext_glob):
name = os.path.basename(ext_path)[:-3]
if name == "__init__":
continue
module = imp.load_source(name, ext_path)
yield name, module
def _discover_via_entry_points(self):
for ep in pkg_resources.iter_entry_points('novaclient.extension'):
name = ep.name
module = ep.load()
yield name, module
def _add_bash_completion_subparser(self, subparsers): def _add_bash_completion_subparser(self, subparsers):
subparser = subparsers.add_parser( subparser = subparsers.add_parser(

View File

@ -19,7 +19,7 @@ import inspect
import mock import mock
import pkg_resources import pkg_resources
import novaclient.shell from novaclient import client
from novaclient.tests.unit import utils from novaclient.tests.unit import utils
@ -38,8 +38,7 @@ class DiscoverTest(utils.TestCase):
@mock.patch.object(pkg_resources, 'iter_entry_points', @mock.patch.object(pkg_resources, 'iter_entry_points',
mock_iter_entry_points) mock_iter_entry_points)
def test(): def test():
shell = novaclient.shell.OpenStackComputeShell() for name, module in client._discover_via_entry_points():
for name, module in shell._discover_via_entry_points():
self.assertEqual('foo', name) self.assertEqual('foo', name)
self.assertTrue(inspect.ismodule(module)) self.assertTrue(inspect.ismodule(module))
@ -47,27 +46,26 @@ class DiscoverTest(utils.TestCase):
def test_discover_extensions(self): def test_discover_extensions(self):
def mock_discover_via_python_path(self): def mock_discover_via_python_path():
yield 'foo', imp.new_module('foo') yield 'foo', imp.new_module('foo')
def mock_discover_via_contrib_path(self, version): def mock_discover_via_contrib_path(version):
yield 'bar', imp.new_module('bar') yield 'bar', imp.new_module('bar')
def mock_discover_via_entry_points(self): def mock_discover_via_entry_points():
yield 'baz', imp.new_module('baz') yield 'baz', imp.new_module('baz')
@mock.patch.object(novaclient.shell.OpenStackComputeShell, @mock.patch.object(client,
'_discover_via_python_path', '_discover_via_python_path',
mock_discover_via_python_path) mock_discover_via_python_path)
@mock.patch.object(novaclient.shell.OpenStackComputeShell, @mock.patch.object(client,
'_discover_via_contrib_path', '_discover_via_contrib_path',
mock_discover_via_contrib_path) mock_discover_via_contrib_path)
@mock.patch.object(novaclient.shell.OpenStackComputeShell, @mock.patch.object(client,
'_discover_via_entry_points', '_discover_via_entry_points',
mock_discover_via_entry_points) mock_discover_via_entry_points)
def test(): def test():
shell = novaclient.shell.OpenStackComputeShell() extensions = client.discover_extensions('1.1')
extensions = shell._discover_extensions('1.1')
self.assertEqual(3, len(extensions)) self.assertEqual(3, len(extensions))
names = sorted(['foo', 'bar', 'baz']) names = sorted(['foo', 'bar', 'baz'])
sorted_extensions = sorted(extensions, key=lambda ext: ext.name) sorted_extensions = sorted(extensions, key=lambda ext: ext.name)