
    @OOf*                        d dl Z d dlZd dlZd dlZd dlZd dlZd dlmZ d dlm	Z	 d dlm
Z
 d dlmZ d dlmZ d dlmZ d dlmZ d d	lmZ d d
lmZ d dlmZ d dlmZ d dlmZ d dlmZ d dlmZ d dlmZ d dlmZ d dlmZ d dlm Z  d dlm!Z! d dlm"Z" d dl#m$Z$ d dl#m%Z% d dl#m&Z& d dl'm(Z( d dl'm)Z) d dl'm*Z* d dl+m,Z, d dl+m-Z- d dl.m/Z/ de0d e1fd!Z2de1e0z  d e0fd"Z3 G d# d$ejh                        Z5e G d% d&ejl                               Z7e G d' d(e7             Z8e G d) d*e7             Z9 G d+ d,ejl                        Z: G d- d.e:      Z; G d/ d0e:      Z< G d1 d2ejz                        Z>g d3Z?y)4    N)Callable)Iterable)Iterator)Mapping)Sequence)	dataclass)fields)
formatdate)	mktime_tz)parsedate_tz)Any)castflow)	multidict)serializable)encoding)cookies)	multipart)status_codes)url)assemble_content_type)infer_content_encoding)parse_content_type)human)strutils)	typecheckalways_bytes)
always_str)WebSocketDataxreturnc                 &    | j                  dd      S Nutf-8surrogateescape)decoder"   s    O/var/www/premiumrankchecker/venv/lib/python3.12/site-packages/mitmproxy/http.py_nativer+   (   s    88G.//    c                 0    t        j                  | dd      S r%   )r   r   r)   s    r*   _always_bytesr.   ,   s      G->??r,   c                   8    e Zd ZU dZddeeeef      f fdZeeeef   df   ed<   e	de
fd       Ze	de
fd       ZdefdZd	e
ez  dd
f fdZdee
   f fdZde
ez  dee
   f fdZde
ez  dee
ez     f fdZded	e
ez  de
ez  f fdZd fd	Z xZS )Headersa  
    Header class which allows both convenient access to individual headers as well as
    direct access to the underlying raw data. Provides a full dictionary interface.

    Create headers with keyword arguments:
    >>> h = Headers(host="example.com", content_type="application/xml")

    Headers mostly behave like a normal dict:
    >>> h["Host"]
    "example.com"

    Headers are case insensitive:
    >>> h["host"]
    "example.com"

    Headers can also be created from a list of raw (header_name, header_value) byte tuples:
    >>> h = Headers([
        (b"Host",b"example.com"),
        (b"Accept",b"text/html"),
        (b"accept",b"application/xml")
    ])

    Multiple headers are folded into a single header as per RFC 7230:
    >>> h["Accept"]
    "text/html, application/xml"

    Setting a header removes all existing headers with the same name:
    >>> h["Accept"] = "application/text"
    >>> h["Accept"]
    "application/text"

    `bytes(h)` returns an HTTP/1 header block:
    >>> print(bytes(h))
    Host: example.com
    Accept: application/text

    For full control, the raw header fields can be accessed:
    >>> h.fields

    Caveats:
     - For use with the "Set-Cookie" and "Cookie" headers, either use `Response.cookies` or see `Headers.get_all`.
    r	   c           
      X   t         |   |       | j                  D ]0  \  }}t        |t              rt        |t              r't        d       | j                  |j                         D ci c]*  \  }}t        |      j                  dd      t        |      , c}}       yc c}}w )a5  
        *Args:*
         - *fields:* (optional) list of ``(name, value)`` header byte tuples,
           e.g. ``[(b"Host", b"example.com")]``. All names and values must be bytes.
         - *\*\*headers:* Additional headers to set. Will overwrite existing values from `fields`.
           For convenience, underscores in header names will be transformed to dashes -
           this behaviour does not extend to other methods.

        If ``**headers`` contains multiple keys that have equal ``.lower()`` representations,
        the behavior is undefined.
        zHeader fields must be bytes.   _   -N)
super__init__r	   
isinstancebytes	TypeErrorupdateitemsr.   replace)selfr	   headerskeyvaluename	__class__s         r*   r5   zHeaders.__init__]   s     	 ++ 	@JCc5)E51I >??	@
 	 $+==?D% d#++D$7u9MM	
s   ./B&
.r#   c                 $    dj                  |       S )N, join)valuess    r*   _reduce_valueszHeaders._reduce_valuesy   s     yy  r,   c                 "    | j                         S N)lower)r>   s    r*   _kconvzHeaders._kconv~   s     yy{r,   c                 f    | j                   r%dj                  d | j                   D              dz   S y)Ns   
c              3   >   K   | ]  }d j                  |        yw)s   : NrD   ).0fields     r*   	<genexpr>z$Headers.__bytes__.<locals>.<genexpr>   s     Ke

5 1Ks   r,   )r	   rE   r<   s    r*   	__bytes__zHeaders.__bytes__   s*    ;;<<Kt{{KKgUUr,   r>   Nc                 :    t        |      }t        | 	  |       y rI   )r.   r4   __delitem__)r<   r>   rA   s     r*   rT   zHeaders.__delitem__   s    C C r,   c              #   N   K   t         |          D ]  }t        |        y wrI   )r4   __iter__r+   )r<   r"   rA   s     r*   rV   zHeaders.__iter__   s(     !# 	A!*	s   "%r@   c                 p    t        |      }t        | 	  |      D cg c]  }t        |       c}S c c}w )a  
        Like `Headers.get`, but does not fold multiple headers into a single one.
        This is useful for Set-Cookie and Cookie headers, which do not support folding.

        *See also:*
         - <https://tools.ietf.org/html/rfc7230#section-3.2.2>
         - <https://datatracker.ietf.org/doc/html/rfc6265#section-5.4>
         - <https://datatracker.ietf.org/doc/html/rfc7540#section-8.1.2.5>
        )r.   r4   get_allr+   )r<   r@   r"   rA   s      r*   rX   zHeaders.get_all   s0     T"$)GOD$9:q
