a
    |P_VB                     @   sr  d Z ddlmZmZ ddlZddlZddlZddlZzDddl	m
Z
mZmZmZmZmZmZmZmZmZmZ ddlmZ W n ey   dd ZY n0 ddlmZmZmZ dd	lmZ dd
lmZ dZ dZ!g dZ"dZ#g dZ$dZ%dZ&dZ'dZ(G dd deZ)G dd de*Z+G dd de+Z,G dd de+Z-G dd deZ.e/dkrne.ej0d d Z1e1j23 Z3e4e35d dS )!zX Representation of Debian binary package (.deb) files


Debfile Classes
===============
    )absolute_importprint_functionN)AnyBinaryIODictIOIteratorListOptionalTextTypeVarUnionoverload)Literalc                 C   s   d S N )fr   r   0/usr/lib/python3/dist-packages/debian/debfile.py<lambda>3       r   )ArFileArErrorArMember)	Changelog)Deb822zdata.tarzcontrol.tar)gzbz2xzZlzmazdebian-binary)ZpreinstZpostinstZprermZpostrmZconfigcontrolzusr/share/doc/%s/changelog.gzz$usr/share/doc/%s/changelog.Debian.gzmd5sumsc                   @   s   e Zd ZdS )DebErrorN__name__
__module____qualname__r   r   r   r   r    G   s   r    c                   @   s   e Zd ZdZdd Zdd Zedd Zdd	 Ze	dddZ
e	d ddZ
d!ddZ
e	d"ddZe	d#ddZd$ddZdd Zdd Zejd dk rdd Zdd Zdd Zd
S )%DebParta  'Part' of a .deb binary package.

    A .deb package is considered as made of 2 parts: a 'data' part
    (corresponding to the possibly compressed 'data.tar' archive embedded
    in a .deb) and a 'control' part (the 'control.tar.gz' archive). Each of
    them is represented by an instance of this class. Each archive should
    be a compressed tar archive although an uncompressed data.tar is permitted;
    supported compression formats are: .tar.gz, .tar.bz2, .tar.xz .

    When referring to file members of the underlying .tar.gz archive, file
    names can be specified in one of 3 formats "file", "./file", "/file". In
    all cases the file is considered relative to the root of the archive. For
    the control part the preferred mechanism is the first one (as in
    deb.control.get_content('control') ); for the data part the preferred
    mechanism is the third one (as in deb.data.get_file('/etc/vim/vimrc') ).
    c                 C   s   || _ d | _d S r   )_DebPart__member_DebPart__tgz)selfmemberr   r   r   __init__]   s    zDebPart.__init__c           	   
      st  | j du rn| jj}tj|d dd }|tv sF|tksF|tkrbt	j
dk r
|dkr
z@ddl}ddl ddl}|jddg|j|jd fd	d
d}W n4 ttfy } ztd| W Y d}~n
d}~0 0 || j d }|jdkrtd|j ||}n| j}ztj|dd| _ W n: tjtjfy^ } ztd| W Y d}~n
d}~0 0 ntd| | j S )zReturn a TarFile object corresponding to this part of a .deb
        package.

        Despite the name, this method gives access to various kind of
        compressed tar archives, not only gzipped ones.
        N   )   r,   r   r   Zunxzz--stdoutFc                      s      j jS r   )signalSIGPIPESIG_DFLr   r-   r   r   r   |   s    zDebPart.tgz.<locals>.<lambda>)stdinstdoutZuniversal_newlinesZ
preexec_fnz%sz!command has failed with code '%s'zr:*)fileobjmodez#tarfile has returned an error: '%s'z"part '%s' has unexpected extension)r'   r&   nameospathsplitext	PART_EXTS	DATA_PART	CTRL_PARTsysversion_info
subprocessr-   ioPopenPIPEOSError
ValueErrorr    Zcommunicateread
returncodeBytesIOtarfileopenZ	ReadErrorZCompressionError)	r(   r5   	extensionr>   r?   procedatabufferr   r0   r   tgzb   s<    	

"
$zDebPart.tgzc                 C   s2   |  dr| dd } n|  dr.| dd } | S )zw try (not so hard) to obtain a member file name in a form relative
        to the .tar.gz root and with no heading '.' ./   N/r+   )
startswith)fnamer   r   r   Z__normalize_member   s
    

