/library/Zend/Tool/Framework/Provider/Signature.php
PHP | 388 lines | 210 code | 39 blank | 139 comment | 21 complexity | cdc6e72e5d621abd9adad0e5e87fa762 MD5 | raw file
Possible License(s): BSD-3-Clause
- <?php
- /**
- * Zend Framework
- *
- * LICENSE
- *
- * This source file is subject to the new BSD license that is bundled
- * with this package in the file LICENSE.txt.
- * It is also available through the world-wide-web at this URL:
- * http://framework.zend.com/license/new-bsd
- * If you did not receive a copy of the license and are unable to
- * obtain it through the world-wide-web, please send an email
- * to license@zend.com so we can send you a copy immediately.
- *
- * @category Zend
- * @package Zend_Tool
- * @subpackage Framework
- * @copyright Copyright (c) 2005-2012 Zend Technologies USA Inc. (http://www.zend.com)
- * @license http://framework.zend.com/license/new-bsd New BSD License
- */
- /**
- * @namespace
- */
- namespace Zend\Tool\Framework\Provider;
- use Zend\Tool\Framework\Provider,
- Zend\Tool\Framework\RegistryEnabled;
- /**
- * The purpose of Zend\Tool\Framework\Provider\Signature is to derive
- * callable signatures from the provided provider.
- *
- * @uses \Zend\Code\Reflection\ClassReflection
- * @uses \Zend\Tool\Framework\Action\Base
- * @uses \Zend\Tool\Framework\Provider\Exception
- * @uses \Zend\Tool\Framework\RegistryEnabled
- * @category Zend
- * @package Zend_Tool
- * @copyright Copyright (c) 2005-2012 Zend Technologies USA Inc. (http://www.zend.com)
- * @license http://framework.zend.com/license/new-bsd New BSD License
- */
- class Signature implements RegistryEnabled
- {
- /**
- * @var \Zend\Tool\Framework\Registry
- */
- protected $_registry = null;
- /**
- * @var \Zend\Tool\Framework\Provider
- */
- protected $_provider = null;
- /**
- * @var string
- */
- protected $_name = null;
- /**
- * @var array
- */
- protected $_specialties = array();
- /**
- * @var array
- */
- protected $_actionableMethods = array();
- /**
- * @var unknown_type
- */
- protected $_actions = array();
- /**
- * @var \Zend\Code\Reflection\ClassReflection
- */
- protected $_providerReflection = null;
- /**
- * @var bool
- */
- protected $_isProcessed = false;
- /**
- * Constructor
- *
- * @param \Zend\Tool\Framework\Provider $provider
- */
- public function __construct(Provider $provider)
- {
- $this->_provider = $provider;
- $this->_providerReflection = new \Zend\Code\Reflection\ClassReflection($provider);
- }
- /**
- * setRegistry()
- *
- * @param \Zend\Tool\Framework\Registry $registry
- * @return \Zend\Tool\Framework\Provider\Signature
- */
- public function setRegistry(\Zend\Tool\Framework\Registry $registry)
- {
- $this->_registry = $registry;
- return $this;
- }
- public function process()
- {
- if ($this->_isProcessed) {
- return;
- }
- $this->_process();
- }
- /**
- * getName() of the provider
- *
- * @return string
- */
- public function getName()
- {
- return $this->_name;
- }
- /**
- * Get the provider for this signature
- *
- * @return \Zend\Tool\Framework\Provider
- */
- public function getProvider()
- {
- return $this->_provider;
- }
- /**
- * getProviderReflection()
- *
- * @return \Zend\Code\Reflection\ClassReflection
- */
- public function getProviderReflection()
- {
- return $this->_providerReflection;
- }
- /**
- * getSpecialities()
- *
- * @return array
- */
- public function getSpecialties()
- {
- return $this->_specialties;
- }
- /**
- * getActions()
- *
- * @return array Array of Actions
- */
- public function getActions()
- {
- return $this->_actions;
- }
- /**
- * getActionableMethods()
- *
- * @return array
- */
- public function getActionableMethods()
- {
- return $this->_actionableMethods;
- }
- /**
- * getActionableMethod() - Get an actionable method by name, this will return an array of
- * useful information about what can be exectued on this provider
- *
- * @param string $methodName
- * @return array
- */
- public function getActionableMethod($methodName)
- {
- if (isset($this->_actionableMethods[$methodName])) {
- return $this->_actionableMethods[$methodName];
- }
- return false;
- }
- /**
- * getActionableMethodByActionName() - Get an actionable method by its action name, this
- * will return an array of useful information about what can be exectued on this provider
- *
- * @param string $actionName
- * @return array
- */
- public function getActionableMethodByActionName($actionName, $specialtyName = '_Global')
- {
- foreach ($this->_actionableMethods as $actionableMethod) {
- if ($actionName == $actionableMethod['actionName']
- && $specialtyName == $actionableMethod['specialty']) {
- return $actionableMethod;
- }
- }
- return false;
- }
- /**
- * _process() is called at construction time and is what will build the signature information
- * for determining what is actionable
- *
- */
- protected function _process()
- {
- $this->_isProcessed = true;
- $this->_processName();
- $this->_processSpecialties();
- $this->_processActionableMethods();
- }
- /**
- * _processName();
- *
- */
- protected function _processName()
- {
- if (method_exists($this->_provider, 'getName')) {
- $this->_name = $this->_provider->getName();
- }
- if ($this->_name == null) {
- $className = get_class($this->_provider);
- $name = $className;
- if (strpos($name, '_')) {
- $name = substr($name, strrpos($name, '_')+1);
- }
- $name = substr($className, strrpos($className, '\\')+1);
- $name = preg_replace('#(Provider|Manifest)$#', '', $name);
- $this->_name = $name;
- }
- }
- /**
- * _processSpecialties() - Break out the specialty names for this provider
- *
- */
- protected function _processSpecialties()
- {
- $specialties = array();
- if ($this->_providerReflection->hasMethod('getSpecialties')) {
- $specialties = $this->_provider->getSpecialties();
- if (!is_array($specialties)) {
- throw new Exception\RuntimeException(
- 'Provider ' . get_class($this->_provider) . ' must return an array for method getSpecialties().'
- );
- }
- } else {
- $defaultProperties = $this->_providerReflection->getDefaultProperties();
- $specialties = (isset($defaultProperties['_specialties'])) ? $defaultProperties['_specialties'] : array();
- if (!is_array($specialties)) {
- throw new Exception\RuntimeException(
- 'Provider ' . get_class($this->_provider) . '\'s property $_specialties must be an array.'
- );
- }
- }
- $this->_specialties = array_merge(array('_Global'), $specialties);
- }
- /**
- * _processActionableMethods() - process all methods that can be called on this provider.
- *
- */
- protected function _processActionableMethods()
- {
- $specialtyRegex = '#(.*)(' . implode('|', $this->_specialties) . ')$#i';
- $methods = $this->_providerReflection->getMethods();
- $actionableMethods = array();
- foreach ($methods as $method) {
- $methodName = $method->getName();
- /**
- * the following will determine what methods are actually actionable
- * public, non-static, non-underscore prefixed, classes that dont
- * contain the name "
- */
- if (!$method->getDeclaringClass()->isInstantiable()
- || !$method->isPublic()
- || $methodName[0] == '_'
- || $method->isStatic()
- || in_array($methodName, array('getContextClasses', 'getName')) // other protected public methods will nee to go here
- ) {
- continue;
- }
- /**
- * check to see if the method was a required method by a Zend\Tool\* interface
- */
- foreach ($method->getDeclaringClass()->getInterfaces() as $methodDeclaringClassInterface) {
- if (strpos($methodDeclaringClassInterface->getName(), 'Zend\\Tool\\') === 0
- && $methodDeclaringClassInterface->hasMethod($methodName)) {
- continue 2;
- }
- }
- $actionableName = ucfirst($methodName);
- if (substr($actionableName, -6) == 'Action') {
- $actionableName = substr($actionableName, 0, -6);
- }
- $actionableMethods[$methodName]['methodName'] = $methodName;
- $matches = null;
- if (preg_match($specialtyRegex, $actionableName, $matches)) {
- $actionableMethods[$methodName]['actionName'] = $matches[1];
- $actionableMethods[$methodName]['specialty'] = $matches[2];
- } else {
- $actionableMethods[$methodName]['actionName'] = $actionableName;
- $actionableMethods[$methodName]['specialty'] = '_Global';
- }
- // get the action, and create non-existent actions when they dont exist (the true part below)
- $action = $this->_registry->getActionRepository()->getAction($actionableMethods[$methodName]['actionName']);
- if ($action == null) {
- $action = new \Zend\Tool\Framework\Action\Base($actionableMethods[$methodName]['actionName']);
- $this->_registry->getActionRepository()->addAction($action);
- }
- $actionableMethods[$methodName]['action'] = $action;
- if (!in_array($actionableMethods[$methodName]['action'], $this->_actions)) {
- $this->_actions[] = $actionableMethods[$methodName]['action'];
- }
- $parameterInfo = array();
- $position = 1;
- foreach ($method->getParameters() as $parameter) {
- $currentParam = $parameter->getName();
- $parameterInfo[$currentParam]['position'] = $position++;
- $parameterInfo[$currentParam]['optional'] = $parameter->isOptional();
- $parameterInfo[$currentParam]['default'] = ($parameter->isOptional()) ? $parameter->getDefaultValue() : null;
- $parameterInfo[$currentParam]['name'] = $currentParam;
- $parameterInfo[$currentParam]['type'] = 'string';
- $parameterInfo[$currentParam]['description'] = null;
- }
- $matches = null;
- if (($docComment = $method->getDocComment()) != '' &&
- (preg_match_all('/@param\s+(\w+)+\s+(\$\S+)\s+(.*?)(?=(?:\*\s*@)|(?:\*\/))/s', $docComment, $matches)))
- {
- for ($i=0; $i <= count($matches[0])-1; $i++) {
- $currentParam = ltrim($matches[2][$i], '$');
- if ($currentParam != '' && isset($parameterInfo[$currentParam])) {
- $parameterInfo[$currentParam]['type'] = $matches[1][$i];
- $descriptionSource = $matches[3][$i];
- if ($descriptionSource != '') {
- $parameterInfo[$currentParam]['description'] = trim($descriptionSource);
- }
- }
- }
- }
- $actionableMethods[$methodName]['parameterInfo'] = $parameterInfo;
- }
- $this->_actionableMethods = $actionableMethods;
- }
- }