:::s   3rF   c                 t    t        |      }|D cg c]  }t        |       }}t        | 	  ||      S c c}w )zc
        Explicitly set multiple headers for the given key.
        See `Headers.get_all`.
        )r.   r4   set_all)r<   r@   rF   r"   rA   s       r*   rZ   zHeaders.set_all   s=    
 T",23q-"33wtV,, 4s   5indexr?   c                 T    t        |      }t        |      }t        | 	  |||       y rI   )r.   r4   insert)r<   r[   r>   r?   rA   s       r*   r]   zHeaders.insert   s'    C e$uc5)r,   c                 J    |rd | j                   D        S t        | 	         S )Nc              3   N   K   | ]  \  }}t        |      t        |      f  y wrI   )r+   rN   kvs      r*   rP   z Headers.items.<locals>.<genexpr>   s!     EAWQZ,Es   #%)r	   r4   r:   )r<   multirA   s     r*   r:   zHeaders.items   s!    EEE7=?"r,   ) )F)__name__
__module____qualname____doc__r   tupler7   r5   __annotations__staticmethodstrrG   rK   rR   rT   r   rV   listrX   rZ   intr]   r:   __classcell__rA   s   @r*   r0   r0   1   s   )V
xeUl(;< 
4 %u%s*++!# ! ! s  5 !sU{ !t !(3- ;C%K ;DI ;-C%K -#+1F -*C *cEk *#+ *
# #r,   r0   c                       e Zd ZU eed<   eed<   edz  ed<   edz  ed<   eed<   edz  ed<   	 d Zd	 Zd
 Z	e
d        Zy)MessageDatahttp_versionr=   Ncontenttrailerstimestamp_starttimestamp_endc                     t        |       D ]C  }t        | |j                        }t        j                  |j                  ||j
                         E y rI   )r	   getattrr@   r   check_option_typetype)r<   rO   vals      r*   __post_init__zMessageData.__post_init__   sA     IdEJJ/++EJJUZZHIr,   c                     |j                         D ]-  \  }}|dv r|t        j                  |      }t        | ||       / y )N)r=   ru   )r:   r0   
from_statesetattr)r<   statera   rb   s       r*   	set_statezMessageData.set_state   sD    KKM 	 DAq++&&q)D!Q	 r,   c                     t        |       j                         }|d   j                         |d<   |d   |d   j                         |d<   |S )Nr=   ru   )varscopy	get_stater<   r   s     r*   r   zMessageData.get_state   sR    T
! +557i( %j 1 ; ; =E*r,   c                     t         j                  |d         |d<   |d   t         j                  |d         |d<    | di |S )Nr=   ru   rd   )r0   r   clsr   s     r*   r   zMessageData.from_state   sM    "--eI.>?i( ' 2 253D EE*|U|r,   )re   rf   rg   r7   rj   r0   floatr}   r   r   classmethodr   rd   r,   r*   rr   rr      s[    T\n4< 	I
   r,   rr   c                   J    e Zd ZU eed<   eed<   eed<   eed<   eed<   eed<   y)RequestDatahostportmethodscheme	authoritypathN)re   rf   rg   rl   rj   rn   r7   rd   r,   r*   r   r      s!    
I
IMM
Kr,   r   c                   "    e Zd ZU eed<   eed<   y)ResponseDatastatus_codereasonN)re   rf   rg   rn   rj   r7   rd   r,   r*   r   r      s    Mr,   r   c                      e Zd ZU dZed        Zd Zd Zee	d<   dZ
eegee   ez  f   ez  e	d<   	 edefd	       Zej$                  d
eez  ddfd       Zedefd       Zedefd       Zedefd       Zedefd       Zedefd       Zej$                  deddfd       Zededz  fd       Zej$                  dedz  ddfd       Zededz  fd       Zej$                  dedz  ddfd       Zededz  fd       Zej$                  dedz  ddfd       Zededz  fd       Zej$                  dedz  ddfd       Zdedz  ddfdZd/dededz  fd Zd!edz  ddfd"Zd/dededz  fd#Z ede!fd$       Z"e"j$                  d%e!ddfd&       Z"ede!dz  fd'       Z#e#j$                  d(e!dz  fd)       Z#d/deddfd*Z$d+eddfd,Z%d-e&de&fd.Z'y)0Messagez(Base class for `Request` and `Response`.c                      | di |S )Nrd   rd   r   s     r*   r   zMessage.from_state   s    |U|r,   c                 6    | j                   j                         S rI   )datar   rQ   s    r*   r   zMessage.get_state   s    yy""$$r,   c                 :    | j                   j                  |       y rI   )r   r   r   s     r*   r   zMessage.set_state   s    		E"r,   r   Fstreamr#   c                 N    | j                   j                  j                  dd      S )z>
        HTTP version string, for example `HTTP/1.1`.
        r&   r'   )r   rs   r(   rQ   s    r*   rs   zMessage.http_version  s"    
 yy%%,,W6GHHr,   rs   Nc                 P    t        j                  |dd      | j                  _        y r%   )r   r   r   rs   )r<   rs   s     r*   rs   zMessage.http_version  s!    !)!6!6'#4"
		r,   c                 4    | j                   j                  dk(  S )Ns   HTTP/1.0r   rs   rQ   s    r*   	is_http10zMessage.is_http10      yy%%44r,   c                 4    | j                   j                  dk(  S )N   HTTP/1.1r   rQ   s    r*   	is_http11zMessage.is_http11  r   r,   c                 4    | j                   j                  dk(  S )Ns   HTTP/2.0r   rQ   s    r*   is_http2zMessage.is_http2  r   r,   c                 4    | j                   j                  dk(  S )Ns   HTTP/3r   rQ   s    r*   is_http3zMessage.is_http3  s    yy%%22r,   c                 .    | j                   j                  S )z#
        The HTTP headers.
        r   r=   rQ   s    r*   r=   zMessage.headers#  s    
 yy   r,   hc                 &    || j                   _        y rI   r   r<   r   s     r*   r=   zMessage.headers*  s    		r,   c                 .    | j                   j                  S )zi
        The [HTTP trailers](https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Trailer).
        r   ru   rQ   s    r*   ru   zMessage.trailers.  s    
 yy!!!r,   c                 &    || j                   _        y rI   r   r   s     r*   ru   zMessage.trailers5  s    		r,   c                 .    | j                   j                  S )z
        The raw (potentially compressed) HTTP message body.

        In contrast to `Message.content` and `Message.text`, accessing this property never raises.

        *See also:* `Message.content`, `Message.text`
        r   rt   rQ   s    r*   raw_contentzMessage.raw_content9  s     yy   r,   rt   c                 &    || j                   _        y rI   r   )r<   rt   s     r*   r   zMessage.raw_contentD  s    #		r,   c                 "    | j                         S )z
        The uncompressed HTTP message body as bytes.

        Accessing this attribute may raise a `ValueError` when the HTTP content-encoding is invalid.

        *See also:* `Message.raw_content`, `Message.text`
        )get_contentrQ   s    r*   rt   zMessage.contentH  s     !!r,   r?   c                 &    | j                  |       y rI   )set_contentr<   r?   s     r*   rt   zMessage.contentS  s    r,   c                 "    | j                         S )z
        The uncompressed and decoded HTTP message body as text.

        Accessing this attribute may raise a `ValueError` when either content-encoding or charset is invalid.

        *See also:* `Message.raw_content`, `Message.content`
        )get_textrQ   s    r*   textzMessage.textW  s     }}r,   c                 &    | j                  |       y rI   )set_textr   s     r*   r   zMessage.textb  s    er,   c                    |d | _         y t        |t              s"t        dt	        |      j
                   d      | j                  j                  d      }	 t        j                  ||xs d      | _         d| j                  v ry t        t        | j                               | j                  d<   y # t        $ r | j                  d= || _         Y Zw xY w)Nz#Message content must be bytes, not z/. Please use .text if you want to assign a str.content-encodingidentityztransfer-encodingzcontent-length)r   r6   r7   r8   r{   re   r=   getr   encode
