def __init__(self, region_name, host, auth, user_agent, signature_version, endpoint_prefix, event_emitter, proxies=None, verify=True, timeout=DEFAULT_TIMEOUT, response_parser_factory=None): self._endpoint_prefix = endpoint_prefix self._signature_version = signature_version self._event_emitter = event_emitter self._user_agent = user_agent self.region_name = region_name self.host = host self.verify = verify self.auth = auth if proxies is None: proxies = {} self.proxies = proxies self.http_session = Session() self.timeout = timeout self._lock = threading.Lock() if response_parser_factory is None: response_parser_factory = parsers.ResponseParserFactory() self._response_parser_factory = response_parser_factory
def __init__(self, service, region_name, host, auth, proxies=None): self.service = service self.session = self.service.session self.region_name = region_name self.host = host self.verify = True self.auth = auth if proxies is None: proxies = {} self.proxies = proxies self.http_session = Session() self._lock = threading.Lock()
def test_patch_http_requests_send(mock_context_wrapper): if sys.version_info[0] != 3: pytest.skip("this test requires python 3+, skipping") patch_http_requests(mock_context_wrapper, None, None) assert hasattr(BotocoreSession.send, "__wrapped__") assert hasattr(BotocoreVendoredSession.send, "__wrapped__") botocore_session = BotocoreSession() botocore_session.send(AWSRequest(method="GET", url="https://www.iopipe.com")) botocore_vendored_session = BotocoreVendoredSession() request = PreparedRequest() request.prepare(method="GET", url="https://www.iopipe.com") botocore_vendored_session.send(request)
def __init__(self, service, region_name, host, auth, proxies=None, verify=True, timeout=DEFAULT_TIMEOUT): self.service = service self.session = self.service.session self.region_name = region_name self.host = host self.verify = verify self.auth = auth if proxies is None: proxies = {} self.proxies = proxies self.http_session = Session() self.timeout = timeout self._lock = threading.Lock()
def __init__(self, region_name, host, auth, user_agent, signature_version, endpoint_prefix, event_emitter, proxies=None, verify=True, timeout=DEFAULT_TIMEOUT): self._endpoint_prefix = endpoint_prefix self._signature_version = signature_version self._event_emitter = event_emitter self._user_agent = user_agent self.region_name = region_name self.host = host self.verify = verify self.auth = auth if proxies is None: proxies = {} self.proxies = proxies self.http_session = Session() self.timeout = timeout self._lock = threading.Lock()
class Endpoint(object): """ Represents an endpoint for a particular service in a specific region. Only an endpoint can make requests. :ivar service: The Service object that describes this endpoints service. :ivar host: The fully qualified endpoint hostname. :ivar session: The session object. """ def __init__(self, region_name, host, auth, user_agent, signature_version, endpoint_prefix, event_emitter, proxies=None, verify=True, timeout=DEFAULT_TIMEOUT, response_parser_factory=None): self._endpoint_prefix = endpoint_prefix self._signature_version = signature_version self._event_emitter = event_emitter self._user_agent = user_agent self.region_name = region_name self.host = host self.verify = verify self.auth = auth if proxies is None: proxies = {} self.proxies = proxies self.http_session = Session() self.timeout = timeout self._lock = threading.Lock() if response_parser_factory is None: response_parser_factory = parsers.ResponseParserFactory() self._response_parser_factory = response_parser_factory def __repr__(self): return '%s(%s)' % (self._endpoint_prefix, self.host) def make_request(self, operation_model, request_dict): logger.debug("Making request for %s (verify_ssl=%s) with params: %s", operation_model, self.verify, request_dict) prepared_request = self.create_request(request_dict) return self._send_request(prepared_request, operation_model) def _choose_signer(self, signer=None): # To decide if we need to do auth or not we check the # signature_version attribute on both the service and # the operation are not None and we make sure there is an # auth class associated with the endpoint. # If any of these are not true, we skip auth. if signer is not None: # If the user explicitly specifies a signer, then we will sign # the request. signer = signer else: do_auth = self._signature_version and self.auth if do_auth: signer = self.auth else: # If we're not suppose to sign the request, then we set the # signer to None. signer = None return signer def create_request(self, params, signer=None): signer = self._choose_signer(signer) request = self._create_request_object(params) prepared_request = self.prepare_request(request, signer) return prepared_request def _create_request_object(self, request_dict): r = request_dict user_agent = self._user_agent headers = r['headers'] headers['User-Agent'] = user_agent url = urljoin(self.host, r['url_path']) if r['query_string']: encoded_query_string = percent_encode_sequence(r['query_string']) if '?' not in url: url += '?%s' % encoded_query_string else: url += '&%s' % encoded_query_string request = AWSRequest(method=r['method'], url=url, data=r['body'], headers=headers) return request def prepare_request(self, request, signer): if signer is not None: with self._lock: # Parts of the auth signing code aren't thread safe (things # that manipulate .auth_path), so we're using a lock here to # prevent race conditions. event_name = 'before-auth.%s' % self._endpoint_prefix self._event_emitter.emit(event_name, endpoint=self, request=request, auth=signer) signer.add_auth(request=request) prepared_request = request.prepare() return prepared_request def _send_request(self, request, operation_model): attempts = 1 response, exception = self._get_response(request, operation_model, attempts) while self._needs_retry(attempts, operation_model, response, exception): attempts += 1 # If there is a stream associated with the request, we need # to reset it before attempting to send the request again. # This will ensure that we resend the entire contents of the # body. request.reset_stream() # Resign the request when retried. signer = self._choose_signer() request = self.prepare_request(request.original, signer) response, exception = self._get_response(request, operation_model, attempts) return response def _get_response(self, request, operation_model, attempts): try: logger.debug("Sending http request: %s", request) http_response = self.http_session.send( request, verify=self.verify, stream=operation_model.has_streaming_output, proxies=self.proxies, timeout=self.timeout) except Exception as e: logger.debug("Exception received when sending HTTP request.", exc_info=True) return (None, e) # This returns the http_response and the parsed_data. response_dict = convert_to_response_dict(http_response, operation_model) parser = self._response_parser_factory.create_parser( operation_model.metadata['protocol']) return ((http_response, parser.parse(response_dict, operation_model.output_shape)), None) def _needs_retry(self, attempts, operation_model, response=None, caught_exception=None): event_name = 'needs-retry.%s.%s' % (self._endpoint_prefix, operation_model.name) responses = self._event_emitter.emit(event_name, response=response, endpoint=self, operation=operation_model, attempts=attempts, caught_exception=caught_exception) handler_response = first_non_none_response(responses) if handler_response is None: return False else: # Request needs to be retried, and we need to sleep # for the specified number of times. logger.debug( "Response received to retry, sleeping for " "%s seconds", handler_response) time.sleep(handler_response) return True
class Endpoint(object): """ Represents an endpoint for a particular service in a specific region. Only an endpoint can make requests. :ivar service: The Service object that describes this endpoints service. :ivar host: The fully qualified endpoint hostname. :ivar session: The session object. """ def __init__(self, region_name, host, auth, user_agent, signature_version, endpoint_prefix, event_emitter, proxies=None, verify=True, timeout=DEFAULT_TIMEOUT): self._endpoint_prefix = endpoint_prefix self._signature_version = signature_version self._event_emitter = event_emitter self._user_agent = user_agent self.region_name = region_name self.host = host self.verify = verify self.auth = auth if proxies is None: proxies = {} self.proxies = proxies self.http_session = Session() self.timeout = timeout self._lock = threading.Lock() def __repr__(self): return '%s(%s)' % (self._endpoint_prefix, self.host) def make_request(self, operation_model, request_dict): logger.debug("Making request for %s (verify_ssl=%s) with params: %s", operation_model, self.verify, request_dict) prepared_request = self.create_request(request_dict) return self._send_request(prepared_request, operation_model) def create_request(self, params, signer=None): # To decide if we need to do auth or not we check the # signature_version attribute on both the service and # the operation are not None and we make sure there is an # auth class associated with the endpoint. # If any of these are not true, we skip auth. if signer is not None: # If the user explicitly specifies a signer, then we will sign # the request. signer = signer else: do_auth = self._signature_version and self.auth if do_auth: signer = self.auth else: # If we're not suppose to sign the request, then we set the signer # to None. signer = None request = self._create_request_object(params) prepared_request = self.prepare_request(request, signer) return prepared_request def _create_request_object(self, request_dict): r = request_dict user_agent = self._user_agent headers = r['headers'] headers['User-Agent'] = user_agent url = urljoin(self.host, r['url_path']) if r['query_string']: encoded_query_string = percent_encode_sequence(r['query_string']) if '?' not in url: url += '?%s' % encoded_query_string else: url += '&%s' % encoded_query_string request = AWSRequest(method=r['method'], url=url, data=r['body'], headers=headers) return request def prepare_request(self, request, signer): if signer is not None: with self._lock: # Parts of the auth signing code aren't thread safe (things # that manipulate .auth_path), so we're using a lock here to # prevent race conditions. event_name = 'before-auth.%s' % self._endpoint_prefix self._event_emitter.emit( event_name, endpoint=self, request=request, auth=signer) signer.add_auth(request=request) prepared_request = request.prepare() return prepared_request def _send_request(self, request, operation_model): attempts = 1 response, exception = self._get_response(request, operation_model, attempts) while self._needs_retry(attempts, operation_model, response, exception): attempts += 1 # If there is a stream associated with the request, we need # to reset it before attempting to send the request again. # This will ensure that we resend the entire contents of the # body. request.reset_stream() response, exception = self._get_response(request, operation_model, attempts) return response def _get_response(self, request, operation_model, attempts): try: logger.debug("Sending http request: %s", request) http_response = self.http_session.send( request, verify=self.verify, stream=operation_model.has_streaming_output, proxies=self.proxies, timeout=self.timeout) except Exception as e: logger.debug("Exception received when sending HTTP request.", exc_info=True) return (None, e) # This returns the http_response and the parsed_data. return (botocore.response.get_response(operation_model, http_response), None) def _needs_retry(self, attempts, operation_model, response=None, caught_exception=None): event_name = 'needs-retry.%s.%s' % (self._endpoint_prefix, operation_model.name) responses = self._event_emitter.emit( event_name, response=response, endpoint=self, operation=operation_model, attempts=attempts, caught_exception=caught_exception) handler_response = first_non_none_response(responses) if handler_response is None: return False else: # Request needs to be retried, and we need to sleep # for the specified number of times. logger.debug("Response received to retry, sleeping for " "%s seconds", handler_response) time.sleep(handler_response) return True
class Endpoint(object): """ Represents an endpoint for a particular service in a specific region. Only an endpoint can make requests. :ivar service: The Service object that describes this endpoints service. :ivar host: The fully qualified endpoint hostname. :ivar session: The session object. """ def __init__(self, region_name, host, user_agent, endpoint_prefix, event_emitter, proxies=None, verify=True, timeout=DEFAULT_TIMEOUT, response_parser_factory=None): self._endpoint_prefix = endpoint_prefix self._event_emitter = event_emitter self._user_agent = user_agent self.region_name = region_name self.host = host self.verify = verify if proxies is None: proxies = {} self.proxies = proxies self.http_session = Session() self.timeout = timeout self._lock = threading.Lock() if response_parser_factory is None: response_parser_factory = parsers.ResponseParserFactory() self._response_parser_factory = response_parser_factory def __repr__(self): return '%s(%s)' % (self._endpoint_prefix, self.host) def make_request(self, operation_model, request_dict): logger.debug("Making request for %s (verify_ssl=%s) with params: %s", operation_model, self.verify, request_dict) return self._send_request(request_dict, operation_model) def create_request(self, params, operation_model=None): request = self._create_request_object(params) if operation_model: event_name = 'request-created.{endpoint_prefix}.{op_name}'.format( endpoint_prefix=self._endpoint_prefix, op_name=operation_model.name) self._event_emitter.emit(event_name, request=request, operation_name=operation_model.name) prepared_request = self.prepare_request(request) return prepared_request def _create_request_object(self, request_dict): r = request_dict user_agent = self._user_agent headers = r['headers'] headers['User-Agent'] = user_agent url = urljoin(self.host, r['url_path']) if r['query_string']: encoded_query_string = percent_encode_sequence(r['query_string']) if '?' not in url: url += '?%s' % encoded_query_string else: url += '&%s' % encoded_query_string request = AWSRequest(method=r['method'], url=url, data=r['body'], headers=headers) return request def prepare_request(self, request): return request.prepare() def _send_request(self, request_dict, operation_model): attempts = 1 request = self.create_request(request_dict, operation_model) response, exception = self._get_response(request, operation_model, attempts) while self._needs_retry(attempts, operation_model, response, exception): attempts += 1 # If there is a stream associated with the request, we need # to reset it before attempting to send the request again. # This will ensure that we resend the entire contents of the # body. request.reset_stream() # Create a new request when retried (including a new signature). request = self.create_request(request_dict, operation_model=operation_model) response, exception = self._get_response(request, operation_model, attempts) return response def _get_response(self, request, operation_model, attempts): try: logger.debug("Sending http request: %s", request) http_response = self.http_session.send( request, verify=self.verify, stream=operation_model.has_streaming_output, proxies=self.proxies, timeout=self.timeout) except Exception as e: logger.debug("Exception received when sending HTTP request.", exc_info=True) return (None, e) # This returns the http_response and the parsed_data. response_dict = convert_to_response_dict(http_response, operation_model) parser = self._response_parser_factory.create_parser( operation_model.metadata['protocol']) return ((http_response, parser.parse(response_dict, operation_model.output_shape)), None) def _needs_retry(self, attempts, operation_model, response=None, caught_exception=None): event_name = 'needs-retry.%s.%s' % (self._endpoint_prefix, operation_model.name) responses = self._event_emitter.emit(event_name, response=response, endpoint=self, operation=operation_model, attempts=attempts, caught_exception=caught_exception) handler_response = first_non_none_response(responses) if handler_response is None: return False else: # Request needs to be retried, and we need to sleep # for the specified number of times. logger.debug( "Response received to retry, sleeping for " "%s seconds", handler_response) time.sleep(handler_response) return True
class Endpoint(object): """ Represents an endpoint for a particular service in a specific region. Only an endpoint can make requests. :ivar service: The Service object that describes this endpoints service. :ivar host: The fully qualified endpoint hostname. :ivar session: The session object. """ def __init__(self, service, region_name, host, auth, proxies=None, verify=True): self.service = service self.session = self.service.session self.region_name = region_name self.host = host self.verify = verify self.auth = auth if proxies is None: proxies = {} self.proxies = proxies self.http_session = Session() self._lock = threading.Lock() def __repr__(self): return '%s(%s)' % (self.service.endpoint_prefix, self.host) def make_request(self, operation, params): logger.debug("Making request for %s (verify_ssl=%s) with params: %s", operation, self.verify, params) prepared_request = self.create_request(operation, params) return self._send_request(prepared_request, operation) def create_request(self, operation, params, signer=None): # To decide if we need to do auth or not we check the # signature_version attribute on both the service and # the operation are not None and we make sure there is an # auth class associated with the endpoint. # If any of these are not true, we skip auth. if signer is not None: # If the user explicitly specifies a signer, then we will sign # the request. signer = signer else: do_auth = (getattr(self.service, 'signature_version', None) and getattr(operation, 'signature_version', True) and self.auth) if do_auth: signer = self.auth else: # If we're not suppose to sign the request, then we set the signer # to None. signer = None request = self._create_request_object(operation, params) prepared_request = self.prepare_request(request, signer) return prepared_request def _create_request_object(self, operation, params): raise NotImplementedError('_create_request_object') def prepare_request(self, request, signer): if signer is not None: with self._lock: # Parts of the auth signing code aren't thread safe (things # that manipulate .auth_path), so we're using a lock here to # prevent race conditions. event = self.session.create_event( 'before-auth', self.service.endpoint_prefix) self.session.emit(event, endpoint=self, request=request, auth=signer) signer.add_auth(request=request) prepared_request = request.prepare() return prepared_request def _send_request(self, request, operation): attempts = 1 response, exception = self._get_response(request, operation, attempts) while self._needs_retry(attempts, operation, response, exception): attempts += 1 # If there is a stream associated with the request, we need # to reset it before attempting to send the request again. # This will ensure that we resend the entire contents of the # body. request.reset_stream() response, exception = self._get_response(request, operation, attempts) return response def _get_response(self, request, operation, attempts): try: logger.debug("Sending http request: %s", request) http_response = self.http_session.send( request, verify=self.verify, stream=operation.is_streaming(), proxies=self.proxies) except Exception as e: logger.debug("Exception received when sending HTTP request.", exc_info=True) return (None, e) # This returns the http_response and the parsed_data. return (botocore.response.get_response(self.session, operation, http_response), None) def _needs_retry(self, attempts, operation, response=None, caught_exception=None): event = self.session.create_event( 'needs-retry', self.service.endpoint_prefix, operation.name) handler_response = self.session.emit_first_non_none_response( event, response=response, endpoint=self, operation=operation, attempts=attempts, caught_exception=caught_exception) if handler_response is None: return False else: # Request needs to be retried, and we need to sleep # for the specified number of times. logger.debug("Response received to retry, sleeping for " "%s seconds", handler_response) time.sleep(handler_response) return True