
ٽX=                 @   sz  d  d l  m Z 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 Z d  d l	 m	 Z
 d  d l m Z d  d l m Z yH d  d l Z d  d l m Z m Z d  d l Z d  d l m Z d Z Wn- e k
 rd	 Z d  d l Z e j Z Yn Xd
 Z d Z d Z d Z d Z d Z  d Z! Gd d   d  Z" Gd d   d e#  Z$ d d   Z% d d   Z& d d   Z' d d   Z( d d   Z) d d   Z* d  d!   Z+ d" d#   Z, d$ d%   Z- Gd& d'   d' e.  Z/ Gd( d)   d) e e/  Z0 d* d+   Z1 d, d-   Z2 Gd. d/   d/ e.  Z3 d0 d1   Z4 e5 d2 k rvd  d l6 Z6 e6 j7 d3 j8 d4  d3 Z9 e: e2 e9   d S)5    )print_functionN)gettext)Thread)ShortcutException)	HTTPErrorURLError)HTTPExceptionFTzhkp://keyserver.ubuntu.com:80/z,https://launchpad.net/api/1.0/%s/+archive/%sz https://launchpad.net/api/1.0/%sz%https://launchpad.net/api/1.0/%s/ppasz#https://launchpad.net/api/1.0/%s/%sz"/etc/ssl/certs/ca-certificates.crtc               @   s(   e  Z d  Z d d   Z d d   Z d S)CurlCallbackc             C   s   d |  _  d  S)N )contents)self r   8/usr/lib/python3/dist-packages/softwareproperties/ppa.py__init__>   s    zCurlCallback.__init__c             C   s   |  j  | |  _  d  S)N)r   )r   Zbufr   r   r   body_callbackA   s    zCurlCallback.body_callbackN)__name__
__module____qualname__r   r   r   r   r   r   r	   =   s   r	   c               @   s+   e  Z d  Z d d d  Z d d   Z d S)PPAExceptionNc             C   s   | |  _  | |  _ d  S)N)valueoriginal_error)r   r   r   r   r   r   r   G   s    	zPPAException.__init__c             C   s   t  |  j  S)N)reprr   )r   r   r   r   __str__K   s    zPPAException.__str__)r   r   r   r   r   r   r   r   r   r   E   s   r   c             C   s   t  j d d |   S)Nz[^a-zA-Z0-9_-]_)resub)sr   r   r   encodeO   s    r   c             C   s   t  r t |   St |   Sd  S)N)NEED_PYCURL_get_https_content_pycurl_get_https_content_py3)lp_urlr   r   r   get_info_from_lpR   s    
r"   c             C   s   t  |  | f } t |  S)N)LAUNCHPAD_PPA_APIr"   )Z
owner_nameppar!   r   r   r   get_ppa_info_from_lpZ   s    r%   c             C   s?   t  |  | f } y t |  d SWn t k
 r: d SYn Xd  S)NTF)!LAUNCHPAD_DISTRIBUTION_SERIES_APIr"   r   )distributionZseriesr!   r   r   r   series_valid_for_distro^   s    
r(   c             C   s$   t  |  } t j j t |  d  S)NZcurrent_series_link)LAUNCHPAD_DISTRIBUTION_APIospathbasenamer"   )r'   r!   r   r   r   get_current_series_from_lpf   s    
r-   c             C   s   yX t  j j t |   d d d i } t  j j | d t } | j   j d d  } Wnb t t	 f k
 r } z< t
 | d  r | j p | } t d |  | f |   WYd  d  } ~ Xn Xt j |  S)	NZheadersZAcceptz application/jsonZcafilezutf-8strictreasonzError reading %s: %s)urllibrequestZRequeststrZurlopenLAUNCHPAD_PPA_CERTreaddecoder   r   hasattrr/   r   jsonloads)r!   r1   Zlp_page	json_dataer/   r   r   r   r    k   s    $,r    c             C   s  y t    } t j   } | j t j d  | j t j d  | j t j | j  t rm | j t j	 t  | j t j
 t |    | j t j d g  | j   | j   | j } WnA t j k
 r } z t d |  | f |   WYd  d  } ~ Xn Xt j |  S)N      zAccept: application/jsonzError reading %s: %s)r	   pycurlZCurlZsetoptZSSL_VERIFYPEERZSSL_VERIFYHOSTZWRITEFUNCTIONr   r3   ZCAINFOZURLr2   Z
HTTPHEADERZperformcloser   errorr   r7   r8   )r!   callbackZcurlr9   r:   r   r   r   r   w   s     	