ValueErrorrl   len)r<   r?   ces      r*   r   zMessage.set_contentf  s    =#D%'5d5k6J6J5K L@ @  \\01	%'ub6FJGD $,,. -0T5E5E1F-GDLL)*  	% /0$D		%s   B3 3CCstrictc                 ,   | j                   y| j                  j                  d      }|rA	 t        j                  | j                   |      }t        |t              rt        d|       |S | j                   S # t        $ r |r | j                   cY S w xY w)z
        Similar to `Message.content`, but does not raise if `strict` is `False`.
        Instead, the compressed message body is returned as-is.
        Nr   zInvalid Content-Encoding: )r   r=   r   r   r(   r6   rl   r   )r<   r   r   rt   s       r*   r   zMessage.get_content  s    
 #\\01	("//$*:*:B?gs+$'A"%FGG ###  ('''(s   ?A8 8BBr   c                    |d | _         y t        | j                  j                  dd            }	 t	        t
        t        j                  ||            | _         y # t        $ re t        | j                  j                  dd            xs ddi f}d|d   d<   t        | | j                  d<   d}|j                  |d	      | _         Y y w xY w)
Ncontent-type r   plainr&      charsetutf8r'   )rt   r   r=   r   r   r7   r   r   r   r   r   )r<   r   enccts       r*   r   zMessage.set_text  s    <DL$T\\%5%5nb%IJ	?xtS'ABDL 
	?#DLL$4$4^R$HI NB
  'BqE)+@"+EDLL(C;;s,=>DL
	?s   )A A+C	C	c                    | j                  |      }|yt        | j                  j                  dd      |      }	 t	        t
        t        j                  ||            S # t        $ r |r |j                  dd      cY S w xY w)z
        Similar to `Message.text`, but does not raise if `strict` is `False`.
        Instead, the message body is returned as surrogate-escaped UTF-8.
        Nr   r   r   r'   )	r   r   r=   r   r   rl   r   r(   r   )r<   r   rt   r   s       r*   r   zMessage.get_text  s}    
 ""6*?$T\\%5%5nb%I7S	=X__Wc:;; 	=>>&*;<<	=s   #A   B Bc                 .    | j                   j                  S )z0
        *Timestamp:* Headers received.
        r   rv   rQ   s    r*   rv   zMessage.timestamp_start  s    
 yy(((r,   rv   c                 &    || j                   _        y rI   r   )r<   rv   s     r*   rv   zMessage.timestamp_start  s    $3		!r,   c                 .    | j                   j                  S )z2
        *Timestamp:* Last byte received.
        r   rw   rQ   s    r*   rw   zMessage.timestamp_end  s    
 yy&&&r,   rw   c                 &    || j                   _        y rI   r   )r<   rw   s     r*   rw   zMessage.timestamp_end  s    "/		r,   c                 l    | j                  |      }| j                  j                  dd       || _        y)a  
        Decodes body based on the current Content-Encoding header, then
        removes the header. If there is no Content-Encoding header, no
        action is taken.

        *Raises:*
         - `ValueError`, when the content-encoding is invalid and strict is True.
        r   N)r   r=   poprt   )r<   r   decodeds      r*   r(   zMessage.decode  s0     ""6*+T2r,   r   c                     || j                   d<   | j                  | _        d| j                   vrt        dt	        |             y)a-  
        Encodes body with the given encoding, where e is "gzip", "deflate", "identity", "br", or "zstd".
        Any existing content-encodings are overwritten, the content is not decoded beforehand.

        *Raises:*
         - `ValueError`, when the specified content-encoding is invalid.
        r   zInvalid content encoding N)r=   r   rt   r   repr)r<   r   s     r*   r   zMessage.encode  sI     ,4'(''T\\18h8HIJJ 2r,   kwargsc                 l    | j                  d      }|t        d      t        j                  |fi |S )a  
        Returns the JSON encoded content of the response, if any.
        `**kwargs` are optional arguments that will be
        passed to `json.loads()`.

        Will raise if the content can not be decoded and then parsed as JSON.

        *Raises:*
         - `json.decoder.JSONDecodeError` if content is not valid JSON.
         - `TypeError` if the content is not available, for example because the response
            has been streamed.
        Fr   z!Message content is not available.)r   r8   jsonloads)r<   r   rt   s      r*   r   zMessage.json  s<     ""%"0??@@::g000r,   )T)(re   rf   rg   rh   r   r   r   r   rr   rj   r   r   r7   r   boolpropertyrl   rs   setterr   r   r   r   r0   r=   ru   r   rt   r   r   r   r   r   r   rv   rw   r(   r   r   r   rd   r,   r*   r   r      s   2 %# @EFHeWhuo556=E Ic I I 
