
    Mh;                     F   d dl Z d dlZd dlZd dlmZmZmZ d dlmZ d dl	m
Z
 d dlmZmZmZmZmZmZmZmZ d dlmZ d dlmZmZmZmZmZmZmZmZ  G d d	          Zd
e j         dede!fdZ"deee j         ef                  deeee j                  ef                  fdZ#dS )    N)ChainMapOrderedDictdeque)suppress)	FrameType)AnyTupleIterableListMappingDictUnionSet)getattr_static)
CannotEvalhas_ast_namecopy_ast_without_contextis_standard_typesof_standard_typesis_anyof_typeensure_dictc                      e Zd Zdeeef         fdZededd fd            Z	de
j        defdZde
j        defdZd	 Zd
 Zd Zd Zde
j        fdZd Zdee
j        e
j        e
j        e
j        f         deeeeef         fdZde
j        deee
j        ef                  fdZde
j        deeee
j                 ef                  fdZdS )	Evaluatornamesc                 "    || _         i | _        dS )z
        Construct a new evaluator with the given variable names.
        This is a low level API, typically you will use `Evaluator.from_frame(frame)`.

        :param names: a mapping from variable names to their values.
        N)r   _cache)selfr   s     N/var/www/html/test/jupyter/venv/lib/python3.11/site-packages/pure_eval/core.py__init__zEvaluator.__init__   s     
    framereturnc           	           | t          t          |j                  t          |j                  t          |j                                      S )z
        Construct an Evaluator that can look up variables from the given frame.

        :param frame: a frame object, e.g. from a traceback or `inspect.currentframe().f_back`.
        )r   r   f_locals	f_globals
f_builtins)clsr"   s     r   
from_framezEvaluator.from_frame"   sL     s8''((())
 
   	r!   nodec                    t          |t          j                  s4t          d                    t          |          j                            t          t                    5  | j	        |         }|t          u rt          |cddd           S # 1 swxY w Y   	 |                     |          x| j	        |<   }|S # t          $ r t          | j	        |<    w xY w)z
        Find the value of the given node.
        If it cannot be evaluated safely, this raises `CannotEval`.
        The result is cached either way.

        :param node: an AST expression to evaluate
        :return: the value of the node
        z$node should be an ast.expr, not {!r}N)
