3
d                 @   s~   d Z ddlmZmZ ddlZddlmZ ddlmZ ej	e
ZdZdZd	ZG d
d deZG dd deZe ZdddZdS )z" An attempt at type-safe casting.
    )getfullargspecgetmroN)FunctionType   )	HasTraitszZThe '%s' class signature for the '%s' method is different from that of the '%s' interface.zHThe '%s' class does not implement the '%s' method of the '%s' interface.zHThe '%s' class does not implement the %s trait(s) of the '%s' interface.c               @   s   e Zd ZdZdS )InterfaceErrorzM The exception raised if a class does not really implement an interface.
    N)__name__
__module____qualname____doc__ r   r   :/tmp/pip-build-7vycvbft/traits/traits/interface_checker.pyr   (   s   r   c               @   sP   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S )InterfaceCheckerz6 Checks that interfaces are actually implemented.
    c             C   sx   yt | W n tk
r&   |g}Y nX t|trTx@|D ]}| j|||s8dS q8W n x|D ]}| j|||sZdS qZW dS )z Checks that the class implements the specified interfaces.

            'interfaces' can be a single interface or a list of interfaces.
        FT)iter	TypeError
issubclassr   _check_has_traits_class_check_non_has_traits_class)selfcls
interfaces
error_mode	interfacer   r   r   check_implements3   s    





z!InterfaceChecker.check_implementsc             C   s   | j |||o| j|||S )zB Checks that a 'HasTraits' class implements an interface.
        )_check_traits_check_methods)r   r   r   r   r   r   r   r   R   s    
z(InterfaceChecker._check_has_traits_classc             C   s   | j |||S )zF Checks that a non-'HasTraits' class implements an interface.
        )r   )r   r   r   r   r   r   r   r   Y   s    z,InterfaceChecker._check_non_has_traits_classc       	      C   s   | j |}| j |}xx|D ]p}||krH| jt| j||| j|f |S t|| }t|| }||kr| jt| j||| j|f |S qW dS )zE Checks that a class implements the methods on an interface.
        T)_get_public_methods_handle_errorMISSING_METHOD_class_namer   BAD_SIGNATURE)	r   r   r   r   Zcls_methodsZinterface_methodsnameZcls_argspecZinterface_argspecr   r   r   r   ^   s(    



zInterfaceChecker._check_methodsc             C   s\   t |j jt |j }t|dkrX| jt| j|tt|dd | j|f |S dS )zD Checks that a class implements the traits on an interface.
        r   r   T)	setZclass_traits
differencelenr   MISSING_TRAITr   reprlist)r   r   r   r   missingr   r   r   r      s    zInterfaceChecker._check_traitsc             C   sd   i }xZt |D ]N}|tkrP x>|jj D ]0\}}|jd r(t|tkr(||kr(|||< q(W qW |S )z Returns all public methods on a class.

            Returns a dictionary containing all public methods keyed by name.
        _)r   r   __dict__items
startswithtyper   )r   r   Zpublic_methodscr!   valuer   r   r   r      s    z$InterfaceChecker._get_public_methodsc             C   s   |j S )N)r   )r   r   r   r   r   r      s    zInterfaceChecker._class_namec             C   s&   |dkrt ||dkr"tj| dS )Nr   F)r   loggerwarning)r   msgr   r   r   r   r      s
    
zInterfaceChecker._handle_errorN)r   r	   r
   r   r   r   r   r   r   r   r   r   r   r   r   r   r   /   s   #r   c             C   s   t j| ||S )z Checks that the class implements the specified interfaces.

        'interfaces' can be a single interface or a list of interfaces.
    )checkerr   )r   r   r   r   r   r   r      s    r   )r   )r   inspectr   r   loggingtypesr   Z
has_traitsr   	getLoggerr   r1   r    r   r&   	Exceptionr   r   r4   r   r   r   r   r   <module>   s   
 	