u 
 
 

 54 5 5 54 5 5 5$ 5 5 3$ 3 3 ! ! ! ^^ T   "'D. " " __'D. T   !UT\ ! ! $54< $D $ $ " " " ^^ UT\  d     cDj   
[[#*   H H$ H2$$ $%$, $,?S4Z ?D ?(=t =sTz =  ) ) ) 4u 4 4 4 'ut| ' ' 054< 0 0T T Ks Kt K1S 1S 1r,   r   c                      e Zd ZU dZeed<   dedededededed	ed
e	e
e
eef   df   z  dedz  de	e
e
eef   df   z  dz  dededz  fdZdefdZe	 	 dCdededeez  d
e	eeez  eez  f   z  ee
eef      z  dd f
d       Zedefd       Zedefd       Zej*                  deez  ddfd       Zedefd       Zej*                  deez  ddfd       Zedefd       Zej*                  deez  ddfd       Zedefd       Zej*                  deez  ddfd       Zededz  fd        Zej*                  ddez  ez  ddfd!       Zedefd"       Zej*                  deddfd#       ZdDd$Zedefd%       Zej*                  deez  ddfd&       Zedefd'       Zej*                  deez  ddfd(       Zedefd)       Zedefd*       Zd+ Z d, Z!ede"jF                  eef   fd-       Z$e$j*                  d.        Z$d/ Z%d0 Z&ede"jF                  eef   fd1       Z'e'j*                  d2        Z'ede
edf   fd3       Z(e(j*                  d4ee   fd5       Z(dDd6Z)dDd7Z*dDd8Z+d9 Z,d:e-e
eef      ddfd;Z.ede"jF                  eef   fd<       Z/e/j*                  d=        Z/de0e
eef      fd>Z1d?e0e
eef      ddfd@Z2ede"jF                  eef   fdA       Z3e3j*                  d?e0e
eef      ddfdB       Z3y)ERequestz
    An HTTP request.
    r   r   r   r   r   r   r   rs   r=   .rt   Nru   rv   rw   c                    t        |t              r|j                  dd      }t        |t              r|j	                  dd      }t        |t              r|j	                  dd      }t        |t              r|j	                  dd      }t        |t              r|j	                  dd      }t        |t              r|j	                  dd      }t        |	t              r!t        dt        |	      j                         t        |t              st        |      }|
t        |
t              st        |
      }
t        |||||||||	|
||      | _
        y )Nidnar   asciiContent must be bytes, not )r   r   r   r   r   r   rs   r=   rt   ru   rv   rw   )r6   r7   r(   rl   r   r   r{   re   r0   r   r   )r<   r   r   r   r   r   r   rs   r=   rt   ru   rv   rw   s                r*   r5   zRequest.__init__  s)     dE";;vx0Dfc"]]7H5Ffc"]]7H5Fi%!(((;IdC ;;w1DlC('..wALgs#:4=;Q;Q:RSTT'7+g&G
