0a20671efe9ccf884d333a2dd42232ebee0a288a
[Packages/TYPO3.CMS.git] / typo3 / sysext / extbase / Classes / Service / ExtensionService.php
1 <?php
2 namespace TYPO3\CMS\Extbase\Service;
3
4 /*
5 * This file is part of the TYPO3 CMS project.
6 *
7 * It is free software; you can redistribute it and/or modify it under
8 * the terms of the GNU General Public License, either version 2
9 * of the License, or any later version.
10 *
11 * For the full copyright and license information, please read the
12 * LICENSE.txt file that was distributed with this source code.
13 *
14 * The TYPO3 project - inspiring people to share!
15 */
16
17 /**
18 * Service for determining basic extension params
19 */
20 class ExtensionService implements \TYPO3\CMS\Core\SingletonInterface
21 {
22 const PLUGIN_TYPE_PLUGIN = 'list_type';
23 const PLUGIN_TYPE_CONTENT_ELEMENT = 'CType';
24
25 /**
26 * @var \TYPO3\CMS\Extbase\Object\ObjectManagerInterface
27 */
28 protected $objectManager;
29
30 /**
31 * @var \TYPO3\CMS\Extbase\Configuration\ConfigurationManagerInterface
32 */
33 protected $configurationManager;
34
35 /**
36 * Cache of result for getTargetPidByPlugin()
37 * @var array
38 */
39 protected $targetPidPluginCache = array();
40
41 /**
42 * @param \TYPO3\CMS\Extbase\Object\ObjectManagerInterface $objectManager
43 */
44 public function injectObjectManager(\TYPO3\CMS\Extbase\Object\ObjectManagerInterface $objectManager)
45 {
46 $this->objectManager = $objectManager;
47 }
48
49 /**
50 * @param \TYPO3\CMS\Extbase\Configuration\ConfigurationManagerInterface $configurationManager
51 */
52 public function injectConfigurationManager(\TYPO3\CMS\Extbase\Configuration\ConfigurationManagerInterface $configurationManager)
53 {
54 $this->configurationManager = $configurationManager;
55 }
56
57 /**
58 * Determines the plugin namespace of the specified plugin (defaults to "tx_[extensionname]_[pluginname]")
59 * If plugin.tx_$pluginSignature.view.pluginNamespace is set, this value is returned
60 * If pluginNamespace is not specified "tx_[extensionname]_[pluginname]" is returned.
61 *
62 * @param string $extensionName name of the extension to retrieve the namespace for
63 * @param string $pluginName name of the plugin to retrieve the namespace for
64 * @return string plugin namespace
65 */
66 public function getPluginNamespace($extensionName, $pluginName)
67 {
68 $pluginSignature = strtolower($extensionName . '_' . $pluginName);
69 $defaultPluginNamespace = 'tx_' . $pluginSignature;
70 $frameworkConfiguration = $this->configurationManager->getConfiguration(\TYPO3\CMS\Extbase\Configuration\ConfigurationManagerInterface::CONFIGURATION_TYPE_FRAMEWORK, $extensionName, $pluginName);
71 if (!isset($frameworkConfiguration['view']['pluginNamespace']) || empty($frameworkConfiguration['view']['pluginNamespace'])) {
72 return $defaultPluginNamespace;
73 }
74 return $frameworkConfiguration['view']['pluginNamespace'];
75 }
76
77 /**
78 * Iterates through the global TypoScript configuration and returns the name of the plugin
79 * that matches specified extensionName, controllerName and actionName.
80 * If no matching plugin was found, NULL is returned.
81 * If more than one plugin matches and the current plugin is not configured to handle the action,
82 * an Exception will be thrown
83 *
84 * @param string $extensionName name of the target extension (UpperCamelCase)
85 * @param string $controllerName name of the target controller (UpperCamelCase)
86 * @param string $actionName name of the target action (lowerCamelCase)
87 * @throws \TYPO3\CMS\Extbase\Exception
88 * @return string name of the target plugin (UpperCamelCase) or NULL if no matching plugin configuration was found
89 */
90 public function getPluginNameByAction($extensionName, $controllerName, $actionName)
91 {
92 $frameworkConfiguration = $this->configurationManager->getConfiguration(\TYPO3\CMS\Extbase\Configuration\ConfigurationManagerInterface::CONFIGURATION_TYPE_FRAMEWORK);
93 // check, whether the current plugin is configured to handle the action
94 if ($extensionName === $frameworkConfiguration['extensionName']) {
95 if (isset($frameworkConfiguration['controllerConfiguration'][$controllerName]) && in_array($actionName, $frameworkConfiguration['controllerConfiguration'][$controllerName]['actions'])) {
96 return $frameworkConfiguration['pluginName'];
97 }
98 }
99 if (!is_array($GLOBALS['TYPO3_CONF_VARS']['EXTCONF']['extbase']['extensions'][$extensionName]['plugins'])) {
100 return null;
101 }
102 $pluginNames = array();
103 foreach ($GLOBALS['TYPO3_CONF_VARS']['EXTCONF']['extbase']['extensions'][$extensionName]['plugins'] as $pluginName => $pluginConfiguration) {
104 if (!is_array($pluginConfiguration['controllers'])) {
105 continue;
106 }
107 foreach ($pluginConfiguration['controllers'] as $pluginControllerName => $pluginControllerActions) {
108 if (strtolower($pluginControllerName) !== strtolower($controllerName)) {
109 continue;
110 }
111 if (in_array($actionName, $pluginControllerActions['actions'])) {
112 $pluginNames[] = $pluginName;
113 }
114 }
115 }
116 if (count($pluginNames) > 1) {
117 throw new \TYPO3\CMS\Extbase\Exception('There is more than one plugin that can handle this request (Extension: "' . $extensionName . '", Controller: "' . $controllerName . '", action: "' . $actionName . '"). Please specify "pluginName" argument', 1280825466);
118 }
119 return !empty($pluginNames) ? $pluginNames[0] : null;
120 }
121
122 /**
123 * Checks if the given action is cacheable or not.
124 *
125 * @param string $extensionName Name of the target extension, without underscores
126 * @param string $pluginName Name of the target plugin
127 * @param string $controllerName Name of the target controller
128 * @param string $actionName Name of the action to be called
129 * @return bool TRUE if the specified plugin action is cacheable, otherwise FALSE
130 */
131 public function isActionCacheable($extensionName, $pluginName, $controllerName, $actionName)
132 {
133 $frameworkConfiguration = $this->configurationManager->getConfiguration(\TYPO3\CMS\Extbase\Configuration\ConfigurationManagerInterface::CONFIGURATION_TYPE_FRAMEWORK, $extensionName, $pluginName);
134 if (isset($frameworkConfiguration['controllerConfiguration'][$controllerName]) && is_array($frameworkConfiguration['controllerConfiguration'][$controllerName]) && is_array($frameworkConfiguration['controllerConfiguration'][$controllerName]['nonCacheableActions']) && in_array($actionName, $frameworkConfiguration['controllerConfiguration'][$controllerName]['nonCacheableActions'])) {
135 return false;
136 }
137 return true;
138 }
139
140 /**
141 * Determines the target page of the specified plugin.
142 * If plugin.tx_$pluginSignature.view.defaultPid is set, this value is used as target page id
143 * If defaultPid is set to "auto", a the target pid is determined by loading the tt_content record that contains this plugin
144 * If the page could not be determined, NULL is returned
145 * If defaultPid is "auto" and more than one page contains the specified plugin, an Exception is thrown
146 *
147 * @param string $extensionName name of the extension to retrieve the target PID for
148 * @param string $pluginName name of the plugin to retrieve the target PID for
149 * @throws \TYPO3\CMS\Extbase\Exception
150 * @return int uid of the target page or NULL if target page could not be determined
151 */
152 public function getTargetPidByPlugin($extensionName, $pluginName)
153 {
154 $frameworkConfiguration = $this->configurationManager->getConfiguration(\TYPO3\CMS\Extbase\Configuration\ConfigurationManagerInterface::CONFIGURATION_TYPE_FRAMEWORK, $extensionName, $pluginName);
155 if (!isset($frameworkConfiguration['view']['defaultPid']) || empty($frameworkConfiguration['view']['defaultPid'])) {
156 return null;
157 }
158 $pluginSignature = strtolower($extensionName . '_' . $pluginName);
159 if ($frameworkConfiguration['view']['defaultPid'] === 'auto') {
160 if (!array_key_exists($pluginSignature, $this->targetPidPluginCache)) {
161 $pages = $GLOBALS['TYPO3_DB']->exec_SELECTgetRows('pid', 'tt_content', 'list_type=' . $GLOBALS['TYPO3_DB']->fullQuoteStr($pluginSignature, 'tt_content') . ' AND CType="list"' . $GLOBALS['TSFE']->sys_page->enableFields('tt_content') . ' AND sys_language_uid=' . $GLOBALS['TSFE']->sys_language_uid, '', '', 2);
162 if (count($pages) > 1) {
163 throw new \TYPO3\CMS\Extbase\Exception('There is more than one "' . $pluginSignature . '" plugin in the current page tree. Please remove one plugin or set the TypoScript configuration "plugin.tx_' . $pluginSignature . '.view.defaultPid" to a fixed page id', 1280773643);
164 }
165 $this->targetPidPluginCache[$pluginSignature] = !empty($pages) ? $pages[0]['pid'] : null;
166 }
167 return $this->targetPidPluginCache[$pluginSignature];
168 }
169 return (int)$frameworkConfiguration['view']['defaultPid'];
170 }
171
172 /**
173 * This returns the name of the first controller of the given plugin.
174 *
175 * @param string $extensionName name of the extension to retrieve the target PID for
176 * @param string $pluginName name of the plugin to retrieve the target PID for
177 * @return string|NULL
178 */
179 public function getDefaultControllerNameByPlugin($extensionName, $pluginName)
180 {
181 if (!is_array($GLOBALS['TYPO3_CONF_VARS']['EXTCONF']['extbase']['extensions'][$extensionName]['plugins'][$pluginName]['controllers'])) {
182 return null;
183 }
184 $controllers = $GLOBALS['TYPO3_CONF_VARS']['EXTCONF']['extbase']['extensions'][$extensionName]['plugins'][$pluginName]['controllers'];
185 return key($controllers);
186 }
187
188 /**
189 * This returns the name of the first action of the given plugin controller.
190 *
191 * @param string $extensionName name of the extension to retrieve the target PID for
192 * @param string $pluginName name of the plugin to retrieve the target PID for
193 * @param string $controllerName name of the controller to retrieve default action for
194 * @return string|NULL
195 */
196 public function getDefaultActionNameByPluginAndController($extensionName, $pluginName, $controllerName)
197 {
198 if (!is_array($GLOBALS['TYPO3_CONF_VARS']['EXTCONF']['extbase']['extensions'][$extensionName]['plugins'][$pluginName]['controllers'][$controllerName]['actions'])) {
199 return null;
200 }
201 $actions = $GLOBALS['TYPO3_CONF_VARS']['EXTCONF']['extbase']['extensions'][$extensionName]['plugins'][$pluginName]['controllers'][$controllerName]['actions'];
202 return current($actions);
203 }
204
205 /**
206 * Resolve the page type number to use for building a link for a specific format
207 *
208 * @param string $extensionName name of the extension that has defined the target page type
209 * @param string $format The format for which to look up the page type
210 * @return int Page type number for target page
211 */
212 public function getTargetPageTypeByFormat($extensionName, $format)
213 {
214 $targetPageType = 0;
215 $settings = $this->configurationManager->getConfiguration(\TYPO3\CMS\Extbase\Configuration\ConfigurationManagerInterface::CONFIGURATION_TYPE_SETTINGS, $extensionName);
216 $formatToPageTypeMapping = isset($settings['view']['formatToPageTypeMapping']) ? $settings['view']['formatToPageTypeMapping'] : array();
217 if (is_array($formatToPageTypeMapping) && array_key_exists($format, $formatToPageTypeMapping)) {
218 $targetPageType = (int)$formatToPageTypeMapping[$format];
219 }
220 return $targetPageType;
221 }
222 }