,r   c             C   s   |  j  d  d } | j d  r1 | j d  } | j  d  d } | d d k rd | d d   } | j  d  d d   } g  } t |  d k  r d d g } n8 t |  d k r | j d d  | j |  n | } d | d j |  f } | S)	N:r;   /r   ~Zubuntur$   z~%s/%s)split
startswithlstripleninsertextendjoin)shortcutZppa_shortcutuserZppa_path_objsppa_pathr$   r   r   r   mangle_ppa_shortcut   s     rN   c             C   s   t  |   d k S)z>Verify that the keyid is a v4 fingerprint with at least 160bit      g      4@)rG   )signing_key_fingerprintr   r   r   verify_keyid_is_v4   s    rR   c               @   ss   e  Z d  Z d Z d d d g Z d d d  Z d d	   Z d
 d   Z d d   Z d d   Z	 d d d  Z
 d S)AddPPASigningKeyz; thread class for adding the signing key in the background Zgpgz--no-default-keyringz--no-optionsNc             C   s(   | |  _  | d  k	 r | n t |  _ d  S)N)rM   DEFAULT_KEYSERVER	keyserver)r   rM   rU   r   r   r   r      s    	zAddPPASigningKey.__init__c             C   s   y" t  |  s! t d |  d SWn  t k
 rD t d  d SYn Xt j |  j d | d | d | d |  j d | g
  } | d	 k S)
Nz-Error: signing key fingerprint '%s' too shortFz-Error: signing key fingerprint does not existz	--homedirz--secret-keyringz	--keyringz--keyserverz--recvr   )rR   print	TypeError
subprocesscallGPG_DEFAULT_OPTIONSrU   )r   keyringZsecret_keyringrQ   keyring_dirresr   r   r   	_recv_key   s    
		zAddPPASigningKey._recv_keyc          
   C   sB   t  j |  j d | d | d | d | g  } | d k r> d Sd S)Nz	--homedirz	--keyringz--outputz--exportr   FT)rX   rY   rZ   )r   r[   Zexport_keyringrQ   r\   r]   r   r   r   _export_key   s    zAddPPASigningKey._export_keyc             C   s   |  j  d | d | d d d g } t j | d d } g  } x= | j   D]/ } | j d  rJ | j | j d	  d
  qJ W| S)Nz	--homedirz	--keyringz--fingerprintz--batchz--with-colonsZuniversal_newlinesTzfpr:rA   	   )rZ   rX   Zcheck_output
splitlinesrE   appendrD   )r   r[   r\   cmdoutputZfingerprintsliner   r   r   _get_fingerprints   s    
z"AddPPASigningKey._get_fingerprintsc             C   sn   |  j  | |  } t |  d k r< t d t |   d S| d } | | k rj t d | | f  d Sd S)Nr;   z(Got '%s' fingerprints, expected only oneFr   z6Fingerprints do not match, not importing: '%s' != '%s'T)rf   rG   rV   )r   r[   Zexpected_fingerprintr\   Zgot_fingerprintsZgot_fingerprintr   r   r   _verify_fingerprint   s    
z$AddPPASigningKey._verify_fingerprintc          #      s  | d k r |  j  }   f d d   } y t |  } Wn6 t k
 ro } z t | j  d SWYd d } ~ Xn Xy | d } Wn7 t k
 r } z t d |  d SWYd d } ~ Xn Xt j     t j	 j
   d  } t j	 j
   d  } |  j | | |    s|    d St j	 j
   d	  } |  j | | |    sO|    d S|  j | |    sr|    d St j j d
  }	 t j	 j
 |	 d t | d d d    }
 t j d d |
 d | g  } |    | d k S)zQuery and add the corresponding PPA signing key.

        The signing key fingerprint is obtained from the Launchpad PPA page,
        via a secure channel, so it can be trusted.
        Nc                s   t  j    d  S)N)shutilZrmtree)Ztmpdir)tmp_keyring_dirr   r   cleanup   s    z5AddPPASigningKey.add_ppa_signing_key.<locals>.cleanupFrQ   z/Error: can't find signing_key_fingerprint at %szsecring.gpgzpubring.gpgzexport-keyring.gpgzDir::Etc::trustedpartsz%s.gpg	referencer;   zapt-keyz	--keyringaddr   )rM   get_ppa_infor   rV   r   
IndexErrortempfileZmkdtempr*   r+   rJ   r^   r_   rg   apt_pkgconfigfind_dirr   rX   rY   )r   rM   rj   Zppa_infor:   rQ   Ztmp_secret_keyringZtmp_keyringZtmp_export_keyringZtrustedgpgdZapt_keyringr]   r   )ri   r   add_ppa_signing_key   sH    	



