[ Index ]
 

Code source de PHP PEAR 1.4.5

Accédez au Source d'autres logiciels libresSoutenez Angelica Josefina !

title

Body

[fermer]

/Cache/ -> Lite.php (source)

   1  <?php
   2  
   3  /**
   4  * Fast, light and safe Cache Class
   5  *
   6  * Cache_Lite is a fast, light and safe cache system. It's optimized
   7  * for file containers. It is fast and safe (because it uses file
   8  * locking and/or anti-corruption tests).
   9  *
  10  * There are some examples in the 'docs/examples' file
  11  * Technical choices are described in the 'docs/technical' file
  12  *
  13  * Memory Caching is from an original idea of
  14  * Mike BENOIT <ipso@snappymail.ca>
  15  *
  16  * Nota : A chinese documentation (thanks to RainX <china_1982@163.com>) is
  17  * available at :
  18  * http://rainx.phpmore.com/manual/cache_lite.html
  19  *
  20  * @package Cache_Lite
  21  * @category Caching
  22  * @version $Id: Lite.php,v 1.45 2006/06/03 08:10:33 fab Exp $
  23  * @author Fabien MARTY <fab@php.net>
  24  */
  25  
  26  define('CACHE_LITE_ERROR_RETURN', 1);
  27  define('CACHE_LITE_ERROR_DIE', 8);
  28  
  29  class Cache_Lite
  30  {
  31  
  32      // --- Private properties ---
  33  
  34      /**
  35      * Directory where to put the cache files
  36      * (make sure to add a trailing slash)
  37      *
  38      * @var string $_cacheDir
  39      */
  40      var $_cacheDir = '/tmp/';
  41  
  42      /**
  43      * Enable / disable caching
  44      *
  45      * (can be very usefull for the debug of cached scripts)
  46      *
  47      * @var boolean $_caching
  48      */
  49      var $_caching = true;
  50  
  51      /**
  52      * Cache lifetime (in seconds)
  53      *
  54      * If null, the cache is valid forever.
  55      *
  56      * @var int $_lifeTime
  57      */
  58      var $_lifeTime = 3600;
  59  
  60      /**
  61      * Enable / disable fileLocking
  62      *
  63      * (can avoid cache corruption under bad circumstances)
  64      *
  65      * @var boolean $_fileLocking
  66      */
  67      var $_fileLocking = true;
  68  
  69      /**
  70      * Timestamp of the last valid cache
  71      *
  72      * @var int $_refreshTime
  73      */
  74      var $_refreshTime;
  75  
  76      /**
  77      * File name (with path)
  78      *
  79      * @var string $_file
  80      */
  81      var $_file;
  82      
  83      /**
  84      * File name (without path)
  85      *
  86      * @var string $_fileName
  87      */
  88      var $_fileName;
  89  
  90      /**
  91      * Enable / disable write control (the cache is read just after writing to detect corrupt entries)
  92      *
  93      * Enable write control will lightly slow the cache writing but not the cache reading
  94      * Write control can detect some corrupt cache files but maybe it's not a perfect control
  95      *
  96      * @var boolean $_writeControl
  97      */
  98      var $_writeControl = true;
  99  
 100      /**
 101      * Enable / disable read control
 102      *
 103      * If enabled, a control key is embeded in cache file and this key is compared with the one
 104      * calculated after the reading.
 105      *
 106      * @var boolean $_writeControl
 107      */
 108      var $_readControl = true;
 109  
 110      /**
 111      * Type of read control (only if read control is enabled)
 112      *
 113      * Available values are :
 114      * 'md5' for a md5 hash control (best but slowest)
 115      * 'crc32' for a crc32 hash control (lightly less safe but faster, better choice)
 116      * 'strlen' for a length only test (fastest)
 117      *
 118      * @var boolean $_readControlType
 119      */
 120      var $_readControlType = 'crc32';
 121  
 122      /**
 123      * Pear error mode (when raiseError is called)
 124      *
 125      * (see PEAR doc)
 126      *
 127      * @see setToDebug()
 128      * @var int $_pearErrorMode
 129      */
 130      var $_pearErrorMode = CACHE_LITE_ERROR_RETURN;
 131      
 132      /**
 133      * Current cache id
 134      *
 135      * @var string $_id
 136      */
 137      var $_id;
 138  
 139      /**
 140      * Current cache group
 141      *
 142      * @var string $_group
 143      */
 144      var $_group;
 145  
 146      /**
 147      * Enable / Disable "Memory Caching"
 148      *
 149      * NB : There is no lifetime for memory caching ! 
 150      *
 151      * @var boolean $_memoryCaching
 152      */
 153      var $_memoryCaching = false;
 154  
 155      /**
 156      * Enable / Disable "Only Memory Caching"
 157      * (be carefull, memory caching is "beta quality")
 158      *
 159      * @var boolean $_onlyMemoryCaching
 160      */
 161      var $_onlyMemoryCaching = false;
 162  
 163      /**
 164      * Memory caching array
 165      *
 166      * @var array $_memoryCachingArray
 167      */
 168      var $_memoryCachingArray = array();
 169  
 170      /**
 171      * Memory caching counter
 172      *
 173      * @var int $memoryCachingCounter
 174      */
 175      var $_memoryCachingCounter = 0;
 176  
 177      /**
 178      * Memory caching limit
 179      *
 180      * @var int $memoryCachingLimit
 181      */
 182      var $_memoryCachingLimit = 1000;
 183      
 184      /**
 185      * File Name protection
 186      *
 187      * if set to true, you can use any cache id or group name
 188      * if set to false, it can be faster but cache ids and group names
 189      * will be used directly in cache file names so be carefull with
 190      * special characters...
 191      *
 192      * @var boolean $fileNameProtection
 193      */
 194      var $_fileNameProtection = true;
 195      
 196      /**
 197      * Enable / disable automatic serialization
 198      *
 199      * it can be used to save directly datas which aren't strings
 200      * (but it's slower)    
 201      *
 202      * @var boolean $_serialize
 203      */
 204      var $_automaticSerialization = false;
 205      
 206      /**
 207      * Disable / Tune the automatic cleaning process
 208      *
 209      * The automatic cleaning process destroy too old (for the given life time)
 210      * cache files when a new cache file is written.
 211      * 0               => no automatic cache cleaning
 212      * 1               => systematic cache cleaning
 213      * x (integer) > 1 => automatic cleaning randomly 1 times on x cache write
 214      *
 215      * @var int $_automaticCleaning
 216      */
 217      var $_automaticCleaningFactor = 0;
 218      
 219      /**
 220      * Nested directory level
 221      *
 222      * Set the hashed directory structure level. 0 means "no hashed directory 
 223      * structure", 1 means "one level of directory", 2 means "two levels"... 
 224      * This option can speed up Cache_Lite only when you have many thousands of 
 225      * cache file. Only specific benchs can help you to choose the perfect value 
 226      * for you. Maybe, 1 or 2 is a good start.
 227      *
 228      * @var int $_hashedDirectoryLevel
 229      */
 230      var $_hashedDirectoryLevel = 0;
 231      
 232      /**
 233      * Umask for hashed directory structure
 234      *
 235      * @var int $_hashedDirectoryUmask
 236      */
 237      var $_hashedDirectoryUmask = 0700;
 238      
 239      /**
 240       * API break for error handling in CACHE_LITE_ERROR_RETURN mode
 241       * 
 242       * In CACHE_LITE_ERROR_RETURN mode, error handling was not good because
 243       * for example save() method always returned a boolean (a PEAR_Error object
 244       * would be better in CACHE_LITE_ERROR_RETURN mode). To correct this without
 245       * breaking the API, this option (false by default) can change this handling.
 246       * 
 247       * @var boolean
 248       */
 249      var $_errorHandlingAPIBreak = false;
 250      
 251      // --- Public methods ---
 252  
 253      /**
 254      * Constructor
 255      *
 256      * $options is an assoc. Available options are :
 257      * $options = array(
 258      *     'cacheDir' => directory where to put the cache files (string),
 259      *     'caching' => enable / disable caching (boolean),
 260      *     'lifeTime' => cache lifetime in seconds (int),
 261      *     'fileLocking' => enable / disable fileLocking (boolean),
 262      *     'writeControl' => enable / disable write control (boolean),
 263      *     'readControl' => enable / disable read control (boolean),
 264      *     'readControlType' => type of read control 'crc32', 'md5', 'strlen' (string),
 265      *     'pearErrorMode' => pear error mode (when raiseError is called) (cf PEAR doc) (int),
 266      *     'memoryCaching' => enable / disable memory caching (boolean),
 267      *     'onlyMemoryCaching' => enable / disable only memory caching (boolean),
 268      *     'memoryCachingLimit' => max nbr of records to store into memory caching (int),
 269      *     'fileNameProtection' => enable / disable automatic file name protection (boolean),
 270      *     'automaticSerialization' => enable / disable automatic serialization (boolean),
 271      *     'automaticCleaningFactor' => distable / tune automatic cleaning process (int),
 272      *     'hashedDirectoryLevel' => level of the hashed directory system (int),
 273      *     'hashedDirectoryUmask' => umask for hashed directory structure (int),
 274      *     'errorHandlingAPIBreak' => API break for better error handling ? (boolean)
 275      * );
 276      *
 277      * @param array $options options
 278      * @access public
 279      */
 280      function Cache_Lite($options = array(NULL))
 281      {
 282          foreach($options as $key => $value) {
 283              $this->setOption($key, $value);
 284          }
 285      }
 286      
 287      /**
 288      * Generic way to set a Cache_Lite option
 289      *
 290      * see Cache_Lite constructor for available options
 291      *
 292      * @var string $name name of the option
 293      * @var mixed $value value of the option
 294      * @access public
 295      */
 296      function setOption($name, $value) 
 297      {
 298          $availableOptions = array('errorHandlingAPIBreak', 'hashedDirectoryUmask', 'hashedDirectoryLevel', 'automaticCleaningFactor', 'automaticSerialization', 'fileNameProtection', 'memoryCaching', 'onlyMemoryCaching', 'memoryCachingLimit', 'cacheDir', 'caching', 'lifeTime', 'fileLocking', 'writeControl', 'readControl', 'readControlType', 'pearErrorMode');
 299          if (in_array($name, $availableOptions)) {
 300              $property = '_'.$name;
 301              $this->$property = $value;
 302          }
 303      }
 304      
 305      /**
 306      * Test if a cache is available and (if yes) return it
 307      *
 308      * @param string $id cache id
 309      * @param string $group name of the cache group
 310      * @param boolean $doNotTestCacheValidity if set to true, the cache validity won't be tested
 311      * @return string data of the cache (else : false)
 312      * @access public
 313      */
 314      function get($id, $group = 'default', $doNotTestCacheValidity = false)
 315      {
 316          $this->_id = $id;
 317          $this->_group = $group;
 318          $data = false;
 319          if ($this->_caching) {
 320              $this->_setRefreshTime();
 321              $this->_setFileName($id, $group);
 322              clearstatcache();
 323              if ($this->_memoryCaching) {
 324                  if (isset($this->_memoryCachingArray[$this->_file])) {
 325                      if ($this->_automaticSerialization) {
 326                          return unserialize($this->_memoryCachingArray[$this->_file]);
 327                      }
 328                      return $this->_memoryCachingArray[$this->_file];
 329                  }
 330                  if ($this->_onlyMemoryCaching) {
 331                      return false;
 332                  }                
 333              }
 334              if (($doNotTestCacheValidity) || (is_null($this->_refreshTime))) {
 335                  if (file_exists($this->_file)) {
 336                      $data = $this->_read();
 337                  }
 338              } else {
 339                  if ((file_exists($this->_file)) && (@filemtime($this->_file) > $this->_refreshTime)) {
 340                      $data = $this->_read();
 341                  }
 342              }
 343              if (($data) and ($this->_memoryCaching)) {
 344                  $this->_memoryCacheAdd($data);
 345              }
 346              if (($this->_automaticSerialization) and (is_string($data))) {
 347                  $data = unserialize($data);
 348              }
 349              return $data;
 350          }
 351          return false;
 352      }
 353      
 354      /**
 355      * Save some data in a cache file
 356      *
 357      * @param string $data data to put in cache (can be another type than strings if automaticSerialization is on)
 358      * @param string $id cache id
 359      * @param string $group name of the cache group
 360      * @return boolean true if no problem (else : false or a PEAR_Error object)
 361      * @access public
 362      */
 363      function save($data, $id = NULL, $group = 'default')
 364      {
 365          if ($this->_caching) {
 366              if ($this->_automaticSerialization) {
 367                  $data = serialize($data);
 368              }
 369              if (isset($id)) {
 370                  $this->_setFileName($id, $group);
 371              }
 372              if ($this->_memoryCaching) {
 373                  $this->_memoryCacheAdd($data);
 374                  if ($this->_onlyMemoryCaching) {
 375                      return true;
 376                  }
 377              }
 378              if ($this->_automaticCleaningFactor>0) {
 379                  $rand = rand(1, $this->_automaticCleaningFactor);
 380                  if ($rand==1) {
 381                      $this->clean(false, 'old');
 382                  }
 383              }
 384              if ($this->_writeControl) {
 385                  $res = $this->_writeAndControl($data);
 386                  if (is_bool($res)) {
 387                      if ($res) {
 388                          return true;  
 389                      }
 390                      // if $res if false, we need to invalidate the cache
 391                      @touch($this->_file, time() - 2*abs($this->_lifeTime));
 392                      return false;
 393                  }            
 394              } else {
 395                  $res = $this->_write($data);
 396              }
 397              if (is_object($res)) {
 398                  // $res is a PEAR_Error object 
 399                  if (!($this->_errorHandlingAPIBreak)) {   
 400                      return false; // we return false (old API)
 401                  }
 402              }
 403              return $res;
 404          }
 405          return false;
 406      }
 407  
 408      /**
 409      * Remove a cache file
 410      *
 411      * @param string $id cache id
 412      * @param string $group name of the cache group
 413      * @return boolean true if no problem
 414      * @access public
 415      */
 416      function remove($id, $group = 'default')
 417      {
 418          $this->_setFileName($id, $group);
 419          if ($this->_memoryCaching) {
 420              if (isset($this->_memoryCachingArray[$this->_file])) {
 421                  unset($this->_memoryCachingArray[$this->_file]);
 422                  $this->_memoryCachingCounter = $this->_memoryCachingCounter - 1;
 423              }
 424              if ($this->_onlyMemoryCaching) {
 425                  return true;
 426              }
 427          }
 428          return $this->_unlink($this->_file);
 429      }
 430  
 431      /**
 432      * Clean the cache
 433      *
 434      * if no group is specified all cache files will be destroyed
 435      * else only cache files of the specified group will be destroyed
 436      *
 437      * @param string $group name of the cache group
 438      * @param string $mode flush cache mode : 'old', 'ingroup', 'notingroup', 
 439      *                                        'callback_myFunction'
 440      * @return boolean true if no problem
 441      * @access public
 442      */
 443      function clean($group = false, $mode = 'ingroup')
 444      {
 445          return $this->_cleanDir($this->_cacheDir, $group, $mode);
 446      }
 447         
 448      /**
 449      * Set to debug mode
 450      *
 451      * When an error is found, the script will stop and the message will be displayed
 452      * (in debug mode only). 
 453      *
 454      * @access public
 455      */
 456      function setToDebug()
 457      {
 458          $this->setOption('pearErrorMode', CACHE_LITE_ERROR_DIE);
 459      }
 460  
 461      /**
 462      * Set a new life time
 463      *
 464      * @param int $newLifeTime new life time (in seconds)
 465      * @access public
 466      */
 467      function setLifeTime($newLifeTime)
 468      {
 469          $this->_lifeTime = $newLifeTime;
 470          $this->_setRefreshTime();
 471      }
 472  
 473      /**
 474      * Save the state of the caching memory array into a cache file cache
 475      *
 476      * @param string $id cache id
 477      * @param string $group name of the cache group
 478      * @access public
 479      */
 480      function saveMemoryCachingState($id, $group = 'default')
 481      {
 482          if ($this->_caching) {
 483              $array = array(
 484                  'counter' => $this->_memoryCachingCounter,
 485                  'array' => $this->_memoryCachingState
 486              );
 487              $data = serialize($array);
 488              $this->save($data, $id, $group);
 489          }
 490      }
 491  
 492      /**
 493      * Load the state of the caching memory array from a given cache file cache
 494      *
 495      * @param string $id cache id
 496      * @param string $group name of the cache group
 497      * @param boolean $doNotTestCacheValidity if set to true, the cache validity won't be tested
 498      * @access public
 499      */
 500      function getMemoryCachingState($id, $group = 'default', $doNotTestCacheValidity = false)
 501      {
 502          if ($this->_caching) {
 503              if ($data = $this->get($id, $group, $doNotTestCacheValidity)) {
 504                  $array = unserialize($data);
 505                  $this->_memoryCachingCounter = $array['counter'];
 506                  $this->_memoryCachingArray = $array['array'];
 507              }
 508          }
 509      }
 510      
 511      /**
 512      * Return the cache last modification time
 513      *
 514      * BE CAREFUL : THIS METHOD IS FOR HACKING ONLY !
 515      *
 516      * @return int last modification time
 517      */
 518      function lastModified() 
 519      {
 520          return @filemtime($this->_file);
 521      }
 522      
 523      /**
 524      * Trigger a PEAR error
 525      *
 526      * To improve performances, the PEAR.php file is included dynamically.
 527      * The file is so included only when an error is triggered. So, in most
 528      * cases, the file isn't included and perfs are much better.
 529      *
 530      * @param string $msg error message
 531      * @param int $code error code
 532      * @access public
 533      */
 534      function raiseError($msg, $code)
 535      {
 536          include_once ('PEAR.php');
 537          return PEAR::raiseError($msg, $code, $this->_pearErrorMode);
 538      }
 539      
 540      /**
 541       * Extend the life of a valid cache file
 542       * 
 543       * see http://pear.php.net/bugs/bug.php?id=6681
 544       * 
 545       * @access public
 546       */
 547      function extendLife()
 548      {
 549          @touch($this->_file);
 550      }
 551      
 552      // --- Private methods ---
 553      
 554      /**
 555      * Compute & set the refresh time
 556      *
 557      * @access private
 558      */
 559      function _setRefreshTime() 
 560      {
 561          if (is_null($this->_lifeTime)) {
 562              $this->_refreshTime = null;
 563          } else {
 564              $this->_refreshTime = time() - $this->_lifeTime;
 565          }
 566      }
 567      
 568      /**
 569      * Remove a file
 570      * 
 571      * @param string $file complete file path and name
 572      * @return boolean true if no problem
 573      * @access private
 574      */
 575      function _unlink($file)
 576      {
 577          if (!@unlink($file)) {
 578              return $this->raiseError('Cache_Lite : Unable to remove cache !', -3);
 579          }
 580          return true;        
 581      }
 582  
 583      /**
 584      * Recursive function for cleaning cache file in the given directory
 585      *
 586      * @param string $dir directory complete path (with a trailing slash)
 587      * @param string $group name of the cache group
 588      * @param string $mode flush cache mode : 'old', 'ingroup', 'notingroup',
 589                                               'callback_myFunction'
 590      * @return boolean true if no problem
 591      * @access private
 592      */
 593      function _cleanDir($dir, $group = false, $mode = 'ingroup')     
 594      {
 595          if ($this->_fileNameProtection) {
 596              $motif = ($group) ? 'cache_'.md5($group).'_' : 'cache_';
 597          } else {
 598              $motif = ($group) ? 'cache_'.$group.'_' : 'cache_';
 599          }
 600          if ($this->_memoryCaching) {
 601              while (list($key, ) = each($this->_memoryCachingArray)) {
 602                  if (strpos($key, $motif, 0)) {
 603                      unset($this->_memoryCachingArray[$key]);
 604                      $this->_memoryCachingCounter = $this->_memoryCachingCounter - 1;
 605                  }
 606              }
 607              if ($this->_onlyMemoryCaching) {
 608                  return true;
 609              }
 610          }
 611          if (!($dh = opendir($dir))) {
 612              return $this->raiseError('Cache_Lite : Unable to open cache directory !', -4);
 613          }
 614          $result = true;
 615          while ($file = readdir($dh)) {
 616              if (($file != '.') && ($file != '..')) {
 617                  if (substr($file, 0, 6)=='cache_') {
 618                      $file2 = $dir . $file;
 619                      if (is_file($file2)) {
 620                          switch (substr($mode, 0, 9)) {
 621                              case 'old':
 622                                  // files older than lifeTime get deleted from cache
 623                                  if (!is_null($this->_lifeTime)) {
 624                                      if ((mktime() - @filemtime($file2)) > $this->_lifeTime) {
 625                                          $result = ($result and ($this->_unlink($file2)));
 626                                      }
 627                                  }
 628                                  break;
 629                              case 'notingrou':
 630                                  if (!strpos($file2, $motif, 0)) {
 631                                      $result = ($result and ($this->_unlink($file2)));
 632                                  }
 633                                  break;
 634                              case 'callback_':
 635                                  $func = substr($mode, 9, strlen($mode) - 9);
 636                                  if ($func($file2, $group)) {
 637                                      $result = ($result and ($this->_unlink($file2)));
 638                                  }
 639                                  break;
 640                              case 'ingroup':
 641                              default:
 642                                  if (strpos($file2, $motif, 0)) {
 643                                      $result = ($result and ($this->_unlink($file2)));
 644                                  }
 645                                  break;
 646                          }
 647                      }
 648                      if ((is_dir($file2)) and ($this->_hashedDirectoryLevel>0)) {
 649                          $result = ($result and ($this->_cleanDir($file2 . '/', $group, $mode)));
 650                      }
 651                  }
 652              }
 653          }
 654          return $result;
 655      }
 656        
 657      /**
 658      * Add some date in the memory caching array
 659      *
 660      * @param string $data data to cache
 661      * @access private
 662      */
 663      function _memoryCacheAdd($data)
 664      {
 665          $this->_memoryCachingArray[$this->_file] = $data;
 666          if ($this->_memoryCachingCounter >= $this->_memoryCachingLimit) {
 667              list($key, ) = each($this->_memoryCachingArray);
 668              unset($this->_memoryCachingArray[$key]);
 669          } else {
 670              $this->_memoryCachingCounter = $this->_memoryCachingCounter + 1;
 671          }
 672      }
 673  
 674      /**
 675      * Make a file name (with path)
 676      *
 677      * @param string $id cache id
 678      * @param string $group name of the group
 679      * @access private
 680      */
 681      function _setFileName($id, $group)
 682      {
 683          
 684          if ($this->_fileNameProtection) {
 685              $suffix = 'cache_'.md5($group).'_'.md5($id);
 686          } else {
 687              $suffix = 'cache_'.$group.'_'.$id;
 688          }
 689          $root = $this->_cacheDir;
 690          if ($this->_hashedDirectoryLevel>0) {
 691              $hash = md5($suffix);
 692              for ($i=0 ; $i<$this->_hashedDirectoryLevel ; $i++) {
 693                  $root = $root . 'cache_' . substr($hash, 0, $i + 1) . '/';
 694              }   
 695          }
 696          $this->_fileName = $suffix;
 697          $this->_file = $root.$suffix;
 698      }
 699      
 700      /**
 701      * Read the cache file and return the content
 702      *
 703      * @return string content of the cache file (else : false or a PEAR_Error object)
 704      * @access private
 705      */
 706      function _read()
 707      {
 708          $fp = @fopen($this->_file, "rb");
 709          if ($this->_fileLocking) @flock($fp, LOCK_SH);
 710          if ($fp) {
 711              clearstatcache();
 712              $length = @filesize($this->_file);
 713              $mqr = get_magic_quotes_runtime();
 714              set_magic_quotes_runtime(0);
 715              if ($this->_readControl) {
 716                  $hashControl = @fread($fp, 32);
 717                  $length = $length - 32;
 718              } 
 719              if ($length) {
 720                  $data = @fread($fp, $length);
 721              } else {
 722                  $data = '';
 723              }
 724              set_magic_quotes_runtime($mqr);
 725              if ($this->_fileLocking) @flock($fp, LOCK_UN);
 726              @fclose($fp);
 727              if ($this->_readControl) {
 728                  $hashData = $this->_hash($data, $this->_readControlType);
 729                  if ($hashData != $hashControl) {
 730                      if (!(is_null($this->_lifeTime))) {
 731                          @touch($this->_file, time() - 2*abs($this->_lifeTime)); 
 732                      } else {
 733                          @unlink($this->_file);
 734                      }
 735                      return false;
 736                  }
 737              }
 738              return $data;
 739          }
 740          return $this->raiseError('Cache_Lite : Unable to read cache !', -2); 
 741      }
 742      
 743      /**
 744      * Write the given data in the cache file
 745      *
 746      * @param string $data data to put in cache
 747      * @return boolean true if ok (a PEAR_Error object else)
 748      * @access private
 749      */
 750      function _write($data)
 751      {
 752          if ($this->_hashedDirectoryLevel > 0) {
 753              $hash = md5($this->_fileName);
 754              $root = $this->_cacheDir;
 755              for ($i=0 ; $i<$this->_hashedDirectoryLevel ; $i++) {
 756                  $root = $root . 'cache_' . substr($hash, 0, $i + 1) . '/';
 757                  if (!(@is_dir($root))) {
 758                      @mkdir($root, $this->_hashedDirectoryUmask);
 759                  }
 760              }
 761          }
 762          $fp = @fopen($this->_file, "wb");
 763          if ($fp) {
 764              if ($this->_fileLocking) @flock($fp, LOCK_EX);
 765              if ($this->_readControl) {
 766                  @fwrite($fp, $this->_hash($data, $this->_readControlType), 32);
 767              }
 768              $len = strlen($data);
 769              @fwrite($fp, $data, $len);
 770              if ($this->_fileLocking) @flock($fp, LOCK_UN);
 771              @fclose($fp);
 772              return true;
 773          }      
 774          return $this->raiseError('Cache_Lite : Unable to write cache file : '.$this->_file, -1);
 775      }
 776         
 777      /**
 778      * Write the given data in the cache file and control it just after to avoir corrupted cache entries
 779      *
 780      * @param string $data data to put in cache
 781      * @return boolean true if the test is ok (else : false or a PEAR_Error object)
 782      * @access private
 783      */
 784      function _writeAndControl($data)
 785      {
 786          $result = $this->_write($data);
 787          if (is_object($result)) {
 788              return $result; # We return the PEAR_Error object
 789          }
 790          $dataRead = $this->_read();
 791          if (is_object($dataRead)) {
 792              return $result; # We return the PEAR_Error object
 793          }
 794          if ((is_bool($dataRead)) && (!$dataRead)) {
 795              return false; 
 796          }
 797          return ($dataRead==$data);
 798      }
 799      
 800      /**
 801      * Make a control key with the string containing datas
 802      *
 803      * @param string $data data
 804      * @param string $controlType type of control 'md5', 'crc32' or 'strlen'
 805      * @return string control key
 806      * @access private
 807      */
 808      function _hash($data, $controlType)
 809      {
 810          switch ($controlType) {
 811          case 'md5':
 812              return md5($data);
 813          case 'crc32':
 814              return sprintf('% 32d', crc32($data));
 815          case 'strlen':
 816              return sprintf('% 32d', strlen($data));
 817          default:
 818              return $this->raiseError('Unknown controlType ! (available values are only \'md5\', \'crc32\', \'strlen\')', -5);
 819          }
 820      }
 821      
 822  } 
 823  
 824  ?>


Généré le : Sun Feb 25 14:08:00 2007 par Balluche grâce à PHPXref 0.7