o
    rÃiý"  ã                   @  sˆ   d dl mZ d dlZd dlZd dlZd dlmZmZ d dlm	Z	 d dl
Zd dlmZmZmZmZ G dd„ dƒZG dd	„ d	eeeeƒZdS )
é    )ÚannotationsN)ÚCounterÚdefaultdict)Úfloor)ÚMovingWindowSupportÚSlidingWindowCounterSupportÚStorageÚTimestampedSlidingWindowc                   @  s   e Zd Zddd„ZdS )	ÚEntryÚexpiryÚfloatÚreturnÚNonec                 C  s   t   ¡ | _| j| | _d S ©N)ÚtimeÚatimer   )Úselfr   © r   úT/var/www/html/pca-backend/venv/lib/python3.10/site-packages/limits/storage/memory.pyÚ__init__   s   
zEntry.__init__N)r   r   r   r   )Ú__name__Ú
__module__Ú__qualname__r   r   r   r   r   r
      s    r
   c                      sì   e Zd ZdZdgZdCdD‡ fdd„ZdEdd„ZdFdd„ZdGdd„ZdGdd„Z	e
dHdd„ƒZdIdJd"d#„ZdIdKd$d%„ZdLd&d'„ZdMd(d)„ZdIdNd+d,„ZdOd-d.„ZdPd0d1„Z	dIdNd2d3„ZdQd8d9„ZdRd:d;„ZdSd<d=„ZdTd>d?„ZdUdAdB„Z‡  ZS )VÚMemoryStoragezÀ
    rate limit storage using :class:`collections.Counter`
    as an in memory storage for fixed and sliding window strategies,
    and a simple list to implement moving window strategy.

    ÚmemoryNFÚuriú
str | NoneÚwrap_exceptionsÚboolÚ_Ústrc                   sV   t ƒ | _ttjƒ| _i | _i | _t d| j	¡| _
| j
 ¡  tƒ j|fd|i|¤Ž d S )Nç{®Gáz„?r   )r   Ústorager   Ú	threadingÚRLockÚlocksÚexpirationsÚeventsÚTimerÚ_MemoryStorage__expire_eventsÚtimerÚstartÚsuperr   )r   r   r   r   ©Ú	__class__r   r   r   $   s   
zMemoryStorage.__init__r   údict[str, limits.typing.Any]c                 C  s   | j  ¡ }|d= |d= |S )Nr*   r%   )Ú__dict__Úcopy©r   Ústater   r   r   Ú__getstate__-   s   
zMemoryStorage.__getstate__r3   r   c                 C  s6   | j  |¡ ttjƒ| _t d| j¡| _| j 	¡  d S ©Nr!   )
r0   Úupdater   r#   r$   r%   r(   r)   r*   r+   r2   r   r   r   Ú__setstate__3   s   zMemoryStorage.__setstate__c              	   C  sò   t | j ¡ ƒD ]G}| j| 8 | j |g ¡ }r1tj|t ¡  dd„ d}| j| d |… | j|< | j |d ¡s?| j |d ¡ W d   ƒ n1 sIw   Y  qt | j	 ¡ ƒD ] }| j	| t ¡ krv| j
 |d ¡ | j	 |d ¡ | j |d ¡ qVd S )Nc                 S  ó   | j  S r   )r   )Úeventr   r   r   Ú<lambda>>   ó    z/MemoryStorage.__expire_events.<locals>.<lambda>©Úkey)Úlistr'   Úkeysr%   ÚgetÚbisectÚbisect_leftr   Úpopr&   r"   )r   r=   r'   Úoldestr   r   r   Ú__expire_events9   s&   ÿ€ù€€üzMemoryStorage.__expire_eventsc                 C  s,   | j  ¡ st d| j¡| _ | j  ¡  d S d S r5   )r*   Úis_aliver#   r(   r)   r+   ©r   r   r   r   Ú__schedule_expiryI   s   
þzMemoryStorage.__schedule_expiryú-type[Exception] | tuple[type[Exception], ...]c                 C  s   t S r   )Ú
ValueErrorrG   r   r   r   Úbase_exceptionsN   s   zMemoryStorage.base_exceptionsé   r=   r   r   ÚamountÚintc                 C  s|   |   |¡ |  ¡  | j| ! | j|  |7  < | j| |kr(t ¡ | | j|< W d  ƒ n1 s2w   Y  | j  |d¡S )zá
        increments the counter for a given rate limit key

        :param key: the key to increment
        :param expiry: amount in seconds for the key to expire in
        :param amount: the number to increment by
        Nr   )r@   Ú_MemoryStorage__schedule_expiryr%   r"   r   r&   )r   r=   r   rM   r   r   r   ÚincrT   s   
€ýzMemoryStorage.incrc                 C  sd   |   |¡ |  ¡  | j|  t| j| | dƒ| j|< W d  ƒ n1 s&w   Y  | j  |d¡S )zŸ
        decrements the counter for a given rate limit key

        :param key: the key to decrement
        :param amount: the number to decrement by
        r   N)r@   rO   r%   Úmaxr"   )r   r=   rM   r   r   r   Údecrd   s   