zDebPart.__normalize_memberc                 C   s*   t |}|   }d| |v p(||v S )z.Check if this part contains a given file name.rO   )r%   _DebPart__normalize_memberrN   getnames)r(   rS   namesr   r   r   has_file   s
    
zDebPart.has_fileNc                 C   s   d S r   r   r(   rS   encodingerrorsr   r   r   get_file   s    zDebPart.get_filec                 C   s   d S r   r   rX   r   r   r   r[      s    c                 C   s   t |}z|  d| }W n  ty@   |  |}Y n0 |du rRtd|durtjd dkrddl}t	|dsdd |_
|j|||d	S ddl}|du rd
}|j|||dS |S )zReturn a file object corresponding to a given file name.

        If encoding is given, then the file object will return Unicode data;
        otherwise, it will return binary data.
        rO   NzFile not found inside packager   r,   flushc                   S   s   d S r   r   r   r   r   r   r      r   z"DebPart.get_file.<locals>.<lambda>rY   rZ   strict)rZ   )r%   rT   rN   ZextractfileKeyErrorr    r<   r=   r?   hasattrr\   TextIOWrappercodecsEncodedFile)r(   rS   rY   rZ   Zfobjr?   rb   r   r   r   r[      s$    


c                 C   s   d S r   r   rX   r   r   r   get_content   s    zDebPart.get_contentc                 C   s   d S r   r   rX   r   r   r   rd      s    c                 C   s,   | j |||d}d}|r(| }|  |S )zReturn the string content of a given file, or None (e.g. for
        directories).

        If encoding is given, then the content will be a Unicode object;
        otherwise, it will contain binary data.
        r]   N)r[   rD   close)r(   rS   rY   rZ   r   Zcontentr   r   r   rd      s    c                 C   s   t |   S r   )iterrN   rU   r(   r   r   r   __iter__   s    zDebPart.__iter__c                 C   s
   |  |S r   rW   r(   rS   r   r   r   __contains__  s    zDebPart.__contains__r   r,   c                 C   s
   |  |S r   ri   rj   r   r   r   has_key  s    zDebPart.has_keyc                 C   s
   |  |S r   )rd   rj   r   r   r   __getitem__  s    zDebPart.__getitem__c                 C   s   | j   d S r   )r&   re   rg   r   r   r   re     s    zDebPart.close)NN)N)NN)NN)N)NN)r"   r#   r$   __doc__r*   rN   staticmethodrT   rW   r   r[   rd   rh   rk   r<   r=   rl   rm   re   r   r   r   r   r%   K   s6   1
	
   
  
r%   c                   @   s   e Zd ZdS )DebDataNr!   r   r   r   r   rp     s   rp   c                   @   sB   e Zd Zdd Zdd Zed
ddZedddZdd	dZdS )
DebControlc                 C   s6   i }t D ](}| |r| |}|dur|||< q|S )zo Return a dictionary of maintainer scripts (postinst, prerm, ...)
        mapping script names to script text. N)MAINT_SCRIPTSrW   rd   )r(   scriptsrS   rL   r   r   r   rs     s    


zDebControl.scriptsc                 C   s   t | tS )z Return the debian/control as a Deb822 (a Debian-specific dict-like
        class) object.

        For a string representation of debian/control try
        .get_content('control') )r   rd   CONTROL_FILErg   r   r   r   
debcontrol*  s    zDebControl.debcontrolNc                 C   s   d S r   r   r(   rY   rZ   r   r   r   r   4  s    zDebControl.md5sumsc                 C   s   d S r   r   rv   r   r   r   r   9  s    c           	      C   s   |  tstdt | jt||d}i }d}|du r:d}| D ]H}||dd\}}tjd dkrt	|t
r| ||< qB|||< qB|  |S )	a   Return a dictionary mapping filenames (of the data part) to
        md5sums. Fails if the control part does not contain a 'md5sum' file.

        Keys of the returned dictionary are the left-hand side values of lines
        in the md5sums member of control.tar.gz, usually file names relative to
        the file system root (without heading '/' or './').

        The returned keys are Unicode objects if an encoding is specified,
        otherwise binary. The returned values are always Unicode.z('%s' file not found, can't list MD5 sumsr]   z
Ns   
r+   r   r,   )rW   MD5_FILEr    r[   	readlinesrstripsplitr<   r=   
isinstancebytesdecodere   )	r(   rY   rZ   Zmd5_fileZsumsnewlinelineZmd5rS   r   r   r   r   >  s     

)NN)N)NN)r"   r#   r$   rs   ru   r   r   r   r   r   r   rq     s   
rq   c                   @   s   e Zd ZdZdddZdd Zedd	 Zed
d Zedd Z	dd Z
dd ZedddZedddZdddZdd Zdd ZdS )DebFilea  Representation of a .deb file (a Debian binary package)

    DebFile objects have the following (read-only) properties:
        - version       debian .deb file format version (not related with the
                        contained package version), 2.0 at the time of writing
                        for all .deb packages in the Debian archive
        - data          DebPart object corresponding to the data.tar.gz (or
                        other compressed or uncompressed tar) archive contained
                        in the .deb file
        - control       DebPart object corresponding to the control.tar.gz (or
                        other compressed tar) archive contained in the .deb
                        file
    Nrc                    s   t | ||| t|    fdd}t vr<tdt i | _t| |t	| jt	< t
