def expected_success(cls, expected_code, read_code): """Check expected success response code against the http response :param int expected_code: The response code that is expected. Optionally a list of integers can be used to specify multiple valid success codes :param int read_code: The response code which was returned in the response :raises AssertionError: if the expected_code isn't a valid http success response code :raises exceptions.InvalidHttpSuccessCode: if the read code isn't an expected http success code """ assert_msg = ( "This function only allowed to use for HTTP status" "codes which explicitly defined in the RFC 7231 & 4918." "{0} is not a defined Success Code!").format(expected_code) if isinstance(expected_code, list): for code in expected_code: assert code in HTTP_SUCCESS + HTTP_REDIRECTION, assert_msg else: assert expected_code in HTTP_SUCCESS + HTTP_REDIRECTION, assert_msg # NOTE(afazekas): the http status code above 400 is processed by # the _error_checker method if read_code < 400: pattern = """Unexpected http success status code {0}, The expected status code is {1}""" if ((not isinstance(expected_code, list) and (read_code != expected_code)) or (isinstance(expected_code, list) and (read_code not in expected_code))): details = pattern.format(read_code, expected_code) raise exceptions.InvalidHttpSuccessCode(details)
def validate_URL_response(URL, expected_status_code=200, expected_body=None, HTTPS_verify=True, client_cert_path=None, CA_certs_path=None, request_interval=CONF.load_balancer.build_interval, request_timeout=CONF.load_balancer.build_timeout): """Check a URL response (HTTP or HTTPS). :param URL: The URL to query. :param expected_status_code: The expected HTTP status code. :param expected_body: The expected response text, None will not compare. :param HTTPS_verify: Should we verify the HTTPS server. :param client_cert_path: Filesystem path to a file with the client private key and certificate. :param CA_certs_path: Filesystem path to a file containing CA certificates to use for HTTPS validation. :param request_interval: Time, in seconds, to timeout a request. :param request_timeout: The maximum time, in seconds, to attempt requests. Failed validation of expected results does not result in a retry. :raises InvalidHttpSuccessCode: The expected_status_code did not match. :raises InvalidHTTPResponseBody: The response body did not match the expected content. :raises TimeoutException: The request timed out. :returns: None """ with requests.Session() as session: session_kwargs = {} if not HTTPS_verify: session_kwargs['verify'] = False if CA_certs_path: session_kwargs['verify'] = CA_certs_path if client_cert_path: session_kwargs['cert'] = client_cert_path session_kwargs['timeout'] = request_interval start = time.time() while time.time() - start < request_timeout: try: response = session.get(URL, **session_kwargs) if response.status_code != expected_status_code: raise exceptions.InvalidHttpSuccessCode( '{0} is not the expected code {1}'.format( response.status_code, expected_status_code)) if expected_body and response.text != expected_body: details = '{} does not match expected {}'.format( response.text, expected_body) raise exceptions.InvalidHTTPResponseBody(resp_body=details) return except requests.exceptions.Timeout: # Don't sleep as we have already waited the interval. LOG.info('Request for {} timed out. Retrying.'.format(URL)) except (exceptions.InvalidHttpSuccessCode, exceptions.InvalidHTTPResponseBody, requests.exceptions.SSLError): raise except Exception as e: LOG.info('Validate URL got exception: {0}. ' 'Retrying.'.format(e)) time.sleep(request_interval) raise exceptions.TimeoutException()