o
    NiT                     @  sP  d 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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mZmZ ddl
mZmZ ddlmZ ddlmZ e	d	Ze	d
Ze	dZd*ddZd+ddZ d,d-ddZ!d.ddZ"G dd dZ#G d d! d!Z$G d"d# d#e$Z%G d$d% d%ej&Z'G d&d' d'e$Z(G d(d) d)Z)dS )/z,Utilities parsing and analyzing Python code.    )annotationsN)	Signature)DEDENTINDENTNAMENEWLINENUMBEROPSTRING)COMMENTNL)Any)unparsez^\s*#: ?(.*)?
?$z^\s*$z^\s*(#.*)?$codestrreturnc                 C  s   |  ddS )N )replace)r    r   H/home/ubuntu/.local/lib/python3.10/site-packages/sphinx/pycode/parser.pyfilter_whitespace   s   r   nodeast.ASTlist[ast.expr]c                 C  s   t | tjr	| jS | jgS )z3Get list of targets from Assign and AnnAssign node.)
isinstanceastAssigntargetstarget)r   r   r   r   get_assign_targets   s   r    selfast.arg | None	list[str]c              	   C  s   |r|j }| jj}|dv rtd|  |dkr*|du s | j|kr$| jgS td|  |dv rUg }| jD ]}tt |t	|| W d   n1 sMw   Y  q3|S |dkry| j
jjdkrs|rs| j
j|krsdt	| j|d	  gS td|  |d
kr| gS |dkrt	| j
|S td| )zConvert assignment-AST to variable names.

    This raises `TypeError` if the assignment does not create new variable::

        ary[0] = 'foo'
        dic["bar"] = 'baz'
        # => TypeError
    )ConstantIndexSlice	Subscriptz%r does not create new variableNameNz*The assignment %r is not instance variable)TupleList	Attributez%sr   r   StarredzUnexpected node name %r)arg	__class____name__	TypeErroridelts
contextlibsuppressextendget_lvar_namesvalueattrNotImplementedError)r   r!   self_id	node_namememberseltr   r   r   r6   %   s:   	
r6   sc                 C  s2   ddd}| |_ t|}|r|ddS dS )	z1Remove common leading indentation from docstring.r   Nonec                   S  s   d S Nr   r   r   r   r   dummyU   s   zdedent_docstring.<locals>.dummyz
 Nr   r?   )__doc__inspectgetdoclstriprstrip)r>   rA   	docstringr   r   r   dedent_docstringR   s   

rJ   c                   @  s8   e Zd ZdZdddZdddZdddZdddZdS )Tokenz)Better token wrapper for tokenize module.kindintr7   r   starttuple[int, int]endsourcer   r   r?   c                 C  s"   || _ || _|| _|| _|| _d S r@   )rL   r7   rN   rP   rQ   )r!   rL   r7   rN   rP   rQ   r   r   r   __init__d   s
   
zToken.__init__otherboolc                 C  sb   t |tr
| j|kS t |tr| j|kS t |ttB r%| j| jgt|kS |d u r+dS td| )NFzUnknown value: %r)r   rM   rL   r   r7   listtuple
ValueError)r!   rS   r   r   r   __eq__r   s   



zToken.__eq__
conditionsc                   s   t  fdd|D S )Nc                 3  s    | ]} |kV  qd S r@   r   ).0	candidater!   r   r   	<genexpr>   s    zToken.match.<locals>.<genexpr>)any)r!   rY   r   r\   r   match~   s   zToken.matchc                 C  s    dt j| j d| j dS )Nz<Token kind=z value=>)tokenizetok_namerL   r7   stripr\   r   r   r   __repr__   s    zToken.__repr__N)rL   rM   r7   r   rN   rO   rP   rO   rQ   r   r   r?   )rS   r   r   rT   )rY   r   r   rT   )r   r   )r/   
__module____qualname__rD   rR   rX   r_   rd   r   r   r   r   rK   a   s    


rK   c                   @  s4   e Zd ZdddZdd
dZdddZdddZdS )TokenProcessorbuffersr#   r   r?   c                   s2   t | || _t fdd| _d | _d | _d S )Nc                     s   t  S r@   )nextr   linesr   r   <lambda>   s    z)TokenProcessor.__init__.<locals>.<lambda>)iterrh   ra   generate_tokenstokenscurrentprevious)r!   rh   r   rj   r   rR      s
   
