[TASK] Replace inject methods with @inject
[Packages/TYPO3.CMS.git] / typo3 / sysext / extbase / Classes / Mvc / Controller / AbstractController.php
1 <?php
2 namespace TYPO3\CMS\Extbase\Mvc\Controller;
3
4 /***************************************************************
5 * Copyright notice
6 *
7 * (c) 2010-2013 Extbase Team (http://forge.typo3.org/projects/typo3v4-mvc)
8 * Extbase is a backport of TYPO3 Flow. All credits go to the TYPO3 Flow team.
9 * All rights reserved
10 *
11 * This script is part of the TYPO3 project. The TYPO3 project is
12 * free software; you can redistribute it and/or modify
13 * it under the terms of the GNU General Public License as published by
14 * the Free Software Foundation; either version 2 of the License, or
15 * (at your option) any later version.
16 *
17 * The GNU General Public License can be found at
18 * http://www.gnu.org/copyleft/gpl.html.
19 * A copy is found in the textfile GPL.txt and important notices to the license
20 * from the author is found in LICENSE.txt distributed with these scripts.
21 *
22 *
23 * This script is distributed in the hope that it will be useful,
24 * but WITHOUT ANY WARRANTY; without even the implied warranty of
25 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
26 * GNU General Public License for more details.
27 *
28 * This copyright notice MUST APPEAR in all copies of the script!
29 ***************************************************************/
30 /**
31 * An abstract base class for Controllers
32 *
33 * @api
34 */
35 abstract class AbstractController implements \TYPO3\CMS\Extbase\Mvc\Controller\ControllerInterface {
36
37 /**
38 * @var \TYPO3\CMS\Extbase\SignalSlot\Dispatcher
39 * @inject
40 */
41 protected $signalSlotDispatcher;
42
43 /**
44 * @var \TYPO3\CMS\Extbase\Object\ObjectManagerInterface
45 */
46 protected $objectManager;
47
48 /**
49 * @var \TYPO3\CMS\Extbase\Mvc\Web\Routing\UriBuilder
50 */
51 protected $uriBuilder;
52
53 /**
54 * @var string Key of the extension this controller belongs to
55 */
56 protected $extensionName;
57
58 /**
59 * Contains the settings of the current extension
60 *
61 * @var array
62 * @api
63 */
64 protected $settings;
65
66 /**
67 * The current request.
68 *
69 * @var \TYPO3\CMS\Extbase\Mvc\Request
70 * @api
71 */
72 protected $request;
73
74 /**
75 * The response which will be returned by this action controller
76 *
77 * @var \TYPO3\CMS\Extbase\Mvc\Response
78 * @api
79 */
80 protected $response;
81
82 /**
83 * @var \TYPO3\CMS\Extbase\Property\Mapper
84 * @deprecated since Extbase 1.4.0, will be removed two versions after Extbase 6.1
85 * @inject
86 */
87 protected $deprecatedPropertyMapper;
88
89 /**
90 * @var \TYPO3\CMS\Extbase\Validation\ValidatorResolver
91 * @inject
92 */
93 protected $validatorResolver;
94
95 /**
96 * @var \TYPO3\CMS\Extbase\Mvc\Controller\Arguments Arguments passed to the controller
97 */
98 protected $arguments;
99
100 /**
101 * The results of the mapping of request arguments to controller arguments
102 *
103 * @var \TYPO3\CMS\Extbase\Property\MappingResults
104 * @api
105 * @deprecated since Extbase 1.4.0, will be removed two versions after Extbase 6.1
106 */
107 protected $argumentsMappingResults;
108
109 /**
110 * An array of supported request types. By default only web requests are supported.
111 * Modify or replace this array if your specific controller supports certain
112 * (additional) request types.
113 *
114 * @var array
115 */
116 protected $supportedRequestTypes = array('TYPO3\\CMS\\Extbase\\Mvc\\Request');
117
118 /**
119 * @var \TYPO3\CMS\Extbase\Mvc\Controller\ControllerContext
120 * @api
121 */
122 protected $controllerContext;
123
124 /**
125 * @return ControllerContext
126 * @api
127 */
128 public function getControllerContext() {
129 return $this->controllerContext;
130 }
131
132 /**
133 * @var \TYPO3\CMS\Extbase\Mvc\Controller\FlashMessageContainer
134 * @api
135 */
136 protected $flashMessageContainer;
137
138 /**
139 * @var \TYPO3\CMS\Extbase\Configuration\ConfigurationManagerInterface
140 */
141 protected $configurationManager;
142
143 /**
144 * Constructs the controller.
145 */
146 public function __construct() {
147 $className = get_class($this);
148 if (strpos($className, '\\') !== FALSE) {
149 $classNameParts = explode('\\', $className, 4);
150 // Skip vendor and product name for core classes
151 if (strpos($className, 'TYPO3\\CMS\\') === 0) {
152 $this->extensionName = $classNameParts[2];
153 } else {
154 $this->extensionName = $classNameParts[1];
155 }
156 } else {
157 list(, $this->extensionName) = explode('_', $className);
158 }
159 }
160
161 /**
162 * @param \TYPO3\CMS\Extbase\Configuration\ConfigurationManagerInterface $configurationManager
163 * @return void
164 */
165 public function injectConfigurationManager(\TYPO3\CMS\Extbase\Configuration\ConfigurationManagerInterface $configurationManager) {
166 $this->configurationManager = $configurationManager;
167 $this->settings = $this->configurationManager->getConfiguration(\TYPO3\CMS\Extbase\Configuration\ConfigurationManagerInterface::CONFIGURATION_TYPE_SETTINGS);
168 }
169
170 /**
171 * Injects the object manager
172 *
173 * @param \TYPO3\CMS\Extbase\Object\ObjectManagerInterface $objectManager
174 * @return void
175 */
176 public function injectObjectManager(\TYPO3\CMS\Extbase\Object\ObjectManagerInterface $objectManager) {
177 $this->objectManager = $objectManager;
178 $this->arguments = $this->objectManager->get('TYPO3\\CMS\\Extbase\\Mvc\\Controller\\Arguments');
179 }
180
181 /**
182 * This method is deprecated! For further information have a look at
183 * the PhpDoc of class \TYPO3\CMS\Extbase\Mvc\Controller\FlashMessageContainer
184 *
185 * @param \TYPO3\CMS\Extbase\Mvc\Controller\FlashMessageContainer $flashMessageContainer
186 * @return void
187 *
188 * @deprecated since Extbase 6.1, will be removed 2 versions later
189 */
190 public function injectFlashMessageContainer(\TYPO3\CMS\Extbase\Mvc\Controller\FlashMessageContainer $flashMessageContainer) {
191 $this->flashMessageContainer = $flashMessageContainer;
192 }
193
194 /**
195 * Checks if the current request type is supported by the controller.
196 *
197 * If your controller only supports certain request types, either
198 * replace / modify the supporteRequestTypes property or override this
199 * method.
200 *
201 * @param \TYPO3\CMS\Extbase\Mvc\RequestInterface $request The current request
202 * @return boolean TRUE if this request type is supported, otherwise FALSE
203 * @api
204 */
205 public function canProcessRequest(\TYPO3\CMS\Extbase\Mvc\RequestInterface $request) {
206 foreach ($this->supportedRequestTypes as $supportedRequestType) {
207 if ($request instanceof $supportedRequestType) {
208 return TRUE;
209 }
210 }
211 return FALSE;
212 }
213
214 /**
215 * Processes a general request. The result can be returned by altering the given response.
216 *
217 * @param \TYPO3\CMS\Extbase\Mvc\RequestInterface $request The request object
218 * @param \TYPO3\CMS\Extbase\Mvc\ResponseInterface $response The response, modified by this handler
219 * @return void
220 * @throws \TYPO3\CMS\Extbase\Mvc\Exception\UnsupportedRequestTypeException if the controller doesn't support the current request type
221 * @api
222 */
223 public function processRequest(\TYPO3\CMS\Extbase\Mvc\RequestInterface $request, \TYPO3\CMS\Extbase\Mvc\ResponseInterface $response) {
224 if (!$this->canProcessRequest($request)) {
225 throw new \TYPO3\CMS\Extbase\Mvc\Exception\UnsupportedRequestTypeException(get_class($this) . ' does not support requests of type "' . get_class($request) . '". Supported types are: ' . implode(' ', $this->supportedRequestTypes), 1187701131);
226 }
227 $response->setRequest($request);
228 $this->request = $request;
229 $this->request->setDispatched(TRUE);
230 $this->response = $response;
231 $this->uriBuilder = $this->objectManager->get('TYPO3\\CMS\\Extbase\\Mvc\\Web\\Routing\\UriBuilder');
232 $this->uriBuilder->setRequest($request);
233 $this->initializeControllerArgumentsBaseValidators();
234 $this->mapRequestArgumentsToControllerArguments();
235 $this->controllerContext = $this->buildControllerContext();
236 }
237
238 /**
239 * Initialize the controller context
240 *
241 * @return \TYPO3\CMS\Extbase\Mvc\Controller\ControllerContext ControllerContext to be passed to the view
242 * @api
243 */
244 protected function buildControllerContext() {
245 /** @var $controllerContext \TYPO3\CMS\Extbase\Mvc\Controller\ControllerContext */
246 $controllerContext = $this->objectManager->get('TYPO3\\CMS\\Extbase\\Mvc\\Controller\\ControllerContext');
247 $controllerContext->setRequest($this->request);
248 $controllerContext->setResponse($this->response);
249 if ($this->arguments !== NULL) {
250 $controllerContext->setArguments($this->arguments);
251 }
252 if ($this->argumentsMappingResults !== NULL) {
253 $controllerContext->setArgumentsMappingResults($this->argumentsMappingResults);
254 }
255 $controllerContext->setUriBuilder($this->uriBuilder);
256
257 $controllerContext->setFlashMessageContainer($this->flashMessageContainer);
258 return $controllerContext;
259 }
260
261 /**
262 * Forwards the request to another action and / or controller.
263 *
264 * Request is directly transfered to the other action / controller
265 * without the need for a new request.
266 *
267 * @param string $actionName Name of the action to forward to
268 * @param string $controllerName Unqualified object name of the controller to forward to. If not specified, the current controller is used.
269 * @param string $extensionName Name of the extension containing the controller to forward to. If not specified, the current extension is assumed.
270 * @param array $arguments Arguments to pass to the target action
271 * @return void
272 * @throws \TYPO3\CMS\Extbase\Mvc\Exception\StopActionException
273 * @see redirect()
274 * @api
275 */
276 public function forward($actionName, $controllerName = NULL, $extensionName = NULL, array $arguments = NULL) {
277 $this->request->setDispatched(FALSE);
278 $this->request->setControllerActionName($actionName);
279 if ($controllerName !== NULL) {
280 $this->request->setControllerName($controllerName);
281 }
282 if ($extensionName !== NULL) {
283 $this->request->setControllerExtensionName($extensionName);
284 }
285 if ($arguments !== NULL) {
286 $this->request->setArguments($arguments);
287 }
288 throw new \TYPO3\CMS\Extbase\Mvc\Exception\StopActionException();
289 }
290
291 /**
292 * Redirects the request to another action and / or controller.
293 *
294 * Redirect will be sent to the client which then performs another request to the new URI.
295 *
296 * NOTE: This method only supports web requests and will thrown an exception
297 * if used with other request types.
298 *
299 * @param string $actionName Name of the action to forward to
300 * @param string $controllerName Unqualified object name of the controller to forward to. If not specified, the current controller is used.
301 * @param string $extensionName Name of the extension containing the controller to forward to. If not specified, the current extension is assumed.
302 * @param array $arguments Arguments to pass to the target action
303 * @param integer $pageUid Target page uid. If NULL, the current page uid is used
304 * @param integer $delay (optional) The delay in seconds. Default is no delay.
305 * @param integer $statusCode (optional) The HTTP status code for the redirect. Default is "303 See Other
306 * @return void
307 * @throws \TYPO3\CMS\Extbase\Mvc\Exception\UnsupportedRequestTypeException If the request is not a web request
308 * @throws \TYPO3\CMS\Extbase\Mvc\Exception\StopActionException
309 * @see forward()
310 * @api
311 */
312 protected function redirect($actionName, $controllerName = NULL, $extensionName = NULL, array $arguments = NULL, $pageUid = NULL, $delay = 0, $statusCode = 303) {
313 if (!$this->request instanceof \TYPO3\CMS\Extbase\Mvc\Web\Request) {
314 throw new \TYPO3\CMS\Extbase\Mvc\Exception\UnsupportedRequestTypeException('redirect() only supports web requests.', 1220539734);
315 }
316 if ($controllerName === NULL) {
317 $controllerName = $this->request->getControllerName();
318 }
319 $this->uriBuilder->reset()->setTargetPageUid($pageUid)->setCreateAbsoluteUri(TRUE);
320 if (\TYPO3\CMS\Core\Utility\GeneralUtility::getIndpEnv('TYPO3_SSL')) {
321 $this->uriBuilder->setAbsoluteUriScheme('https');
322 }
323 $uri = $this->uriBuilder->uriFor($actionName, $arguments, $controllerName, $extensionName);
324 $this->redirectToUri($uri, $delay, $statusCode);
325 }
326
327 /**
328 * Redirects the web request to another uri.
329 *
330 * NOTE: This method only supports web requests and will thrown an exception if used with other request types.
331 *
332 * @param mixed $uri A string representation of a URI
333 * @param integer $delay (optional) The delay in seconds. Default is no delay.
334 * @param integer $statusCode (optional) The HTTP status code for the redirect. Default is "303 See Other
335 * @throws \TYPO3\CMS\Extbase\Mvc\Exception\UnsupportedRequestTypeException If the request is not a web request
336 * @throws \TYPO3\CMS\Extbase\Mvc\Exception\StopActionException
337 * @api
338 */
339 protected function redirectToUri($uri, $delay = 0, $statusCode = 303) {
340 if (!$this->request instanceof \TYPO3\CMS\Extbase\Mvc\Web\Request) {
341 throw new \TYPO3\CMS\Extbase\Mvc\Exception\UnsupportedRequestTypeException('redirect() only supports web requests.', 1220539734);
342 }
343
344 $this->objectManager->get('TYPO3\CMS\Extbase\Service\CacheService')->clearCachesOfRegisteredPageIds();
345
346 $uri = $this->addBaseUriIfNecessary($uri);
347 $escapedUri = htmlentities($uri, ENT_QUOTES, 'utf-8');
348 $this->response->setContent('<html><head><meta http-equiv="refresh" content="' . intval($delay) . ';url=' . $escapedUri . '"/></head></html>');
349 $this->response->setStatus($statusCode);
350 $this->response->setHeader('Location', (string) $uri);
351 throw new \TYPO3\CMS\Extbase\Mvc\Exception\StopActionException();
352 }
353
354 /**
355 * Adds the base uri if not already in place.
356 *
357 * @param string $uri The URI
358 * @return string
359 */
360 protected function addBaseUriIfNecessary($uri) {
361 return \TYPO3\CMS\Core\Utility\GeneralUtility::locationHeaderUrl((string) $uri);
362 }
363
364 /**
365 * Sends the specified HTTP status immediately.
366 *
367 * NOTE: This method only supports web requests and will thrown an exception if used with other request types.
368 *
369 * @param integer $statusCode The HTTP status code
370 * @param string $statusMessage A custom HTTP status message
371 * @param string $content Body content which further explains the status
372 * @throws \TYPO3\CMS\Extbase\Mvc\Exception\UnsupportedRequestTypeException If the request is not a web request
373 * @throws \TYPO3\CMS\Extbase\Mvc\Exception\StopActionException
374 * @api
375 */
376 public function throwStatus($statusCode, $statusMessage = NULL, $content = NULL) {
377 if (!$this->request instanceof \TYPO3\CMS\Extbase\Mvc\Web\Request) {
378 throw new \TYPO3\CMS\Extbase\Mvc\Exception\UnsupportedRequestTypeException('throwStatus() only supports web requests.', 1220539739);
379 }
380 $this->response->setStatus($statusCode, $statusMessage);
381 if ($content === NULL) {
382 $content = $this->response->getStatus();
383 }
384 $this->response->setContent($content);
385 throw new \TYPO3\CMS\Extbase\Mvc\Exception\StopActionException();
386 }
387
388 /**
389 * Collects the base validators which were defined for the data type of each
390 * controller argument and adds them to the argument's validator chain.
391 *
392 * @return void
393 */
394 public function initializeControllerArgumentsBaseValidators() {
395 foreach ($this->arguments as $argument) {
396 $validator = $this->validatorResolver->getBaseValidatorConjunction($argument->getDataType());
397 if ($validator !== NULL) {
398 $argument->setValidator($validator);
399 }
400 }
401 }
402
403 /**
404 * Maps arguments delivered by the request object to the local controller arguments.
405 *
406 * @throws Exception\RequiredArgumentMissingException
407 * @return void
408 */
409 protected function mapRequestArgumentsToControllerArguments() {
410 if ($this->configurationManager->isFeatureEnabled('rewrittenPropertyMapper')) {
411 foreach ($this->arguments as $argument) {
412 $argumentName = $argument->getName();
413 if ($this->request->hasArgument($argumentName)) {
414 $argument->setValue($this->request->getArgument($argumentName));
415 } elseif ($argument->isRequired()) {
416 throw new \TYPO3\CMS\Extbase\Mvc\Controller\Exception\RequiredArgumentMissingException('Required argument "' . $argumentName . '" is not set.', 1298012500);
417 }
418 }
419 } else {
420 // @deprecated since Extbase 1.4, will be removed two versions after Extbase 6.1
421 $optionalPropertyNames = array();
422 $allPropertyNames = $this->arguments->getArgumentNames();
423 foreach ($allPropertyNames as $propertyName) {
424 if ($this->arguments[$propertyName]->isRequired() === FALSE) {
425 $optionalPropertyNames[] = $propertyName;
426 }
427 }
428 /** @var $validator ArgumentsValidator */
429 $validator = $this->objectManager->get('TYPO3\\CMS\\Extbase\\Mvc\\Controller\\ArgumentsValidator');
430 $this->deprecatedPropertyMapper->mapAndValidate($allPropertyNames, $this->request->getArguments(), $this->arguments, $optionalPropertyNames, $validator);
431 $this->argumentsMappingResults = $this->deprecatedPropertyMapper->getMappingResults();
432 }
433 }
434 }
435
436 ?>