/**
  * Checks if the specified method matches with the method annotation filter pattern
  *
  * @param string $className Name of the class to check against - not used here
  * @param string $methodName Name of the method
  * @param string $methodDeclaringClassName Name of the class the method was originally declared in
  * @param mixed $pointcutQueryIdentifier Some identifier for this query - must at least differ from a previous identifier. Used for circular reference detection - not used here
  * @return boolean TRUE if the class matches, otherwise FALSE
  */
 public function matches($className, $methodName, $methodDeclaringClassName, $pointcutQueryIdentifier)
 {
     if ($methodDeclaringClassName === NULL || !method_exists($methodDeclaringClassName, $methodName)) {
         return FALSE;
     }
     return $this->reflectionService->getMethodAnnotations($methodDeclaringClassName, $methodName, $this->annotation) !== array();
 }
示例#2
0
 /**
  * Add the Annotated Method to the Navigation
  *
  * @param \TYPO3\FLOW3\AOP\JoinPointInterface $joinPoint
  * @FLOW3\Before("method(public .*\Controller\.*Controller->.*Action(.*))")
  * @return void
  */
 public function addNavigationitem(\TYPO3\FLOW3\AOP\JoinPointInterface $joinPoint)
 {
     $currentClassName = $joinPoint->getClassName();
     $currentMethodName = $joinPoint->getMethodName();
     $controllers = $this->reflectionService->getAllSubClassNamesForClass("\\TYPO3\\FLOW3\\MVC\\Controller\\ActionController");
     foreach ($controllers as $className) {
         $methods = get_class_methods($className);
         if (is_array($methods)) {
             foreach ($methods as $methodName) {
                 if ($this->reflectionService->isMethodAnnotatedWith($className, $methodName, "Admin\\Annotations\\Navigation")) {
                     $annotations = $this->reflectionService->getMethodAnnotations($className, $methodName, "Admin\\Annotations\\Navigation");
                     foreach ($annotations as $annotation) {
                         $action = str_replace("Action", "", $methodName);
                         $controller = $this->helper->getControllerByClassName($className);
                         $package = $this->objectManager->getPackageKeyByObjectName($className);
                         $arguments = array("action" => $action, "controller" => $controller, "package" => $package);
                         $title = !is_null($annotation->title) ? $annotation->title : sprintf("%s (%s)", $controller, $action);
                         \Admin\Core\API::addNavigationitem($title, $annotation->position, $arguments, $annotation->priority, $annotation->parent);
                     }
                 }
             }
         }
     }
     $settings = $this->helper->getSettings("Admin.Navigation");
     foreach ($settings as $position => $items) {
         foreach ($items as $title => $conf) {
             $priority = isset($conf["priority"]) ? $conf["priority"] : 100;
             $arguments = $conf["Arguments"];
             \Admin\Core\API::addNavigationitem($title, strtolower($position), $arguments, $priority);
         }
     }
 }
示例#3
0
 /**
  * Builds the method documentation block for the specified method keeping the vital annotations
  *
  * @param string $className Name of the class the method is declared in
  * @param string $methodName Name of the method to create the parameters code for
  * @return string $methodDocumentation DocComment for the given method
  */
 protected function buildMethodDocumentation($className, $methodName)
 {
     $methodDocumentation = "\t/**\n\t * Autogenerated Proxy Method\n";
     if ($this->reflectionService->hasMethod($className, $methodName)) {
         $methodTags = $this->reflectionService->getMethodTagsValues($className, $methodName);
         $allowedTags = array('param', 'return', 'throws');
         foreach ($methodTags as $tag => $values) {
             if (in_array($tag, $allowedTags)) {
                 if (count($values) === 0) {
                     $methodDocumentation .= '	 * @' . $tag . "\n";
                 } else {
                     foreach ($values as $value) {
                         $methodDocumentation .= '	 * @' . $tag . ' ' . $value . "\n";
                     }
                 }
             }
         }
         $methodAnnotations = $this->reflectionService->getMethodAnnotations($className, $methodName);
         foreach ($methodAnnotations as $annotation) {
             $methodDocumentation .= '	 * ' . \TYPO3\FLOW3\Object\Proxy\Compiler::renderAnnotation($annotation) . "\n";
         }
     }
     $methodDocumentation .= "\t */\n";
     return $methodDocumentation;
 }
