File indexing completed on 2024-12-22 05:36:38

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_EventManager
0017  * @copyright  Copyright (c) 2005-2015 Zend Technologies USA Inc. (http://www.zend.com)
0018  * @license    http://framework.zend.com/license/new-bsd     New BSD License
0019  */
0020 
0021 if (version_compare(PHP_VERSION, '5.3.0', '<')) {
0022     class SplStack implements Iterator, ArrayAccess, Countable
0023     {
0024         /**
0025          * Delete items during iteration
0026          */
0027         const IT_MODE_DELETE = 1;
0028 
0029         /**
0030          * Keep items during iteration
0031          */
0032         const IT_MODE_KEEP = 0;
0033 
0034         /**
0035          * Mode used when iterating
0036          * @var int
0037          */
0038         protected $mode = self::IT_MODE_KEEP;
0039 
0040         /**
0041          * Count of elements in the stack 
0042          * 
0043          * @var int
0044          */
0045         protected $count = 0;
0046 
0047         /**
0048          * Data represented by this stack
0049          * 
0050          * @var array
0051          */
0052         protected $data = array();
0053 
0054         /**
0055          * Sorted stack of values
0056          * 
0057          * @var false|array
0058          */
0059         protected $stack = false;
0060 
0061         /**
0062          * Set the iterator mode
0063          *
0064          * Must be set to one of IT_MODE_DELETE or IT_MODE_KEEP
0065          * 
0066          * @todo   Currently, IteratorMode is ignored, as we use the default (keep); should this be implemented?
0067          * @param  int $mode 
0068          * @return void
0069          * @throws InvalidArgumentException
0070          */
0071         public function setIteratorMode($mode)
0072         {
0073             $expected = array(
0074                 self::IT_MODE_DELETE => true,
0075                 self::IT_MODE_KEEP => true,
0076             );
0077 
0078             if (!isset($expected[$mode])) {
0079                 throw new InvalidArgumentException(sprintf('Invalid iterator mode specified ("%s")', $mode));
0080             }
0081 
0082             $this->mode = $mode;
0083         }
0084 
0085         /**
0086          * Return last element in the stack
0087          * 
0088          * @return mixed
0089          */
0090         public function bottom()
0091         {
0092             $this->rewind();
0093             $value = array_pop($this->stack);
0094             array_push($this->stack, $value);
0095             return $value;
0096         }
0097 
0098         /**
0099          * Countable: return count of items in the stack
0100          * 
0101          * @return int
0102          */
0103         public function count()
0104         {
0105             return $this->count;
0106         }
0107 
0108         /**
0109          * Iterator: return current item in the stack
0110          * 
0111          * @return mixed
0112          */
0113         public function current()
0114         {
0115             if (!$this->stack) {
0116                 $this->rewind();
0117             }
0118             return current($this->stack);
0119         }
0120 
0121         /**
0122          * Get iteration mode
0123          * 
0124          * @return int
0125          */
0126         public function getIteratorMode()
0127         {
0128             return $this->mode;
0129         }
0130 
0131         /**
0132          * Is the stack empty?
0133          *
0134          * @return bool
0135          */
0136         public function isEmpty()
0137         {
0138             return ($this->count === 0);
0139         }
0140 
0141         /**
0142          * Iterator: return key of current item in the stack
0143          *
0144          * @return mixed
0145          */
0146         public function key()
0147         {
0148             if (!$this->stack) {
0149                 $this->rewind();
0150             }
0151             return key($this->stack);
0152         }
0153 
0154         /**
0155          * Iterator: advance pointer to next item in the stack
0156          * 
0157          * @return void
0158          */
0159         public function next()
0160         {
0161             if (!$this->stack) {
0162                 $this->rewind();
0163             }
0164             return next($this->stack);
0165         }
0166 
0167         /**
0168          * ArrayAccess: does an item exist at the specified offset?
0169          * 
0170          * @param  mixed $index 
0171          * @return bool
0172          */
0173         public function offsetExists($index)
0174         {
0175             return array_key_exists($index, $this->data);
0176         }
0177 
0178         /**
0179          * ArrayAccess: get the item at the specified offset
0180          * 
0181          * @param  mixed $index 
0182          * @return mixed
0183          * @throws OutOfRangeException
0184          */
0185         public function offsetGet($index)
0186         {
0187             if (!$this->offsetExists($index)) {
0188                 throw OutOfRangeException(sprintf('Invalid index ("%s") specified', $index));
0189             }
0190             return $this->data[$index];
0191         }
0192 
0193         /**
0194          * ArrayAccess: add an item at the specified offset
0195          * 
0196          * @param  mixed $index 
0197          * @param  mixed $newval 
0198          * @return void
0199          */
0200         public function offsetSet($index, $newval)
0201         {
0202             $this->data[$index] = $newval;
0203             $this->stack = false;
0204             $this->count++;
0205         }
0206 
0207         /**
0208          * ArrayAccess: unset the item at the specified offset
0209          * 
0210          * @param  mixed $index 
0211          * @return void
0212          * @throws OutOfRangeException
0213          */
0214         public function offsetUnset($index)
0215         {
0216             if (!$this->offsetExists($index)) {
0217                 throw OutOfRangeException(sprintf('Invalid index ("%s") specified', $index));
0218             }
0219             unset($this->data[$index]);
0220             $this->stack = false;
0221             $this->count--;
0222         }
0223 
0224         /**
0225          * Pop a node from the end of the stack
0226          *
0227          * @return mixed
0228          * @throws RuntimeException
0229          */
0230         public function pop()
0231         {
0232             $val         = array_pop($this->data);
0233             $this->stack = false;
0234             $this->count--;
0235             return $val;
0236         }
0237 
0238         /**
0239          * Move the iterator to the previous node
0240          *
0241          * @todo   Does this need to be implemented?
0242          * @return void
0243          */
0244         public function prev()
0245         {
0246         }
0247 
0248         /**
0249          * Push an element to the list
0250          * 
0251          * @param  mixed $value 
0252          * @return void
0253          */
0254         public function push($value)
0255         {
0256             array_push($this->data, $value);
0257             $this->count++;
0258             $this->stack  = false;
0259         }
0260 
0261         /**
0262          * Iterator: rewind to beginning of stack
0263          * 
0264          * @return void
0265          */
0266         public function rewind()
0267         {
0268             if (is_array($this->stack)) {
0269                 return reset($this->stack);
0270             }
0271             $this->stack = array_reverse($this->data, true);
0272         }
0273 
0274         /**
0275          * Serialize the storage
0276          *
0277          * @return string
0278          */
0279         public function serialize()
0280         {
0281             return serialize($this->data);
0282         }
0283 
0284         /**
0285          * Shifts a node from the beginning of the list
0286          *
0287          * @return mixed
0288          * @throws RuntimeException
0289          */
0290         public function shift()
0291         {
0292             $val         = array_shift($this->data);
0293             $this->stack = false;
0294             $this->count--;
0295             return $val;
0296         }
0297 
0298         /**
0299          * Peek at the top node of the stack
0300          * 
0301          * @return mixed
0302          */
0303         public function top()
0304         {
0305             $this->rewind();
0306             $value = array_shift($this->stack);
0307             array_unshift($this->stack, $value);
0308             return $value;
0309         }
0310 
0311         /**
0312          * Unserialize the storage
0313          *
0314          * @param  string
0315          * @return void
0316          */
0317         public function unserialize($serialized)
0318         {
0319             $this->data  = unserialize($serialized);
0320             $this->stack = false;
0321         }
0322 
0323         /**
0324          * Unshift a node onto the beginning of the list
0325          *
0326          * @param  mixed $value
0327          * @return void
0328          */
0329         public function unshift($value)
0330         {
0331             array_unshift($this->data, $value);
0332             $this->count++;
0333             $this->stack  = false;
0334         }
0335         
0336         /**
0337          * Iterator: is the current pointer valid?
0338          *
0339          * @return bool
0340          */
0341         public function valid()
0342         {
0343             $key = key($this->stack);
0344             $var = ($key !== null && $key !== false);
0345             return $var;
0346         }
0347     }
0348 }
0349 
0350 /**
0351  * Collection of signal handler return values
0352  *
0353  * @category   Zend
0354  * @package    Zend_EventManager
0355  * @copyright  Copyright (c) 2005-2015 Zend Technologies USA Inc. (http://www.zend.com)
0356  * @license    http://framework.zend.com/license/new-bsd     New BSD License
0357  */
0358 class Zend_EventManager_ResponseCollection extends SplStack 
0359 {
0360     protected $stopped = false;
0361 
0362     /**
0363      * Did the last response provided trigger a short circuit of the stack?
0364      * 
0365      * @return bool
0366      */
0367     public function stopped()
0368     {
0369         return $this->stopped;
0370     }
0371 
0372     /**
0373      * Mark the collection as stopped (or its opposite)
0374      * 
0375      * @param  bool $flag 
0376      * @return Zend_EventManager_ResponseCollection
0377      */
0378     public function setStopped($flag)
0379     {
0380         $this->stopped = (bool) $flag;
0381         return $this;
0382     }
0383 
0384     /**
0385      * Convenient access to the first handler return value.
0386      *
0387      * @return mixed The first handler return value
0388      */
0389     public function first()
0390     {
0391         return parent::bottom();
0392     }
0393 
0394     /**
0395      * Convenient access to the last handler return value.
0396      *
0397      * If the collection is empty, returns null. Otherwise, returns value
0398      * returned by last handler.
0399      *
0400      * @return mixed The last handler return value
0401      */
0402     public function last()
0403     {
0404         if (count($this) === 0) {
0405             return null;
0406         }
0407         return parent::top();
0408     }
0409 
0410     /**
0411      * Check if any of the responses match the given value.
0412      *
0413      * @param  mixed $value The value to look for among responses
0414      */
0415     public function contains($value)
0416     {
0417         foreach ($this as $response) {
0418             if ($response === $value) {
0419                 return true;
0420             }
0421         }
0422         return false;
0423     }
0424 }