B
    A!p\0                 @   s  d 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Zddl	Z	ddl
m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 G dd	 d	ejZed
e G dd deZdZG dd deddddddgZddiZede Zdd ZG dd dejZG dd de Z!ej"ej#ej$ej%dZ&dd Z'd d! Z(d"d# Z)G d$d% d%e Z*G d&d' d'e*Z+d(d) Z,e, Z-d*d+ e-D Z.ej/j0d,e-e.d-d.d/ Z1e2d0krd1ej3krd2Zej34d1 e5ej3 dS )3z(Functional full-module tests for PyLint.    N)configparser)checkers)
interfaces)lint)	reportersc               @   s,   e Zd Zejd dk r dZdZndZdZdS )test_dialectr         :   
:
N)__name__
__module____qualname__sysversion_infoZ	delimiterZlineterminator r   r   :lib/python3.7/site-packages/pylint/test/test_functional.pyr   "   s
   r   testc               @   s   e Zd ZdS )NoFileErrorN)r   r   r   r   r   r   r   r   .   s   r   Fc               @   s,   e Zd Zedd Zedd Zdd ZdS )
OutputLinec             C   s<   | |j |j|jpd|jdd|jtjkr2|jjntj	jS )N z
r   )
symbollineobjmsgreplace
confidencer   Z	UNDEFINEDnameHIGH)clsr   r   r   r   from_msg=   s    zOutputLine.from_msgc             C   s@   t |dkr|d ntjj}| |d t|d |d |d |S )N      r         r   )lenr   r   r   int)r    rowr   r   r   r   from_csvD   s    zOutputLine.from_csvc             C   s"   | j tjjkr| d d S | S d S )N)r   r   r   r   )selfr   r   r   to_csvI   s    zOutputLine.to_csvN)r   r   r   classmethodr!   r)   r,   r   r   r   r   r   ;   s   r   r   linenoobjectr   r   z[a-z][a-z\-]+zt\s*#\s*(?:(?P<line>[+-]?[0-9]+):)?(?:(?P<op>[><=]+) *(?P<version>[0-9.]+):)?\s*\[(?P<msgs>%(msg)s(?:,\s*%(msg)s)*)\]c             C   s   t dd | dD S )Nc             s   s   | ]}t |V  qd S )N)r'   ).0Zdigitr   r   r   	<genexpr>^   s    z'parse_python_version.<locals>.<genexpr>.)tuplesplit)strr   r   r   parse_python_version]   s    r6   c               @   s$   e Zd Zdd Zdd Zdd ZdS )FunctionalTestReporterc             C   s   | j | d S )N)messagesappend)r+   r   r   r   r   handle_messageb   s    z%FunctionalTestReporter.handle_messagec             C   s
   g | _ d S )N)r8   )r+   modulefilepathr   r   r   on_set_current_modulee   s    z,FunctionalTestReporter.on_set_current_modulec             C   s   dS )zIgnore layouts.Nr   )r+   Zlayoutr   r   r   display_reportsh   s    z&FunctionalTestReporter.display_reportsN)r   r   r   r:   r=   r>   r   r   r   r   r7   a   s   r7   c               @   sj   e Zd ZdZeedd dZdd Zdd Zed	d
 Z	edd Z
edd Zedd ZdddZdS )FunctionalTestFilez0A single functional test case file with options.c             C   s
   |  dS )N,)r4   )sr   r   r   <lambda>r   s    zFunctionalTestFile.<lambda>)	min_pyver	max_pyverrequiresc             C   s0   || _ |dd| _ddg g d| _|   d S )Nz.pyr   )r%   r"   )r#   r   )rC   rD   rE   except_implementations)
_directoryr   baseoptions_parse_options)r+   Z	directoryfilenamer   r   r   __init__v   s    
zFunctionalTestFile.__init__c             C   st   t  }|d y|| j W n tk
r6   Y nX x6|dD ](\}}| j|dd }||| j	|< qDW d S )NZtestoptionsc             S   s   | S )Nr   )vr   r   r   rB      s    z3FunctionalTestFile._parse_options.<locals>.<lambda>)
r   ZConfigParserZadd_sectionreadoption_filer   items_CONVERTERSgetrI   )r+   Zcpr   valueZconvr   r   r   rJ      s    
z!FunctionalTestFile._parse_optionsc             C   s
   |  dS )Nz.rc)
