Source for file PresenterHelpers.php

Documentation is available at PresenterHelpers.php

  1. 1: <?php
  2. 2:  
  3. 3: /**
  4. 4:  * Nette Framework
  5. 5:  *
  6. 6:  * Copyright (c) 2004, 2009 David Grudl (http://davidgrudl.com)
  7. 7:  *
  8. 8:  * This source file is subject to the "Nette license" that is bundled
  9. 9:  * with this package in the file license.txt.
  10. 10:  *
  11. 11:  * For more information please see http://nettephp.com
  12. 12:  *
  13. 13:  * @copyright  Copyright (c) 2004, 2009 David Grudl
  14. 14:  * @license    http://nettephp.com/license  Nette license
  15. 15:  * @link       http://nettephp.com
  16. 16:  * @category   Nette
  17. 17:  * @package    Nette\Application
  18. 18:  */
  19. 19:  
  20. 20:  
  21. 21:  
  22. 22: /**
  23. 23:  * Helpers for Presenter & PresenterComponent.
  24. 24:  *
  25. 25:  * @author     David Grudl
  26. 26:  * @copyright  Copyright (c) 2004, 2009 David Grudl
  27. 27:  * @package    Nette\Application
  28. 28:  * @ignore internal
  29. 29:  */
  30. 30: final class PresenterHelpers
  31. 31: {
  32. 32:     /** @var array getPersistentParams cache */
  33. 33:     private static $ppCache array();
  34. 34:  
  35. 35:     /** @var array getPersistentComponents cache */
  36. 36:     private static $pcCache array();
  37. 37:  
  38. 38:     /** @var array isMethodCallable cache */
  39. 39:     private static $mcCache array();
  40. 40:  
  41. 41:     /** @var array getMethodParams cache */
  42. 42:     private static $mpCache array();
  43. 43:  
  44. 44:  
  45. 45:  
  46. 46:     /**
  47. 47:      * Static class - cannot be instantiated.
  48. 48:      */
  49. 49:     final public function __construct()
  50. 50:     {
  51. 51:         throw new LogicException("Cannot instantiate static class " get_class($this));
  52. 52:     }
  53. 53:  
  54. 54:  
  55. 55:  
  56. 56:     /**
  57. 57:      * Returns array of classes persistent parameters.
  58. 58:      * @param  string  class name
  59. 59:      * @return array 
  60. 60:      */
  61. 61:     public static function getPersistentParams($class)
  62. 62:     {
  63. 63:         $params self::$ppCache[$class];
  64. 64:         if ($params !== NULLreturn $params;
  65. 65:         $params array();
  66. 66:         if (is_subclass_of($class'PresenterComponent')) {
  67. 67:             // $class::getPersistentParams() in PHP 5.3
  68. 68:             $defaults get_class_vars($class);
  69. 69:             foreach (call_user_func(array($class'getPersistentParams')$classas $name => $meta{
  70. 70:                 if (is_string($meta)) $name $meta;
  71. 71:                 $params[$namearray(
  72. 72:                     'def' => $defaults[$name],
  73. 73:                     'since' => $class,
  74. 74:                 );
  75. 75:             }
  76. 76:             $params self::getPersistentParams(get_parent_class($class)) $params;
  77. 77:         }
  78. 78:         return $params;
  79. 79:     }
  80. 80:  
  81. 81:  
  82. 82:  
  83. 83:     /**
  84. 84:      * Returns array of classes persistent components.
  85. 85:      * @param  string  class name
  86. 86:      * @return array 
  87. 87:      */
  88. 88:     public static function getPersistentComponents($class)
  89. 89:     {
  90. 90:         $components self::$pcCache[$class];
  91. 91:         if ($components !== NULLreturn $components;
  92. 92:         $components array();
  93. 93:         if (is_subclass_of($class'Presenter')) {
  94. 94:             // $class::getPersistentComponents() in PHP 5.3
  95. 95:             foreach (call_user_func(array($class'getPersistentComponents')$classas $name => $meta{
  96. 96:                 if (is_string($meta)) $name $meta;
  97. 97:                 $components[$namearray('since' => $class);
  98. 98:             }
  99. 99:             $components self::getPersistentComponents(get_parent_class($class)) $components;
  100. 100:         }
  101. 101:         return $components;
  102. 102:     }
  103. 103:  
  104. 104:  
  105. 105:  
  106. 106:     /**
  107. 107:      * Is a method callable? It means class is instantiable and method has
  108. 108:      * public visibility, is non-static and non-abstract.
  109. 109:      * @param  string  class name
  110. 110:      * @param  string  method name
  111. 111:      * @return bool 
  112. 112:      */
  113. 113:     public static function isMethodCallable($class$method)
  114. 114:     {
  115. 115:         $cache self::$mcCache[strtolower($class ':' $method)];
  116. 116:         if ($cache !== NULLreturn $cache;
  117. 117:  
  118. 118:         try {
  119. 119:             $cache FALSE;
  120. 120:             // check class
  121. 121:             $rc new ReflectionClass($class);
  122. 122:             if (!$rc->isInstantiable()) {
  123. 123:                 return FALSE;
  124. 124:             }
  125. 125:  
  126. 126:             // check method
  127. 127:             $rm $rc->getMethod($method);
  128. 128:             if (!$rm || !$rm->isPublic(|| $rm->isAbstract(|| $rm->isStatic()) {
  129. 129:                 return FALSE;
  130. 130:             }
  131. 131:  
  132. 132:             return $cache TRUE;
  133. 133:  
  134. 134:         catch (ReflectionException $e{
  135. 135:             return FALSE;
  136. 136:         }
  137. 137:     }
  138. 138:  
  139. 139:  
  140. 140:  
  141. 141:     /**
  142. 142:      * Converts named parameters to list of arguments.
  143. 143:      * Used by PresenterComponent::tryCall()
  144. 144:      * @param  string  class name
  145. 145:      * @param  string  method name
  146. 146:      * @param  array   parameters - associative array
  147. 147:      * @return array   arguments  - list
  148. 148:      */
  149. 149:     public static function paramsToArgs($class$method$params)
  150. 150:     {
  151. 151:         $args array();
  152. 152:         $i 0;
  153. 153:         foreach (self::getMethodParams($class$methodas $name => $def{
  154. 154:             if (isset($params[$name])) // NULL treats as none value
  155. 155:                 $val $params[$name];
  156. 156:                 if ($def !== NULL{
  157. 157:                     settype($valgettype($def));
  158. 158:                 }
  159. 159:                 $args[$i++$val;
  160. 160:             else {
  161. 161:                 $args[$i++$def;
  162. 162:             }
  163. 163:         }
  164. 164:  
  165. 165:         return $args;
  166. 166:     }
  167. 167:  
  168. 168:  
  169. 169:  
  170. 170:     /**
  171. 171:      * Converts list of arguments to named parameters.
  172. 172:      * Used by Presenter::createRequest() & PresenterComponent::link()
  173. 173:      * @param  string  class name
  174. 174:      * @param  string  method name
  175. 175:      * @param  array   arguments
  176. 176:      * @param  array   supplemental arguments
  177. 177:      * @return void 
  178. 178:      * @throws InvalidLinkException
  179. 179:      */
  180. 180:     public static function argsToParams($class$method$args$supplemental array())
  181. 181:     {
  182. 182:         $i 0;
  183. 183:         foreach (self::getMethodParams($class$methodas $name => $def{
  184. 184:             if (array_key_exists($i$args)) {
  185. 185:                 $args[$name$args[$i];
  186. 186:                 unset($args[$i]);
  187. 187:                 $i++;
  188. 188:  
  189. 189:             elseif (array_key_exists($name$args)) {
  190. 190:                 // continue with process
  191. 191:  
  192. 192:             elseif (array_key_exists($name$supplemental)) {
  193. 193:                 $args[$name$supplemental[$name];
  194. 194:  
  195. 195:             else {
  196. 196:                 continue;
  197. 197:             }
  198. 198:  
  199. 199:             if ($def === NULL{
  200. 200:                 if ((string) $args[$name=== ''$args[$nameNULL// value transmit is unnecessary
  201. 201:             else {
  202. 202:                 settype($args[$name]gettype($def));
  203. 203:                 if ($args[$name=== $def$args[$nameNULL;
  204. 204:             }
  205. 205:         }
  206. 206:  
  207. 207:         if (array_key_exists($i$args)) {
  208. 208:             throw new InvalidLinkException("Extra parameter for signal '$class:$method'.");
  209. 209:         }
  210. 210:     }
  211. 211:  
  212. 212:  
  213. 213:  
  214. 214:     /**
  215. 215:      * Returns array of methods parameters and theirs default values.
  216. 216:      * @param  string  class name
  217. 217:      * @param  string  method name
  218. 218:      * @return array 
  219. 219:      */
  220. 220:     private static function getMethodParams($class$method)
  221. 221:     {
  222. 222:         $cache self::$mpCache[strtolower($class ':' $method)];
  223. 223:         if ($cache !== NULLreturn $cache;
  224. 224:         $rm new ReflectionMethod($class$method);
  225. 225:         $cache array();
  226. 226:         foreach ($rm->getParameters(as $param{
  227. 227:             $cache[$param->getName()$param->isDefaultValueAvailable()
  228. 228:                 ? $param->getDefaultValue()
  229. 229:                 : NULL;
  230. 230:         }
  231. 231:         return $cache;
  232. 232:     }
  233. 233: