summaryrefslogtreecommitdiff
path: root/openstackclient/tests
diff options
context:
space:
mode:
Diffstat (limited to 'openstackclient/tests')
-rw-r--r--openstackclient/tests/common/test_clientmanager.py3
-rw-r--r--openstackclient/tests/common/test_utils.py39
-rw-r--r--openstackclient/tests/compute/v2/test_server.py47
-rw-r--r--openstackclient/tests/image/v1/test_image.py9
-rw-r--r--openstackclient/tests/image/v2/test_image.py50
-rw-r--r--openstackclient/tests/test_shell.py447
-rw-r--r--openstackclient/tests/volume/v2/__init__.py0
-rw-r--r--openstackclient/tests/volume/v2/fakes.py136
-rw-r--r--openstackclient/tests/volume/v2/test_backup.py82
-rw-r--r--openstackclient/tests/volume/v2/test_snapshot.py82
-rw-r--r--openstackclient/tests/volume/v2/test_type.py82
-rw-r--r--openstackclient/tests/volume/v2/test_volume.py82
12 files changed, 842 insertions, 217 deletions
diff --git a/openstackclient/tests/common/test_clientmanager.py b/openstackclient/tests/common/test_clientmanager.py
index 26cf4967..4e2f46b4 100644
--- a/openstackclient/tests/common/test_clientmanager.py
+++ b/openstackclient/tests/common/test_clientmanager.py
@@ -12,12 +12,13 @@
# License for the specific language governing permissions and limitations
# under the License.
#
+
+import json as jsonutils
import mock
from requests_mock.contrib import fixture
from keystoneclient.auth.identity import v2 as auth_v2
from keystoneclient import service_catalog
-from oslo_serialization import jsonutils
from openstackclient.api import auth
from openstackclient.api import auth_plugin
diff --git a/openstackclient/tests/common/test_utils.py b/openstackclient/tests/common/test_utils.py
index cda0b135..d9f5b7a5 100644
--- a/openstackclient/tests/common/test_utils.py
+++ b/openstackclient/tests/common/test_utils.py
@@ -13,6 +13,9 @@
# under the License.
#
+import time
+import uuid
+
import mock
from openstackclient.common import exceptions
@@ -120,6 +123,42 @@ class TestUtils(test_utils.TestCase):
utils.sort_items,
items, sort_str)
+ @mock.patch.object(time, 'sleep')
+ def test_wait_for_delete_ok(self, mock_sleep):
+ # Tests the normal flow that the resource is deleted with a 404 coming
+ # back on the 2nd iteration of the wait loop.
+ resource = mock.MagicMock(status='ACTIVE', progress=None)
+ mock_get = mock.Mock(side_effect=[resource,
+ exceptions.NotFound(404)])
+ manager = mock.MagicMock(get=mock_get)
+ res_id = str(uuid.uuid4())
+ callback = mock.Mock()
+ self.assertTrue(utils.wait_for_delete(manager, res_id,
+ callback=callback))
+ mock_sleep.assert_called_once_with(5)
+ callback.assert_called_once_with(0)
+
+ @mock.patch.object(time, 'sleep')
+ def test_wait_for_delete_timeout(self, mock_sleep):
+ # Tests that we fail if the resource is not deleted before the timeout.
+ resource = mock.MagicMock(status='ACTIVE')
+ mock_get = mock.Mock(return_value=resource)
+ manager = mock.MagicMock(get=mock_get)
+ res_id = str(uuid.uuid4())
+ self.assertFalse(utils.wait_for_delete(manager, res_id, sleep_time=1,
+ timeout=1))
+ mock_sleep.assert_called_once_with(1)
+
+ @mock.patch.object(time, 'sleep')
+ def test_wait_for_delete_error(self, mock_sleep):
+ # Tests that we fail if the resource goes to error state while waiting.
+ resource = mock.MagicMock(status='ERROR')
+ mock_get = mock.Mock(return_value=resource)
+ manager = mock.MagicMock(get=mock_get)
+ res_id = str(uuid.uuid4())
+ self.assertFalse(utils.wait_for_delete(manager, res_id))
+ self.assertFalse(mock_sleep.called)
+
class NoUniqueMatch(Exception):
pass
diff --git a/openstackclient/tests/compute/v2/test_server.py b/openstackclient/tests/compute/v2/test_server.py
index baf53742..a8a1936d 100644
--- a/openstackclient/tests/compute/v2/test_server.py
+++ b/openstackclient/tests/compute/v2/test_server.py
@@ -16,6 +16,7 @@
import copy
import mock
+from openstackclient.common import utils as common_utils
from openstackclient.compute.v2 import server
from openstackclient.tests.compute.v2 import fakes as compute_fakes
from openstackclient.tests import fakes
@@ -319,6 +320,52 @@ class TestServerDelete(TestServer):
compute_fakes.server_id,
)
+ @mock.patch.object(common_utils, 'wait_for_delete', return_value=True)
+ def test_server_delete_wait_ok(self, mock_wait_for_delete):
+ arglist = [
+ compute_fakes.server_id, '--wait'
+ ]
+ verifylist = [
+ ('servers', [compute_fakes.server_id]),
+ ]
+ parsed_args = self.check_parser(self.cmd, arglist, verifylist)
+
+ # DisplayCommandBase.take_action() returns two tuples
+ self.cmd.take_action(parsed_args)
+
+ self.servers_mock.delete.assert_called_with(
+ compute_fakes.server_id,
+ )
+
+ mock_wait_for_delete.assert_called_once_with(
+ self.servers_mock,
+ compute_fakes.server_id,
+ callback=server._show_progress
+ )
+
+ @mock.patch.object(common_utils, 'wait_for_delete', return_value=False)
+ def test_server_delete_wait_fails(self, mock_wait_for_delete):
+ arglist = [
+ compute_fakes.server_id, '--wait'
+ ]
+ verifylist = [
+ ('servers', [compute_fakes.server_id]),
+ ]
+ parsed_args = self.check_parser(self.cmd, arglist, verifylist)
+
+ # DisplayCommandBase.take_action() returns two tuples
+ self.assertRaises(SystemExit, self.cmd.take_action, parsed_args)
+
+ self.servers_mock.delete.assert_called_with(
+ compute_fakes.server_id,
+ )
+
+ mock_wait_for_delete.assert_called_once_with(
+ self.servers_mock,
+ compute_fakes.server_id,
+ callback=server._show_progress
+ )
+
class TestServerImageCreate(TestServer):
diff --git a/openstackclient/tests/image/v1/test_image.py b/openstackclient/tests/image/v1/test_image.py
index ef7ca9ea..eec8cfa5 100644
--- a/openstackclient/tests/image/v1/test_image.py
+++ b/openstackclient/tests/image/v1/test_image.py
@@ -547,6 +547,9 @@ class TestImageSet(TestImage):
'--owner', 'new-owner',
'--min-disk', '2',
'--min-ram', '4',
+ '--container-format', 'ovf',
+ '--disk-format', 'vmdk',
+ '--size', '35165824',
image_fakes.image_name,
]
verifylist = [
@@ -554,6 +557,9 @@ class TestImageSet(TestImage):
('owner', 'new-owner'),
('min_disk', 2),
('min_ram', 4),
+ ('container_format', 'ovf'),
+ ('disk_format', 'vmdk'),
+ ('size', 35165824),
('image', image_fakes.image_name),
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
@@ -566,6 +572,9 @@ class TestImageSet(TestImage):
'owner': 'new-owner',
'min_disk': 2,
'min_ram': 4,
+ 'container_format': 'ovf',
+ 'disk_format': 'vmdk',
+ 'size': 35165824
}
# ImageManager.update(image, **kwargs)
self.images_mock.update.assert_called_with(
diff --git a/openstackclient/tests/image/v2/test_image.py b/openstackclient/tests/image/v2/test_image.py
index 73b5d39a..7cfaf083 100644
--- a/openstackclient/tests/image/v2/test_image.py
+++ b/openstackclient/tests/image/v2/test_image.py
@@ -331,3 +331,53 @@ class TestImageShow(TestImage):
self.assertEqual(image_fakes.IMAGE_columns, columns)
self.assertEqual(image_fakes.IMAGE_data, data)
+
+
+class TestImageSet(TestImage):
+
+ def setUp(self):
+ super(TestImageSet, self).setUp()
+ # Set up the schema
+ self.model = warlock.model_factory(
+ image_fakes.IMAGE_schema,
+ schemas.SchemaBasedModel,
+ )
+
+ self.images_mock.get.return_value = self.model(**image_fakes.IMAGE)
+ self.images_mock.update.return_value = self.model(**image_fakes.IMAGE)
+ # Get the command object to test
+ self.cmd = image.SetImage(self.app, None)
+
+ def test_image_set_options(self):
+ arglist = [
+ '--name', 'new-name',
+ '--owner', 'new-owner',
+ '--min-disk', '2',
+ '--min-ram', '4',
+ image_fakes.image_id,
+ ]
+ verifylist = [
+ ('name', 'new-name'),
+ ('owner', 'new-owner'),
+ ('min_disk', 2),
+ ('min_ram', 4),
+ ('image', image_fakes.image_id),
+ ]
+ parsed_args = self.check_parser(self.cmd, arglist, verifylist)
+
+ # DisplayCommandBase.take_action() returns two tuples
+ columns, data = self.cmd.take_action(parsed_args)
+
+ kwargs = {
+ 'name': 'new-name',
+ 'owner': 'new-owner',
+ 'min_disk': 2,
+ 'min_ram': 4,
+ 'protected': False
+ }
+ # ImageManager.update(image, **kwargs)
+ self.images_mock.update.assert_called_with(
+ image_fakes.image_id, **kwargs)
+
+ self.assertEqual(image_fakes.IMAGE_columns, columns)
+ self.assertEqual(image_fakes.IMAGE_data, data)
diff --git a/openstackclient/tests/test_shell.py b/openstackclient/tests/test_shell.py
index 492b60de..8850d8f9 100644
--- a/openstackclient/tests/test_shell.py
+++ b/openstackclient/tests/test_shell.py
@@ -25,13 +25,15 @@ DEFAULT_AUTH_URL = "http://127.0.0.1:5000/v2.0/"
DEFAULT_PROJECT_ID = "xxxx-yyyy-zzzz"
DEFAULT_PROJECT_NAME = "project"
DEFAULT_DOMAIN_ID = "aaaa-bbbb-cccc"
-DEFAULT_DOMAIN_NAME = "domain"
+DEFAULT_DOMAIN_NAME = "default"
DEFAULT_USER_DOMAIN_ID = "aaaa-bbbb-cccc"
DEFAULT_USER_DOMAIN_NAME = "domain"
DEFAULT_PROJECT_DOMAIN_ID = "aaaa-bbbb-cccc"
DEFAULT_PROJECT_DOMAIN_NAME = "domain"
DEFAULT_USERNAME = "username"
DEFAULT_PASSWORD = "password"
+
+DEFAULT_CLOUD = "altocumulus"
DEFAULT_REGION_NAME = "ZZ9_Plural_Z_Alpha"
DEFAULT_TOKEN = "token"
DEFAULT_SERVICE_URL = "http://127.0.0.1:8771/v3.0/"
@@ -90,6 +92,54 @@ PUBLIC_1 = {
}
+# The option table values is a tuple of (<value>, <test-opt>, <test-env>)
+# where <value> is the test value to use, <test-opt> is True if this option
+# should be tested as a CLI option and <test-env> is True of this option
+# should be tested as an environment variable.
+
+# Global options that should be parsed before shell.initialize_app() is called
+global_options = {
+ '--os-cloud': (DEFAULT_CLOUD, True, True),
+ '--os-region-name': (DEFAULT_REGION_NAME, True, True),
+ '--os-default-domain': (DEFAULT_DOMAIN_NAME, True, True),
+ '--os-cacert': ('/dev/null', True, True),
+ '--timing': (True, True, False),
+}
+
+auth_options = {
+ '--os-auth-url': (DEFAULT_AUTH_URL, True, True),
+ '--os-project-id': (DEFAULT_PROJECT_ID, True, True),
+ '--os-project-name': (DEFAULT_PROJECT_NAME, True, True),
+ '--os-domain-id': (DEFAULT_DOMAIN_ID, True, True),
+ '--os-domain-name': (DEFAULT_DOMAIN_NAME, True, True),
+ '--os-user-domain-id': (DEFAULT_USER_DOMAIN_ID, True, True),
+ '--os-user-domain-name': (DEFAULT_USER_DOMAIN_NAME, True, True),
+ '--os-project-domain-id': (DEFAULT_PROJECT_DOMAIN_ID, True, True),
+ '--os-project-domain-name': (DEFAULT_PROJECT_DOMAIN_NAME, True, True),
+ '--os-username': (DEFAULT_USERNAME, True, True),
+ '--os-password': (DEFAULT_PASSWORD, True, True),
+ '--os-region-name': (DEFAULT_REGION_NAME, True, True),
+ '--os-trust-id': ("1234", True, True),
+ '--os-auth-type': ("v2password", True, True),
+ '--os-token': (DEFAULT_TOKEN, True, True),
+ '--os-url': (DEFAULT_SERVICE_URL, True, True),
+}
+
+
+def opt2attr(opt):
+ if opt.startswith('--os-'):
+ attr = opt[5:]
+ elif opt.startswith('--'):
+ attr = opt[2:]
+ else:
+ attr = opt
+ return attr.lower().replace('-', '_')
+
+
+def opt2env(opt):
+ return opt[2:].upper().replace('-', '_')
+
+
def make_shell():
"""Create a new command shell and mock out some bits."""
_shell = shell.OpenStackShell()
@@ -115,69 +165,54 @@ class TestShell(utils.TestCase):
super(TestShell, self).tearDown()
self.cmd_patch.stop()
- def _assert_password_auth(self, cmd_options, default_args):
- with mock.patch("openstackclient.shell.OpenStackShell.initialize_app",
- self.app):
+ def _assert_initialize_app_arg(self, cmd_options, default_args):
+ """Check the args passed to initialize_app()
+
+ The argv argument to initialize_app() is the remainder from parsing
+ global options declared in both cliff.app and
+ openstackclient.OpenStackShell build_option_parser(). Any global
+ options passed on the commmad line should not be in argv but in
+ _shell.options.
+ """
+
+ with mock.patch(
+ "openstackclient.shell.OpenStackShell.initialize_app",
+ self.app,
+ ):
_shell, _cmd = make_shell(), cmd_options + " list project"
fake_execute(_shell, _cmd)
self.app.assert_called_with(["list", "project"])
- self.assertEqual(
- default_args.get("auth_url", ''),
- _shell.options.auth_url,
- )
- self.assertEqual(
- default_args.get("project_id", ''),
- _shell.options.project_id,
- )
- self.assertEqual(
- default_args.get("project_name", ''),
- _shell.options.project_name,
- )
- self.assertEqual(
- default_args.get("domain_id", ''),
- _shell.options.domain_id,
- )
- self.assertEqual(
- default_args.get("domain_name", ''),
- _shell.options.domain_name,
- )
- self.assertEqual(
- default_args.get("user_domain_id", ''),
- _shell.options.user_domain_id,
- )
- self.assertEqual(
- default_args.get("user_domain_name", ''),
- _shell.options.user_domain_name,
- )
- self.assertEqual(
- default_args.get("project_domain_id", ''),
- _shell.options.project_domain_id,
- )
- self.assertEqual(
- default_args.get("project_domain_name", ''),
- _shell.options.project_domain_name,
- )
- self.assertEqual(
- default_args.get("username", ''),
- _shell.options.username,
- )
- self.assertEqual(
- default_args.get("password", ''),
- _shell.options.password,
- )
- self.assertEqual(
- default_args.get("region_name", ''),
- _shell.options.region_name,
- )
- self.assertEqual(
- default_args.get("trust_id", ''),
- _shell.options.trust_id,
- )
- self.assertEqual(
- default_args.get('auth_type', ''),
- _shell.options.auth_type,
- )
+ for k in default_args.keys():
+ self.assertEqual(
+ default_args[k],
+ vars(_shell.options)[k],
+ "%s does not match" % k,
+ )
+
+ def _assert_cloud_config_arg(self, cmd_options, default_args):
+ """Check the args passed to cloud_config.get_one_cloud()
+
+ The argparse argument to get_one_cloud() is an argparse.Namespace
+ object that contains all of the options processed to this point in
+ initialize_app().
+ """
+
+ self.occ_get_one = mock.Mock("Test Shell")
+ with mock.patch(
+ "os_client_config.config.OpenStackConfig.get_one_cloud",
+ self.occ_get_one,
+ ):
+ _shell, _cmd = make_shell(), cmd_options + " list project"
+ fake_execute(_shell, _cmd)
+
+ opts = self.occ_get_one.call_args[1]['argparse']
+ for k in default_args.keys():
+ self.assertEqual(
+ default_args[k],
+ vars(opts)[k],
+ "%s does not match" % k,
+ )
def _assert_token_auth(self, cmd_options, default_args):
with mock.patch("openstackclient.shell.OpenStackShell.initialize_app",
@@ -258,136 +293,91 @@ class TestShellHelp(TestShell):
_shell.options.deferred_help)
-class TestShellPasswordAuth(TestShell):
+class TestShellOptions(TestShell):
def setUp(self):
- super(TestShellPasswordAuth, self).setUp()
+ super(TestShellOptions, self).setUp()
self.orig_env, os.environ = os.environ, {}
def tearDown(self):
- super(TestShellPasswordAuth, self).tearDown()
+ super(TestShellOptions, self).tearDown()
os.environ = self.orig_env
- def test_only_url_flow(self):
- flag = "--os-auth-url " + DEFAULT_AUTH_URL
- kwargs = {
- "auth_url": DEFAULT_AUTH_URL,
- }
- self._assert_password_auth(flag, kwargs)
-
- def test_only_project_id_flow(self):
- flag = "--os-project-id " + DEFAULT_PROJECT_ID
- kwargs = {
- "project_id": DEFAULT_PROJECT_ID,
- }
- self._assert_password_auth(flag, kwargs)
-
- def test_only_project_name_flow(self):
- flag = "--os-project-name " + DEFAULT_PROJECT_NAME
- kwargs = {
- "project_name": DEFAULT_PROJECT_NAME,
- }
- self._assert_password_auth(flag, kwargs)
-
- def test_only_domain_id_flow(self):
- flag = "--os-domain-id " + DEFAULT_DOMAIN_ID
- kwargs = {
- "domain_id": DEFAULT_DOMAIN_ID,
- }
- self._assert_password_auth(flag, kwargs)
-
- def test_only_domain_name_flow(self):
- flag = "--os-domain-name " + DEFAULT_DOMAIN_NAME
- kwargs = {
- "domain_name": DEFAULT_DOMAIN_NAME,
- }
- self._assert_password_auth(flag, kwargs)
-
- def test_only_user_domain_id_flow(self):
- flag = "--os-user-domain-id " + DEFAULT_USER_DOMAIN_ID
- kwargs = {
- "user_domain_id": DEFAULT_USER_DOMAIN_ID,
- }
- self._assert_password_auth(flag, kwargs)
+ def _test_options_init_app(self, test_opts):
+ for opt in test_opts.keys():
+ if not test_opts[opt][1]:
+ continue
+ key = opt2attr(opt)
+ if type(test_opts[opt][0]) is str:
+ cmd = opt + " " + test_opts[opt][0]
+ else:
+ cmd = opt
+ kwargs = {
+ key: test_opts[opt][0],
+ }
+ self._assert_initialize_app_arg(cmd, kwargs)
+
+ def _test_options_get_one_cloud(self, test_opts):
+ for opt in test_opts.keys():
+ if not test_opts[opt][1]:
+ continue
+ key = opt2attr(opt)
+ if type(test_opts[opt][0]) is str:
+ cmd = opt + " " + test_opts[opt][0]
+ else:
+ cmd = opt
+ kwargs = {
+ key: test_opts[opt][0],
+ }
+ self._assert_cloud_config_arg(cmd, kwargs)
+
+ def _test_env_init_app(self, test_opts):
+ for opt in test_opts.keys():
+ if not test_opts[opt][2]:
+ continue
+ key = opt2attr(opt)
+ kwargs = {
+ key: test_opts[opt][0],
+ }
+ env = {
+ opt2env(opt): test_opts[opt][0],
+ }
+ os.environ = env.copy()
+ self._assert_initialize_app_arg("", kwargs)
+
+ def _test_env_get_one_cloud(self, test_opts):
+ for opt in test_opts.keys():
+ if not test_opts[opt][2]:
+ continue
+ key = opt2attr(opt)
+ kwargs = {
+ key: test_opts[opt][0],
+ }
+ env = {
+ opt2env(opt): test_opts[opt][0],
+ }
+ os.environ = env.copy()
+ self._assert_cloud_config_arg("", kwargs)
- def test_only_user_domain_name_flow(self):
- flag = "--os-user-domain-name " + DEFAULT_USER_DOMAIN_NAME
- kwargs = {
- "user_domain_name": DEFAULT_USER_DOMAIN_NAME,
- }
- self._assert_password_auth(flag, kwargs)
+ def test_empty_auth(self):
+ os.environ = {}
+ self._assert_initialize_app_arg("", {})
+ self._assert_cloud_config_arg("", {})
- def test_only_project_domain_id_flow(self):
- flag = "--os-project-domain-id " + DEFAULT_PROJECT_DOMAIN_ID
- kwargs = {
- "project_domain_id": DEFAULT_PROJECT_DOMAIN_ID,
- }
- self._assert_password_auth(flag, kwargs)
+ def test_global_options(self):
+ self._test_options_init_app(global_options)
+ self._test_options_get_one_cloud(global_options)
- def test_only_project_domain_name_flow(self):
- flag = "--os-project-domain-name " + DEFAULT_PROJECT_DOMAIN_NAME
- kwargs = {
- "project_domain_name": DEFAULT_PROJECT_DOMAIN_NAME,
- }
- self._assert_password_auth(flag, kwargs)
+ def test_auth_options(self):
+ self._test_options_init_app(auth_options)
+ self._test_options_get_one_cloud(auth_options)
- def test_only_username_flow(self):
- flag = "--os-username " + DEFAULT_USERNAME
- kwargs = {
- "username": DEFAULT_USERNAME,
- }
- self._assert_password_auth(flag, kwargs)
-
- def test_only_password_flow(self):
- flag = "--os-password " + DEFAULT_PASSWORD
- kwargs = {
- "password": DEFAULT_PASSWORD,
- }
- self._assert_password_auth(flag, kwargs)
+ def test_global_env(self):
+ self._test_env_init_app(global_options)
+ self._test_env_get_one_cloud(global_options)
- def test_only_region_name_flow(self):
- flag = "--os-region-name " + DEFAULT_REGION_NAME
- kwargs = {
- "region_name": DEFAULT_REGION_NAME,
- }
- self._assert_password_auth(flag, kwargs)
-
- def test_only_trust_id_flow(self):
- flag = "--os-trust-id " + "1234"
- kwargs = {
- "trust_id": "1234",
- }
- self._assert_password_auth(flag, kwargs)
-
- def test_only_auth_type_flow(self):
- flag = "--os-auth-type " + "v2password"
- kwargs = {
- "auth_type": DEFAULT_AUTH_PLUGIN
- }
- self._assert_password_auth(flag, kwargs)
-
-
-class TestShellTokenAuth(TestShell):
- def test_only_token(self):
- flag = "--os-token " + DEFAULT_TOKEN
- kwargs = {
- "token": DEFAULT_TOKEN,
- "auth_url": '',
- }
- self._assert_token_auth(flag, kwargs)
-
- def test_only_auth_url(self):
- flag = "--os-auth-url " + DEFAULT_AUTH_URL
- kwargs = {
- "token": '',
- "auth_url": DEFAULT_AUTH_URL,
- }
- self._assert_token_auth(flag, kwargs)
-
- def test_empty_auth(self):
- os.environ = {}
- flag = ""
- kwargs = {}
- self._assert_token_auth(flag, kwargs)
+ def test_auth_env(self):
+ self._test_env_init_app(auth_options)
+ self._test_env_get_one_cloud(auth_options)
class TestShellTokenAuthEnv(TestShell):
@@ -437,33 +427,6 @@ class TestShellTokenAuthEnv(TestShell):
self._assert_token_auth(flag, kwargs)
-class TestShellTokenEndpointAuth(TestShell):
- def test_only_token(self):
- flag = "--os-token " + DEFAULT_TOKEN
- kwargs = {
- "token": DEFAULT_TOKEN,
- "url": '',
- }
- self._assert_token_endpoint_auth(flag, kwargs)
-
- def test_only_url(self):
- flag = "--os-url " + DEFAULT_SERVICE_URL
- kwargs = {
- "token": '',
- "url": DEFAULT_SERVICE_URL,
- }
- self._assert_token_endpoint_auth(flag, kwargs)
-
- def test_empty_auth(self):
- os.environ = {}
- flag = ""
- kwargs = {
- "token": '',
- "auth_url": '',
- }
- self._assert_token_endpoint_auth(flag, kwargs)
-
-
class TestShellTokenEndpointAuthEnv(TestShell):
def setUp(self):
super(TestShellTokenEndpointAuthEnv, self).setUp()
@@ -527,13 +490,65 @@ class TestShellCli(TestShell):
super(TestShellCli, self).tearDown()
os.environ = self.orig_env
- def test_shell_args(self):
+ def test_shell_args_no_options(self):
_shell = make_shell()
with mock.patch("openstackclient.shell.OpenStackShell.initialize_app",
self.app):
fake_execute(_shell, "list user")
self.app.assert_called_with(["list", "user"])
+ def test_shell_args_ca_options(self):
+ _shell = make_shell()
+
+ # NOTE(dtroyer): The commented out asserts below are the desired
+ # behaviour and will be uncommented when the
+ # handling for --verify and --insecure is fixed.
+
+ # Default
+ fake_execute(_shell, "list user")
+ self.assertIsNone(_shell.options.verify)
+ self.assertIsNone(_shell.options.insecure)
+ self.assertEqual('', _shell.options.cacert)
+ self.assertTrue(_shell.verify)
+
+ # --verify
+ fake_execute(_shell, "--verify list user")
+ self.assertTrue(_shell.options.verify)
+ self.assertIsNone(_shell.options.insecure)
+ self.assertEqual('', _shell.options.cacert)
+ self.assertTrue(_shell.verify)
+
+ # --insecure
+ fake_execute(_shell, "--insecure list user")
+ self.assertIsNone(_shell.options.verify)
+ self.assertTrue(_shell.options.insecure)
+ self.assertEqual('', _shell.options.cacert)
+ self.assertFalse(_shell.verify)
+
+ # --os-cacert
+ fake_execute(_shell, "--os-cacert foo list user")
+ self.assertIsNone(_shell.options.verify)
+ self.assertIsNone(_shell.options.insecure)
+ self.assertEqual('foo', _shell.options.cacert)
+ self.assertTrue(_shell.verify)
+
+ # --os-cacert and --verify
+ fake_execute(_shell, "--os-cacert foo --verify list user")
+ self.assertTrue(_shell.options.verify)
+ self.assertIsNone(_shell.options.insecure)
+ self.assertEqual('foo', _shell.options.cacert)
+ self.assertTrue(_shell.verify)
+
+ # --os-cacert and --insecure
+ # NOTE(dtroyer): This really is a bogus combination, the default is
+ # to follow the requests.Session convention and let
+ # --os-cacert override --insecure
+ fake_execute(_shell, "--os-cacert foo --insecure list user")
+ self.assertIsNone(_shell.options.verify)
+ self.assertTrue(_shell.options.insecure)
+ self.assertEqual('foo', _shell.options.cacert)
+ self.assertTrue(_shell.verify)
+
def test_default_env(self):
flag = ""
kwargs = {
@@ -559,7 +574,7 @@ class TestShellCli(TestShell):
@mock.patch("os_client_config.config.OpenStackConfig._load_config_file")
def test_shell_args_cloud_no_vendor(self, config_mock):
- config_mock.return_value = copy.deepcopy(CLOUD_1)
+ config_mock.return_value = ('file.yaml', copy.deepcopy(CLOUD_1))
_shell = make_shell()
fake_execute(
@@ -596,8 +611,8 @@ class TestShellCli(TestShell):
@mock.patch("os_client_config.config.OpenStackConfig._load_vendor_file")
@mock.patch("os_client_config.config.OpenStackConfig._load_config_file")
def test_shell_args_cloud_public(self, config_mock, public_mock):
- config_mock.return_value = copy.deepcopy(CLOUD_2)
- public_mock.return_value = copy.deepcopy(PUBLIC_1)
+ config_mock.return_value = ('file.yaml', copy.deepcopy(CLOUD_2))
+ public_mock.return_value = ('file.yaml', copy.deepcopy(PUBLIC_1))
_shell = make_shell()
fake_execute(
@@ -636,8 +651,8 @@ class TestShellCli(TestShell):
@mock.patch("os_client_config.config.OpenStackConfig._load_vendor_file")
@mock.patch("os_client_config.config.OpenStackConfig._load_config_file")
def test_shell_args_precedence(self, config_mock, vendor_mock):
- config_mock.return_value = copy.deepcopy(CLOUD_2)
- vendor_mock.return_value = copy.deepcopy(PUBLIC_1)
+ config_mock.return_value = ('file.yaml', copy.deepcopy(CLOUD_2))
+ vendor_mock.return_value = ('file.yaml', copy.deepcopy(PUBLIC_1))
_shell = make_shell()
# Test command option overriding config file value
@@ -690,8 +705,8 @@ class TestShellCliEnv(TestShell):
@mock.patch("os_client_config.config.OpenStackConfig._load_vendor_file")
@mock.patch("os_client_config.config.OpenStackConfig._load_config_file")
def test_shell_args_precedence_1(self, config_mock, vendor_mock):
- config_mock.return_value = copy.deepcopy(CLOUD_2)
- vendor_mock.return_value = copy.deepcopy(PUBLIC_1)
+ config_mock.return_value = ('file.yaml', copy.deepcopy(CLOUD_2))
+ vendor_mock.return_value = ('file.yaml', copy.deepcopy(PUBLIC_1))
_shell = make_shell()
# Test env var
@@ -731,8 +746,8 @@ class TestShellCliEnv(TestShell):
@mock.patch("os_client_config.config.OpenStackConfig._load_vendor_file")
@mock.patch("os_client_config.config.OpenStackConfig._load_config_file")
def test_shell_args_precedence_2(self, config_mock, vendor_mock):
- config_mock.return_value = copy.deepcopy(CLOUD_2)
- vendor_mock.return_value = copy.deepcopy(PUBLIC_1)
+ config_mock.return_value = ('file.yaml', copy.deepcopy(CLOUD_2))
+ vendor_mock.return_value = ('file.yaml', copy.deepcopy(PUBLIC_1))
_shell = make_shell()
# Test command option overriding config file value
diff --git a/openstackclient/tests/volume/v2/__init__.py b/openstackclient/tests/volume/v2/__init__.py
new file mode 100644
index 00000000..e69de29b
--- /dev/null
+++ b/openstackclient/tests/volume/v2/__init__.py
diff --git a/openstackclient/tests/volume/v2/fakes.py b/openstackclient/tests/volume/v2/fakes.py
new file mode 100644
index 00000000..3eade391
--- /dev/null
+++ b/openstackclient/tests/volume/v2/fakes.py
@@ -0,0 +1,136 @@
+#
+# 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.
+#
+
+import mock
+
+from openstackclient.tests import fakes
+from openstackclient.tests.identity.v2_0 import fakes as identity_fakes
+from openstackclient.tests import utils
+
+volume_id = "ce26708d-a7f8-4b4b-9861-4a80256615a6"
+volume_name = "fake_volume"
+volume_description = "fake description"
+volume_status = "available"
+volume_size = 20
+volume_type = "fake_lvmdriver-1"
+volume_metadata = {
+ "foo": "bar"
+}
+volume_snapshot_id = 1
+volume_availability_zone = "nova"
+volume_attachments = ["fake_attachments"]
+
+VOLUME = {
+ "id": volume_id,
+ "name": volume_name,
+ "description": volume_description,
+ "status": volume_status,
+ "size": volume_size,
+ "volume_type": volume_type,
+ "metadata": volume_metadata,
+ "snapshot_id": volume_snapshot_id,
+ "availability_zone": volume_availability_zone,
+ "attachments": volume_attachments
+}
+
+VOLUME_columns = tuple(sorted(VOLUME))
+VOLUME_data = tuple((VOLUME[x] for x in sorted(VOLUME)))
+
+
+snapshot_id = "cb2d364e-4d1c-451a-8c68-b5bbcb340fb2"
+snapshot_name = "fake_snapshot"
+snapshot_description = "fake description"
+snapshot_size = 10
+snapshot_metadata = {
+ "foo": "bar"
+}
+snapshot_volume_id = "bdbae8dc-e6ca-43c0-8076-951cc1b093a4"
+
+SNAPSHOT = {
+ "id": snapshot_id,
+ "name": snapshot_name,
+ "description": snapshot_description,
+ "size": snapshot_size,
+ "metadata": snapshot_metadata
+}
+
+SNAPSHOT_columns = tuple(sorted(SNAPSHOT))
+SNAPSHOT_data = tuple((SNAPSHOT[x] for x in sorted(SNAPSHOT)))
+
+
+type_id = "5520dc9e-6f9b-4378-a719-729911c0f407"
+type_description = "fake description"
+type_name = "fake-lvmdriver-1"
+type_extra_specs = {
+ "foo": "bar"
+}
+
+TYPE = {
+ 'id': type_id,
+ 'name': type_name,
+ 'description': type_description,
+ 'extra_specs': type_extra_specs
+}
+
+TYPE_columns = tuple(sorted(TYPE))
+TYPE_data = tuple((TYPE[x] for x in sorted(TYPE)))
+
+backup_id = "3c409fe6-4d03-4a06-aeab-18bdcdf3c8f4"
+backup_volume_id = "bdbae8dc-e6ca-43c0-8076-951cc1b093a4"
+backup_name = "fake_backup"
+backup_description = "fake description"
+backup_object_count = None
+backup_container = None
+backup_size = 10
+
+BACKUP = {
+ "id": backup_id,
+ "name": backup_name,
+ "volume_id": backup_volume_id,
+ "description": backup_description,
+ "object_count": backup_object_count,
+ "container": backup_container,
+ "size": backup_size
+}
+
+BACKUP_columns = tuple(sorted(BACKUP))
+BACKUP_data = tuple((BACKUP[x] for x in sorted(BACKUP)))
+
+
+class FakeVolumeClient(object):
+ def __init__(self, **kwargs):
+ self.volumes = mock.Mock()
+ self.volumes.resource_class = fakes.FakeResource(None, {})
+ self.volume_snapshots = mock.Mock()
+ self.volume_snapshots.resource_class = fakes.FakeResource(None, {})
+ self.backups = mock.Mock()
+ self.backups.resource_class = fakes.FakeResource(None, {})
+ self.volume_types = mock.Mock()
+ self.volume_types.resource_class = fakes.FakeResource(None, {})
+ self.auth_token = kwargs['token']
+ self.management_url = kwargs['endpoint']
+
+
+class TestVolume(utils.TestCommand):
+ def setUp(self):
+ super(TestVolume, self).setUp()
+
+ self.app.client_manager.volume = FakeVolumeClient(
+ endpoint=fakes.AUTH_URL,
+ token=fakes.AUTH_TOKEN
+ )
+ self.app.client_manager.identity = identity_fakes.FakeIdentityv2Client(
+ endpoint=fakes.AUTH_URL,
+ token=fakes.AUTH_TOKEN
+ )
diff --git a/openstackclient/tests/volume/v2/test_backup.py b/openstackclient/tests/volume/v2/test_backup.py
new file mode 100644
index 00000000..e24cac3c
--- /dev/null
+++ b/openstackclient/tests/volume/v2/test_backup.py
@@ -0,0 +1,82 @@
+#
+# 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.
+#
+
+import copy
+
+from openstackclient.tests import fakes
+from openstackclient.tests.volume.v2 import fakes as volume_fakes
+from openstackclient.volume.v2 import backup
+
+
+class TestBackup(volume_fakes.TestVolume):
+
+ def setUp(self):
+ super(TestBackup, self).setUp()
+
+ self.backups_mock = self.app.client_manager.volume.backups
+ self.backups_mock.reset_mock()
+
+
+class TestBackupShow(TestBackup):
+ def setUp(self):
+ super(TestBackupShow, self).setUp()
+
+ self.backups_mock.get.return_value = fakes.FakeResource(
+ None,
+ copy.deepcopy(volume_fakes.BACKUP),
+ loaded=True)
+ # Get the command object to test
+ self.cmd = backup.ShowBackup(self.app, None)
+
+ def test_backup_show(self):
+ arglist = [
+ volume_fakes.backup_id
+ ]
+ verifylist = [
+ ("backup", volume_fakes.backup_id)
+ ]
+ parsed_args = self.check_parser(self.cmd, arglist, verifylist)
+
+ columns, data = self.cmd.take_action(parsed_args)
+ self.backups_mock.get.assert_called_with(volume_fakes.backup_id)
+
+ self.assertEqual(volume_fakes.BACKUP_columns, columns)
+ self.assertEqual(volume_fakes.BACKUP_data, data)
+
+
+class TestBackupDelete(TestBackup):
+ def setUp(self):
+ super(TestBackupDelete, self).setUp()
+
+ self.backups_mock.get.return_value = fakes.FakeResource(
+ None,
+ copy.deepcopy(volume_fakes.BACKUP),
+ loaded=True)
+ self.backups_mock.delete.return_value = None
+
+ # Get the command object to mock
+ self.cmd = backup.DeleteBackup(self.app, None)
+
+ def test_backup_delete(self):
+ arglist = [
+ volume_fakes.backup_id
+ ]
+ verifylist = [
+ ("backups", [volume_fakes.backup_id])
+ ]
+
+ parsed_args = self.check_parser(self.cmd, arglist, verifylist)
+
+ self.cmd.take_action(parsed_args)
+ self.backups_mock.delete.assert_called_with(volume_fakes.backup_id)
diff --git a/openstackclient/tests/volume/v2/test_snapshot.py b/openstackclient/tests/volume/v2/test_snapshot.py
new file mode 100644
index 00000000..91015410
--- /dev/null
+++ b/openstackclient/tests/volume/v2/test_snapshot.py
@@ -0,0 +1,82 @@
+#
+# 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.
+#
+
+import copy
+
+from openstackclient.tests import fakes
+from openstackclient.tests.volume.v2 import fakes as volume_fakes
+from openstackclient.volume.v2 import snapshot
+
+
+class TestSnapshot(volume_fakes.TestVolume):
+
+ def setUp(self):
+ super(TestSnapshot, self).setUp()
+
+ self.snapshots_mock = self.app.client_manager.volume.volume_snapshots
+ self.snapshots_mock.reset_mock()
+
+
+class TestSnapshotShow(TestSnapshot):
+ def setUp(self):
+ super(TestSnapshotShow, self).setUp()
+
+ self.snapshots_mock.get.return_value = fakes.FakeResource(
+ None,
+ copy.deepcopy(volume_fakes.SNAPSHOT),
+ loaded=True)
+ # Get the command object to test
+ self.cmd = snapshot.ShowSnapshot(self.app, None)
+
+ def test_snapshot_show(self):
+ arglist = [
+ volume_fakes.snapshot_id
+ ]
+ verifylist = [
+ ("snapshot", volume_fakes.snapshot_id)
+ ]
+ parsed_args = self.check_parser(self.cmd, arglist, verifylist)
+
+ columns, data = self.cmd.take_action(parsed_args)
+ self.snapshots_mock.get.assert_called_with(volume_fakes.snapshot_id)
+
+ self.assertEqual(volume_fakes.SNAPSHOT_columns, columns)
+ self.assertEqual(volume_fakes.SNAPSHOT_data, data)
+
+
+class TestSnapshotDelete(TestSnapshot):
+ def setUp(self):
+ super(TestSnapshotDelete, self).setUp()
+
+ self.snapshots_mock.get.return_value = fakes.FakeResource(
+ None,
+ copy.deepcopy(volume_fakes.SNAPSHOT),
+ loaded=True)
+ self.snapshots_mock.delete.return_value = None
+
+ # Get the command object to mock
+ self.cmd = snapshot.DeleteSnapshot(self.app, None)
+
+ def test_snapshot_delete(self):
+ arglist = [
+ volume_fakes.snapshot_id
+ ]
+ verifylist = [
+ ("snapshots", [volume_fakes.snapshot_id])
+ ]
+
+ parsed_args = self.check_parser(self.cmd, arglist, verifylist)
+
+ self.cmd.take_action(parsed_args)
+ self.snapshots_mock.delete.assert_called_with(volume_fakes.snapshot_id)
diff --git a/openstackclient/tests/volume/v2/test_type.py b/openstackclient/tests/volume/v2/test_type.py
new file mode 100644
index 00000000..6cc988b2
--- /dev/null
+++ b/openstackclient/tests/volume/v2/test_type.py
@@ -0,0 +1,82 @@
+#
+# 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.
+#
+
+import copy
+
+from openstackclient.tests import fakes
+from openstackclient.tests.volume.v2 import fakes as volume_fakes
+from openstackclient.volume.v2 import volume_type
+
+
+class TestType(volume_fakes.TestVolume):
+
+ def setUp(self):
+ super(TestType, self).setUp()
+
+ self.types_mock = self.app.client_manager.volume.volume_types
+ self.types_mock.reset_mock()
+
+
+class TestTypeShow(TestType):
+ def setUp(self):
+ super(TestTypeShow, self).setUp()
+
+ self.types_mock.get.return_value = fakes.FakeResource(
+ None,
+ copy.deepcopy(volume_fakes.TYPE),
+ loaded=True)
+ # Get the command object to test
+ self.cmd = volume_type.ShowVolumeType(self.app, None)
+
+ def test_type_show(self):
+ arglist = [
+ volume_fakes.type_id
+ ]
+ verifylist = [
+ ("volume_type", volume_fakes.type_id)
+ ]
+ parsed_args = self.check_parser(self.cmd, arglist, verifylist)
+
+ columns, data = self.cmd.take_action(parsed_args)
+ self.types_mock.get.assert_called_with(volume_fakes.type_id)
+
+ self.assertEqual(volume_fakes.TYPE_columns, columns)
+ self.assertEqual(volume_fakes.TYPE_data, data)
+
+
+class TestTypeDelete(TestType):
+ def setUp(self):
+ super(TestTypeDelete, self).setUp()
+
+ self.types_mock.get.return_value = fakes.FakeResource(
+ None,
+ copy.deepcopy(volume_fakes.TYPE),
+ loaded=True)
+ self.types_mock.delete.return_value = None
+
+ # Get the command object to mock
+ self.cmd = volume_type.DeleteVolumeType(self.app, None)
+
+ def test_type_delete(self):
+ arglist = [
+ volume_fakes.type_id
+ ]
+ verifylist = [
+ ("volume_type", volume_fakes.type_id)
+ ]
+
+ parsed_args = self.check_parser(self.cmd, arglist, verifylist)
+
+ self.cmd.take_action(parsed_args)
+ self.types_mock.delete.assert_called_with(volume_fakes.type_id)
diff --git a/openstackclient/tests/volume/v2/test_volume.py b/openstackclient/tests/volume/v2/test_volume.py
new file mode 100644
index 00000000..9e991b72
--- /dev/null
+++ b/openstackclient/tests/volume/v2/test_volume.py
@@ -0,0 +1,82 @@
+#
+# 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.
+#
+
+import copy
+
+from openstackclient.tests import fakes
+from openstackclient.tests.volume.v2 import fakes as volume_fakes
+from openstackclient.volume.v2 import volume
+
+
+class TestVolume(volume_fakes.TestVolume):
+
+ def setUp(self):
+ super(TestVolume, self).setUp()
+
+ self.volumes_mock = self.app.client_manager.volume.volumes
+ self.volumes_mock.reset_mock()
+
+
+class TestVolumeShow(TestVolume):
+ def setUp(self):
+ super(TestVolumeShow, self).setUp()
+
+ self.volumes_mock.get.return_value = fakes.FakeResource(
+ None,
+ copy.deepcopy(volume_fakes.VOLUME),
+ loaded=True)
+ # Get the command object to test
+ self.cmd = volume.ShowVolume(self.app, None)
+
+ def test_volume_show(self):
+ arglist = [
+ volume_fakes.volume_id
+ ]
+ verifylist = [
+ ("volume", volume_fakes.volume_id)
+ ]
+ parsed_args = self.check_parser(self.cmd, arglist, verifylist)
+
+ columns, data = self.cmd.take_action(parsed_args)
+ self.volumes_mock.get.assert_called_with(volume_fakes.volume_id)
+
+ self.assertEqual(volume_fakes.VOLUME_columns, columns)
+ self.assertEqual(volume_fakes.VOLUME_data, data)
+
+
+class TestVolumeDelete(TestVolume):
+ def setUp(self):
+ super(TestVolumeDelete, self).setUp()
+
+ self.volumes_mock.get.return_value = fakes.FakeResource(
+ None,
+ copy.deepcopy(volume_fakes.VOLUME),
+ loaded=True)
+ self.volumes_mock.delete.return_value = None
+
+ # Get the command object to mock
+ self.cmd = volume.DeleteVolume(self.app, None)
+
+ def test_volume_delete(self):
+ arglist = [
+ volume_fakes.volume_id
+ ]
+ verifylist = [
+ ("volumes", [volume_fakes.volume_id])
+ ]
+
+ parsed_args = self.check_parser(self.cmd, arglist, verifylist)
+
+ self.cmd.take_action(parsed_args)
+ self.volumes_mock.delete.assert_called_with(volume_fakes.volume_id)