isinstanceastexpr	TypeErrorformattype__name__r   KeyErrorr   r   _handle)r   r*   results      r   __getitem__zEvaluator.__getitem__0   s    $)) 	`BII$t**J]^^___h 	 	[&F##  	 	 	 	 	 	 	 	 	 	 	 	 	 	 	 		)-d););;DKM 	 	 	 *DK	s   #BBB B< <Cc                 f   t          t                    5  t          j        |          cddd           S # 1 swxY w Y   t	          |t          j                  r(	 | j        |j                 S # t          $ r t          w xY wt	          |t          j
                  r$| |j                 }|j        }t          ||          S t	          |t          j                  r|                     |          S t	          |t          j        t          j        t          j        t          j        f          r|                     |          S t	          |t          j                  r|                     |          S t	          |t          j                  r|                     |          S t	          |t          j                  r|                     |          S t	          |t          j                  r|                     |          S t	          |t          j                  r|                     |          S t          )z
        This is where the evaluation happens.
        Users should use `__getitem__`, i.e. `evaluator[node]`,
        as it provides caching.

        :param node: an AST expression to evaluate
        :return: the value of the node
        N)r   	Exceptionr-   literal_evalr,   Namer   idr3   r   	Attributevalueattrr   	Subscript_handle_subscriptr   r	   r   r   _handle_containerUnaryOp_handle_unaryBinOp_handle_binopBoolOp_handle_boolopCompare_handle_compareCall_handle_call)r   r*   r=   r>   s       r   r4   zEvaluator._handleK   s)    i   	* 	*#D))	* 	* 	* 	* 	* 	* 	* 	* 	* 	* 	* 	* 	* 	* 	* 	* dCH%% 	+!z$'** ! ! !  !cm,, 	+$E9D!%...cm,, 	+))$///sxCGSXFGG 	+))$///ck** 		+%%d+++ci(( 	+%%d+++cj)) 	+&&t,,,ck** 	+''---ch'' 	+$$T***s   6::A. .B c                     |j         rt           |j                 } fd|j        D             }t	          |t
          t          t          t          t          t          t          t          t          t          t          t           t"          t$          t&          t(                    st'          |          dk    r9t	          |t*          t,          t.          t0          t2          t4          t6                    s@t'          |          dk    rYt	          |t.          t8          t2          t4          t:                    r,d |D             }	  || S # t<          $ r}t          |d }~ww xY wt'          |          dk    rc|d         }t	          |t>          t@                    r&	  ||          S # t<          $ r}t          |d }~ww xY wt	          |tB          tD          tF                    rvtI          |t          t0          t          t*          t,          tJ          tL                     |D ]}tO          |dd           	  ||          S # t<          $ r}t          |d }~ww xY wt	          |tP          tR          tT          tV          t*          t,          tX          t.          tZ          t0                    r8tO          |dd           	  ||          S # t<          $ r}t          |d }~ww xY wt          )	Nc                      g | ]
}|         S  rN   ).0argr   s     r   
<listcomp>z*Evaluator._handle_call.<locals>.<listcomp>u   s    ///cS	///r!   r      c                 2    g | ]}t          |d d           S )Fcheck_dict_valuesdeep)r   )rO   rP   s     r   rQ   z*Evaluator._handle_call.<locals>.<listcomp>   s7        "#UKKK  r!      FrT   T).keywordsr   funcargsr   sliceintrangeroundcomplexlisttupleabshexbinoctboolordfloatlenchrsetdictstr	frozensetbytes	bytearrayobjectdivmodpowr8   r;   r1   allanysumr   r   r   r   sortedminmaxhashasciirepr)r   r*   rY   rZ   erP   xs   `      r   rK   zEvaluator._handle_callq   s   = 	DI////TY/// #  	(( 4yyA~~tS$Yy&QQ 4yyA~~tS&%C@@    D(tT{" ( ( ( a'( t99>>q'CdB%% ,,499$  , , ,$!+,dCc** ,UItS$USSS N NA%a5uMMMMM,499$  , , ,$!+, fc3c4T9  , "#DIIII,499$  , , ,$!+,s`   8D= =
EEE
F 
F1$F,,F1&
H1 1
I;II)
J4 4
K>KKc                    | |j                  }d}t          |j        |j                  D ]]\  }}| |         }t	          |          }t
          j        t          j        t
          j	        t          j
        t
          j        t          j        t
          j        t          j        t
          j        t          j        t
          j        t          j        t
          j        t          j        t
          j        t          j        t
          j        d t
          j        d i
|         }|t
          j        t
          j        fvr$t3          |dd           t3          |dd           	  |||          }n# t4          $ r}t6          |d }~ww xY w|s|c S |}_|S )NTc                 
    | |v S NrN   abs     r   <lambda>z+Evaluator._handle_compare.<locals>.<lambda>   s
    a1f r!   c                 
    | |vS r   rN   r   s     r   r   z+Evaluator._handle_compare.<locals>.<lambda>   s
    ! r!   FrT   )leftzipopscomparatorsr1   r-   EqoperatoreqNotEqneLtltLtEleGtgtGtEgeIsis_IsNotis_notInNotInr   r8   r   )	r   r*   r   r5   oprightop_typeop_funcr}   s	            r   rI   zEvaluator._handle_compare   sS   DITXt'788 	 	IBKE2hhG	8;	8?,,	33 G svsy111!$%dKKKK!%5tLLLL( u-- ( ( ( a'( DDs   E%%
E</E77E<c                 Z   t          | |j        d                  dd          }|j        dd          D ]w}t          |j        t          j                  r|pt          | |         dd          }<t          |j        t          j                  sJ |ot          | |         dd          }x|S )Nr   FrT   rW   )r   valuesr,   r   r-   OrAnd)r   r*   r   r   s       r   rG   zEvaluator._handle_boolop   s     Q E
 
 
 [_ 	 	E $'36**  0K5u      "$'3733333  1K5u! ! ! r!   c                    t          |j                  }t          j        t          j        t          j        t          j        t          j        t          j	        t          j
        t          j        t          j        t          j        t          j        t          j        t          j        t          j        t          j        t          j        t          j        t          j        t          j        t          j        t          j        t          j        t          j        t          j        i                    |          }|st:          | |j                 }t?          t          |          t@          tB          tD          tF                    }tI          |d|          }t          |          tJ          tL          fv o|t          j        k    }tI          | |j'                 ||p|          }	  |||          S # tP          $ r}t:          |d }~ww xY wNFrT   ))r1   r   r-   Addr   addSubsubMultmulDivtruedivFloorDivfloordivModmodPowrs   LShiftlshiftRShiftrshiftBitOror_BitXorxorBitAndand_getr   r   r   rk   rn   rl   r   r   rm   ro   r   r8   )	r   r*   r   r   r   	hash_type