8W(Ex(H%+'
	r,   r#   c                     | j                   r(| j                  r| j                    d| j                   }nd}| j                  xs d}d| j                   d| | dS )N:r   zRequest( ))r   r   r   r   )r<   hostportr   s      r*   __repr__zRequest.__repr__7  sV    99))Adii[1HHyyB$++az$q99r,   r   c                 \   t        |t              rnzt        |t              r!t        d |j                         D              }nIt        |t              rt        |      }n-t        dj                  t        |      j                               | dd|j                  dd      dddd|dd	t        j                         t        j                               }||_        t        |t              r	||_        |S t        |t              r	||_        |S t        d
t        |      j                   d      )z>
        Simplified API for creating request objects.
        c              3   V   K   | ]!  \  }}t        |d d      t        |d d      f # ywr&   r'   Nr   r`   s      r*   rP   zRequest.make.<locals>.<genexpr>P  :      
 Aq !G->? G->?   ')6Expected headers to be an iterable or dict, but is {}.r   r   r&   r'   r,   r   N,Expected content to be str or bytes, but is .)r6   r0   dictr:   r   r8   formatr{   re   r   timer   r7   rt   rl   r   )r   r   r   rt   r=   reqs         r*   makezRequest.make?  s"    gw'& 
 $MMO G *g&GHOOM**  MM'#45IIKIIK
 gu%!CK 
 %CH 
	 >tG}?U?U>VVWX r,   c                 >    | j                   dk(  ry| j                  ryy)z
        *Read-only:* HTTP request form as defined in [RFC 7230](https://tools.ietf.org/html/rfc7230#section-5.3).

        origin-form and asterisk-form are subsumed as "relative".
        CONNECTr   absoluterelative)r   r   rQ   s    r*   first_line_formatzRequest.first_line_format|  s      ;;)#^^r,   c                 j    | j                   j                  j                  dd      j                         S )z2
        HTTP request method, e.g. "GET".
        r&   r'   )r   r   r(   upperrQ   s    r*   r   zRequest.method  s+    
 yy&&w0ABHHJJr,   r|   c                 <    t        |dd      | j                  _        y r%   )r   r   r   r<   r|   s     r*   r   zRequest.method      'W6GH		r,   c                 N    | j                   j                  j                  dd      S )zI
        HTTP request scheme, which should be "http" or "https".
        r&   r'   )r   r   r(   rQ   s    r*   r   zRequest.scheme  s"    
 yy&&w0ABBr,   c                 <    t        |dd      | j                  _        y r%   )r   r   r   r  s     r*   r   zRequest.scheme  r  r,   c                     	 | j                   j                  j                  d      S # t        $ r) | j                   j                  j                  dd      cY S w xY w)a  
        HTTP request authority.

        For HTTP/1, this is the authority portion of the request target
        (in either absolute-form or authority-form).
        For origin-form and asterisk-form requests, this property is set to an empty string.

        For HTTP/2, this is the :authority pseudo header.

        *See also:* `Request.host`, `Request.host_header`, `Request.pretty_host`
        r   r   r'   )r   r   r(   UnicodeErrorrQ   s    r*   r   zRequest.authority  sR    	I99&&--f55 	I99&&--f6GHH	Is   $' /AAc                     t        |t              r	 |j                  dd      }|| j                  _        y # t        $ r |j                  dd      }Y /w xY w)Nr   r   r   r'   )r6   rl   r   r  r   r   r  s     r*   r   zRequest.authority  sQ    c3<jj2 "		   <jj):;<s   6 AAc                 .    | j                   j                  S )a  
        Target server for this request. This may be parsed from the raw request
        (e.g. from a ``GET http://example.com/ HTTP/1.1`` request line)
        or inferred from the proxy mode (e.g. an IP in transparent mode).

        Setting the host attribute also updates the host header and authority information, if present.

        *See also:* `Request.authority`, `Request.host_header`, `Request.pretty_host`
        )r   r   rQ   s    r*   r   zRequest.host  s     yy~~r,   c                 \    t        |dd      | j                  _        | j                          y )Nr   r   )r    r   r   _update_host_and_authorityr  s     r*   r   zRequest.host  s"    #C:		'')r,   c                     | j                   s| j                  r4| j                  xs& | j                  j                  j                  dd      S | j                  j                  j                  dd      S )a  
        The request's host/authority header.

        This property maps to either ``request.headers["Host"]`` or
        ``request.authority``, depending on whether it's HTTP/1.x or HTTP/2.0.

        *See also:* `Request.authority`,`Request.host`, `Request.pretty_host`
        HostN)r   r   r   r   r=   r   rQ   s    r*   host_headerzRequest.host_header  sT     ==DMM>>HTYY%6%6%:%:64%HH99$$((66r,   c                 >   |F| j                   s| j                  rd| j                  _        | j                  j                  dd        y | j                   s| j                  r|| _        | j                   s| j                  rd| j                  v r|| j                  d<   y y )Nr,   r  )r   r   r   r   r=   r   r  s     r*   r  zRequest.host_header  st    ;}}&)		#LLVT*}}!$MMT]]v7M'*V$ 8Nr,   c                 .    | j                   j                  S )z
        Target port.
        )r   r   rQ   s    r*   r   zRequest.port  s    
 yy~~r,   c                     t        |t              st        d|d      || j                  _        | j                          y )NzPort must be an integer, not r   )r6   rn   r   r   r   r  )r<   r   s     r*   r   zRequest.port  s8    $$<THAFGG		'')r,   c                    t        j                  | j                  | j                  | j                        }d| j
                  j                  v r|| j
                  j                  d<   | j
                  j                  r|| _        y y )Nr  )r   r   r   r   r   r   r=   r   r  s     r*   r  z"Request._update_host_and_authority  sa    ll4;;		499= TYY&&&(+DIIf%99 DN r,   c                 N    | j                   j                  j                  dd      S )aS  
        HTTP request path, e.g. "/index.html" or "/index.html?a=b".
        Usually starts with a slash, except for OPTIONS requests, which may just be "*".

        This attribute includes both path and query parts of the target URI
        (see Sections 3.3 and 3.4 of [RFC3986](https://datatracker.ietf.org/doc/html/rfc3986)).
        r&   r'   )r   r   r(   rQ   s    r*   r   zRequest.path  s      yy~~$$W.?@@r,   c                 <    t        |dd      | j                  _        y r%   )r   r   r   r  s     r*   r   zRequest.path  s    %c74EF		r,   c                     | j                   dk(  r| j                   d| j                   S t        j                  | j
                  | j                  | j                  | j                        S )z
        The full URL string, constructed from `Request.scheme`, `Request.host`, `Request.port` and `Request.path`.

        Settings this property updates these attributes as well.
        r   r   )r  r   r   r   unparser   r   rQ   s    r*   r   zRequest.url  sP     !![0ii[$))--{{4;;		499diiHHr,   c                 z    t        |dd      }t        j                  |      \  | _        | _        | _        | _        y r%   )r    r   parser   r   r   r   r  s     r*   r   zRequest.url  s/    g'897:yy~4TY	49r,   c                 j    | j                   }|rt        j                  |d      d   S | j                  S )ar  
        *Read-only:* Like `Request.host`, but using `Request.host_header` header as an additional (preferred) data source.
        This is useful in transparent mode where `Request.host` is only an IP address.

        *Warning:* When working in adversarial environments, this may not reflect the actual destination
        as the Host header could be spoofed.
        Fcheckr   )r  r   parse_authorityr   )r<   r   s     r*   pretty_hostzRequest.pretty_host!  s4     $$	&&y>qAA99r,   c                 F   | j                   dk(  r| j                  S | j                  }|s| j                  S t        j                  |d      \  }}|xs# t        j
                  | j                        xs d}t        j                  | j                  ||| j                        S )zm
        *Read-only:* Like `Request.url`, but using `Request.pretty_host` instead of `Request.host`.
        r   Fr#  i  )	r  r   r  r   r%  default_portr   r  r   )r<   r  r&  pretty_ports       r*   
pretty_urlzRequest.pretty_url0  s    
 !![0>>!&&88O#&#6#6{%#P [!IS%5%5dkk%BIc{{4;;[$))LLr,   c                     t         j                  j                  | j                        j                  }t        t        j                  |            S rI   )urllibr!  urlparser   queryri   r(   )r<   r.  s     r*   
_get_queryzRequest._get_queryA  s4    %%dhh/55SZZ&''r,   c                     t        j                  |      }t        j                  j	                  | j                         \  }}}}}}t        j                  j                  dd||||g      | _        y )Nr   )r   r   r,  r!  r-  
urlunparser   )r<   
query_datar.  _r   paramsfragments          r*   
_set_queryzRequest._set_queryE  sX    

