B
    nôb\!G  ã            
   @   s²  d Z ddlmZmZ ddlm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mZmZmZmZ ddlmZmZmZmZmZmZ ddlmZ ddlmZmZ dd	lm Z 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,m-Z- ddl.m/Z/ ddl0m1Z1 yeddƒZ2W n2 e3k
rL Z4 zddl5Z5e5j5Z2W ddZ4[4X Y nX e 6¡ Z7dZ8e
j9Z:ej;de2dƒe8e:d G dd„ de/ƒZ<G dd„ deƒZ=dd„ Z>e?dkr®e>ƒ  dS )zPylint widgeté    )Úprint_functionÚwith_statementN)Úgetopenfilename)Ú
QByteArrayÚQProcessÚ
QTextCodecÚSignalÚSlot)ÚQHBoxLayoutÚQLabelÚQMessageBoxÚQTreeWidgetItemÚQVBoxLayoutÚQWidget)Údependencies)Úget_conf_pathÚget_translation)ÚpickleÚto_text_string)Úicon_manager)Úto_unicode_from_fs)Úcreate_toolbutton)Úgetcwd_or_home)Úis_module_or_packageÚPythonModulesComboBox)ÚOneColumnTree)Ú
TextEditorÚpylintZspyder_pylintz>=0.25zStatic code analysis)Zrequired_versionZinstalled_versionc               @   s<   e Zd Zdd„ Zdd„ Zdd„ Zdd„ Zd	d
„ Zdd„ ZdS )ÚResultsTreec             C   s,   t  | |¡ d | _d | _d | _|  d¡ d S )NÚ )r   Ú__init__ÚfilenameÚresultsÚdataÚ	set_title)ÚselfÚparent© r'   ú>lib/python3.7/site-packages/spyder_pylint/widgets/pylintgui.pyr    :   s
    zResultsTree.__init__c             C   s8   | j  t|ƒ¡}|dk	r4|\}}|  ¡ j ||d¡ dS )zDouble-click eventNr   )r#   ÚgetÚidr&   Z	edit_gotoÚemit)r%   Úitemr#   ÚfnameÚlinenor'   r'   r(   Ú	activatedA   s    zResultsTree.activatedc             C   s   |   |¡ dS )zClick eventN)r/   )r%   r,   r'   r'   r(   ÚclickedH   s    zResultsTree.clickedc             C   s   |   ¡  |  d¡ d S )Nr   )Úclearr$   )r%   r'   r'   r(   Úclear_resultsL   s    zResultsTree.clear_resultsc             C   s   || _ || _|  ¡  d S )N)r!   r"   Úrefresh)r%   r!   r"   r'   r'   r(   Úset_resultsP   s    zResultsTree.set_resultsc             C   s†  t dƒ| j }|  |¡ |  ¡  i | _t dƒt d¡| jd ft dƒt d¡| jd ft dƒt d	¡| jd
 ft dƒt d¡| jd ff}xô|D ]ê\}}}|dt|ƒt|ƒdkr¸dndf 7 }t	| |gt	j
