Пример #1
0
 /**
  * Get by key
  *
  * @param $key
  * @param array $options
  * @return bool|string
  * @throws Exception\ItemNotFoundException|Exception\UnexpectedValueException
  */
 protected function internalGetItem($key, array &$options)
 {
     if (!$this->internalHasItem($key, $options) || !($keyInfo = $this->getKeyInfo($key, $options['namespace']))) {
         if ($options['ignore_missing_items']) {
             return false;
         } else {
             throw new Exception\ItemNotFoundException("Key '{$key}' not found within namespace '{$options['namespace']}'");
         }
     }
     $baseOptions = $this->getOptions();
     try {
         $data = $this->getFileContent($keyInfo['filespec'] . '.dat');
         if ($baseOptions->getReadControl()) {
             if (($info = $this->readInfoFile($keyInfo['filespec'] . '.ifo')) && isset($info['hash'], $info['algo']) && Utils::generateHash($info['algo'], $data, true) != $info['hash']) {
                 throw new Exception\UnexpectedValueException("ReadControl: Stored hash and computed hash don't match");
             }
         }
         return $data;
     } catch (Exception $e) {
         try {
             // remove cache file on exception
             $this->internalRemoveItem($key, $options);
         } catch (Exception $tmp) {
         }
         // do not throw remove exception on this point
         throw $e;
     }
 }
Пример #2
0
 /**
  * Internal method to store multiple items.
  *
  * Options:
  *  - namespace <string>
  *    - The namespace to use
  *  - tags <array>
  *    - An array of tags
  *
  * @param  array $normalizedKeyValuePairs
  * @param  array $normalizedOptions
  * @return boolean
  * @throws Exception\ExceptionInterface
  */
 protected function internalSetItems(array &$normalizedKeyValuePairs, array &$normalizedOptions)
 {
     $baseOptions = $this->getOptions();
     $oldUmask = null;
     // create an associated array of files and contents to write
     $contents = array();
     foreach ($normalizedKeyValuePairs as $key => &$value) {
         $filespec = $this->getFileSpec($key, $normalizedOptions);
         // init directory level
         if ($baseOptions->getDirLevel() > 0) {
             $path = dirname($filespec);
             if (!file_exists($path)) {
                 $oldUmask = $oldUmask === null ? umask($baseOptions->getDirUmask()) : $oldUmask;
                 ErrorHandler::start();
                 $mkdir = mkdir($path, 0777, true);
                 $error = ErrorHandler::stop();
                 if (!$mkdir) {
                     umask($oldUmask);
                     throw new Exception\RuntimeException("Error creating directory '{$path}'", 0, $error);
                 }
             }
         }
         // *.dat file
         $contents[$filespec . '.dat'] =& $value;
         // *.ifo file
         $info = null;
         if ($baseOptions->getReadControl()) {
             $info['hash'] = Utils::generateHash($baseOptions->getReadControlAlgo(), $value, true);
             $info['algo'] = $baseOptions->getReadControlAlgo();
         }
         if (isset($normalizedOptions['tags'])) {
             $info['tags'] =& $normalizedOptions['tags'];
         }
         if ($info) {
             $contents[$filespec . '.ifo'] = serialize($info);
         } else {
             $this->unlink($filespec . '.ifo');
         }
     }
     // write to disk
     try {
         // set umask for files
         if ($oldUmask !== null) {
             // $oldUmask could be defined on create directory
             umask($baseOptions->getFileUmask());
         } else {
             $oldUmask = umask($baseOptions->getFileUmask());
         }
         while ($contents) {
             $nonBlocking = count($contents) > 1;
             $wouldblock = null;
             foreach ($contents as $file => &$content) {
                 $this->putFileContent($file, $content, $nonBlocking, $wouldblock);
                 if (!$nonBlocking || !$wouldblock) {
                     unset($contents[$file]);
                 }
             }
         }
         // reset umask
         umask($oldUmask);
         return true;
     } catch (Exception $e) {
         // reset umask on exception
         umask($oldUmask);
         throw $e;
     }
 }