:&*0,,*?*?*I'1dFAxLL++RT65(,ST	r,   c                 V    t        j                  | j                  | j                        S )z
        The request query as a mutable mapping view on the request's path.
        For the most part, this behaves like a dictionary.
        Modifications to the MultiDictView update `Request.path`, and vice versa.
        )r   MultiDictViewr/  r6  rQ   s    r*   r.  zRequest.queryJ  s     &&tHHr,   c                 &    | j                  |       y rI   )r6  r   s     r*   r.  zRequest.queryS  s    r,   c                 t    | j                   j                  d      }t        t        j                  |            S )NCookie)r=   rX   ri   r   parse_cookie_headersr   s     r*   _get_cookieszRequest._get_cookiesW  s,    LL  *W11!455r,   c                 H    t        j                  |      | j                  d<   y )Ncookie)r   format_cookie_headerr=   r   s     r*   _set_cookieszRequest._set_cookies[  s    !(!=!=e!DXr,   c                 V    t        j                  | j                  | j                        S )z
        The request cookies.
        For the most part, this behaves like a dictionary.
        Modifications to the MultiDictView update `Request.headers`, and vice versa.
        r   r8  r=  rA  rQ   s    r*   r   zRequest.cookies^  s#     &&t'8'8$:K:KLLr,   c                 &    | j                  |       y rI   rA  r   s     r*   r   zRequest.cookiesg      % r,   c                     t         j                  j                  | j                        j                  }t        d |j                  d      D              S )zc
        The URL's path components as a tuple of strings.
        Components are unquoted.
        c              3   L   K   | ]  }|st        j                  |        y wrI   )r   unquote)rN   is     r*   rP   z*Request.path_components.<locals>.<genexpr>u  s     BS[[^Bs   $$/)r,  r!  r-  r   r   ri   split)r<   r   s     r*   path_componentszRequest.path_componentsk  s=     ||$$TXX.33 BTZZ_BBBr,   
componentsc                     t        d |      }ddj                  |      z   }t        j                  j	                  | j
                        \  }}}}}}t        j                  j                  dd||||g      | _        y )Nc                 0    t        j                  | d      S )Nr   )safe)r   quoter)   s    r*   <lambda>z)Request.path_components.<locals>.<lambda>y  s    399QR#8 r,   rK  r   )maprE   r,  r!  r-  r   r1  r   )r<   rN  r   r3  r4  r.  r5  s          r*   rM  zRequest.path_componentsw  sj    8*E
SXXj))+1<<+@+@+J(1aLL++RT65(,ST	r,   c                 N    d}|D ]  }| j                   j                  |d         y)z_
        Modifies this request to remove headers that might produce a cached response.
        )zif-modified-sincezif-none-matchN)r=   r   )r<   
delheadersrJ  s      r*   	anticachezRequest.anticache~  s.    

  	&ALLQ%	&r,   c                 "    d| j                   d<   y)zZ
        Modify the Accept-Encoding header to only accept uncompressed responses.
        r   accept-encodingN)r=   rQ   s    r*   anticompzRequest.anticomp  s     +5&'r,   c                     | j                   j                  d      r(dj                  fddD              | j                   d<   yy)zk
        Limits the permissible Accept-Encoding values, based on what we can decode appropriately.
        rY  rC   c              3   *   K   | ]
  }|v r|  y wrI   rd   )rN   eaccept_encodings     r*   rP   z-Request.constrain_encoding.<locals>.<genexpr>  s!      8' 8s   >   brgzipzstddeflater   N)r=   r   rE   )r<   r^  s    @r*   constrain_encodingzRequest.constrain_encoding  sG     ,,**+<=.2ii 8F8 /DLL*+ r,   c                     d| j                   j                  dd      j                         v }|r.t        t	        j
                  | j                  d                  S y)N!application/x-www-form-urlencodedr   r   Fr   rd   )r=   r   rJ   ri   r   r(   r   r<   is_valid_content_types     r*   _get_urlencoded_formzRequest._get_urlencoded_form  sS    /||399;< 	 !DMMM$?@AAr,   	form_datac                     d| j                   d<   t        j                  || j                  d            j                         | _        y)z
        Sets the body to the URL-encoded form data, and adds the appropriate content-type header.
        This will overwrite the existing content if there is one.
        re  r   Fr   N)r=   r   r   r   rt   )r<   ri  s     r*   _set_urlencoded_formzRequest._set_urlencoded_form  s9    
 (K^$zz)T]]%]-HIPPRr,   c                 V    t        j                  | j                  | j                        S )a	  
        The URL-encoded form data.

        If the content-type indicates non-form data or the form could not be parsed, this is set to
        an empty `MultiDictView`.

        Modifications to the MultiDictView update `Request.content`, and vice versa.
        )r   r8  rh  rk  rQ   s    r*   urlencoded_formzRequest.urlencoded_form  s(     &&%%t'@'@
 	
r,   c                 &    | j                  |       y rI   )rk  r   s     r*   rm  zRequest.urlencoded_form  s    !!%(r,   c                    d| j                   j                  dd      j                         v }|rF| j                  :	 t	        j
                  | j                   j                  d      | j                        S g S # t        $ r Y g S w xY w)Nmultipart/form-datar   r   )r=   r   rJ   rt   r   decode_multipartr   rf  s     r*   _get_multipart_formzRequest._get_multipart_form  s    !T\\%5%5nb%I%O%O%QQ 	 !T\\%= 11LL$$^4dll 
 	  	s   8A7 7	BBr?   c                 P   | j                   j                  dd      }|j                         j                  d      }|sN	 dt	        j
                  t        j                  d            j                         z   }d| x| j                   d<   }t        j                  ||      | _        y )Nr   r   rp  z--------------------   zmultipart/form-data; boundary=)r=   r   rJ   