ƒ}| d|¡ |sì| d¡ i }xŠ|D ]€\}}}	}
t t | j¡¡d }| |¡s>| |¡}||d … }t | j¡}| d¡s`||krnt ||¡}ntj|f| d¡žŽ }t |¡rœt |d¡}x(dD ] }t || ¡r¢|| }P q¢W t | j¡r| |¡}|d krt	||gt	j
ƒ}| dt d¡¡ |||< |}n|}t|
ƒdkr:d|
||	f }nd||	f }t	||gt	j
ƒ}| dt d¡¡ ||f| jt|ƒ< qøW q’W d S )NzResults for Z
ConventionZ
conventionzC:ZRefactorZrefactorzR:ÚWarningZwarningzW:ÚErrorÚerrorzE:z (%d message%s)é   Úsr   r   TÚ.r    )z.pyz.pywZpythonz[%s] %d : %sz%d : %sZarrow)Ú_r!   r$   r1   r#   ÚimaÚiconr"   Úlenr   ZTypeZsetIconZsetDisabledÚospÚsplitextÚbasenameÚ
startswithÚfindÚdirnameÚjoinÚsplitÚisdirÚisfiler)   r*   )r%   Útitler"   r=   ZmessagesZ
title_itemÚmodulesÚmoduler.   ÚmessageÚmsg_idrA   Zi_baserD   ÚmodnameZextr&   r,   ÚtextZmsg_itemr'   r'   r(   r3   U   sd    






zResultsTree.refreshN)	Ú__name__Ú
__module__Ú__qualname__r    r/   r0   r2   r4   r3   r'   r'   r'   r(   r   9   s   r   c               @   s¶   e Zd ZdZedƒZdZeeƒZ	d&dd„Z
dd„ Zeƒ d	d
„ ƒZdd„ Zdd„ Zdd„ Zdd„ Zdd„ Zeƒ dd„ ƒZeƒ dd„ ƒZd'dd„Zd(dd„Zdd „ Zd!d"„ Zd)d#d$„Zd%S )*ÚPylintWidgetz
    Pylint widget
    zpylint.resultsz1.1.0éd   c          	   C   sB  t  | |¡ |  d¡ d | _d | _|| _g | _t | j	¡rŠy6t
 t| j	dƒ ¡ ¡}|d | jkrn|dd … | _W n ttfk
rˆ   Y nX t| ƒ| _t| t d¡tdƒtdƒ| jdd	| _t| t d
¡tdƒtdƒdd| _| jj | jj¡ | jj | j¡ t| t d¡tdƒ| jd}tƒ | _ tƒ | _!t| t d¡tdƒdtdƒ| j"d| _#t$| ƒ| _%t&ƒ }| '| j¡ | '|¡ | '| j¡ | '| j¡ t&ƒ }| '| j ¡ | (¡  | '| j!¡ | (¡  | '| j#¡ t)ƒ }| *|¡ | *|¡ | '| j%¡ |  +|¡ d | _,|  -d¡ |  ¡  | jr2|  .¡  | j /|  0¡ ¡ n| j d¡ d S )NZPylintÚrbr   r8   ÚrunZAnalyzezRun analysisT)r=   rO   ÚtipÚ	triggeredÚtext_beside_iconÚstopZStopzStop current analysis)r=   rO   rW   rY   ZfileopenzSelect Python file)r=   rW   rX   ÚlogZOutputzComplete output)r=   rO   rY   rW   rX   F)1r   r    ZsetWindowTitleÚoutputÚerror_outputÚmax_entriesÚrdatar?   rH   ÚDATAPATHr   ÚloadsÚopenÚreadÚVERSIONÚEOFErrorÚImportErrorr   Ú	filecombor   r<   r=   r;   ÚstartÚstart_buttonÚstop_buttonZvalidÚconnectÚ
setEnabledÚ	show_dataÚselect_filer   Ú	ratelabelÚ	datelabelÚshow_logÚ
log_buttonr   Ú
treewidgetr
   Z	addWidgetZ
addStretchr   Z	addLayoutZ	setLayoutÚprocessÚset_running_stateÚremove_obsolete_itemsZaddItemsÚget_filenames)r%   r&   r^   r#   Zbrowse_buttonZhlayout1Zhlayout2Zlayoutr'   r'   r(   r    —   sv    









zPylintWidget.__init__c             C   s~   t |ƒ}|  ¡  |  |¡\}}|d krJ| j |¡ | j | j ¡ d ¡ n| j | j |¡¡ | j ¡  | j 	¡ rz|  
¡  d S )Nr8   )r   Úkill_if_runningÚget_datarg   ZaddItemZsetCurrentIndexÚcountZfindTextZselectedZis_validrh   )r%   r!   ÚindexÚ_datar'   r'   r(   Úanalyzeá   s    

zPylintWidget.analyzec             C   sJ   | j  d¡ t| tdƒtƒ tdƒd ƒ\}}| j  d¡ |rF|  |¡ d S )NFzSelect Python filezPython filesz (*.py ; *.pyw)T)Úredirect_stdior+   r   r;   r   r}   )r%   r!   Z
_selfilterr'   r'   r(   rn   î   s    zPylintWidget.select_filec             C   s   dd„ | j D ƒ| _ dS )zRemoving obsolete itemsc             S   s    g | ]\}}t |ƒr||f‘qS r'   )r   )Ú.0r!   r#   r'   r'   r(   ú
<listcomp>ú   s    z6PylintWidget.remove_obsolete_items.<locals>.<listcomp>N)r_   )r%   r'   r'   r(   rv   ø   s    z"PylintWidget.remove_obsolete_itemsc             C   s   dd„ | j D ƒS )Nc             S   s   g | ]\}}|‘qS r'   r'   )r   r!   r|   r'   r'   r(   r€   þ   s    z.PylintWidget.get_filenames.<locals>.<listcomp>)r_   )r%   r'   r'   r(   rw   ý   s    zPylintWidget.get_filenamesc             C   s>   t  |¡}x.t| jƒD ]\}\}}||kr||fS qW dS d S )N)NN)r?   ÚabspathÚ	enumerater_   )r%   r!   r{   r-   r#   r'   r'   r(   ry      s
    
zPylintWidget.get_datac             C   sJ   t  |¡}|  |¡\}}|d k	r,| j |¡ | j d||f¡ |  ¡  d S )Nr   )r?   r   ry   r_   ÚpopÚinsertÚsave)r%   r!   r#   r{   r|   r'   r'   r(   Úset_data  s    
zPylintWidget.set_datac             C   sF   x t | jƒ| jkr | j d¡ qW t | jg| j t| jdƒd¡ d S )NéÿÿÿÿÚwbé   )	r>   r_   r^   rƒ   r   Údumprd   rb   r`   )r%   r'   r'   r(   r…     s    zPylintWidget.savec             C   s$   | j r t| j tdƒddd ¡  d S )NzPylint outputT)i¼  iô  )rI   ÚreadonlyÚsize)r\   r   r;   Úexec_)r%   r'   r'   r(   rq     s    zPylintWidget.show_logc                s:  t ˆ j ¡ ƒ}tˆ ƒˆ _ˆ j tj¡ ˆ j t 	|¡¡ ˆ jj
 ˆ j¡ ˆ jj ‡ fdd„¡ ˆ jj tjf‡ fdd„	¡ ˆ jj ˆ jj¡ dˆ _dˆ _t}|d k	rêdddg}| d¡d	 d