_file_type)r+   r   r   r   rO      s    zFunctionalTestFile.option_filec             C   s   t j| j}d|| jgS )Nr2   )ospathbasenamerG   joinrH   )r+   packager   r   r   r;      s    zFunctionalTestFile.modulec             C   s   | j dddS )Nz.txtF)check_exists)rT   )r+   r   r   r   expected_output   s    z"FunctionalTestFile.expected_outputc             C   s
   |  dS )Nz.py)rT   )r+   r   r   r   source   s    zFunctionalTestFile.sourceTc             C   s2   t j| j| j| }|r&t j|r*|S td S )N)rU   rV   rX   rG   rH   existsr   )r+   ZextrZ   r   r   r   r   rT      s    zFunctionalTestFile._file_typeN)T)r   r   r   __doc__r6   rQ   rL   rJ   propertyrO   r;   r[   r\   rT   r   r   r   r   r?   l   s   r?   )><z>=z<=c             C   s   dd t | dD S )Nc             S   s   g | ]}t |qS r   )r   r)   )r0   r(   r   r   r   
<listcomp>   s    z)parse_expected_output.<locals>.<listcomp>r   )csvreader)streamr   r   r   parse_expected_output   s    rf   c       	      C   s   t  }xt| D ]\}}t|}|dkr.q|d}|dkrJ|d }n.|ds^|drp|d t| }nt|}|d}|d}|rt|}t	| t
j|sqx0|dd	D ]}||| f  d7  < qW qW |S )
zParses a file and get expected messages.

    :param stream: File-like input stream.
    :returns: A dict mapping line,msg-symbol tuples to the count on this line.
    Nr   r$   +-versionopZmsgsr@   )collectionsCounter	enumerate_EXPECTED_REsearchgroup
startswithr'   r6   
_OPERATORSr   r   r4   strip)	re   r8   ir   matchri   rj   ZrequiredZmsg_idr   r   r   get_expected_messages   s(    




 rv   c             C   s^   |   }|| i }x>tt|D ],\}}|dkr&|| |dk r&| ||< q&W ||fS )a  Takes two multisets and compares them.

    A multiset is a dict with the cardinality of the key as the value.

    :param left_op: The expected entries.
    :param right_op: Actual entries.

    :returns: The two multisets of missing and unexpected messages.
    r   )copysubtractlistsixZ	iteritemspop)Zleft_opZright_opmissing
unexpectedkeyrS   r   r   r   multiset_difference   s    


r   c               @   sh   e Zd Z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dd Zdd Zdd ZdS )LintModuleTestNc             C   sz   t  }t | _| j| d| jj_t| j | j	d y| j
|j | j  W n tk
rn   Y nX || _d S )Nr   I)r7   r   ZPyLinter_linterZset_reporterZconfigZ
persistentr   Z
initializedisableZread_config_filerO   Zload_config_filer   
_test_file)r+   	test_fileZtest_reporterr   r   r   rL      s    

zLintModuleTest.__init__c          	   C   s   |   r$tdtjdd f  g }x@| jjd D ]0}yt| W q6 t	k
rd   |
| Y q6X q6W |rtdd|f  | jjd rdd	 | jjd dD }t }||krtd
|f  d S )NzTest cannot run with Python %s. r   rE   zRequires %s to be present.r@   rF   c             S   s   g | ]}|  qS r   )rs   )r0   itemr   r   r   rb     s    z(LintModuleTest.setUp.<locals>.<listcomp>z-Test cannot run with Python implementation %r)!_should_be_skipped_due_to_versionpytestskipr   ri   r4   r   rI   
__import__ImportErrorr9   rX   platformZpython_implementation)r+   r|   ZreqZimplementationsimplementationr   r   r   setUp   s$    zLintModuleTest.setUpc             C   s$   t j| jjd k p"t j| jjd kS )NrC   rD   )r   r   r   rI   )r+   r   r   r   r     s    z0LintModuleTest._should_be_skipped_due_to_versionc             C   s   d| j j| jj| jjf S )Nz
%s (%s.%s))r   rH   	__class__r   r   )r+   r   r   r   __str__  s    zLintModuleTest.__str__c             C   s   t | jjS )N)openr   r[   )r+   r   r   r   _open_expected_file  s    z"LintModuleTest._open_expected_filec             C   sH   | j jdkrt| j jS d| j jkr6tj| j jddS tj| j jddS )NZinvalid_encoded_datalatin1)encodingutf8)r   rH   r   r\   io)r+   r   r   r   _open_source_file  s
    z LintModuleTest._open_source_filec          	   C   sJ   |   }t|}W d Q R X |r>|  }t|}W d Q R X ng }||fS )N)r   rv   r   rf   )r+   fobjZexpected_msgsZexpected_output_linesr   r   r   _get_expected  s    

