Completed
Push — master ( b4adf1...7cbf62 )
by Marc
02:01
created

ViewHelperInvoker   A

Complexity

Total Complexity 10

Size/Duplication

Total Lines 55
Duplicated Lines 0 %

Coupling/Cohesion

Components 0
Dependencies 6

Importance

Changes 0
Metric Value
dl 0
loc 55
c 0
b 0
f 0
rs 10
wmc 10
lcom 0
cbo 6

1 Method

Rating   Name   Duplication   Size   Complexity  
F invoke() 0 41 10
1
<?php
2
namespace TYPO3Fluid\Fluid\Core\ViewHelper;
3
4
/*
5
 * This file belongs to the package "TYPO3 Fluid".
6
 * See LICENSE.txt that was shipped with this package.
7
 */
8
9
use TYPO3Fluid\Fluid\Core\Parser\SyntaxTree\NodeInterface;
10
use TYPO3Fluid\Fluid\Core\Rendering\RenderingContextInterface;
11
12
/**
13
 * Class ViewHelperInvoker
14
 *
15
 * Class which is responsible for calling the render methods
16
 * on ViewHelpers, and this alone.
17
 *
18
 * Can be replaced via the ViewHelperResolver if the system
19
 * that implements Fluid requires special handling of classes.
20
 * This includes for example when you want to validate arguments
21
 * differently, wish to use another ViewHelper initialization
22
 * process, or wish to store instances of ViewHelpers to reuse
23
 * as if they were Singletons.
24
 *
25
 * To override the instantiation process and class name resolving,
26
 * see ViewHelperResolver. This particular class should only be
27
 * responsible for invoking the render method of a ViewHelper
28
 * using the properties available in the node.
29
 */
30
class ViewHelperInvoker
31
{
32
33
    /**
34
     * Invoke the ViewHelper described by the ViewHelperNode, the properties
35
     * of which will already have been filled by the ViewHelperResolver.
36
     *
37
     * @param string|ViewHelperInterface $viewHelperClassNameOrInstance
38
     * @param array $arguments
39
     * @param RenderingContextInterface $renderingContext
40
     * @param null|\Closure $renderChildrenClosure
41
     * @return string
42
     */
43
    public function invoke($viewHelperClassNameOrInstance, array $arguments, RenderingContextInterface $renderingContext, \Closure $renderChildrenClosure = null)
44
    {
45
        $viewHelperResolver = $renderingContext->getViewHelperResolver();
46
        if ($viewHelperClassNameOrInstance instanceof ViewHelperInterface) {
47
            $viewHelper = $viewHelperClassNameOrInstance;
48
        } else {
49
            $viewHelper = $viewHelperResolver->createViewHelperInstanceFromClassName($viewHelperClassNameOrInstance);
50
        }
51
        $expectedViewHelperArguments = $viewHelperResolver->getArgumentDefinitionsForViewHelper($viewHelper);
52
53
        // Rendering process
54
        $evaluatedArguments = [];
55
        $undeclaredArguments = [];
56
57
        try {
58
            foreach ($expectedViewHelperArguments as $argumentName => $argumentDefinition) {
59
                if (isset($arguments[$argumentName])) {
60
                    /** @var NodeInterface|mixed $argumentValue */
61
                    $argumentValue = $arguments[$argumentName];
62
                    $evaluatedArguments[$argumentName] = $argumentValue instanceof NodeInterface ? $argumentValue->evaluate($renderingContext) : $argumentValue;
63
                } else {
64
                    $evaluatedArguments[$argumentName] = $argumentDefinition->getDefaultValue();
65
                }
66
            }
67
            foreach ($arguments as $argumentName => $argumentValue) {
68
                if (!array_key_exists($argumentName, $evaluatedArguments)) {
69
                    $undeclaredArguments[$argumentName] = $argumentValue instanceof NodeInterface ? $argumentValue->evaluate($renderingContext) : $argumentValue;
70
                }
71
            }
72
73
            if ($renderChildrenClosure) {
74
                $viewHelper->setRenderChildrenClosure($renderChildrenClosure);
75
            }
76
            $viewHelper->setRenderingContext($renderingContext);
77
            $viewHelper->setArguments($evaluatedArguments);
78
            $viewHelper->handleAdditionalArguments($undeclaredArguments);
79
            return $viewHelper->initializeArgumentsAndRender();
80
        } catch (Exception $error) {
81
            return $renderingContext->getErrorHandler()->handleViewHelperError($error);
82
        }
83
    }
84
}
85