krÎ|ddg7 }n
|dg7 }|t |¡g7 }nt |¡g}ˆ j tj|¡ ˆ j ¡ }ˆ  |¡ |s6t ˆ tdƒtdƒ¡ d S )Nc                  s   ˆ j ddS )NT)r7   )Úread_outputr'   )r%   r'   r(   Ú<lambda>$  s    z$PylintWidget.start.<locals>.<lambda>c                s   ˆ   | |¡S )N)Úfinished)ZecZes)r%   r'   r(   r   %  s    r   z-mr   z--output-format=textr:   r   Ú0z-iZyesz9--msg-template='{msg_id}:{line:3d},{column}: {obj}: {msg}r6   zProcess failed to start) r   rg   ÚcurrentTextr   rt   ZsetProcessChannelModeZSeparateChannelsZsetWorkingDirectoryr?   rD   ZreadyReadStandardOutputrk   rŽ   ZreadyReadStandardErrorr   Z
ExitStatusrj   r0   Úkillr\   r]   Ú
PYLINT_VERrF   rA   rh   ÚsysÚ
executableZwaitForStartedru   r   Úcriticalr;   )r%   r!   ZplverZp_argsZrunningr'   )r%   r(   rh     s2    




zPylintWidget.startTc             C   s   | j  | ¡ | j |¡ d S )N)ri   rl   rj   )r%   Ústater'   r'   r(   ru   A  s    zPylintWidget.set_running_stateFc             C   s’   |r| j  tj¡ n| j  tj¡ tƒ }x0| j  ¡ rX|rH|| j  ¡ 7 }q*|| j  ¡ 7 }q*W t	t
 | ¡ ¡ƒ}|r€|  j|7  _n|  j|7  _d S )N)rt   ZsetReadChannelr   ZStandardErrorZStandardOutputr   ZbytesAvailableZreadAllStandardErrorZreadAllStandardOutputr   Úlocale_codecZ	toUnicoder#   r]   r\   )r%   r7   ZqbarO   r'   r'   r(   rŽ   E  s    zPylintWidget.read_outputc             C   s  |   d¡ | jsB| jr>t | tdƒ| j¡ td| j tjd d S g g g g dœ}d}d}xÔ| j 	¡ D ]Æ}| 
|¡r„|t|ƒd … }qdt d|¡s’qd| d	¡}|d
kr¦qd|d |… }| d	|d ¡}	|	d
krÌqd||d |	…  ¡ }
|
sæqdt|
 d¡d ƒ}