startswithbinasciihexlifyosurandomr(   r   encode_multipartrt   )r<   r?   r   rg  boundarys        r*   _set_multipart_formzRequest._set_multipart_form  s    \\nb1 "
 5 56K L$  ("2"22::b>"B"I"I"KKH0
;DLL(2 !11"e<r,   c                 V    t        j                  | j                  | j                        S )a  
        The multipart form data.

        If the content-type indicates non-form data or the form could not be parsed, this is set to
        an empty `MultiDictView`.

        Modifications to the MultiDictView update `Request.content`, and vice versa.
        )r   r8  rr  r|  rQ   s    r*   multipart_formzRequest.multipart_form  s(     &&$$d&>&>
 	
r,   c                 &    | j                  |       y rI   )r|  r   s     r*   r~  zRequest.multipart_form  s      'r,   )r   rd   )r#   N)4re   rf   rg   rh   r   rj   rl   rn   r7   r0   ri   r   r5   r   r   r   r   r  r   r  r   r   r   r   r   r  r   r  r   r   r&  r*  r/  r6  r   r8  r.  r=  rA  r   rM  rW  rZ  rc  rh  r   rk  rm  rm   rr  r|  r~  rd   r,   r*   r   r     s    1
1
 1
 	1

 1
 1
 1
 1
 5ue|!4c!9::1
 1
 E%u"5s":;;dB1
 1
 t|1
f:# : 
  " :: : 	: d3;e344xeUl@S7TT: 
: :x 3   K K K ]]I#+ I$ I I C C C ]]I#+ I$ I I I3 I I" "S5[ "T " " 
c 
 
 
[[*e * * * 7S4Z 7 7 
+tczE1 
+d 
+ 
+ c   
[[* * * *! Ac A A 
[[Ge G G G IS I I 	ZZFsU{ Ft F F S   MC M M (U
 Iy..sCx8 I I \\ 6E M00c: M M ^^! ! 	CsCx 	C 	C U(3- U U	&5
ShuS#X.G SD S 
!8!8c!B 
 
 ) )T%u*=%> =eE5L.A)B =t =  
	 7 7u E 
 
 (Due|)<$= ($ ( (r,   r   c                      e Zd ZU dZeed<   dedededee	e	eef   df   z  ded	z  d
d	ez  e	e	eef   df   z  de
de
d	z  fdZdefdZe	 	 	 ddedeez  deeeeez  f   z  ee	eef      z  dd fd       Zedefd       Zej(                  dedd	fd       Zedefd       Zej(                  deez  dd	fd       Zd Zd Zedej2                  ee	eej4                  eed	z  f   f   f   fd       Zej(                  d        ZddZy	)Responsez
    An HTTP response.
    r   rs   r   r   r=   .rt   Nru   rv   rw   c	           
         t        |t              r|j                  dd      }t        |t              r|j                  dd      }t        |t              r!t        dt	        |      j
                         t        |t              st        |      }|t        |t              st        |      }t        ||||||||      | _        y )Nr   r   r   )rs   r   r   r=   rt   ru   rv   rw   )	r6   rl   r   r   r{   re   r0   r   r   )	r<   rs   r   r   r=   rt   ru   rv   rw   s	            r*   r5   zResponse.__init__  s     lC('..wALfc"]]7H5Fgs#:4=;Q;Q:RSTT'7+g&G
8W(Ex(H %#+'	
	r,   r#   c                     | j                   rL| j                  j                  dd      }t        j                  t        | j                               }| d| }nd}d| j                   d| dS )Nr   zunknown content typerC   z
no contentz	Response(r   )r   r=   r   r   pretty_sizer   r   )r<   r   sizedetailss       r*   r   zResponse.__repr__  sm    !!.2HIB$$S)9)9%:;DBtfoG"G4++,Bwiq99r,   c                    t        |t              r|}nzt        |t              r!t        d |j                         D              }nIt        |t              rt        |      }n-t        dj                  t        |      j                               | d|t        j                  j                  |d      j                         |ddt        j                         t        j                               }t        |t              r	||_        |S t        |t               r	||_        |S t        dt        |      j                   d      )z?
        Simplified API for creating response objects.
        c              3   V   K   | ]!  \  }}t        |d d      t        |d d      f # ywr   r   r`   s      r*   rP   z Response.make.<locals>.<genexpr>0  r   r   r   r   r   Nr   r   )r6   r0   r   r:   r   r8   r   r{   re   r   	RESPONSESr   r   r   r7   rt   rl   r   )r   r   rt   r=   resps        r*   r  zResponse.make!  s!    gw'G& 
 $MMO G *g&GHOOM**  ""&&{B7>>@IIKIIK	
 gu%"DL  %DI 	 >tG}?U?U>VVWX r,   c                 .    | j                   j                  S )z1
        HTTP Status Code, e.g. ``200``.
        r   r   rQ   s    r*   r   zResponse.status_codeW  s    
 yy$$$r,   c                 &    || j                   _        y rI   r  )r<   r   s     r*   r   zResponse.status_code^  s     +		r,   c                 L    | j                   j                  j                  d      S )z
        HTTP reason phrase, for example "Not Found".

        HTTP/2 responses do not contain a reason phrase, an empty string will be returned instead.
        