ÿzMemoryStorage.decrc                 C  sN   | j  |d¡t ¡ kr | j |d¡ | j  |d¡ | j |d¡ | j |d¡S )zB
        :param key: the key to get the counter value for
        r   N)r&   r@   r   r"   rC   r%   ©r   r=   r   r   r   r@   r   s
   zMemoryStorage.getc                 C  s<   | j  |d¡ | j |d¡ | j |d¡ | j |d¡ dS )z>
        :param key: the key to clear rate limits for
        N)r"   rC   r&   r'   r%   rS   r   r   r   Úclear~   s   zMemoryStorage.clearÚlimitc              	   C  sÊ   ||krdS |   ¡  | j| L | j |g ¡ t ¡ }z| j| ||  }W n ty1   d}Y nw |rD|j|| krD	 W d  ƒ dS t|ƒg| | j| dd…< 	 W d  ƒ dS 1 s^w   Y  dS )zÖ
        :param key: rate limit key to acquire an entry in
        :param limit: amount of entries allowed
        :param expiry: expiry of the entry
        :param amount: the number of entries to acquire
        FNr   T)rO   r%   r'   Ú
setdefaultr   Ú
IndexErrorr   r
   )r   r=   rU   r   rM   Ú	timestampÚentryr   r   r   Úacquire_entry‡   s"   ÿ÷$ôzMemoryStorage.acquire_entryc                 C  s   | j  |t ¡ ¡S )z;
        :param key: the key to get the expiry for
        )r&   r@   r   rS   r   r   r   Ú
get_expiry    s   zMemoryStorage.get_expiryútuple[float, int]c                 C  sN   t   ¡ }| j |g ¡ }r#tj|||  dd„ d}||d  j|fS |dfS )zí
        returns the starting point and the number of entries in the moving
        window

        :param key: rate limit key
        :param expiry: expiry of entry
        :return: (start of window, number of acquired entries)
        c                 S  r8   r   )r   )rY   r   r   r   r:   ³   r;   z1MemoryStorage.get_moving_window.<locals>.<lambda>r<   rL   r   )r   r'   r@   rA   rB   r   )r   r=   rU   r   rX   r'   rD   r   r   r   Úget_moving_window§   s   	ÿzMemoryStorage.get_moving_windowc                 C  s¦   ||krdS t   ¡ }|  |||¡\}}|  ||||¡\}}	}
}||	 | |
 }t|ƒ| |kr1dS | j|d| |d}
||	 | |
 }t|ƒ|krQ|  ||¡ dS dS )NFé   )rM   T)r   Úsliding_window_keysÚ_get_sliding_window_infor   rP   rR   )r   r=   rU   r   rM   ÚnowÚprevious_keyÚcurrent_keyÚprevious_countÚprevious_ttlÚcurrent_countr   Úweighted_countr   r   r   Úacquire_sliding_window_entry¸   s&   ûz*MemoryStorage.acquire_sliding_window_entryrb   rc   ra   útuple[int, float, int, float]c           	      C  sb   |   |¡}|   |¡}|dkrtdƒ}nd|| | d  | }d|| d  | | }||||fS )Nr   rL   )r@   r   )	r   rb   rc   r   ra   rd   rf   re   Úcurrent_ttlr   r   r   r`   Ù   s   


z&MemoryStorage._get_sliding_window_infoc                 C  s*   t   ¡ }|  |||¡\}}|  ||||¡S r   )r   r_   r`   ©r   r=   r   ra   rb   rc   r   r   r   Úget_sliding_windowé   s   z MemoryStorage.get_sliding_windowc                 C  s2   t   ¡ }|  |||¡\}}|  |¡ |  |¡ d S r   )r   r_   rT   rk   r   r   r   Úclear_sliding_windowð   s   
z"MemoryStorage.clear_sliding_windowc                 C  s   dS )z-
        check if storage is healthy
        Tr   rG   r   r   r   Úcheckö   s   zMemoryStorage.checkú
int | Nonec                 C  sB   t t| jƒt| jƒƒ}| j ¡  | j ¡  | j ¡  | j ¡  |S r   )rQ   Úlenr"   r'   rT   r&   r%   )r   Ú	num_itemsr   r   r   Úresetý   s   



zMemoryStorage.reset)NF)r   r   r   r   r   r    )r   r/   )r3   r/   r   r   )r   r   )r   rI   )rL   )r=   r    r   r   rM   rN   r   rN   )r=   r    rM   rN   r   rN   )r=   r    r   rN   )r=   r    r   r   )
r=   r    rU   rN   r   rN   rM   rN   r   r   )r=   r    r   r   )r=   r    rU   rN   r   rN   r   r\   )
rb   r    rc   r    r   rN   ra   r   r   ri   )r=   r    r   rN   r   ri   )r=   r    r   rN   r   r   )r   r   )r   ro   )r   r   r   Ú__doc__ÚSTORAGE_SCHEMEr   r4   r7   r)   rO   ÚpropertyrK   rP   rR   r@   rT   rZ   r[   r]   rh   r`   rl   rm   rn   rr   Ú__classcell__r   r   r-   r   r      s0    
	




	

û
!


r   )Ú
__future__r   rA   r#   r   Úcollectionsr   r   Úmathr   Úlimits.typingÚlimitsÚlimits.storage.baser   r   r   r	   r
   r   r   r   r   r   Ú<module>   s    
ÿ