def cmd_assert(cmd, retries=1, pollrate=60, on_retry=None): """ Run a command, logging (using exec_cmd) and raise an exception if the return code of the command indicates failure. Try the command multiple times if requested. :param cmd <string|list>: A shell command :param retries int: The number of times to try before declaring failure :param pollrate int: how long to sleep between tries :param on_retry <string|list>: A shell command to run before retrying a failure :return: (stdout,stderr) if exit code is zero """ for try_num in range(0, retries): if try_num > 0: logger.debug( "cmd_assert: Failed {} times. Retrying in {} seconds: {}". format(try_num, pollrate, cmd)) time.sleep(pollrate) if on_retry is not None: cmd_gather(on_retry) # no real use for the result though result, stdout, stderr = cmd_gather(cmd) if result == SUCCESS: break logger.debug("cmd_assert: Final result = {} in {} tries.".format( result, try_num)) assertion.success( result, "Error running [{}] {}. See debug log.".format(pushd.Dir.getcwd(), cmd)) return stdout, stderr
def get_latest_build_info(self): """ Queries brew to determine the most recently built release of the component associated with this image. This method does not rely on the "release" label needing to be present in the Dockerfile. :return: A tuple: (component name, version, release); e.g. ("registry-console-docker", "v3.6.173.0.75", "1") """ component_name = self.get_component_name() tag = "{}-candidate".format(self.branch()) rc, stdout, stderr = exectools.cmd_gather( ["brew", "latest-build", tag, component_name]) assertion.success(rc, "Unable to search brew builds: %s" % stderr) latest = stdout.strip().splitlines()[-1].split(' ')[0] if not latest.startswith(component_name): # If no builds found, `brew latest-build` output will appear as: # Build Tag Built by # ---------------------------------------- -------------------- ---------------- raise IOError("No builds detected for %s using tag: %s" % (self.qualified_name, tag)) # latest example: "registry-console-docker-v3.6.173.0.75-1"" name, version, release = latest.rsplit( "-", 2) # [ "registry-console-docker", "v3.6.173.0.75", "1"] return name, version, release
def test_success(self): """ Verify that return codes indicating pass and fail respond correctly """ # When we move to Python 3 this will raise ChildProcessError directly try: assertion.success(0, "this should not fail") except assertion.ChildProcessError as proc_fail: self.fail("success reported as fail: {}".format(proc_fail)) with self.assertRaises(assertion.ChildProcessError): assertion.success(1, "process failed")