U
    d                      @  sZ  d Z ddlmZ ddl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 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 ejrd
dlmZ d
dlmZ eeee eedef  f Zd0dddddddZdddddddZdddd d!d"Zdd#ddd$d%d&Zddddd$d'd(Zd)ddd*d+d,Zdd)ddd-d.d/ZdS )1zhRoutines to handle adaption of legacy call signatures,
generation of deprecation notes and docstrings.

    )annotationsN)Any)Callable)List)Optional)Tuple)Type   )_ET)_ListenerFnType   )util)FullArgSpec)_ClsLevelDispatch)_HasEventsDispatch.strz	List[str]zOptional[Callable[..., Any]]z2Callable[[Callable[..., Any]], Callable[..., Any]])sinceargnames	converterreturnc                   s   ddd fdd}|S )a_  legacy sig decorator


    :param since: string version for deprecation warning
    :param argnames: list of strings, which is *all* arguments that the legacy
     version accepted, including arguments that are still there
    :param converter: lambda that will accept tuple of this full arg signature
     and return tuple of new arg signature.

    zCallable[..., Any])fnr   c                   s&   t | dsg | _| j f | S )N_legacy_signatures)hasattrr   append)r   r   r   r    ;/tmp/pip-unpacked-wheel-wbr0uges/sqlalchemy/event/legacy.pyleg3   s    
z_legacy_signature.<locals>.legr   )r   r   r   r   r   r   r   _legacy_signature#   s    r   z_ClsLevelDispatch[_ET]r   r   )dispatch_collectionr   argspecr   c                   s   j D ]\  d dkr.d dd  ndt t|jkrt|jkrdjdjrjdnd	f }d
jj|f d k	rrt	ddddfdd}n dddd fdd}|  S qS )Nz**kwTr   Fzdef %s(%s%s), , **kw zThe argument signature for the "%s.%s" event listener has changed as of version %s, and conversion for the old argument signature will be removed in a future release.  The new signature is "%s"r   )argskwr   c                    s&   t jd  d k	st |   S )Nversion)r   warn_deprecatedAssertionError)r%   r&   )convr   r   warning_txtr   r   wrap_lega   s    z%_wrap_fn_for_legacy.<locals>.wrap_legc                    sJ   t jd ttj|   fddD }r>||S | S d S )Nr'   c                   s   g | ]} | qS r   r   ).0nameZargdictr   r   
<listcomp>k   s     z9_wrap_fn_for_legacy.<locals>.wrap_leg.<locals>.<listcomp>)r   r)   dictzip	arg_names)r%   r&   Zargs_from_dict)r   r   r   has_kwr   r,   r0   r   r-   h   s    
)
legacy_signatureslenr%   boolvarkwr/   joinr4   clsnamer*   )r   r   r    Zformatted_defr-   r   )r   r+   r   r   r5   r   r,   r   _wrap_fn_for_legacy<   s6    

 	
r<   )textindentr   c                   s   d  fdd| dD S )N
c                 3  s   | ]} | V  qd S Nr   )r.   liner>   r   r   	<genexpr>w   s     z_indent.<locals>.<genexpr>)r:   split)r=   r>   r   rB   r   _indentv   s    rE   r   )r   sample_targetr   r   c                 C  s   t ddd | jdd D d}| jr@tdd | jD }nd }d}||rVd	| nd
|j| jrfdnd
d| j||d; }|S )Nr?   c                 s  s   | ]}d d|i V  qdS )z%(arg)s = kw['%(arg)s']argNr   )r.   rG   r   r   r   rC      s   z+_standard_listen_example.<locals>.<genexpr>r   r   z    c                 s  s   | ]\}}}|V  qd S r@   r   )r.   r   r%   r+   r   r   r   rC      s   zfrom sqlalchemy import event


@event.listens_for(%(sample_target)s, '%(event_name)s')
def receive_%(event_name)s(%(named_event_arguments)s%(has_kw_arguments)s):
    "listen for the '%(event_name)s' event"

    # ... (event handling logic) ...
z (arguments as of %s)r$   r#   r"   )current_since
event_namehas_kw_argumentsnamed_event_argumentsexample_kw_argrF   )rE   r:   r4   r6   max__name__r5   )r   rF   r   rL   rH   r=   r   r   r   _standard_listen_examplez   s0    

	


rO   c              	   C  sD   d}| j D ]4\}}}|d||j| jr(dndd||d 7 }q
|S )Nr$   a&  
# DEPRECATED calling style (pre-%(since)s, will be removed in a future release)
@event.listens_for(%(sample_target)s, '%(event_name)s')
def receive_%(event_name)s(%(named_event_arguments)s%(has_kw_arguments)s):
    "listen for the '%(event_name)s' event"

    # ... (event handling logic) ...
z **kwr"   )r   rI   rJ   rK   rF   )r6   rN   r5   r:   )r   rF   r   r=   r   r%   r+   r   r   r   _legacy_listen_examples   s    rP   zType[_HasEventsDispatch[_ET]])parent_dispatch_clsr   r   c              	     sJ    j d \}}}d|j jd fdd jD  jr@dndd S )	Nr   a=  
.. versionchanged:: %(since)s
    The :meth:`.%(clsname)s.%(event_name)s` event now accepts the 
    arguments %(named_event_arguments)s%(has_kw_arguments)s.
    Support for listener functions which accept the previous 
    argument signature(s) listed above as "deprecated" will be 
    removed in a future release.r"   c                 3  s"   | ]}d j  j|d V  qdS )z6:paramref:`.%(clsname)s.%(event_name)s.%(param_name)s`)r;   rI   
param_nameN)rN   r/   )r.   rR   r   rQ   r   r   rC      s   z-_version_signature_changes.<locals>.<genexpr>r#   r$   )r   r;   rI   rK   rJ   )r6   rN   r/   r:   r4   r5   )rQ   r   r   r%   r+   r   rS   r   _version_signature_changes   s    	rT   )r   rQ   r   r   c                 C  s`   d}t |dd}|tt| ||d }| jrP|tt| ||d7 }|t|| 7 }t|j|dS )Nz@.. container:: event_signatures

     Example argument forms::

Z_target_class_docobjz        r	   )	getattrrE   rO   r6   rP   rT   r   Zinject_docstring_text__doc__)r   rQ   r   headerrF   r=   r   r   r   _augment_fn_docs   s"    

 rY   )N)rW   
__future__r   typingr   r   r   r   r   r   registryr
   r   r$   r   Zutil.compatr   TYPE_CHECKINGattrr   baser   r   Z_LegacySignatureTyper   r<   rE   rO   rP   rT   rY   r   r   r   r   <module>   s0    :)