Add bare parameter to get/list/search server

The bare parameter tells shade to skip all additional calls it makes to
fill in extra information on the server record from other services, such
as fixing the addresses dict. This is useful internally in shade where
there are times when one is getting the server dict just to get its id
so other operations, such as getting the console log or attaching
security groups, can be performed.

Change-Id: Ic9cc6e8be4f4e30f76d3abb655d9a3cf0cb9918b
This commit is contained in:
Monty Taylor 2017-03-29 03:53:14 -05:00
parent 8aa8688ba8
commit c1984b636e
No known key found for this signature in database
GPG Key ID: 7BAE94BC7141A594
2 changed files with 42 additions and 27 deletions

View File

@ -1566,9 +1566,9 @@ class OpenStackCloud(_normalize.Normalizer):
def search_servers( def search_servers(
self, name_or_id=None, filters=None, detailed=False, self, name_or_id=None, filters=None, detailed=False,
all_projects=False): all_projects=False, bare=False):
servers = self.list_servers( servers = self.list_servers(
detailed=detailed, all_projects=all_projects) detailed=detailed, all_projects=all_projects, bare=bare)
return _utils._filter_list(servers, name_or_id, filters) return _utils._filter_list(servers, name_or_id, filters)
def search_server_groups(self, name_or_id=None, filters=None): def search_server_groups(self, name_or_id=None, filters=None):
@ -1845,9 +1845,18 @@ class OpenStackCloud(_normalize.Normalizer):
_tasks.NovaSecurityGroupList(search_opts=filters)) _tasks.NovaSecurityGroupList(search_opts=filters))
return self._normalize_secgroups(groups) return self._normalize_secgroups(groups)
def list_servers(self, detailed=False, all_projects=False): def list_servers(self, detailed=False, all_projects=False, bare=False):
"""List all available servers. """List all available servers.
:param detailed: Whether or not to add detailed additional information.
Defaults to False.
:param all_projects: Whether to list servers from all projects or just
the current auth scoped project.
:param bare: Whether to skip adding any additional information to the
server record. Defaults to False, meaning the addresses
dict will be populated as needed from neutron. Setting
to True implies detailed = False.
:returns: A list of server ``munch.Munch``. :returns: A list of server ``munch.Munch``.
""" """
@ -1865,13 +1874,14 @@ class OpenStackCloud(_normalize.Normalizer):
if not (first_run and self._servers is not None): if not (first_run and self._servers is not None):
self._servers = self._list_servers( self._servers = self._list_servers(
detailed=detailed, detailed=detailed,
all_projects=all_projects) all_projects=all_projects,
bare=bare)
self._servers_time = time.time() self._servers_time = time.time()
finally: finally:
self._servers_lock.release() self._servers_lock.release()
return self._servers return self._servers
def _list_servers(self, detailed=False, all_projects=False): def _list_servers(self, detailed=False, all_projects=False, bare=False):
with _utils.shade_exceptions( with _utils.shade_exceptions(
"Error fetching server list on {cloud}:{region}:".format( "Error fetching server list on {cloud}:{region}:".format(
cloud=self.name, cloud=self.name,
@ -1882,7 +1892,9 @@ class OpenStackCloud(_normalize.Normalizer):
servers = self._normalize_servers( servers = self._normalize_servers(
self.manager.submit_task(_tasks.ServerList(**kwargs))) self.manager.submit_task(_tasks.ServerList(**kwargs)))
if detailed: if bare:
return servers
elif detailed:
return [ return [
meta.get_hostvars_from_server(self, server) meta.get_hostvars_from_server(self, server)
for server in servers for server in servers
@ -2611,7 +2623,7 @@ class OpenStackCloud(_normalize.Normalizer):
""" """
if not isinstance(server, dict): if not isinstance(server, dict):
server = self.get_server(server) server = self.get_server(server, bare=True)
if not server: if not server:
raise OpenStackCloudException( raise OpenStackCloudException(
@ -2624,7 +2636,8 @@ class OpenStackCloud(_normalize.Normalizer):
except OpenStackCloudBadRequest: except OpenStackCloudBadRequest:
return "" return ""
def get_server(self, name_or_id=None, filters=None, detailed=False): def get_server(
self, name_or_id=None, filters=None, detailed=False, bare=False):
"""Get a server by name or ID. """Get a server by name or ID.
:param name_or_id: Name or ID of the server. :param name_or_id: Name or ID of the server.
@ -2642,13 +2655,19 @@ class OpenStackCloud(_normalize.Normalizer):
OR OR
A string containing a jmespath expression for further filtering. A string containing a jmespath expression for further filtering.
Example:: "[?last_name==`Smith`] | [?other.gender]==`Female`]" Example:: "[?last_name==`Smith`] | [?other.gender]==`Female`]"
:param detailed: Whether or not to add detailed additional information.
Defaults to False.
:param bare: Whether to skip adding any additional information to the
server record. Defaults to False, meaning the addresses
dict will be populated as needed from neutron. Setting
to True implies detailed = False.
:returns: A server ``munch.Munch`` or None if no matching server is :returns: A server ``munch.Munch`` or None if no matching server is
found. found.
""" """
searchfunc = functools.partial(self.search_servers, searchfunc = functools.partial(self.search_servers,
detailed=detailed) detailed=detailed, bare=bare)
return _utils._get_entity(searchfunc, name_or_id, filters) return _utils._get_entity(searchfunc, name_or_id, filters)
def get_server_by_id(self, id): def get_server_by_id(self, id):
@ -3198,7 +3217,7 @@ class OpenStackCloud(_normalize.Normalizer):
:raises: OpenStackCloudException if there are problems uploading :raises: OpenStackCloudException if there are problems uploading
""" """
if not isinstance(server, dict): if not isinstance(server, dict):
server_obj = self.get_server(server) server_obj = self.get_server(server, bare=True)
if not server_obj: if not server_obj:
raise OpenStackCloudException( raise OpenStackCloudException(
"Server {server} could not be found and therefore" "Server {server} could not be found and therefore"
@ -4231,7 +4250,7 @@ class OpenStackCloud(_normalize.Normalizer):
return True return True
def get_server_id(self, name_or_id): def get_server_id(self, name_or_id):
server = self.get_server(name_or_id) server = self.get_server(name_or_id, bare=True)
if server: if server:
return server['id'] return server['id']
return None return None
@ -5533,7 +5552,8 @@ class OpenStackCloud(_normalize.Normalizer):
""" """
try: try:
self.manager.submit_task( self.manager.submit_task(
_tasks.ServerSetMetadata(server=self.get_server(name_or_id), _tasks.ServerSetMetadata(
server=self.get_server(name_or_id, bare=True),
metadata=metadata)) metadata=metadata))
except OpenStackCloudException: except OpenStackCloudException:
raise raise
@ -5553,7 +5573,8 @@ class OpenStackCloud(_normalize.Normalizer):
""" """
try: try:
self.manager.submit_task( self.manager.submit_task(
_tasks.ServerDeleteMetadata(server=self.get_server(name_or_id), _tasks.ServerDeleteMetadata(
server=self.get_server(name_or_id, bare=True),
keys=metadata_keys)) keys=metadata_keys))
except OpenStackCloudException: except OpenStackCloudException:
raise raise
@ -5579,7 +5600,8 @@ class OpenStackCloud(_normalize.Normalizer):
:raises: OpenStackCloudException on operation error. :raises: OpenStackCloudException on operation error.
""" """
server = self.get_server(name_or_id) # If delete_ips is True, we need the server to not be bare.
server = self.get_server(name_or_id, bare=not delete_ips)
if not server: if not server:
return False return False
@ -5652,7 +5674,7 @@ class OpenStackCloud(_normalize.Normalizer):
# to be friendly with the server. # to be friendly with the server.
wait=self._SERVER_AGE or 2): wait=self._SERVER_AGE or 2):
with _utils.shade_exceptions("Error in deleting server"): with _utils.shade_exceptions("Error in deleting server"):
server = self.get_server(server['id']) server = self.get_server(server['id'], bare=True)
if not server: if not server:
break break
@ -5677,13 +5699,14 @@ class OpenStackCloud(_normalize.Normalizer):
:raises: OpenStackCloudException on operation error. :raises: OpenStackCloudException on operation error.
""" """
server = self.get_server(name_or_id=name_or_id) server = self.get_server(name_or_id=name_or_id, bare=True)
if server is None: if server is None:
raise OpenStackCloudException( raise OpenStackCloudException(
"failed to find server '{server}'".format(server=name_or_id)) "failed to find server '{server}'".format(server=name_or_id))
with _utils.shade_exceptions( with _utils.shade_exceptions(
"Error updating server {0}".format(name_or_id)): "Error updating server {0}".format(name_or_id)):
# TODO(mordred) This is not sending back a normalized server
return self.manager.submit_task( return self.manager.submit_task(
_tasks.ServerUpdate( _tasks.ServerUpdate(
server=server['id'], **kwargs)) server=server['id'], **kwargs))

View File

@ -11,10 +11,8 @@
# under the License. # under the License.
import mock
import uuid import uuid
import shade
from shade.tests.unit import base from shade.tests.unit import base
from shade.tests import fakes from shade.tests import fakes
@ -45,13 +43,7 @@ class TestServerConsole(base.RequestsMockTestCase):
self.output, self.cloud.get_server_console(self.server)) self.output, self.cloud.get_server_console(self.server))
self.assert_calls() self.assert_calls()
@mock.patch.object(shade.OpenStackCloud, 'has_service') def test_get_server_console_name_or_id(self):
def test_get_server_console_name_or_id(self, mock_has_service):
# Turn off neutron for now - we don't _actually_ want to show all
# of the nova normalization calls.
# TODO(mordred) Tell get_server_console to tell shade to skip
# adding normalization, since we don't consume them
mock_has_service.return_value = False
self.register_uris([ self.register_uris([
dict(method='GET', dict(method='GET',