def wait_for_server_creation(self, server_id): """ @summary: Waits for a server to be created successfully @param server_id: The uuid of the server @type server_id: String @return: A server object after it has been successfully built @rtype: Server """ verifier = StatusProgressionVerifier( 'server', server_id, lambda id_: self.verify_entity( self.servers_client.get_server(id_)).status, server_id) verifier.set_global_state_properties( timeout=self.config.server_build_timeout) verifier.add_state(expected_statuses=[ServerStates.BUILD], acceptable_statuses=[ServerStates.ACTIVE], error_statuses=[ServerStates.ERROR], poll_rate=self.config.server_status_interval) verifier.add_state(expected_statuses=[ServerStates.ACTIVE], error_statuses=[ServerStates.ERROR], poll_rate=self.config.server_status_interval) verifier.start() response = self.servers_client.get_server(server_id) return self.verify_entity(response)
def verify_volume_suceeded(self, volume_id, volume_size): """Raises an exception if the volume doesn't pass through the normal expected series of states for a volume create. """ timeout = self.volumes.behaviors.calculate_volume_clone_timeout( volume_size) verifier = StatusProgressionVerifier( 'volume', volume_id, self.volumes.behaviors.get_volume_status, volume_id) verifier.add_state( expected_statuses=[statuses.Volume.CREATING], acceptable_statuses=[statuses.Volume.AVAILABLE], error_statuses=[statuses.Volume.ERROR], timeout=self.volumes.config.volume_clone_min_timeout, poll_rate=self.volumes.config.volume_status_poll_frequency, poll_failure_retry_limit=3) verifier.add_state( expected_statuses=[statuses.Volume.AVAILABLE], error_statuses=[statuses.Volume.ERROR], timeout=timeout, poll_rate=self.volumes.config.volume_status_poll_frequency, poll_failure_retry_limit=3) verifier.start()
def wait_for_server_creation(self, server_id): """ @summary: Waits for a server to be created successfully @param server_id: The uuid of the server @type server_id: String @return: A server object after it has been successfully built @rtype: Server """ verifier = StatusProgressionVerifier( 'server', server_id, lambda id_: self.verify_entity( self.servers_client.get_server(id_)).status, server_id) retry_limit = self.config.server_status_poll_failure_max_retries verifier.set_global_state_properties( timeout=self.config.server_build_timeout) verifier.add_state( expected_statuses=[ServerStates.BUILD], acceptable_statuses=[ServerStates.ACTIVE], error_statuses=[ServerStates.ERROR], poll_rate=self.config.server_status_interval, poll_failure_retry_limit=retry_limit) verifier.add_state( expected_statuses=[ServerStates.ACTIVE], error_statuses=[ServerStates.ERROR], poll_rate=self.config.server_status_interval, poll_failure_retry_limit=retry_limit) try: verifier.start() except (StatusProgressionError, StatusPollError) as e: if not e.args: e.args=('',) e.args = ( 'Failed to create server with instance ' 'id {id}'.format(id=server_id),) + e.args e.args = ('; '.join(e.args),) raise except Exception as e: if not e.args: e.args=('',) e.args = ( 'Unexpected error occurred while waiting for server {id}' 'to be created.'.format(id=server_id),) + e.args e.args = ('; '.join(e.args),) raise response = self.servers_client.get_server(server_id) return self.verify_entity(response)
def verify_volume_has_errored(self, volume_id): """Raises an exception if the volume doesn't enter the "error" state, or becomes unexpectedly "available" """ verifier = StatusProgressionVerifier( 'volume', volume_id, self.volumes.behaviors.get_volume_status, volume_id) verifier.add_state( expected_statuses=[statuses.Volume.ERROR], error_statuses=[statuses.Volume.AVAILABLE], timeout=self.volumes.config.volume_clone_min_timeout, poll_rate=self.volumes.config.volume_status_poll_frequency, poll_failure_retry_limit=3) verifier.start()
def wait_for_server_creation(self, server_id): """ @summary: Waits for a server to be created successfully @param server_id: The uuid of the server @type server_id: String @return: A server object after it has been successfully built @rtype: Server """ verifier = StatusProgressionVerifier( 'server', server_id, lambda id_: self.verify_entity( self.servers_client.get_server(id_)).status, server_id) retry_limit = self.config.server_status_poll_failure_max_retries verifier.set_global_state_properties( timeout=self.config.server_build_timeout) verifier.add_state(expected_statuses=[ServerStates.BUILD], acceptable_statuses=[ServerStates.ACTIVE], error_statuses=[ServerStates.ERROR], poll_rate=self.config.server_status_interval, poll_failure_retry_limit=retry_limit) verifier.add_state(expected_statuses=[ServerStates.ACTIVE], error_statuses=[ServerStates.ERROR], poll_rate=self.config.server_status_interval, poll_failure_retry_limit=retry_limit) try: verifier.start() except (StatusProgressionError, StatusPollError) as e: if not e.args: e.args = ('', ) e.args = ('Failed to create server with instance ' 'id {id}'.format(id=server_id), ) + e.args e.args = ('; '.join(e.args), ) raise except Exception as e: if not e.args: e.args = ('', ) e.args = ('Unexpected error occurred while waiting for server {id}' 'to be created.'.format(id=server_id), ) + e.args e.args = ('; '.join(e.args), ) raise response = self.servers_client.get_server(server_id) return self.verify_entity(response)
def verify_volume_status_progression_during_attachment( self, volume_id, state_list=None): def _get_volume_status(self, volume_id): resp = self.volumes_client.get_volume_info(volume_id=volume_id) if not resp.ok: msg = ("get_volume_status() failure: get_volume_info() call" " failed with a {0} status code".format( resp.status_code)) self._log.error(msg) raise Exception(msg) if resp.entity is None: msg = ("get_volume_status() failure: unable to deserialize" " response from get_volume_info() call") self._log.error(msg) raise Exception(msg) return resp.entity.status verifier = StatusProgressionVerifier('volume', volume_id, _get_volume_status, *[self, volume_id]) #verifier.add_state(status, timeout, pollrate, retries, transient) verifier.add_state(expected_statuses=['available'], acceptable_statuses=['attaching', 'in-use'], error_statuses=['error', 'creating'], timeout=10, poll_rate=1, poll_failure_retry_limit=3) verifier.add_state(expected_statuses=['attaching'], acceptable_statuses=['in-use'], error_statuses=['error', 'creating'], timeout=self.config.attachment_timeout, poll_rate=self.config.api_poll_rate, poll_failure_retry_limit=3) verifier.add_state(expected_statuses=['in-use'], error_statuses=['available', 'error', 'creating'], timeout=self.config.attachment_timeout, poll_rate=self.config.api_poll_rate, poll_failure_retry_limit=3) verifier.start()
def create_available_volume( self, size, volume_type, name=None, description=None, availability_zone=None, metadata=None, bootable=None, image_ref=None, snapshot_id=None, source_volid=None, timeout=None, ): metadata = metadata or {} timeout = timeout or self.calculate_volume_create_timeout(size) self._log.info("create_available_volume() is creating a volume") resp = self.create_volume( size, volume_type, name=name, description=description, availability_zone=availability_zone, metadata=metadata, bootable=bootable, image_ref=image_ref, snapshot_id=snapshot_id, source_volid=source_volid, ) volume = self._verify_entity(resp) # Verify volume progression from 'creating' to 'available' verifier = StatusProgressionVerifier("volume", volume.id_, self.get_volume_status, volume.id_) verifier.add_state( expected_statuses=[self.statuses.Volume.CREATING], acceptable_statuses=[self.statuses.Volume.AVAILABLE], error_statuses=[self.statuses.Volume.ERROR], timeout=self.config.volume_create_min_timeout, poll_rate=1, ) verifier.add_state( expected_statuses=[self.statuses.Volume.AVAILABLE], error_statuses=[self.statuses.Volume.ERROR], timeout=timeout, poll_rate=1, ) verifier.start() # Return volume model resp = self.client.get_volume_info(volume.id_) volume = self._verify_entity(resp) return volume
def create_available_volume(self, size, volume_type, name=None, description=None, availability_zone=None, metadata=None, bootable=None, image_ref=None, snapshot_id=None, source_volid=None, timeout=None): metadata = metadata or {} timeout = timeout or self.calculate_volume_create_timeout(size) self._log.info("create_available_volume() is creating a volume") resp = self.create_volume(size, volume_type, name=name, description=description, availability_zone=availability_zone, metadata=metadata, bootable=bootable, image_ref=image_ref, snapshot_id=snapshot_id, source_volid=source_volid) volume = self._verify_entity(resp) # Verify volume progression from 'creating' to 'available' verifier = StatusProgressionVerifier('volume', volume.id_, self.get_volume_status, volume.id_) verifier.add_state( expected_statuses=[self.statuses.Volume.CREATING], acceptable_statuses=[self.statuses.Volume.AVAILABLE], error_statuses=[self.statuses.Volume.ERROR], timeout=self.config.volume_create_min_timeout, poll_rate=1) verifier.add_state(expected_statuses=[self.statuses.Volume.AVAILABLE], error_statuses=[self.statuses.Volume.ERROR], timeout=timeout, poll_rate=1) verifier.start() # Return volume model resp = self.client.get_volume_info(volume.id_) volume = self._verify_entity(resp) return volume
def create_available_snapshot(self, volume_id, name=None, description=None, force_create=True, timeout=None): # Try and get volume size to calculate minimum wait time vol_size = None if not timeout: try: resp = self.client.get_volume_info(volume_id) self._verify_entity(resp) vol_size = resp.entity.size except: # If volume size isn't available, timeout defaults to # a non-optimized value pass timeout = self.calculate_snapshot_create_timeout(vol_size) self._log.debug( "create_available_snapshot() timeout set to {0}".format(timeout)) # Create the snaphsot self._log.info("create_available_snapshot is creating a snapshot") resp = self.create_snapshot(volume_id, force_create=force_create, name=name, description=description) self._verify_entity(resp) # Verify snapshot status progression snapshot = resp.entity verifier = StatusProgressionVerifier('snapshot', snapshot.id_, self.get_snapshot_status, snapshot.id_) verifier.add_state( expected_statuses=[self.statuses.Snapshot.CREATING], acceptable_statuses=[self.statuses.Snapshot.AVAILABLE], error_statuses=[self.statuses.Snapshot.ERROR], timeout=self.config.snapshot_create_min_timeout, poll_rate=1) verifier.add_state( expected_statuses=[self.statuses.Snapshot.AVAILABLE], error_statuses=[self.statuses.Snapshot.ERROR], timeout=timeout, poll_rate=self.config.snapshot_status_poll_frequency) verifier.start() # Return snapshot model resp = self.client.get_snapshot_info(snapshot.id_) snapshot = self._verify_entity(resp) return snapshot
def verify_volume_status_progression_during_attachment( self, volume_id, state_list=None): def _get_volume_status(self, volume_id): resp = self.volumes_client.get_volume_info(volume_id=volume_id) if not resp.ok: msg = ( "get_volume_status() failure: get_volume_info() call" " failed with a {0} status code".format(resp.status_code)) self._log.error(msg) raise Exception(msg) if resp.entity is None: msg = ( "get_volume_status() failure: unable to deserialize" " response from get_volume_info() call") self._log.error(msg) raise Exception(msg) return resp.entity.status verifier = StatusProgressionVerifier( 'volume', volume_id, _get_volume_status, *[self, volume_id]) #verifier.add_state(status, timeout, pollrate, retries, transient) verifier.add_state( expected_statuses=['available'], acceptable_statuses=['attaching', 'in-use'], error_statuses=['error', 'creating'], timeout=10, poll_rate=1, poll_failure_retry_limit=3) verifier.add_state( expected_statuses=['attaching'], acceptable_statuses=['in-use'], error_statuses=['error', 'creating'], timeout=self.config.attachment_timeout, poll_rate=self.config.api_poll_rate, poll_failure_retry_limit=3) verifier.add_state( expected_statuses=['in-use'], error_statuses=['available', 'error', 'creating'], timeout=self.config.attachment_timeout, poll_rate=self.config.api_poll_rate, poll_failure_retry_limit=3) verifier.start()
def create_task_with_transitions_failure(self, input_, task_type, final_status=None): """ @summary: Create a task and verify that it transitions through the expected statuses for a failure scenario """ response = self.client.create_task(input_=input_, type_=task_type) task = response.entity # Verify task progresses as expected verifier = StatusProgressionVerifier('task', task.id_, self.get_task_status, task.id_) verifier.add_state( expected_statuses=[TaskStatus.PENDING], acceptable_statuses=[TaskStatus.PROCESSING, TaskStatus.FAILURE], error_statuses=[TaskStatus.SUCCESS], timeout=self.config.task_timeout, poll_rate=1) verifier.add_state( expected_statuses=[TaskStatus.PROCESSING], acceptable_statuses=[TaskStatus.FAILURE], error_statuses=[TaskStatus.PENDING, TaskStatus.SUCCESS], timeout=self.config.task_timeout, poll_rate=1) if final_status == TaskStatus.FAILURE: verifier.add_state( expected_statuses=[TaskStatus.FAILURE], error_statuses=[TaskStatus.PENDING, TaskStatus.SUCCESS], timeout=self.config.task_timeout, poll_rate=1) verifier.start() response = self.client.get_task(task.id_) return response.entity
def verify_snapshot_build_has_errored(self, snapshot_id, timeout): """ Raises an exception if the snapshot does not enter the "error" state, or becomes unexpectedly "available" """ verifier = StatusProgressionVerifier( 'snapshot', snapshot_id, self.volumes.behaviors.get_snapshot_status, snapshot_id) # Every known status that isn't 'ERROR' is added to the error statuses error_statuses = statuses.Snapshot.values() error_statuses.remove(statuses.Snapshot.ERROR) error_statuses.remove(statuses.Snapshot.CREATING) verifier.add_state( expected_statuses=[statuses.Snapshot.ERROR], error_statuses=error_statuses, timeout=timeout, poll_rate=self.volumes.config.snapshot_status_poll_frequency, poll_failure_retry_limit=3) verifier.start()
def verify_image_creation_progression(self, image_id): verifier = StatusProgressionVerifier( 'image', image_id, lambda id_: self.verify_entity( self.images_client.get_image(id_)).status, image_id) verifier.set_global_state_properties( timeout=self.config.snapshot_timeout) verifier.add_state( expected_statuses=[ImageStates.SAVING], acceptable_statuses=[ImageStates.ACTIVE], error_statuses=[ImageStates.ERROR, ImageStates.DELETED], poll_rate=self.config.image_status_interval) verifier.add_state( expected_statuses=[ImageStates.ACTIVE], error_statuses=[ImageStates.ERROR, ImageStates.DELETED], poll_rate=self.config.image_status_interval) verifier.start() response = self.images_client.get_image(image_id) return self.verify_entity(response)
def verify_volume_availability(cls, volume): verifier = StatusProgressionVerifier('volume', volume.id_, cls.get_volume_status, volume.id_) verifier.add_state(expected_statuses=[statuses.Volume.CREATING], acceptable_statuses=[statuses.Volume.AVAILABLE], error_statuses=[statuses.Volume.ERROR], timeout=1800, poll_rate=10) verifier.add_state(expected_statuses=[statuses.Volume.AVAILABLE], error_statuses=[statuses.Volume.ERROR], timeout=1800, poll_rate=10) verifier.start()
def wait_for_snapshot_status( self, snapshot_id, expected_status, timeout, poll_rate=None): verifier = StatusProgressionVerifier( 'snapshot', snapshot_id, self.get_snapshot_status, snapshot_id) verifier.set_global_state_properties(timeout) verifier.add_state( expected_statuses=[expected_status], poll_rate=self.config.snapshot_status_poll_frequency, poll_failure_retry_limit= self.config.snapshot_status_poll_failure_max_retries) verifier.start()
def verify_volume_create_status_progresion(self, volume_id, timeout): """Raises an exception if the volume doesn't pass through the normal expected series of states for a volume create. """ verifier = StatusProgressionVerifier('volume', volume_id, self.get_volume_status, volume_id) verifier.set_global_state_properties(timeout) verifier.add_state( expected_statuses=[self.statuses.Volume.CREATING], acceptable_statuses=[self.statuses.Volume.AVAILABLE], error_statuses=[self.statuses.Volume.ERROR], poll_rate=self.config.volume_status_poll_frequency, poll_failure_retry_limit=( self.config.volume_status_poll_failure_max_retries)) verifier.add_state( expected_statuses=[self.statuses.Volume.AVAILABLE], error_statuses=[self.statuses.Volume.ERROR], poll_rate=self.config.volume_status_poll_frequency, poll_failure_retry_limit=( self.config.volume_status_poll_failure_max_retries)) verifier.start()
def verify_snapshot_create_status_progression(self, snapshot_id, timeout): verifier = StatusProgressionVerifier( 'snapshot', snapshot_id, self.get_snapshot_status, snapshot_id) verifier.add_state( expected_statuses=[self.statuses.Snapshot.CREATING], acceptable_statuses=[self.statuses.Snapshot.AVAILABLE], error_statuses=[self.statuses.Snapshot.ERROR], timeout=self.config.snapshot_create_min_timeout, poll_rate=1) verifier.add_state( expected_statuses=[self.statuses.Snapshot.AVAILABLE], error_statuses=[self.statuses.Snapshot.ERROR], timeout=timeout, poll_rate=self.config.snapshot_status_poll_frequency) verifier.start()
def create_available_snapshot( self, volume_id, name=None, description=None, force_create=True, timeout=None): # Try and get volume size to calculate minimum wait time vol_size = None if not timeout: try: resp = self.client.get_volume_info(volume_id) self._verify_entity(resp) vol_size = resp.entity.size except: # If volume size isn't available, timeout defaults to # a non-optimized value pass timeout = self.calculate_snapshot_create_timeout(vol_size) self._log.debug( "create_available_snapshot() timeout set to {0}".format(timeout)) # Create the snaphsot self._log.info("create_available_snapshot is creating a snapshot") resp = self.create_snapshot( volume_id, force_create=force_create, name=name, description=description) self._verify_entity(resp) # Verify snapshot status progression snapshot = resp.entity verifier = StatusProgressionVerifier( 'snapshot', snapshot.id_, self.get_snapshot_status, snapshot.id_) verifier.add_state( expected_statuses=[self.statuses.Snapshot.CREATING], acceptable_statuses=[self.statuses.Snapshot.AVAILABLE], error_statuses=[self.statuses.Snapshot.ERROR], timeout=self.config.snapshot_create_min_timeout, poll_rate=1) verifier.add_state( expected_statuses=[self.statuses.Snapshot.AVAILABLE], error_statuses=[self.statuses.Snapshot.ERROR], timeout=timeout, poll_rate=self.config.snapshot_status_poll_frequency) verifier.start() # Return snapshot model resp = self.client.get_snapshot_info(snapshot.id_) snapshot = self._verify_entity(resp) return snapshot
def create_task_with_transitions(self, input_, task_type, final_status=None): """ @summary: Create a task and verify that it transitions through the expected statuses """ response = self.client.create_task( input_=input_, type_=task_type) task = response.entity # Verify task progresses as expected verifier = StatusProgressionVerifier( 'task', task.id_, self.get_task_status, task.id_) verifier.add_state( expected_statuses=[TaskStatus.PENDING], acceptable_statuses=[TaskStatus.PROCESSING, TaskStatus.SUCCESS], error_statuses=[TaskStatus.FAILURE], timeout=self.config.task_timeout, poll_rate=1) verifier.add_state( expected_statuses=[TaskStatus.PROCESSING], acceptable_statuses=[TaskStatus.SUCCESS], error_statuses=[TaskStatus.FAILURE], timeout=self.config.task_timeout, poll_rate=1) if final_status == TaskStatus.SUCCESS: verifier.add_state( expected_statuses=[TaskStatus.SUCCESS], error_statuses=[TaskStatus.FAILURE], timeout=self.config.task_timeout, poll_rate=1) verifier.start() response = self.client.get_task(task.id_) return response.entity
def verify_volume_create_status_progresion(self, volume_id, timeout): """Raises an exception if the volume doesn't pass through the normal expected series of states for a volume create. """ verifier = StatusProgressionVerifier( 'volume', volume_id, self.get_volume_status, volume_id) verifier.set_global_state_properties(timeout) verifier.add_state( expected_statuses=[self.statuses.Volume.CREATING], acceptable_statuses=[self.statuses.Volume.AVAILABLE], error_statuses=[self.statuses.Volume.ERROR], poll_rate=self.config.volume_status_poll_frequency, poll_failure_retry_limit= self.config.volume_status_poll_failure_max_retries) verifier.add_state( expected_statuses=[self.statuses.Volume.AVAILABLE], error_statuses=[self.statuses.Volume.ERROR], poll_rate=self.config.volume_status_poll_frequency, poll_failure_retry_limit= self.config.volume_status_poll_failure_max_retries) verifier.start()
def wait_for_snapshot_status(self, snapshot_id, expected_status, timeout, poll_rate=None): """ This method can end up polling for the entire timeout if the snapshot enters a permament unexpected state. It's been included for backwards compatibility only and should generally be avoided.""" verifier = StatusProgressionVerifier('snapshot', snapshot_id, self.get_snapshot_status, snapshot_id) verifier.set_global_state_properties(timeout) verifier.add_state( expected_statuses=[expected_status], poll_rate=self.config.snapshot_status_poll_frequency, poll_failure_retry_limit=( self.config.snapshot_status_poll_failure_max_retries)) verifier.start()
def verify_snapshot_create_status_progression(self, snapshot_id, timeout): verifier = StatusProgressionVerifier('snapshot', snapshot_id, self.get_snapshot_status, snapshot_id) verifier.add_state( expected_statuses=[self.statuses.Snapshot.CREATING], acceptable_statuses=[self.statuses.Snapshot.AVAILABLE], error_statuses=[self.statuses.Snapshot.ERROR], timeout=self.config.snapshot_create_min_timeout, poll_rate=self.config.snapshot_status_poll_frequency, poll_failure_retry_limit=( self.config.snapshot_status_poll_failure_max_retries)) verifier.add_state( expected_statuses=[self.statuses.Snapshot.AVAILABLE], error_statuses=[self.statuses.Snapshot.ERROR], timeout=timeout, poll_rate=self.config.snapshot_status_poll_frequency, poll_failure_retry_limit=( self.config.snapshot_status_poll_failure_max_retries)) verifier.start()
def verify_volume_availability(cls, volume): verifier = StatusProgressionVerifier( 'volume', volume.id_, cls.get_volume_status, volume.id_) verifier.add_state( expected_statuses=[statuses.Volume.CREATING], acceptable_statuses=[statuses.Volume.AVAILABLE], error_statuses=[statuses.Volume.ERROR], timeout=1800, poll_rate=10) verifier.add_state( expected_statuses=[ statuses.Volume.AVAILABLE], error_statuses=[ statuses.Volume.ERROR], timeout=1800, poll_rate=10) verifier.start()
def verify_volume_status_progression_during_detachment( self, volume_id, raise_on_error=True): """ Track the status progression of volume volume_id being detached. Optionally fails silently if rais_on_error is set to False. :param volume_id: the uuid of the volume being tracked :returns: None """ verifier = StatusProgressionVerifier('volume', volume_id, self._get_volume_status, volume_id) verifier.set_global_state_properties( timeout=self.config.attachment_timeout) verifier.add_state( expected_statuses=['in-use'], acceptable_statuses=['detaching', 'available'], error_statuses=['error', 'attaching', 'creating', 'deleting'], poll_rate=self.config.api_poll_rate, poll_failure_retry_limit=3) verifier.add_state( expected_statuses=['detaching'], acceptable_statuses=['available'], error_statuses=['error', 'attaching', 'creating', 'deleting'], poll_rate=self.config.api_poll_rate, poll_failure_retry_limit=3) verifier.add_state(expected_statuses=['available'], error_statuses=[ 'error', 'attaching', 'creating', 'deleting', 'in-use' ], poll_rate=self.config.api_poll_rate, poll_failure_retry_limit=3) try: verifier.start() except Exception as exception: if raise_on_error: raise exception
def create_task_with_transitions(self, create_task_resp, final_status=None, response_entity_type=None): """ @summary: Create a task and verify that it transitions through the expected statuses @param create_task_resp: Create task api response @type create_task_resp: Object @param final_status: Flag to determine success or failure @type final_status: String @param response_entity_type: Response entity type to be passed on to python requests @type response_entity_type: Type @return: Task @rtype: Object """ if not response_entity_type: response_entity_type = Task task = self.verify_resp(create_task_resp, 'create task') # Verify task progresses as expected verifier = StatusProgressionVerifier( 'task', task.id_, self.get_task_status, task.id_, response_entity_type=response_entity_type) if final_status == TaskStatus.SUCCESS: error_statuses = [TaskStatus.FAILURE] else: error_statuses = [TaskStatus.SUCCESS] verifier.add_state( expected_statuses=[TaskStatus.PENDING], acceptable_statuses=[TaskStatus.PROCESSING, final_status], error_statuses=error_statuses, timeout=self.config.task_timeout, poll_rate=1) if final_status == TaskStatus.SUCCESS: error_statuses = [TaskStatus.PENDING, TaskStatus.FAILURE] else: error_statuses = [TaskStatus.PENDING, TaskStatus.SUCCESS] verifier.add_state(expected_statuses=[TaskStatus.PROCESSING], acceptable_statuses=[final_status], error_statuses=error_statuses, timeout=self.config.task_timeout, poll_rate=1) if final_status == TaskStatus.SUCCESS: verifier.add_state( expected_statuses=[TaskStatus.SUCCESS], error_statuses=[TaskStatus.PENDING, TaskStatus.FAILURE], timeout=self.config.task_timeout, poll_rate=1) else: verifier.add_state( expected_statuses=[TaskStatus.FAILURE], error_statuses=[TaskStatus.PENDING, TaskStatus.SUCCESS], timeout=self.config.task_timeout, poll_rate=1) verifier.start() return self.client.get_task_details( task.id_, response_entity_type=response_entity_type).entity
def create_available_volume(self, size, volume_type, name=None, description=None, availability_zone=None, metadata=None, bootable=None, image_ref=None, snapshot_id=None, source_volid=None, timeout=None): """Create a volume and wait for it to reach the 'available' status""" metadata = metadata or {} timeout = timeout or self.calculate_volume_create_timeout(size) try: if image_ref: timeout = self.calculate_copy_image_to_volume_timeout(size) self._log.info( "Copy image to volume timeout calculated at {0} " "seconds".format(timeout)) elif snapshot_id: timeout = self.calculate_snapshot_restore_timeout(size) self._log.info( "Create volume from snapshot timeout calculated at {0} " "seconds".format(timeout)) elif source_volid: timeout = self.calculate_volume_clone_timeout(size) self._log.info("Clone a volume timeout calculated at {0} " "seconds".format(timeout)) except: # Worst case if no config values are set. # Use the default volume create timeout. self._log.info("Unable to use create-method-specific timeout, " "defaulting to normal volume create timeout of {0} " "seconds".format(timeout)) self._log.info("create_available_volume() is creating a volume") start_time = time() resp = self.create_volume(size, volume_type, name=name, description=description, availability_zone=availability_zone, metadata=metadata, bootable=bootable, image_ref=image_ref, snapshot_id=snapshot_id, source_volid=source_volid) timeout = timeout - (time() - start_time) volume = self._verify_entity(resp) # Verify volume progression from 'creating' to 'available' verifier = StatusProgressionVerifier('volume', volume.id_, self.get_volume_status, volume.id_) verifier.set_global_state_properties(timeout) verifier.add_state( expected_statuses=[self.statuses.Volume.CREATING], acceptable_statuses=[self.statuses.Volume.AVAILABLE], error_statuses=[self.statuses.Volume.ERROR], poll_rate=self.config.volume_status_poll_frequency) verifier.add_state(expected_statuses=[self.statuses.Volume.AVAILABLE], error_statuses=[self.statuses.Volume.ERROR], poll_rate=self.config.volume_status_poll_frequency) verifier.start() # Return volume model resp = self.client.get_volume_info(volume.id_) volume = self._verify_entity(resp) return volume
def verify_server_snapshotting_progression(self, server_id): # Wait while the server is imaging verifier = StatusProgressionVerifier( 'server', server_id, lambda id_: self.verify_entity( self.servers_client.get_server(id_)).task_state, server_id) verifier.set_global_state_properties( timeout=self.config.snapshot_timeout) verifier.add_state( expected_statuses=[ComputeTaskStates.IMAGE_SNAPSHOT], acceptable_statuses=[ ComputeTaskStates.IMAGE_PENDING_UPLOAD, ComputeTaskStates.IMAGE_UPLOADING ], poll_rate=self.config.image_status_interval) verifier.add_state( expected_statuses=[ComputeTaskStates.IMAGE_PENDING_UPLOAD], acceptable_statuses=[ComputeTaskStates.IMAGE_UPLOADING], error_statuses=[ComputeTaskStates.NONE], poll_rate=self.config.image_status_interval) verifier.add_state( expected_statuses=[ComputeTaskStates.IMAGE_UPLOADING], error_statuses=[ComputeTaskStates.NONE], poll_rate=self.config.image_status_interval) verifier.add_state(expected_statuses=[ComputeTaskStates.NONE], poll_rate=self.config.image_status_interval) verifier.start() response = self.servers_client.get_server(server_id) return self.verify_entity(response)
def create_available_volume( self, size, volume_type, name=None, description=None, availability_zone=None, metadata=None, bootable=None, image_ref=None, snapshot_id=None, source_volid=None, timeout=None): """Create a volume and wait for it to reach the 'available' status""" metadata = metadata or {} timeout = timeout or self.calculate_volume_create_timeout(size) try: if image_ref: timeout = self.calculate_copy_image_to_volume_timeout(size) self._log.info( "Copy image to volume timeout calculated at {0} " "seconds".format(timeout)) elif snapshot_id: timeout = self.calculate_snapshot_restore_timeout(size) self._log.info( "Create volume from snapshot timeout calculated at {0} " "seconds".format(timeout)) elif source_volid: timeout = self.calculate_volume_clone_timeout(size) self._log.info( "Clone a volume timeout calculated at {0} " "seconds".format(timeout)) except: # Worst case if no config values are set. # Use the default volume create timeout. self._log.info( "Unable to use create-method-specific timeout, " "defaulting to normal volume create timeout of {0} " "seconds".format(timeout)) self._log.info("create_available_volume() is creating a volume") start_time = time() resp = self.create_volume( size, volume_type, name=name, description=description, availability_zone=availability_zone, metadata=metadata, bootable=bootable, image_ref=image_ref, snapshot_id=snapshot_id, source_volid=source_volid) timeout = timeout - (time() - start_time) volume = self._verify_entity(resp) # Verify volume progression from 'creating' to 'available' verifier = StatusProgressionVerifier( 'volume', volume.id_, self.get_volume_status, volume.id_) verifier.set_global_state_properties(timeout) verifier.add_state( expected_statuses=[self.statuses.Volume.CREATING], acceptable_statuses=[self.statuses.Volume.AVAILABLE], error_statuses=[self.statuses.Volume.ERROR], poll_rate=self.config.volume_status_poll_frequency) verifier.add_state( expected_statuses=[self.statuses.Volume.AVAILABLE], error_statuses=[self.statuses.Volume.ERROR], poll_rate=self.config.volume_status_poll_frequency) verifier.start() # Return volume model resp = self.client.get_volume_info(volume.id_) volume = self._verify_entity(resp) return volume
def verify_volume_status_progression_during_detachment( self, volume_id, raise_on_error=True): """ Track the status progression of volume volume_id being detached. Optionally fails silently if rais_on_error is set to False. :param volume_id: the uuid of the volume being tracked :returns: None """ verifier = StatusProgressionVerifier( 'volume', volume_id, self._get_volume_status, volume_id) verifier.set_global_state_properties( timeout=self.config.attachment_timeout) verifier.add_state( expected_statuses=['in-use'], acceptable_statuses=['detaching', 'available'], error_statuses=['error', 'attaching', 'creating', 'deleting'], poll_rate=self.config.api_poll_rate, poll_failure_retry_limit=3) verifier.add_state( expected_statuses=['detaching'], acceptable_statuses=['available'], error_statuses=['error', 'attaching', 'creating', 'deleting'], poll_rate=self.config.api_poll_rate, poll_failure_retry_limit=3) verifier.add_state( expected_statuses=['available'], error_statuses=[ 'error', 'attaching', 'creating', 'deleting', 'in-use'], poll_rate=self.config.api_poll_rate, poll_failure_retry_limit=3) try: verifier.start() except Exception as exception: if raise_on_error: raise exception
def verify_volume_status_progression_during_attachment( self, volume_id, state_list=None): verifier = StatusProgressionVerifier( 'volume', volume_id, self._get_volume_status, volume_id) verifier.set_global_state_properties( timeout=self.config.attachment_timeout) verifier.add_state( expected_statuses=['available'], acceptable_statuses=['attaching', 'in-use'], error_statuses=['error', 'creating'], poll_rate=self.config.api_poll_rate, poll_failure_retry_limit=3) verifier.add_state( expected_statuses=['attaching'], acceptable_statuses=['in-use'], error_statuses=['error', 'creating'], poll_rate=self.config.api_poll_rate, poll_failure_retry_limit=3) verifier.add_state( expected_statuses=['in-use'], error_statuses=['available', 'error', 'creating'], poll_rate=self.config.api_poll_rate, poll_failure_retry_limit=3) verifier.start()
def verify_volume_status_progression_during_attachment( self, volume_id, state_list=None): verifier = StatusProgressionVerifier('volume', volume_id, self._get_volume_status, volume_id) verifier.set_global_state_properties( timeout=self.config.attachment_timeout) verifier.add_state(expected_statuses=['available'], acceptable_statuses=['attaching', 'in-use'], error_statuses=['error', 'creating'], poll_rate=self.config.api_poll_rate, poll_failure_retry_limit=3) verifier.add_state(expected_statuses=['attaching'], acceptable_statuses=['in-use'], error_statuses=['error', 'creating'], poll_rate=self.config.api_poll_rate, poll_failure_retry_limit=3) verifier.add_state(expected_statuses=['in-use'], error_statuses=['available', 'error', 'creating'], poll_rate=self.config.api_poll_rate, poll_failure_retry_limit=3) verifier.start()
def verify_server_snapshotting_progression(self, server_id): # Wait while the server is imaging verifier = StatusProgressionVerifier( 'server', server_id, lambda id_: self.verify_entity( self.servers_client.get_server(id_)).task_state, server_id) verifier.set_global_state_properties( timeout=self.config.snapshot_timeout) verifier.add_state( expected_statuses=[ComputeTaskStates.IMAGE_SNAPSHOT], acceptable_statuses=[ComputeTaskStates.IMAGE_PENDING_UPLOAD, ComputeTaskStates.IMAGE_UPLOADING], poll_rate=self.config.image_status_interval) verifier.add_state( expected_statuses=[ComputeTaskStates.IMAGE_PENDING_UPLOAD], acceptable_statuses=[ComputeTaskStates.IMAGE_UPLOADING, ComputeTaskStates.NONE], poll_rate=self.config.image_status_interval) verifier.add_state( expected_statuses=[ComputeTaskStates.IMAGE_UPLOADING], acceptable_statuses=[ComputeTaskStates.NONE], poll_rate=self.config.image_status_interval) verifier.add_state( expected_statuses=[ComputeTaskStates.NONE], poll_rate=self.config.image_status_interval) verifier.start() response = self.servers_client.get_server(server_id) return self.verify_entity(response)
def create_task_with_transitions(self, create_task_resp, final_status=None, response_entity_type=None): """ @summary: Create a task and verify that it transitions through the expected statuses @param create_task_resp: Create task api response @type create_task_resp: Object @param final_status: Flag to determine success or failure @type final_status: String @param response_entity_type: Response entity type to be passed on to python requests @type response_entity_type: Type @return: Task @rtype: Object """ if not response_entity_type: response_entity_type = Task task = self.verify_resp(create_task_resp, 'create task') # Verify task progresses as expected verifier = StatusProgressionVerifier( 'task', task.id_, self.get_task_status, task.id_, response_entity_type=response_entity_type) if final_status == TaskStatus.SUCCESS: error_statuses = [TaskStatus.FAILURE] else: error_statuses = [TaskStatus.SUCCESS] verifier.add_state( expected_statuses=[TaskStatus.PENDING], acceptable_statuses=[TaskStatus.PROCESSING, final_status], error_statuses=error_statuses, timeout=self.config.task_timeout, poll_rate=1) if final_status == TaskStatus.SUCCESS: error_statuses = [TaskStatus.PENDING, TaskStatus.FAILURE] else: error_statuses = [TaskStatus.PENDING, TaskStatus.SUCCESS] verifier.add_state( expected_statuses=[TaskStatus.PROCESSING], acceptable_statuses=[final_status], error_statuses=error_statuses, timeout=self.config.task_timeout, poll_rate=1) if final_status == TaskStatus.SUCCESS: verifier.add_state( expected_statuses=[TaskStatus.SUCCESS], error_statuses=[TaskStatus.PENDING, TaskStatus.FAILURE], timeout=self.config.task_timeout, poll_rate=1) else: verifier.add_state( expected_statuses=[TaskStatus.FAILURE], error_statuses=[TaskStatus.PENDING, TaskStatus.SUCCESS], timeout=self.config.task_timeout, poll_rate=1) verifier.start() return self.client.get_task_details( task.id_, response_entity_type=response_entity_type).entity
def create_task_with_transitions(self, input_, task_type, outcome, final_status=None): """ @summary: Create a task and verify that it transitions through the expected statuses @param input_: Image properties and location data @type input_: Dictionary @param task_type: Type of task @type task_type: String @param outcome: Expected final status @type outcome: Integer @param final_status: Flag to determine success or failure @type final_status: String @return: Task @rtype: Object """ response = self.client.create_task(input_=input_, type_=task_type) task = response.entity response = self.client.get_task_details(task.id_) task_status = response.entity.status.lower() # Verify task progresses as expected verifier = StatusProgressionVerifier('task', task.id_, task_status, task.id_) verifier.add_state( expected_statuses=[TaskStatus.PENDING], acceptable_statuses=[TaskStatus.PROCESSING, outcome], error_statuses=[TaskStatus.SUCCESS], timeout=self.config.task_timeout, poll_rate=1) verifier.add_state( expected_statuses=[TaskStatus.PROCESSING], acceptable_statuses=[outcome], error_statuses=[TaskStatus.PENDING, TaskStatus.SUCCESS], timeout=self.config.task_timeout, poll_rate=1) if final_status == TaskStatus.SUCCESS: verifier.add_state( expected_statuses=[TaskStatus.SUCCESS], error_statuses=[TaskStatus.PENDING, TaskStatus.FAILURE], timeout=self.config.task_timeout, poll_rate=1) if final_status == TaskStatus.FAILURE: verifier.add_state( expected_statuses=[TaskStatus.FAILURE], error_statuses=[TaskStatus.PENDING, TaskStatus.SUCCESS], timeout=self.config.task_timeout, poll_rate=1) verifier.start() return self.client.get_task_details(task.id_).entity
def create_task_with_transitions(self, input_, task_type, final_status=None): """ @summary: Create a task and verify that it transitions through the expected statuses @param input_: Image properties and location data @type input_: Dictionary @param task_type: Type of task @type task_type: String @param final_status: Flag to determine success or failure @type final_status: String @return: Task @rtype: Object """ if task_type == TaskTypes.IMPORT: resp = self.client.task_to_import_image(input_, TaskTypes.IMPORT) else: resp = self.client.task_to_export_image(input_, TaskTypes.EXPORT) task = self.verify_resp(resp, "create task") # Verify task progresses as expected verifier = StatusProgressionVerifier("task", task.id_, self.get_task_status, task.id_) if final_status == TaskStatus.SUCCESS: error_statuses = [TaskStatus.FAILURE] else: error_statuses = [TaskStatus.SUCCESS] verifier.add_state( expected_statuses=[TaskStatus.PENDING], acceptable_statuses=[TaskStatus.PROCESSING, final_status], error_statuses=error_statuses, timeout=self.config.task_timeout, poll_rate=1, ) if final_status == TaskStatus.SUCCESS: error_statuses = [TaskStatus.PENDING, TaskStatus.FAILURE] else: error_statuses = [TaskStatus.PENDING, TaskStatus.SUCCESS] verifier.add_state( expected_statuses=[TaskStatus.PROCESSING], acceptable_statuses=[final_status], error_statuses=error_statuses, timeout=self.config.task_timeout, poll_rate=1, ) if final_status == TaskStatus.SUCCESS: verifier.add_state( expected_statuses=[TaskStatus.SUCCESS], error_statuses=[TaskStatus.PENDING, TaskStatus.FAILURE], timeout=self.config.task_timeout, poll_rate=1, ) else: verifier.add_state( expected_statuses=[TaskStatus.FAILURE], error_statuses=[TaskStatus.PENDING, TaskStatus.SUCCESS], timeout=self.config.task_timeout, poll_rate=1, ) verifier.start() return self.client.get_task_details(task.id_).entity