File indexing completed on 2025-01-19 05:20:57

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_Frontend
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_Core
0026  */
0027 // require_once 'Zend/Cache/Core.php';
0028 
0029 
0030 /**
0031  * @package    Zend_Cache
0032  * @subpackage Zend_Cache_Frontend
0033  * @copyright  Copyright (c) 2005-2015 Zend Technologies USA Inc. (http://www.zend.com)
0034  * @license    http://framework.zend.com/license/new-bsd     New BSD License
0035  */
0036 class Zend_Cache_Frontend_File extends Zend_Cache_Core
0037 {
0038 
0039     /**
0040      * Consts for master_files_mode
0041      */
0042     const MODE_AND = 'AND';
0043     const MODE_OR  = 'OR';
0044 
0045     /**
0046      * Available options
0047      *
0048      * ====> (string) master_file :
0049      * - a complete path of the master file
0050      * - deprecated (see master_files)
0051      *
0052      * ====> (array) master_files :
0053      * - an array of complete path of master files
0054      * - this option has to be set !
0055      *
0056      * ====> (string) master_files_mode :
0057      * - Zend_Cache_Frontend_File::MODE_AND or Zend_Cache_Frontend_File::MODE_OR
0058      * - if MODE_AND, then all master files have to be touched to get a cache invalidation
0059      * - if MODE_OR (default), then a single touched master file is enough to get a cache invalidation
0060      *
0061      * ====> (boolean) ignore_missing_master_files
0062      * - if set to true, missing master files are ignored silently
0063      * - if set to false (default), an exception is thrown if there is a missing master file
0064      * @var array available options
0065      */
0066     protected $_specificOptions = array(
0067         'master_file' => null,
0068         'master_files' => null,
0069         'master_files_mode' => 'OR',
0070         'ignore_missing_master_files' => false
0071     );
0072 
0073     /**
0074      * Master file mtimes
0075      *
0076      * Array of int
0077      *
0078      * @var array
0079      */
0080     private $_masterFile_mtimes = null;
0081 
0082     /**
0083      * Constructor
0084      *
0085      * @param  array $options Associative array of options
0086      * @throws Zend_Cache_Exception
0087      * @return void
0088      */
0089     public function __construct(array $options = array())
0090     {
0091         foreach ($options as $name => $value) {
0092             $this->setOption($name, $value);
0093         }
0094         if (!isset($this->_specificOptions['master_files'])) {
0095             Zend_Cache::throwException('master_files option must be set');
0096         }
0097     }
0098 
0099     /**
0100      * Change the master_files option
0101      *
0102      * @param array $masterFiles the complete paths and name of the master files
0103      */
0104     public function setMasterFiles(array $masterFiles)
0105     {
0106         $this->_specificOptions['master_file']  = null; // to keep a compatibility
0107         $this->_specificOptions['master_files'] = null;
0108         $this->_masterFile_mtimes = array();
0109 
0110         clearstatcache();
0111         $i = 0;
0112         foreach ($masterFiles as $masterFile) {
0113             if (file_exists($masterFile)) {
0114                 $mtime = filemtime($masterFile);
0115             } else {
0116                 $mtime = false;
0117             }
0118 
0119             if (!$this->_specificOptions['ignore_missing_master_files'] && !$mtime) {
0120                 Zend_Cache::throwException('Unable to read master_file : ' . $masterFile);
0121             }
0122 
0123             $this->_masterFile_mtimes[$i] = $mtime;
0124             $this->_specificOptions['master_files'][$i] = $masterFile;
0125             if ($i === 0) { // to keep a compatibility
0126                 $this->_specificOptions['master_file'] = $masterFile;
0127             }
0128 
0129             $i++;
0130         }
0131     }
0132 
0133     /**
0134      * Change the master_file option
0135      *
0136      * To keep the compatibility
0137      *
0138      * @deprecated
0139      * @param string $masterFile the complete path and name of the master file
0140      */
0141     public function setMasterFile($masterFile)
0142     {
0143           $this->setMasterFiles(array($masterFile));
0144     }
0145 
0146     /**
0147      * Public frontend to set an option
0148      *
0149      * Just a wrapper to get a specific behaviour for master_file
0150      *
0151      * @param  string $name  Name of the option
0152      * @param  mixed  $value Value of the option
0153      * @throws Zend_Cache_Exception
0154      * @return void
0155      */
0156     public function setOption($name, $value)
0157     {
0158         if ($name == 'master_file') {
0159             $this->setMasterFile($value);
0160         } else if ($name == 'master_files') {
0161             $this->setMasterFiles($value);
0162         } else {
0163             parent::setOption($name, $value);
0164         }
0165     }
0166 
0167     /**
0168      * Test if a cache is available for the given id and (if yes) return it (false else)
0169      *
0170      * @param  string  $id                     Cache id
0171      * @param  boolean $doNotTestCacheValidity If set to true, the cache validity won't be tested
0172      * @param  boolean $doNotUnserialize       Do not serialize (even if automatic_serialization is true) => for internal use
0173      * @return mixed|false Cached datas
0174      */
0175     public function load($id, $doNotTestCacheValidity = false, $doNotUnserialize = false)
0176     {
0177         if (!$doNotTestCacheValidity) {
0178             if ($this->test($id)) {
0179                 return parent::load($id, true, $doNotUnserialize);
0180             }
0181             return false;
0182         }
0183         return parent::load($id, true, $doNotUnserialize);
0184     }
0185 
0186     /**
0187      * Test if a cache is available for the given id
0188      *
0189      * @param  string $id Cache id
0190      * @return int|false Last modified time of cache entry if it is available, false otherwise
0191      */
0192     public function test($id)
0193     {
0194         $lastModified = parent::test($id);
0195         if ($lastModified) {
0196             if ($this->_specificOptions['master_files_mode'] == self::MODE_AND) {
0197                 // MODE_AND
0198                 foreach($this->_masterFile_mtimes as $masterFileMTime) {
0199                     if ($masterFileMTime) {
0200                         if ($lastModified > $masterFileMTime) {
0201                             return $lastModified;
0202                         }
0203                     }
0204                 }
0205             } else {
0206                 // MODE_OR
0207                 $res = true;
0208                 foreach($this->_masterFile_mtimes as $masterFileMTime) {
0209                     if ($masterFileMTime) {
0210                         if ($lastModified <= $masterFileMTime) {
0211                             return false;
0212                         }
0213                     }
0214                 }
0215                 return $lastModified;
0216             }
0217         }
0218         return false;
0219     }
0220 
0221 }
0222