Browse Source

Merge pull request #4602 from cakephp/controller-initialize

3.0 Add Controller::initialize
José Lorenzo Rodríguez 11 years ago
parent
commit
0dc1e77b93

+ 49 - 21
src/Controller/Controller.php

@@ -180,6 +180,24 @@ class Controller implements EventListener {
 	public $viewClass = 'Cake\View\View';
 
 /**
+ * The path to this controllers view templates.
+ * Example `Articles`
+ *
+ * Set automatically using conventions in Controller::__construct().
+ *
+ * @var string
+ */
+	public $viewPath;
+
+/**
+ * The name of the view file to render. The name specified
+ * is the filename in /app/Template/<SubFolder> without the .ctp extension.
+ *
+ * @var string
+ */
+	public $view = null;
+
+/**
  * Instance of the View created during rendering. Won't be set until after
  * Controller::render() is called.
  *
@@ -221,27 +239,18 @@ class Controller implements EventListener {
 	public $methods = array();
 
 /**
- * The path to this controllers view templates.
- * Example `Articles`
- *
- * Set automatically using conventions in Controller::__construct().
- *
- * @var string
- */
-	public $viewPath;
-
-/**
  * Constructor.
  *
  * Sets a number of properties based on conventions if they are empty. To override the
  * conventions CakePHP uses you can define properties in your class declaration.
  *
  * @param \Cake\Network\Request $request Request object for this controller. Can be null for testing,
- *  but expect that features that use the request parameters will not work.
+ *   but expect that features that use the request parameters will not work.
  * @param \Cake\Network\Response $response Response object for this controller.
  * @param string $name Override the name useful in testing when using mocks.
+ * @param \Cake\Event\EventManager $eventManager The event manager. Defaults to a new instance.
  */
-	public function __construct(Request $request = null, Response $response = null, $name = null) {
+	public function __construct(Request $request = null, Response $response = null, $name = null, $eventManager = null) {
 		if ($this->name === null && $name === null) {
 			list(, $name) = namespaceSplit(get_class($this));
 			$name = substr($name, 0, -10);
@@ -268,10 +277,30 @@ class Controller implements EventListener {
 		if ($response instanceof Response) {
 			$this->response = $response;
 		}
+		if ($eventManager) {
+			$this->eventManager($eventManager);
+		}
 
 		$this->modelFactory('Table', ['Cake\ORM\TableRegistry', 'get']);
 		$modelClass = ($this->plugin ? $this->plugin . '.' : '') . $this->name;
 		$this->_setModelClass($modelClass);
+
+		$this->initialize();
+
+		$this->_mergeControllerVars();
+		$this->_loadComponents();
+		$this->eventManager()->attach($this);
+	}
+
+/**
+ * Initialization hook method.
+ *
+ * Implement this method to avoid having to overwrite
+ * the constructor and call parent.
+ *
+ * @return void
+ */
+	public function initialize() {
 	}
 
 /**
@@ -292,7 +321,7 @@ class Controller implements EventListener {
  * This method will also set the component to a property.
  * For example:
  *
- * `$this->addComponent('DebugKit.Toolbar');`
+ * `$this->addComponent('Acl.Acl');`
  *
  * Will result in a `Toolbar` property being set.
  *
@@ -432,19 +461,18 @@ class Controller implements EventListener {
 	}
 
 /**
- * Loads Model and Component classes.
+ * No-op for backwards compatibility.
  *
- * Using the $components properties, classes are loaded
- * and components have their callbacks attached to the EventManager.
- * It is also at this time that Controller callbacks are bound.
+ * The code that used to live here is now in Controller::__construct().
  *
+ * @deprecated 3.0.0 Will be removed in 3.0.0.
  * @return void
- * @link http://book.cakephp.org/2.0/en/controllers.html#Controller::constructClasses
  */
 	public function constructClasses() {
-		$this->_mergeControllerVars();
-		$this->_loadComponents();
-		$this->eventManager()->attach($this);
+		trigger_error(
+			'Controller::constructClasses() is deprecated and will be removed in the first RC release',
+			E_USER_DEPRECATED
+		);
 	}
 
 /**

+ 0 - 1
src/Controller/ErrorController.php

@@ -31,7 +31,6 @@ class ErrorController extends Controller {
  */
 	public function __construct($request = null, $response = null) {
 		parent::__construct($request, $response);
-		$this->constructClasses();
 		if (count(Router::extensions()) &&
 			!isset($this->RequestHandler)
 		) {

+ 0 - 1
src/Routing/Dispatcher.php

@@ -104,7 +104,6 @@ class Dispatcher {
  *   instance of Response
  */
 	protected function _invoke(Controller $controller) {
-		$controller->constructClasses();
 		$result = $controller->startupProcess();
 		if ($result instanceof Response) {
 			return $result;

+ 0 - 1
src/Shell/Task/TestTask.php

@@ -363,7 +363,6 @@ class TestTask extends BakeTask {
  * @return void
  */
 	protected function _processController($subject) {
-		$subject->constructClasses();
 		$models = [$subject->modelClass];
 		foreach ($models as $model) {
 			list(, $model) = pluginSplit($model);

+ 1 - 2
src/TestSuite/ControllerTestCase.php

@@ -416,11 +416,10 @@ abstract class ControllerTestCase extends TestCase {
 			$config = isset($controller->components[$component]) ? $controller->components[$component] : array();
 			$component = $this->getMock($componentClass, $methods, array($registry, $config));
 			$registry->set($name, $component);
+			$controller->{$name} = $component;
 		}
 
-		$controller->constructClasses();
 		$this->_dirtyController = false;
-
 		$this->controller = $controller;
 		return $this->controller;
 	}

+ 7 - 18
tests/TestCase/Controller/Component/AuthComponentTest.php

@@ -72,8 +72,6 @@ class AuthComponentTest extends TestCase {
 		$response = $this->getMock('Cake\Network\Response', array('stop'));
 
 		$this->Controller = new AuthTestController($request, $response);
-		$this->Controller->constructClasses();
-
 		$this->Auth = new TestAuthComponent($this->Controller->components());
 
 		$Users = TableRegistry::get('AuthUsers');
@@ -821,7 +819,7 @@ class AuthComponentTest extends TestCase {
  */
 	public function testNoRedirectOnLoginAction() {
 		$event = new Event('Controller.startup', $this->Controller);
-		$controller = $this->getMock('Cake\Controller\Controller');
+		$controller = $this->getMock('Cake\Controller\Controller', ['redirect']);
 		$controller->methods = array('login');
 
 		$url = '/AuthTest/login';
@@ -982,19 +980,10 @@ class AuthComponentTest extends TestCase {
  * @return void
  */
 	public function testComponentSettings() {
-		Router::connect('/:controller');
-
-		$request = new Request();
-		$this->Controller = new AuthTestController($request, $this->getMock('Cake\Network\Response'));
-
-		$this->Controller->components = array(
-			'Auth' => array(
-				'loginAction' => array('controller' => 'people', 'action' => 'login'),
-				'logoutRedirect' => array('controller' => 'people', 'action' => 'login'),
-			),
-			'Session'
-		);
-		$this->Controller->constructClasses();
+		$this->Auth->config([
+			'loginAction' => array('controller' => 'people', 'action' => 'login'),
+			'logoutRedirect' => array('controller' => 'people', 'action' => 'login'),
+		]);
 
 		$expected = array(
 			'loginAction' => array('controller' => 'people', 'action' => 'login'),
@@ -1002,11 +991,11 @@ class AuthComponentTest extends TestCase {
 		);
 		$this->assertEquals(
 			$expected['loginAction'],
-			$this->Controller->Auth->config('loginAction')
+			$this->Auth->config('loginAction')
 		);
 		$this->assertEquals(
 			$expected['logoutRedirect'],
-			$this->Controller->Auth->config('logoutRedirect')
+			$this->Auth->config('logoutRedirect')
 		);
 	}
 

+ 1 - 2
tests/TestCase/Controller/Component/CookieComponentTest.php

@@ -41,8 +41,7 @@ class CookieComponentTest extends TestCase {
 			array('redirect'),
 			array(new Request(), new Response())
 		);
-		$controller->components = array('Cookie');
-		$controller->constructClasses();
+		$controller->addComponent('Cookie');
 		$this->Controller = $controller;
 		$this->Cookie = $controller->Cookie;
 		$this->request = $controller->request;

+ 9 - 9
tests/TestCase/Controller/Component/CsrfComponentTest.php

@@ -34,7 +34,7 @@ class CsrfComponentTest extends TestCase {
 	public function setUp() {
 		parent::setUp();
 
-		$controller = $this->getMock('Cake\Controller\Controller');
+		$controller = $this->getMock('Cake\Controller\Controller', ['redirect']);
 		$this->registry = new ComponentRegistry($controller);
 		$this->component = new CsrfComponent($this->registry);
 	}
@@ -57,7 +57,7 @@ class CsrfComponentTest extends TestCase {
 	public function testSettingCookie() {
 		$_SERVER['REQUEST_METHOD'] = 'GET';
 
-		$controller = $this->getMock('Cake\Controller\Controller');
+		$controller = $this->getMock('Cake\Controller\Controller', ['redirect']);
 		$controller->request = new Request(['base' => '/dir']);
 		$controller->response = new Response();
 
@@ -94,7 +94,7 @@ class CsrfComponentTest extends TestCase {
 		$_SERVER['REQUEST_METHOD'] = $method;
 		$_SERVER['HTTP_X_CSRF_TOKEN'] = 'testing123';
 
-		$controller = $this->getMock('Cake\Controller\Controller');
+		$controller = $this->getMock('Cake\Controller\Controller', ['redirect']);
 		$controller->request = new Request(['cookies' => ['csrfToken' => 'testing123']]);
 		$controller->response = new Response();
 
@@ -114,7 +114,7 @@ class CsrfComponentTest extends TestCase {
 		$_SERVER['REQUEST_METHOD'] = $method;
 		$_SERVER['HTTP_X_CSRF_TOKEN'] = 'nope';
 
-		$controller = $this->getMock('Cake\Controller\Controller');
+		$controller = $this->getMock('Cake\Controller\Controller', ['redirect']);
 		$controller->request = new Request([
 			'cookies' => ['csrfToken' => 'testing123']
 		]);
@@ -133,7 +133,7 @@ class CsrfComponentTest extends TestCase {
 	public function testValidTokenRequestData($method) {
 		$_SERVER['REQUEST_METHOD'] = $method;
 
-		$controller = $this->getMock('Cake\Controller\Controller');
+		$controller = $this->getMock('Cake\Controller\Controller', ['redirect']);
 		$controller->request = new Request([
 			'post' => ['_csrfToken' => 'testing123'],
 			'cookies' => ['csrfToken' => 'testing123']
@@ -155,7 +155,7 @@ class CsrfComponentTest extends TestCase {
 	public function testInvalidTokenRequestData($method) {
 		$_SERVER['REQUEST_METHOD'] = $method;
 
-		$controller = $this->getMock('Cake\Controller\Controller');
+		$controller = $this->getMock('Cake\Controller\Controller', ['redirect']);
 		$controller->request = new Request([
 			'post' => ['_csrfToken' => 'nope'],
 			'cookies' => ['csrfToken' => 'testing123']
@@ -174,7 +174,7 @@ class CsrfComponentTest extends TestCase {
 	public function testCsrfValidationSkipsRequestAction() {
 		$_SERVER['REQUEST_METHOD'] = 'POST';
 
-		$controller = $this->getMock('Cake\Controller\Controller');
+		$controller = $this->getMock('Cake\Controller\Controller', ['redirect']);
 		$controller->request = new Request([
 			'params' => ['requested' => 1],
 			'post' => ['_csrfToken' => 'nope'],
@@ -196,7 +196,7 @@ class CsrfComponentTest extends TestCase {
 	public function testConfigurationCookieCreate() {
 		$_SERVER['REQUEST_METHOD'] = 'GET';
 
-		$controller = $this->getMock('Cake\Controller\Controller');
+		$controller = $this->getMock('Cake\Controller\Controller', ['redirect']);
 		$controller->request = new Request(['base' => '/dir']);
 		$controller->response = new Response();
 
@@ -226,7 +226,7 @@ class CsrfComponentTest extends TestCase {
 	public function testConfigurationValidate() {
 		$_SERVER['REQUEST_METHOD'] = 'POST';
 
-		$controller = $this->getMock('Cake\Controller\Controller');
+		$controller = $this->getMock('Cake\Controller\Controller', ['redirect']);
 		$controller->request = new Request([
 			'cookies' => ['csrfToken' => 'nope', 'token' => 'yes'],
 			'post' => ['_csrfToken' => 'no match', 'token' => 'yes'],

+ 1 - 2
tests/TestCase/Controller/Component/RequestHandlerComponentTest.php

@@ -68,7 +68,6 @@ class RequestHandlerComponentTest extends TestCase {
 		$request = new Request('controller_posts/index');
 		$response = $this->getMock('Cake\Network\Response', array('_sendHeader', 'stop'));
 		$this->Controller = new RequestHandlerTestController($request, $response);
-		$this->Controller->constructClasses();
 		$this->RequestHandler = new RequestHandlerComponent($this->Controller->components());
 
 		Router::scope('/', function($routes) {
@@ -98,7 +97,7 @@ class RequestHandlerComponentTest extends TestCase {
 		$config = array(
 			'viewClassMap' => array('json' => 'MyPlugin.MyJson')
 		);
-		$controller = $this->getMock('Cake\Controller\Controller');
+		$controller = $this->getMock('Cake\Controller\Controller', ['redirect']);
 		$collection = new ComponentRegistry($controller);
 		$requestHandler = new RequestHandlerComponent($collection, $config);
 		$this->assertEquals(array('json' => 'MyPlugin.MyJson'), $requestHandler->config('viewClassMap'));

+ 0 - 1
tests/TestCase/Controller/Component/SecurityComponentTest.php

@@ -141,7 +141,6 @@ class SecurityComponentTest extends TestCase {
 			->will($this->returnValue('/articles/index'));
 
 		$this->Controller = new SecurityTestController($request);
-		$this->Controller->constructClasses();
 		$this->Controller->Security = $this->Controller->TestSecurity;
 		$this->Controller->Security->config('blackHoleCallback', 'fail');
 		$this->Security = $this->Controller->Security;

+ 1 - 3
tests/TestCase/Controller/ComponentTest.php

@@ -112,9 +112,7 @@ class ComponentTest extends TestCase {
  */
 	public function testSomethingReferencingCookieComponent() {
 		$Controller = new ComponentTestController();
-		$Controller->components = array('SomethingWithCookie');
-		$Controller->uses = false;
-		$Controller->constructClasses();
+		$Controller->addComponent('SomethingWithCookie');
 		$Controller->startupProcess();
 
 		$this->assertInstanceOf('TestApp\Controller\Component\SomethingWithCookieComponent', $Controller->SomethingWithCookie);

+ 10 - 55
tests/TestCase/Controller/ControllerTest.php

@@ -339,9 +339,8 @@ class ControllerTest extends TestCase {
 		Plugin::load('TestPlugin');
 
 		$Controller = new TestPluginController(new Request(), new Response());
-		$Controller->components[] = 'TestPlugin.Other';
+		$Controller->addComponent('TestPlugin.Other');
 
-		$Controller->constructClasses();
 		$this->assertInstanceOf('TestPlugin\Controller\Component\OtherComponent', $Controller->Other);
 	}
 
@@ -513,9 +512,7 @@ class ControllerTest extends TestCase {
  */
 	public function testMergeVars() {
 		$request = new Request();
-
 		$TestController = new TestController($request);
-		$TestController->constructClasses();
 
 		$expected = [
 			'Html' => null,
@@ -530,8 +527,6 @@ class ControllerTest extends TestCase {
 		$this->assertEquals($expected, $TestController->components);
 
 		$TestController = new AnotherTestController($request);
-		$TestController->constructClasses();
-
 		$this->assertEquals(
 			'Posts',
 			$TestController->modelClass,
@@ -540,38 +535,6 @@ class ControllerTest extends TestCase {
 	}
 
 /**
- * test that options from child classes replace those in the parent classes.
- *
- * @return void
- */
-	public function testChildComponentOptionsSupercedeParents() {
-		$request = new Request('controller_posts/index');
-
-		$TestController = new TestController($request);
-
-		$expected = array('foo');
-		$TestController->components = array('Cookie' => $expected);
-		$TestController->constructClasses();
-		$this->assertEquals($expected, $TestController->components['Cookie']);
-	}
-
-/**
- * Ensure that _mergeControllerVars is not being greedy and merging with
- * ControllerTestAppController when you make an instance of Controller
- *
- * @return void
- */
-	public function testMergeVarsNotGreedy() {
-		$request = new Request('controller_posts/index');
-
-		$Controller = new Controller($request);
-		$Controller->components = [];
-		$Controller->constructClasses();
-
-		$this->assertFalse(isset($Controller->Session));
-	}
-
-/**
  * testReferer method
  *
  * @return void
@@ -631,15 +594,15 @@ class ControllerTest extends TestCase {
  * @return void
  */
 	public function testStartupProcess() {
-		$Controller = $this->getMock('Cake\Controller\Controller', array('eventManager'));
-
 		$eventManager = $this->getMock('Cake\Event\EventManager');
+		$controller = new Controller(null, null, null, $eventManager);
+
 		$eventManager->expects($this->at(0))->method('dispatch')
 			->with(
 				$this->logicalAnd(
 					$this->isInstanceOf('Cake\Event\Event'),
 					$this->attributeEqualTo('_name', 'Controller.initialize'),
-					$this->attributeEqualTo('_subject', $Controller)
+					$this->attributeEqualTo('_subject', $controller)
 				)
 			)
 			->will($this->returnValue($this->getMock('Cake\Event\Event', null, [], '', false)));
@@ -649,15 +612,12 @@ class ControllerTest extends TestCase {
 				$this->logicalAnd(
 					$this->isInstanceOf('Cake\Event\Event'),
 					$this->attributeEqualTo('_name', 'Controller.startup'),
-					$this->attributeEqualTo('_subject', $Controller)
+					$this->attributeEqualTo('_subject', $controller)
 				)
 			)
 			->will($this->returnValue($this->getMock('Cake\Event\Event', null, [], '', false)));
 
-		$Controller->expects($this->exactly(2))->method('eventManager')
-			->will($this->returnValue($eventManager));
-
-		$Controller->startupProcess();
+		$controller->startupProcess();
 	}
 
 /**
@@ -666,23 +626,20 @@ class ControllerTest extends TestCase {
  * @return void
  */
 	public function testShutdownProcess() {
-		$Controller = $this->getMock('Cake\Controller\Controller', array('eventManager'));
-
 		$eventManager = $this->getMock('Cake\Event\EventManager');
+		$controller = new Controller(null, null, null, $eventManager);
+
 		$eventManager->expects($this->once())->method('dispatch')
 			->with(
 				$this->logicalAnd(
 					$this->isInstanceOf('Cake\Event\Event'),
 					$this->attributeEqualTo('_name', 'Controller.shutdown'),
-					$this->attributeEqualTo('_subject', $Controller)
+					$this->attributeEqualTo('_subject', $controller)
 				)
 			)
 			->will($this->returnValue($this->getMock('Cake\Event\Event', null, [], '', false)));
 
-		$Controller->expects($this->once())->method('eventManager')
-			->will($this->returnValue($eventManager));
-
-		$Controller->shutdownProcess();
+		$controller->shutdownProcess();
 	}
 
 /**
@@ -697,7 +654,6 @@ class ControllerTest extends TestCase {
 
 		$Controller = new Controller($request, $response);
 		$Controller->request->query['url'] = [];
-		$Controller->constructClasses();
 		$this->assertEquals([], $Controller->paginate);
 
 		$this->assertNotContains('Paginator', $Controller->helpers);
@@ -728,7 +684,6 @@ class ControllerTest extends TestCase {
 
 		$Controller = new Controller($request, $response);
 		$Controller->request->query['url'] = [];
-		$Controller->constructClasses();
 		$Controller->modelClass = 'Posts';
 		$results = $Controller->paginate();
 

+ 0 - 2
tests/TestCase/Shell/Task/TestTaskTest.php

@@ -389,7 +389,6 @@ class TestTaskTest extends TestCase {
 
 		$this->assertNotContains('function setUp()', $result);
 		$this->assertNotContains("\$this->Posts = new PostsController()", $result);
-		$this->assertNotContains("\$this->Posts->constructClasses()", $result);
 
 		$this->assertNotContains('function tearDown()', $result);
 		$this->assertNotContains('unset($this->Posts)', $result);
@@ -417,7 +416,6 @@ class TestTaskTest extends TestCase {
 
 		$this->assertNotContains('function setUp()', $result);
 		$this->assertNotContains("\$this->Posts = new PostsController()", $result);
-		$this->assertNotContains("\$this->Posts->constructClasses()", $result);
 
 		$this->assertNotContains('function tearDown()', $result);
 		$this->assertNotContains('unset($this->Posts)', $result);

+ 1 - 1
tests/TestCase/View/Helper/HtmlHelperTest.php

@@ -63,7 +63,7 @@ class HtmlHelperTest extends TestCase {
  */
 	public function setUp() {
 		parent::setUp();
-		$controller = $this->getMock('Cake\Controller\Controller');
+		$controller = $this->getMock('Cake\Controller\Controller', ['redirect']);
 		$this->View = $this->getMock('Cake\View\View', array('append'));
 		$this->Html = new HtmlHelper($this->View);
 		$this->Html->request = new Request();

+ 0 - 1
tests/TestCase/View/ViewTest.php

@@ -1124,7 +1124,6 @@ class ViewTest extends TestCase {
 		$this->assertNull($View->render(false, 'ajax2'));
 
 		$this->PostsController->helpers = array('Session', 'Html');
-		$this->PostsController->constructClasses();
 		$this->PostsController->request->params['action'] = 'index';
 		Configure::write('Cache.check', true);