formattingr   r}   s	            r   rE   zEvaluator._handle_binop   sc   tw--GX\GX\HhlGX%L(+GX\GX\JJIx|JJ
 #g,, 	  	DI4::sIt[II	 YOOO$ZZC</FGsw4F
!((y
 
 

	$2dE??" 	$ 	$ 	$!#	$s   G' '
G>1G99G>c                 p   t          | |j                 dd          }t          |j                  }t          j        t          j        t          j        t          j	        t          j
        t          j        t          j        t          j        i|         }	  ||          S # t          $ r}t          |d }~ww xY wr   )r   operandr1   r   r-   USubr   negUAddposNotnot_Invertinvertr8   r   )r   r*   r=   r   r   r}   s         r   rC   zEvaluator._handle_unary
  s    !%e
 
 
 tw--HhlHhlGX]J	

 	$2e99 	$ 	$ 	$!#	$s   
B 
B5(B00B5c           	           |j                  }t          |dt          t          |          t          t
                               |j        }t          |t          j	                  r(t           fd|j
        |j        |j        fD              }nJt          |t          j                  rt          t          |t          j                  r|j         } |         }t          |dd           	 ||         S # t           $ r t          w xY w)NFrT   c                 (    g | ]}|d n|         S r   rN   )rO   pr   s     r   rQ   z/Evaluator._handle_subscript.<locals>.<listcomp>"  s5        IDD47  r!   T)r=   r   r   r1   rl   r   r[   r,   r-   SlicelowerupperstepExtSlicer   Indexr8   )r   r*   r=   indexs   `   r   r@   zEvaluator._handle_subscript  s    TZ UUT;1W1W	
 	
 	
 	
 
eSY'' 	    #k5;
C  EE s|,, 	 %++ $KE%5tDDDD	< 	 	 		s   -C5 5Dc                     t          |t          j                  r|j        }d|v rt          n|j        } fd|D             }t          |t          j                  r|S t          |t          j                  rt          |          S t          d |D                       st          t          |t          j
                  r%	 t          |          S # t          $ r t          w xY wt          |t          j                  sJ  fdt          ||j                  D             }	 t          |          S # t          $ r t          w xY w)z;Handle container nodes, including List, Set, Tuple and DictNc                      g | ]
}|         S rN   rN   )rO   eltr   s     r   rQ   z/Evaluator._handle_container.<locals>.<listcomp>?  s    ***cS	***r!   c              3   :   K   | ]}t          |d d          V  dS )FTrT   N)r   )rO   r   s     r   	<genexpr>z.Evaluator._handle_container.<locals>.<genexpr>F  sC       
 
KNcUFFF
 
 
 
 
 
r!   c                 *    g | ]\  }}||         fS rN   rN   )rO   r   valr   s      r   rQ   z/Evaluator._handle_container.<locals>.<listcomp>S  s&    IIIhc3#tCy!IIIr!   )r,   r-   r   keysr   eltsr   r	   ra   rt   r   rk   r/   r   r   rl   )r   r*   r   pairss   `   r   rA   zEvaluator._handle_container4  s~   
 dCH%% 	9Dt||    9D****T***dCH%% 	KdCI&& 	;;  
 
RV
 
 
 
 
 	 dCG$$ 	!!4yy  ! ! !  ! $)))))IIII#dDK2H2HIII	;; 	 	 		s   C C%&D5 5Erootc              #      K   t          j        |          D ]=}t          |t           j                  s	 | |         }n# t          $ r Y 3w xY w||fV  >dS )a5  
        Find all expressions in the given tree that can be safely evaluated.
        This is a low level API, typically you will use `interesting_expressions_grouped`.

        :param root: any AST node
        :return: generator of pairs (tuples) of expression nodes and their corresponding values.
        N)r-   walkr,   r.   r   )r   r   r*   r=   s       r   find_expressionszEvaluator.find_expressionsY  s       HTNN 		 		DdCH-- T
    +		 		s   >
