
v^+                 @   s   d  Z  d d l Z d d l Z d d l Z d d l Z d d l 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 m Z Gd d   d e  Z d S)zFile-based cache backend    N)DEFAULT_TIMEOUT	BaseCache)locks)file_move_safec                   s   e  Z d  Z d Z e j Z   f d d   Z e d d d  Z	 d d d d  Z
 d	 d
   Z e d d d  Z e d d d  Z d d d  Z d d   Z d d d  Z d d   Z d d   Z d d d  Z d d   Z d d   Z d d    Z   S)!FileBasedCachez.djcachec                s3   t    j |  t j j |  |  _ |  j   d  S)N)super__init__ospathabspath_dir
_createdir)selfdirparams)	__class__ F/tmp/pip-build-8lau8j11/django/django/core/cache/backends/filebased.pyr      s    zFileBasedCache.__init__Nc             C   s0   |  j  | |  r d S|  j | | | |  d S)NFT)has_keyset)r   keyvaluetimeoutversionr   r   r   add   s    zFileBasedCache.addc             C   ss   |  j  | |  } yH t | d  2 } |  j |  sR t j t j | j     SWd  QRXWn t k
 rn Yn X| S)Nrb)	_key_to_fileopen_is_expiredpickleloadszlib
decompressreadFileNotFoundError)r   r   defaultr   fnamefr   r   r   get   s    'zFileBasedCache.getc             C   sT   |  j  |  } | j t j | |  j   | j t j t j | |  j    d  S)N)Zget_backend_timeoutwriter   dumpspickle_protocolr!   compress)r   filer   r   Zexpiryr   r   r   _write_content)   s    zFileBasedCache._write_contentc       
      C   s   |  j    |  j | |  } |  j   t j d |  j  \ } } d } zI t | d   }	 |  j |	 | |  Wd  QRXt | | d d d } Wd  | s t	 j
 |  Xd  S)Nr   FwbZallow_overwriteT)r   r   _culltempfilemkstempr   r   r.   r   r	   remove)
r   r   r   r   r   r&   fdtmp_pathZrenamedr'   r   r   r   r   .   s    


zFileBasedCache.setc             C   s   y t  |  j | |  d   } zl t j | t j  |  j |  rJ d St j t j	 | j
     } | j d  |  j | | |  d SWd  t j |  XWd  QRXWn t k
 r d SYn Xd  S)Nzr+bFr   T)r   r   r   lockLOCK_EXr   r   r    r!   r"   r#   seekr.   Zunlockr$   )r   r   r   r   r'   Zprevious_valuer   r   r   touch=   s    zFileBasedCache.touchc             C   s   |  j  |  j | |   d  S)N)_deleter   )r   r   r   r   r   r   deleteN   s    zFileBasedCache.deletec             C   sT   | j  |  j  s& t j j |  r* d  Sy t j |  Wn t k
 rO Yn Xd  S)N)
startswithr   r	   r
   existsr3   r$   )r   r&   r   r   r   r:   Q   s    &zFileBasedCache._deletec          	   C   sO   |  j  | |  } t j j |  rK t | d   } |  j |  SWd  QRXd S)Nr   F)r   r	   r
   r=   r   r   )r   r   r   r&   r'   r   r   r   r   Z   s
    zFileBasedCache.has_keyc             C   s   |  j    } t |  } | |  j k  r+ d S|  j d k rD |  j   St j | t | |  j   } x | D] } |  j |  qj Wd S)z
        Remove random cache entries if max_entries is reached at a ratio
        of num_entries / cull_frequency. A value of 0 for CULL_FREQUENCY means
        that the entire cache will be purged.
        Nr   )	_list_cache_fileslenZ_max_entriesZ_cull_frequencyclearrandomsampleintr:   )r   filelistZnum_entriesr&   r   r   r   r0   a   s    
	zFileBasedCache._cullc             C   s   t  j |  j d d d d  S)Ni  exist_okT)r	   makedirsr   )r   r   r   r   r   s   s    zFileBasedCache._createdirc             C   s_   |  j  | d | } |  j |  t j j |  j d j t j | j    j	   |  j
 g   S)z
        Convert a key into a cache file path. Basically this is the
        root cache path joined with the md5sum of the key and a suffix.
        r    )Zmake_keyZvalidate_keyr	   r
   joinr   hashlibmd5encode	hexdigestcache_suffix)r   r   r   r   r   r   r   v   s    zFileBasedCache._key_to_filec             C   s(   x! |  j    D] } |  j |  q Wd S)z-
        Remove all the cache files.
        N)r>   r:   )r   r&   r   r   r   r@      s    zFileBasedCache.clearc             C   sn   y t  j |  } Wn t k
 r- d } Yn X| d k	 rj | t j   k  rj | j   |  j | j  d Sd S)zL
        Take an open cache file `f` and delete it if it's expired.
        r   NTF)r   loadEOFErrortimecloser:   name)r   r'   expr   r   r   r      s    
zFileBasedCache._is_expiredc                s-     f d d   t  j   j d   j  D S)z
        Get a list of paths to all the cache files. These are all the files
        in the root cache dir that end on the cache_suffix.
        c                s(   g  |  ] } t  j j   j |   q Sr   )r	   r
   rH   r   ).0r&   )r   r   r   
<listcomp>   s   	z4FileBasedCache._list_cache_files.<locals>.<listcomp>z*%s)globglob1r   rM   )r   r   )r   r   r>      s    z FileBasedCache._list_cache_files)__name__
__module____qualname__rM   r   HIGHEST_PROTOCOLr+   r   r   r   r(   r.   r   r9   r;   r:   r   r0   r   r   r@   r   r>   r   r   )r   r   r      s"   	
	
r   )__doc__rV   rI   r	   r   rA   r1   rP   r!   Zdjango.core.cache.backends.baser   r   Zdjango.core.filesr   Zdjango.core.files.mover   r   r   r   r   r   <module>   s   