o
    ¯b!  ã                   @   s<  d Z ddlZddlZddlZddlZddl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 ddlmZ ddlmZ G d	d
„ d
eƒZG dd„ dƒZG dd„ dƒZdd„ ZzejZW n eyk   d dd„ZY nw dd„ Zdejfdd„Ze	ded�Z	d dee deej dee fdd„Z e Z!dd„ Z"ddgZ#dS )!zL
Plugin system for Twisted.

@author: Jp Calderone
@author: Glyph Lefkowitz
é    N)ÚIterableÚOptionalÚTypeÚTypeVar)Ú	InterfaceÚ
providedBy)Úlog)ÚgetAdapterFactory)Ú	getModule)ÚnamedAnyc                   @   s   e Zd ZdZdS )ÚIPluginzý
    Interface that must be implemented by all plugins.

    Only objects which implement this interface will be considered for return
    by C{getPlugins}.  To be useful, plugins should also implement some other
    application-specific interface.
    N)Ú__name__Ú
__module__Ú__qualname__Ú__doc__© r   r   ú0/usr/lib/python3/dist-packages/twisted/plugin.pyr      s    r   c                   @   s8   e Zd Zdd„ Zdefdd„Zdd„ Zdd	d
„ZeZdS )ÚCachedPluginc                 C   s*   || _ || _|| _|| _| j j | ¡ d S ©N)ÚdropinÚnameÚdescriptionÚprovidedÚpluginsÚappend)Úselfr   r   r   r   r   r   r   Ú__init__'   s
   zCachedPlugin.__init__Úreturnc                 C   s&   d  | j| jjd dd„ | jD ƒ¡¡S )Nz(<CachedPlugin {!r}/{!r} (provides {!r})>z, c                 S   s   g | ]}|j ‘qS r   )r   )Ú.0Úir   r   r   Ú
<listcomp>2   s    z)CachedPlugin.__repr__.<locals>.<listcomp>)Úformatr   r   Ú
moduleNameÚjoinr   ©r   r   r   r   Ú__repr__.   s
   ýzCachedPlugin.__repr__c                 C   s   t | jjd | j ƒS )NÚ.)r   r   r"   r   r$   r   r   r   Úload5   s   zCachedPlugin.loadNc                 C   sH   | j D ]}| |¡r|  ¡   S t||d ƒd ur!||  ¡ |ƒ  S q|S r   )r   ÚisOrExtendsr'   r	   )r   Ú	interfaceÚregistryÚdefaultÚprovidedInterfacer   r   r   Ú__conform__8   s   

ÿzCachedPlugin.__conform__)NN)	r   r   r   r   Ústrr%   r'   r-   ÚgetComponentr   r   r   r   r   &   s    
	r   c                   @   s   e Zd ZdZdd„ ZdS )ÚCachedDropinaþ  
    A collection of L{CachedPlugin} instances from a particular module in a
    plugin package.

    @type moduleName: C{str}
    @ivar moduleName: The fully qualified name of the plugin module this
        represents.

    @type description: C{str} or L{None}
    @ivar description: A brief explanation of this collection of plugins
        (probably the plugin module's docstring).

    @type plugins: C{list}
    @ivar plugins: The L{CachedPlugin} instances which were loaded from this
        dropin.
    c                 C   s   || _ || _g | _d S r   )r"   r   r   )r   r"   r   r   r   r   r   V   s   
zCachedDropin.__init__N)r   r   r   r   r   r   r   r   r   r0   D   s    r0   c                 C   sP   t | j| jƒ}| j ¡ D ]\}}t|d ƒ}|d ur%t|||jtt|ƒƒƒ q|S r   )	r0   r   r   Ú__dict__Úitemsr   r   Úlistr   )Úproviderr   ÚkÚvÚpluginr   r   r   Ú_generateCacheEntry\   s   
€r8   c                 C   s   i }| D ]}|||< q|S r   r   )ÚkeysÚvalueÚdr5   r   r   r   Úfromkeysj   s   
r<   c                 C   sà  i }t | jƒ}i }| ¡ D ]}|j ¡ }||vrg ||< || }| |¡ q| ¡ D ]Ã\}}| d¡}z | ¡ }	| 	d¡�}
t
 |
