/library/Zend/Cache/Pattern/PatternOptions.php

https://github.com/zucchi/zf2 · PHP · 771 lines · 465 code · 44 blank · 262 comment · 17 complexity · 4702ab05daac1829d7f7ff49e0ff60df MD5 · raw file

  1. <?php
  2. /**
  3. * Zend Framework (http://framework.zend.com/)
  4. *
  5. * @link http://github.com/zendframework/zf2 for the canonical source repository
  6. * @copyright Copyright (c) 2005-2012 Zend Technologies USA Inc. (http://www.zend.com)
  7. * @license http://framework.zend.com/license/new-bsd New BSD License
  8. * @package Zend_Cache
  9. */
  10. namespace Zend\Cache\Pattern;
  11. use Traversable;
  12. use Zend\Cache\Exception;
  13. use Zend\Cache\StorageFactory;
  14. use Zend\Cache\Storage\StorageInterface as Storage;
  15. use Zend\Stdlib\AbstractOptions;
  16. /**
  17. * @category Zend
  18. * @package Zend_Cache
  19. * @subpackage Pattern
  20. */
  21. class PatternOptions extends AbstractOptions
  22. {
  23. /**
  24. * Used by:
  25. * - ClassCache
  26. * - ObjectCache
  27. * @var bool
  28. */
  29. protected $cacheByDefault = true;
  30. /**
  31. * Used by:
  32. * - CallbackCache
  33. * - ClassCache
  34. * - ObjectCache
  35. * @var bool
  36. */
  37. protected $cacheOutput = true;
  38. /**
  39. * Used by:
  40. * - ClassCache
  41. * @var null|string
  42. */
  43. protected $class;
  44. /**
  45. * Used by:
  46. * - ClassCache
  47. * @var array
  48. */
  49. protected $classCacheMethods = array();
  50. /**
  51. * Used by:
  52. * - ClassCache
  53. * @var array
  54. */
  55. protected $classNonCacheMethods = array();
  56. /**
  57. * Used by:
  58. * - CaptureCache
  59. * @var false|int
  60. */
  61. protected $umask = false;
  62. /**
  63. * Used by:
  64. * - CaptureCache
  65. * @var false|int
  66. */
  67. protected $dirPermission = 0700;
  68. /**
  69. * Used by:
  70. * - CaptureCache
  71. * @var false|int
  72. */
  73. protected $filePermission = 0600;
  74. /**
  75. * Used by:
  76. * - CaptureCache
  77. * @var bool
  78. */
  79. protected $fileLocking = true;
  80. /**
  81. * Used by:
  82. * - CaptureCache
  83. * @var string
  84. */
  85. protected $indexFilename = 'index.html';
  86. /**
  87. * Used by:
  88. * - ObjectCache
  89. * @var null|object
  90. */
  91. protected $object;
  92. /**
  93. * Used by:
  94. * - ObjectCache
  95. * @var bool
  96. */
  97. protected $objectCacheMagicProperties = false;
  98. /**
  99. * Used by:
  100. * - ObjectCache
  101. * @var array
  102. */
  103. protected $objectCacheMethods = array();
  104. /**
  105. * Used by:
  106. * - ObjectCache
  107. * @var null|string
  108. */
  109. protected $objectKey;
  110. /**
  111. * Used by:
  112. * - ObjectCache
  113. * @var array
  114. */
  115. protected $objectNonCacheMethods = array('__tostring');
  116. /**
  117. * Used by:
  118. * - CaptureCache
  119. * @var null|string
  120. */
  121. protected $publicDir;
  122. /**
  123. * Used by:
  124. * - CallbackCache
  125. * - ClassCache
  126. * - ObjectCache
  127. * - OutputCache
  128. * @var null|Storage
  129. */
  130. protected $storage;
  131. /**
  132. * Constructor
  133. *
  134. * @param array|Traversable|null $options
  135. * @return PatternOptions
  136. * @throws Exception\InvalidArgumentException
  137. */
  138. public function __construct($options = null)
  139. {
  140. // disable file/directory permissions by default on windows systems
  141. if (strtoupper(substr(PHP_OS, 0, 3)) == 'WIN') {
  142. $this->filePermission = false;
  143. $this->dirPermission = false;
  144. }
  145. parent::__construct($options);
  146. }
  147. /**
  148. * Set flag indicating whether or not to cache by default
  149. *
  150. * Used by:
  151. * - ClassCache
  152. * - ObjectCache
  153. *
  154. * @param bool $cacheByDefault
  155. * @return PatternOptions
  156. */
  157. public function setCacheByDefault($cacheByDefault)
  158. {
  159. $this->cacheByDefault = $cacheByDefault;
  160. return $this;
  161. }
  162. /**
  163. * Do we cache by default?
  164. *
  165. * Used by:
  166. * - ClassCache
  167. * - ObjectCache
  168. *
  169. * @return bool
  170. */
  171. public function getCacheByDefault()
  172. {
  173. return $this->cacheByDefault;
  174. }
  175. /**
  176. * Set whether or not to cache output
  177. *
  178. * Used by:
  179. * - CallbackCache
  180. * - ClassCache
  181. * - ObjectCache
  182. *
  183. * @param bool $cacheOutput
  184. * @return PatternOptions
  185. */
  186. public function setCacheOutput($cacheOutput)
  187. {
  188. $this->cacheOutput = (bool) $cacheOutput;
  189. return $this;
  190. }
  191. /**
  192. * Will we cache output?
  193. *
  194. * Used by:
  195. * - CallbackCache
  196. * - ClassCache
  197. * - ObjectCache
  198. *
  199. * @return bool
  200. */
  201. public function getCacheOutput()
  202. {
  203. return $this->cacheOutput;
  204. }
  205. /**
  206. * Set class name
  207. *
  208. * Used by:
  209. * - ClassCache
  210. *
  211. * @param string $class
  212. * @throws Exception\InvalidArgumentException
  213. * @return PatternOptions
  214. */
  215. public function setClass($class)
  216. {
  217. if (!is_string($class)) {
  218. throw new Exception\InvalidArgumentException('Invalid classname provided; must be a string');
  219. }
  220. $this->class = $class;
  221. return $this;
  222. }
  223. /**
  224. * Get class name
  225. *
  226. * Used by:
  227. * - ClassCache
  228. *
  229. * @return null|string
  230. */
  231. public function getClass()
  232. {
  233. return $this->class;
  234. }
  235. /**
  236. * Set list of method return values to cache
  237. *
  238. * Used by:
  239. * - ClassCache
  240. *
  241. * @param array $classCacheMethods
  242. * @return PatternOptions
  243. */
  244. public function setClassCacheMethods(array $classCacheMethods)
  245. {
  246. $this->classCacheMethods = $this->recursiveStrtolower($classCacheMethods);
  247. return $this;
  248. }
  249. /**
  250. * Get list of methods from which to cache return values
  251. *
  252. * Used by:
  253. * - ClassCache
  254. *
  255. * @return array
  256. */
  257. public function getClassCacheMethods()
  258. {
  259. return $this->classCacheMethods;
  260. }
  261. /**
  262. * Set list of method return values NOT to cache
  263. *
  264. * Used by:
  265. * - ClassCache
  266. *
  267. * @param array $classNonCacheMethods
  268. * @return PatternOptions
  269. */
  270. public function setClassNonCacheMethods(array $classNonCacheMethods)
  271. {
  272. $this->classNonCacheMethods = $this->recursiveStrtolower($classNonCacheMethods);
  273. return $this;
  274. }
  275. /**
  276. * Get list of methods from which NOT to cache return values
  277. *
  278. * Used by:
  279. * - ClassCache
  280. *
  281. * @return array
  282. */
  283. public function getClassNonCacheMethods()
  284. {
  285. return $this->classNonCacheMethods;
  286. }
  287. /**
  288. * Set directory permission
  289. *
  290. * @param false|int $dirPermission
  291. * @throws Exception\InvalidArgumentException
  292. * @return PatternOptions
  293. */
  294. public function setDirPermission($dirPermission)
  295. {
  296. if ($dirPermission !== false) {
  297. if (is_string($dirPermission)) {
  298. $dirPermission = octdec($dirPermission);
  299. } else {
  300. $dirPermission = (int) $dirPermission;
  301. }
  302. // validate
  303. if (($dirPermission & 0700) != 0700) {
  304. throw new Exception\InvalidArgumentException(
  305. 'Invalid directory permission: need permission to execute, read and write by owner'
  306. );
  307. }
  308. }
  309. $this->dirPermission = $dirPermission;
  310. return $this;
  311. }
  312. /**
  313. * Gets directory permission
  314. *
  315. * @return false|int
  316. */
  317. public function getDirPermission()
  318. {
  319. return $this->dirPermission;
  320. }
  321. /**
  322. * Set umask
  323. *
  324. * Used by:
  325. * - CaptureCache
  326. *
  327. * @param false|int $umask
  328. * @throws Exception\InvalidArgumentException
  329. * @return PatternOptions
  330. */
  331. public function setUmask($umask)
  332. {
  333. if ($umask !== false) {
  334. if (is_string($umask)) {
  335. $umask = octdec($umask);
  336. } else {
  337. $umask = (int) $umask;
  338. }
  339. // validate
  340. if ($umask & 0700) {
  341. throw new Exception\InvalidArgumentException(
  342. 'Invalid umask: need permission to execute, read and write by owner'
  343. );
  344. }
  345. // normalize
  346. $umask = $umask & 0777;
  347. }
  348. $this->umask = $umask;
  349. return $this;
  350. }
  351. /**
  352. * Get umask
  353. *
  354. * Used by:
  355. * - CaptureCache
  356. *
  357. * @return false|int
  358. */
  359. public function getUmask()
  360. {
  361. return $this->umask;
  362. }
  363. /**
  364. * Set whether or not file locking should be used
  365. *
  366. * Used by:
  367. * - CaptureCache
  368. *
  369. * @param bool $fileLocking
  370. * @return PatternOptions
  371. */
  372. public function setFileLocking($fileLocking)
  373. {
  374. $this->fileLocking = (bool) $fileLocking;
  375. return $this;
  376. }
  377. /**
  378. * Is file locking enabled?
  379. *
  380. * Used by:
  381. * - CaptureCache
  382. *
  383. * @return bool
  384. */
  385. public function getFileLocking()
  386. {
  387. return $this->fileLocking;
  388. }
  389. /**
  390. * Set file permission
  391. *
  392. * @param false|int $filePermission
  393. * @throws Exception\InvalidArgumentException
  394. * @return PatternOptions
  395. */
  396. public function setFilePermission($filePermission)
  397. {
  398. if ($filePermission !== false) {
  399. if (is_string($filePermission)) {
  400. $filePermission = octdec($filePermission);
  401. } else {
  402. $filePermission = (int) $filePermission;
  403. }
  404. // validate
  405. if (($filePermission & 0600) != 0600) {
  406. throw new Exception\InvalidArgumentException(
  407. 'Invalid file permission: need permission to read and write by owner'
  408. );
  409. } elseif ($filePermission & 0111) {
  410. throw new Exception\InvalidArgumentException(
  411. "Invalid file permission: Files shoudn't be executable"
  412. );
  413. }
  414. }
  415. $this->filePermission = $filePermission;
  416. return $this;
  417. }
  418. /**
  419. * Gets file permission
  420. *
  421. * @return false|int
  422. */
  423. public function getFilePermission()
  424. {
  425. return $this->filePermission;
  426. }
  427. /**
  428. * Set value for index filename
  429. *
  430. * @param string $indexFilename
  431. * @return PatternOptions
  432. */
  433. public function setIndexFilename($indexFilename)
  434. {
  435. $this->indexFilename = (string) $indexFilename;
  436. return $this;
  437. }
  438. /**
  439. * Get value for index filename
  440. *
  441. * @return string
  442. */
  443. public function getIndexFilename()
  444. {
  445. return $this->indexFilename;
  446. }
  447. /**
  448. * Set object to cache
  449. *
  450. * @param mixed $object
  451. * @throws Exception\InvalidArgumentException
  452. * @return $this
  453. */
  454. public function setObject($object)
  455. {
  456. if (!is_object($object)) {
  457. throw new Exception\InvalidArgumentException(sprintf(
  458. '%s expects an object; received "%s"', __METHOD__, gettype($object)
  459. ));
  460. }
  461. $this->object = $object;
  462. return $this;
  463. }
  464. /**
  465. * Get object to cache
  466. *
  467. * @return null|object
  468. */
  469. public function getObject()
  470. {
  471. return $this->object;
  472. }
  473. /**
  474. * Set flag indicating whether or not to cache magic properties
  475. *
  476. * Used by:
  477. * - ObjectCache
  478. *
  479. * @param bool $objectCacheMagicProperties
  480. * @return PatternOptions
  481. */
  482. public function setObjectCacheMagicProperties($objectCacheMagicProperties)
  483. {
  484. $this->objectCacheMagicProperties = (bool) $objectCacheMagicProperties;
  485. return $this;
  486. }
  487. /**
  488. * Should we cache magic properties?
  489. *
  490. * Used by:
  491. * - ObjectCache
  492. *
  493. * @return bool
  494. */
  495. public function getObjectCacheMagicProperties()
  496. {
  497. return $this->objectCacheMagicProperties;
  498. }
  499. /**
  500. * Set list of object methods for which to cache return values
  501. *
  502. * @param array $objectCacheMethods
  503. * @return PatternOptions
  504. * @throws Exception\InvalidArgumentException
  505. */
  506. public function setObjectCacheMethods(array $objectCacheMethods)
  507. {
  508. $this->objectCacheMethods = $this->normalizeObjectMethods($objectCacheMethods);
  509. return $this;
  510. }
  511. /**
  512. * Get list of object methods for which to cache return values
  513. *
  514. * @return array
  515. */
  516. public function getObjectCacheMethods()
  517. {
  518. return $this->objectCacheMethods;
  519. }
  520. /**
  521. * Set the object key part.
  522. *
  523. * Used to generate a callback key in order to speed up key generation.
  524. *
  525. * Used by:
  526. * - ObjectCache
  527. *
  528. * @param mixed $objectKey
  529. * @return $this
  530. */
  531. public function setObjectKey($objectKey)
  532. {
  533. if ($objectKey !== null) {
  534. $this->objectKey = (string) $objectKey;
  535. } else {
  536. $this->objectKey = null;
  537. }
  538. return $this;
  539. }
  540. /**
  541. * Get object key
  542. *
  543. * Used by:
  544. * - ObjectCache
  545. *
  546. * @return mixed
  547. */
  548. public function getObjectKey()
  549. {
  550. if (!$this->objectKey) {
  551. return get_class($this->getObject());
  552. }
  553. return $this->objectKey;
  554. }
  555. /**
  556. * Set list of object methods for which NOT to cache return values
  557. *
  558. * @param array $objectNonCacheMethods
  559. * @return PatternOptions
  560. * @throws Exception\InvalidArgumentException
  561. */
  562. public function setObjectNonCacheMethods(array $objectNonCacheMethods)
  563. {
  564. $this->objectNonCacheMethods = $this->normalizeObjectMethods($objectNonCacheMethods);
  565. return $this;
  566. }
  567. /**
  568. * Get list of object methods for which NOT to cache return values
  569. *
  570. * @return array
  571. */
  572. public function getObjectNonCacheMethods()
  573. {
  574. return $this->objectNonCacheMethods;
  575. }
  576. /**
  577. * Set location of public directory
  578. *
  579. * Used by:
  580. * - CaptureCache
  581. *
  582. * @param string $publicDir
  583. * @throws Exception\InvalidArgumentException
  584. * @return PatternOptions
  585. */
  586. public function setPublicDir($publicDir)
  587. {
  588. $publicDir = (string) $publicDir;
  589. if (!is_dir($publicDir)) {
  590. throw new Exception\InvalidArgumentException(
  591. "Public directory '{$publicDir}' not found or not a directory"
  592. );
  593. } elseif (!is_writable($publicDir)) {
  594. throw new Exception\InvalidArgumentException(
  595. "Public directory '{$publicDir}' not writable"
  596. );
  597. } elseif (!is_readable($publicDir)) {
  598. throw new Exception\InvalidArgumentException(
  599. "Public directory '{$publicDir}' not readable"
  600. );
  601. }
  602. $this->publicDir = rtrim(realpath($publicDir), \DIRECTORY_SEPARATOR);
  603. return $this;
  604. }
  605. /**
  606. * Get location of public directory
  607. *
  608. * Used by:
  609. * - CaptureCache
  610. *
  611. * @return null|string
  612. */
  613. public function getPublicDir()
  614. {
  615. return $this->publicDir;
  616. }
  617. /**
  618. * Set storage adapter
  619. *
  620. * Required for the following Pattern classes:
  621. * - CallbackCache
  622. * - ClassCache
  623. * - ObjectCache
  624. * - OutputCache
  625. *
  626. * @param string|array|Storage $storage
  627. * @return PatternOptions
  628. */
  629. public function setStorage($storage)
  630. {
  631. $this->storage = $this->storageFactory($storage);
  632. return $this;
  633. }
  634. /**
  635. * Get storage adapter
  636. *
  637. * Used by:
  638. * - CallbackCache
  639. * - ClassCache
  640. * - ObjectCache
  641. * - OutputCache
  642. *
  643. * @return null|Storage
  644. */
  645. public function getStorage()
  646. {
  647. return $this->storage;
  648. }
  649. /**
  650. * Recursively apply strtolower on all values of an array, and return as a
  651. * list of unique values
  652. *
  653. * @param array $array
  654. * @return array
  655. */
  656. protected function recursiveStrtolower(array $array)
  657. {
  658. return array_values(array_unique(array_map('strtolower', $array)));
  659. }
  660. /**
  661. * Normalize object methods
  662. *
  663. * Recursively casts values to lowercase, then determines if any are in a
  664. * list of methods not handled, raising an exception if so.
  665. *
  666. * @param array $methods
  667. * @return array
  668. * @throws Exception\InvalidArgumentException
  669. */
  670. protected function normalizeObjectMethods(array $methods)
  671. {
  672. $methods = $this->recursiveStrtolower($methods);
  673. $intersect = array_intersect(array('__set', '__get', '__unset', '__isset'), $methods);
  674. if (!empty($intersect)) {
  675. throw new Exception\InvalidArgumentException(
  676. "Magic properties are handled by option 'cache_magic_properties'"
  677. );
  678. }
  679. return $methods;
  680. }
  681. /**
  682. * Create a storage object from a given specification
  683. *
  684. * @param array|string|Storage $storage
  685. * @throws Exception\InvalidArgumentException
  686. * @return Storage
  687. */
  688. protected function storageFactory($storage)
  689. {
  690. if (is_array($storage)) {
  691. $storage = StorageFactory::factory($storage);
  692. } elseif (is_string($storage)) {
  693. $storage = StorageFactory::adapterFactory($storage);
  694. } elseif (!($storage instanceof Storage)) {
  695. throw new Exception\InvalidArgumentException(
  696. 'The storage must be an instanceof Zend\Cache\Storage\StorageInterface '
  697. . 'or an array passed to Zend\Cache\Storage::factory '
  698. . 'or simply the name of the storage adapter'
  699. );
  700. }
  701. return $storage;
  702. }
  703. }