||	d d … }||
||f}||d d	   |¡ qdW d }d}| j |¡}|dkrz| j d|¡}|dkrz| j|t|ƒ |… }d}|d k	rÈd}| j ||¡}|dkrÈ| j d|¡}| j|t|ƒ |… }t| j ¡ ƒ}|  |t ¡ |||f¡ | j| j | _| jdd d S )NFr6   zpylint error:

)Úfile)zC:zR:zW:zE:z************* Module r   z^[CRWE]+([0-9]{4})?:ú:r‡   r8   ú,r   zYour code has been rated at z/10zprevious run: T)Újustanalyzed)ru   r\   r]   r   r—   r;   Úprintr•   ÚstderrÚ
splitlinesrB   r>   ÚreÚmatchrC   ÚstripÚintrF   Úappendr   rg   r’   r†   ÚtimeZ	localtimerm   )r%   Z	exit_codeZexit_statusr"   Z
txt_modulerK   ÚlineZi1rM   Zi2Zline_nbrL   r,   ÚrateZtxt_rateZi_rateZ
i_rate_endZpreviousZtxt_prunZi_prunZ
i_prun_endr!   r'   r'   r(   r   V  s^    






zPylintWidget.finishedc             C   s2   | j d k	r.| j  ¡ tjkr.| j  ¡  | j  ¡  d S )N)rt   r˜   r   ZRunningr“   ZwaitForFinished)r%   r'   r'   r(   rx   ’  s    

zPylintWidget.kill_if_runningc             C   s`  |s
d | _ | j | j d k	o&t| j ƒdk¡ |  ¡  t| j ¡ ƒ}|sHd S |  |¡\}}|d krvt	dƒ}| j
 ¡  d}nÎ|\}}}	}
|d kr¢t	dƒ}| j
 ¡  d}n¢d}d}d}d}t|ƒd	krÄd
}nt|ƒdkrÔd}t	dƒ}|| ||d| f  }|	rt	dƒ}d||	f }||| 7 }| j
 ||
¡ tt d|¡dd}|| }| j |¡ | j |¡ d S )Nr   z#Source code has not been rated yet.r   z7Analysis did not succeed (see output for more details).z.<span style='color: #444444'><b>%s </b></span>z(<span style='color: %s'><b>%s</b></span>z&<span style='color: #666666'>%s</span>z#FF0000g      @z#22AA22g      @z#EE5500zGlobal evaluation:z%s/10zprevious run:z (%s %s/10)z%d %b %Y %H:%MÚutf8)Úencoding)r\   rr   rl   r>   rx   r   rg   r’   ry   r;   rs   r2   Úfloatr4   r¦   Zstrftimero   ZsetTextrp   )r%   r   r!   Z_indexr#   rO   Z	date_textZdatetimer¨   Zprevious_rater"   Z
text_styleZ
rate_styleZprevrate_styleZcolorZ	text_prunZdater'   r'   r(   rm   ˜  sN    


zPylintWidget.show_dataN)rT   )T)F)F)rP   rQ   rR   Ú__doc__r   r`   rd   r   Úboolr~   r    r}   r	   rn   rv   rw   ry   r†   r…   rq   rh   ru   rŽ   r   rx   rm   r'   r'   r'   r(   rS      s&   
J
&

<rS   c              C   sN   ddl m}  | dd}tdƒ}| dd¡ | ¡  | t¡ t | 	¡ ¡ dS )zRun pylint widget testr   )Úqapplicationé   )Z	test_timeNi€  ià  )
Úspyder.utils.qthelpersr®   rS   ZresizeZshowr}   Ú__file__r•   Úexitr   )r®   ZappZwidgetr'   r'   r(   ÚtestÊ  s    

r³   Ú__main__)@r¬   Z
__future__r   r   Úos.pathÚpathr?   r¡   r•   r¦   r   Zqtpy.compatr   Zqtpy.QtCorer   r   r   r   r	   Zqtpy.QtWidgetsr
   r   r   r   r   r   Zspyderr   Zspyder.config.baser   r   Zspyder.py3compatr   r   Zspyder.utilsr   r<   Zspyder.utils.encodingr   r°   r   Zspyder.utils.miscr   Zspyder.widgets.comboboxesr   r   Zspyder.widgets.onecolumntreer   Z*spyder.widgets.variableexplorer.texteditorr   r;   ÚKeyErrorr7   ÚgettextZcodecForLocaler™   ZPYLINT_REQVERÚ__version__r”   Úaddr   rS   r³   rP   r'   r'   r'   r(   Ú<module>   sH    
V  =