示例#4
0
 /**
  * Detects and registers any validators for arguments:
  * - by the data type specified in the param annotations
  * - additional validators specified in the validate annotations of a method
  *
  * @param string $className
  * @param string $methodName
  * @return array An Array of ValidatorConjunctions for each method parameters.
  * @throws Exception\InvalidValidationConfigurationException
  * @throws Exception\NoSuchValidatorException
  * @throws Exception\InvalidTypeHintException
  */
 public function buildMethodArgumentsValidatorConjunctions($className, $methodName)
 {
     $validatorConjunctions = array();
     $methodParameters = $this->reflectionService->getMethodParameters($className, $methodName);
     if (count($methodParameters) === 0) {
         return $validatorConjunctions;
     }
     foreach ($methodParameters as $parameterName => $methodParameter) {
         $validatorConjunction = $this->createValidator('TYPO3\\FLOW3\\Validation\\Validator\\ConjunctionValidator');
         if (!array_key_exists('type', $methodParameter)) {
             throw new \TYPO3\FLOW3\Validation\Exception\InvalidTypeHintException('Missing type information, probably no @param annotation for parameter "$' . $parameterName . '" in ' . $className . '->' . $methodName . '()', 1281962564);
         }
         if (strpos($methodParameter['type'], '\\') === FALSE) {
             $typeValidator = $this->createValidator($methodParameter['type']);
         } elseif (strpos($methodParameter['type'], '\\Model\\') !== FALSE) {
             $possibleValidatorClassName = str_replace('\\Model\\', '\\Validator\\', $methodParameter['type']) . 'Validator';
             $typeValidator = $this->createValidator($possibleValidatorClassName);
         } else {
             $typeValidator = NULL;
         }
         if ($typeValidator !== NULL) {
             $validatorConjunction->addValidator($typeValidator);
         }
         $validatorConjunctions[$parameterName] = $validatorConjunction;
     }
     $validateAnnotations = $this->reflectionService->getMethodAnnotations($className, $methodName, 'TYPO3\\FLOW3\\Annotations\\Validate');
     foreach ($validateAnnotations as $validateAnnotation) {
         $newValidator = $this->createValidator($validateAnnotation->type, $validateAnnotation->options);
         if ($newValidator === NULL) {
             throw new \TYPO3\FLOW3\Validation\Exception\NoSuchValidatorException('Invalid validate annotation in ' . $className . '->' . $methodName . '(): Could not resolve class name for  validator "' . $validateAnnotation->type . '".', 1239853109);
         }
         if (isset($validatorConjunctions[$validateAnnotation->argumentName])) {
             $validatorConjunctions[$validateAnnotation->argumentName]->addValidator($newValidator);
         } elseif (strpos($validateAnnotation->argumentName, '.') !== FALSE) {
             $objectPath = explode('.', $validateAnnotation->argumentName);
             $argumentName = array_shift($objectPath);
             $validatorConjunctions[$argumentName]->addValidator($this->buildSubObjectValidator($objectPath, $newValidator));
         } else {
             throw new \TYPO3\FLOW3\Validation\Exception\InvalidValidationConfigurationException('Invalid validate annotation in ' . $className . '->' . $methodName . '(): Validator specified for argument name "' . $validateAnnotation->argumentName . '", but this argument does not exist.', 1253172726);
         }
     }
     return $validatorConjunctions;
 }
