diff --git a/cake/console/libs/shell.php b/cake/console/libs/shell.php index 720cfcc7e8d..a15da2e50f7 100644 --- a/cake/console/libs/shell.php +++ b/cake/console/libs/shell.php @@ -61,6 +61,13 @@ class Shell extends Object { */ public $args = array(); +/** + * Shell paths + * + * @var string + */ + public $shellPaths = array(); + /** * The file name of the shell that was invoked. * @@ -132,6 +139,13 @@ class Shell extends Object { */ public $Tasks; +/** + * Normalized map of tasks. + * + * @var string + */ + protected $_taskMap = array(); + /** * stdout object. * @@ -177,7 +191,7 @@ function __construct(&$dispatch, $stdout = null, $stderr = null, $stdin = null) } $this->Dispatch =& $dispatch; - $this->Tasks = new TaskCollection($this); + $this->Tasks = new TaskCollection($this, $dispatch); $this->stdout = $stdout; $this->stderr = $stderr; @@ -272,14 +286,28 @@ public function loadTasks() { if ($this->tasks === true || empty($this->tasks) || empty($this->Tasks)) { return true; } - $tasks = TaskCollection::normalizeObjectArray((array)$this->tasks); - foreach ($tasks as $task => $properties) { - $this->{$task} = $this->Tasks->load($properties['class'], $properties['settings']); + $this->_taskMap = TaskCollection::normalizeObjectArray((array)$this->tasks); + foreach ($this->_taskMap as $task => $properties) { $this->taskNames[] = $task; } return true; } +/** + * Overload get for lazy building of tasks + * + * @return void + */ + public function __get($name) { + if (empty($this->{$name}) && in_array($name, $this->taskNames)) { + $properties = $this->_taskMap[$name]; + $this->{$name} = $this->Tasks->load($properties['class'], $properties['settings']); + $this->{$name}->initialize(); + $this->{$name}->loadTasks(); + } + return $this->{$name}; + } + /** * Prompts the user for input, and returns it. * diff --git a/cake/console/libs/task_collection.php b/cake/console/libs/task_collection.php index a3b16216673..eecd3f578d0 100644 --- a/cake/console/libs/task_collection.php +++ b/cake/console/libs/task_collection.php @@ -25,6 +25,7 @@ class TaskCollection extends ObjectCollection { * @var array */ protected $_Shell; + protected $_Dispatch; /** * Constructor @@ -32,8 +33,9 @@ class TaskCollection extends ObjectCollection { * @param array $paths Array of paths to search for tasks on . * @return void */ - public function __construct(Shell $Shell) { + public function __construct(Shell $Shell, ShellDispatcher $dispatcher) { $this->_Shell = $Shell; + $this->_Dispatch = $dispatcher; } /** * Loads/constructs a task. Will return the instance in the registry if it already exists. @@ -61,7 +63,7 @@ public function load($task, $settings = array(), $enable = true) { } $this->_loaded[$name] = new $taskClass( - $this->_Shell, $this->_Shell->stdout, $this->_Shell->stderr, $this->_Shell->stdin + $this->_Dispatch, $this->_Shell->stdout, $this->_Shell->stderr, $this->_Shell->stdin ); if ($enable === true) { $this->_enabled[] = $name; diff --git a/cake/console/shell_dispatcher.php b/cake/console/shell_dispatcher.php index 04e9904a3f3..267cf4cb404 100644 --- a/cake/console/shell_dispatcher.php +++ b/cake/console/shell_dispatcher.php @@ -184,9 +184,7 @@ protected function _initEnvironment() { */ function __buildPaths() { $paths = array(); - if (!class_exists('Folder')) { - require LIBS . 'folder.php'; - } + $plugins = App::objects('plugin', null, false); foreach ((array)$plugins as $plugin) { $pluginPath = App::pluginPath($plugin); @@ -272,17 +270,10 @@ public function dispatch() { $methods = array(); - if ($Shell instanceof Shell) { + if ($Shell instanceof Shell) { $Shell->initialize(); $Shell->loadTasks(); - foreach ($Shell->taskNames as $task) { - if (is_a($Shell->{$task}, 'Shell')) { - $Shell->{$task}->initialize(); - $Shell->{$task}->loadTasks(); - } - } - $task = Inflector::camelize($arg); if (in_array($task, $Shell->taskNames)) { diff --git a/cake/tests/cases/console/libs/task_collection.test.php b/cake/tests/cases/console/libs/task_collection.test.php index 94935106bc5..b277c6c60bf 100644 --- a/cake/tests/cases/console/libs/task_collection.test.php +++ b/cake/tests/cases/console/libs/task_collection.test.php @@ -30,7 +30,8 @@ class TaskCollectionTest extends CakeTestCase { function setup() { $shell = $this->getMock('Shell', array(), array(), '', false); $shell->shellPaths = App::path('shells'); - $this->Tasks = new TaskCollection($shell); + $dispatcher = $this->getMock('ShellDispatcher', array(), array(), '', false); + $this->Tasks = new TaskCollection($shell, $dispatcher); } /** @@ -86,10 +87,12 @@ function testLoadMissingTaskFile() { * @return void */ function testLoadPluginTask() { + $dispatcher = $this->getMock('ShellDispatcher', array(), array(), '', false); $shell = $this->getMock('Shell', array(), array(), '', false); $shell->shellPaths = App::path('shells'); $shell->shellPaths[] = TEST_CAKE_CORE_INCLUDE_PATH . 'tests' . DS . 'test_app' . DS . 'plugins' . DS . 'test_plugin' . DS . 'vendors' . DS . 'shells' . DS; - $this->Tasks = new TaskCollection($shell); + $dispatcher->shellPaths = $shell->shellPaths; + $this->Tasks = new TaskCollection($shell, $dispatcher); $result = $this->Tasks->load('TestPlugin.OtherTask'); $this->assertType('OtherTaskTask', $result, 'Task class is wrong.');