A
Ac                 Z    t          d |                     |          D                       S )aP  
        Find all interesting expressions in the given tree that can be safely evaluated,
        grouping equivalent nodes together.

        For more control and details, see:
         - Evaluator.find_expressions
         - is_expression_interesting
         - group_expressions

        :param root: any AST node
        :return: A list of pairs (tuples) containing:
                    - A list of equivalent AST expressions
                    - The value of the first expression node
                       (which should be the same for all nodes, unless threads are involved)
        c              3   ,   K   | ]}t          | |V  d S r   )is_expression_interesting)rO   pairs     r   r   z<Evaluator.interesting_expressions_grouped.<locals>.<genexpr>~  sA       !
 !
($/!
!
 !
 !
 !
 !
 !
r!   )group_expressionsr   )r   r   s     r   interesting_expressions_groupedz)Evaluator.interesting_expressions_groupedm  s@    " ! !
 !
--d33!
 !
 !
 
 
 	
r!   N)r2   
__module____qualname__r   rm   r   r    classmethodr   r)   r-   r.   r6   r4   rK   rI   rG   rE   rB   rC   r@   r   r   r	   r   r   rA   ASTr
   r   r   rN   r!   r   r   r      s       	gc3h/ 	 	 	 	 y [    [ S    6$CH $ $ $ $ $L@ @ @D! ! !F  &$ $ $B$#+ $ $ $ $   4##)SWch>?# 
tUC%	&# # # #JSW %#:N1O    (
CG 
U4PSPX>[^K^E_@` 
 
 
 
 
 
r!   r   r*   r=   r#   c                 8   t          t                    5  t          j        |            	 ddd           dS # 1 swxY w Y   t	          ||           rdS t          | t          j                  r+t          t          | j	        t                                |u rdS dS )an  
    Determines if an expression is potentially interesting, at least in my opinion.
    Returns False for the following expressions whose value is generally obvious:
        - Literals (e.g. 123, 'abc', [1, 2, 3], {'a': (), 'b': ([1, 2], [3])})
        - Variables or attributes whose name is equal to the value's __name__.
            For example, a function `def foo(): ...` is not interesting when referred to
            as `foo` as it usually would, but `bar` can be interesting if `bar is foo`.
            Similarly the method `self.foo` is not interesting.
        - Builtins (e.g. `len`) referred to by their usual name.

    This is a low level API, typically you will use `interesting_expressions_grouped`.

    :param node: an AST expression
    :param value: the value of the node
    :return: a boolean: True if the expression is interesting, False otherwise
    NFT)r   
ValueErrorr-   r9   r   r,   r:   getattrbuiltinsr;   rq   )r*   r=   s     r   r   r     s    $ 
*		                  E4   u tSX&&$'68844==u4s   8<<expressionsc                     i }| D ]W\  }}t          j        t          |                    }|                    |g |f          d                             |           Xt          |                                          S )a  
    Organise expression nodes and their values such that equivalent nodes are together.
    Two nodes are considered equivalent if they have the same structure,
    ignoring context (Load, Store, or Delete) and location (lineno, col_offset).
    For example, this will group together the same variable name mentioned multiple times in an expression.

    This will not check the values of the nodes. Equivalent nodes should have the same values,
    unless threads are involved.

    This is a low level API, typically you will use `interesting_expressions_grouped`.

    :param expressions: pairs of AST expressions and their values, as obtained from
                          `Evaluator.find_expressions`, or `(node, evaluator[node])`.
    :return: A list of pairs (tuples) containing:
                - A list of equivalent AST expressions
                - The value of the first expression node
                   (which should be the same for all nodes, unless threads are involved)
    r   )r-   dumpr   
setdefaultappendr`   r   )r   r5   r*   r=   r   s        r   r   r     sz    ( F" = =ex06677$U,,Q/66t<<<<   r!   )$r-   r   r   collectionsr   r   r   
contextlibr   typesr   typingr   r	   r
   r   r   r   r   r   pure_eval.my_getattr_staticr   pure_eval.utilsr   r   r   r   r   r   r   r   r   r.   rf   r   r   rN   r!   r   <module>r      s   



   4 4 4 4 4 4 4 4 4 4             H H H H H H H H H H H H H H H H H H H H 6 6 6 6 6 6	 	 	 	 	 	 	 	 	 	 	 	 	 	 	 	 	 	 	 	l
 l
 l
 l
 l
 l
 l
 l
^!CH !S !T ! ! ! !H!8E#(C-,@#A !d5QUVYV^Q_adQdKeFf ! ! ! ! ! !r!   