zTokenProcessor.__init__linenorM   r   c                 C     | j |d  S zReturns specified line.   rh   r!   rr   r   r   r   get_line      zTokenProcessor.get_lineToken | Nonec                 C  s>   z| j | _tt| j | _ W | j S  ty   d| _ Y | j S w )z_Fetch the next token from source code.

        Returns ``None`` if sequence finished.
        N)rp   rq   rK   ri   ro   StopIterationr\   r   r   r   fetch_token   s   zTokenProcessor.fetch_token	conditionr   list[Token]c                 C  s   g }|    }rI|| ||kr	 |S |tdgkr$|| tdg7 }n|tdgkr4|| tdg7 }n|tdgkrC|| tdg7 }|    }s|S )zlFetch tokens until specified token appeared.

        .. note:: This also handles parenthesis well.
        (){}[])r|   appendr	   fetch_until)r!   r}   ro   rp   r   r   r   r      s   
zTokenProcessor.fetch_untilN)rh   r#   r   r?   rr   rM   r   r   )r   rz   )r}   r   r   r~   )r/   re   rf   rR   rx   r|   r   r   r   r   r   rg      s
    


rg   c                      s6   e Zd ZdZd fddZdd	d
ZdddZ  ZS )AfterCommentParserzPython source code parser to pick up comments after assignments.

    This parser takes code which starts with an assignment statement,
    and returns the comment for the variable if one exists.
    rk   r#   r   r?   c                   s   t  | d | _d S r@   )superrR   commentr!   rk   r.   r   r   rR      s   
zAfterCommentParser.__init__r~   c                 C  s   g }|    }rf|| |tdgkr|| tdg7 }nC|tdgkr-|| tdg7 }n3|tdgkr=|| tdg7 }n#|tkrI|| t7 }n|tdgkrR	 |S |r`|jtttt	hvr`	 |S |    }s|S )z%Fetch right-hand value of assignment.r   r   r   r   r   r   ;)
r|   r   r	   r   r   r   rL   r   r   r
   )r!   ro   rp   r   r   r   fetch_rvalue   s&   
zAfterCommentParser.fetch_rvaluec                 C  s   |    }r"|tdgtts"|sJ |    }r"|tdgttr|dus(J |tdgkr;|   | j}|dus;J |tkrE|j| _dS dS )z3Parse the code and obtain comment after assignment.=N)	r|   r_   r	   r   r   r   rp   r7   r   )r!   tokr   r   r   parse   s   

zAfterCommentParser.parserk   r#   r   r?   )r   r~   rC   )r/   re   rf   rD   rR   r   r   __classcell__r   r   r   r   r      s
    
r   c                      s   e Zd ZdZdH fdd	ZdIddZdJddZdJddZdKddZdLddZ	dMddZ
dNd d!ZdNd"d#ZdOd%d&ZdPd)d*ZdQ fd,d-ZdRd/d0ZdSd2d3ZdTd5d6ZdUd8d9ZdVd;d<ZdWd>d?ZdXdAdBZdYdCdDZdZdFdGZ  ZS )[VariableCommentPickerz7Python source code parser to pick up variable comments.rh   r#   encodingr   r   r?   c                   sl   t  | _|| _|| _g | _g | _d | _i | _i | _	d | _
i | _g | _i | _d | _d | _d | _t   d S r@   )	itertoolscountcounterrh   r   contextcurrent_classescurrent_functioncommentsr   rq   	defordersfinals	overloadstypingtyping_finaltyping_overloadr   rR   )r!   rh   r   r   r   r   rR      s    
zVariableCommentPicker.__init__namelist[str] | Nonec                 C  s@   | j r| jr| jd dkr| jdd |g S dS g | j|S )z;Get qualified name for given object as a list of string(s).rR   N)r   r   r   )r!   r   r   r   r   get_qualname_for   s
   z&VariableCommentPicker.get_qualname_forc                 C  s,   |  |}|rt| j| jd|< d S d S N.)r   ri   r   r   joinr!   r   qualnamer   r   r   	add_entry  s   
zVariableCommentPicker.add_entryc                 C  s(   |  |}|r| jd| d S d S r   )r   r   r   r   r   r   r   r   add_final_entry	  s   
z%VariableCommentPicker.add_final_entryfuncast.FunctionDefc                 C  sF   ddl m} | |j}|r!| jd|g }||| d S d S )Nr   )signature_from_astr   )sphinx.util.inspectr   r   r   r   
setdefaultr   r   )r!   r   r   r   r   r   r   r   add_overload_entry  s   z(VariableCommentPicker.add_overload_entryr   c                 C  s6   |  |}|rd|d d }|| j||f< d S d S Nr   r   )r   r   r   )r!   r   r   r   basenamer   r   r   add_variable_comment  s
   
z*VariableCommentPicker.add_variable_comment
annotationr   c                 C  s:   |  |}|rd|d d }t|| j||f< d S d S r   )r   r   ast_unparser   )r!   r   r   r   r   r   r   r   add_variable_annotation  s
   