¡}W d  ƒ n1 sMw   Y  W n ty`   i }d}	Y nw d}i }|D ]7}|j d¡d }d||< ||vs€|j ¡ |	kržd}z| ¡ }W n ty•   t ¡  Y qgw t|ƒ}|||< qgt| ¡ ƒD ]}||vr°||= d}q¥|rèz
| t
 |¡¡ W n* tyÙ } ztjd	|j|jd
� W Y d}~nd}~w tyç   t dd¡ Y nw | |¡ q*|S )a;  
    Compute all the possible loadable plugins, while loading as few as
    possible and hitting the filesystem as little as possible.

    @param module: a Python module object.  This represents a package to search
    for plugins.

    @return: a dictionary mapping module names to L{CachedDropin} instances.
    zdropin.cacheÚrNr   Fr&   éÿÿÿÿTz@Unable to write to plugin cache %(path)s: error number %(errno)d)r!   ÚpathÚerrnoz)Unexpected error while writing cache file)r
   r   ÚiterModulesÚfilePathÚparentr   r2   ÚchildÚgetModificationTimeÚopenÚpickler'   ÚBaseExceptionr   Úsplitr   Úerrr8   r3   r9   Ú
setContentÚdumpsÚOSErrorÚmsgr?   r@   Úupdate)ÚmoduleÚallCachesCombinedÚmodÚbucketsÚplugmodÚfppÚbucketÚpseudoPackagePathÚ
dropinPathÚ
lastCachedÚfÚdropinDotCacheÚ
needsWriteÚexistingKeysÚpluginModuleÚ	pluginKeyr4   ÚentryÚer   r   r   ÚgetCacheq   sr   



ÿ€þþ€€ú€ÿrb   r   c                  C   s   dd l m}  | S )Nr   )Útwisted.pluginsr   ©Úpackager   r   r   Ú_pluginsPackage½   s   rf   Ú_TInterface)Úboundr)   re   c              
   c   sr   � |du rt ƒ }t|ƒ}| ¡ D ]&\}}|jD ]}z| |dƒ}W n ty-   t ¡  Y qw |dur5|V  qqdS )ac  
    Retrieve all plugins implementing the given interface beneath the given module.

    @param interface: An interface class.  Only plugins which implement this
    interface will be returned.

    @param package: A package beneath which plugins are installed.  For
    most uses, the default value is correct.

    @return: An iterator of plugins.
    N)rf   rb   r2   r   rH   r   rJ   )r)   re   Ú
allDropinsÚkeyr   r7   Úadaptedr   r   r   Ú
getPluginsÆ   s    €
ÿ€ùÿrl   c                    s   |   d¡‰ ‡ fdd„tjD ƒS )a¨  
    Return a list of additional directories which should be searched for
    modules to be included as part of the named plugin package.

    @type name: C{str}
    @param name: The fully-qualified Python name of a plugin package, eg
        C{'twisted.plugins'}.

    @rtype: C{list} of C{str}
    @return: The absolute paths to other directories which may contain plugin
        modules for the named plugin package.
    r&   c                    sJ   g | ]!}t j t jj|gˆ d g ¢R Ž ¡st j t jj|gˆ ¢R Ž ¡‘qS )z__init__.py)Úosr?   Úexistsr#   Úabspath)r   Úxrd   r   r   r    ý   s     ýÿz&pluginPackagePaths.<locals>.<listcomp>)rI   Úsysr?   )r   r   rd   r   ÚpluginPackagePathsæ   s   


þrr   r   )$r   rm   rG   rq   ÚtypesÚtypingr   r   r   r   Úzope.interfacer   r   Útwisted.pythonr   Útwisted.python.componentsr	   Útwisted.python.modulesr
   Útwisted.python.reflectr   r   r   r0   r8   Údictr<   ÚAttributeErrorrb   Ú
ModuleTyperf   rg   rl   Ú
getPlugInsrr   Ú__all__r   r   r   r   Ú<module>   sD   


þ	Lÿÿÿ
þ