示例#5
0
 /**
  * Calls the specified action method and passes the arguments.
  *
  * If the action returns a string, it is appended to the content in the
  * response object. If the action doesn't return anything and a valid
  * view exists, the view is rendered automatically.
  *
  * @return void
  */
 protected function callActionMethod()
 {
     $preparedArguments = array();
     foreach ($this->arguments as $argument) {
         $preparedArguments[] = $argument->getValue();
     }
     $validationResult = $this->arguments->getValidationResults();
     if (!$validationResult->hasErrors()) {
         $actionResult = call_user_func_array(array($this, $this->actionMethodName), $preparedArguments);
     } else {
         $ignoreValidationAnnotations = $this->reflectionService->getMethodAnnotations(get_class($this), $this->actionMethodName, 'TYPO3\\FLOW3\\Annotations\\IgnoreValidation');
         $ignoredArguments = array_map(function ($annotation) {
             return $annotation->argumentName;
         }, $ignoreValidationAnnotations);
         // if there exists more errors than in ignoreValidationAnnotations_=> call error method
         // else => call action method
         $shouldCallActionMethod = TRUE;
         foreach ($validationResult->getSubResults() as $argumentName => $subValidationResult) {
             if (!$subValidationResult->hasErrors()) {
                 continue;
             }
             if (array_search($argumentName, $ignoredArguments) !== FALSE) {
                 continue;
             }
             $shouldCallActionMethod = FALSE;
         }
         if ($shouldCallActionMethod) {
             $actionResult = call_user_func_array(array($this, $this->actionMethodName), $preparedArguments);
         } else {
             $actionResult = call_user_func(array($this, $this->errorMethodName));
         }
     }
     if ($actionResult === NULL && $this->view instanceof \TYPO3\FLOW3\Mvc\View\ViewInterface) {
         $this->response->appendContent($this->view->render());
     } elseif (is_string($actionResult) && strlen($actionResult) > 0) {
         $this->response->appendContent($actionResult);
     } elseif (is_object($actionResult) && method_exists($actionResult, '__toString')) {
         $this->response->appendContent((string) $actionResult);
     }
 }