z-VariableCommentPicker.add_variable_annotation
decoratorsr   rT   c              	   C  d   g }| j r|d| j   | jr|| j |D ]}zt||v r%W  dS W q ty/   Y qw dS )Nz%s.finalTF)r   r   r   r   r9   )r!   r   final	decoratorr   r   r   is_final#     zVariableCommentPicker.is_finalc              	   C  r   )Nz%s.overloadTF)r   r   r   r   r9   )r!   r   overloadr   r   r   r   is_overload3  r   z!VariableCommentPicker.is_overloadr"   c                 C  s@   | j r| j jjr| j jjd S | j r| j jjr| j jjd S dS )z8Returns the name of the first argument if in a function.r   N)r   argsposonlyargsr\   r   r   r   get_selfC  s
   zVariableCommentPicker.get_selfrr   rM   c                 C  rs   rt   rv   rw   r   r   r   rx   K  ry   zVariableCommentPicker.get_liner   c                   s   t  | || _dS )z(Updates self.previous to the given node.N)r   visitrq   r!   r   r   r   r   r   O  s   
zVariableCommentPicker.visit
ast.Importc                 C  sn   |j D ]1}| |jp|j |jdkr|jp|j| _q|jdkr(|jp%|j| _q|jdkr4|jp2|j| _qdS )8Handles Import node and record the order of definitions.r   ztyping.finalztyping.overloadN)namesr   asnamer   r   r   r   r!   r   r   r   r   r   visit_ImportT  s   



z"VariableCommentPicker.visit_Importast.ImportFromc                 C  sh   |j D ].}| |jp|j |jdkr |jdkr |jp|j| _q|jdkr1|jdkr1|jp/|j| _qdS )r   r   r   r   N)r   r   r   r   moduler   r   r   r   r   r   visit_ImportFrom`  s   
z&VariableCommentPicker.visit_ImportFrom
ast.Assignc                   s  zt |}ttj fdd|D g } |j}W n
 ty%   Y dS w t|dr;|j	r;|D ]	} 
||j	 q0nt|drO|jrO|D ]	} 
||j qEt||jd g j|jd  }|  |jrt|jr|D ]} |td|j  | qpdS t|d|j rg }t|jd D ]} |jd | }	t|	r|td|	 q |rtdt|}
|D ]} ||
  | qdS |D ]} | qdS )	z3Handles Assign node and pick up a variable comment.c                   s   g | ]
}t |  d qS )r\   )r6   r   )rZ   tr\   r   r   
<listcomp>p  s    z6VariableCommentPicker.visit_Assign.<locals>.<listcomp>Nr   type_commentz\1ru   
)r    	functoolsreduceoperatoriaddrx   rr   r0   hasattrr   r   r   r   
col_offsetrh   r   r   
comment_rer_   r   subr   	indent_reranger   rJ   r   reversed)r!   r   r   varnamescurrent_linevarnameparsercomment_linesibefore_liner   r   r\   r   visit_Assignj  sZ   
z"VariableCommentPicker.visit_Assignast.AnnAssignc                 C     |  | dS )z6Handles AnnAssign node and pick up a variable comment.N)r   r   r   r   r   visit_AnnAssign  ry   z%VariableCommentPicker.visit_AnnAssignast.Exprc                 C  s   t | jtjtjB r\t |jtjr^t |jjtr`z9t| j}t	|d | 
 }|D ]%}t |jjtr7|jj}n
|jj| jp?d}| |t| | | q)W dS  ty[   Y dS w dS dS dS )z2Handles Expr node and pick up a comment if string.r   utf-8N)r   rq   r   r   	AnnAssignr7   r$   r   r    r6   r   decoder   r   rJ   r   r0   )r!   r   r   r   r   rI   r   r   r   
visit_Expr  s(   

z VariableCommentPicker.visit_Exprast.Tryc                 C  s0   |j D ]}| | q|jD ]}| | qdS )zHandles Try node and processes body and else-clause.

        .. note:: pycode parser ignores objects definition in except-clause.
        N)bodyr   orelse)r!   r   subnoder   r   r   	visit_Try  s
   

zVariableCommentPicker.visit_Tryast.ClassDefc                 C  st   | j |j | |j | |jr| |j | j|j || _|j	D ]}| 
| q&| j  | j   dS )z&Handles ClassDef node and set context.N)r   r   r   r   r   decorator_listr   r   rq   r   r   popr!   r   childr   r   r   visit_ClassDef  s   

z$VariableCommentPicker.visit_ClassDefc                 C  s   | j du rA| |j | |jr| |j | |jr"| | | j	|j || _ |j
D ]}| | q/| j  d| _ dS dS )z)Handles FunctionDef node and set context.N)r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   visit_FunctionDef  s   




