File indexing completed on 2024-05-26 06:02:46

0001 <?php
0002 /**
0003  * Zend Framework
0004  *
0005  * LICENSE
0006  *
0007  * This source file is subject to the new BSD license that is bundled
0008  * with this package in the file LICENSE.txt.
0009  * It is also available through the world-wide-web at this URL:
0010  * http://framework.zend.com/license/new-bsd
0011  * If you did not receive a copy of the license and are unable to
0012  * obtain it through the world-wide-web, please send an email
0013  * to license@zend.com so we can send you a copy immediately.
0014  *
0015  * @category   Zend
0016  * @package    Zend_Cache
0017  * @subpackage Zend_Cache_Backend
0018  * @copyright  Copyright (c) 2005-2015 Zend Technologies USA Inc. (http://www.zend.com)
0019  * @license    http://framework.zend.com/license/new-bsd     New BSD License
0020  * @version    $Id$
0021  */
0022 
0023 
0024 /**
0025  * @see Zend_Cache_Backend_Interface
0026  */
0027 // require_once 'Zend/Cache/Backend/ExtendedInterface.php';
0028 
0029 /**
0030  * @see Zend_Cache_Backend
0031  */
0032 // require_once 'Zend/Cache/Backend.php';
0033 
0034 
0035 /**
0036  * @package    Zend_Cache
0037  * @subpackage Zend_Cache_Backend
0038  * @copyright  Copyright (c) 2005-2015 Zend Technologies USA Inc. (http://www.zend.com)
0039  * @license    http://framework.zend.com/license/new-bsd     New BSD License
0040  */
0041 class Zend_Cache_Backend_WinCache extends Zend_Cache_Backend implements Zend_Cache_Backend_ExtendedInterface
0042 {
0043     /**
0044      * Log message
0045      */
0046     const TAGS_UNSUPPORTED_BY_CLEAN_OF_WINCACHE_BACKEND = 'Zend_Cache_Backend_WinCache::clean() : tags are unsupported by the WinCache backend';
0047     const TAGS_UNSUPPORTED_BY_SAVE_OF_WINCACHE_BACKEND =  'Zend_Cache_Backend_WinCache::save() : tags are unsupported by the WinCache backend';
0048 
0049     /**
0050      * Constructor
0051      *
0052      * @param  array $options associative array of options
0053      * @throws Zend_Cache_Exception
0054      * @return void
0055      */
0056     public function __construct(array $options = array())
0057     {
0058         if (!extension_loaded('wincache')) {
0059             Zend_Cache::throwException('The wincache extension must be loaded for using this backend !');
0060         }
0061         parent::__construct($options);
0062     }
0063 
0064     /**
0065      * Test if a cache is available for the given id and (if yes) return it (false else)
0066      *
0067      * WARNING $doNotTestCacheValidity=true is unsupported by the WinCache backend
0068      *
0069      * @param  string  $id                     cache id
0070      * @param  boolean $doNotTestCacheValidity if set to true, the cache validity won't be tested
0071      * @return string cached datas (or false)
0072      */
0073     public function load($id, $doNotTestCacheValidity = false)
0074     {
0075         $tmp = wincache_ucache_get($id);
0076         if (is_array($tmp)) {
0077             return $tmp[0];
0078         }
0079         return false;
0080     }
0081 
0082     /**
0083      * Test if a cache is available or not (for the given id)
0084      *
0085      * @param  string $id cache id
0086      * @return mixed false (a cache is not available) or "last modified" timestamp (int) of the available cache record
0087      */
0088     public function test($id)
0089     {
0090         $tmp = wincache_ucache_get($id);
0091         if (is_array($tmp)) {
0092             return $tmp[1];
0093         }
0094         return false;
0095     }
0096 
0097     /**
0098      * Save some string datas into a cache record
0099      *
0100      * Note : $data is always "string" (serialization is done by the
0101      * core not by the backend)
0102      *
0103      * @param string $data datas to cache
0104      * @param string $id cache id
0105      * @param array $tags array of strings, the cache record will be tagged by each string entry
0106      * @param int $specificLifetime if != false, set a specific lifetime for this cache record (null => infinite lifetime)
0107      * @return boolean true if no problem
0108      */
0109     public function save($data, $id, $tags = array(), $specificLifetime = false)
0110     {
0111         $lifetime = $this->getLifetime($specificLifetime);
0112         $result = wincache_ucache_set($id, array($data, time(), $lifetime), $lifetime);
0113         if (count($tags) > 0) {
0114             $this->_log(self::TAGS_UNSUPPORTED_BY_SAVE_OF_WINCACHE_BACKEND);
0115         }
0116         return $result;
0117     }
0118 
0119     /**
0120      * Remove a cache record
0121      *
0122      * @param  string $id cache id
0123      * @return boolean true if no problem
0124      */
0125     public function remove($id)
0126     {
0127         return wincache_ucache_delete($id);
0128     }
0129 
0130     /**
0131      * Clean some cache records
0132      *
0133      * Available modes are :
0134      * 'all' (default)  => remove all cache entries ($tags is not used)
0135      * 'old'            => unsupported
0136      * 'matchingTag'    => unsupported
0137      * 'notMatchingTag' => unsupported
0138      * 'matchingAnyTag' => unsupported
0139      *
0140      * @param  string $mode clean mode
0141      * @param  array  $tags array of tags
0142      * @throws Zend_Cache_Exception
0143      * @return boolean true if no problem
0144      */
0145     public function clean($mode = Zend_Cache::CLEANING_MODE_ALL, $tags = array())
0146     {
0147         switch ($mode) {
0148             case Zend_Cache::CLEANING_MODE_ALL:
0149                 return wincache_ucache_clear();
0150                 break;
0151             case Zend_Cache::CLEANING_MODE_OLD:
0152                 $this->_log("Zend_Cache_Backend_WinCache::clean() : CLEANING_MODE_OLD is unsupported by the WinCache backend");
0153                 break;
0154             case Zend_Cache::CLEANING_MODE_MATCHING_TAG:
0155             case Zend_Cache::CLEANING_MODE_NOT_MATCHING_TAG:
0156             case Zend_Cache::CLEANING_MODE_MATCHING_ANY_TAG:
0157                 $this->_log(self::TAGS_UNSUPPORTED_BY_CLEAN_OF_WINCACHE_BACKEND);
0158                 break;
0159             default:
0160                 Zend_Cache::throwException('Invalid mode for clean() method');
0161                 break;
0162         }
0163     }
0164 
0165     /**
0166      * Return true if the automatic cleaning is available for the backend
0167      *
0168      * DEPRECATED : use getCapabilities() instead
0169      *
0170      * @deprecated
0171      * @return boolean
0172      */
0173     public function isAutomaticCleaningAvailable()
0174     {
0175         return false;
0176     }
0177 
0178     /**
0179      * Return the filling percentage of the backend storage
0180      *
0181      * @throws Zend_Cache_Exception
0182      * @return int integer between 0 and 100
0183      */
0184     public function getFillingPercentage()
0185     {
0186         $mem = wincache_ucache_meminfo();
0187         $memSize = $mem['memory_total'];
0188         $memUsed = $memSize - $mem['memory_free'];
0189         if ($memSize == 0) {
0190             Zend_Cache::throwException('can\'t get WinCache memory size');
0191         }
0192         if ($memUsed > $memSize) {
0193             return 100;
0194         }
0195         return ((int) (100. * ($memUsed / $memSize)));
0196     }
0197 
0198     /**
0199      * Return an array of stored tags
0200      *
0201      * @return array array of stored tags (string)
0202      */
0203     public function getTags()
0204     {
0205         $this->_log(self::TAGS_UNSUPPORTED_BY_SAVE_OF_WINCACHE_BACKEND);
0206         return array();
0207     }
0208 
0209     /**
0210      * Return an array of stored cache ids which match given tags
0211      *
0212      * In case of multiple tags, a logical AND is made between tags
0213      *
0214      * @param array $tags array of tags
0215      * @return array array of matching cache ids (string)
0216      */
0217     public function getIdsMatchingTags($tags = array())
0218     {
0219         $this->_log(self::TAGS_UNSUPPORTED_BY_SAVE_OF_WINCACHE_BACKEND);
0220         return array();
0221     }
0222 
0223     /**
0224      * Return an array of stored cache ids which don't match given tags
0225      *
0226      * In case of multiple tags, a logical OR is made between tags
0227      *
0228      * @param array $tags array of tags
0229      * @return array array of not matching cache ids (string)
0230      */
0231     public function getIdsNotMatchingTags($tags = array())
0232     {
0233         $this->_log(self::TAGS_UNSUPPORTED_BY_SAVE_OF_WINCACHE_BACKEND);
0234         return array();
0235     }
0236 
0237     /**
0238      * Return an array of stored cache ids which match any given tags
0239      *
0240      * In case of multiple tags, a logical AND is made between tags
0241      *
0242      * @param array $tags array of tags
0243      * @return array array of any matching cache ids (string)
0244      */
0245     public function getIdsMatchingAnyTags($tags = array())
0246     {
0247         $this->_log(self::TAGS_UNSUPPORTED_BY_SAVE_OF_WINCACHE_BACKEND);
0248         return array();
0249     }
0250 
0251     /**
0252      * Return an array of stored cache ids
0253      *
0254      * @return array array of stored cache ids (string)
0255      */
0256     public function getIds()
0257     {
0258         $res = array();
0259         $array = wincache_ucache_info();
0260         $records = $array['ucache_entries'];
0261         foreach ($records as $record) {
0262             $res[] = $record['key_name'];
0263         }
0264         return $res;
0265     }
0266 
0267     /**
0268      * Return an array of metadatas for the given cache id
0269      *
0270      * The array must include these keys :
0271      * - expire : the expire timestamp
0272      * - tags : a string array of tags
0273      * - mtime : timestamp of last modification time
0274      *
0275      * @param string $id cache id
0276      * @return array array of metadatas (false if the cache id is not found)
0277      */
0278     public function getMetadatas($id)
0279     {
0280         $tmp = wincache_ucache_get($id);
0281         if (is_array($tmp)) {
0282             $data = $tmp[0];
0283             $mtime = $tmp[1];
0284             if (!isset($tmp[2])) {
0285                 return false;
0286             }
0287             $lifetime = $tmp[2];
0288             return array(
0289                 'expire' => $mtime + $lifetime,
0290                 'tags' => array(),
0291                 'mtime' => $mtime
0292             );
0293         }
0294         return false;
0295     }
0296 
0297     /**
0298      * Give (if possible) an extra lifetime to the given cache id
0299      *
0300      * @param string $id cache id
0301      * @param int $extraLifetime
0302      * @return boolean true if ok
0303      */
0304     public function touch($id, $extraLifetime)
0305     {
0306         $tmp = wincache_ucache_get($id);
0307         if (is_array($tmp)) {
0308             $data = $tmp[0];
0309             $mtime = $tmp[1];
0310             if (!isset($tmp[2])) {
0311                 return false;
0312             }
0313             $lifetime = $tmp[2];
0314             $newLifetime = $lifetime - (time() - $mtime) + $extraLifetime;
0315             if ($newLifetime <=0) {
0316                 return false;
0317             }
0318             return wincache_ucache_set($id, array($data, time(), $newLifetime), $newLifetime);
0319         }
0320         return false;
0321     }
0322 
0323     /**
0324      * Return an associative array of capabilities (booleans) of the backend
0325      *
0326      * The array must include these keys :
0327      * - automatic_cleaning (is automating cleaning necessary)
0328      * - tags (are tags supported)
0329      * - expired_read (is it possible to read expired cache records
0330      *                 (for doNotTestCacheValidity option for example))
0331      * - priority does the backend deal with priority when saving
0332      * - infinite_lifetime (is infinite lifetime can work with this backend)
0333      * - get_list (is it possible to get the list of cache ids and the complete list of tags)
0334      *
0335      * @return array associative of with capabilities
0336      */
0337     public function getCapabilities()
0338     {
0339         return array(
0340             'automatic_cleaning' => false,
0341             'tags' => false,
0342             'expired_read' => false,
0343             'priority' => false,
0344             'infinite_lifetime' => false,
0345             'get_list' => true
0346         );
0347     }
0348 
0349 }