summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--README.rst76
-rw-r--r--doc/requirements.txt1
-rw-r--r--doc/source/cli/authentication.rst14
-rw-r--r--doc/source/cli/man/openstack.rst112
-rw-r--r--doc/source/cli/plugin-commands/index.rst1
-rw-r--r--doc/source/cli/plugin-commands/searchlight.rst4
-rw-r--r--doc/source/conf.py3
-rw-r--r--doc/source/contributor/plugins.rst1
-rw-r--r--lower-constraints.txt67
-rw-r--r--openstackclient/common/quota.py13
-rw-r--r--openstackclient/compute/v2/aggregate.py263
-rw-r--r--openstackclient/compute/v2/flavor.py262
-rw-r--r--openstackclient/compute/v2/server.py88
-rw-r--r--openstackclient/identity/v2_0/catalog.py2
-rw-r--r--openstackclient/identity/v3/identity_provider.py24
-rw-r--r--openstackclient/image/v1/image.py6
-rw-r--r--openstackclient/image/v2/image.py6
-rw-r--r--openstackclient/tests/unit/common/test_quota.py23
-rw-r--r--openstackclient/tests/unit/compute/v2/fakes.py20
-rw-r--r--openstackclient/tests/unit/compute/v2/test_aggregate.py273
-rw-r--r--openstackclient/tests/unit/compute/v2/test_flavor.py508
-rw-r--r--openstackclient/tests/unit/compute/v2/test_server_backup.py6
-rw-r--r--openstackclient/tests/unit/compute/v2/test_server_image.py6
-rw-r--r--openstackclient/tests/unit/identity/v2_0/test_catalog.py17
-rw-r--r--openstackclient/tests/unit/identity/v2_0/test_project.py2
-rw-r--r--openstackclient/tests/unit/identity/v2_0/test_user.py8
-rw-r--r--openstackclient/tests/unit/identity/v3/test_catalog.py10
-rw-r--r--openstackclient/tests/unit/identity/v3/test_identity_provider.py75
-rw-r--r--openstackclient/tests/unit/image/v1/test_image.py10
-rw-r--r--openstackclient/tests/unit/image/v2/test_image.py25
-rw-r--r--openstackclient/tests/unit/network/v2/test_ip_availability.py8
-rw-r--r--openstackclient/tests/unit/network/v2/test_network.py46
-rw-r--r--openstackclient/tests/unit/network/v2/test_network_agent.py14
-rw-r--r--openstackclient/tests/unit/network/v2/test_port.py64
-rw-r--r--openstackclient/tests/unit/network/v2/test_router.py32
-rw-r--r--openstackclient/tests/unit/network/v2/test_security_group_compute.py10
-rw-r--r--openstackclient/tests/unit/network/v2/test_security_group_network.py16
-rw-r--r--openstackclient/tests/unit/network/v2/test_subnet.py42
-rw-r--r--openstackclient/tests/unit/network/v2/test_subnet_pool.py40
-rw-r--r--openstackclient/tests/unit/utils.py16
-rw-r--r--openstackclient/tests/unit/volume/v1/test_qos_specs.py12
-rw-r--r--openstackclient/tests/unit/volume/v1/test_type.py14
-rw-r--r--openstackclient/tests/unit/volume/v1/test_volume.py36
-rw-r--r--openstackclient/tests/unit/volume/v1/test_volume_backup.py10
-rw-r--r--openstackclient/tests/unit/volume/v2/test_consistency_group.py14
-rw-r--r--openstackclient/tests/unit/volume/v2/test_qos_specs.py12
-rw-r--r--openstackclient/tests/unit/volume/v2/test_type.py24
-rw-r--r--openstackclient/tests/unit/volume/v2/test_volume.py40
-rw-r--r--openstackclient/tests/unit/volume/v2/test_volume_backup.py4
-rw-r--r--releasenotes/notes/add_id_and_enabled_to_list_identity_provider-e0981063a2dc5961.yaml3
-rw-r--r--releasenotes/notes/fix-openstak-image-save-sdk-port-eb160e8ffc92e514.yaml7
-rw-r--r--releasenotes/notes/remove-nlbaas-quota-8b38e0c91ab113cb.yaml4
-rw-r--r--releasenotes/notes/switch-aggregate-to-sdk-ced451a0f28bf6ea.yaml4
-rw-r--r--releasenotes/notes/switch-flavor-to-sdk-b874a3c39559815e.yaml4
-rw-r--r--requirements.txt6
-rw-r--r--setup.cfg1
-rw-r--r--test-requirements.txt3
-rw-r--r--tox.ini8
58 files changed, 1452 insertions, 968 deletions
diff --git a/README.rst b/README.rst
index 41d01124..7dfabd84 100644
--- a/README.rst
+++ b/README.rst
@@ -76,25 +76,63 @@ Configuration
The CLI is configured via environment variables and command-line
options as listed in https://docs.openstack.org/python-openstackclient/latest/cli/authentication.html.
-Authentication using username/password is most commonly used::
-
- export OS_AUTH_URL=<url-to-openstack-identity>
- export OS_IDENTITY_API_VERSION=3
- export OS_PROJECT_NAME=<project-name>
- export OS_PROJECT_DOMAIN_NAME=<project-domain-name>
- export OS_USERNAME=<username>
- export OS_USER_DOMAIN_NAME=<user-domain-name>
- export OS_PASSWORD=<password> # (optional)
-
-The corresponding command-line options look very similar::
-
- --os-auth-url <url>
- --os-identity-api-version 3
- --os-project-name <project-name>
- --os-project-domain-name <project-domain-name>
- --os-username <username>
- --os-user-domain-name <user-domain-name>
- [--os-password <password>]
+Authentication using username/password is most commonly used:
+
+- For a local user, your configuration will look like the one below::
+
+ export OS_AUTH_URL=<url-to-openstack-identity>
+ export OS_IDENTITY_API_VERSION=3
+ export OS_PROJECT_NAME=<project-name>
+ export OS_PROJECT_DOMAIN_NAME=<project-domain-name>
+ export OS_USERNAME=<username>
+ export OS_USER_DOMAIN_NAME=<user-domain-name>
+ export OS_PASSWORD=<password> # (optional)
+
+ The corresponding command-line options look very similar::
+
+ --os-auth-url <url>
+ --os-identity-api-version 3
+ --os-project-name <project-name>
+ --os-project-domain-name <project-domain-name>
+ --os-username <username>
+ --os-user-domain-name <user-domain-name>
+ [--os-password <password>]
+
+- For a federated user, your configuration will look the so::
+
+ export OS_PROJECT_NAME=<project-name>
+ export OS_PROJECT_DOMAIN_NAME=<project-domain-name>
+ export OS_AUTH_URL=<url-to-openstack-identity>
+ export OS_IDENTITY_API_VERSION=3
+ export OS_AUTH_PLUGIN=openid
+ export OS_AUTH_TYPE=v3oidcpassword
+ export OS_USERNAME=<username-in-idp>
+ export OS_PASSWORD=<password-in-idp>
+ export OS_IDENTITY_PROVIDER=<the-desired-idp-in-keystone>
+ export OS_CLIENT_ID=<the-client-id-configured-in-the-idp>
+ export OS_CLIENT_SECRET=<the-client-secred-configured-in-the-idp>
+ export OS_OPENID_SCOPE=<the-scopes-of-desired-attributes-to-claim-from-idp>
+ export OS_PROTOCOL=<the-protocol-used-in-the-apache2-oidc-proxy>
+ export OS_ACCESS_TOKEN_TYPE=<the-access-token-type-used-by-your-idp>
+ export OS_DISCOVERY_ENDPOINT=<the-well-known-endpoint-of-the-idp>
+
+ The corresponding command-line options look very similar::
+
+ --os-project-name <project-name>
+ --os-project-domain-name <project-domain-name>
+ --os-auth-url <url-to-openstack-identity>
+ --os-identity-api-version 3
+ --os-auth-plugin openid
+ --os-auth-type v3oidcpassword
+ --os-username <username-in-idp>
+ --os-password <password-in-idp>
+ --os-identity-provider <the-desired-idp-in-keystone>
+ --os-client-id <the-client-id-configured-in-the-idp>
+ --os-client-secret <the-client-secred-configured-in-the-idp>
+ --os-openid-scope <the-scopes-of-desired-attributes-to-claim-from-idp>
+ --os-protocol <the-protocol-used-in-the-apache2-oidc-proxy>
+ --os-access-token-type <the-access-token-type-used-by-your-idp>
+ --os-discovery-endpoint <the-well-known-endpoint-of-the-idp>
If a password is not provided above (in plaintext), you will be interactively
prompted to provide one securely.
diff --git a/doc/requirements.txt b/doc/requirements.txt
index 962b0e26..28030ca4 100644
--- a/doc/requirements.txt
+++ b/doc/requirements.txt
@@ -26,7 +26,6 @@ python-neutronclient>=6.7.0 # Apache-2.0
python-octaviaclient>=1.11.0 # Apache-2.0
python-rsdclient>=1.0.1 # Apache-2.0
python-saharaclient>=1.4.0 # Apache-2.0
-python-searchlightclient>=1.0.0 #Apache-2.0
python-senlinclient>=1.1.0 # Apache-2.0
python-troveclient>=3.1.0 # Apache-2.0
python-watcherclient>=2.5.0 # Apache-2.0
diff --git a/doc/source/cli/authentication.rst b/doc/source/cli/authentication.rst
index 3b404bce..2e9148c3 100644
--- a/doc/source/cli/authentication.rst
+++ b/doc/source/cli/authentication.rst
@@ -133,3 +133,17 @@ Thus, a minimal set of environment variables would be:
$ export OS_USERNAME=admin
$ export OS_PASSWORD=secret
$ export OS_PROJECT_NAME=admin
+
+Federated users support
+-----------------------
+
+The OpenStackClient also allows the use of Federated users to log in.
+It enables one to use the identity providers credentials such as Google or
+Facebook to log in the OpenStackClient instead of using the Keystone
+credentials.
+
+This is useful in a Federated environment where one credential give access
+to many applications/services that the Federation supports. To check how to
+configure the OpenStackClient to allow Federated users to log in, please check
+the
+:ref:`Authentication using federation. <manpage>`
diff --git a/doc/source/cli/man/openstack.rst b/doc/source/cli/man/openstack.rst
index 687e39eb..dc327a66 100644
--- a/doc/source/cli/man/openstack.rst
+++ b/doc/source/cli/man/openstack.rst
@@ -44,6 +44,7 @@ command line. The primary difference is the use of 'project' in the name of the
* ``token``: Authentication with a token
* ``password``: Authentication with a username and a password
+* ``openid`` : Authentication using the protocol OpenID Connect
Refer to the keystoneclient library documentation for more details about these plugins and their options, and for a complete list of available plugins.
Please bear in mind that some plugins might not support all of the functionalities of :program:`openstack`; for example the v3unscopedsaml plugin can deliver only unscoped tokens, some commands might not be available through this authentication method.
@@ -53,6 +54,31 @@ Additionally, it is possible to use Keystone's service token to authenticate, by
.. NOTE::
To use the ``v3unscopedsaml`` method, the lxml package will need to be installed.
+AUTHENTICATION USING FEDERATION
+-------------------------------
+
+To use federated authentication, your configuration file needs the following:
+
+::
+
+ export OS_PROJECT_NAME=<project-name>
+ export OS_PROJECT_DOMAIN_NAME=<project-domain-name>
+ export OS_AUTH_URL=<url-to-openstack-identity>
+ export OS_IDENTITY_API_VERSION=3
+ export OS_AUTH_PLUGIN=openid
+ export OS_AUTH_TYPE=v3oidcpassword
+ export OS_USERNAME=<username-in-idp>
+ export OS_PASSWORD=<password-in-idp>
+ export OS_IDENTITY_PROVIDER=<the-desired-idp>
+ export OS_CLIENT_ID=<the-client-id-configured-in-the-idp>
+ export OS_CLIENT_SECRET=<the-client-secred-configured-in-the-idp>
+ export OS_OPENID_SCOPE=<the-scopes-of-desired-attributes-to-claim-from-idp>
+ export OS_PROTOCOL=<the-protocol-used-in-the-apache2-oidc-proxy>
+ export OS_ACCESS_TOKEN_TYPE=<the-access-token-type-used-by-your-idp>
+ export OS_DISCOVERY_ENDPOINT=<the-well-known-endpoint-of-the-idp>
+ export OS_ACCESS_TOKEN_ENDPOINT=<the-idp-access-token-url>
+
+
OPTIONS
=======
@@ -356,6 +382,24 @@ Show the detailed information for server ``appweb01``::
--os-auth-url http://localhost:5000:/v2.0 \
server show appweb01
+The same but using openid to authenticate in keystone::
+
+ openstack \
+ --os-project-name ExampleCo \
+ --os-auth-url http://localhost:5000:/v2.0 \
+ --os-auth-plugin openid \
+ --os-auth-type v3oidcpassword \
+ --os-username demo-idp \
+ --os-password secret-idp \
+ --os-identity-provider google \
+ --os-client-id the-id-assigned-to-keystone-in-google \
+ --os-client-secret 3315162f-2b28-4809-9369-cb54730ac837 \
+ --os-openid-scope 'openid email profile'\
+ --os-protocol openid \
+ --os-access-token-type access_token \
+ --os-discovery-endpoint https://accounts.google.com/.well-known/openid-configuration \
+ server show appweb01
+
The same command if the auth environment variables (:envvar:`OS_AUTH_URL`, :envvar:`OS_PROJECT_NAME`,
:envvar:`OS_USERNAME`, :envvar:`OS_PASSWORD`) are set::
@@ -404,6 +448,24 @@ The following environment variables can be set to alter the behaviour of :progra
Authentication URL
+.. envvar:: OS_AUTH_TYPE
+
+ Define the authentication plugin that will be used to handle the
+ authentication process. One of the following:
+
+ - ``v2password``
+ - ``v2token``
+ - ``v3password``
+ - ``v3token``
+ - ``v3oidcclientcredentials``
+ - ``v3oidcpassword``
+ - ``v3oidcauthorizationcode``
+ - ``v3oidcaccesstoken``
+ - ``v3totp``
+ - ``v3tokenlessauth``
+ - ``v3applicationcredential``
+ - ``v3multifactor``
+
.. envvar:: OS_URL
Service URL (when using the service token)
@@ -473,6 +535,56 @@ The following environment variables can be set to alter the behaviour of :progra
Interface type. Valid options are `public`, `admin` and `internal`.
+.. envvar:: OS_PROTOCOL
+
+ Define the protocol that is used to execute the federated authentication
+ process. It is used in the Keystone authentication URL generation process.
+
+.. envvar:: OS_IDENTITY_PROVIDER
+
+ Define the identity provider of your federation that will be used. It is
+ used by the Keystone authentication URL generation process. The available
+ Identity Providers can be listed using the
+ :program:`openstack identity provider list` command
+
+.. envvar:: OS_CLIENT_ID
+
+ Configure the ``CLIENT_ID`` that the CLI will use to authenticate the
+ application (OpenStack) in the Identity Provider. This value is defined on
+ the identity provider side. Do not confuse with the user ID.
+
+.. envvar:: OS_CLIENT_SECRET
+
+ Configure the OS_CLIENT_SECRET that the CLI will use to authenticate the
+ CLI (OpenStack secret in the identity provider).
+
+.. envvar:: OS_OPENID_SCOPE
+
+ Configure the attribute scopes that will be claimed by the Service Provider
+ (SP), in this case OpenStack, from the identity provider. These scopes and
+ which attributes each scope contains are defined in the identity provider
+ side. This parameter can receive multiple values separated by space.
+
+.. envvar:: OS_ACCESS_TOKEN_TYPE
+
+ Define the type of access token that is used in the token introspection
+ process.
+ This variable can assume only one of the states ("access_token" or
+ "id_token").
+
+.. envvar:: OS_DISCOVERY_ENDPOINT
+
+ Configure the identity provider's discovery URL. This URL will provide a
+ discover document that contains metadata describing the identity provider
+ endpoints. This variable is optional if the variable
+ ``OS_ACCESS_TOKEN_ENDPOINT`` is defined.
+
+.. envvar:: OS_ACCESS_TOKEN_ENDPOINT
+
+ Overrides the value presented in the discovery document retrieved from
+ ``OS_DISCOVERY_ENDPOINT`` URL request. This variable is optional if the
+ ``OS_DISCOVERY_ENDPOINT`` is configured.
+
.. NOTE::
If you switch to openstackclient from project specified clients, like:
novaclient, neutronclient and so on, please use `OS_INTERFACE` instead of
diff --git a/doc/source/cli/plugin-commands/index.rst b/doc/source/cli/plugin-commands/index.rst
index 33a8fe06..8c9c5c13 100644
--- a/doc/source/cli/plugin-commands/index.rst
+++ b/doc/source/cli/plugin-commands/index.rst
@@ -22,7 +22,6 @@ Plugin Commands
placement
rsd
sahara
- searchlight
senlin
trove
watcher
diff --git a/doc/source/cli/plugin-commands/searchlight.rst b/doc/source/cli/plugin-commands/searchlight.rst
deleted file mode 100644
index be934aeb..00000000
--- a/doc/source/cli/plugin-commands/searchlight.rst
+++ /dev/null
@@ -1,4 +0,0 @@
-searchlight
------------
-
-.. autoprogram-cliff:: openstack.search.v1
diff --git a/doc/source/conf.py b/doc/source/conf.py
index 2216ddd7..4b60ce4a 100644
--- a/doc/source/conf.py
+++ b/doc/source/conf.py
@@ -263,6 +263,9 @@ autoprogram_cliff_ignored = [
'--help', '--format', '--column', '--max-width', '--fit-width',
'--print-empty', '--prefix', '--noindent', '--quote']
+# Prevent cliff from generating "This command is provided by the
+# python-openstackclient plugin."
+autoprogram_cliff_app_dist_name = 'python-openstackclient'
# -- Options for sphinxcontrib.apidoc ----------------------------------------
diff --git a/doc/source/contributor/plugins.rst b/doc/source/contributor/plugins.rst
index 7ea48edd..fe2cc14a 100644
--- a/doc/source/contributor/plugins.rst
+++ b/doc/source/contributor/plugins.rst
@@ -37,7 +37,6 @@ The following is a list of projects that are an OpenStackClient plugin.
- python-octaviaclient
- python-rsdclient
- python-saharaclient
-- python-searchlightclient
- python-senlinclient
- python-tripleoclient\*\*
- python-troveclient
diff --git a/lower-constraints.txt b/lower-constraints.txt
index b489501b..287f7d45 100644
--- a/lower-constraints.txt
+++ b/lower-constraints.txt
@@ -1,21 +1,17 @@
amqp==2.1.1
-aodhclient==0.9.0
appdirs==1.3.0
asn1crypto==0.23.0
-bandit==1.1.0
+Babel==2.6.0
+bcrypt==3.2.0
cachetools==2.0.0
cffi==1.14.0
-cliff==3.4.0
+cliff==3.5.0
cmd2==0.8.0
-contextlib2==0.4.0
coverage==4.0
-cryptography==2.1
+cryptography==2.7
ddt==1.0.1
debtcollector==1.2.0
decorator==4.4.1
-deprecation==1.0
-docker-pycreds==0.2.1
-docker==2.4.2
dogpile.cache==0.6.5
eventlet==0.18.2
extras==1.0.0
@@ -23,12 +19,8 @@ fasteners==0.7.0
fixtures==3.0.0
future==0.16.0
futurist==2.1.0
-gitdb==0.6.4
-GitPython==1.0.1
-gnocchiclient==3.3.1
greenlet==0.4.15
-httplib2==0.9.1
-idna==2.6
+importlib-metadata==3.1.1
iso8601==0.1.11
Jinja2==2.10
jmespath==0.9.0
@@ -39,17 +31,18 @@ keystoneauth1==3.18.0
kombu==4.0.0
linecache2==1.0.0
MarkupSafe==1.1.1
+mock==4.0.2
monotonic==0.6
mox3==0.20.0
msgpack-python==0.4.0
munch==2.1.0
netaddr==0.7.18
netifaces==0.10.4
-openstacksdk==0.51.0
+openstacksdk==0.52.0
+os-client-config==2.1.0
os-service-types==1.7.0
os-testr==1.0.0
-osc-lib==2.2.0
-osc-placement==1.7.0
+osc-lib==2.3.0
oslo.concurrency==3.26.0
oslo.config==5.2.0
oslo.context==2.19.2
@@ -66,71 +59,41 @@ paramiko==2.7.1
Paste==2.0.2
PasteDeploy==1.5.0
pbr==2.0.0
-pika-pool==0.1.3
pika==0.10.0
-ply==3.10
-positional==1.2.1
+pika-pool==0.1.3
prettytable==0.7.2
-pyasn1==0.1.8
-pycodestyle==2.0.0
pycparser==2.18
pyinotify==0.9.6
-pyOpenSSL==17.1.0
+PyNaCl==1.4.0
pyparsing==2.1.0
pyperclip==1.5.27
-python-barbicanclient==4.5.2
python-cinderclient==3.3.0
python-dateutil==2.5.3
-python-designateclient==2.7.0
-python-glanceclient==2.8.0
-python-heatclient==1.10.0
-python-ironic-inspector-client==1.5.0
-python-ironicclient==2.3.0
-python-karborclient==0.6.0
python-keystoneclient==3.22.0
python-mimeparse==1.6.0
-python-mistralclient==3.1.0
-python-muranoclient==0.8.2
-python-neutronclient==6.7.0
python-novaclient==15.1.0
-python-octaviaclient==1.11.0
-python-rsdclient==1.0.1
-python-saharaclient==1.4.0
-python-searchlightclient==1.0.0
-python-senlinclient==1.1.0
python-subunit==1.0.0
-python-swiftclient==3.2.0
-python-troveclient==3.1.0
-python-watcherclient==2.5.0
-python-zaqarclient==1.0.0
-python-zunclient==3.6.0
pytz==2013.6
-PyYAML==3.12
+PyYAML==3.13
repoze.lru==0.7
-requests-mock==1.2.0
requests==2.14.2
+requests-mock==1.2.0
requestsexceptions==1.2.0
rfc3986==0.3.1
Routes==2.3.1
-rsd-lib==0.1.0
simplejson==3.5.1
-smmap==0.9.0
+six==1.15.0
statsd==3.2.1
stestr==1.0.0
stevedore==2.0.1
-sushy==0.1.0
tempest==17.1.0
tenacity==3.2.1
testrepository==0.0.18
testtools==2.2.0
traceback2==1.4.0
-ujson==1.35
unittest2==1.1.0
urllib3==1.21.1
-validictory==1.1.1
vine==1.1.4
-warlock==1.2.0
WebOb==1.7.1
-websocket-client==0.44.0
wrapt==1.7.0
-yaql==1.1.3
+zipp==3.4.0
diff --git a/openstackclient/common/quota.py b/openstackclient/common/quota.py
index 11de986b..643cb4e4 100644
--- a/openstackclient/common/quota.py
+++ b/openstackclient/common/quota.py
@@ -161,6 +161,13 @@ class BaseQuota(object):
raise
return quota._info
+ def _network_quota_to_dict(self, network_quota):
+ if type(network_quota) is not dict:
+ dict_quota = network_quota.to_dict()
+ else:
+ dict_quota = network_quota
+ return {k: v for k, v in dict_quota.items() if v is not None}
+
def get_network_quota(self, parsed_args):
quota_class = (
parsed_args.quota_class if 'quota_class' in parsed_args else False)
@@ -174,13 +181,11 @@ class BaseQuota(object):
client = self.app.client_manager.network
if default:
network_quota = client.get_quota_default(project)
- if type(network_quota) is not dict:
- network_quota = network_quota.to_dict()
+ network_quota = self._network_quota_to_dict(network_quota)
else:
network_quota = client.get_quota(project,
details=detail)
- if type(network_quota) is not dict:
- network_quota = network_quota.to_dict()
+ network_quota = self._network_quota_to_dict(network_quota)
if detail:
# NOTE(slaweq): Neutron returns values with key "used" but
# Nova for example returns same data with key "in_use"
diff --git a/openstackclient/compute/v2/aggregate.py b/openstackclient/compute/v2/aggregate.py
index 599659a3..8b70f426 100644
--- a/openstackclient/compute/v2/aggregate.py
+++ b/openstackclient/compute/v2/aggregate.py
@@ -18,6 +18,7 @@
import logging
+from openstack import utils as sdk_utils
from osc_lib.cli import format_columns
from osc_lib.cli import parseractions
from osc_lib.command import command
@@ -30,6 +31,25 @@ from openstackclient.i18n import _
LOG = logging.getLogger(__name__)
+_aggregate_formatters = {
+ 'Hosts': format_columns.ListColumn,
+ 'Metadata': format_columns.DictColumn,
+ 'hosts': format_columns.ListColumn,
+ 'metadata': format_columns.DictColumn,
+}
+
+
+def _get_aggregate_columns(item):
+ # To maintain backwards compatibility we need to rename sdk props to
+ # whatever OSC was using before
+ column_map = {
+ 'metadata': 'properties',
+ }
+ hidden_columns = ['links', 'location']
+ return utils.get_osc_show_columns_for_sdk_resource(
+ item, column_map, hidden_columns)
+
+
class AddAggregateHost(command.ShowOne):
_description = _("Add host to aggregate")
@@ -48,26 +68,18 @@ class AddAggregateHost(command.ShowOne):
return parser
def take_action(self, parsed_args):
- compute_client = self.app.client_manager.compute
+ compute_client = self.app.client_manager.sdk_connection.compute
- aggregate = utils.find_resource(
- compute_client.aggregates,
- parsed_args.aggregate,
- )
- data = compute_client.aggregates.add_host(aggregate, parsed_args.host)
-
- info = {}
- info.update(data._info)
-
- # Special mapping for columns to make the output easier to read:
- # 'metadata' --> 'properties'
- info.update(
- {
- 'hosts': format_columns.ListColumn(info.pop('hosts')),
- 'properties': format_columns.DictColumn(info.pop('metadata')),
- },
- )
- return zip(*sorted(info.items()))
+ aggregate = compute_client.find_aggregate(
+ parsed_args.aggregate, ignore_missing=False)
+
+ aggregate = compute_client.add_host_to_aggregate(
+ aggregate.id, parsed_args.host)
+
+ display_columns, columns = _get_aggregate_columns(aggregate)
+ data = utils.get_item_properties(
+ aggregate, columns, formatters=_aggregate_formatters)
+ return (display_columns, data)
class CreateAggregate(command.ShowOne):
@@ -95,36 +107,25 @@ class CreateAggregate(command.ShowOne):
return parser
def take_action(self, parsed_args):
- compute_client = self.app.client_manager.compute
+ compute_client = self.app.client_manager.sdk_connection.compute
- info = {}
- data = compute_client.aggregates.create(
- parsed_args.name,
- parsed_args.zone,
- )
- info.update(data._info)
+ attrs = {'name': parsed_args.name}
+
+ if parsed_args.zone:
+ attrs['availability_zone'] = parsed_args.zone
+
+ aggregate = compute_client.create_aggregate(**attrs)
if parsed_args.property:
- info.update(compute_client.aggregates.set_metadata(
- data,
+ aggregate = compute_client.set_aggregate_metadata(
+ aggregate.id,
parsed_args.property,
- )._info)
-
- # Special mapping for columns to make the output easier to read:
- # 'metadata' --> 'properties'
- hosts = None
- properties = None
- if 'hosts' in info.keys():
- hosts = format_columns.ListColumn(info.pop('hosts'))
- if 'metadata' in info.keys():
- properties = format_columns.DictColumn(info.pop('metadata'))
- info.update(
- {
- 'hosts': hosts,
- 'properties': properties,
- },
- )
- return zip(*sorted(info.items()))
+ )
+
+ display_columns, columns = _get_aggregate_columns(aggregate)
+ data = utils.get_item_properties(
+ aggregate, columns, formatters=_aggregate_formatters)
+ return (display_columns, data)
class DeleteAggregate(command.Command):
@@ -141,13 +142,14 @@ class DeleteAggregate(command.Command):
return parser
def take_action(self, parsed_args):
- compute_client = self.app.client_manager.compute
+ compute_client = self.app.client_manager.sdk_connection.compute
result = 0
for a in parsed_args.aggregate:
try:
- data = utils.find_resource(
- compute_client.aggregates, a)
- compute_client.aggregates.delete(data.id)
+ aggregate = compute_client.find_aggregate(
+ a, ignore_missing=False)
+ compute_client.delete_aggregate(
+ aggregate.id, ignore_missing=False)
except Exception as e:
result += 1
LOG.error(_("Failed to delete aggregate with name or "
@@ -175,15 +177,15 @@ class ListAggregate(command.Lister):
return parser
def take_action(self, parsed_args):
- compute_client = self.app.client_manager.compute
+ compute_client = self.app.client_manager.sdk_connection.compute
- data = compute_client.aggregates.list()
+ aggregates = list(compute_client.aggregates())
if parsed_args.long:
# Remove availability_zone from metadata because Nova doesn't
- for d in data:
- if 'availability_zone' in d.metadata:
- d.metadata.pop('availability_zone')
+ for aggregate in aggregates:
+ if 'availability_zone' in aggregate.metadata:
+ aggregate.metadata.pop('availability_zone')
# This is the easiest way to change column headers
column_headers = (
"ID",
@@ -204,14 +206,11 @@ class ListAggregate(command.Lister):
"Availability Zone",
)
- return (column_headers,
- (utils.get_item_properties(
- s, columns,
- formatters={
- 'Hosts': format_columns.ListColumn,
- 'Metadata': format_columns.DictColumn,
- },
- ) for s in data))
+ data = (
+ utils.get_item_properties(
+ s, columns, formatters=_aggregate_formatters
+ ) for s in aggregates)
+ return (column_headers, data)
class RemoveAggregateHost(command.ShowOne):
@@ -232,29 +231,18 @@ class RemoveAggregateHost(command.ShowOne):
return parser
def take_action(self, parsed_args):
- compute_client = self.app.client_manager.compute
+ compute_client = self.app.client_manager.sdk_connection.compute
- aggregate = utils.find_resource(
- compute_client.aggregates,
- parsed_args.aggregate,
- )
- data = compute_client.aggregates.remove_host(
- aggregate,
- parsed_args.host,
- )
+ aggregate = compute_client.find_aggregate(
+ parsed_args.aggregate, ignore_missing=False)
- info = {}
- info.update(data._info)
+ aggregate = compute_client.remove_host_from_aggregate(
+ aggregate.id, parsed_args.host)
- # Special mapping for columns to make the output easier to read:
- # 'metadata' --> 'properties'
- info.update(
- {
- 'hosts': format_columns.ListColumn(info.pop('hosts')),
- 'properties': format_columns.DictColumn(info.pop('metadata')),
- },
- )
- return zip(*sorted(info.items()))
+ display_columns, columns = _get_aggregate_columns(aggregate)
+ data = utils.get_item_properties(
+ aggregate, columns, formatters=_aggregate_formatters)
+ return (display_columns, data)
class SetAggregate(command.Command):
@@ -296,11 +284,9 @@ class SetAggregate(command.Command):
def take_action(self, parsed_args):
- compute_client = self.app.client_manager.compute
- aggregate = utils.find_resource(
- compute_client.aggregates,
- parsed_args.aggregate,
- )
+ compute_client = self.app.client_manager.sdk_connection.compute
+ aggregate = compute_client.find_aggregate(
+ parsed_args.aggregate, ignore_missing=False)
kwargs = {}
if parsed_args.name:
@@ -308,18 +294,12 @@ class SetAggregate(command.Command):
if parsed_args.zone:
kwargs['availability_zone'] = parsed_args.zone
if kwargs:
- compute_client.aggregates.update(
- aggregate,
- kwargs
- )
+ compute_client.update_aggregate(aggregate.id, **kwargs)
set_property = {}
if parsed_args.no_property:
- # NOTE(RuiChen): "availability_zone" is removed from response of
- # aggregate show and create commands, don't see it
- # anywhere, so pop it, avoid the unexpected server
- # exception(can't unset the availability zone from
- # aggregate metadata in nova).
+ # NOTE(RuiChen): "availability_zone" can not be unset from
+ # properties. It is already excluded from show and create output.
set_property.update({key: None
for key in aggregate.metadata.keys()
if key != 'availability_zone'})
@@ -327,8 +307,8 @@ class SetAggregate(command.Command):
set_property.update(parsed_args.property)
if set_property:
- compute_client.aggregates.set_metadata(
- aggregate,
+ compute_client.set_aggregate_metadata(
+ aggregate.id,
set_property
)
@@ -347,31 +327,18 @@ class ShowAggregate(command.ShowOne):
def take_action(self, parsed_args):
- compute_client = self.app.client_manager.compute
- data = utils.find_resource(
- compute_client.aggregates,
- parsed_args.aggregate,
- )
+ compute_client = self.app.client_manager.sdk_connection.compute
+ aggregate = compute_client.find_aggregate(
+ parsed_args.aggregate, ignore_missing=False)
+
# Remove availability_zone from metadata because Nova doesn't
- if 'availability_zone' in data.metadata:
- data.metadata.pop('availability_zone')
-
- # Special mapping for columns to make the output easier to read:
- # 'metadata' --> 'properties'
- data._info.update(
- {
- 'hosts': format_columns.ListColumn(
- data._info.pop('hosts')
- ),
- 'properties': format_columns.DictColumn(
- data._info.pop('metadata')
- ),
- },
- )
+ if 'availability_zone' in aggregate.metadata:
+ aggregate.metadata.pop('availability_zone')
- info = {}
- info.update(data._info)
- return zip(*sorted(info.items()))
+ display_columns, columns = _get_aggregate_columns(aggregate)
+ data = utils.get_item_properties(
+ aggregate, columns, formatters=_aggregate_formatters)
+ return (display_columns, data)
class UnsetAggregate(command.Command):
@@ -394,14 +361,56 @@ class UnsetAggregate(command.Command):
return parser
def take_action(self, parsed_args):
- compute_client = self.app.client_manager.compute
- aggregate = utils.find_resource(
- compute_client.aggregates,
- parsed_args.aggregate)
+ compute_client = self.app.client_manager.sdk_connection.compute
+ aggregate = compute_client.find_aggregate(
+ parsed_args.aggregate, ignore_missing=False)
unset_property = {}
if parsed_args.property:
unset_property.update({key: None for key in parsed_args.property})
if unset_property:
- compute_client.aggregates.set_metadata(aggregate,
- unset_property)
+ compute_client.set_aggregate_metadata(
+ aggregate, unset_property)
+
+
+class CacheImageForAggregate(command.Command):
+ _description = _("Request image caching for aggregate")
+ # NOTE(gtema): According to stephenfin and dansmith there is no and will
+ # not be anything to return.
+
+ def get_parser(self, prog_name):
+ parser = super(CacheImageForAggregate, self).get_parser(prog_name)
+ parser.add_argument(
+ 'aggregate',
+ metavar='<aggregate>',
+ help=_("Aggregate (name or ID)")
+ )
+ parser.add_argument(
+ 'image',
+ metavar='<image>',
+ nargs='+',
+ help=_("Image ID to request caching for aggregate (name or ID). "
+ "May be specified multiple times.")
+ )
+ return parser
+
+ def take_action(self, parsed_args):
+ compute_client = self.app.client_manager.sdk_connection.compute
+
+ if not sdk_utils.supports_microversion(compute_client, '2.81'):
+ msg = _(
+ 'This operation requires server support for '
+ 'API microversion 2.81'
+ )
+ raise exceptions.CommandError(msg)
+
+ aggregate = compute_client.find_aggregate(
+ parsed_args.aggregate, ignore_missing=False)
+
+ images = []
+ for img in parsed_args.image:
+ image = self.app.client_manager.sdk_connection.image.find_image(
+ img, ignore_missing=False)
+ images.append(image.id)
+
+ compute_client.aggregate_precache_images(aggregate.id, images)
diff --git a/openstackclient/compute/v2/flavor.py b/openstackclient/compute/v2/flavor.py
index 00431b7b..8477e8ef 100644
--- a/openstackclient/compute/v2/flavor.py
+++ b/openstackclient/compute/v2/flavor.py
@@ -17,7 +17,8 @@
import logging
-from novaclient import api_versions
+from openstack import exceptions as sdk_exceptions
+from openstack import utils as sdk_utils
from osc_lib.cli import format_columns
from osc_lib.cli import parseractions
from osc_lib.command import command
@@ -33,10 +34,7 @@ LOG = logging.getLogger(__name__)
_formatters = {
'extra_specs': format_columns.DictColumn,
- # Unless we finish switch to use SDK resources this need to be doubled this
- # way
- 'properties': format_columns.DictColumn,
- 'Properties': format_columns.DictColumn
+ 'properties': format_columns.DictColumn
}
@@ -51,29 +49,10 @@ def _get_flavor_columns(item):
}
hidden_columns = ['links', 'location']
-
return utils.get_osc_show_columns_for_sdk_resource(
item, column_map, hidden_columns)
-def _find_flavor(compute_client, flavor):
- try:
- return compute_client.flavors.get(flavor)
- except Exception as ex:
- if type(ex).__name__ == 'NotFound':
- pass
- else:
- raise
- try:
- return compute_client.flavors.find(name=flavor, is_public=None)
- except Exception as ex:
- if type(ex).__name__ == 'NotFound':
- msg = _("No flavor with a name or ID of '%s' exists.") % flavor
- raise exceptions.CommandError(msg)
- else:
- raise
-
-
class CreateFlavor(command.ShowOne):
_description = _("Create new flavor")
@@ -87,9 +66,7 @@ class CreateFlavor(command.ShowOne):
parser.add_argument(
"--id",
metavar="<id>",
- default='auto',
- help=_("Unique flavor ID; 'auto' creates a UUID "
- "(default: auto)")
+ help=_("Unique flavor ID")
)
parser.add_argument(
"--ram",
@@ -170,32 +147,36 @@ class CreateFlavor(command.ShowOne):
return parser
def take_action(self, parsed_args):
- compute_client = self.app.client_manager.compute
+ compute_client = self.app.client_manager.sdk_connection.compute
identity_client = self.app.client_manager.identity
if parsed_args.project and parsed_args.public:
msg = _("--project is only allowed with --private")
raise exceptions.CommandError(msg)
+ args = {
+ 'name': parsed_args.name,
+ 'ram': parsed_args.ram,
+ 'vcpus': parsed_args.vcpus,
+ 'disk': parsed_args.disk,
+ 'id': parsed_args.id,
+ 'ephemeral': parsed_args.ephemeral,
+ 'swap': parsed_args.swap,
+ 'rxtx_factor': parsed_args.rxtx_factor,
+ 'is_public': parsed_args.public,
+ }
+
if parsed_args.description:
- if compute_client.api_version < api_versions.APIVersion("2.55"):
- msg = _("--os-compute-api-version 2.55 or later is required")
+ if not sdk_utils.supports_microversion(compute_client, '2.55'):
+ msg = _(
+ 'The --description parameter requires server support for '
+ 'API microversion 2.55'
+ )
raise exceptions.CommandError(msg)
- args = (
- parsed_args.name,
- parsed_args.ram,
- parsed_args.vcpus,
- parsed_args.disk,
- parsed_args.id,
- parsed_args.ephemeral,
- parsed_args.swap,
- parsed_args.rxtx_factor,
- parsed_args.public,
- parsed_args.description
- )
+ args['description'] = parsed_args.description
- flavor = compute_client.flavors.create(*args)
+ flavor = compute_client.create_flavor(**args)
if parsed_args.project:
try:
@@ -204,7 +185,7 @@ class CreateFlavor(command.ShowOne):
parsed_args.project,
parsed_args.project_domain,
).id
- compute_client.flavor_access.add_tenant_access(
+ compute_client.flavor_add_tenant_access(
flavor.id, project_id)
except Exception as e:
msg = _("Failed to add project %(project)s access to "
@@ -212,19 +193,14 @@ class CreateFlavor(command.ShowOne):
LOG.error(msg, {'project': parsed_args.project, 'e': e})
if parsed_args.property:
try:
- flavor.set_keys(parsed_args.property)
+ flavor = compute_client.create_flavor_extra_specs(
+ flavor, parsed_args.property)
except Exception as e:
LOG.error(_("Failed to set flavor property: %s"), e)
- flavor_info = flavor._info.copy()
- flavor_info['properties'] = flavor.get_keys()
-
- display_columns, columns = _get_flavor_columns(flavor_info)
- data = utils.get_dict_properties(
- flavor_info, columns,
- formatters=_formatters,
- mixed_case_fields=['OS-FLV-DISABLED:disabled',
- 'OS-FLV-EXT-DATA:ephemeral'])
+ display_columns, columns = _get_flavor_columns(flavor)
+ data = utils.get_dict_properties(flavor, columns,
+ formatters=_formatters)
return (display_columns, data)
@@ -243,12 +219,12 @@ class DeleteFlavor(command.Command):
return parser
def take_action(self, parsed_args):
- compute_client = self.app.client_manager.compute
+ compute_client = self.app.client_manager.sdk_connection.compute
result = 0
for f in parsed_args.flavor:
try:
- flavor = _find_flavor(compute_client, f)
- compute_client.flavors.delete(flavor.id)
+ flavor = compute_client.find_flavor(f, ignore_missing=False)
+ compute_client.delete_flavor(flavor.id)
except Exception as e:
result += 1
LOG.error(_("Failed to delete flavor with name or "
@@ -307,37 +283,63 @@ class ListFlavor(command.Lister):
return parser
def take_action(self, parsed_args):
- compute_client = self.app.client_manager.compute
+ compute_client = self.app.client_manager.sdk_connection.compute
+ # is_public is ternary - None means give all flavors,
+ # True is public only and False is private only
+ # By default Nova assumes True and gives admins public flavors
+ # and flavors from their own projects only.
+ is_public = None if parsed_args.all else parsed_args.public
+
+ query_attrs = {
+ 'is_public': is_public
+ }
+ if parsed_args.marker:
+ query_attrs['marker'] = parsed_args.marker
+ if parsed_args.limit:
+ query_attrs['limit'] = parsed_args.limit
+ if parsed_args.limit or parsed_args.marker:
+ # User passed explicit pagination request, switch off SDK
+ # pagination
+ query_attrs['paginated'] = False
+
+ data = list(compute_client.flavors(**query_attrs))
+ # Even if server supports 2.61 some policy might stop it sending us
+ # extra_specs. So try to fetch them if they are absent
+ for f in data:
+ if not f.extra_specs:
+ compute_client.fetch_flavor_extra_specs(f)
+
columns = (
+ "id",
+ "name",
+ "ram",
+ "disk",
+ "ephemeral",
+ "vcpus",
+ "is_public"
+ )
+ if parsed_args.long:
+ columns += (
+ "swap",
+ "rxtx_factor",
+ "extra_specs",
+ )
+
+ column_headers = (
"ID",
"Name",
"RAM",
"Disk",
"Ephemeral",
"VCPUs",
- "Is Public",
+ "Is Public"
)
-
- # is_public is ternary - None means give all flavors,
- # True is public only and False is private only
- # By default Nova assumes True and gives admins public flavors
- # and flavors from their own projects only.
- is_public = None if parsed_args.all else parsed_args.public
-
- data = compute_client.flavors.list(is_public=is_public,
- marker=parsed_args.marker,
- limit=parsed_args.limit)
-
if parsed_args.long:
- columns = columns + (
+ column_headers += (
"Swap",
"RXTX Factor",
"Properties",
)
- for f in data:
- f.properties = f.get_keys()
-
- column_headers = columns
return (column_headers,
(utils.get_item_properties(
@@ -387,24 +389,42 @@ class SetFlavor(command.Command):
return parser
def take_action(self, parsed_args):
- compute_client = self.app.client_manager.compute
+ compute_client = self.app.client_manager.sdk_connection.compute
identity_client = self.app.client_manager.identity
- flavor = _find_flavor(compute_client, parsed_args.flavor)
+ try:
+ flavor = compute_client.find_flavor(
+ parsed_args.flavor,
+ get_extra_specs=True,
+ ignore_missing=False)
+ except sdk_exceptions.ResourceNotFound as e:
+ raise exceptions.CommandError(e.message)
+
+ if parsed_args.description:
+ if not sdk_utils.supports_microversion(compute_client, '2.55'):
+ msg = _(
+ 'The --description parameter requires server support for '
+ 'API microversion 2.55'
+ )
+ raise exceptions.CommandError(msg)
+
+ compute_client.update_flavor(
+ flavor=flavor.id, description=parsed_args.description)
result = 0
- key_list = []
if parsed_args.no_property:
try:
- for key in flavor.get_keys().keys():
- key_list.append(key)
- flavor.unset_keys(key_list)
+ for key in flavor.extra_specs.keys():
+ compute_client.delete_flavor_extra_specs_property(
+ flavor.id, key)
except Exception as e:
LOG.error(_("Failed to clear flavor property: %s"), e)
result += 1
+
if parsed_args.property:
try:
- flavor.set_keys(parsed_args.property)
+ compute_client.create_flavor_extra_specs(
+ flavor.id, parsed_args.property)
except Exception as e:
LOG.error(_("Failed to set flavor property: %s"), e)
result += 1
@@ -420,7 +440,7 @@ class SetFlavor(command.Command):
parsed_args.project,
parsed_args.project_domain,
).id
- compute_client.flavor_access.add_tenant_access(
+ compute_client.flavor_add_tenant_access(
flavor.id, project_id)
except Exception as e:
LOG.error(_("Failed to set flavor access to project: %s"), e)
@@ -430,13 +450,6 @@ class SetFlavor(command.Command):
raise exceptions.CommandError(_("Command Failed: One or more of"
" the operations failed"))
- if parsed_args.description:
- if compute_client.api_version < api_versions.APIVersion("2.55"):
- msg = _("--os-compute-api-version 2.55 or later is required")
- raise exceptions.CommandError(msg)
- compute_client.flavors.update(flavor=flavor.id,
- description=parsed_args.description)
-
class ShowFlavor(command.ShowOne):
_description = _("Display flavor details")
@@ -451,35 +464,32 @@ class ShowFlavor(command.ShowOne):
return parser
def take_action(self, parsed_args):
- compute_client = self.app.client_manager.compute
- resource_flavor = _find_flavor(compute_client, parsed_args.flavor)
+ compute_client = self.app.client_manager.sdk_connection.compute
+ flavor = compute_client.find_flavor(
+ parsed_args.flavor, get_extra_specs=True, ignore_missing=False)
access_projects = None
# get access projects list of this flavor
- if not resource_flavor.is_public:
+ if not flavor.is_public:
try:
- flavor_access = compute_client.flavor_access.list(
- flavor=resource_flavor.id)
- access_projects = [utils.get_field(access, 'tenant_id')
- for access in flavor_access]
+ flavor_access = compute_client.get_flavor_access(
+ flavor=flavor.id)
+ access_projects = [
+ utils.get_field(access, 'tenant_id')
+ for access in flavor_access]
except Exception as e:
msg = _("Failed to get access projects list "
"for flavor '%(flavor)s': %(e)s")
LOG.error(msg, {'flavor': parsed_args.flavor, 'e': e})
- flavor = resource_flavor._info.copy()
- flavor.update({
- 'access_project_ids': access_projects
- })
-
- flavor['properties'] = resource_flavor.get_keys()
+ # Since we need to inject "access_project_id" into resource - convert
+ # it to dict and treat it respectively
+ flavor = flavor.to_dict()
+ flavor['access_project_ids'] = access_projects
display_columns, columns = _get_flavor_columns(flavor)
data = utils.get_dict_properties(
- flavor, columns,
- formatters=_formatters,
- mixed_case_fields=['OS-FLV-DISABLED:disabled',
- 'OS-FLV-EXT-DATA:ephemeral'])
+ flavor, columns, formatters=_formatters)
return (display_columns, data)
@@ -512,32 +522,40 @@ class UnsetFlavor(command.Command):
return parser
def take_action(self, parsed_args):
- compute_client = self.app.client_manager.compute
+ compute_client = self.app.client_manager.sdk_connection.compute
identity_client = self.app.client_manager.identity
- flavor = _find_flavor(compute_client, parsed_args.flavor)
+ try:
+ flavor = compute_client.find_flavor(
+ parsed_args.flavor,
+ get_extra_specs=True,
+ ignore_missing=False)
+ except sdk_exceptions.ResourceNotFound as e:
+ raise exceptions.CommandError(_(e.message))
result = 0
if parsed_args.property:
- try:
- flavor.unset_keys(parsed_args.property)
- except Exception as e:
- LOG.error(_("Failed to unset flavor property: %s"), e)
- result += 1
+ for key in parsed_args.property:
+ try:
+ compute_client.delete_flavor_extra_specs_property(
+ flavor.id, key)
+ except sdk_exceptions.SDKException as e:
+ LOG.error(_("Failed to unset flavor property: %s"), e)
+ result += 1
if parsed_args.project:
try:
if flavor.is_public:
msg = _("Cannot remove access for a public flavor")
raise exceptions.CommandError(msg)
- else:
- project_id = identity_common.find_project(
- identity_client,
- parsed_args.project,
- parsed_args.project_domain,
- ).id
- compute_client.flavor_access.remove_tenant_access(
- flavor.id, project_id)
+
+ project_id = identity_common.find_project(
+ identity_client,
+ parsed_args.project,
+ parsed_args.project_domain,
+ ).id
+ compute_client.flavor_remove_tenant_access(
+ flavor.id, project_id)
except Exception as e:
LOG.error(_("Failed to remove flavor access from project: %s"),
e)
diff --git a/openstackclient/compute/v2/server.py b/openstackclient/compute/v2/server.py
index c6da0fba..24c09ed1 100644
--- a/openstackclient/compute/v2/server.py
+++ b/openstackclient/compute/v2/server.py
@@ -711,7 +711,12 @@ class CreateServer(command.ShowOne):
parser.add_argument(
'--availability-zone',
metavar='<zone-name>',
- help=_('Select an availability zone for the server'),
+ help=_('Select an availability zone for the server. '
+ 'Host and node are optional parameters. '
+ 'Availability zone in the format '
+ '<zone-name>:<host-name>:<node-name>, '
+ '<zone-name>::<node-name>, <zone-name>:<host-name> '
+ 'or <zone-name>'),
)
parser.add_argument(
'--host',
@@ -2443,47 +2448,57 @@ class RebuildServer(command.ShowOne):
parser.add_argument(
'--image',
metavar='<image>',
- help=_('Recreate server from the specified image (name or ID).'
- ' Defaults to the currently used one.'),
+ help=_(
+ 'Recreate server from the specified image (name or ID).'
+ 'Defaults to the currently used one.'
+ ),
)
parser.add_argument(
'--password',
metavar='<password>',
- help=_("Set the password on the rebuilt instance"),
+ help=_('Set a password on the rebuilt server'),
)
parser.add_argument(
'--property',
metavar='<key=value>',
action=parseractions.KeyValueAction,
- help=_('Set a property on the rebuilt instance '
- '(repeat option to set multiple values)'),
+ help=_(
+ 'Set a new property on the rebuilt server '
+ '(repeat option to set multiple values)'
+ ),
)
parser.add_argument(
'--description',
metavar='<description>',
- help=_('New description for the server (supported by '
- '--os-compute-api-version 2.19 or above'),
- )
- parser.add_argument(
- '--wait',
- action='store_true',
- help=_('Wait for rebuild to complete'),
+ help=_(
+ 'Set a new description on the rebuilt server '
+ '(supported by --os-compute-api-version 2.19 or above)'
+ ),
)
key_group = parser.add_mutually_exclusive_group()
key_group.add_argument(
'--key-name',
metavar='<key-name>',
- help=_("Set the key name of key pair on the rebuilt instance."
- " Cannot be specified with the '--key-unset' option."
- " (Supported by API versions '2.54' - '2.latest')"),
+ help=_(
+ 'Set the key name of key pair on the rebuilt server. '
+ 'Cannot be specified with the --key-unset option. '
+ '(supported by --os-compute-api-version 2.54 or above)'
+ ),
)
key_group.add_argument(
'--key-unset',
action='store_true',
default=False,
- help=_("Unset the key name of key pair on the rebuilt instance."
- " Cannot be specified with the '--key-name' option."
- " (Supported by API versions '2.54' - '2.latest')"),
+ help=_(
+ 'Unset the key name of key pair on the rebuilt server. '
+ 'Cannot be specified with the --key-name option. '
+ '(supported by --os-compute-api-version 2.54 or above)'
+ ),
+ )
+ parser.add_argument(
+ '--wait',
+ action='store_true',
+ help=_('Wait for rebuild to complete'),
)
return parser
@@ -2509,24 +2524,38 @@ class RebuildServer(command.ShowOne):
image = image_client.get_image(image_id)
kwargs = {}
+
if parsed_args.property:
kwargs['meta'] = parsed_args.property
+
if parsed_args.description:
if server.api_version < api_versions.APIVersion("2.19"):
- msg = _("Description is not supported for "
- "--os-compute-api-version less than 2.19")
+ msg = _(
+ '--os-compute-api-version 2.19 or greater is required to '
+ 'support the --description option'
+ )
raise exceptions.CommandError(msg)
+
kwargs['description'] = parsed_args.description
- if parsed_args.key_name or parsed_args.key_unset:
+ if parsed_args.key_name:
+ if compute_client.api_version < api_versions.APIVersion('2.54'):
+ msg = _(
+ '--os-compute-api-version 2.54 or greater is required to '
+ 'support the --key-name option'
+ )
+ raise exceptions.CommandError(msg)
+
+ kwargs['key_name'] = parsed_args.key_name
+ elif parsed_args.key_unset:
if compute_client.api_version < api_versions.APIVersion('2.54'):
- msg = _('--os-compute-api-version 2.54 or later is required')
+ msg = _(
+ '--os-compute-api-version 2.54 or greater is required to '
+ 'support the --no-key-name option'
+ )
raise exceptions.CommandError(msg)
- if parsed_args.key_unset:
kwargs['key_name'] = None
- if parsed_args.key_name:
- kwargs['key_name'] = parsed_args.key_name
server = server.rebuild(image, parsed_args.password, **kwargs)
if parsed_args.wait:
@@ -2537,13 +2566,12 @@ class RebuildServer(command.ShowOne):
):
self.app.stdout.write(_('Complete\n'))
else:
- LOG.error(_('Error rebuilding server: %s'),
- server.id)
+ LOG.error(_('Error rebuilding server: %s'), server.id)
self.app.stdout.write(_('Error rebuilding server\n'))
raise SystemExit
- details = _prep_server_detail(compute_client, image_client, server,
- refresh=False)
+ details = _prep_server_detail(
+ compute_client, image_client, server, refresh=False)
return zip(*sorted(details.items()))
diff --git a/openstackclient/identity/v2_0/catalog.py b/openstackclient/identity/v2_0/catalog.py
index ccedbf33..05d0e9ae 100644
--- a/openstackclient/identity/v2_0/catalog.py
+++ b/openstackclient/identity/v2_0/catalog.py
@@ -91,7 +91,7 @@ class ShowCatalog(command.ShowOne):
for service in auth_ref.service_catalog.catalog:
if (service.get('name') == parsed_args.service or
service.get('type') == parsed_args.service):
- data = service
+ data = service.copy()
data['endpoints'] = EndpointsColumn(data['endpoints'])
if 'endpoints_links' in data:
data.pop('endpoints_links')
diff --git a/openstackclient/identity/v3/identity_provider.py b/openstackclient/identity/v3/identity_provider.py
index 2b2d9d11..7307cea0 100644
--- a/openstackclient/identity/v3/identity_provider.py
+++ b/openstackclient/identity/v3/identity_provider.py
@@ -143,10 +143,32 @@ class DeleteIdentityProvider(command.Command):
class ListIdentityProvider(command.Lister):
_description = _("List identity providers")
+ def get_parser(self, prog_name):
+ parser = super(ListIdentityProvider, self).get_parser(prog_name)
+ parser.add_argument(
+ '--id',
+ metavar='<id>',
+ help=_('The Identity Providers’ ID attribute'),
+ )
+ parser.add_argument(
+ '--enabled',
+ dest='enabled',
+ action='store_true',
+ help=_('The Identity Providers that are enabled will be returned'),
+ )
+ return parser
+
def take_action(self, parsed_args):
columns = ('ID', 'Enabled', 'Domain ID', 'Description')
identity_client = self.app.client_manager.identity
- data = identity_client.federation.identity_providers.list()
+
+ kwargs = {}
+ if parsed_args.id:
+ kwargs['id'] = parsed_args.id
+ if parsed_args.enabled:
+ kwargs['enabled'] = True
+
+ data = identity_client.federation.identity_providers.list(**kwargs)
return (columns,
(utils.get_item_properties(
s, columns,
diff --git a/openstackclient/image/v1/image.py b/openstackclient/image/v1/image.py
index cf1d6817..64aa3fcd 100644
--- a/openstackclient/image/v1/image.py
+++ b/openstackclient/image/v1/image.py
@@ -478,7 +478,11 @@ class SaveImage(command.Command):
image_client = self.app.client_manager.image
image = image_client.find_image(parsed_args.image)
- image_client.download_image(image.id, output=parsed_args.file)
+ output_file = parsed_args.file
+ if output_file is None:
+ output_file = getattr(sys.stdout, "buffer", sys.stdout)
+
+ image_client.download_image(image.id, stream=True, output=output_file)
class SetImage(command.Command):
diff --git a/openstackclient/image/v2/image.py b/openstackclient/image/v2/image.py
index 4f3e9d0b..58d92f51 100644
--- a/openstackclient/image/v2/image.py
+++ b/openstackclient/image/v2/image.py
@@ -803,7 +803,11 @@ class SaveImage(command.Command):
image_client = self.app.client_manager.image
image = image_client.find_image(parsed_args.image)
- image_client.download_image(image.id, output=parsed_args.file)
+ output_file = parsed_args.file
+ if output_file is None:
+ output_file = getattr(sys.stdout, "buffer", sys.stdout)
+
+ image_client.download_image(image.id, stream=True, output=output_file)
class SetImage(command.Command):
diff --git a/openstackclient/tests/unit/common/test_quota.py b/openstackclient/tests/unit/common/test_quota.py
index 6504c5b0..8771359c 100644
--- a/openstackclient/tests/unit/common/test_quota.py
+++ b/openstackclient/tests/unit/common/test_quota.py
@@ -1087,3 +1087,26 @@ class TestQuotaShow(TestQuota):
identity_fakes.project_id, details=False
)
self.assertNotCalled(self.network.get_quota_default)
+
+ def test_network_quota_show_remove_empty(self):
+ arglist = [
+ self.projects[0].name,
+ ]
+ verifylist = [
+ ('project', self.projects[0].name),
+ ]
+ parsed_args = self.check_parser(self.cmd, arglist, verifylist)
+
+ # First check that all regular values are returned
+ result = self.cmd.get_network_quota(parsed_args)
+ self.assertEqual(len(network_fakes.QUOTA), len(result))
+
+ # set 1 of the values to None, and verify it is not returned
+ orig_get_quota = self.network.get_quota
+ network_quotas = copy.copy(network_fakes.QUOTA)
+ network_quotas['healthmonitor'] = None
+ self.network.get_quota = mock.Mock(return_value=network_quotas)
+ result = self.cmd.get_network_quota(parsed_args)
+ self.assertEqual(len(network_fakes.QUOTA) - 1, len(result))
+ # Go back to default mock
+ self.network.get_quota = orig_get_quota
diff --git a/openstackclient/tests/unit/compute/v2/fakes.py b/openstackclient/tests/unit/compute/v2/fakes.py
index 3a06d271..d3d037a9 100644
--- a/openstackclient/tests/unit/compute/v2/fakes.py
+++ b/openstackclient/tests/unit/compute/v2/fakes.py
@@ -19,6 +19,7 @@ from unittest import mock
import uuid
from novaclient import api_versions
+from openstack.compute.v2 import flavor as _flavor
from openstackclient.api import compute_v2
from openstackclient.tests.unit import fakes
@@ -164,7 +165,6 @@ class FakeComputev2Client(object):
self.extensions.resource_class = fakes.FakeResource(None, {})
self.flavors = mock.Mock()
- self.flavors.resource_class = fakes.FakeResource(None, {})
self.flavor_access = mock.Mock()
self.flavor_access.resource_class = fakes.FakeResource(None, {})
@@ -777,27 +777,13 @@ class FakeFlavor(object):
'os-flavor-access:is_public': True,
'description': 'description',
'OS-FLV-EXT-DATA:ephemeral': 0,
- 'properties': {'property': 'value'},
+ 'extra_specs': {'property': 'value'},
}
# Overwrite default attributes.
flavor_info.update(attrs)
- # Set default methods.
- flavor_methods = {
- 'set_keys': None,
- 'unset_keys': None,
- 'get_keys': {'property': 'value'},
- }
-
- flavor = fakes.FakeResource(info=copy.deepcopy(flavor_info),
- methods=flavor_methods,
- loaded=True)
-
- # Set attributes with special mappings in nova client.
- flavor.disabled = flavor_info['OS-FLV-DISABLED:disabled']
- flavor.is_public = flavor_info['os-flavor-access:is_public']
- flavor.ephemeral = flavor_info['OS-FLV-EXT-DATA:ephemeral']
+ flavor = _flavor.Flavor(**flavor_info)
return flavor
diff --git a/openstackclient/tests/unit/compute/v2/test_aggregate.py b/openstackclient/tests/unit/compute/v2/test_aggregate.py
index cd0c1525..e12edd0f 100644
--- a/openstackclient/tests/unit/compute/v2/test_aggregate.py
+++ b/openstackclient/tests/unit/compute/v2/test_aggregate.py
@@ -16,12 +16,14 @@
from unittest import mock
from unittest.mock import call
+from openstack import exceptions as sdk_exceptions
+from openstack import utils as sdk_utils
from osc_lib.cli import format_columns
from osc_lib import exceptions
-from osc_lib import utils
from openstackclient.compute.v2 import aggregate
from openstackclient.tests.unit.compute.v2 import fakes as compute_fakes
+from openstackclient.tests.unit.image.v2 import fakes as image_fakes
class TestAggregate(compute_fakes.TestComputev2):
@@ -48,8 +50,17 @@ class TestAggregate(compute_fakes.TestComputev2):
super(TestAggregate, self).setUp()
# Get a shortcut to the AggregateManager Mock
- self.aggregate_mock = self.app.client_manager.compute.aggregates
- self.aggregate_mock.reset_mock()
+ self.app.client_manager.sdk_connection = mock.Mock()
+ self.app.client_manager.sdk_connection.compute = mock.Mock()
+ self.sdk_client = self.app.client_manager.sdk_connection.compute
+ self.sdk_client.aggregates = mock.Mock()
+ self.sdk_client.find_aggregate = mock.Mock()
+ self.sdk_client.create_aggregate = mock.Mock()
+ self.sdk_client.update_aggregate = mock.Mock()
+ self.sdk_client.update_aggregate = mock.Mock()
+ self.sdk_client.set_aggregate_metadata = mock.Mock()
+ self.sdk_client.add_host_to_aggregate = mock.Mock()
+ self.sdk_client.remove_host_from_aggregate = mock.Mock()
class TestAggregateAddHost(TestAggregate):
@@ -57,8 +68,8 @@ class TestAggregateAddHost(TestAggregate):
def setUp(self):
super(TestAggregateAddHost, self).setUp()
- self.aggregate_mock.get.return_value = self.fake_ag
- self.aggregate_mock.add_host.return_value = self.fake_ag
+ self.sdk_client.find_aggregate.return_value = self.fake_ag
+ self.sdk_client.add_host_to_aggregate.return_value = self.fake_ag
self.cmd = aggregate.AddAggregateHost(self.app, None)
def test_aggregate_add_host(self):
@@ -72,11 +83,12 @@ class TestAggregateAddHost(TestAggregate):
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
columns, data = self.cmd.take_action(parsed_args)
- self.aggregate_mock.get.assert_called_once_with(parsed_args.aggregate)
- self.aggregate_mock.add_host.assert_called_once_with(self.fake_ag,
- parsed_args.host)
+ self.sdk_client.find_aggregate.assert_called_once_with(
+ parsed_args.aggregate, ignore_missing=False)
+ self.sdk_client.add_host_to_aggregate.assert_called_once_with(
+ self.fake_ag.id, parsed_args.host)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
class TestAggregateCreate(TestAggregate):
@@ -84,8 +96,8 @@ class TestAggregateCreate(TestAggregate):
def setUp(self):
super(TestAggregateCreate, self).setUp()
- self.aggregate_mock.create.return_value = self.fake_ag
- self.aggregate_mock.set_metadata.return_value = self.fake_ag
+ self.sdk_client.create_aggregate.return_value = self.fake_ag
+ self.sdk_client.set_aggregate_metadata.return_value = self.fake_ag
self.cmd = aggregate.CreateAggregate(self.app, None)
def test_aggregate_create(self):
@@ -97,10 +109,10 @@ class TestAggregateCreate(TestAggregate):
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
columns, data = self.cmd.take_action(parsed_args)
- self.aggregate_mock.create.assert_called_once_with(parsed_args.name,
- None)
+ self.sdk_client.create_aggregate.assert_called_once_with(
+ name=parsed_args.name)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_aggregate_create_with_zone(self):
arglist = [
@@ -114,10 +126,10 @@ class TestAggregateCreate(TestAggregate):
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
columns, data = self.cmd.take_action(parsed_args)
- self.aggregate_mock.create.assert_called_once_with(parsed_args.name,
- parsed_args.zone)
+ self.sdk_client.create_aggregate.assert_called_once_with(
+ name=parsed_args.name, availability_zone=parsed_args.zone)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_aggregate_create_with_property(self):
arglist = [
@@ -131,12 +143,12 @@ class TestAggregateCreate(TestAggregate):
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
columns, data = self.cmd.take_action(parsed_args)
- self.aggregate_mock.create.assert_called_once_with(parsed_args.name,
- None)
- self.aggregate_mock.set_metadata.assert_called_once_with(
- self.fake_ag, parsed_args.property)
+ self.sdk_client.create_aggregate.assert_called_once_with(
+ name=parsed_args.name)
+ self.sdk_client.set_aggregate_metadata.assert_called_once_with(
+ self.fake_ag.id, parsed_args.property)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
class TestAggregateDelete(TestAggregate):
@@ -146,7 +158,7 @@ class TestAggregateDelete(TestAggregate):
def setUp(self):
super(TestAggregateDelete, self).setUp()
- self.aggregate_mock.get = (
+ self.sdk_client.find_aggregate = (
compute_fakes.FakeAggregate.get_aggregates(self.fake_ags))
self.cmd = aggregate.DeleteAggregate(self.app, None)
@@ -158,10 +170,11 @@ class TestAggregateDelete(TestAggregate):
('aggregate', [self.fake_ags[0].id]),
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
- result = self.cmd.take_action(parsed_args)
- self.aggregate_mock.get.assert_called_once_with(self.fake_ags[0].id)
- self.aggregate_mock.delete.assert_called_once_with(self.fake_ags[0].id)
- self.assertIsNone(result)
+ self.cmd.take_action(parsed_args)
+ self.sdk_client.find_aggregate.assert_called_once_with(
+ self.fake_ags[0].id, ignore_missing=False)
+ self.sdk_client.delete_aggregate.assert_called_once_with(
+ self.fake_ags[0].id, ignore_missing=False)
def test_delete_multiple_aggregates(self):
arglist = []
@@ -172,13 +185,13 @@ class TestAggregateDelete(TestAggregate):
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
- result = self.cmd.take_action(parsed_args)
+ self.cmd.take_action(parsed_args)
calls = []
for a in self.fake_ags:
- calls.append(call(a.id))
- self.aggregate_mock.delete.assert_has_calls(calls)
- self.assertIsNone(result)
+ calls.append(call(a.id, ignore_missing=False))
+ self.sdk_client.find_aggregate.assert_has_calls(calls)
+ self.sdk_client.delete_aggregate.assert_has_calls(calls)
def test_delete_multiple_agggregates_with_exception(self):
arglist = [
@@ -191,23 +204,21 @@ class TestAggregateDelete(TestAggregate):
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
- find_mock_result = [self.fake_ags[0], exceptions.CommandError]
- with mock.patch.object(utils, 'find_resource',
- side_effect=find_mock_result) as find_mock:
- try:
- self.cmd.take_action(parsed_args)
- self.fail('CommandError should be raised.')
- except exceptions.CommandError as e:
- self.assertEqual('1 of 2 aggregates failed to delete.',
- str(e))
-
- find_mock.assert_any_call(self.aggregate_mock, self.fake_ags[0].id)
- find_mock.assert_any_call(self.aggregate_mock, 'unexist_aggregate')
+ self.sdk_client.find_aggregate.side_effect = [
+ self.fake_ags[0], sdk_exceptions.NotFoundException]
+ try:
+ self.cmd.take_action(parsed_args)
+ self.fail('CommandError should be raised.')
+ except exceptions.CommandError as e:
+ self.assertEqual('1 of 2 aggregates failed to delete.',
+ str(e))
- self.assertEqual(2, find_mock.call_count)
- self.aggregate_mock.delete.assert_called_once_with(
- self.fake_ags[0].id
- )
+ calls = []
+ for a in arglist:
+ calls.append(call(a, ignore_missing=False))
+ self.sdk_client.find_aggregate.assert_has_calls(calls)
+ self.sdk_client.delete_aggregate.assert_called_with(
+ self.fake_ags[0].id, ignore_missing=False)
class TestAggregateList(TestAggregate):
@@ -245,7 +256,7 @@ class TestAggregateList(TestAggregate):
def setUp(self):
super(TestAggregateList, self).setUp()
- self.aggregate_mock.list.return_value = [self.fake_ag]
+ self.sdk_client.aggregates.return_value = [self.fake_ag]
self.cmd = aggregate.ListAggregate(self.app, None)
def test_aggregate_list(self):
@@ -254,7 +265,7 @@ class TestAggregateList(TestAggregate):
columns, data = self.cmd.take_action(parsed_args)
self.assertEqual(self.list_columns, columns)
- self.assertItemEqual(self.list_data, tuple(data))
+ self.assertItemsEqual(self.list_data, tuple(data))
def test_aggregate_list_with_long(self):
arglist = [
@@ -267,7 +278,7 @@ class TestAggregateList(TestAggregate):
columns, data = self.cmd.take_action(parsed_args)
self.assertEqual(self.list_columns_long, columns)
- self.assertListItemEqual(self.list_data_long, tuple(data))
+ self.assertItemsEqual(self.list_data_long, tuple(data))
class TestAggregateRemoveHost(TestAggregate):
@@ -275,11 +286,11 @@ class TestAggregateRemoveHost(TestAggregate):
def setUp(self):
super(TestAggregateRemoveHost, self).setUp()
- self.aggregate_mock.get.return_value = self.fake_ag
- self.aggregate_mock.remove_host.return_value = self.fake_ag
+ self.sdk_client.find_aggregate.return_value = self.fake_ag
+ self.sdk_client.remove_host_from_aggregate.return_value = self.fake_ag
self.cmd = aggregate.RemoveAggregateHost(self.app, None)
- def test_aggregate_add_host(self):
+ def test_aggregate_remove_host(self):
arglist = [
'ag1',
'host1',
@@ -290,11 +301,12 @@ class TestAggregateRemoveHost(TestAggregate):
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
columns, data = self.cmd.take_action(parsed_args)
- self.aggregate_mock.get.assert_called_once_with(parsed_args.aggregate)
- self.aggregate_mock.remove_host.assert_called_once_with(
- self.fake_ag, parsed_args.host)
+ self.sdk_client.find_aggregate.assert_called_once_with(
+ parsed_args.aggregate, ignore_missing=False)
+ self.sdk_client.remove_host_from_aggregate.assert_called_once_with(
+ self.fake_ag.id, parsed_args.host)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
class TestAggregateSet(TestAggregate):
@@ -302,7 +314,7 @@ class TestAggregateSet(TestAggregate):
def setUp(self):
super(TestAggregateSet, self).setUp()
- self.aggregate_mock.get.return_value = self.fake_ag
+ self.sdk_client.find_aggregate.return_value = self.fake_ag
self.cmd = aggregate.SetAggregate(self.app, None)
def test_aggregate_set_no_option(self):
@@ -315,9 +327,10 @@ class TestAggregateSet(TestAggregate):
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
result = self.cmd.take_action(parsed_args)
- self.aggregate_mock.get.assert_called_once_with(parsed_args.aggregate)
- self.assertNotCalled(self.aggregate_mock.update)
- self.assertNotCalled(self.aggregate_mock.set_metadata)
+ self.sdk_client.find_aggregate.assert_called_once_with(
+ parsed_args.aggregate, ignore_missing=False)
+ self.assertNotCalled(self.sdk_client.update_aggregate)
+ self.assertNotCalled(self.sdk_client.set_aggregate_metadata)
self.assertIsNone(result)
def test_aggregate_set_with_name(self):
@@ -332,10 +345,11 @@ class TestAggregateSet(TestAggregate):
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
result = self.cmd.take_action(parsed_args)
- self.aggregate_mock.get.assert_called_once_with(parsed_args.aggregate)
- self.aggregate_mock.update.assert_called_once_with(
- self.fake_ag, {'name': parsed_args.name})
- self.assertNotCalled(self.aggregate_mock.set_metadata)
+ self.sdk_client.find_aggregate.assert_called_once_with(
+ parsed_args.aggregate, ignore_missing=False)
+ self.sdk_client.update_aggregate.assert_called_once_with(
+ self.fake_ag.id, name=parsed_args.name)
+ self.assertNotCalled(self.sdk_client.set_aggregate_metadata)
self.assertIsNone(result)
def test_aggregate_set_with_zone(self):
@@ -350,10 +364,11 @@ class TestAggregateSet(TestAggregate):
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
result = self.cmd.take_action(parsed_args)
- self.aggregate_mock.get.assert_called_once_with(parsed_args.aggregate)
- self.aggregate_mock.update.assert_called_once_with(
- self.fake_ag, {'availability_zone': parsed_args.zone})
- self.assertNotCalled(self.aggregate_mock.set_metadata)
+ self.sdk_client.find_aggregate.assert_called_once_with(
+ parsed_args.aggregate, ignore_missing=False)
+ self.sdk_client.update_aggregate.assert_called_once_with(
+ self.fake_ag.id, availability_zone=parsed_args.zone)
+ self.assertNotCalled(self.sdk_client.set_aggregate_metadata)
self.assertIsNone(result)
def test_aggregate_set_with_property(self):
@@ -369,10 +384,11 @@ class TestAggregateSet(TestAggregate):
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
result = self.cmd.take_action(parsed_args)
- self.aggregate_mock.get.assert_called_once_with(parsed_args.aggregate)
- self.assertNotCalled(self.aggregate_mock.update)
- self.aggregate_mock.set_metadata.assert_called_once_with(
- self.fake_ag, parsed_args.property)
+ self.sdk_client.find_aggregate.assert_called_once_with(
+ parsed_args.aggregate, ignore_missing=False)
+ self.assertNotCalled(self.sdk_client.update_aggregate)
+ self.sdk_client.set_aggregate_metadata.assert_called_once_with(
+ self.fake_ag.id, parsed_args.property)
self.assertIsNone(result)
def test_aggregate_set_with_no_property_and_property(self):
@@ -388,10 +404,11 @@ class TestAggregateSet(TestAggregate):
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
result = self.cmd.take_action(parsed_args)
- self.aggregate_mock.get.assert_called_once_with(parsed_args.aggregate)
- self.assertNotCalled(self.aggregate_mock.update)
- self.aggregate_mock.set_metadata.assert_called_once_with(
- self.fake_ag, {'key1': None, 'key2': 'value2'})
+ self.sdk_client.find_aggregate.assert_called_once_with(
+ parsed_args.aggregate, ignore_missing=False)
+ self.assertNotCalled(self.sdk_client.update_aggregate)
+ self.sdk_client.set_aggregate_metadata.assert_called_once_with(
+ self.fake_ag.id, {'key1': None, 'key2': 'value2'})
self.assertIsNone(result)
def test_aggregate_set_with_no_property(self):
@@ -405,10 +422,11 @@ class TestAggregateSet(TestAggregate):
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
result = self.cmd.take_action(parsed_args)
- self.aggregate_mock.get.assert_called_once_with(parsed_args.aggregate)
- self.assertNotCalled(self.aggregate_mock.update)
- self.aggregate_mock.set_metadata.assert_called_once_with(
- self.fake_ag, {'key1': None})
+ self.sdk_client.find_aggregate.assert_called_once_with(
+ parsed_args.aggregate, ignore_missing=False)
+ self.assertNotCalled(self.sdk_client.update_aggregate)
+ self.sdk_client.set_aggregate_metadata.assert_called_once_with(
+ self.fake_ag.id, {'key1': None})
self.assertIsNone(result)
def test_aggregate_set_with_zone_and_no_property(self):
@@ -424,11 +442,12 @@ class TestAggregateSet(TestAggregate):
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
result = self.cmd.take_action(parsed_args)
- self.aggregate_mock.get.assert_called_once_with(parsed_args.aggregate)
- self.aggregate_mock.update.assert_called_once_with(
- self.fake_ag, {'availability_zone': parsed_args.zone})
- self.aggregate_mock.set_metadata.assert_called_once_with(
- self.fake_ag, {'key1': None})
+ self.sdk_client.find_aggregate.assert_called_once_with(
+ parsed_args.aggregate, ignore_missing=False)
+ self.sdk_client.update_aggregate.assert_called_once_with(
+ self.fake_ag.id, availability_zone=parsed_args.zone)
+ self.sdk_client.set_aggregate_metadata.assert_called_once_with(
+ self.fake_ag.id, {'key1': None})
self.assertIsNone(result)
@@ -457,7 +476,7 @@ class TestAggregateShow(TestAggregate):
def setUp(self):
super(TestAggregateShow, self).setUp()
- self.aggregate_mock.get.return_value = self.fake_ag
+ self.sdk_client.find_aggregate.return_value = self.fake_ag
self.cmd = aggregate.ShowAggregate(self.app, None)
def test_aggregate_show(self):
@@ -469,10 +488,11 @@ class TestAggregateShow(TestAggregate):
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
columns, data = self.cmd.take_action(parsed_args)
- self.aggregate_mock.get.assert_called_once_with(parsed_args.aggregate)
+ self.sdk_client.find_aggregate.assert_called_once_with(
+ parsed_args.aggregate, ignore_missing=False)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, tuple(data))
+ self.assertItemsEqual(self.data, tuple(data))
class TestAggregateUnset(TestAggregate):
@@ -480,7 +500,7 @@ class TestAggregateUnset(TestAggregate):
def setUp(self):
super(TestAggregateUnset, self).setUp()
- self.aggregate_mock.get.return_value = self.fake_ag
+ self.sdk_client.find_aggregate.return_value = self.fake_ag
self.cmd = aggregate.UnsetAggregate(self.app, None)
def test_aggregate_unset(self):
@@ -495,7 +515,7 @@ class TestAggregateUnset(TestAggregate):
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
result = self.cmd.take_action(parsed_args)
- self.aggregate_mock.set_metadata.assert_called_once_with(
+ self.sdk_client.set_aggregate_metadata.assert_called_once_with(
self.fake_ag, {'unset_key': None})
self.assertIsNone(result)
@@ -512,7 +532,7 @@ class TestAggregateUnset(TestAggregate):
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
result = self.cmd.take_action(parsed_args)
- self.aggregate_mock.set_metadata.assert_called_once_with(
+ self.sdk_client.set_aggregate_metadata.assert_called_once_with(
self.fake_ag, {'unset_key1': None, 'unset_key2': None})
self.assertIsNone(result)
@@ -526,5 +546,72 @@ class TestAggregateUnset(TestAggregate):
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
result = self.cmd.take_action(parsed_args)
- self.assertNotCalled(self.aggregate_mock.set_metadata)
+ self.assertNotCalled(self.sdk_client.set_aggregate_metadata)
self.assertIsNone(result)
+
+
+class TestAggregateCacheImage(TestAggregate):
+
+ images = image_fakes.FakeImage.create_images(count=2)
+
+ def setUp(self):
+ super(TestAggregateCacheImage, self).setUp()
+
+ self.sdk_client.find_aggregate.return_value = self.fake_ag
+ self.find_image_mock = mock.Mock(side_effect=self.images)
+ self.app.client_manager.sdk_connection.image.find_image = \
+ self.find_image_mock
+
+ self.cmd = aggregate.CacheImageForAggregate(self.app, None)
+
+ @mock.patch.object(sdk_utils, 'supports_microversion', return_value=False)
+ def test_aggregate_not_supported(self, sm_mock):
+ arglist = [
+ 'ag1',
+ 'im1'
+ ]
+ verifylist = [
+ ('aggregate', 'ag1'),
+ ('image', ['im1']),
+ ]
+ parsed_args = self.check_parser(self.cmd, arglist, verifylist)
+ self.assertRaises(
+ exceptions.CommandError,
+ self.cmd.take_action,
+ parsed_args
+ )
+
+ @mock.patch.object(sdk_utils, 'supports_microversion', return_value=True)
+ def test_aggregate_add_single_image(self, sm_mock):
+ arglist = [
+ 'ag1',
+ 'im1'
+ ]
+ verifylist = [
+ ('aggregate', 'ag1'),
+ ('image', ['im1']),
+ ]
+ parsed_args = self.check_parser(self.cmd, arglist, verifylist)
+ self.cmd.take_action(parsed_args)
+ self.sdk_client.find_aggregate.assert_called_once_with(
+ parsed_args.aggregate, ignore_missing=False)
+ self.sdk_client.aggregate_precache_images.assert_called_once_with(
+ self.fake_ag.id, [self.images[0].id])
+
+ @mock.patch.object(sdk_utils, 'supports_microversion', return_value=True)
+ def test_aggregate_add_multiple_images(self, sm_mock):
+ arglist = [
+ 'ag1',
+ 'im1',
+ 'im2',
+ ]
+ verifylist = [
+ ('aggregate', 'ag1'),
+ ('image', ['im1', 'im2']),
+ ]
+ parsed_args = self.check_parser(self.cmd, arglist, verifylist)
+ self.cmd.take_action(parsed_args)
+ self.sdk_client.find_aggregate.assert_called_once_with(
+ parsed_args.aggregate, ignore_missing=False)
+ self.sdk_client.aggregate_precache_images.assert_called_once_with(
+ self.fake_ag.id, [self.images[0].id, self.images[1].id])
diff --git a/openstackclient/tests/unit/compute/v2/test_flavor.py b/openstackclient/tests/unit/compute/v2/test_flavor.py
index 2828d74e..4c4882ec 100644
--- a/openstackclient/tests/unit/compute/v2/test_flavor.py
+++ b/openstackclient/tests/unit/compute/v2/test_flavor.py
@@ -12,11 +12,11 @@
# License for the specific language governing permissions and limitations
# under the License.
#
-
from unittest import mock
-from unittest.mock import call
-import novaclient
+from openstack.compute.v2 import flavor as _flavor
+from openstack import exceptions as sdk_exceptions
+from openstack import utils as sdk_utils
from osc_lib.cli import format_columns
from osc_lib import exceptions
@@ -31,13 +31,19 @@ class TestFlavor(compute_fakes.TestComputev2):
def setUp(self):
super(TestFlavor, self).setUp()
- # Get a shortcut to the FlavorManager Mock
- self.flavors_mock = self.app.client_manager.compute.flavors
- self.flavors_mock.reset_mock()
-
- # Get a shortcut to the FlavorAccessManager Mock
- self.flavor_access_mock = self.app.client_manager.compute.flavor_access
- self.flavor_access_mock.reset_mock()
+ # SDK mock
+ self.app.client_manager.sdk_connection = mock.Mock()
+ self.app.client_manager.sdk_connection.compute = mock.Mock()
+ self.sdk_client = self.app.client_manager.sdk_connection.compute
+ self.sdk_client.flavors = mock.Mock()
+ self.sdk_client.find_flavor = mock.Mock()
+ self.sdk_client.delete_flavor = mock.Mock()
+ self.sdk_client.update_flavor = mock.Mock()
+ self.sdk_client.flavor_add_tenant_access = mock.Mock()
+ self.sdk_client.flavor_remove_tenant_access = mock.Mock()
+ self.sdk_client.create_flavor_extra_specs = mock.Mock()
+ self.sdk_client.update_flavor_extra_specs_property = mock.Mock()
+ self.sdk_client.delete_flavor_extra_specs_property = mock.Mock()
self.projects_mock = self.app.client_manager.identity.projects
self.projects_mock.reset_mock()
@@ -48,6 +54,7 @@ class TestFlavorCreate(TestFlavor):
flavor = compute_fakes.FakeFlavor.create_one_flavor(
attrs={'links': 'flavor-links'})
project = identity_fakes.FakeProject.create_one_project()
+
columns = (
'OS-FLV-DISABLED:disabled',
'OS-FLV-EXT-DATA:ephemeral',
@@ -60,17 +67,32 @@ class TestFlavorCreate(TestFlavor):
'ram',
'rxtx_factor',
'swap',
- 'vcpus',
+ 'vcpus'
)
+
data = (
- flavor.disabled,
+ flavor.is_disabled,
flavor.ephemeral,
flavor.description,
flavor.disk,
flavor.id,
flavor.name,
flavor.is_public,
- format_columns.DictColumn(flavor.properties),
+ format_columns.DictColumn(flavor.extra_specs),
+ flavor.ram,
+ flavor.rxtx_factor,
+ flavor.swap,
+ flavor.vcpus,
+ )
+ data_private = (
+ flavor.is_disabled,
+ flavor.ephemeral,
+ flavor.description,
+ flavor.disk,
+ flavor.id,
+ flavor.name,
+ False,
+ format_columns.DictColumn(flavor.extra_specs),
flavor.ram,
flavor.rxtx_factor,
flavor.swap,
@@ -82,7 +104,7 @@ class TestFlavorCreate(TestFlavor):
# Return a project
self.projects_mock.get.return_value = self.project
- self.flavors_mock.create.return_value = self.flavor
+ self.sdk_client.create_flavor.return_value = self.flavor
self.cmd = flavor.CreateFlavor(self.app, None)
def test_flavor_create_default_options(self):
@@ -95,23 +117,23 @@ class TestFlavorCreate(TestFlavor):
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
- default_args = (
- self.flavor.name,
- 256,
- 1,
- 0,
- 'auto',
- 0,
- 0,
- 1.0,
- True,
- None,
- )
+ default_args = {
+ 'name': self.flavor.name,
+ 'ram': 256,
+ 'vcpus': 1,
+ 'disk': 0,
+ 'id': None,
+ 'ephemeral': 0,
+ 'swap': 0,
+ 'rxtx_factor': 1.0,
+ 'is_public': True,
+ }
+
columns, data = self.cmd.take_action(parsed_args)
- self.flavors_mock.create.assert_called_once_with(*default_args)
+ self.sdk_client.create_flavor.assert_called_once_with(**default_args)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_flavor_create_all_options(self):
@@ -143,29 +165,44 @@ class TestFlavorCreate(TestFlavor):
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
- args = (
- self.flavor.name,
- self.flavor.ram,
- self.flavor.vcpus,
- self.flavor.disk,
- self.flavor.id,
- self.flavor.ephemeral,
- self.flavor.swap,
- self.flavor.rxtx_factor,
- self.flavor.is_public,
- self.flavor.description,
- )
- self.app.client_manager.compute.api_version = 2.55
- with mock.patch.object(novaclient.api_versions,
- 'APIVersion',
- return_value=2.55):
+ args = {
+ 'name': self.flavor.name,
+ 'ram': self.flavor.ram,
+ 'vcpus': self.flavor.vcpus,
+ 'disk': self.flavor.disk,
+ 'id': self.flavor.id,
+ 'ephemeral': self.flavor.ephemeral,
+ 'swap': self.flavor.swap,
+ 'rxtx_factor': self.flavor.rxtx_factor,
+ 'is_public': self.flavor.is_public,
+ 'description': self.flavor.description
+ }
+
+ props = {'property': 'value'}
+
+ # SDK updates the flavor object instance. In order to make the
+ # verification clear and preciese let's create new flavor and change
+ # expected props this way
+ create_flavor = _flavor.Flavor(**self.flavor)
+ expected_flavor = _flavor.Flavor(**self.flavor)
+ expected_flavor.extra_specs = props
+ # convert expected data tuple to list to be able to modify it
+ cmp_data = list(self.data)
+ cmp_data[7] = format_columns.DictColumn(props)
+ self.sdk_client.create_flavor.return_value = create_flavor
+ self.sdk_client.create_flavor_extra_specs.return_value = \
+ expected_flavor
+
+ with mock.patch.object(sdk_utils, 'supports_microversion',
+ return_value=True):
columns, data = self.cmd.take_action(parsed_args)
- self.flavors_mock.create.assert_called_once_with(*args)
- self.flavor.set_keys.assert_called_once_with({'property': 'value'})
- self.flavor.get_keys.assert_called_once_with()
+ self.sdk_client.create_flavor.assert_called_once_with(**args)
+ self.sdk_client.create_flavor_extra_specs.assert_called_once_with(
+ create_flavor, props)
+ self.sdk_client.get_flavor_access.assert_not_called()
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(tuple(cmp_data), data)
def test_flavor_create_other_options(self):
@@ -200,33 +237,47 @@ class TestFlavorCreate(TestFlavor):
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
- args = (
- self.flavor.name,
- self.flavor.ram,
- self.flavor.vcpus,
- self.flavor.disk,
- 'auto',
- self.flavor.ephemeral,
- self.flavor.swap,
- self.flavor.rxtx_factor,
- self.flavor.is_public,
- self.flavor.description,
- )
- self.app.client_manager.compute.api_version = 2.55
- with mock.patch.object(novaclient.api_versions,
- 'APIVersion',
- return_value=2.55):
+ args = {
+ 'name': self.flavor.name,
+ 'ram': self.flavor.ram,
+ 'vcpus': self.flavor.vcpus,
+ 'disk': self.flavor.disk,
+ 'id': 'auto',
+ 'ephemeral': self.flavor.ephemeral,
+ 'swap': self.flavor.swap,
+ 'rxtx_factor': self.flavor.rxtx_factor,
+ 'is_public': False,
+ 'description': self.flavor.description
+ }
+
+ props = {'key1': 'value1', 'key2': 'value2'}
+
+ # SDK updates the flavor object instance. In order to make the
+ # verification clear and preciese let's create new flavor and change
+ # expected props this way
+ create_flavor = _flavor.Flavor(**self.flavor)
+ expected_flavor = _flavor.Flavor(**self.flavor)
+ expected_flavor.extra_specs = props
+ expected_flavor.is_public = False
+ # convert expected data tuple to list to be able to modify it
+ cmp_data = list(self.data_private)
+ cmp_data[7] = format_columns.DictColumn(props)
+ self.sdk_client.create_flavor.return_value = create_flavor
+ self.sdk_client.create_flavor_extra_specs.return_value = \
+ expected_flavor
+
+ with mock.patch.object(sdk_utils, 'supports_microversion',
+ return_value=True):
columns, data = self.cmd.take_action(parsed_args)
- self.flavors_mock.create.assert_called_once_with(*args)
- self.flavor_access_mock.add_tenant_access.assert_called_with(
+ self.sdk_client.create_flavor.assert_called_once_with(**args)
+ self.sdk_client.flavor_add_tenant_access.assert_called_with(
self.flavor.id,
self.project.id,
)
- self.flavor.set_keys.assert_called_with(
- {'key1': 'value1', 'key2': 'value2'})
- self.flavor.get_keys.assert_called_with()
+ self.sdk_client.create_flavor_extra_specs.assert_called_with(
+ create_flavor, props)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(cmp_data, data)
def test_public_flavor_create_with_project(self):
arglist = [
@@ -278,29 +329,28 @@ class TestFlavorCreate(TestFlavor):
('name', self.flavor.name),
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
- self.app.client_manager.compute.api_version = 2.55
- with mock.patch.object(novaclient.api_versions,
- 'APIVersion',
- return_value=2.55):
+ with mock.patch.object(sdk_utils, 'supports_microversion',
+ return_value=True):
+
columns, data = self.cmd.take_action(parsed_args)
- args = (
- self.flavor.name,
- self.flavor.ram,
- self.flavor.vcpus,
- self.flavor.disk,
- self.flavor.id,
- self.flavor.ephemeral,
- self.flavor.swap,
- self.flavor.rxtx_factor,
- False,
- 'fake description',
- )
+ args = {
+ 'name': self.flavor.name,
+ 'ram': self.flavor.ram,
+ 'vcpus': self.flavor.vcpus,
+ 'disk': self.flavor.disk,
+ 'id': self.flavor.id,
+ 'ephemeral': self.flavor.ephemeral,
+ 'swap': self.flavor.swap,
+ 'rxtx_factor': self.flavor.rxtx_factor,
+ 'is_public': self.flavor.is_public,
+ 'description': 'fake description'
+ }
- self.flavors_mock.create.assert_called_once_with(*args)
+ self.sdk_client.create_flavor.assert_called_once_with(**args)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data_private, data)
def test_flavor_create_with_description_api_older(self):
arglist = [
@@ -318,10 +368,8 @@ class TestFlavorCreate(TestFlavor):
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
- self.app.client_manager.compute.api_version = 2.54
- with mock.patch.object(novaclient.api_versions,
- 'APIVersion',
- return_value=2.55):
+ with mock.patch.object(sdk_utils, 'supports_microversion',
+ return_value=False):
self.assertRaises(exceptions.CommandError, self.cmd.take_action,
parsed_args)
@@ -333,9 +381,7 @@ class TestFlavorDelete(TestFlavor):
def setUp(self):
super(TestFlavorDelete, self).setUp()
- self.flavors_mock.get = (
- compute_fakes.FakeFlavor.get_flavors(self.flavors))
- self.flavors_mock.delete.return_value = None
+ self.sdk_client.delete_flavor.return_value = None
self.cmd = flavor.DeleteFlavor(self.app, None)
@@ -348,9 +394,13 @@ class TestFlavorDelete(TestFlavor):
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
+ self.sdk_client.find_flavor.return_value = self.flavors[0]
+
result = self.cmd.take_action(parsed_args)
- self.flavors_mock.delete.assert_called_with(self.flavors[0].id)
+ self.sdk_client.find_flavor.assert_called_with(self.flavors[0].id,
+ ignore_missing=False)
+ self.sdk_client.delete_flavor.assert_called_with(self.flavors[0].id)
self.assertIsNone(result)
def test_delete_multiple_flavors(self):
@@ -362,12 +412,17 @@ class TestFlavorDelete(TestFlavor):
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
+
+ self.sdk_client.find_flavor.side_effect = self.flavors
+
result = self.cmd.take_action(parsed_args)
- calls = []
- for f in self.flavors:
- calls.append(call(f.id))
- self.flavors_mock.delete.assert_has_calls(calls)
+ find_calls = [
+ mock.call(i.id, ignore_missing=False) for i in self.flavors
+ ]
+ delete_calls = [mock.call(i.id) for i in self.flavors]
+ self.sdk_client.find_flavor.assert_has_calls(find_calls)
+ self.sdk_client.delete_flavor.assert_has_calls(delete_calls)
self.assertIsNone(result)
def test_multi_flavors_delete_with_exception(self):
@@ -380,11 +435,10 @@ class TestFlavorDelete(TestFlavor):
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
- find_mock_result = [self.flavors[0], exceptions.CommandError]
- self.flavors_mock.get = (
- mock.Mock(side_effect=find_mock_result)
- )
- self.flavors_mock.find.side_effect = exceptions.NotFound(None)
+ self.sdk_client.find_flavor.side_effect = [
+ self.flavors[0],
+ sdk_exceptions.ResourceNotFound
+ ]
try:
self.cmd.take_action(parsed_args)
@@ -392,15 +446,18 @@ class TestFlavorDelete(TestFlavor):
except exceptions.CommandError as e:
self.assertEqual('1 of 2 flavors failed to delete.', str(e))
- self.flavors_mock.get.assert_any_call(self.flavors[0].id)
- self.flavors_mock.get.assert_any_call('unexist_flavor')
- self.flavors_mock.delete.assert_called_once_with(self.flavors[0].id)
+ find_calls = [
+ mock.call(self.flavors[0].id, ignore_missing=False),
+ mock.call('unexist_flavor', ignore_missing=False),
+ ]
+ delete_calls = [mock.call(self.flavors[0].id)]
+ self.sdk_client.find_flavor.assert_has_calls(find_calls)
+ self.sdk_client.delete_flavor.assert_has_calls(delete_calls)
class TestFlavorList(TestFlavor):
- # Return value of self.flavors_mock.list().
- flavors = compute_fakes.FakeFlavor.create_flavors(count=1)
+ _flavor = compute_fakes.FakeFlavor.create_one_flavor()
columns = (
'ID',
@@ -418,24 +475,27 @@ class TestFlavorList(TestFlavor):
)
data = ((
- flavors[0].id,
- flavors[0].name,
- flavors[0].ram,
- flavors[0].disk,
- flavors[0].ephemeral,
- flavors[0].vcpus,
- flavors[0].is_public,
- ), )
+ _flavor.id,
+ _flavor.name,
+ _flavor.ram,
+ _flavor.disk,
+ _flavor.ephemeral,
+ _flavor.vcpus,
+ _flavor.is_public,
+ ),)
data_long = (data[0] + (
- flavors[0].swap,
- flavors[0].rxtx_factor,
- format_columns.DictColumn(flavors[0].properties)
+ _flavor.swap,
+ _flavor.rxtx_factor,
+ format_columns.DictColumn(_flavor.extra_specs)
), )
def setUp(self):
super(TestFlavorList, self).setUp()
- self.flavors_mock.list.return_value = self.flavors
+ self.api_mock = mock.Mock()
+ self.api_mock.side_effect = [[self._flavor], [], ]
+
+ self.sdk_client.flavors = self.api_mock
# Get the command object to test
self.cmd = flavor.ListFlavor(self.app, None)
@@ -458,16 +518,14 @@ class TestFlavorList(TestFlavor):
# Set expected values
kwargs = {
'is_public': True,
- 'limit': None,
- 'marker': None
}
- self.flavors_mock.list.assert_called_with(
+ self.sdk_client.flavors.assert_called_with(
**kwargs
)
self.assertEqual(self.columns, columns)
- self.assertEqual(tuple(self.data), tuple(data))
+ self.assertEqual(self.data, tuple(data))
def test_flavor_list_all_flavors(self):
arglist = [
@@ -487,16 +545,14 @@ class TestFlavorList(TestFlavor):
# Set expected values
kwargs = {
'is_public': None,
- 'limit': None,
- 'marker': None
}
- self.flavors_mock.list.assert_called_with(
+ self.sdk_client.flavors.assert_called_with(
**kwargs
)
self.assertEqual(self.columns, columns)
- self.assertEqual(tuple(self.data), tuple(data))
+ self.assertEqual(self.data, tuple(data))
def test_flavor_list_private_flavors(self):
arglist = [
@@ -516,16 +572,14 @@ class TestFlavorList(TestFlavor):
# Set expected values
kwargs = {
'is_public': False,
- 'limit': None,
- 'marker': None
}
- self.flavors_mock.list.assert_called_with(
+ self.sdk_client.flavors.assert_called_with(
**kwargs
)
self.assertEqual(self.columns, columns)
- self.assertEqual(tuple(self.data), tuple(data))
+ self.assertEqual(self.data, tuple(data))
def test_flavor_list_public_flavors(self):
arglist = [
@@ -545,16 +599,14 @@ class TestFlavorList(TestFlavor):
# Set expected values
kwargs = {
'is_public': True,
- 'limit': None,
- 'marker': None
}
- self.flavors_mock.list.assert_called_with(
+ self.sdk_client.flavors.assert_called_with(
**kwargs
)
self.assertEqual(self.columns, columns)
- self.assertEqual(tuple(self.data), tuple(data))
+ self.assertEqual(self.data, tuple(data))
def test_flavor_list_long(self):
arglist = [
@@ -574,21 +626,19 @@ class TestFlavorList(TestFlavor):
# Set expected values
kwargs = {
'is_public': True,
- 'limit': None,
- 'marker': None
}
- self.flavors_mock.list.assert_called_with(
+ self.sdk_client.flavors.assert_called_with(
**kwargs
)
self.assertEqual(self.columns_long, columns)
- self.assertListItemEqual(self.data_long, tuple(data))
+ self.assertItemsEqual(self.data_long, tuple(data))
class TestFlavorSet(TestFlavor):
- # Return value of self.flavors_mock.find().
+ # Return value of self.sdk_client.find_flavor().
flavor = compute_fakes.FakeFlavor.create_one_flavor(
attrs={'os-flavor-access:is_public': False})
project = identity_fakes.FakeProject.create_one_project()
@@ -596,8 +646,7 @@ class TestFlavorSet(TestFlavor):
def setUp(self):
super(TestFlavorSet, self).setUp()
- self.flavors_mock.find.return_value = self.flavor
- self.flavors_mock.get.side_effect = exceptions.NotFound(None)
+ self.sdk_client.find_flavor.return_value = self.flavor
# Return a project
self.projects_mock.get.return_value = self.project
self.cmd = flavor.SetFlavor(self.app, None)
@@ -614,9 +663,14 @@ class TestFlavorSet(TestFlavor):
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
result = self.cmd.take_action(parsed_args)
- self.flavors_mock.find.assert_called_with(name=parsed_args.flavor,
- is_public=None)
- self.flavor.set_keys.assert_called_with({'FOO': '"B A R"'})
+ self.sdk_client.find_flavor.assert_called_with(
+ parsed_args.flavor,
+ get_extra_specs=True,
+ ignore_missing=False
+ )
+ self.sdk_client.create_flavor_extra_specs.assert_called_with(
+ self.flavor.id,
+ {'FOO': '"B A R"'})
self.assertIsNone(result)
def test_flavor_set_no_property(self):
@@ -631,9 +685,13 @@ class TestFlavorSet(TestFlavor):
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
result = self.cmd.take_action(parsed_args)
- self.flavors_mock.find.assert_called_with(name=parsed_args.flavor,
- is_public=None)
- self.flavor.unset_keys.assert_called_with(['property'])
+ self.sdk_client.find_flavor.assert_called_with(
+ parsed_args.flavor,
+ get_extra_specs=True,
+ ignore_missing=False
+ )
+ self.sdk_client.delete_flavor_extra_specs_property.assert_called_with(
+ self.flavor.id, 'property')
self.assertIsNone(result)
def test_flavor_set_project(self):
@@ -649,13 +707,16 @@ class TestFlavorSet(TestFlavor):
result = self.cmd.take_action(parsed_args)
- self.flavors_mock.find.assert_called_with(name=parsed_args.flavor,
- is_public=None)
- self.flavor_access_mock.add_tenant_access.assert_called_with(
+ self.sdk_client.find_flavor.assert_called_with(
+ parsed_args.flavor,
+ get_extra_specs=True,
+ ignore_missing=False
+ )
+ self.sdk_client.flavor_add_tenant_access.assert_called_with(
self.flavor.id,
self.project.id,
)
- self.flavor.set_keys.assert_not_called()
+ self.sdk_client.create_flavor_extra_specs.assert_not_called()
self.assertIsNone(result)
def test_flavor_set_no_project(self):
@@ -681,8 +742,9 @@ class TestFlavorSet(TestFlavor):
self.cmd, arglist, verifylist)
def test_flavor_set_with_unexist_flavor(self):
- self.flavors_mock.get.side_effect = exceptions.NotFound(None)
- self.flavors_mock.find.side_effect = exceptions.NotFound(None)
+ self.sdk_client.find_flavor.side_effect = [
+ sdk_exceptions.ResourceNotFound()
+ ]
arglist = [
'--project', self.project.id,
@@ -708,9 +770,12 @@ class TestFlavorSet(TestFlavor):
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
result = self.cmd.take_action(parsed_args)
- self.flavors_mock.find.assert_called_with(name=parsed_args.flavor,
- is_public=None)
- self.flavor_access_mock.add_tenant_access.assert_not_called()
+ self.sdk_client.find_flavor.assert_called_with(
+ parsed_args.flavor,
+ get_extra_specs=True,
+ ignore_missing=False
+ )
+ self.sdk_client.flavor_add_tenant_access.assert_not_called()
self.assertIsNone(result)
def test_flavor_set_description_api_newer(self):
@@ -724,11 +789,11 @@ class TestFlavorSet(TestFlavor):
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
self.app.client_manager.compute.api_version = 2.55
- with mock.patch.object(novaclient.api_versions,
- 'APIVersion',
- return_value=2.55):
+ with mock.patch.object(sdk_utils,
+ 'supports_microversion',
+ return_value=True):
result = self.cmd.take_action(parsed_args)
- self.flavors_mock.update.assert_called_with(
+ self.sdk_client.update_flavor.assert_called_with(
flavor=self.flavor.id, description='description')
self.assertIsNone(result)
@@ -743,9 +808,9 @@ class TestFlavorSet(TestFlavor):
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
self.app.client_manager.compute.api_version = 2.54
- with mock.patch.object(novaclient.api_versions,
- 'APIVersion',
- return_value=2.55):
+ with mock.patch.object(sdk_utils,
+ 'supports_microversion',
+ return_value=False):
self.assertRaises(exceptions.CommandError, self.cmd.take_action,
parsed_args)
@@ -760,11 +825,12 @@ class TestFlavorSet(TestFlavor):
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
self.app.client_manager.compute.api_version = 2.55
- with mock.patch.object(novaclient.api_versions,
- 'APIVersion',
- return_value=2.55):
+
+ with mock.patch.object(sdk_utils,
+ 'supports_microversion',
+ return_value=True):
result = self.cmd.take_action(parsed_args)
- self.flavors_mock.update.assert_called_with(
+ self.sdk_client.update_flavor.assert_called_with(
flavor=self.flavor.id, description='description')
self.assertIsNone(result)
@@ -779,16 +845,17 @@ class TestFlavorSet(TestFlavor):
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
self.app.client_manager.compute.api_version = 2.54
- with mock.patch.object(novaclient.api_versions,
- 'APIVersion',
- return_value=2.55):
+
+ with mock.patch.object(sdk_utils,
+ 'supports_microversion',
+ return_value=False):
self.assertRaises(exceptions.CommandError, self.cmd.take_action,
parsed_args)
class TestFlavorShow(TestFlavor):
- # Return value of self.flavors_mock.find().
+ # Return value of self.sdk_client.find_flavor().
flavor_access = compute_fakes.FakeFlavorAccess.create_one_flavor_access()
flavor = compute_fakes.FakeFlavor.create_one_flavor()
@@ -805,11 +872,11 @@ class TestFlavorShow(TestFlavor):
'ram',
'rxtx_factor',
'swap',
- 'vcpus',
+ 'vcpus'
)
data = (
- flavor.disabled,
+ flavor.is_disabled,
flavor.ephemeral,
None,
flavor.description,
@@ -817,7 +884,7 @@ class TestFlavorShow(TestFlavor):
flavor.id,
flavor.name,
flavor.is_public,
- format_columns.DictColumn(flavor.get_keys()),
+ format_columns.DictColumn(flavor.extra_specs),
flavor.ram,
flavor.rxtx_factor,
flavor.swap,
@@ -828,9 +895,8 @@ class TestFlavorShow(TestFlavor):
super(TestFlavorShow, self).setUp()
# Return value of _find_resource()
- self.flavors_mock.find.return_value = self.flavor
- self.flavors_mock.get.side_effect = exceptions.NotFound(None)
- self.flavor_access_mock.list.return_value = [self.flavor_access]
+ self.sdk_client.find_flavor.return_value = self.flavor
+ self.sdk_client.get_flavor_access.return_value = [self.flavor_access]
self.cmd = flavor.ShowFlavor(self.app, None)
def test_show_no_options(self):
@@ -854,7 +920,7 @@ class TestFlavorShow(TestFlavor):
columns, data = self.cmd.take_action(parsed_args)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_private_flavor_show(self):
private_flavor = compute_fakes.FakeFlavor.create_one_flavor(
@@ -862,7 +928,7 @@ class TestFlavorShow(TestFlavor):
'os-flavor-access:is_public': False,
}
)
- self.flavors_mock.find.return_value = private_flavor
+ self.sdk_client.find_flavor.return_value = private_flavor
arglist = [
private_flavor.name,
@@ -872,7 +938,7 @@ class TestFlavorShow(TestFlavor):
]
data_with_project = (
- private_flavor.disabled,
+ private_flavor.is_disabled,
private_flavor.ephemeral,
[self.flavor_access.tenant_id],
private_flavor.description,
@@ -880,7 +946,7 @@ class TestFlavorShow(TestFlavor):
private_flavor.id,
private_flavor.name,
private_flavor.is_public,
- format_columns.DictColumn(private_flavor.get_keys()),
+ format_columns.DictColumn(private_flavor.extra_specs),
private_flavor.ram,
private_flavor.rxtx_factor,
private_flavor.swap,
@@ -891,15 +957,15 @@ class TestFlavorShow(TestFlavor):
columns, data = self.cmd.take_action(parsed_args)
- self.flavor_access_mock.list.assert_called_with(
+ self.sdk_client.get_flavor_access.assert_called_with(
flavor=private_flavor.id)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(data_with_project, data)
+ self.assertItemsEqual(data_with_project, data)
class TestFlavorUnset(TestFlavor):
- # Return value of self.flavors_mock.find().
+ # Return value of self.sdk_client.find_flavor().
flavor = compute_fakes.FakeFlavor.create_one_flavor(
attrs={'os-flavor-access:is_public': False})
project = identity_fakes.FakeProject.create_one_project()
@@ -907,12 +973,13 @@ class TestFlavorUnset(TestFlavor):
def setUp(self):
super(TestFlavorUnset, self).setUp()
- self.flavors_mock.find.return_value = self.flavor
- self.flavors_mock.get.side_effect = exceptions.NotFound(None)
+ self.sdk_client.find_flavor.return_value = self.flavor
# Return a project
self.projects_mock.get.return_value = self.project
self.cmd = flavor.UnsetFlavor(self.app, None)
+ self.mock_shortcut = self.sdk_client.delete_flavor_extra_specs_property
+
def test_flavor_unset_property(self):
arglist = [
'--property', 'property',
@@ -925,12 +992,49 @@ class TestFlavorUnset(TestFlavor):
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
result = self.cmd.take_action(parsed_args)
- self.flavors_mock.find.assert_called_with(name=parsed_args.flavor,
- is_public=None)
- self.flavor.unset_keys.assert_called_with(['property'])
- self.flavor_access_mock.remove_tenant_access.assert_not_called()
+ self.sdk_client.find_flavor.assert_called_with(
+ parsed_args.flavor,
+ get_extra_specs=True,
+ ignore_missing=False)
+ self.mock_shortcut.assert_called_with(
+ self.flavor.id, 'property')
+ self.sdk_client.flavor_remove_tenant_access.assert_not_called()
self.assertIsNone(result)
+ def test_flavor_unset_properties(self):
+ arglist = [
+ '--property', 'property1',
+ '--property', 'property2',
+ 'baremetal'
+ ]
+ verifylist = [
+ ('property', ['property1', 'property2']),
+ ('flavor', 'baremetal'),
+ ]
+ parsed_args = self.check_parser(self.cmd, arglist, verifylist)
+
+ self.cmd.take_action(parsed_args)
+ self.sdk_client.find_flavor.assert_called_with(
+ parsed_args.flavor,
+ get_extra_specs=True,
+ ignore_missing=False)
+ calls = [
+ mock.call(self.flavor.id, 'property1'),
+ mock.call(self.flavor.id, 'property2')
+ ]
+ self.mock_shortcut.assert_has_calls(
+ calls)
+
+ # A bit tricky way to ensure we do not unset other properties
+ calls.append(mock.call(self.flavor.id, 'property'))
+ self.assertRaises(
+ AssertionError,
+ self.mock_shortcut.assert_has_calls,
+ calls
+ )
+
+ self.sdk_client.flavor_remove_tenant_access.assert_not_called()
+
def test_flavor_unset_project(self):
arglist = [
'--project', self.project.id,
@@ -945,13 +1049,14 @@ class TestFlavorUnset(TestFlavor):
result = self.cmd.take_action(parsed_args)
self.assertIsNone(result)
- self.flavors_mock.find.assert_called_with(name=parsed_args.flavor,
- is_public=None)
- self.flavor_access_mock.remove_tenant_access.assert_called_with(
+ self.sdk_client.find_flavor.assert_called_with(
+ parsed_args.flavor, get_extra_specs=True,
+ ignore_missing=False)
+ self.sdk_client.flavor_remove_tenant_access.assert_called_with(
self.flavor.id,
self.project.id,
)
- self.flavor.unset_keys.assert_not_called()
+ self.sdk_client.delete_flavor_extra_specs_proerty.assert_not_called()
self.assertIsNone(result)
def test_flavor_unset_no_project(self):
@@ -977,8 +1082,9 @@ class TestFlavorUnset(TestFlavor):
self.cmd, arglist, verifylist)
def test_flavor_unset_with_unexist_flavor(self):
- self.flavors_mock.get.side_effect = exceptions.NotFound(None)
- self.flavors_mock.find.side_effect = exceptions.NotFound(None)
+ self.sdk_client.find_flavor.side_effect = [
+ sdk_exceptions.ResourceNotFound
+ ]
arglist = [
'--project', self.project.id,
@@ -1004,4 +1110,4 @@ class TestFlavorUnset(TestFlavor):
result = self.cmd.take_action(parsed_args)
self.assertIsNone(result)
- self.flavor_access_mock.remove_tenant_access.assert_not_called()
+ self.sdk_client.flavor_remove_tenant_access.assert_not_called()
diff --git a/openstackclient/tests/unit/compute/v2/test_server_backup.py b/openstackclient/tests/unit/compute/v2/test_server_backup.py
index 5cdc2080..753db9cd 100644
--- a/openstackclient/tests/unit/compute/v2/test_server_backup.py
+++ b/openstackclient/tests/unit/compute/v2/test_server_backup.py
@@ -139,7 +139,7 @@ class TestServerBackupCreate(TestServerBackup):
)
self.assertEqual(self.image_columns(images[0]), columns)
- self.assertItemEqual(self.image_data(images[0]), data)
+ self.assertItemsEqual(self.image_data(images[0]), data)
def test_server_backup_create_options(self):
servers = self.setup_servers_mock(count=1)
@@ -173,7 +173,7 @@ class TestServerBackupCreate(TestServerBackup):
)
self.assertEqual(self.image_columns(images[0]), columns)
- self.assertItemEqual(self.image_data(images[0]), data)
+ self.assertItemsEqual(self.image_data(images[0]), data)
@mock.patch.object(common_utils, 'wait_for_status', return_value=False)
def test_server_backup_wait_fail(self, mock_wait_for_status):
@@ -269,4 +269,4 @@ class TestServerBackupCreate(TestServerBackup):
)
self.assertEqual(self.image_columns(images[0]), columns)
- self.assertItemEqual(self.image_data(images[0]), data)
+ self.assertItemsEqual(self.image_data(images[0]), data)
diff --git a/openstackclient/tests/unit/compute/v2/test_server_image.py b/openstackclient/tests/unit/compute/v2/test_server_image.py
index 1cec5b68..06f6017c 100644
--- a/openstackclient/tests/unit/compute/v2/test_server_image.py
+++ b/openstackclient/tests/unit/compute/v2/test_server_image.py
@@ -133,7 +133,7 @@ class TestServerImageCreate(TestServerImage):
)
self.assertEqual(self.image_columns(images[0]), columns)
- self.assertItemEqual(self.image_data(images[0]), data)
+ self.assertItemsEqual(self.image_data(images[0]), data)
def test_server_image_create_options(self):
servers = self.setup_servers_mock(count=1)
@@ -161,7 +161,7 @@ class TestServerImageCreate(TestServerImage):
)
self.assertEqual(self.image_columns(images[0]), columns)
- self.assertItemEqual(self.image_data(images[0]), data)
+ self.assertItemsEqual(self.image_data(images[0]), data)
@mock.patch.object(common_utils, 'wait_for_status', return_value=False)
def test_server_create_image_wait_fail(self, mock_wait_for_status):
@@ -229,4 +229,4 @@ class TestServerImageCreate(TestServerImage):
)
self.assertEqual(self.image_columns(images[0]), columns)
- self.assertItemEqual(self.image_data(images[0]), data)
+ self.assertItemsEqual(self.image_data(images[0]), data)
diff --git a/openstackclient/tests/unit/identity/v2_0/test_catalog.py b/openstackclient/tests/unit/identity/v2_0/test_catalog.py
index 17355074..e2c56ba1 100644
--- a/openstackclient/tests/unit/identity/v2_0/test_catalog.py
+++ b/openstackclient/tests/unit/identity/v2_0/test_catalog.py
@@ -71,9 +71,10 @@ class TestCatalogList(TestCatalog):
datalist = ((
'supernova',
'compute',
- catalog.EndpointsColumn(self.service_catalog['endpoints']),
+ catalog.EndpointsColumn(
+ auth_ref.service_catalog.catalog[0]['endpoints']),
), )
- self.assertListItemEqual(datalist, tuple(data))
+ self.assertItemsEqual(datalist, tuple(data))
def test_catalog_list_with_endpoint_url(self):
attr = {
@@ -113,9 +114,10 @@ class TestCatalogList(TestCatalog):
datalist = ((
'supernova',
'compute',
- catalog.EndpointsColumn(service_catalog['endpoints']),
+ catalog.EndpointsColumn(
+ auth_ref.service_catalog.catalog[0]['endpoints']),
), )
- self.assertListItemEqual(datalist, tuple(data))
+ self.assertItemsEqual(datalist, tuple(data))
class TestCatalogShow(TestCatalog):
@@ -150,16 +152,17 @@ class TestCatalogShow(TestCatalog):
collist = ('endpoints', 'id', 'name', 'type')
self.assertEqual(collist, columns)
datalist = (
- catalog.EndpointsColumn(self.service_catalog['endpoints']),
+ catalog.EndpointsColumn(
+ auth_ref.service_catalog.catalog[0]['endpoints']),
self.service_catalog.id,
'supernova',
'compute',
)
- self.assertItemEqual(datalist, data)
+ self.assertItemsEqual(datalist, data)
class TestFormatColumns(TestCatalog):
- def test_endpoints_column_human_readabale(self):
+ def test_endpoints_column_human_readable(self):
col = catalog.EndpointsColumn(self.service_catalog['endpoints'])
self.assertEqual(
'one\n publicURL: https://public.one.example.com\n '
diff --git a/openstackclient/tests/unit/identity/v2_0/test_project.py b/openstackclient/tests/unit/identity/v2_0/test_project.py
index cd8c825d..766d5dab 100644
--- a/openstackclient/tests/unit/identity/v2_0/test_project.py
+++ b/openstackclient/tests/unit/identity/v2_0/test_project.py
@@ -643,7 +643,7 @@ class TestProjectShow(TestProject):
self.fake_proj_show.name,
format_columns.DictColumn({}),
)
- self.assertItemEqual(datalist, data)
+ self.assertItemsEqual(datalist, data)
class TestProjectUnset(TestProject):
diff --git a/openstackclient/tests/unit/identity/v2_0/test_user.py b/openstackclient/tests/unit/identity/v2_0/test_user.py
index 4308b05d..dd300478 100644
--- a/openstackclient/tests/unit/identity/v2_0/test_user.py
+++ b/openstackclient/tests/unit/identity/v2_0/test_user.py
@@ -482,7 +482,7 @@ class TestUserList(TestUser):
self.users_mock.list.assert_called_with(tenant_id=None)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.datalist, tuple(data))
+ self.assertItemsEqual(self.datalist, tuple(data))
def test_user_list_project(self):
arglist = [
@@ -502,7 +502,7 @@ class TestUserList(TestUser):
self.users_mock.list.assert_called_with(tenant_id=project_id)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.datalist, tuple(data))
+ self.assertItemsEqual(self.datalist, tuple(data))
def test_user_list_long(self):
arglist = [
@@ -531,7 +531,7 @@ class TestUserList(TestUser):
self.fake_user_l.email,
True,
), )
- self.assertListItemEqual(datalist, tuple(data))
+ self.assertItemsEqual(datalist, tuple(data))
class TestUserSet(TestUser):
@@ -819,4 +819,4 @@ class TestUserShow(TestUser):
self.fake_user.name,
self.fake_project.id,
)
- self.assertItemEqual(datalist, data)
+ self.assertItemsEqual(datalist, data)
diff --git a/openstackclient/tests/unit/identity/v3/test_catalog.py b/openstackclient/tests/unit/identity/v3/test_catalog.py
index 3630ccb6..97ce48f6 100644
--- a/openstackclient/tests/unit/identity/v3/test_catalog.py
+++ b/openstackclient/tests/unit/identity/v3/test_catalog.py
@@ -91,9 +91,10 @@ class TestCatalogList(TestCatalog):
datalist = ((
'supernova',
'compute',
- catalog.EndpointsColumn(self.fake_service['endpoints']),
+ catalog.EndpointsColumn(
+ auth_ref.service_catalog.catalog[0]['endpoints']),
), )
- self.assertListItemEqual(datalist, tuple(data))
+ self.assertItemsEqual(datalist, tuple(data))
class TestCatalogShow(TestCatalog):
@@ -128,12 +129,13 @@ class TestCatalogShow(TestCatalog):
collist = ('endpoints', 'id', 'name', 'type')
self.assertEqual(collist, columns)
datalist = (
- catalog.EndpointsColumn(self.fake_service['endpoints']),
+ catalog.EndpointsColumn(
+ auth_ref.service_catalog.catalog[0]['endpoints']),
'qwertyuiop',
'supernova',
'compute',
)
- self.assertItemEqual(datalist, data)
+ self.assertItemsEqual(datalist, data)
class TestFormatColumns(TestCatalog):
diff --git a/openstackclient/tests/unit/identity/v3/test_identity_provider.py b/openstackclient/tests/unit/identity/v3/test_identity_provider.py
index a419a9bc..5aff2b1b 100644
--- a/openstackclient/tests/unit/identity/v3/test_identity_provider.py
+++ b/openstackclient/tests/unit/identity/v3/test_identity_provider.py
@@ -89,7 +89,7 @@ class TestIdentityProviderCreate(TestIdentityProvider):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
def test_create_identity_provider_description(self):
arglist = [
@@ -117,7 +117,7 @@ class TestIdentityProviderCreate(TestIdentityProvider):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
def test_create_identity_provider_remote_id(self):
arglist = [
@@ -145,7 +145,7 @@ class TestIdentityProviderCreate(TestIdentityProvider):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
def test_create_identity_provider_remote_ids_multiple(self):
arglist = [
@@ -174,7 +174,7 @@ class TestIdentityProviderCreate(TestIdentityProvider):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
def test_create_identity_provider_remote_ids_file(self):
arglist = [
@@ -207,7 +207,7 @@ class TestIdentityProviderCreate(TestIdentityProvider):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
def test_create_identity_provider_disabled(self):
@@ -250,7 +250,7 @@ class TestIdentityProviderCreate(TestIdentityProvider):
identity_fakes.idp_id,
identity_fakes.formatted_idp_remote_ids
)
- self.assertItemEqual(datalist, data)
+ self.assertItemsEqual(datalist, data)
def test_create_identity_provider_domain_name(self):
arglist = [
@@ -278,7 +278,7 @@ class TestIdentityProviderCreate(TestIdentityProvider):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
def test_create_identity_provider_domain_id(self):
arglist = [
@@ -306,7 +306,7 @@ class TestIdentityProviderCreate(TestIdentityProvider):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
class TestIdentityProviderDelete(TestIdentityProvider):
@@ -382,7 +382,62 @@ class TestIdentityProviderList(TestIdentityProvider):
identity_fakes.domain_id,
identity_fakes.idp_description,
), )
- self.assertListItemEqual(datalist, tuple(data))
+ self.assertItemsEqual(datalist, tuple(data))
+
+ def test_identity_provider_list_ID_option(self):
+ arglist = ['--id',
+ identity_fakes.idp_id]
+ verifylist = [
+ ('id', identity_fakes.idp_id)
+ ]
+ parsed_args = self.check_parser(self.cmd, arglist, verifylist)
+
+ # In base command class Lister in cliff, abstract method take_action()
+ # returns a tuple containing the column names and an iterable
+ # containing the data to be listed.
+ columns, data = self.cmd.take_action(parsed_args)
+
+ kwargs = {
+ 'id': identity_fakes.idp_id
+ }
+ self.identity_providers_mock.list.assert_called_with(**kwargs)
+
+ collist = ('ID', 'Enabled', 'Domain ID', 'Description')
+ self.assertEqual(collist, columns)
+ datalist = ((
+ identity_fakes.idp_id,
+ True,
+ identity_fakes.domain_id,
+ identity_fakes.idp_description,
+ ), )
+ self.assertItemsEqual(datalist, tuple(data))
+
+ def test_identity_provider_list_enabled_option(self):
+ arglist = ['--enabled']
+ verifylist = [
+ ('enabled', True)
+ ]
+ parsed_args = self.check_parser(self.cmd, arglist, verifylist)
+
+ # In base command class Lister in cliff, abstract method take_action()
+ # returns a tuple containing the column names and an iterable
+ # containing the data to be listed.
+ columns, data = self.cmd.take_action(parsed_args)
+
+ kwargs = {
+ 'enabled': True
+ }
+ self.identity_providers_mock.list.assert_called_with(**kwargs)
+
+ collist = ('ID', 'Enabled', 'Domain ID', 'Description')
+ self.assertEqual(collist, columns)
+ datalist = ((
+ identity_fakes.idp_id,
+ True,
+ identity_fakes.domain_id,
+ identity_fakes.idp_description,
+ ), )
+ self.assertItemsEqual(datalist, tuple(data))
class TestIdentityProviderSet(TestIdentityProvider):
@@ -667,4 +722,4 @@ class TestIdentityProviderShow(TestIdentityProvider):
identity_fakes.idp_id,
identity_fakes.formatted_idp_remote_ids
)
- self.assertItemEqual(datalist, data)
+ self.assertItemsEqual(datalist, data)
diff --git a/openstackclient/tests/unit/image/v1/test_image.py b/openstackclient/tests/unit/image/v1/test_image.py
index 2f190a7a..db64983c 100644
--- a/openstackclient/tests/unit/image/v1/test_image.py
+++ b/openstackclient/tests/unit/image/v1/test_image.py
@@ -100,7 +100,7 @@ class TestImageCreate(TestImage):
self.assertEqual(self.client.update_image.call_args_list, [])
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
@mock.patch('sys.stdin', side_effect=[None])
def test_image_reserve_options(self, raw_input):
@@ -149,7 +149,7 @@ class TestImageCreate(TestImage):
self.assertEqual(self.client.update_image.call_args_list, [])
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
@mock.patch('openstackclient.image.v1.image.io.open', name='Open')
def test_image_create_file(self, mock_open):
@@ -205,7 +205,7 @@ class TestImageCreate(TestImage):
self.assertEqual(self.client.update_image.call_args_list, [])
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
class TestImageDelete(TestImage):
@@ -386,7 +386,7 @@ class TestImageList(TestImage):
format_columns.DictColumn(
{'Alpha': 'a', 'Beta': 'b', 'Gamma': 'g'}),
), )
- self.assertListItemEqual(datalist, tuple(data))
+ self.assertItemsEqual(datalist, tuple(data))
@mock.patch('osc_lib.api.utils.simple_filter')
def test_image_list_property_option(self, sf_mock):
@@ -737,7 +737,7 @@ class TestImageShow(TestImage):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_image_show_human_readable(self):
arglist = [
diff --git a/openstackclient/tests/unit/image/v2/test_image.py b/openstackclient/tests/unit/image/v2/test_image.py
index b094817e..b72e9835 100644
--- a/openstackclient/tests/unit/image/v2/test_image.py
+++ b/openstackclient/tests/unit/image/v2/test_image.py
@@ -111,7 +111,7 @@ class TestImageCreate(TestImage):
self.assertEqual(
self.expected_columns,
columns)
- self.assertItemEqual(
+ self.assertItemsEqual(
self.expected_data,
data)
@@ -166,7 +166,7 @@ class TestImageCreate(TestImage):
self.assertEqual(
self.expected_columns,
columns)
- self.assertItemEqual(
+ self.assertItemsEqual(
self.expected_data,
data)
@@ -255,7 +255,7 @@ class TestImageCreate(TestImage):
self.assertEqual(
self.expected_columns,
columns)
- self.assertItemEqual(
+ self.assertItemsEqual(
self.expected_data,
data)
@@ -513,7 +513,7 @@ class TestImageList(TestImage):
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.datalist, tuple(data))
+ self.assertItemsEqual(self.datalist, tuple(data))
def test_image_list_public_option(self):
arglist = [
@@ -537,7 +537,7 @@ class TestImageList(TestImage):
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.datalist, tuple(data))
+ self.assertItemsEqual(self.datalist, tuple(data))
def test_image_list_private_option(self):
arglist = [
@@ -561,7 +561,7 @@ class TestImageList(TestImage):
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.datalist, tuple(data))
+ self.assertItemsEqual(self.datalist, tuple(data))
def test_image_list_community_option(self):
arglist = [
@@ -609,7 +609,7 @@ class TestImageList(TestImage):
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.datalist, tuple(data))
+ self.assertItemsEqual(self.datalist, tuple(data))
def test_image_list_shared_member_status_option(self):
arglist = [
@@ -697,7 +697,7 @@ class TestImageList(TestImage):
self._image.owner_id,
format_columns.ListColumn(self._image.tags),
), )
- self.assertListItemEqual(datalist, tuple(data))
+ self.assertItemsEqual(datalist, tuple(data))
@mock.patch('osc_lib.api.utils.simple_filter')
def test_image_list_property_option(self, sf_mock):
@@ -725,7 +725,7 @@ class TestImageList(TestImage):
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.datalist, tuple(data))
+ self.assertItemsEqual(self.datalist, tuple(data))
@mock.patch('osc_lib.utils.sort_items')
def test_image_list_sort_option(self, si_mock):
@@ -747,7 +747,7 @@ class TestImageList(TestImage):
str,
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.datalist, tuple(data))
+ self.assertItemsEqual(self.datalist, tuple(data))
def test_image_list_limit_option(self):
ret_limit = 1
@@ -1472,7 +1472,7 @@ class TestImageShow(TestImage):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_image_show_human_readable(self):
self.client.find_image.return_value = self.new_image
@@ -1618,7 +1618,7 @@ class TestImageSave(TestImage):
verifylist = [
('file', '/path/to/file'),
- ('image', self.image.id)
+ ('image', self.image.id),
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
@@ -1626,6 +1626,7 @@ class TestImageSave(TestImage):
self.client.download_image.assert_called_once_with(
self.image.id,
+ stream=True,
output='/path/to/file')
diff --git a/openstackclient/tests/unit/network/v2/test_ip_availability.py b/openstackclient/tests/unit/network/v2/test_ip_availability.py
index 9a712704..ade57837 100644
--- a/openstackclient/tests/unit/network/v2/test_ip_availability.py
+++ b/openstackclient/tests/unit/network/v2/test_ip_availability.py
@@ -75,7 +75,7 @@ class TestListIPAvailability(TestIPAvailability):
self.network.network_ip_availabilities.assert_called_once_with(
**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_list_ip_version(self):
arglist = [
@@ -93,7 +93,7 @@ class TestListIPAvailability(TestIPAvailability):
self.network.network_ip_availabilities.assert_called_once_with(
**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_list_project(self):
arglist = [
@@ -113,7 +113,7 @@ class TestListIPAvailability(TestIPAvailability):
self.network.network_ip_availabilities.assert_called_once_with(
**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
class TestShowIPAvailability(TestIPAvailability):
@@ -176,4 +176,4 @@ class TestShowIPAvailability(TestIPAvailability):
self._ip_availability.network_name,
ignore_missing=False)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
diff --git a/openstackclient/tests/unit/network/v2/test_network.py b/openstackclient/tests/unit/network/v2/test_network.py
index 5f8eed67..e29b72c7 100644
--- a/openstackclient/tests/unit/network/v2/test_network.py
+++ b/openstackclient/tests/unit/network/v2/test_network.py
@@ -146,7 +146,7 @@ class TestCreateNetworkIdentityV3(TestNetwork):
})
self.assertFalse(self.network.set_tags.called)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_all_options(self):
arglist = [
@@ -211,7 +211,7 @@ class TestCreateNetworkIdentityV3(TestNetwork):
'dns_domain': 'example.org.',
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_other_options(self):
arglist = [
@@ -238,7 +238,7 @@ class TestCreateNetworkIdentityV3(TestNetwork):
'port_security_enabled': False,
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def _test_create_with_tag(self, add_tags=True):
arglist = [self._network.name]
@@ -270,7 +270,7 @@ class TestCreateNetworkIdentityV3(TestNetwork):
else:
self.assertFalse(self.network.set_tags.called)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_with_tags(self):
self._test_create_with_tag(add_tags=True)
@@ -385,7 +385,7 @@ class TestCreateNetworkIdentityV2(TestNetwork):
})
self.assertFalse(self.network.set_tags.called)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_with_domain_identityv2(self):
arglist = [
@@ -577,7 +577,7 @@ class TestListNetwork(TestNetwork):
self.network.networks.assert_called_once_with()
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_list_external(self):
arglist = [
@@ -598,7 +598,7 @@ class TestListNetwork(TestNetwork):
**{'router:external': True, 'is_router_external': True}
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_list_internal(self):
arglist = [
@@ -615,7 +615,7 @@ class TestListNetwork(TestNetwork):
**{'router:external': False, 'is_router_external': False}
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_network_list_long(self):
arglist = [
@@ -634,7 +634,7 @@ class TestListNetwork(TestNetwork):
self.network.networks.assert_called_once_with()
self.assertEqual(self.columns_long, columns)
- self.assertListItemEqual(self.data_long, list(data))
+ self.assertItemsEqual(self.data_long, list(data))
def test_list_name(self):
test_name = "fakename"
@@ -653,7 +653,7 @@ class TestListNetwork(TestNetwork):
**{'name': test_name}
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_network_list_enable(self):
arglist = [
@@ -671,7 +671,7 @@ class TestListNetwork(TestNetwork):
**{'admin_state_up': True, 'is_admin_state_up': True}
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_network_list_disable(self):
arglist = [
@@ -689,7 +689,7 @@ class TestListNetwork(TestNetwork):
**{'admin_state_up': False, 'is_admin_state_up': False}
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_network_list_project(self):
project = identity_fakes_v3.FakeProject.create_one_project()
@@ -708,7 +708,7 @@ class TestListNetwork(TestNetwork):
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_network_list_project_domain(self):
project = identity_fakes_v3.FakeProject.create_one_project()
@@ -727,7 +727,7 @@ class TestListNetwork(TestNetwork):
self.network.networks.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_network_list_share(self):
arglist = [
@@ -744,7 +744,7 @@ class TestListNetwork(TestNetwork):
**{'shared': True, 'is_shared': True}
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_network_list_no_share(self):
arglist = [
@@ -761,7 +761,7 @@ class TestListNetwork(TestNetwork):
**{'shared': False, 'is_shared': False}
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_network_list_status(self):
choices = ['ACTIVE', 'BUILD', 'DOWN', 'ERROR']
@@ -780,7 +780,7 @@ class TestListNetwork(TestNetwork):
**{'status': test_status}
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_network_list_provider_network_type(self):
network_type = self._network[0].provider_network_type
@@ -798,7 +798,7 @@ class TestListNetwork(TestNetwork):
'provider_network_type': network_type}
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_network_list_provider_physical_network(self):
physical_network = self._network[0].provider_physical_network
@@ -816,7 +816,7 @@ class TestListNetwork(TestNetwork):
'provider_physical_network': physical_network}
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_network_list_provider_segment(self):
segmentation_id = self._network[0].provider_segmentation_id
@@ -834,7 +834,7 @@ class TestListNetwork(TestNetwork):
'provider_segmentation_id': segmentation_id}
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_network_list_dhcp_agent(self):
arglist = [
@@ -853,7 +853,7 @@ class TestListNetwork(TestNetwork):
*attrs)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(list(data), list(self.data))
+ self.assertItemsEqual(list(data), list(self.data))
def test_list_with_tag_options(self):
arglist = [
@@ -878,7 +878,7 @@ class TestListNetwork(TestNetwork):
'not_any_tags': 'black,white'}
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
class TestSetNetwork(TestNetwork):
@@ -1111,7 +1111,7 @@ class TestShowNetwork(TestNetwork):
self._network.name, ignore_missing=False)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
class TestUnsetNetwork(TestNetwork):
diff --git a/openstackclient/tests/unit/network/v2/test_network_agent.py b/openstackclient/tests/unit/network/v2/test_network_agent.py
index 3181ee78..fceac68e 100644
--- a/openstackclient/tests/unit/network/v2/test_network_agent.py
+++ b/openstackclient/tests/unit/network/v2/test_network_agent.py
@@ -246,7 +246,7 @@ class TestListNetworkAgent(TestNetworkAgent):
self.network.agents.assert_called_once_with(**{})
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_network_agents_list_agent_type(self):
arglist = [
@@ -263,7 +263,7 @@ class TestListNetworkAgent(TestNetworkAgent):
'agent_type': 'DHCP agent',
})
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_network_agents_list_host(self):
arglist = [
@@ -280,7 +280,7 @@ class TestListNetworkAgent(TestNetworkAgent):
'host': self.network_agents[0].host,
})
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_network_agents_list_networks(self):
arglist = [
@@ -298,7 +298,7 @@ class TestListNetworkAgent(TestNetworkAgent):
self.network.network_hosting_dhcp_agents.assert_called_once_with(
*attrs)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_network_agents_list_routers(self):
arglist = [
@@ -318,7 +318,7 @@ class TestListNetworkAgent(TestNetworkAgent):
*attrs)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_network_agents_list_routers_with_long_option(self):
arglist = [
@@ -343,7 +343,7 @@ class TestListNetworkAgent(TestNetworkAgent):
router_agent_data = [d + ('',) for d in self.data]
self.assertEqual(router_agent_columns, columns)
- self.assertListItemEqual(router_agent_data, list(data))
+ self.assertItemsEqual(router_agent_data, list(data))
class TestRemoveNetworkFromAgent(TestNetworkAgent):
@@ -571,4 +571,4 @@ class TestShowNetworkAgent(TestNetworkAgent):
self.network.get_agent.assert_called_once_with(
self._network_agent.id)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(list(self.data), list(data))
+ self.assertItemsEqual(list(self.data), list(data))
diff --git a/openstackclient/tests/unit/network/v2/test_port.py b/openstackclient/tests/unit/network/v2/test_port.py
index f7685f46..e21f9d01 100644
--- a/openstackclient/tests/unit/network/v2/test_port.py
+++ b/openstackclient/tests/unit/network/v2/test_port.py
@@ -151,7 +151,7 @@ class TestCreatePort(TestPort):
self.assertFalse(self.network.set_tags.called)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_full_options(self):
arglist = [
@@ -209,7 +209,7 @@ class TestCreatePort(TestPort):
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_invalid_json_binding_profile(self):
arglist = [
@@ -260,7 +260,7 @@ class TestCreatePort(TestPort):
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_with_security_group(self):
secgroup = network_fakes.FakeSecurityGroup.create_one_security_group()
@@ -289,7 +289,7 @@ class TestCreatePort(TestPort):
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_port_with_dns_name(self):
arglist = [
@@ -315,7 +315,7 @@ class TestCreatePort(TestPort):
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_with_security_groups(self):
sg_1 = network_fakes.FakeSecurityGroup.create_one_security_group()
@@ -345,7 +345,7 @@ class TestCreatePort(TestPort):
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_with_no_security_groups(self):
arglist = [
@@ -371,7 +371,7 @@ class TestCreatePort(TestPort):
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_with_no_fixed_ips(self):
arglist = [
@@ -397,7 +397,7 @@ class TestCreatePort(TestPort):
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_port_with_allowed_address_pair_ipaddr(self):
pairs = [{'ip_address': '192.168.1.123'},
@@ -427,7 +427,7 @@ class TestCreatePort(TestPort):
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_port_with_allowed_address_pair(self):
pairs = [{'ip_address': '192.168.1.123',
@@ -463,7 +463,7 @@ class TestCreatePort(TestPort):
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_port_with_qos(self):
qos_policy = network_fakes.FakeNetworkQosPolicy.create_one_qos_policy()
@@ -491,7 +491,7 @@ class TestCreatePort(TestPort):
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_port_security_enabled(self):
arglist = [
@@ -600,7 +600,7 @@ class TestCreatePort(TestPort):
self.assertFalse(self.network.set_tags.called)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_with_tags(self):
self._test_create_with_tag(add_tags=True, add_tags_in_post=True)
@@ -643,7 +643,7 @@ class TestCreatePort(TestPort):
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_with_uplink_status_propagation_enabled(self):
self._test_create_with_uplink_status_propagation(enable=True)
@@ -723,7 +723,7 @@ class TestCreatePort(TestPort):
self.network.create_port.assert_called_once_with(**create_args)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_with_numa_affinity_policy_required(self):
self._test_create_with_numa_affinity_policy(policy='required')
@@ -890,7 +890,7 @@ class TestListPort(TestPort):
self.network.ports.assert_called_once_with(
fields=LIST_FIELDS_TO_RETRIEVE)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_port_list_router_opt(self):
arglist = [
@@ -910,7 +910,7 @@ class TestListPort(TestPort):
'fields': LIST_FIELDS_TO_RETRIEVE,
})
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
@mock.patch.object(utils, 'find_resource')
def test_port_list_with_server_option(self, mock_find):
@@ -931,7 +931,7 @@ class TestListPort(TestPort):
fields=LIST_FIELDS_TO_RETRIEVE)
mock_find.assert_called_once_with(mock.ANY, 'fake-server-name')
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_port_list_device_id_opt(self):
arglist = [
@@ -951,7 +951,7 @@ class TestListPort(TestPort):
'fields': LIST_FIELDS_TO_RETRIEVE,
})
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_port_list_device_owner_opt(self):
arglist = [
@@ -971,7 +971,7 @@ class TestListPort(TestPort):
'fields': LIST_FIELDS_TO_RETRIEVE,
})
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_port_list_all_opt(self):
arglist = [
@@ -1000,7 +1000,7 @@ class TestListPort(TestPort):
'fields': LIST_FIELDS_TO_RETRIEVE,
})
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_port_list_mac_address_opt(self):
arglist = [
@@ -1020,7 +1020,7 @@ class TestListPort(TestPort):
'fields': LIST_FIELDS_TO_RETRIEVE,
})
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_port_list_fixed_ip_opt_ip_address(self):
ip_address = self._ports[0].fixed_ips[0]['ip_address']
@@ -1040,7 +1040,7 @@ class TestListPort(TestPort):
'fields': LIST_FIELDS_TO_RETRIEVE,
})
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_port_list_fixed_ip_opt_ip_address_substr(self):
ip_address_ss = self._ports[0].fixed_ips[0]['ip_address'][:-1]
@@ -1060,7 +1060,7 @@ class TestListPort(TestPort):
'fields': LIST_FIELDS_TO_RETRIEVE,
})
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_port_list_fixed_ip_opt_subnet_id(self):
subnet_id = self._ports[0].fixed_ips[0]['subnet_id']
@@ -1082,7 +1082,7 @@ class TestListPort(TestPort):
'fields': LIST_FIELDS_TO_RETRIEVE,
})
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_port_list_fixed_ip_opts(self):
subnet_id = self._ports[0].fixed_ips[0]['subnet_id']
@@ -1108,7 +1108,7 @@ class TestListPort(TestPort):
'fields': LIST_FIELDS_TO_RETRIEVE,
})
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_port_list_fixed_ips(self):
subnet_id = self._ports[0].fixed_ips[0]['subnet_id']
@@ -1136,7 +1136,7 @@ class TestListPort(TestPort):
'fields': LIST_FIELDS_TO_RETRIEVE,
})
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_list_port_with_long(self):
arglist = [
@@ -1154,7 +1154,7 @@ class TestListPort(TestPort):
self.network.ports.assert_called_once_with(
fields=LIST_FIELDS_TO_RETRIEVE + LIST_FIELDS_TO_RETRIEVE_LONG)
self.assertEqual(self.columns_long, columns)
- self.assertListItemEqual(self.data_long, list(data))
+ self.assertItemsEqual(self.data_long, list(data))
def test_port_list_host(self):
arglist = [
@@ -1173,7 +1173,7 @@ class TestListPort(TestPort):
self.network.ports.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_port_list_project(self):
project = identity_fakes.FakeProject.create_one_project()
@@ -1195,7 +1195,7 @@ class TestListPort(TestPort):
self.network.ports.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_port_list_project_domain(self):
project = identity_fakes.FakeProject.create_one_project()
@@ -1219,7 +1219,7 @@ class TestListPort(TestPort):
self.network.ports.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_list_with_tag_options(self):
arglist = [
@@ -1245,7 +1245,7 @@ class TestListPort(TestPort):
'fields': LIST_FIELDS_TO_RETRIEVE}
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
class TestSetPort(TestPort):
@@ -1845,7 +1845,7 @@ class TestShowPort(TestPort):
self._port.name, ignore_missing=False)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
class TestUnsetPort(TestPort):
diff --git a/openstackclient/tests/unit/network/v2/test_router.py b/openstackclient/tests/unit/network/v2/test_router.py
index 09b4957c..323c9198 100644
--- a/openstackclient/tests/unit/network/v2/test_router.py
+++ b/openstackclient/tests/unit/network/v2/test_router.py
@@ -184,7 +184,7 @@ class TestCreateRouter(TestRouter):
})
self.assertFalse(self.network.set_tags.called)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def _test_create_with_ha_options(self, option, ha):
arglist = [
@@ -208,7 +208,7 @@ class TestCreateRouter(TestRouter):
'ha': ha,
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_with_ha_option(self):
self._test_create_with_ha_options('--ha', True)
@@ -237,7 +237,7 @@ class TestCreateRouter(TestRouter):
'distributed': distributed,
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_with_distributed_option(self):
self._test_create_with_distributed_options('--distributed', True)
@@ -268,7 +268,7 @@ class TestCreateRouter(TestRouter):
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def _test_create_with_tag(self, add_tags=True):
arglist = [self.new_router.name]
@@ -301,7 +301,7 @@ class TestCreateRouter(TestRouter):
else:
self.assertFalse(self.network.set_tags.called)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_with_tags(self):
self._test_create_with_tag(add_tags=True)
@@ -494,7 +494,7 @@ class TestListRouter(TestRouter):
self.network.routers.assert_called_once_with()
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_router_list_no_ha_no_distributed(self):
_routers = network_fakes.FakeRouter.create_routers({
@@ -531,7 +531,7 @@ class TestListRouter(TestRouter):
self.network.routers.assert_called_once_with()
self.assertEqual(self.columns_long, columns)
- self.assertListItemEqual(self.data_long, list(data))
+ self.assertItemsEqual(self.data_long, list(data))
def test_router_list_long_no_az(self):
arglist = [
@@ -552,7 +552,7 @@ class TestListRouter(TestRouter):
self.network.routers.assert_called_once_with()
self.assertEqual(self.columns_long_no_az, columns)
- self.assertListItemEqual(self.data_long_no_az, list(data))
+ self.assertItemsEqual(self.data_long_no_az, list(data))
def test_list_name(self):
test_name = "fakename"
@@ -570,7 +570,7 @@ class TestListRouter(TestRouter):
**{'name': test_name}
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_router_list_enable(self):
arglist = [
@@ -587,7 +587,7 @@ class TestListRouter(TestRouter):
**{'admin_state_up': True, 'is_admin_state_up': True}
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_router_list_disable(self):
arglist = [
@@ -605,7 +605,7 @@ class TestListRouter(TestRouter):
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_router_list_project(self):
project = identity_fakes_v3.FakeProject.create_one_project()
@@ -623,7 +623,7 @@ class TestListRouter(TestRouter):
self.network.routers.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_router_list_project_domain(self):
project = identity_fakes_v3.FakeProject.create_one_project()
@@ -643,7 +643,7 @@ class TestListRouter(TestRouter):
self.network.routers.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_router_list_agents_no_args(self):
arglist = [
@@ -671,7 +671,7 @@ class TestListRouter(TestRouter):
self.network.agent_hosted_routers(
*attrs)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_list_with_tag_options(self):
arglist = [
@@ -696,7 +696,7 @@ class TestListRouter(TestRouter):
'not_any_tags': 'black,white'}
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
class TestRemovePortFromRouter(TestRouter):
@@ -1403,7 +1403,7 @@ class TestShowRouter(TestRouter):
'device_id': self._router.id
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_show_no_ha_no_distributed(self):
_router = network_fakes.FakeRouter.create_one_router({
diff --git a/openstackclient/tests/unit/network/v2/test_security_group_compute.py b/openstackclient/tests/unit/network/v2/test_security_group_compute.py
index b4ddcf80..837c9b21 100644
--- a/openstackclient/tests/unit/network/v2/test_security_group_compute.py
+++ b/openstackclient/tests/unit/network/v2/test_security_group_compute.py
@@ -88,7 +88,7 @@ class TestCreateSecurityGroupCompute(TestSecurityGroupCompute):
self._security_group['name'],
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_security_group_create_all_options(self, sg_mock):
sg_mock.return_value = self._security_group
@@ -109,7 +109,7 @@ class TestCreateSecurityGroupCompute(TestSecurityGroupCompute):
self._security_group['description'],
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
@mock.patch(
@@ -255,7 +255,7 @@ class TestListSecurityGroupCompute(TestSecurityGroupCompute):
kwargs = {'search_opts': {'all_tenants': False}}
sg_mock.assert_called_once_with(**kwargs)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_security_group_list_all_projects(self, sg_mock):
sg_mock.return_value = self._security_groups
@@ -272,7 +272,7 @@ class TestListSecurityGroupCompute(TestSecurityGroupCompute):
kwargs = {'search_opts': {'all_tenants': True}}
sg_mock.assert_called_once_with(**kwargs)
self.assertEqual(self.columns_all_projects, columns)
- self.assertListItemEqual(self.data_all_projects, list(data))
+ self.assertItemsEqual(self.data_all_projects, list(data))
@mock.patch(
@@ -401,4 +401,4 @@ class TestShowSecurityGroupCompute(TestSecurityGroupCompute):
sg_mock.assert_called_once_with(self._security_group['id'])
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
diff --git a/openstackclient/tests/unit/network/v2/test_security_group_network.py b/openstackclient/tests/unit/network/v2/test_security_group_network.py
index 7c1d7fb6..fe377785 100644
--- a/openstackclient/tests/unit/network/v2/test_security_group_network.py
+++ b/openstackclient/tests/unit/network/v2/test_security_group_network.py
@@ -96,7 +96,7 @@ class TestCreateSecurityGroupNetwork(TestSecurityGroupNetwork):
'name': self._security_group.name,
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_all_options(self):
arglist = [
@@ -124,7 +124,7 @@ class TestCreateSecurityGroupNetwork(TestSecurityGroupNetwork):
'tenant_id': self.project.id,
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def _test_create_with_tag(self, add_tags=True):
arglist = [self._security_group.name]
@@ -155,7 +155,7 @@ class TestCreateSecurityGroupNetwork(TestSecurityGroupNetwork):
else:
self.assertFalse(self.network.set_tags.called)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_with_tags(self):
self._test_create_with_tag(add_tags=True)
@@ -293,7 +293,7 @@ class TestListSecurityGroupNetwork(TestSecurityGroupNetwork):
self.network.security_groups.assert_called_once_with(
fields=security_group.ListSecurityGroup.FIELDS_TO_RETRIEVE)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_security_group_list_all_projects(self):
arglist = [
@@ -309,7 +309,7 @@ class TestListSecurityGroupNetwork(TestSecurityGroupNetwork):
self.network.security_groups.assert_called_once_with(
fields=security_group.ListSecurityGroup.FIELDS_TO_RETRIEVE)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_security_group_list_project(self):
project = identity_fakes.FakeProject.create_one_project()
@@ -329,7 +329,7 @@ class TestListSecurityGroupNetwork(TestSecurityGroupNetwork):
self.network.security_groups.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_security_group_list_project_domain(self):
project = identity_fakes.FakeProject.create_one_project()
@@ -351,7 +351,7 @@ class TestListSecurityGroupNetwork(TestSecurityGroupNetwork):
self.network.security_groups.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_list_with_tag_options(self):
arglist = [
@@ -539,7 +539,7 @@ class TestShowSecurityGroupNetwork(TestSecurityGroupNetwork):
self.network.find_security_group.assert_called_once_with(
self._security_group.id, ignore_missing=False)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
class TestUnsetSecurityGroupNetwork(TestSecurityGroupNetwork):
diff --git a/openstackclient/tests/unit/network/v2/test_subnet.py b/openstackclient/tests/unit/network/v2/test_subnet.py
index 47d0c6b4..1b4bfdad 100644
--- a/openstackclient/tests/unit/network/v2/test_subnet.py
+++ b/openstackclient/tests/unit/network/v2/test_subnet.py
@@ -255,7 +255,7 @@ class TestCreateSubnet(TestSubnet):
})
self.assertFalse(self.network.set_tags.called)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_from_subnet_pool_options(self):
# Mock SDK calls for this test.
@@ -317,7 +317,7 @@ class TestCreateSubnet(TestSubnet):
'service_types': self._subnet_from_pool.service_types,
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data_subnet_pool, data)
+ self.assertItemsEqual(self.data_subnet_pool, data)
def test_create_options_subnet_range_ipv6(self):
# Mock SDK calls for this test.
@@ -390,7 +390,7 @@ class TestCreateSubnet(TestSubnet):
})
self.assertFalse(self.network.set_tags.called)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data_ipv6, data)
+ self.assertItemsEqual(self.data_ipv6, data)
def test_create_with_network_segment(self):
# Mock SDK calls for this test.
@@ -424,7 +424,7 @@ class TestCreateSubnet(TestSubnet):
})
self.assertFalse(self.network.set_tags.called)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_with_description(self):
# Mock SDK calls for this test.
@@ -458,7 +458,7 @@ class TestCreateSubnet(TestSubnet):
})
self.assertFalse(self.network.set_tags.called)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def _test_create_with_dns(self, publish_dns=True):
arglist = [
@@ -490,7 +490,7 @@ class TestCreateSubnet(TestSubnet):
dns_publish_fixed_ip=publish_dns,
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_with_dns(self):
self._test_create_with_dns(publish_dns=True)
@@ -535,7 +535,7 @@ class TestCreateSubnet(TestSubnet):
else:
self.assertFalse(self.network.set_tags.called)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_with_tags(self):
self._test_create_with_tag(add_tags=True)
@@ -691,7 +691,7 @@ class TestListSubnet(TestSubnet):
self.network.subnets.assert_called_once_with()
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_subnet_list_long(self):
arglist = [
@@ -706,7 +706,7 @@ class TestListSubnet(TestSubnet):
self.network.subnets.assert_called_once_with()
self.assertEqual(self.columns_long, columns)
- self.assertListItemEqual(self.data_long, list(data))
+ self.assertItemsEqual(self.data_long, list(data))
def test_subnet_list_ip_version(self):
arglist = [
@@ -722,7 +722,7 @@ class TestListSubnet(TestSubnet):
self.network.subnets.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_subnet_list_dhcp(self):
arglist = [
@@ -738,7 +738,7 @@ class TestListSubnet(TestSubnet):
self.network.subnets.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_subnet_list_no_dhcp(self):
arglist = [
@@ -754,7 +754,7 @@ class TestListSubnet(TestSubnet):
self.network.subnets.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_subnet_list_service_type(self):
arglist = [
@@ -769,7 +769,7 @@ class TestListSubnet(TestSubnet):
self.network.subnets.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_subnet_list_project(self):
project = identity_fakes_v3.FakeProject.create_one_project()
@@ -787,7 +787,7 @@ class TestListSubnet(TestSubnet):
self.network.subnets.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_subnet_list_service_type_multiple(self):
arglist = [
@@ -805,7 +805,7 @@ class TestListSubnet(TestSubnet):
'network:floatingip_agent_gateway']}
self.network.subnets.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_subnet_list_project_domain(self):
project = identity_fakes_v3.FakeProject.create_one_project()
@@ -825,7 +825,7 @@ class TestListSubnet(TestSubnet):
self.network.subnets.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_subnet_list_network(self):
network = network_fakes.FakeNetwork.create_one_network()
@@ -843,7 +843,7 @@ class TestListSubnet(TestSubnet):
self.network.subnets.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_subnet_list_gateway(self):
subnet = network_fakes.FakeSubnet.create_one_subnet()
@@ -861,7 +861,7 @@ class TestListSubnet(TestSubnet):
self.network.subnets.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_subnet_list_name(self):
subnet = network_fakes.FakeSubnet.create_one_subnet()
@@ -879,7 +879,7 @@ class TestListSubnet(TestSubnet):
self.network.subnets.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_subnet_list_subnet_range(self):
subnet = network_fakes.FakeSubnet.create_one_subnet()
@@ -897,7 +897,7 @@ class TestListSubnet(TestSubnet):
self.network.subnets.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_list_with_tag_options(self):
arglist = [
@@ -1244,7 +1244,7 @@ class TestShowSubnet(TestSubnet):
self._subnet.name, ignore_missing=False)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
class TestUnsetSubnet(TestSubnet):
diff --git a/openstackclient/tests/unit/network/v2/test_subnet_pool.py b/openstackclient/tests/unit/network/v2/test_subnet_pool.py
index eb454646..243fc76d 100644
--- a/openstackclient/tests/unit/network/v2/test_subnet_pool.py
+++ b/openstackclient/tests/unit/network/v2/test_subnet_pool.py
@@ -133,7 +133,7 @@ class TestCreateSubnetPool(TestSubnetPool):
})
self.assertFalse(self.network.set_tags.called)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_prefixlen_options(self):
arglist = [
@@ -163,7 +163,7 @@ class TestCreateSubnetPool(TestSubnetPool):
'name': self._subnet_pool.name,
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_len_negative(self):
arglist = [
@@ -201,7 +201,7 @@ class TestCreateSubnetPool(TestSubnetPool):
'name': self._subnet_pool.name,
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_address_scope_option(self):
arglist = [
@@ -224,7 +224,7 @@ class TestCreateSubnetPool(TestSubnetPool):
'name': self._subnet_pool.name,
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_default_and_shared_options(self):
arglist = [
@@ -250,7 +250,7 @@ class TestCreateSubnetPool(TestSubnetPool):
'shared': True,
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_with_description(self):
arglist = [
@@ -273,7 +273,7 @@ class TestCreateSubnetPool(TestSubnetPool):
'description': self._subnet_pool.description,
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_with_default_quota(self):
arglist = [
@@ -294,7 +294,7 @@ class TestCreateSubnetPool(TestSubnetPool):
'default_quota': 10,
})
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def _test_create_with_tag(self, add_tags=True):
arglist = [
@@ -328,7 +328,7 @@ class TestCreateSubnetPool(TestSubnetPool):
else:
self.assertFalse(self.network.set_tags.called)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_create_with_tags(self):
self._test_create_with_tag(add_tags=True)
@@ -476,7 +476,7 @@ class TestListSubnetPool(TestSubnetPool):
self.network.subnet_pools.assert_called_once_with()
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_subnet_pool_list_long(self):
arglist = [
@@ -491,7 +491,7 @@ class TestListSubnetPool(TestSubnetPool):
self.network.subnet_pools.assert_called_once_with()
self.assertEqual(self.columns_long, columns)
- self.assertListItemEqual(self.data_long, list(data))
+ self.assertItemsEqual(self.data_long, list(data))
def test_subnet_pool_list_no_share(self):
arglist = [
@@ -507,7 +507,7 @@ class TestListSubnetPool(TestSubnetPool):
self.network.subnet_pools.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_subnet_pool_list_share(self):
arglist = [
@@ -523,7 +523,7 @@ class TestListSubnetPool(TestSubnetPool):
self.network.subnet_pools.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_subnet_pool_list_no_default(self):
arglist = [
@@ -539,7 +539,7 @@ class TestListSubnetPool(TestSubnetPool):
self.network.subnet_pools.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_subnet_pool_list_default(self):
arglist = [
@@ -555,7 +555,7 @@ class TestListSubnetPool(TestSubnetPool):
self.network.subnet_pools.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_subnet_pool_list_project(self):
project = identity_fakes_v3.FakeProject.create_one_project()
@@ -573,7 +573,7 @@ class TestListSubnetPool(TestSubnetPool):
self.network.subnet_pools.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_subnet_pool_list_project_domain(self):
project = identity_fakes_v3.FakeProject.create_one_project()
@@ -593,7 +593,7 @@ class TestListSubnetPool(TestSubnetPool):
self.network.subnet_pools.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_subnet_pool_list_name(self):
subnet_pool = network_fakes.FakeSubnetPool.create_one_subnet_pool()
@@ -611,7 +611,7 @@ class TestListSubnetPool(TestSubnetPool):
self.network.subnet_pools.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_subnet_pool_list_address_scope(self):
addr_scope = network_fakes.FakeAddressScope.create_one_address_scope()
@@ -629,7 +629,7 @@ class TestListSubnetPool(TestSubnetPool):
self.network.subnet_pools.assert_called_once_with(**filters)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_list_with_tag_options(self):
arglist = [
@@ -654,7 +654,7 @@ class TestListSubnetPool(TestSubnetPool):
'not_any_tags': 'black,white'}
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
class TestSetSubnetPool(TestSubnetPool):
@@ -1008,7 +1008,7 @@ class TestShowSubnetPool(TestSubnetPool):
ignore_missing=False
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
class TestUnsetSubnetPool(TestSubnetPool):
diff --git a/openstackclient/tests/unit/utils.py b/openstackclient/tests/unit/utils.py
index 4130f18e..39cb5614 100644
--- a/openstackclient/tests/unit/utils.py
+++ b/openstackclient/tests/unit/utils.py
@@ -17,7 +17,6 @@
from io import StringIO
import os
-from cliff import columns as cliff_columns
import fixtures
import testtools
@@ -85,18 +84,3 @@ class TestCommand(TestCase):
self.assertIn(attr, parsed_args)
self.assertEqual(value, getattr(parsed_args, attr))
return parsed_args
-
- def assertListItemEqual(self, expected, actual):
- self.assertEqual(len(expected), len(actual))
- for item_expected, item_actual in zip(expected, actual):
- self.assertItemEqual(item_expected, item_actual)
-
- def assertItemEqual(self, expected, actual):
- self.assertEqual(len(expected), len(actual))
- for col_expected, col_actual in zip(expected, actual):
- if isinstance(col_expected, cliff_columns.FormattableColumn):
- self.assertIsInstance(col_actual, col_expected.__class__)
- self.assertEqual(col_expected.human_readable(),
- col_actual.human_readable())
- else:
- self.assertEqual(col_expected, col_actual)
diff --git a/openstackclient/tests/unit/volume/v1/test_qos_specs.py b/openstackclient/tests/unit/volume/v1/test_qos_specs.py
index 83c533b6..5500438b 100644
--- a/openstackclient/tests/unit/volume/v1/test_qos_specs.py
+++ b/openstackclient/tests/unit/volume/v1/test_qos_specs.py
@@ -109,7 +109,7 @@ class TestQosCreate(TestQos):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
def test_qos_create_with_consumer(self):
arglist = [
@@ -129,7 +129,7 @@ class TestQosCreate(TestQos):
{'consumer': self.new_qos_spec.consumer}
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
def test_qos_create_with_properties(self):
arglist = [
@@ -155,7 +155,7 @@ class TestQosCreate(TestQos):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
class TestQosDelete(TestQos):
@@ -350,7 +350,7 @@ class TestQosList(TestQos):
self.qos_mock.list.assert_called_with()
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_qos_list_no_association(self):
self.qos_mock.reset_mock()
@@ -377,7 +377,7 @@ class TestQosList(TestQos):
format_columns.ListColumn(None),
format_columns.DictColumn(self.qos_specs[1].specs),
)
- self.assertListItemEqual(ex_data, list(data))
+ self.assertItemsEqual(ex_data, list(data))
class TestQosSet(TestQos):
@@ -454,7 +454,7 @@ class TestQosShow(TestQos):
self.qos_spec.name,
format_columns.DictColumn(self.qos_spec.specs),
)
- self.assertItemEqual(datalist, tuple(data))
+ self.assertItemsEqual(datalist, tuple(data))
class TestQosUnset(TestQos):
diff --git a/openstackclient/tests/unit/volume/v1/test_type.py b/openstackclient/tests/unit/volume/v1/test_type.py
index 8bee5747..f1d46914 100644
--- a/openstackclient/tests/unit/volume/v1/test_type.py
+++ b/openstackclient/tests/unit/volume/v1/test_type.py
@@ -78,7 +78,7 @@ class TestTypeCreate(TestType):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_type_create_with_encryption(self):
encryption_info = {
@@ -139,7 +139,7 @@ class TestTypeCreate(TestType):
body,
)
self.assertEqual(encryption_columns, columns)
- self.assertItemEqual(encryption_data, data)
+ self.assertItemsEqual(encryption_data, data)
class TestTypeDelete(TestType):
@@ -270,7 +270,7 @@ class TestTypeList(TestType):
columns, data = self.cmd.take_action(parsed_args)
self.types_mock.list.assert_called_once_with()
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_type_list_with_options(self):
arglist = [
@@ -284,7 +284,7 @@ class TestTypeList(TestType):
columns, data = self.cmd.take_action(parsed_args)
self.types_mock.list.assert_called_once_with()
self.assertEqual(self.columns_long, columns)
- self.assertListItemEqual(self.data_long, list(data))
+ self.assertItemsEqual(self.data_long, list(data))
def test_type_list_with_encryption(self):
encryption_type = volume_fakes.FakeType.create_one_encryption_type(
@@ -328,7 +328,7 @@ class TestTypeList(TestType):
self.encryption_types_mock.list.assert_called_once_with()
self.types_mock.list.assert_called_once_with()
self.assertEqual(encryption_columns, columns)
- self.assertListItemEqual(encryption_data, list(data))
+ self.assertItemsEqual(encryption_data, list(data))
class TestTypeSet(TestType):
@@ -469,7 +469,7 @@ class TestTypeShow(TestType):
self.types_mock.get.assert_called_with(self.volume_type.id)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_type_show_with_encryption(self):
encryption_type = volume_fakes.FakeType.create_one_encryption_type()
@@ -513,7 +513,7 @@ class TestTypeShow(TestType):
self.types_mock.get.assert_called_with(self.volume_type.id)
self.encryption_types_mock.get.assert_called_with(self.volume_type.id)
self.assertEqual(encryption_columns, columns)
- self.assertItemEqual(encryption_data, data)
+ self.assertItemsEqual(encryption_data, data)
class TestTypeUnset(TestType):
diff --git a/openstackclient/tests/unit/volume/v1/test_volume.py b/openstackclient/tests/unit/volume/v1/test_volume.py
index 25cdf92a..704a66da 100644
--- a/openstackclient/tests/unit/volume/v1/test_volume.py
+++ b/openstackclient/tests/unit/volume/v1/test_volume.py
@@ -135,7 +135,7 @@ class TestVolumeCreate(TestVolume):
None,
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
def test_volume_create_options(self):
arglist = [
@@ -179,7 +179,7 @@ class TestVolumeCreate(TestVolume):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
def test_volume_create_user_project_id(self):
# Return a project
@@ -226,7 +226,7 @@ class TestVolumeCreate(TestVolume):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
def test_volume_create_user_project_name(self):
# Return a project
@@ -273,7 +273,7 @@ class TestVolumeCreate(TestVolume):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
def test_volume_create_properties(self):
arglist = [
@@ -314,7 +314,7 @@ class TestVolumeCreate(TestVolume):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
def test_volume_create_image_id(self):
image = image_fakes.FakeImage.create_one_image()
@@ -357,7 +357,7 @@ class TestVolumeCreate(TestVolume):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
def test_volume_create_image_name(self):
image = image_fakes.FakeImage.create_one_image()
@@ -400,7 +400,7 @@ class TestVolumeCreate(TestVolume):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
def test_volume_create_with_source(self):
self.volumes_mock.get.return_value = self.new_volume
@@ -430,7 +430,7 @@ class TestVolumeCreate(TestVolume):
None,
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
def test_volume_create_with_bootable_and_readonly(self):
arglist = [
@@ -468,7 +468,7 @@ class TestVolumeCreate(TestVolume):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
self.volumes_mock.set_bootable.assert_called_with(
self.new_volume.id, True)
self.volumes_mock.update_readonly_flag.assert_called_with(
@@ -510,7 +510,7 @@ class TestVolumeCreate(TestVolume):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
self.volumes_mock.set_bootable.assert_called_with(
self.new_volume.id, False)
self.volumes_mock.update_readonly_flag.assert_called_with(
@@ -562,7 +562,7 @@ class TestVolumeCreate(TestVolume):
self.assertEqual(2, mock_error.call_count)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
self.volumes_mock.set_bootable.assert_called_with(
self.new_volume.id, True)
self.volumes_mock.update_readonly_flag.assert_called_with(
@@ -765,7 +765,7 @@ class TestVolumeList(TestVolume):
columns, data = self.cmd.take_action(parsed_args)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.datalist, tuple(data))
+ self.assertItemsEqual(self.datalist, tuple(data))
def test_volume_list_name(self):
arglist = [
@@ -782,7 +782,7 @@ class TestVolumeList(TestVolume):
columns, data = self.cmd.take_action(parsed_args)
self.assertEqual(self.columns, tuple(columns))
- self.assertListItemEqual(self.datalist, tuple(data))
+ self.assertItemsEqual(self.datalist, tuple(data))
def test_volume_list_status(self):
arglist = [
@@ -799,7 +799,7 @@ class TestVolumeList(TestVolume):
columns, data = self.cmd.take_action(parsed_args)
self.assertEqual(self.columns, tuple(columns))
- self.assertListItemEqual(self.datalist, tuple(data))
+ self.assertItemsEqual(self.datalist, tuple(data))
def test_volume_list_all_projects(self):
arglist = [
@@ -816,7 +816,7 @@ class TestVolumeList(TestVolume):
columns, data = self.cmd.take_action(parsed_args)
self.assertEqual(self.columns, tuple(columns))
- self.assertListItemEqual(self.datalist, tuple(data))
+ self.assertItemsEqual(self.datalist, tuple(data))
def test_volume_list_long(self):
arglist = [
@@ -856,7 +856,7 @@ class TestVolumeList(TestVolume):
volume.AttachmentsColumn(self._volume.attachments),
format_columns.DictColumn(self._volume.metadata),
), )
- self.assertListItemEqual(datalist, tuple(data))
+ self.assertItemsEqual(datalist, tuple(data))
def test_volume_list_with_limit(self):
arglist = [
@@ -881,7 +881,7 @@ class TestVolumeList(TestVolume):
'all_tenants': False, }
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.datalist, tuple(data))
+ self.assertItemsEqual(self.datalist, tuple(data))
def test_volume_list_negative_limit(self):
arglist = [
@@ -1272,7 +1272,7 @@ class TestVolumeShow(TestVolume):
self.volumes_mock.get.assert_called_with(self._volume.id)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
def test_volume_show_backward_compatibility(self):
arglist = [
diff --git a/openstackclient/tests/unit/volume/v1/test_volume_backup.py b/openstackclient/tests/unit/volume/v1/test_volume_backup.py
index 20aadcd3..a7131550 100644
--- a/openstackclient/tests/unit/volume/v1/test_volume_backup.py
+++ b/openstackclient/tests/unit/volume/v1/test_volume_backup.py
@@ -100,7 +100,7 @@ class TestBackupCreate(TestBackup):
self.new_backup.description,
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_backup_create_without_name(self):
arglist = [
@@ -124,7 +124,7 @@ class TestBackupCreate(TestBackup):
self.new_backup.description,
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
class TestBackupDelete(TestBackup):
@@ -277,7 +277,7 @@ class TestBackupList(TestBackup):
search_opts=search_opts,
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_backup_list_with_options(self):
arglist = [
@@ -309,7 +309,7 @@ class TestBackupList(TestBackup):
search_opts=search_opts,
)
self.assertEqual(self.columns_long, columns)
- self.assertListItemEqual(self.data_long, list(data))
+ self.assertItemsEqual(self.data_long, list(data))
class TestBackupRestore(TestBackup):
@@ -391,4 +391,4 @@ class TestBackupShow(TestBackup):
self.backups_mock.get.assert_called_with(self.backup.id)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
diff --git a/openstackclient/tests/unit/volume/v2/test_consistency_group.py b/openstackclient/tests/unit/volume/v2/test_consistency_group.py
index c3bd71e3..6bb6c029 100644
--- a/openstackclient/tests/unit/volume/v2/test_consistency_group.py
+++ b/openstackclient/tests/unit/volume/v2/test_consistency_group.py
@@ -251,7 +251,7 @@ class TestConsistencyGroupCreate(TestConsistencyGroup):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_consistency_group_create_from_source(self):
arglist = [
@@ -279,7 +279,7 @@ class TestConsistencyGroupCreate(TestConsistencyGroup):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_consistency_group_create_from_snapshot(self):
arglist = [
@@ -307,7 +307,7 @@ class TestConsistencyGroupCreate(TestConsistencyGroup):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
class TestConsistencyGroupDelete(TestConsistencyGroup):
@@ -463,7 +463,7 @@ class TestConsistencyGroupList(TestConsistencyGroup):
self.consistencygroups_mock.list.assert_called_once_with(
detailed=True, search_opts={'all_tenants': False})
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_consistency_group_list_with_all_project(self):
arglist = [
@@ -480,7 +480,7 @@ class TestConsistencyGroupList(TestConsistencyGroup):
self.consistencygroups_mock.list.assert_called_once_with(
detailed=True, search_opts={'all_tenants': True})
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_consistency_group_list_with_long(self):
arglist = [
@@ -497,7 +497,7 @@ class TestConsistencyGroupList(TestConsistencyGroup):
self.consistencygroups_mock.list.assert_called_once_with(
detailed=True, search_opts={'all_tenants': False})
self.assertEqual(self.columns_long, columns)
- self.assertListItemEqual(self.data_long, list(data))
+ self.assertItemsEqual(self.data_long, list(data))
class TestConsistencyGroupRemoveVolume(TestConsistencyGroup):
@@ -705,4 +705,4 @@ class TestConsistencyGroupShow(TestConsistencyGroup):
self.consistencygroups_mock.get.assert_called_once_with(
self.consistency_group.id)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
diff --git a/openstackclient/tests/unit/volume/v2/test_qos_specs.py b/openstackclient/tests/unit/volume/v2/test_qos_specs.py
index 073ec570..bc4cee8b 100644
--- a/openstackclient/tests/unit/volume/v2/test_qos_specs.py
+++ b/openstackclient/tests/unit/volume/v2/test_qos_specs.py
@@ -112,7 +112,7 @@ class TestQosCreate(TestQos):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_qos_create_with_consumer(self):
arglist = [
@@ -133,7 +133,7 @@ class TestQosCreate(TestQos):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_qos_create_with_properties(self):
arglist = [
@@ -159,7 +159,7 @@ class TestQosCreate(TestQos):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
class TestQosDelete(TestQos):
@@ -342,7 +342,7 @@ class TestQosList(TestQos):
self.qos_mock.list.assert_called_with()
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_qos_list_no_association(self):
self.qos_mock.reset_mock()
@@ -369,7 +369,7 @@ class TestQosList(TestQos):
format_columns.ListColumn(None),
format_columns.DictColumn(self.qos_specs[1].specs),
)
- self.assertListItemEqual(ex_data, list(data))
+ self.assertItemsEqual(ex_data, list(data))
class TestQosSet(TestQos):
@@ -449,7 +449,7 @@ class TestQosShow(TestQos):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, tuple(data))
+ self.assertItemsEqual(self.data, tuple(data))
class TestQosUnset(TestQos):
diff --git a/openstackclient/tests/unit/volume/v2/test_type.py b/openstackclient/tests/unit/volume/v2/test_type.py
index f13d0851..000464c5 100644
--- a/openstackclient/tests/unit/volume/v2/test_type.py
+++ b/openstackclient/tests/unit/volume/v2/test_type.py
@@ -93,7 +93,7 @@ class TestTypeCreate(TestType):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_type_create_private(self):
arglist = [
@@ -119,7 +119,7 @@ class TestTypeCreate(TestType):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_public_type_create_with_project(self):
arglist = [
@@ -196,7 +196,7 @@ class TestTypeCreate(TestType):
body,
)
self.assertEqual(encryption_columns, columns)
- self.assertItemEqual(encryption_data, data)
+ self.assertItemsEqual(encryption_data, data)
class TestTypeDelete(TestType):
@@ -330,7 +330,7 @@ class TestTypeList(TestType):
columns, data = self.cmd.take_action(parsed_args)
self.types_mock.list.assert_called_once_with(is_public=None)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_type_list_with_options(self):
arglist = [
@@ -348,7 +348,7 @@ class TestTypeList(TestType):
columns, data = self.cmd.take_action(parsed_args)
self.types_mock.list.assert_called_once_with(is_public=True)
self.assertEqual(self.columns_long, columns)
- self.assertListItemEqual(self.data_long, list(data))
+ self.assertItemsEqual(self.data_long, list(data))
def test_type_list_with_private_option(self):
arglist = [
@@ -365,7 +365,7 @@ class TestTypeList(TestType):
columns, data = self.cmd.take_action(parsed_args)
self.types_mock.list.assert_called_once_with(is_public=False)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_type_list_with_default_option(self):
arglist = [
@@ -383,7 +383,7 @@ class TestTypeList(TestType):
columns, data = self.cmd.take_action(parsed_args)
self.types_mock.default.assert_called_once_with()
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data_with_default_type, list(data))
+ self.assertItemsEqual(self.data_with_default_type, list(data))
def test_type_list_with_encryption(self):
encryption_type = volume_fakes.FakeType.create_one_encryption_type(
@@ -427,7 +427,7 @@ class TestTypeList(TestType):
self.encryption_types_mock.list.assert_called_once_with()
self.types_mock.list.assert_called_once_with(is_public=None)
self.assertEqual(encryption_columns, columns)
- self.assertListItemEqual(encryption_data, list(data))
+ self.assertItemsEqual(encryption_data, list(data))
class TestTypeSet(TestType):
@@ -713,7 +713,7 @@ class TestTypeShow(TestType):
self.types_mock.get.assert_called_with(self.volume_type.id)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.data, data)
+ self.assertItemsEqual(self.data, data)
def test_type_show_with_access(self):
arglist = [
@@ -746,7 +746,7 @@ class TestTypeShow(TestType):
private_type.name,
format_columns.DictColumn(private_type.extra_specs)
)
- self.assertItemEqual(private_type_data, data)
+ self.assertItemsEqual(private_type_data, data)
def test_type_show_with_list_access_exec(self):
arglist = [
@@ -778,7 +778,7 @@ class TestTypeShow(TestType):
private_type.name,
format_columns.DictColumn(private_type.extra_specs)
)
- self.assertItemEqual(private_type_data, data)
+ self.assertItemsEqual(private_type_data, data)
def test_type_show_with_encryption(self):
encryption_type = volume_fakes.FakeType.create_one_encryption_type()
@@ -824,7 +824,7 @@ class TestTypeShow(TestType):
self.types_mock.get.assert_called_with(self.volume_type.id)
self.encryption_types_mock.get.assert_called_with(self.volume_type.id)
self.assertEqual(encryption_columns, columns)
- self.assertItemEqual(encryption_data, data)
+ self.assertItemsEqual(encryption_data, data)
class TestTypeUnset(TestType):
diff --git a/openstackclient/tests/unit/volume/v2/test_volume.py b/openstackclient/tests/unit/volume/v2/test_volume.py
index 4e204ad1..b9fe4e83 100644
--- a/openstackclient/tests/unit/volume/v2/test_volume.py
+++ b/openstackclient/tests/unit/volume/v2/test_volume.py
@@ -136,7 +136,7 @@ class TestVolumeCreate(TestVolume):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
def test_volume_create_options(self):
consistency_group = (
@@ -182,7 +182,7 @@ class TestVolumeCreate(TestVolume):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
def test_volume_create_properties(self):
arglist = [
@@ -218,7 +218,7 @@ class TestVolumeCreate(TestVolume):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
def test_volume_create_image_id(self):
image = image_fakes.FakeImage.create_one_image()
@@ -256,7 +256,7 @@ class TestVolumeCreate(TestVolume):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
def test_volume_create_image_name(self):
image = image_fakes.FakeImage.create_one_image()
@@ -294,7 +294,7 @@ class TestVolumeCreate(TestVolume):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
def test_volume_create_with_snapshot(self):
snapshot = volume_fakes.FakeSnapshot.create_one_snapshot()
@@ -331,7 +331,7 @@ class TestVolumeCreate(TestVolume):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
def test_volume_create_with_bootable_and_readonly(self):
arglist = [
@@ -369,7 +369,7 @@ class TestVolumeCreate(TestVolume):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
self.volumes_mock.set_bootable.assert_called_with(
self.new_volume.id, True)
self.volumes_mock.update_readonly_flag.assert_called_with(
@@ -411,7 +411,7 @@ class TestVolumeCreate(TestVolume):
)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
self.volumes_mock.set_bootable.assert_called_with(
self.new_volume.id, False)
self.volumes_mock.update_readonly_flag.assert_called_with(
@@ -463,7 +463,7 @@ class TestVolumeCreate(TestVolume):
self.assertEqual(2, mock_error.call_count)
self.assertEqual(self.columns, columns)
- self.assertItemEqual(self.datalist, data)
+ self.assertItemsEqual(self.datalist, data)
self.volumes_mock.set_bootable.assert_called_with(
self.new_volume.id, True)
self.volumes_mock.update_readonly_flag.assert_called_with(
@@ -680,7 +680,7 @@ class TestVolumeList(TestVolume):
self.mock_volume.size,
volume.AttachmentsColumn(self.mock_volume.attachments),
), )
- self.assertListItemEqual(datalist, tuple(data))
+ self.assertItemsEqual(datalist, tuple(data))
def test_volume_list_project(self):
arglist = [
@@ -720,7 +720,7 @@ class TestVolumeList(TestVolume):
self.mock_volume.size,
volume.AttachmentsColumn(self.mock_volume.attachments),
), )
- self.assertListItemEqual(datalist, tuple(data))
+ self.assertItemsEqual(datalist, tuple(data))
def test_volume_list_project_domain(self):
arglist = [
@@ -762,7 +762,7 @@ class TestVolumeList(TestVolume):
self.mock_volume.size,
volume.AttachmentsColumn(self.mock_volume.attachments),
), )
- self.assertListItemEqual(datalist, tuple(data))
+ self.assertItemsEqual(datalist, tuple(data))
def test_volume_list_user(self):
arglist = [
@@ -801,7 +801,7 @@ class TestVolumeList(TestVolume):
self.mock_volume.size,
volume.AttachmentsColumn(self.mock_volume.attachments),
), )
- self.assertListItemEqual(datalist, tuple(data))
+ self.assertItemsEqual(datalist, tuple(data))
def test_volume_list_user_domain(self):
arglist = [
@@ -843,7 +843,7 @@ class TestVolumeList(TestVolume):
self.mock_volume.size,
volume.AttachmentsColumn(self.mock_volume.attachments),
), )
- self.assertListItemEqual(datalist, tuple(data))
+ self.assertItemsEqual(datalist, tuple(data))
def test_volume_list_name(self):
arglist = [
@@ -883,7 +883,7 @@ class TestVolumeList(TestVolume):
self.mock_volume.size,
volume.AttachmentsColumn(self.mock_volume.attachments),
), )
- self.assertListItemEqual(datalist, tuple(data))
+ self.assertItemsEqual(datalist, tuple(data))
def test_volume_list_status(self):
arglist = [
@@ -923,7 +923,7 @@ class TestVolumeList(TestVolume):
self.mock_volume.size,
volume.AttachmentsColumn(self.mock_volume.attachments),
), )
- self.assertListItemEqual(datalist, tuple(data))
+ self.assertItemsEqual(datalist, tuple(data))
def test_volume_list_all_projects(self):
arglist = [
@@ -963,7 +963,7 @@ class TestVolumeList(TestVolume):
self.mock_volume.size,
volume.AttachmentsColumn(self.mock_volume.attachments),
), )
- self.assertListItemEqual(datalist, tuple(data))
+ self.assertItemsEqual(datalist, tuple(data))
def test_volume_list_long(self):
arglist = [
@@ -1017,7 +1017,7 @@ class TestVolumeList(TestVolume):
volume.AttachmentsColumn(self.mock_volume.attachments),
format_columns.DictColumn(self.mock_volume.metadata),
), )
- self.assertListItemEqual(datalist, tuple(data))
+ self.assertItemsEqual(datalist, tuple(data))
def test_volume_list_with_marker_and_limit(self):
arglist = [
@@ -1056,7 +1056,7 @@ class TestVolumeList(TestVolume):
'name': None,
'all_tenants': False, }
)
- self.assertListItemEqual(datalist, tuple(data))
+ self.assertItemsEqual(datalist, tuple(data))
def test_volume_list_negative_limit(self):
arglist = [
@@ -1450,7 +1450,7 @@ class TestVolumeShow(TestVolume):
volume_fakes.FakeVolume.get_volume_columns(self._volume),
columns)
- self.assertItemEqual(
+ self.assertItemsEqual(
volume_fakes.FakeVolume.get_volume_data(self._volume),
data)
diff --git a/openstackclient/tests/unit/volume/v2/test_volume_backup.py b/openstackclient/tests/unit/volume/v2/test_volume_backup.py
index 4e1f7ee1..13513ed8 100644
--- a/openstackclient/tests/unit/volume/v2/test_volume_backup.py
+++ b/openstackclient/tests/unit/volume/v2/test_volume_backup.py
@@ -314,7 +314,7 @@ class TestBackupList(TestBackup):
limit=None,
)
self.assertEqual(self.columns, columns)
- self.assertListItemEqual(self.data, list(data))
+ self.assertItemsEqual(self.data, list(data))
def test_backup_list_with_options(self):
arglist = [
@@ -353,7 +353,7 @@ class TestBackupList(TestBackup):
limit=3,
)
self.assertEqual(self.columns_long, columns)
- self.assertListItemEqual(self.data_long, list(data))
+ self.assertItemsEqual(self.data_long, list(data))
class TestBackupRestore(TestBackup):
diff --git a/releasenotes/notes/add_id_and_enabled_to_list_identity_provider-e0981063a2dc5961.yaml b/releasenotes/notes/add_id_and_enabled_to_list_identity_provider-e0981063a2dc5961.yaml
new file mode 100644
index 00000000..fccd0a63
--- /dev/null
+++ b/releasenotes/notes/add_id_and_enabled_to_list_identity_provider-e0981063a2dc5961.yaml
@@ -0,0 +1,3 @@
+---
+features:
+ - Add ``--id`` and ``--enabled`` option to ``identity provider list`` command. \ No newline at end of file
diff --git a/releasenotes/notes/fix-openstak-image-save-sdk-port-eb160e8ffc92e514.yaml b/releasenotes/notes/fix-openstak-image-save-sdk-port-eb160e8ffc92e514.yaml
new file mode 100644
index 00000000..857f3c50
--- /dev/null
+++ b/releasenotes/notes/fix-openstak-image-save-sdk-port-eb160e8ffc92e514.yaml
@@ -0,0 +1,7 @@
+---
+fixes:
+ - Stream image download to avoid buffering data in memory which rapidly
+ exhausts memory resulting in OOM kill or system crash for all but the
+ smallest of images. Fixes https://storyboard.openstack.org/#!/story/2007672
+ - Restore default behavior of 'openstack image save' to send data to stdout
+ Relates to https://storyboard.openstack.org/#!/story/2007672. \ No newline at end of file
diff --git a/releasenotes/notes/remove-nlbaas-quota-8b38e0c91ab113cb.yaml b/releasenotes/notes/remove-nlbaas-quota-8b38e0c91ab113cb.yaml
new file mode 100644
index 00000000..572e215b
--- /dev/null
+++ b/releasenotes/notes/remove-nlbaas-quota-8b38e0c91ab113cb.yaml
@@ -0,0 +1,4 @@
+---
+other:
+ - |
+ Remove deprecated neutron-lbaas results from ``quota show`` command.
diff --git a/releasenotes/notes/switch-aggregate-to-sdk-ced451a0f28bf6ea.yaml b/releasenotes/notes/switch-aggregate-to-sdk-ced451a0f28bf6ea.yaml
new file mode 100644
index 00000000..0df2d635
--- /dev/null
+++ b/releasenotes/notes/switch-aggregate-to-sdk-ced451a0f28bf6ea.yaml
@@ -0,0 +1,4 @@
+---
+features:
+ - Switch aggregate operations to use SDK
+ - Adds 'aggregate cache image' operation
diff --git a/releasenotes/notes/switch-flavor-to-sdk-b874a3c39559815e.yaml b/releasenotes/notes/switch-flavor-to-sdk-b874a3c39559815e.yaml
new file mode 100644
index 00000000..7863c323
--- /dev/null
+++ b/releasenotes/notes/switch-flavor-to-sdk-b874a3c39559815e.yaml
@@ -0,0 +1,4 @@
+---
+features:
+ - Switch compute.flavor operations from direct API calls (novaclient) to
+ OpenStackSDK.
diff --git a/requirements.txt b/requirements.txt
index 9430a7fd..ed55ce37 100644
--- a/requirements.txt
+++ b/requirements.txt
@@ -3,10 +3,10 @@
# process, which may cause wedges in the gate later.
pbr!=2.1.0,>=2.0.0 # Apache-2.0
-cliff>=3.4.0 # Apache-2.0
+cliff>=3.5.0 # Apache-2.0
iso8601>=0.1.11 # MIT
-openstacksdk>=0.51.0 # Apache-2.0
-osc-lib>=2.2.0 # Apache-2.0
+openstacksdk>=0.52.0 # Apache-2.0
+osc-lib>=2.3.0 # Apache-2.0
oslo.i18n>=3.15.3 # Apache-2.0
python-keystoneclient>=3.22.0 # Apache-2.0
python-novaclient>=15.1.0 # Apache-2.0
diff --git a/setup.cfg b/setup.cfg
index a29852e3..9299fb91 100644
--- a/setup.cfg
+++ b/setup.cfg
@@ -65,6 +65,7 @@ openstack.compute.v2 =
aggregate_set = openstackclient.compute.v2.aggregate:SetAggregate
aggregate_show = openstackclient.compute.v2.aggregate:ShowAggregate
aggregate_unset = openstackclient.compute.v2.aggregate:UnsetAggregate
+ aggregate_cache_image = openstackclient.compute.v2.aggregate:CacheImageForAggregate
compute_service_delete = openstackclient.compute.v2.service:DeleteService
compute_service_list = openstackclient.compute.v2.service:ListService
diff --git a/test-requirements.txt b/test-requirements.txt
index 3dce687b..8b61a5c0 100644
--- a/test-requirements.txt
+++ b/test-requirements.txt
@@ -1,10 +1,8 @@
# The order of packages is significant, because pip processes them in the order
# of appearance. Changing the order has an impact on the overall integration
# process, which may cause wedges in the gate later.
-hacking>=2.0.0 # Apache-2.0
coverage!=4.4,>=4.0 # Apache-2.0
fixtures>=3.0.0 # Apache-2.0/BSD
-flake8-import-order>=0.13 # LGPLv3
oslotest>=3.2.0 # Apache-2.0
requests>=2.14.2 # Apache-2.0
requests-mock>=1.2.0 # Apache-2.0
@@ -12,6 +10,5 @@ stestr>=1.0.0 # Apache-2.0
testtools>=2.2.0 # MIT
tempest>=17.1.0 # Apache-2.0
osprofiler>=1.4.0 # Apache-2.0
-bandit!=1.6.0,>=1.1.0 # Apache-2.0
wrapt>=1.7.0 # BSD License
ddt>=1.0.1 # MIT
diff --git a/tox.ini b/tox.ini
index 663463e2..ebcdc2d5 100644
--- a/tox.ini
+++ b/tox.ini
@@ -28,9 +28,13 @@ commands =
{toxinidir}/tools/fast8.sh
[testenv:pep8]
+deps =
+ hacking>=2.0.0
+ bandit!=1.6.0,>=1.1.0
+ flake8-import-order>=0.13 # LGPLv3
commands =
- flake8
- bandit -r openstackclient -x tests -s B105,B106,B107,B401,B404,B603,B606,B607,B110,B605,B101
+ flake8
+ bandit -r openstackclient -x tests -s B105,B106,B107,B401,B404,B603,B606,B607,B110,B605,B101
[testenv:bandit]
# This command runs the bandit security linter against the openstackclient