U m^jP@sddlZddlZddlZddlZddlmZmZmZddlm Z e e Z GdddeZGdddeZGdd d eZGd d d eZGd d d eZGdddeZGdddeZdS)N)ensure_unicode ensure_bytesurlparse) EXCEPTION_MAPc@s2eZdZdddddgZddZdd Zd d Zd S) Monitorzbefore-parameter-buildzrequest-createdzresponse-receivedz after-callzafter-call-errorcCs||_||_dS)zAbstraction for monitoring clients API calls :param adapter: An adapter that takes event emitter events and produces monitor events :param publisher: A publisher for generated monitor events N)_adapter _publisher)selfadapterZ publisherr m/private/var/folders/sd/whlwsn6x1_qgglc0mjv25_695qk2gl/T/pip-install-4zq3fp6i/botocore/botocore/monitoring.py__init__"szMonitor.__init__cCs|jD]}|||jqdS)z(Register an event emitter to the monitorN)_EVENTS_TO_REGISTERZ register_lastcapture)r Z event_emitterZevent_to_registerr r r register-s zMonitor.registerc Ks\z"|j||}|r |j|Wn4tk rV}ztjd||ddW5d}~XYnXdS)zCaptures an incoming event from the event emitter It will feed an event emitter event to the monitor's adaptor to create a monitor event and then publish that event to the monitor's publisher. z:Exception %s raised by client monitor in handling event %sT)exc_infoN)rfeedrpublish Exceptionloggerdebug)r event_namepayloadZ monitor_eventer r r r2szMonitor.captureN)__name__ __module__ __qualname__rr rrr r r r rs rc@sreZdZejfddZddZddZddZd d Zd d Z d dZ ddZ ddZ ddZ ddZddZdS)MonitorEventAdaptercCs ||_dS)zAdapts event emitter events to produce monitor events :type time: callable :param time: A callable that produces the current time N)_time)r timer r r r CszMonitorEventAdapter.__init__cCs||f|S)aFeed an event emitter event to generate a monitor event :type emitter_event_name: str :param emitter_event_name: The name of the event emitted :type emitter_payload: dict :param emitter_payload: The payload to associated to the event emitted :rtype: BaseMonitorEvent :returns: A monitor event based on the event emitter events fired ) _get_handler)r Zemitter_event_nameZemitter_payloadr r r rKszMonitorEventAdapter.feedcCs t|d|ddddS)NZ_handle_.r-_)getattrsplitreplace)r rr r r r [sz MonitorEventAdapter._get_handlercKs t|jj|j|d|d<dS)Nservice operation timestampcurrent_api_call_event) APICallEventZ service_modelZ service_idZ wire_name_get_current_time)r modelcontextkwargsr r r _handle_before_parameter_build`s z2MonitorEventAdapter._handle_before_parameter_buildcKs6|j}|dj|d}|j|_|j|_||d<dS)Nr+)r*current_api_call_attempt_event)r/new_api_call_attemptr-headersrequest_headersurl)r requestr0r/Znew_attempt_eventr r r _handle_request_createdgsz+MonitorEventAdapter._handle_request_createdcKsR|d}|||_|dk rH|dd|_|dd|_|d|_n||_|S)Nr2ResponseMetadataZHTTPStatusCodeZ HTTPHeadersError)pop _get_latencylatencyhttp_status_coderesponse_headersget parsed_errorwire_exception)r Zparsed_responser/ exceptionr0 attempt_eventr r r _handle_response_receivedps   z-MonitorEventAdapter._handle_response_receivedcKs |ddd|d_||S)Nr9ZMaxAttemptsReachedFr+)r@retries_exceeded_complete_api_call)r r/parsedr0r r r _handle_after_call~s z&MonitorEventAdapter._handle_after_callcKs|||d_||SNr+)_is_retryable_exceptionrFrG)r r/rCr0r r r _handle_after_call_errorsz,MonitorEventAdapter._handle_after_call_errorcCst|ttdS)NZGENERAL_CONNECTION_ERROR) isinstancetupleRETRYABLE_EXCEPTIONS)r rCr r r rKs z+MonitorEventAdapter._is_retryable_exceptioncCs|d}|||_|SrJ)r;r<r=)r r/Z call_eventr r r rGs  z&MonitorEventAdapter._complete_api_callcCs||jSN)r-r*r eventr r r r<sz MonitorEventAdapter._get_latencycCst|dS)Ni)intrr r r r r-sz%MonitorEventAdapter._get_current_timeN)rrrrr rr r1r8rErIrLrKrGr<r-r r r r rBs  rc@s$eZdZddZddZddZdS)BaseMonitorEventcCs||_||_||_dS)aBase monitor event :type service: str :param service: A string identifying the service associated to the event :type operation: str :param operation: A string identifying the operation of service associated to the event :type timestamp: int :param timestamp: Epoch time in milliseconds from when the event began Nr')r r(r)r*r r r r szBaseMonitorEvent.__init__cCsd|jj|jfS)Nz%s(%r)) __class__r__dict__rTr r r __repr__szBaseMonitorEvent.__repr__cCst||jr|j|jkSdS)NF)rMrVrW)r otherr r r __eq__s  zBaseMonitorEvent.__eq__N)rrrr rXrZr r r r rUsrUcs&eZdZdfdd ZddZZS)r,NFcs:tt|j|||d||_||_|dkr0g|_||_dS)aMonitor event for a single API call This event corresponds to a single client method call, which includes every HTTP requests attempt made in order to complete the client call :type service: str :param service: A string identifying the service associated to the event :type operation: str :param operation: A string identifying the operation of service associated to the event :type timestamp: int :param timestamp: Epoch time in milliseconds from when the event began :type latency: int :param latency: The time in milliseconds to complete the client call :type attempts: list :param attempts: The list of APICallAttempts associated to the APICall :type retries_exceeded: bool :param retries_exceeded: True if API call exceeded retries. False otherwise r'N)superr,r r=attemptsrF)r r(r)r*r=r\rFrVr r r s zAPICallEvent.__init__cCs"t|j|j|d}|j||S)zInstantiates APICallAttemptEvent associated to the APICallEvent :type timestamp: int :param timestamp: Epoch time in milliseconds to associate to the APICallAttemptEvent r')APICallAttemptEventr(r)r\append)r r*rDr r r r3s z!APICallEvent.new_api_call_attempt)NNF)rrrr r3 __classcell__r r r]r r,s %r,cseZdZdfdd ZZS)r^Nc sDtt|j|||d||_||_||_||_||_| |_| |_ dS)aMonitor event for a single API call attempt This event corresponds to a single HTTP request attempt in completing the entire client method call. :type service: str :param service: A string identifying the service associated to the event :type operation: str :param operation: A string identifying the operation of service associated to the event :type timestamp: int :param timestamp: Epoch time in milliseconds from when the HTTP request started :type latency: int :param latency: The time in milliseconds to complete the HTTP request whether it succeeded or failed :type url: str :param url: The URL the attempt was sent to :type http_status_code: int :param http_status_code: The HTTP status code of the HTTP response if there was a response :type request_headers: dict :param request_headers: The HTTP headers sent in making the HTTP request :type response_headers: dict :param response_headers: The HTTP headers returned in the HTTP response if there was a response :type parsed_error: dict :param parsed_error: The error parsed if the service returned an error back :type wire_exception: Exception :param wire_exception: The exception raised in sending the HTTP request (i.e. ConnectionError) r'N) r[r^r r=r6r>r5r?rArB) r r(r)r*r=r6r>r5r?rArBr]r r r s0 zAPICallAttemptEvent.__init__)NNNNNNN)rrrr r`r r r]r r^sr^c @s&eZdZdZdZdZdZdZddddZe d e d d Z d d ddddddddddg Z ddZ ddZddZddZd d!Zd"d#Zd$d%Zd&d'Zd(d)Zd*d+Zd,d-Zd.d/Zd0d1Zd2d3Zd4d5Zd6d7Zd8d9Zd:d;Zdd?Z d@dAZ!dBdCZ"dDdEZ#dFdGZ$dHdIZ%dJS)K CSMSerializeriZXAmznRequestIdZ XAmzRequestIdZXAmzId2)zx-amzn-requestidzx-amz-request-idz x-amz-id-2zSAWS4-HMAC-SHA256 Credential=(?P\w+)/\d+/(?P[a-z0-9-]+)/zAWS (?P\w+):)v4Zs3r(r)r*r\r=rFr6r5r>r?rArBcCs||||_dS)zSerializes monitor events to CSM (Client Side Monitoring) format :type csm_client_id: str :param csm_client_id: The application identifier to associate to the serialized events N)_validate_client_id csm_client_idr rgr r r r Os zCSMSerializer.__init__cCs$t||jkr td||jfdS)NzTThe value provided for csm_client_id: %s exceeds the maximum length of %s characters)len_MAX_CLIENT_ID_LENGTH ValueErrorrhr r r rfYsz!CSMSerializer._validate_client_idcCsf||}||}||d<|jD]0}t||d}|dk r"t|d||||dq"ttj|ddS)zSerializes a monitor event to the CSM format :type event: BaseMonitorEvent :param event: The event to serialize to bytes :rtype: bytes :returns: The CSM serialized form of the event ZTypeNZ _serialize_) event_type),:) separators)_get_base_event_dict_get_event_type_SERIALIZEABLE_EVENT_PROPERTIESr$rjsondumps)r rR event_dictrlattrvaluer r r serializeas      zCSMSerializer.serializecCs d|jdS)N)VersionZClientId)rgrQr r r rpusz"CSMSerializer._get_base_event_dictcKs ||d<dS)NZServicer )r r(rur0r r r _serialize_service{sz CSMSerializer._serialize_servicecKs ||d<dS)NZApir )r r)rur0r r r _serialize_operation~sz"CSMSerializer._serialize_operationcKs ||d<dS)NZ Timestampr )r r*rur0r r r _serialize_timestampsz"CSMSerializer._serialize_timestampcKs$t||d<|r |||ddS)NZ AttemptCount)ri_add_fields_from_last_attempt)r r\rur0r r r _serialize_attemptss z!CSMSerializer._serialize_attemptscCs~|jr2||j}|dk r"||d<||j|d<|jdk rF|j|d<|jdk r`||j|d|jdk rz||j|ddS)NRegion UserAgentZFinalHttpStatusCodeApiCall)r5 _get_region_get_user_agentr>rA_serialize_parsed_errorrB_serialize_wire_exception)r ru last_attemptregionr r r rs*     z+CSMSerializer._add_fields_from_last_attemptcCs&|dkr||d<n|dkr"||d<dS)NrZLatencyApiCallAttemptZAttemptLatencyr )r r=rurlr r r _serialize_latencys z CSMSerializer._serialize_latencycKs|rdnd|d<dS)NryrZMaxRetriesExceededr )r rFrur0r r r _serialize_retries_exceededsz)CSMSerializer._serialize_retries_exceededcKst|j|d<dS)NZFqdn)rnetloc)r r6rur0r r r _serialize_urlszCSMSerializer._serialize_urlcKsX|||d<||r&|||d<||}|dk r@||d<d|krT|d|d<dS)NrZ AccessKeyrzX-Amz-Security-TokenZ SessionToken)r _is_signed_get_access_keyr)r r5rur0rr r r _serialize_request_headerss  z(CSMSerializer._serialize_request_headerscKs ||d<dS)NZHttpStatusCoder )r r>rur0r r r _serialize_http_status_codesz)CSMSerializer._serialize_http_status_codecKs,|jD]\}}||kr ||||<q dSrP)"_RESPONSE_HEADERS_TO_EVENT_ENTRIESitems)r r?rur0headerentryr r r _serialize_response_headerssz)CSMSerializer._serialize_response_headerscKsH|dkr dnd}||d|j||d<||d|j||d<dS)NrFinalZCodeZ AwsExceptionMessageZAwsExceptionMessage) _truncate_MAX_ERROR_CODE_LENGTH_MAX_MESSAGE_LENGTH)r rArurlr0 field_prefixr r r rs z%CSMSerializer._serialize_parsed_errorcKsH|dkr dnd}||jj|j||d<|t||j||d<dS)NrrrZ SdkExceptionZSdkExceptionMessage)rrVr_MAX_EXCEPTION_CLASS_LENGTHstrr)r rBrurlr0rr r r rs z'CSMSerializer._serialize_wire_exceptioncCs t|trdSt|trdSdS)Nrr)rMr,r^rQr r r rqs  zCSMSerializer._get_event_typecCs"||}||\}}|dS)NZ access_key)_get_auth_value_get_auth_matchgroup)r r5auth_valr# auth_matchr r r rs zCSMSerializer._get_access_keycCs<||sdS||}||\}}|dkr2dS|dS)NreZsigning_region)rrrr)r r5rsignature_versionrr r r rs  zCSMSerializer._get_regioncCs|t|dd|jS)Nz User-Agentr)rrr@_MAX_USER_AGENT_LENGTHr r5r r r rszCSMSerializer._get_user_agentcCsd|kSN Authorizationr rr r r rszCSMSerializer._is_signedcCs t|dSr)rrr r r rszCSMSerializer._get_auth_valuecCs2|jD]"\}}||}|r ||fSq dS)N)NN) _AUTH_REGEXSrmatch)r rrregexrr r r rs  zCSMSerializer._get_auth_matchcCs*t||kr&td|||d|S|S)Nz6Truncating following value to maximum length of %s: %s)rirr)r text max_lengthr r r rs  zCSMSerializer._truncateN)&rrrrjrrrrrrecompilerrrr rfrxrpr{r|r}rrrrrrrrrrrqrrrrrrrr r r r ra+sl     rac@s eZdZdZddZddZdS)SocketPublisheri cCs||_||f|_||_dS)a)Publishes monitor events to a socket :type socket: socket.socket :param socket: The socket object to use to publish events :type host: string :param host: The host to send events to :type port: integer :param port: The port on the host to send events to :param serializer: The serializer to use to serialize the event to a form that can be published to the socket. This must have a `serialize()` method that accepts a monitor event and return bytes N)_socket_address _serializer)r sockethostport serializerr r r r s zSocketPublisher.__init__cCsF|j|}t||jkr2tdt||jdS|j||jdS)zPublishes a specified monitor event :type event: BaseMonitorEvent :param event: The monitor event to be sent over the publisher's socket to the desired address. z`Serialized event of size %s exceeds the maximum length allowed: %s. Not sending event to socket.N) rrxri_MAX_MONITOR_EVENT_LENGTHrrrsendtor)r rRZserialized_eventr r r rs zSocketPublisher.publishN)rrrrr rr r r r rsr)rsloggingrrZbotocore.compatrrrZbotocore.retryhandlerrrO getLoggerrrobjectrrrUr,r^rarr r r r  s  )Z6=U