ISO-8859-1)r   r   r(   rQ   s    r*   r   zResponse.reasonb  s     yy&&|44r,   c                 N    t        j                  |d      | j                  _        y )Nr  )r   r   r   r   )r<   r   s     r*   r   zResponse.reasonl  s    #00F		r,   c                     | j                   j                  d      }t        j                  |      }t	        d |D              S )N
set-cookiec              3   0   K   | ]  \  }}}|||ff  y wrI   rd   )rN   r@   r?   attrss       r*   rP   z(Response._get_cookies.<locals>.<genexpr>s  s      R0BeUdUEN+Rs   )r=   rX   r   parse_set_cookie_headersri   )r<   r   all_cookiess      r*   r=  zResponse._get_cookiesp  s7    LL  .66q9RkRRRr,   c                     g }|D ]5  \  }}t        j                  ||d   |d   fg      }|j                  |       7 | j                  j	                  d|       y )Nr      r  )r   format_set_cookie_headerappendr=   rZ   )r<   r?   cookie_headersra   rb   headers         r*   rA  zResponse._set_cookiesu  s_     	*DAq551Q416GHF!!&)	* 	\>:r,   c                 V    t        j                  | j                  | j                        S )a  
        The response cookies. A possibly empty `MultiDictView`, where the keys are cookie
        name strings, and values are `(cookie value, attributes)` tuples. Within
        attributes, unary attributes (e.g. `HTTPOnly`) are indicated by a `None` value.
        Modifications to the MultiDictView update `Response.headers`, and vice versa.

        *Warning:* Changes to `attributes` will not be picked up unless you also reassign
        the `(cookie value, attributes)` tuple directly in the `MultiDictView`.
        rC  rQ   s    r*   r   zResponse.cookies|  s#     &&t'8'8$:K:KLLr,   c                 &    | j                  |       y rI   rE  r   s     r*   r   zResponse.cookies  rF  r,   c                    |st        j                          }|| j                  z
  }g d}|D ]U  }|| j                  v st        | j                  |         }|s-t	        |      |z   }	 t        |d      | j                  |<   W g }| j                  j                  d      D ]*  }	 t        j                  ||      }	|j                  |	       , |r| j                  j                  d|       yy# t        $ r Y w xY w# t        $ r |}	Y Ow xY w)z
        This fairly complex and heuristic function refreshes a server
        response for replay.

         - It adjusts date, expires, and last-modified headers.
         - It adjusts cookie expiration.
        )dateexpireszlast-modifiedT)usegmtr  N)r   rv   r=   r   r   r
   OSErrorrX   r   refresh_set_cookie_headerr   r  rZ   )
r<   nowdeltarefresh_headersrJ  dnewcset_cookie_header	refresheds
             r*   refreshzResponse.refresh  s    ))+Cd***

 ! 	ADLL  a1#A,.C*4S*FQ	 !%!5!5l!C 	 .#==>OQVW	 HHY	  LL  q1  #   .-	.s$   (C.%C=.	C:9C:=D
D)   r,   rd   rI   )re   rf   rg   rh   r   rj   r7   rn   r0   ri   r   r5   rl   r   r   r   r   r  r   r   r   r   r=  rA  r   r8  	MultiDictr   r  rd   r,   r*   r  r    s    !
!
 !
 	!

 5ue|!4c!9::!
 !
 .5ue|)<c)A#BB!
 !
 t|!
F:# :  " 33 3
 gc3;.//(5;N2OO3 
3 3j %S % % ,s ,t , , 5 5 5 ]]GS5[ GT G GS
; M		 	 eC1D1DS#PT*_1U,U&V!V	WM M ^^! !!2r,   r  c                   2    e Zd ZU dZeed<   	 dZedz  ed<   	 dZe	j                  dz  ed<   	 dZedz  ed<   	 dej                  f fdZd	ej                  ddf fd
Zd Zedefd       Zedefd       Zej.                  deddfd       Z fdZ xZS )HTTPFlowz\
    An HTTPFlow is a collection of objects representing a single HTTP
    transaction.
    requestNresponseerror	websocketr#   c                     i t         |          | j                  j                         | j                  r| j                  j                         nd | j                  r| j                  j                         dS d dS )N)r  r  r  )r4   r   r  r  r  )r<   rA   s    r*   r   zHTTPFlow.get_state  sq    
g!
||--/59]]//17;~~113	
 	
 LP	
 	
r,   r   c                 2   t         j                  |j                  d            | _        |j                  d      x}rt        j                  |      nd | _        |j                  d      x}rt        j                  |      nd | _        t        | %  |       y )Nr  r  r  )
r   r   r   r  r  r  r!   r  r4   r   )r<   r   rwrA   s       r*   r   zHTTPFlow.set_state  s    ))%))I*>?8=		*8M3M13M++A.TX16;1G,GA,GM$$Q'd 	 	% r,   c                 v    d}dD ]  }t        | |d      s|d| d| dz  } |dz  }|j                  |       S )	Nz	<HTTPFlow)r  r  r  r  client_connserver_connFz
  z	 = {flow.}>r   )ry   r   )r<   sas      r*   r   zHTTPFlow.__repr__  s[    
 		1A tQ&vaS
1#R00		1 	
SxxTx""r,   c                 .    | j                   j                  S )z4*Read-only:* An alias for `Request.timestamp_start`.)r  rv   rQ   s    r*   rv   zHTTPFlow.timestamp_start  s     ||+++r,   c                 T    t        j                  dt        d       t        | dd      S )NHTTPFlow.mode is deprecated.r   
stacklevel_moderegular)warningswarnDeprecationWarningry   rQ   s    r*   modezHTTPFlow.mode  s$    46HUVWtWi00r,   r|   c                 J    t        j                  dt        d       || _        y )Nr  r   r  )r  r  r  r  r  s     r*   r  zHTTPFlow.mode  s    46HUVW
r,   c                     t         |          }| j                  r| j                  j                         |_        | j                  r| j                  j                         |_        |S rI   )r4   r   r  r  )r<   frA   s     r*   r   zHTTPFlow.copy  sI    GLN<<))+AI==++-AJr,   )re   rf   rg   rh   r   rj   r  r  r  r   Errorr  r!   r   Stater   r   r   r   r   rv   rl   r  r   r   ro   rp   s   @r*   r  r    s    
 $ $Hho$%#E4::# '+I}t#*
<-- 
!|11 !d !# , , , 1c 1 1 
[[    r,   r  )r  r   r   r  r0   )@rv  r   rx  r   urllib.parser,  r  collections.abcr   r   r   r   r   dataclassesr   r	   email.utilsr
   r   r   typingr   r   	mitmproxyr   mitmproxy.coretypesr   r   mitmproxy.netr   mitmproxy.net.httpr   r   r   r   mitmproxy.net.http.headersr   r   r   mitmproxy.utilsr   r   r   mitmproxy.utils.strutilsr   r    mitmproxy.websocketr!   r7   rl   r+   r.   r  r0   Serializablerr   r   r   r   r   r  Flowr  __all__rd   r,   r*   <module>r     sU     	    $ $ $ # $ !  " ! $    ) , " & ( + " < = 9 ! $ % 1 / -0u 0 0@S5[ @U @
#i!! #D ",++ " "J +   ;  
Q1l'' Q1hn(g n(bB2w B2JLtyy L^r,   