zLintModuleTest._get_expectedc             C   sd   | j jj}|jdd d t }g }x4|D ],}||j|jf  d7  < |t	
| q,W ||fS )Nc             S   s   | j | j| jfS )N)r   r   r   )mr   r   r   rB   +  s    z.LintModuleTest._get_received.<locals>.<lambda>)r~   r$   )r   Zreporterr8   sortrk   rl   r   r   r9   r   r!   )r+   r8   Zreceived_msgsZreceived_output_linesr   r   r   r   _get_received)  s    

zLintModuleTest._get_receivedc             C   s   | j | jjg |  \}}|  \}}||krd| jj g}t||\}}|rt|d |	dd t
|D  |r|d |	dd t
|D  td| | ||| d S )NzWrong results for file "%s":z
Expected in testdata:c             s   s   | ]}d | V  qdS )z %3d: %sNr   )r0   r   r   r   r   r1   ?  s    z*LintModuleTest._runTest.<locals>.<genexpr>z
Unexpected in testdata:c             s   s   | ]}d | V  qdS )z %3d: %sNr   )r0   r   r   r   r   r1   B  s    r   )r   Zcheckr   r;   r   r   rH   r   r9   extendsortedr   ZfailrX   _check_output_text)r+   expected_messagesZexpected_textZreceived_messagesZreceived_textr   r|   r}   r   r   r   _runTest3  s    


zLintModuleTest._runTestc             C   sJ   g g  }}x6|D ].}|d |d f|kr4| | q| | qW ||fS )Nr$   r   )r9   )r+   r   linesemittedZomittedr   r   r   r   _split_linesF  s    

zLintModuleTest._split_linesc             C   s$   |  ||d |ks t| jjd S )Nr   )r   AssertionErrorr   rH   )r+   r   expected_linesreceived_linesr   r   r   r   O  s    z!LintModuleTest._check_output_text)r   r   r   ZmaxDiffrL   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r      s   
	r   c                   s$   e Zd Z fddZdd Z  ZS )LintModuleOutputUpdatec                s,   yt t|  S  tk
r&   t S X d S )N)superr   r   IOErrorr   StringIO)r+   )r   r   r   r   V  s    z*LintModuleOutputUpdate._open_expected_filec       	   	   C   s   |sd S |  ||\}}||kr~|| |jdd d t| jjd0}tj|dd}x|D ]}||	  q^W W d Q R X d S )Nc             S   s   | d | d | d fS )Nr$   r   r   r   )r   r   r   r   rB   c  s    z;LintModuleOutputUpdate._check_output_text.<locals>.<lambda>)r~   wr   )Zdialect)
r   r   r   r   r   r[   rc   writerZwriterowr,   )	r+   r   r   r   r   Z	remainingr   r   r   r   r   r   r   \  s    

z)LintModuleOutputUpdate._check_output_text)r   r   r   r   r   __classcell__r   r   )r   r   r   U  s   r   c              C   s\   t jt jt jtd} g }x4t | D ]&}|dkr.|dr.|t	| | q.W |S )NZ
functionalz__init__.pyz.py)
rU   rV   rX   dirnameabspath__file__listdirendswithr9   r?   )Z	input_dirZsuitefnamer   r   r   	get_testsi  s    r   c             C   s   g | ]
}|j qS r   )rH   )r0   tr   r   r   rb   t  s    rb   r   )Zidsc             C   s(   t rt| nt| }|  |  d S )N)UPDATEr   r   r   r   )r   ZLintTestr   r   r   test_functionalw  s    r   __main__z-uT)6r^   rc   rk   r   operatorrU   rer   r   rz   Z	six.movesr   r   Zpylintr   r   r   r   Zexcelr   Zregister_dialect	Exceptionr   r   
namedtupler   Z_MESSAGEcompilern   r6   ZBaseReporterr7   r/   r?   gtltgelerr   rf   rv   r   r   r   r   ZTESTSZTESTS_NAMESZmarkZparametrizer   r   argvremovemainr   r   r   r   <module>   s\   	;
p