示例#6
0
 /**
  * Creates and returns an aspect from the annotations found in a class which
  * is tagged as an aspect. The object acting as an advice will already be
  * fetched (and therefore instantiated if necessary).
  *
  * @param  string $aspectClassName Name of the class which forms the aspect, contains advices etc.
  * @return mixed The aspect container containing one or more advisors or FALSE if no container could be built
  * @throws \TYPO3\FLOW3\Aop\Exception
  */
 protected function buildAspectContainer($aspectClassName)
 {
     $aspectContainer = new \TYPO3\FLOW3\Aop\AspectContainer($aspectClassName);
     $methodNames = get_class_methods($aspectClassName);
     foreach ($methodNames as $methodName) {
         foreach ($this->reflectionService->getMethodAnnotations($aspectClassName, $methodName) as $annotation) {
             $annotationClass = get_class($annotation);
             switch ($annotationClass) {
                 case 'TYPO3\\FLOW3\\Annotations\\Around':
                     $pointcutFilterComposite = $this->pointcutExpressionParser->parse($annotation->pointcutExpression, $this->renderSourceHint($aspectClassName, $methodName, $annotationClass));
                     $advice = new \TYPO3\FLOW3\Aop\Advice\AroundAdvice($aspectClassName, $methodName);
                     $pointcut = new \TYPO3\FLOW3\Aop\Pointcut\Pointcut($annotation->pointcutExpression, $pointcutFilterComposite, $aspectClassName);
                     $advisor = new \TYPO3\FLOW3\Aop\Advisor($advice, $pointcut);
                     $aspectContainer->addAdvisor($advisor);
                     break;
                 case 'TYPO3\\FLOW3\\Annotations\\Before':
                     $pointcutFilterComposite = $this->pointcutExpressionParser->parse($annotation->pointcutExpression, $this->renderSourceHint($aspectClassName, $methodName, $annotationClass));
                     $advice = new \TYPO3\FLOW3\Aop\Advice\BeforeAdvice($aspectClassName, $methodName);
                     $pointcut = new \TYPO3\FLOW3\Aop\Pointcut\Pointcut($annotation->pointcutExpression, $pointcutFilterComposite, $aspectClassName);
                     $advisor = new \TYPO3\FLOW3\Aop\Advisor($advice, $pointcut);
                     $aspectContainer->addAdvisor($advisor);
                     break;
                 case 'TYPO3\\FLOW3\\Annotations\\AfterReturning':
                     $pointcutFilterComposite = $this->pointcutExpressionParser->parse($annotation->pointcutExpression, $this->renderSourceHint($aspectClassName, $methodName, $annotationClass));
                     $advice = new \TYPO3\FLOW3\Aop\Advice\AfterReturningAdvice($aspectClassName, $methodName);
                     $pointcut = new \TYPO3\FLOW3\Aop\Pointcut\Pointcut($annotation->pointcutExpression, $pointcutFilterComposite, $aspectClassName);
                     $advisor = new \TYPO3\FLOW3\Aop\Advisor($advice, $pointcut);
                     $aspectContainer->addAdvisor($advisor);
                     break;
                 case 'TYPO3\\FLOW3\\Annotations\\AfterThrowing':
                     $pointcutFilterComposite = $this->pointcutExpressionParser->parse($annotation->pointcutExpression, $this->renderSourceHint($aspectClassName, $methodName, $annotationClass));
                     $advice = new \TYPO3\FLOW3\Aop\Advice\AfterThrowingAdvice($aspectClassName, $methodName);
                     $pointcut = new \TYPO3\FLOW3\Aop\Pointcut\Pointcut($annotation->pointcutExpression, $pointcutFilterComposite, $aspectClassName);
                     $advisor = new \TYPO3\FLOW3\Aop\Advisor($advice, $pointcut);
                     $aspectContainer->addAdvisor($advisor);
                     break;
                 case 'TYPO3\\FLOW3\\Annotations\\After':
                     $pointcutFilterComposite = $this->pointcutExpressionParser->parse($annotation->pointcutExpression, $this->renderSourceHint($aspectClassName, $methodName, $annotationClass));
                     $advice = new \TYPO3\FLOW3\Aop\Advice\AfterAdvice($aspectClassName, $methodName);
                     $pointcut = new \TYPO3\FLOW3\Aop\Pointcut\Pointcut($annotation->pointcutExpression, $pointcutFilterComposite, $aspectClassName);
                     $advisor = new \TYPO3\FLOW3\Aop\Advisor($advice, $pointcut);
                     $aspectContainer->addAdvisor($advisor);
                     break;
                 case 'TYPO3\\FLOW3\\Annotations\\Pointcut':
                     $pointcutFilterComposite = $this->pointcutExpressionParser->parse($annotation->expression, $this->renderSourceHint($aspectClassName, $methodName, $annotationClass));
                     $pointcut = new \TYPO3\FLOW3\Aop\Pointcut\Pointcut($annotation->expression, $pointcutFilterComposite, $aspectClassName, $methodName);
                     $aspectContainer->addPointcut($pointcut);
                     break;
             }
         }
     }
     $introduceAnnotation = $this->reflectionService->getClassAnnotation($aspectClassName, 'TYPO3\\FLOW3\\Annotations\\Introduce');
     if ($introduceAnnotation !== NULL) {
         if ($introduceAnnotation->interfaceName === NULL) {
             throw new \TYPO3\FLOW3\Aop\Exception('The interface introduction in class "' . $aspectClassName . '" does not contain the required interface name).', 1172694761);
         }
         $pointcutFilterComposite = $this->pointcutExpressionParser->parse($introduceAnnotation->pointcutExpression, $this->renderSourceHint($aspectClassName, $methodName, 'TYPO3\\FLOW3\\Annotations\\Introduce'));
         $pointcut = new \TYPO3\FLOW3\Aop\Pointcut\Pointcut($introduceAnnotation->pointcutExpression, $pointcutFilterComposite, $aspectClassName);
         $introduction = new \TYPO3\FLOW3\Aop\InterfaceIntroduction($aspectClassName, $introduceAnnotation->interfaceName, $pointcut);
         $aspectContainer->addInterfaceIntroduction($introduction);
     }
     foreach ($this->reflectionService->getClassPropertyNames($aspectClassName) as $propertyName) {
         $introduceAnnotation = $this->reflectionService->getPropertyAnnotation($aspectClassName, $propertyName, 'TYPO3\\FLOW3\\Annotations\\Introduce');
         if ($introduceAnnotation !== NULL) {
             $pointcutFilterComposite = $this->pointcutExpressionParser->parse($introduceAnnotation->pointcutExpression, $this->renderSourceHint($aspectClassName, $propertyName, 'TYPO3\\FLOW3\\Annotations\\Introduce'));
             $pointcut = new \TYPO3\FLOW3\Aop\Pointcut\Pointcut($introduceAnnotation->pointcutExpression, $pointcutFilterComposite, $aspectClassName);
             $introduction = new \TYPO3\FLOW3\Aop\PropertyIntroduction($aspectClassName, $propertyName, $pointcut);
             $aspectContainer->addPropertyIntroduction($introduction);
         }
     }
     if (count($aspectContainer->getAdvisors()) < 1 && count($aspectContainer->getPointcuts()) < 1 && count($aspectContainer->getInterfaceIntroductions()) < 1) {
         throw new \TYPO3\FLOW3\Aop\Exception('The class "' . $aspectClassName . '" is tagged to be an aspect but doesn\'t contain advices nor pointcut or introduction declarations.', 1169124534);
     }
     return $aspectContainer;
 }