mò mã¸Ec@scdZdkZdkZdkZdkZdkZdkZdklZdk l Z l Z l Z l Z lZd„Zdefd„ƒYZdfd„ƒYZd efd „ƒYZd fd „ƒYZd eefd„ƒYZdeefd„ƒYZd„Zdfd„ƒYZdeefd„ƒYZdeefd„ƒYZdefd„ƒYZdS(s9HTTP Authentication and Proxy support. All but HTTPProxyPasswordMgr come from Python 2.5. Copyright 2006 John J. Lee This code is free software; you can redistribute it and/or modify it under the terms of the BSD or ZPL 2.1 licenses (see the file COPYING.txt included with the distribution). N(s BaseHandler(s getproxiessunquotes splittypes splitusers splitpasswdc CsÛt|ƒ\}}|idƒpd}|}n[|idƒptd|ƒ‚n|iddƒ}|djo d}n|d|!}t |ƒ\}}|dj ot |ƒ\}}n d}}||||fS(s3Return (scheme, user, password, host/port) given a URL or an authority. If a URL is supplied, it must have an authority (host:port) component. According to RFC 3986, having an authority component means the URL must have two slashes after the scheme: >>> _parse_proxy('file:/ftp.example.com/') Traceback (most recent call last): ValueError: proxy URL with no authority: 'file:/ftp.example.com/' The first three items of the returned tuple may be None. Examples of authority parsing: >>> _parse_proxy('proxy.example.com') (None, None, None, 'proxy.example.com') >>> _parse_proxy('proxy.example.com:3128') (None, None, None, 'proxy.example.com:3128') The authority component may optionally include userinfo (assumed to be username:password): >>> _parse_proxy('joe:password@proxy.example.com') (None, 'joe', 'password', 'proxy.example.com') >>> _parse_proxy('joe:password@proxy.example.com:3128') (None, 'joe', 'password', 'proxy.example.com:3128') Same examples, but with URLs instead: >>> _parse_proxy('http://proxy.example.com/') ('http', None, None, 'proxy.example.com') >>> _parse_proxy('http://proxy.example.com:3128/') ('http', None, None, 'proxy.example.com:3128') >>> _parse_proxy('http://joe:password@proxy.example.com/') ('http', 'joe', 'password', 'proxy.example.com') >>> _parse_proxy('http://joe:password@proxy.example.com:3128') ('http', 'joe', 'password', 'proxy.example.com:3128') Everything after the authority is ignored: >>> _parse_proxy('ftp://joe:password@proxy.example.com/rubbish:3128') ('ftp', 'joe', 'password', 'proxy.example.com') Test for no trailing '/' case: >>> _parse_proxy('http://joe:password@proxy.example.com') ('http', 'joe', 'password', 'proxy.example.com') t/s//sproxy URL with no authority: %riiÿÿÿÿN(t splittypetproxytschemetr_schemet startswithtNonet authorityt ValueErrortfindtendt splitusertuserinfothostportt splitpasswdtusertpassword( RRR RRR RRR ((t./data/zmath/zope/lib/python/mechanize/_auth.pyt _parse_proxys 1      t ProxyHandlercBs#tZdZdd„Zd„ZRS(NidcCs|djo tƒ}nt|dƒp td‚||_x=|iƒD]/\}}t |d||||i d„ƒqJWdS(Nthas_keysproxies must be a mappings%s_opencCs||||ƒS(N(tmethtrRttype(RRRR((Rtgs( tproxiesRt getproxiesthasattrtAssertionErrortselftitemsRturltsetattrt proxy_open(RRRR((Rt__init__`s     c Cs×|iƒ}t|ƒ\}} }}|djo |}n| oP|oIdt | ƒt |ƒf}t i |ƒiƒ} |idd| ƒnt |ƒ}|i||ƒ||jodSn|ii|ƒSdS(Ns%s:%ssProxy-authorizationsBasic (treqtget_typet orig_typeRRt proxy_typeRRR Rtunquotet user_passtbase64t encodestringtstriptcredst add_headert set_proxyRtparenttopen( RR#RRR%R(R RR&R,R((RR!js     (t__name__t __module__t handler_orderRR"R!(((RR\s tHTTPPasswordMgrcBs5tZd„Zd„Zd„Zd„Zd„ZRS(NcCs h|_dS(N(Rtpasswd(R((RR"ƒscCsqt|tƒo |g}ntt|i|ƒƒ}||ijoh|i|tauthreqRRRtrxtsearchtmotgroupsRR<tlowerRtretry_http_basic_auththostR#(RRVR]R#RUR<RRY((Rthttp_error_auth_reqedÌscCs§|ii||ƒ\}}|dj owd||f}dt i |ƒi ƒ}|ii|idƒ|jodSn|i|i|ƒ|ii|ƒSndSdS(Ns%s:%ssBasic %s(RR5RER<R]RtpwRtrawR)R*R+tauthR#RUR>t auth_headerR-R/R0(RR]R#R<R_RaR`R((RR\Øs ( R1R2tretcompiletIRWRR"R^R\(((RRR¾s  tHTTPBasicAuthHandlercBstZdZd„ZRS(Nt AuthorizationcCs"|iƒ}|id|||ƒS(Nswww-authenticate(R#t get_full_urlRRR^RU(RR#tfptcodetmsgRUR((Rthttp_error_401és  (R1R2RbRl(((RRfåstProxyBasicAuthHandlercBstZdZd„ZRS(NsProxy-authorizationcCs"|iƒ}|id|||ƒS(Nsproxy-authenticate(R#tget_hostRRR^RU(RR#RiRjRkRUR((Rthttp_error_407ós  (R1R2RbRo(((RRmïscCsŠtiidƒo-tdƒ}|i|ƒ}|iƒ|SnGg}t |ƒD]}|t t iddƒƒqQ~}di|ƒSdS(sReturn n random bytes.s /dev/urandomiitN(tostpathtexistsR0tftreadtntstcloset_[1]trangetitchrtrandomt randrangetLtjoin(RvRtR{RRyRw((Rt randombytesýs  9tAbstractDigestAuthHandlercBsStZdd„Zd„Zd„Zd„Zd„Zd„Zd„Z d„Z RS( NcCsH|djo tƒ}n||_|ii|_d|_d|_dS(Ni(R5RR4RR=tretriedt nonce_count(RR5((RR"s     cCs d|_dS(Ni(RRƒ(R((Rtreset_retry_countscCs™|i|dƒ}|idjo"t|i ƒdd|dƒ‚n|id7_|o;|i ƒd}|i ƒdjo|i ||ƒSq•ndS(Nii‘sdigest auth failediitdigest(RUR>RbRRVRRƒt HTTPErrorR#RhtsplitRR[tretry_http_digest_auth(RRbR]R#RURRV((RR^!scCs¥|iddƒ\}}tt|ƒƒ}|i||ƒ}|o^d|}|i i |i dƒ|jodSn|i|i |ƒ|ii|ƒ}|SndS(Nt is Digest %s(RaRˆttokent challengetparse_keqv_listtparse_http_listtchalRtget_authorizationR#tauth_valRUR>RbRtadd_unredirected_headerR/R0tresp(RR#RaRŒR“RR‹R‘((RR‰2s cCs<tid|i|tiƒtdƒfƒiƒ}|d S(Ns %s:%s:%s:%sii( tshatnewRR„tnoncettimetctimeRt hexdigesttdig(RR–Rš((Rt get_cnonce>s4cCsKyK|d}|d} |idƒ}|iddƒ}|iddƒ}Wntj o dSnX|i |ƒ\} }| djodSn|i i||iƒƒ\}}|djodSn|iƒo|i|iƒ|ƒ}nd}d|||f} d|iƒ|iƒf} |d joc|id 7_d |i}|i| ƒ}d | |||| | ƒf} || | ƒ| ƒ}n7|djo)|| | ƒd| | | ƒfƒ}nd ||| |iƒ|f}|o|d|7}n|o|d|7}n|d|7}|o|d||f7}n|S(NR<R–tqopt algorithmtMD5topaques%s:%s:%ss%s:%sRais%08xs%s:%s:%s:%s:%ss>username="%s", realm="%s", nonce="%s", uri="%s", response="%s"s , opaque="%s"s , digest="%s"s, algorithm="%s"s, qop=auth, nc=%s, cnonce="%s"("RR<R–R>RœRRRŸtKeyErrorRtget_algorithm_implstHtKDR5RER#RhRR_thas_datatget_entity_digesttget_datatentdigtA1t get_methodt get_selectortA2R„tncvalueR›tcnoncetnoncebittrespdigRI(RR#RRœR§R<R_RŸR¯R¨R«R®R–R¢R­R¬RIRRR£((RRHsJ    !     )csJ|djo d„‰n|djo d„‰n‡d†}ˆ|fS(NRžcCsti|ƒiƒS(N(tmd5R•txR™(R±((RRƒstSHAcCsti|ƒiƒS(N(R”R•R±R™(R±((RR…scsˆd||fƒS(Ns%s:%s(R¢Rwtd(RwR³(R¢(RR‡s(RR¢R£(RRR¢R£((R¢RR¡€s      cCsdS(N(R(RtdataR((RR¥Šs( R1R2RR"R…R^R‰R›RR¡R¥(((RR‚ s    8 tHTTPDigestAuthHandlercBstZdZdZd„ZRS(s¨An authentication protocol defined by RFC 2069 Digest authentication improves on basic authentication because it does not transmit passwords in the clear. RgcCs?ti|iƒƒd}|id|||ƒ}|iƒ|S(Niswww-authenticate( RFR#RhR]RR^RUtretryR…(RR#RiRjRkRUR]R¶((RRl˜s   (R1R2t__doc__RbRl(((RRµs tProxyDigestAuthHandlercBstZdZd„ZRS(NsProxy-AuthorizationcCs2|iƒ}|id|||ƒ}|iƒ|S(Nsproxy-authenticate(R#RnR]RR^RUR¶R…(RR#RiRjRkRUR]R¶((RRo¤s    (R1R2RbRo(((RR¸ stHTTPProxyPasswordMgrcBs,tZd„Zd„Zd„Zd„ZRS(NcCsy|djpt|tƒo |g}n|}|ii|hƒ}x-|D]%}|i |ƒ}||f||tauthinfo_by_domainR;treduced_authuriRAR7RCRDRR( RR<R@R¼R7R¾RCR½RR¿R((RREºs"       cCs%|djodSnti||ƒS(N(R7RR4R;R(RR7((RR;Ís cCs<|djo|\}}|df}nti|||ƒS(NR(RIRRJR RrR4RDR(RRIRJR Rr((RRDÒs  (R1R2R=RER;RD(((RR¹­s  (R·RcR)RFRMR°R”turllib2t BaseHandlerturllibRR'RR RRRR4RQRRRfRmRR‚RµR¸R¹(R'RRRÁRRRRRMR¹R R)R4RcRmRR¸R‚RfR°RQRFR”RRµ((Rt? s6 % H%3 '  „