File indexing completed on 2025-03-02 05:29:45

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_Search_Lucene
0017  * @subpackage Storage
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 /** Zend_Search_Lucene_Storage_Directory */
0025 // require_once 'Zend/Search/Lucene/Storage/Directory.php';
0026 
0027 
0028 /**
0029  * FileSystem implementation of Directory abstraction.
0030  *
0031  * @category   Zend
0032  * @package    Zend_Search_Lucene
0033  * @subpackage Storage
0034  * @copyright  Copyright (c) 2005-2015 Zend Technologies USA Inc. (http://www.zend.com)
0035  * @license    http://framework.zend.com/license/new-bsd     New BSD License
0036  */
0037 class Zend_Search_Lucene_Storage_Directory_Filesystem extends Zend_Search_Lucene_Storage_Directory
0038 {
0039     /**
0040      * Filesystem path to the directory
0041      *
0042      * @var string
0043      */
0044     protected $_dirPath = null;
0045 
0046     /**
0047      * Cache for Zend_Search_Lucene_Storage_File_Filesystem objects
0048      * Array: filename => Zend_Search_Lucene_Storage_File object
0049      *
0050      * @var array
0051      * @throws Zend_Search_Lucene_Exception
0052      */
0053     protected $_fileHandlers;
0054 
0055     /**
0056      * Default file permissions
0057      *
0058      * @var integer
0059      */
0060     protected static $_defaultFilePermissions = 0666;
0061 
0062 
0063     /**
0064      * Get default file permissions
0065      *
0066      * @return integer
0067      */
0068     public static function getDefaultFilePermissions()
0069     {
0070         return self::$_defaultFilePermissions;
0071     }
0072 
0073     /**
0074      * Set default file permissions
0075      *
0076      * @param integer $mode
0077      */
0078     public static function setDefaultFilePermissions($mode)
0079     {
0080         self::$_defaultFilePermissions = $mode;
0081     }
0082 
0083 
0084     /**
0085      * Utility function to recursive directory creation
0086      *
0087      * @param string $dir
0088      * @param integer $mode
0089      * @param boolean $recursive
0090      * @return boolean
0091      */
0092 
0093     public static function mkdirs($dir, $mode = 0775, $recursive = true)
0094     {
0095         $mode = $mode & ~0002;
0096 
0097         if (($dir === null) || $dir === '') {
0098             return false;
0099         }
0100         if (is_dir($dir) || $dir === '/') {
0101             return true;
0102         }
0103         if (self::mkdirs(dirname($dir), $mode, $recursive)) {
0104             return mkdir($dir, $mode);
0105         }
0106         return false;
0107     }
0108 
0109 
0110     /**
0111      * Object constructor
0112      * Checks if $path is a directory or tries to create it.
0113      *
0114      * @param string $path
0115      * @throws Zend_Search_Lucene_Exception
0116      */
0117     public function __construct($path)
0118     {
0119         if (!is_dir($path)) {
0120             if (file_exists($path)) {
0121                 // require_once 'Zend/Search/Lucene/Exception.php';
0122                 throw new Zend_Search_Lucene_Exception('Path exists, but it\'s not a directory');
0123             } else {
0124                 if (!self::mkdirs($path)) {
0125                     // require_once 'Zend/Search/Lucene/Exception.php';
0126                     throw new Zend_Search_Lucene_Exception("Can't create directory '$path'.");
0127                 }
0128             }
0129         }
0130         $this->_dirPath = $path;
0131         $this->_fileHandlers = array();
0132     }
0133 
0134 
0135     /**
0136      * Closes the store.
0137      *
0138      * @return void
0139      */
0140     public function close()
0141     {
0142         foreach ($this->_fileHandlers as $fileObject) {
0143             $fileObject->close();
0144         }
0145 
0146         $this->_fileHandlers = array();
0147     }
0148 
0149 
0150     /**
0151      * Returns an array of strings, one for each file in the directory.
0152      *
0153      * @return array
0154      */
0155     public function fileList()
0156     {
0157         $result = array();
0158 
0159         $dirContent = opendir( $this->_dirPath );
0160         while (($file = readdir($dirContent)) !== false) {
0161             if (($file == '..')||($file == '.'))   continue;
0162 
0163             if( !is_dir($this->_dirPath . '/' . $file) ) {
0164                 $result[] = $file;
0165             }
0166         }
0167         closedir($dirContent);
0168 
0169         return $result;
0170     }
0171 
0172     /**
0173      * Creates a new, empty file in the directory with the given $filename.
0174      *
0175      * @param string $filename
0176      * @return Zend_Search_Lucene_Storage_File
0177      * @throws Zend_Search_Lucene_Exception
0178      */
0179     public function createFile($filename)
0180     {
0181         if (isset($this->_fileHandlers[$filename])) {
0182             $this->_fileHandlers[$filename]->close();
0183         }
0184         unset($this->_fileHandlers[$filename]);
0185         // require_once 'Zend/Search/Lucene/Storage/File/Filesystem.php';
0186         $this->_fileHandlers[$filename] = new Zend_Search_Lucene_Storage_File_Filesystem($this->_dirPath . '/' . $filename, 'w+b');
0187 
0188         // Set file permissions, but don't care about any possible failures, since file may be already
0189         // created by anther user which has to care about right permissions
0190         @chmod($this->_dirPath . '/' . $filename, self::$_defaultFilePermissions);
0191 
0192         return $this->_fileHandlers[$filename];
0193     }
0194 
0195 
0196     /**
0197      * Removes an existing $filename in the directory.
0198      *
0199      * @param string $filename
0200      * @return void
0201      * @throws Zend_Search_Lucene_Exception
0202      */
0203     public function deleteFile($filename)
0204     {
0205         if (isset($this->_fileHandlers[$filename])) {
0206             $this->_fileHandlers[$filename]->close();
0207         }
0208         unset($this->_fileHandlers[$filename]);
0209 
0210         global $php_errormsg;
0211         $trackErrors = ini_get('track_errors');
0212         ini_set('track_errors', '1');
0213         if (!@unlink($this->_dirPath . '/' . $filename)) {
0214             ini_set('track_errors', $trackErrors);
0215             // require_once 'Zend/Search/Lucene/Exception.php';
0216             throw new Zend_Search_Lucene_Exception('Can\'t delete file: ' . $php_errormsg);
0217         }
0218         ini_set('track_errors', $trackErrors);
0219     }
0220 
0221     /**
0222      * Purge file if it's cached by directory object
0223      *
0224      * Method is used to prevent 'too many open files' error
0225      *
0226      * @param string $filename
0227      * @return void
0228      */
0229     public function purgeFile($filename)
0230     {
0231         if (isset($this->_fileHandlers[$filename])) {
0232             $this->_fileHandlers[$filename]->close();
0233         }
0234         unset($this->_fileHandlers[$filename]);
0235     }
0236 
0237 
0238     /**
0239      * Returns true if a file with the given $filename exists.
0240      *
0241      * @param string $filename
0242      * @return boolean
0243      */
0244     public function fileExists($filename)
0245     {
0246         return isset($this->_fileHandlers[$filename]) ||
0247                file_exists($this->_dirPath . '/' . $filename);
0248     }
0249 
0250 
0251     /**
0252      * Returns the length of a $filename in the directory.
0253      *
0254      * @param string $filename
0255      * @return integer
0256      */
0257     public function fileLength($filename)
0258     {
0259         if (isset( $this->_fileHandlers[$filename] )) {
0260             return $this->_fileHandlers[$filename]->size();
0261         }
0262         return filesize($this->_dirPath .'/'. $filename);
0263     }
0264 
0265 
0266     /**
0267      * Returns the UNIX timestamp $filename was last modified.
0268      *
0269      * @param string $filename
0270      * @return integer
0271      */
0272     public function fileModified($filename)
0273     {
0274         return filemtime($this->_dirPath .'/'. $filename);
0275     }
0276 
0277 
0278     /**
0279      * Renames an existing file in the directory.
0280      *
0281      * @param string $from
0282      * @param string $to
0283      * @return void
0284      * @throws Zend_Search_Lucene_Exception
0285      */
0286     public function renameFile($from, $to)
0287     {
0288         global $php_errormsg;
0289 
0290         if (isset($this->_fileHandlers[$from])) {
0291             $this->_fileHandlers[$from]->close();
0292         }
0293         unset($this->_fileHandlers[$from]);
0294 
0295         if (isset($this->_fileHandlers[$to])) {
0296             $this->_fileHandlers[$to]->close();
0297         }
0298         unset($this->_fileHandlers[$to]);
0299 
0300         if (file_exists($this->_dirPath . '/' . $to)) {
0301             if (!unlink($this->_dirPath . '/' . $to)) {
0302                 // require_once 'Zend/Search/Lucene/Exception.php';
0303                 throw new Zend_Search_Lucene_Exception('Delete operation failed');
0304             }
0305         }
0306 
0307         $trackErrors = ini_get('track_errors');
0308         ini_set('track_errors', '1');
0309 
0310         $success = @rename($this->_dirPath . '/' . $from, $this->_dirPath . '/' . $to);
0311         if (!$success) {
0312             ini_set('track_errors', $trackErrors);
0313             // require_once 'Zend/Search/Lucene/Exception.php';
0314             throw new Zend_Search_Lucene_Exception($php_errormsg);
0315         }
0316 
0317         ini_set('track_errors', $trackErrors);
0318 
0319         return $success;
0320     }
0321 
0322 
0323     /**
0324      * Sets the modified time of $filename to now.
0325      *
0326      * @param string $filename
0327      * @return void
0328      */
0329     public function touchFile($filename)
0330     {
0331         return touch($this->_dirPath .'/'. $filename);
0332     }
0333 
0334 
0335     /**
0336      * Returns a Zend_Search_Lucene_Storage_File object for a given $filename in the directory.
0337      *
0338      * If $shareHandler option is true, then file handler can be shared between File Object
0339      * requests. It speed-ups performance, but makes problems with file position.
0340      * Shared handler are good for short atomic requests.
0341      * Non-shared handlers are useful for stream file reading (especial for compound files).
0342      *
0343      * @param string $filename
0344      * @param boolean $shareHandler
0345      * @return Zend_Search_Lucene_Storage_File
0346      */
0347     public function getFileObject($filename, $shareHandler = true)
0348     {
0349         $fullFilename = $this->_dirPath . '/' . $filename;
0350 
0351         // require_once 'Zend/Search/Lucene/Storage/File/Filesystem.php';
0352         if (!$shareHandler) {
0353             return new Zend_Search_Lucene_Storage_File_Filesystem($fullFilename);
0354         }
0355 
0356         if (isset( $this->_fileHandlers[$filename] )) {
0357             $this->_fileHandlers[$filename]->seek(0);
0358             return $this->_fileHandlers[$filename];
0359         }
0360 
0361         $this->_fileHandlers[$filename] = new Zend_Search_Lucene_Storage_File_Filesystem($fullFilename);
0362         return $this->_fileHandlers[$filename];
0363     }
0364 }