z'VariableCommentPicker.visit_FunctionDefast.AsyncFunctionDefc                 C  r   )z.Handles AsyncFunctionDef node and set context.N)r   r   r   r   r   visit_AsyncFunctionDef  ry   z,VariableCommentPicker.visit_AsyncFunctionDef)rh   r#   r   r   r   r?   )r   r   r   r   )r   r   r   r?   )r   r   r   r?   )r   r   r   r   r   r?   )r   r   r   r   r   r?   )r   r   r   rT   )r   r"   r   )r   r   r   r?   )r   r   r   r?   )r   r   r   r?   )r   r   r   r?   )r   r   r   r?   )r   r   r   r?   )r   r   r   r?   )r   r   r   r?   )r   r   r   r?   )r   r   r   r?   )r/   re   rf   rD   rR   r   r   r   r   r   r   r   r   r   rx   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r      s.    




	









7




r   c                      sJ   e Zd ZdZd fddZdddZdddZdddZdddZ  Z	S )DefinitionFinderzXPython source code parser to detect location of functions,
    classes and methods.
    rk   r#   r   r?   c                   s(   t  | d | _g | _g | _i | _d S r@   )r   rR   r   r   indentsdefinitionsr   r   r   r   rR     s
   
zDefinitionFinder.__init__r   r   entrytuple[str, int, int]c                 C  s:   | j r| j d d |d   krdkrdS  || j|< dS )zAdd a location of definition.r   r   defN)r   r   )r!   r   r  r   r   r   add_definition  s   &zDefinitionFinder.add_definitionc                 C  s   	 |   }|du rdS |tkrnJ|tdgkr-| jdu s$| jttttr-| j	du r,|| _	n-|t
dgr:| d n |t
dgrG| d n|tkrR| jd n|tkrZ|   q)z1Parse the code to obtain location of definitions.TN@classr  )rS   NN)r|   r   r	   rq   r_   r   r   r   r   r   r   parse_definitionr   r   finalize_block)r!   tokenr   r   r   r     s,   

zDefinitionFinder.parsetypc                 C  s   |   }| j|j d| j}| jr| jjd }d| _n|jd }| tdg |   	t
trB| t | j|||f dS | ||||jd f | j  dS )zParse AST of definition.r   r   N:)r|   r   r   r7   r   r   rN   r   r	   r_   r   r   r   r   r  rP   r   )r!   r
  r   funcname	start_posr   r   r   r    s   

z!DefinitionFinder.parse_definitionc                 C  s|   | j  }|d dkr<|\}}}| jjd d }t| |r,|d8 }t| |s | ||||f | j  dS dS )zFinalize definition block.r   rS   ru   N)	r   r   rp   rP   emptyline_rer_   rx   r  r   )r!   
definitionr
  r  r  end_posr   r   r   r  &  s   

zDefinitionFinder.finalize_blockr   )r   r   r  r  r   r?   rC   )r
  r   r   r?   )
r/   re   rf   rD   rR   r  r   r  r  r   r   r   r   r   r     s    


r   c                   @  s:   e Zd ZdZdddd	Zdd
dZdddZdddZdS )ParserzyPython source code parser to pick up variable comments.

    This is a better wrapper for ``VariableCommentPicker``.
    r   r   r   r   r   r?   c                 C  s8   t || _|| _i | _i | _i | _i | _g | _i | _d S r@   )	r   r   r   r   r   r   r   r   r   )r!   r   r   r   r   r   rR   9  s   

zParser.__init__c                 C  s   |    |   dS )zParse the source code.N)parse_commentsr  r\   r   r   r   r   C  s   zParser.parsec                 C  sZ   t j| jdd}t| jd| j}|| |j| _|j| _|j	| _	|j
| _
|j| _dS )z$Parse the code and pick up comments.T)type_commentsN)r   r   r   r   
splitlinesr   r   r   r   r   r   r   )r!   treepickerr   r   r   r  H  s   
zParser.parse_commentsc                 C  s$   t | jd}|  |j| _dS )z0Parse the location of definitions from the code.TN)r   r   r  r   r   )r!   r   r   r   r   r  S  s   zParser.parse_definitionN)r   )r   r   r   r   r   r?   rC   )r/   re   rf   rD   rR   r   r  r  r   r   r   r   r  3  s    


r  )r   r   r   r   )r   r   r   r   r@   )r   r   r!   r"   r   r#   )r>   r   r   r   )*rD   
__future__r   r   r3   r   rE   r   r   rera   r   r	  r   r   r   r   r   r	   r
   r   r   r   r   sphinx.pycode.astr   r   compiler   r   r  r   r    r6   rJ   rK   rg   r   NodeVisitorr   r   r  r   r   r   r   <module>   s<    $





-$-2  M