z$AddPPASigningKey.add_ppa_signing_key)r   r   r   __doc__rZ   r   r^   r_   rf   rg   rs   r   r   r   r   rS      s   rS   c               @   s+   e  Z d  Z d d d  Z d d   Z d S)AddPPASigningKeyThreadNc             C   s*   t  j |   t j |  d | d | d  S)NrM   rU   )r   r   rS   )r   rM   rU   r   r   r   r   #  s    zAddPPASigningKeyThread.__init__c             C   s   |  j  |  j  d  S)N)rs   rM   )r   r   r   r   run'  s    zAddPPASigningKeyThread.run)r   r   r   r   rv   r   r   r   r   ru     s   ru   c             C   sz  yWg  } y4y t  t |   } Wn( t k
 rJ t d  j d |   SYn Xt  t |   } | d rq t d  n	 t d  } | d d k r| j t d  d | d |  d	 | i  | j t d
   xc | d D]1 } | j t d  d | d d | d i  q Wn# | j t d  d | d |  i  d j |  SWn t k
 rUd SYn XWn t	 k
 rut d  SYn Xd  S)Nz,ERROR: '{user}' user or team does not exist.rL   Zis_teamZteamZ
total_sizer   z:The %(entity)s named '%(user)s' has no PPA named '%(ppa)s'Zentityr$   z0Please choose from the following available PPAs:entriesz * '%(name)s':  %(displayname)snameZdisplaynamez5The %(entity)s named '%(user)s' does not have any PPA
r
   z4Please check that the PPA name or format is correct.)
r"   LAUNCHPAD_USER_APIr   r   formatLAUNCHPAD_USER_PPAS_APIrb   rJ   KeyErrorImportError)rL   Zppa_namemsgZlp_userZlp_ppasZentity_namer$   r   r   r   _get_suggested_ppa_message+  s4    "
r   c             C   s!  |  j  d  d } d j |  j  d  d d    } yM t | |  } | d j  d  d | d <| d j  d  d | d <| SWn t t f k
 r g  } | j t d  | | f  t d	 j |  d	 t | |    Yn8 t	 t
 f k
 rt t d
  t | | f   Yn Xd  S)NrB   r   r;   Zdistribution_linkr'   Z
owner_linkownerzCannot add PPA: 'ppa:%s/%s'.ry   zUCannot access PPA (%s) to get PPA information, please check your internet connection.r   )rD   rJ   r%   r   	Exceptionrb   r   r   r   
ValueErrorr   r#   )rK   rL   r$   Zretr   r   r   r   rm   K  s"    "	rm   c                   sX   e  Z d  Z   f d d   Z d d   Z d d d  Z d d	   Z d d
 d  Z   S)PPAShortcutHandlerc          
      s   t  t |   j   y t |  |  _ Wn& t t d  j d |    Yn Xt |  j  } d | k r | d r t t d    | |  _	 d  S)Nz-ERROR: '{shortcut}' is not a valid ppa formatrK   Zprivatez.Adding private PPAs is not supported currently)
superr   r   rN   rK   r   r   r{   rm   _info)r   rK   info)	__class__r   r   r   e  s    zPPAShortcutHandler.__init__c             C   s   |  j  S)N)r   )r   r   r   r   r   t  s    zPPAShortcutHandler.infoNc             C   s   | d  k	 rI | |  j  d k rI t |  j  d |  rI t |  j  d  } d |  j  d d d   |  j  d |  j  d | f } t j j d  } t j j | d t	 |  j  d d d    t	 |  j  d  t	 |  j  d  | f  } | | f S)Nr'   z-deb http://ppa.launchpad.net/%s/%s/%s %s mainr   r;   rx   zDir::Etc::sourcepartsz%s-%s-%s-%s.list)
r   r(   r-   rp   rq   rr   r*   r+   rJ   r   )r   ZcodenameZdistroZdeblineZsourceslistdfilenamer   r   r   expandw  s    *zPPAShortcutHandler.expandc             C   s   d S)NTr   )r   r   r   r   should_confirm  s    z!PPAShortcutHandler.should_confirmc             C   s#   t  |  j d d | } | j   S)Nrk   rU   )rS   r   rs   )r   rU   Zapskr   r   r   add_key  s    zPPAShortcutHandler.add_key)r   r   r   r   r   r   r   r   r   r   )r   r   r   d  s
   r   c             C   s   |  j  d  s d  St |   S)Nzppa:)rE   r   )rK   r   r   r   shortcut_handler  s    r   __main__r;   rA   );Z
__future__r   rp   r7   r*   r   rh   rX   ro   r   r   Z	threadingr   Zsoftwareproperties.shortcutsr   Zurllib.requestr0   Zurllib.errorr   r   Zurllib.parseZhttp.clientr   r   r~   r=   r?   rT   r#   rz   r|   r)   r&   r3   r	   r   r   r   r"   r%   r(   r-   r    r   rN   rR   objectrS   ru   r   rm   r   r   r   sysargvrD   r$   rV   r   r   r   r   <module>   s`   

z 0