| |t| jt< d | _| t}|  | _|  d S )Nc                    sj    fddt D } ttfv r(|  t|}|sFtd| t|dkr^td| t|d S )Nc                    s   g | ]}d  |f qS )z%s.%sr   ).0Zextbasenamer   r   
<listcomp>w  r   zBDebFile.__init__.<locals>.compressed_part_name.<locals>.<listcomp>z9missing required part in given .deb (expected one of: %s)r+   z>too many parts in given .deb (was looking for only one of: %s)r   )	r9   r:   r;   appendintersectionsetr    lenlist)r   Z
candidatespartsZactual_namesr   r   compressed_part_nameu  s"    
z.DebFile.__init__.<locals>.compressed_part_namez4missing required part in given .deb (expected: '%s'))r   r*   r   rU   	INFO_PARTr    _DebFile__partsrq   	getmemberr;   rp   r:   _DebFile__pkgnamerD   strip_DebFile__versionre   )r(   filenamer4   r3   r   r   r   r   r   r*   p  s(    
zDebFile.__init__c                 C   s   |   d | _d S )Npackage)ru   r   rg   r   r   r   Z__updatePkgName  s    zDebFile.__updatePkgNamec                 C   s   | j S r   )r   rg   r   r   r   version  s    zDebFile.versionc                 C   s
   | j t S r   )r   r:   rg   r   r   r   rL     s    zDebFile.datac                 C   s
   | j t S r   )r   r;   rg   r   r   r   r     s    zDebFile.controlc                 C   s
   | j  S )z See .control.debcontrol() )r   ru   rg   r   r   r   ru     s    zDebFile.debcontrolc                 C   s
   | j  S )z See .control.scripts() )r   rs   rg   r   r   r   rs     s    zDebFile.scriptsc                 C   s   d S r   r   rv   r   r   r   r     s    zDebFile.md5sumsc                 C   s   d S r   r   rv   r   r   r   r     s    c                 C   s   | j j||dS )z See .control.md5sums() r]   )r   r   rv   r   r   r   r     s    c                 C   sl   | j du r|   t| j  t| j  fD ]@}| j|r&tj| j|d}|	 }|
  t|  S q&dS )z Return a Changelog object for the changelog.Debian.gz of the
        present .deb package. Return None if no changelog can be found. N)r3   )r   _DebFile__updatePkgNameCHANGELOG_DEBIANCHANGELOG_NATIVErL   rW   gzipZGzipFiler[   rD   re   r   )r(   rS   r   Zraw_changelogr   r   r   	changelog  s    
zDebFile.changelogc                 C   s   | j   | j  d S r   )r   re   rL   rg   r   r   r   re     s    
zDebFile.close)Nr   N)NN)N)NN)r"   r#   r$   rn   r*   r   propertyr   rL   r   ru   rs   r   r   r   re   r   r   r   r   r   `  s$   
(



r   __main__r+   )r   )6rn   Z
__future__r   r   r   rG   r<   os.pathr6   typingr   r   r   r   r   r	   r
   r   r   r   r   Ztyping_extensionsr   ImportErrorZdebian.arfiler   r   r   Zdebian.changelogr   Zdebian.deb822r   r:   r;   r9   r   rr   rt   r   r   rw   r    objectr%   rp   rq   r   r"   argvZdebr   rN   printr   r   r   r   r   <module>   s@   4 KF}