Пример #3
0
 /**
  * Internal method to store multiple items.
  *
  * @param  array $normalizedKeyValuePairs
  * @return array Array of not stored keys
  * @throws Exception\ExceptionInterface
  */
 protected function internalSetItems(array &$normalizedKeyValuePairs)
 {
     $baseOptions = $this->getOptions();
     $oldUmask = null;
     // create an associated array of files and contents to write
     $contents = array();
     foreach ($normalizedKeyValuePairs as $key => &$value) {
         $filespec = $this->getFileSpec($key);
         $this->prepareDirectoryStructure($filespec);
         // *.dat file
         $contents[$filespec . '.dat'] =& $value;
         // *.ifo file
         $info = null;
         if ($baseOptions->getReadControl()) {
             $info['hash'] = Utils::generateHash($baseOptions->getReadControlAlgo(), $value, true);
             $info['algo'] = $baseOptions->getReadControlAlgo();
         }
         if ($info) {
             $contents[$filespec . '.ifo'] = serialize($info);
         } else {
             $this->unlink($filespec . '.ifo');
             $this->unlink($filespec . '.tag');
         }
     }
     // write to disk
     try {
         // set umask for files
         $oldUmask = umask($baseOptions->getFileUmask());
         while ($contents) {
             $nonBlocking = count($contents) > 1;
             $wouldblock = null;
             foreach ($contents as $file => &$content) {
                 $this->putFileContent($file, $content, $nonBlocking, $wouldblock);
                 if (!$nonBlocking || !$wouldblock) {
                     unset($contents[$file]);
                 }
             }
         }
         // reset umask
         umask($oldUmask);
         // return OK
         return array();
     } catch (BaseException $e) {
         // reset umask on exception
         umask($oldUmask);
         throw $e;
     }
 }
Пример #4
0
 public function testGenerateHashStrlenRaw()
 {
     $this->assertEquals(pack('l', strlen('test')), Utils::generateHash('strlen', 'test', true));
 }
Пример #5
0
 /**
  * Internal method to store an item.
  *
  * Options:
  *  - namespace <string>
  *    - The namespace to use
  *  - tags <array>
  *    - An array of tags
  *
  * @param  string $normalizedKey
  * @param  mixed  $value
  * @param  array  $normalizedOptions
  * @return boolean
  * @throws Exception
  */
 protected function internalSetItem(&$normalizedKey, &$value, array &$normalizedOptions)
 {
     $baseOptions = $this->getOptions();
     $oldUmask = null;
     $lastInfoId = $normalizedOptions['namespace'] . $baseOptions->getNamespaceSeparator() . $normalizedKey;
     if ($this->lastInfoId == $lastInfoId) {
         $filespec = $this->lastInfo['filespec'];
         // if lastKeyInfo is available I'm sure that the cache directory exist
     } else {
         $filespec = $this->getFileSpec($normalizedKey, $normalizedOptions['namespace']);
         if ($baseOptions->getDirLevel() > 0) {
             $path = dirname($filespec);
             if (!file_exists($path)) {
                 $oldUmask = umask($baseOptions->getDirUmask());
                 ErrorHandler::start();
                 $mkdir = mkdir($path, 0777, true);
                 $error = ErrorHandler::stop();
                 if (!$mkdir) {
                     throw new Exception\RuntimeException("Error creating directory '{$path}'", 0, $error);
                 }
             }
         }
     }
     $info = null;
     if ($baseOptions->getReadControl()) {
         $info['hash'] = Utils::generateHash($baseOptions->getReadControlAlgo(), $value, true);
         $info['algo'] = $baseOptions->getReadControlAlgo();
     }
     if (isset($options['tags']) && $normalizedOptions['tags']) {
         $tags = $normalizedOptions['tags'];
         if (!is_array($tags)) {
             $tags = array($tags);
         }
         $info['tags'] = array_values(array_unique($tags));
     }
     try {
         if ($oldUmask !== null) {
             // $oldUmask could be defined on set directory_umask
             umask($baseOptions->getFileUmask());
         } else {
             $oldUmask = umask($baseOptions->getFileUmask());
         }
         $ret = $this->putFileContent($filespec . '.dat', $value);
         if ($ret && $info) {
             // Don't throw exception if writing of info file failed
             // -> only return false
             try {
                 $ret = $this->putFileContent($filespec . '.ifo', serialize($info));
             } catch (Exception\RuntimeException $e) {
                 $ret = false;
             }
         }
         $this->lastInfoId = null;
         // reset file_umask
         umask($oldUmask);
         return $ret;
     } catch (Exception $e) {
         // reset umask on exception
         umask($oldUmask);
         throw $e;
     }
 }