Преглед изворни кода

ZF-7940
- Remerging Zend_Tool 1.10 feature from incubator to trunk.


git-svn-id: http://framework.zend.com/svn/framework/standard/trunk@19525 44c647ce-9c0f-0410-b52a-842ac1e357ba

ralph пре 16 година
родитељ
комит
e81cedbe6f
51 измењених фајлова са 2894 додато и 359 уклоњено
  1. 540 139
      bin/zf.php
  2. 2 1
      bin/zf.sh
  3. 36 17
      library/Zend/Tool/Framework/Client/Abstract.php
  4. 147 8
      library/Zend/Tool/Framework/Client/Config.php
  5. 55 42
      library/Zend/Tool/Framework/Client/Console.php
  6. 43 14
      library/Zend/Tool/Framework/Client/Console/ArgumentParser.php
  7. 3 7
      library/Zend/Tool/Framework/Client/Console/HelpSystem.php
  8. 66 0
      library/Zend/Tool/Framework/Client/Console/ResponseDecorator/AlignCenter.php
  9. 69 0
      library/Zend/Tool/Framework/Client/Console/ResponseDecorator/Blockize.php
  10. 56 0
      library/Zend/Tool/Framework/Client/Console/ResponseDecorator/Indention.php
  11. 206 0
      library/Zend/Tool/Framework/Client/Manifest.php
  12. 2 2
      library/Zend/Tool/Framework/Client/Response.php
  13. 12 6
      library/Zend/Tool/Framework/Loader/Abstract.php
  14. 157 0
      library/Zend/Tool/Framework/Loader/BasicLoader.php
  15. 42 0
      library/Zend/Tool/Framework/Loader/Interface.php
  16. 13 0
      library/Zend/Tool/Framework/Manifest/Repository.php
  17. 8 0
      library/Zend/Tool/Framework/Metadata/Attributable.php
  18. 7 1
      library/Zend/Tool/Framework/Metadata/Basic.php
  19. 70 5
      library/Zend/Tool/Framework/Metadata/Dynamic.php
  20. 1 1
      library/Zend/Tool/Framework/Metadata/Interface.php
  21. 2 2
      library/Zend/Tool/Framework/Registry.php
  22. 1 1
      library/Zend/Tool/Framework/Registry/Interface.php
  23. 2 0
      library/Zend/Tool/Framework/System/Manifest.php
  24. 311 0
      library/Zend/Tool/Framework/System/Provider/Config.php
  25. 11 1
      library/Zend/Tool/Project/Context/Filesystem/Directory.php
  26. 11 1
      library/Zend/Tool/Project/Context/Filesystem/File.php
  27. 6 2
      library/Zend/Tool/Project/Context/Repository.php
  28. 39 0
      library/Zend/Tool/Project/Context/Zf/AbstractClassFile.php
  29. 2 0
      library/Zend/Tool/Project/Context/Zf/ApplicationConfigFile.php
  30. 25 1
      library/Zend/Tool/Project/Context/Zf/ApplicationDirectory.php
  31. 19 3
      library/Zend/Tool/Project/Context/Zf/BootstrapFile.php
  32. 23 29
      library/Zend/Tool/Project/Context/Zf/ControllerFile.php
  33. 7 4
      library/Zend/Tool/Project/Context/Zf/DbTableFile.php
  34. 109 0
      library/Zend/Tool/Project/Context/Zf/LayoutScriptFile.php
  35. 57 0
      library/Zend/Tool/Project/Context/Zf/LayoutScriptsDirectory.php
  36. 68 6
      library/Zend/Tool/Project/Context/Zf/ModelFile.php
  37. 1 1
      library/Zend/Tool/Project/Context/Zf/ModulesDirectory.php
  38. 9 1
      library/Zend/Tool/Project/Context/Zf/ViewControllerScriptsDirectory.php
  39. 10 2
      library/Zend/Tool/Project/Context/Zf/ViewScriptFile.php
  40. 10 2
      library/Zend/Tool/Project/Profile/Iterator/ContextFilter.php
  41. 3 0
      library/Zend/Tool/Project/Provider/Abstract.php
  42. 17 4
      library/Zend/Tool/Project/Provider/Action.php
  43. 39 0
      library/Zend/Tool/Project/Provider/Application.php
  44. 13 3
      library/Zend/Tool/Project/Provider/Controller.php
  45. 202 0
      library/Zend/Tool/Project/Provider/DbAdapter.php
  46. 88 0
      library/Zend/Tool/Project/Provider/DbTable.php
  47. 125 0
      library/Zend/Tool/Project/Provider/Layout.php
  48. 26 47
      library/Zend/Tool/Project/Provider/Manifest.php
  49. 116 3
      library/Zend/Tool/Project/Provider/Model.php
  50. 5 1
      library/Zend/Tool/Project/Provider/Project.php
  51. 2 2
      library/Zend/Tool/Project/Provider/View.php

+ 540 - 139
bin/zf.php

@@ -20,199 +20,600 @@
  * @version    $Id$
  * @version    $Id$
  */
  */
 
 
-zf_main();
-
 /**
 /**
- * zf_main() - The main() function to run
+ * ZF
+ *  
+ * @category   Zend
+ * @package    Zend_Tool
+ * @subpackage Framework
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
  */
  */
-function zf_main() {
-    global $_zf;
-    $_zf = array();
-    zf_setup_home_directory();
-    zf_setup_storage_directory();
-    zf_setup_config_file();
-    zf_setup_php_runtime();
-    zf_setup_tool_runtime();
-    zf_run($_zf);
-}
+class ZF
+{
 
 
-function zf_setup_home_directory() {
-    global $_zf;
+    /**
+     * @var bool
+     */
+    protected $_clientLoaded = false;
     
     
-    // check for explicity set ENV var ZF_HOME
-    if (($zfHome = getenv('ZF_HOME')) && file_exists($zfHome)) {
-        $_zf['HOME'] = $zfHome;
-    } elseif (($home = getenv('HOME'))) {
-        $_zf['HOME'] = $home;
-    } elseif (($home = getenv('HOMEPATH'))) {
-        $_zf['HOME'] = $home;
-    }
+    /**
+     * @var string
+     */
+    protected $_mode = 'runTool';
     
     
-    $homeRealpath = realpath($_zf['HOME']);
+    /**
+     * @var array of messages
+     */
+    protected $_messages = array();
     
     
-    if ($homeRealpath) {
-        $_zf['HOME'] = $homeRealpath;
-    } else {
-        unset($_zf['HOME']);
-    }
+    /**
+     * @var string
+     */
+    protected $_homeDirectory = null;
     
     
-}
-
-function zf_setup_storage_directory() {
-    global $_zf;
+    /**
+     * @var string
+     */
+    protected $_storageDirectory = null;
     
     
-    if (($zfStorage = getenv('ZF_STORAGE_DIR')) && file_exists($zfStorage)) {
-        $_zf['STORAGE_DIR'] = $zfStorage;
-    } elseif (isset($_zf['HOME']) && file_exists($_zf['HOME'] . '/.zf/')) {
-        $_zf['STORAGE_DIR'] = $_zf['HOME'] . '/.zf/';
-    } else {
-        return;
+    /**
+     * @var string
+     */
+    protected $_configFile = null;
+    
+    /**
+     * main()
+     * 
+     * @return void
+     */
+    public static function main()
+    {
+        $zf = new self();
+        $zf->bootstrap();
+        $zf->run();
     }
     }
     
     
-    $storageRealpath = realpath($_zf['STORAGE_DIR']);
+    /**
+     * bootstrap()
+     * 
+     * @return ZF
+     */
+    public function bootstrap()
+    {
+        // detect settings
+        $this->_mode             = $this->_detectMode();
+        $this->_homeDirectory    = $this->_detectHomeDirectory();
+        $this->_storageDirectory = $this->_detectStorageDirectory();
+        $this->_configFile       = $this->_detectConfigFile();
+        
+        // setup
+        $this->_setupPHPRuntime();
+        $this->_setupToolRuntime();
+    }
     
     
-    if ($storageRealpath) {
-        $_zf['STORAGE_DIR'] = $storageRealpath;
-    } else {
-        unset($_zf['STORAGE_DIR']);
+    /**
+     * run()
+     * 
+     * @return ZF
+     */
+    public function run()
+    {
+        switch ($this->_mode) {
+            case 'runError':
+                $this->_runError();
+                $this->_runInfo();
+                break;
+            case 'runSetup':
+                if ($this->_runSetup() === false) {
+                    $this->_runInfo();
+                }
+                break;
+            case 'runInfo':
+                $this->_runInfo();
+                break;
+            case 'runTool':
+            default:
+                $this->_runTool();
+                break;
+        }
+        
+        return $this;
     }
     }
     
     
-}
+    /**
+     * _detectMode()
+     * 
+     * @return ZF
+     */
+    protected function _detectMode()
+    {
+        $arguments = $_SERVER['argv'];
 
 
-function zf_setup_config_file() {
-    global $_zf;
-    
-    if (($zfConfigFile = getenv('ZF_CONFIG_FILE')) && file_exists($zfConfigFile)) {
-        $_zf['CONFIG_FILE'] = $zfConfigFile;
-    } elseif (isset($_zf['HOME'])) {
-        if (file_exists($_zf['HOME'] . '/.zf.ini')) {
-            $_zf['CONFIG_FILE'] = $_zf['HOME'] . '/.zf.ini';    
-        } elseif (file_exists($_zf['HOME'] . '/zf.ini')) {
-            $_zf['CONFIG_FILE'] = $_zf['HOME'] . '/zf.ini';
+        $mode = 'runTool';
+        
+        if (!isset($arguments[0])) {
+            return $mode;
+        }
+        
+        if ($arguments[0] == $_SERVER['PHP_SELF']) {
+            $this->_executable = array_shift($arguments);
         }
         }
+        
+        if (!isset($arguments[0])) {
+            return $mode;
+        }
+        
+        if ($arguments[0] == '--setup') {
+            $mode = 'runSetup';
+        } elseif ($arguments[0] == '--info') {
+            $mode = 'runInfo';
+    	}
+    	
+    	return $mode;
     }
     }
+    
 
 
-    if (isset($_zf['CONFIG_FILE']) && ($zrealpath = realpath($_zf['CONFIG_FILE']))) {
-
-        $_zf['CONFIG_FILE'] = $zrealpath;
+    /**
+     * _detectHomeDirectory() - detect the home directory in a variety of different places
+     * 
+     * @param $mustExist Should the returned value already exist in the file system
+     * @param $returnMessages Should it log messages for output later
+     * @return string
+     */
+    protected function _detectHomeDirectory($mustExist = true, $returnMessages = true)
+    {
+        $homeDirectory = null;
         
         
-        $zsuffix = substr($_zf['CONFIG_FILE'], -4);
+        $homeDirectory = getenv('ZF_HOME'); // check env var ZF_HOME
+        if ($homeDirectory) {
+            $this->_logMessage('Home directory found in environment variable ZF_HOME with value ' . $homeDirectory, $returnMessages);
+            if (!$mustExist || ($mustExist && file_exists($homeDirectory))) {
+                return $homeDirectory;
+            } else {
+                $this->_logMessage('Home directory does not exist at ' . $homeDirectory, $returnMessages);
+            }
+        }
         
         
-        if ($zsuffix === '.ini') {
-            $_zf['CONFIG_TYPE'] = 'ini';
-        } else {
-            unset($_zf['CONFIG_FILE']);
+        $homeDirectory = getenv('HOME'); // HOME environment variable
+        
+        if ($homeDirectory) {
+            $this->_logMessage('Home directory found in environment variable HOME with value ' . $homeDirectory, $returnMessages);
+            if (!$mustExist || ($mustExist && file_exists($homeDirectory))) {
+                return $homeDirectory;
+            } else {
+                $this->_logMessage('Home directory does not exist at ' . $homeDirectory, $returnMessages);
+            }
+            
         }
         }
 
 
+        $homeDirectory = getenv('HOMEPATH');
+            
+        if ($homeDirectory) {
+            $this->_logMessage('Home directory found in environment variable HOMEPATH with value ' . $homeDirectory, $returnMessages);
+            if (!$mustExist || ($mustExist && file_exists($homeDirectory))) {
+                return $homeDirectory;
+            } else {
+                $this->_logMessage('Home directory does not exist at ' . $homeDirectory, $returnMessages);
+            }
+        }
+        
+        return false;
     }
     }
     
     
-}
-
-
-
-function zf_setup_php_runtime() {
-    global $_zf;
-    if (!isset($_zf['CONFIG_TYPE']) || $_zf['CONFIG_TYPE'] !== 'ini') {
-        return;
+    /**
+     * _detectStorageDirectory() - Detect where the storage directory is from a variaty of possiblities
+     * 
+     * @param $mustExist Should the returned value already exist in the file system
+     * @param $returnMessages Should it log messages for output later
+     * @return string
+     */
+    protected function _detectStorageDirectory($mustExist = true, $returnMessages = true)
+    {
+        $storageDirectory = false;
+        
+        $storageDirectory = getenv('ZF_STORAGE_DIR');
+        if ($storageDirectory) {
+            $this->_logMessage('Storage directory path found in environment variable ZF_STORAGE_DIR with value ' . $storageDirectory, $returnMessages);
+            if (!$mustExist || ($mustExist && file_exists($storageDirectory))) {
+                return $storageDirectory;
+            } else {
+                $this->_logMessage('Storage directory does not exist at ' . $storageDirectory, $returnMessages);
+            }
+        }
+        
+        $homeDirectory = ($this->_homeDirectory) ? $this->_homeDirectory : $this->_detectHomeDirectory(true, false); 
+        
+        if ($homeDirectory) {
+            $storageDirectory = $homeDirectory . '/.zf/';
+            $this->_logMessage('Storage directory assumed in home directory at location ' . $storageDirectory, $returnMessages);
+            if (!$mustExist || ($mustExist && file_exists($storageDirectory))) {
+                return $storageDirectory;
+            } else {
+                $this->_logMessage('Storage directory does not exist at ' . $storageDirectory, $returnMessages);
+            }
+        }
+        
+        return false;
     }
     }
-    $zfini_settings = parse_ini_file($_zf['CONFIG_FILE']);
-    $phpini_settings = ini_get_all();
-    foreach ($zfini_settings as $zfini_key => $zfini_value) {
-        if (substr($zfini_key, 0, 4) === 'php.') {
-            $phpini_key = substr($zfini_key, 4); 
-            if (array_key_exists($phpini_key, $phpini_settings)) {
-                ini_set($phpini_key, $zfini_value);
+    
+    /**
+     * _detectConfigFile() - Detect config file location from a variety of possibilities
+     * 
+     * @param $mustExist Should the returned value already exist in the file system
+     * @param $returnMessages Should it log messages for output later
+     * @return string
+     */
+    protected function _detectConfigFile($mustExist = true, $returnMessages = true)
+    {
+        $configFile = null;
+        
+        $configFile = getenv('ZF_CONFIG_FILE');
+        if ($configFile) {
+            $this->_logMessage('Config file found environment variable ZF_CONFIG_FILE at ' . $configFile, $returnMessages);
+            if (!$mustExist || ($mustExist && file_exists($configFile))) {
+                return $configFile;
+            } else {
+                $this->_logMessage('Config file does not exist at ' . $configFile, $returnMessages);
             }
             }
         }
         }
+        
+        $homeDirectory = ($this->_homeDirectory) ? $this->_homeDirectory : $this->_detectHomeDirectory(true, false);
+        if ($homeDirectory) {
+            $configFile = $homeDirectory . '/.zf.ini';
+            $this->_logMessage('Config file assumed in home directory at location ' . $configFile, $returnMessages);
+            if (!$mustExist || ($mustExist && file_exists($configFile))) {
+                return $configFile;
+            } else {
+                $this->_logMessage('Config file does not exist at ' . $configFile, $returnMessages);
+            }
+        }
+        
+        $storageDirectory = ($this->_storageDirectory) ? $this->_storageDirectory : $this->_detectStorageDirectory(true, false);
+        if ($storageDirectory) {
+            $configFile = $storageDirectory . '/zf.ini';
+            $this->_logMessage('Config file assumed in storage directory at location ' . $configFile, $returnMessages);
+            if (!$mustExist || ($mustExist && file_exists($configFile))) {
+                return $configFile;
+            } else {
+                $this->_logMessage('Config file does not exist at ' . $configFile, $returnMessages);
+            }
+        }
+        
+        return false;
     }
     }
-}
+    
 
 
-function zf_setup_tool_runtime() {
-    //global $_zf;
+    /**
+     * _setupPHPRuntime() - parse the config file if it exists for php ini values to set
+     * 
+     * @return void
+     */
+    protected function _setupPHPRuntime()
+    {
+    	// set php runtime settings
+    	ini_set('display_errors', true);
+    	
+        // support the changing of the current working directory, necessary for some providers
+        if (isset($_ENV['ZEND_TOOL_CURRENT_WORKING_DIRECTORY'])) {
+            chdir($_ENV['ZEND_TOOL_CURRENT_WORKING_DIRECTORY']);
+        }
+    	
+        if (!$this->_configFile) {
+            return;
+        }
+        $zfINISettings = parse_ini_file($this->_configFile);
+        $phpINISettings = ini_get_all();
+        foreach ($zfINISettings as $zfINIKey => $zfINIValue) {
+            if (substr($zfINIKey, 0, 4) === 'php.') {
+                $phpINIKey = substr($zfINIKey, 4); 
+                if (array_key_exists($phpINIKey, $phpINISettings)) {
+                    ini_set($phpINIKey, $zfINIValue);
+                }
+            }
+        }
 
 
-    // last ditch efforts
-    if (zf_try_client_load()) {
-        return;
+        return null;
     }
     }
     
     
-    $zfIncludePath['original'] = get_include_path();
-    
-    // if ZF is not in the include_path, but relative to this file, put it in the include_path
-    if (($zfIncludePath['prepend'] = getenv('ZEND_TOOL_INCLUDE_PATH_PREPEND')) || ($zfIncludePath['whole'] = getenv('ZEND_TOOL_INCLUDE_PATH'))) {
-        if (isset($zfIncludePath['prepend']) && ($zfIncludePath['prepend'] !== false) && (($zfIncludePath['prependRealpath'] = realpath($zfIncludePath['prepend'])) !== false)) {
-            set_include_path($zfIncludePath['prependRealpath'] . PATH_SEPARATOR . $zfIncludePath['original']);
-        } elseif (isset($zfIncludePath['whole']) && ($zfIncludePath['whole'] !== false) && (($zfIncludePath['wholeRealpath'] = realpath($zfIncludePath['whole'])) !== false)) {
-            set_include_path($zfIncludePath['wholeRealpath']);
+    /**
+     * _setupToolRuntime() - setup the tools include_path and load the proper framwork parts that
+     * enable Zend_Tool to work.
+     * 
+     * @return void
+     */
+    protected function _setupToolRuntime()
+    {
+
+        // last ditch efforts
+        if ($this->_tryClientLoad()) {
+            return;
+        }
+        
+        // if ZF is not in the include_path, but relative to this file, put it in the include_path
+        if (($includePathPrepend = getenv('ZEND_TOOL_INCLUDE_PATH_PREPEND')) || ($includePathFull = getenv('ZEND_TOOL_INCLUDE_PATH'))) {
+            if (isset($includePathPrepend) && ($includePathPrepend !== false)) {
+                set_include_path($includePathPrepend . PATH_SEPARATOR . get_include_path());
+            } elseif (isset($includePathFull) && ($includePathFull !== false)) {
+                set_include_path($includePathFull);
+            }
+        }
+        
+        if ($this->_tryClientLoad()) {
+            return;
+        }
+        
+        $zfIncludePath['relativePath'] = dirname(__FILE__) . '/../library/';
+        if (file_exists($zfIncludePath['relativePath'] . 'Zend/Tool/Framework/Client/Console.php')) {
+            set_include_path(realpath($zfIncludePath['relativePath']) . PATH_SEPARATOR . get_include_path());
         }
         }
-    }
     
     
-    if (zf_try_client_load()) {
-        return;
+        if (!$this->_tryClientLoad()) {
+            $this->_mode = 'runError';
+            return;
+        }
+        
+        return null;
     }
     }
     
     
-    $zfIncludePath['relativePath'] = dirname(__FILE__) . '/../library/';
-    if (file_exists($zfIncludePath['relativePath'] . 'Zend/Tool/Framework/Client/Console.php')) {
-        set_include_path(realpath($zfIncludePath['relativePath']) . PATH_SEPARATOR . get_include_path());
-    }
-
-    if (!zf_try_client_load()) {
-        zf_display_error();
-        exit(1);
+    /**
+     * _tryClientLoad() - Attempt to load the Zend_Tool_Framework_Client_Console to enable the tool to run.
+     * 
+     * This method will return false if its not loaded to allow the consumer to alter the environment in such
+     * a way that it can be called again to try loading the proper file/class.
+     * 
+     * @return bool if the client is actuall loaded or not
+     */
+    protected function _tryClientLoad()
+    {
+        $this->_clientLoaded = false;
+        $fh = @fopen('Zend/Tool/Framework/Client/Console.php', 'r', true);
+        if (!$fh) {
+            return $this->_clientLoaded; // false
+        } else {
+            fclose($fh);
+            unset($fh);
+            include 'Zend/Tool/Framework/Client/Console.php';
+            $this->_clientLoaded = class_exists('Zend_Tool_Framework_Client_Console');
+        }
+        
+        return $this->_clientLoaded;
     }
     }
     
     
-}
-
-function zf_try_client_load() {
-    $loaded = @include_once 'Zend/Tool/Framework/Client/Console.php';
-    return $loaded;
-}
-
-/**
- * zf_display_error()
- */
-function zf_display_error() {
-    
-    echo <<<EOS
+    /**
+     * _runError() - Output the error screen that tells the user that the tool was not setup
+     * in a sane way
+     * 
+     * @return void
+     */
+    protected function _runError()
+    {
+        
+        echo <<<EOS
     
     
 ***************************** ZF ERROR ********************************
 ***************************** ZF ERROR ********************************
 In order to run the zf command, you need to ensure that Zend Framework
 In order to run the zf command, you need to ensure that Zend Framework
-is inside your include_path.  If you are running this tool without 
-ZendFramework in your include_path, you can alternatively set one of 
-two environment variables to for this tool to work:
-
-a) ZEND_TOOL_INCLUDE_PATH_PREPEND="/path/to/ZendFramework/library"
+is inside your include_path.  There are a variety of ways that you can
+ensure that this zf command line tool knows where the Zend Framework
+library is on your system, but not all of them can be described here.
 
 
-OR alternatively
+The easiest way to get the zf command running is to allow is to give it
+the include path via an environment variable ZEND_TOOL_INCLUDE_PATH or
+ZEND_TOOL_INCLUDE_PATH_PREPEND with the proper include path to use,
+then run the command "zf --setup".  This command is designed to create
+a storage location for your user, as well as create the zf.ini file
+that the zf command will consult in order to run properly on your
+system.  
 
 
-b) ZEND_TOOL_INCLUDE_PATH="/path/to/ZendFramework/library"
+Example you would run:
 
 
-The former (a) will make the specified Zend Framework first in the
-include_path whereas the latter (b) will replace the include_path
-with the specified path.
+$ ZEND_TOOL_INCLUDE_PATH=/path/to/library zf --setup
 
 
-Information:
+Your are encourged to read more in the link that follows.
 
 
 EOS;
 EOS;
 
 
-    echo '    attempted include_path: ' . get_include_path() . PHP_EOL;
-    echo '    script location: ' . $_SERVER['SCRIPT_NAME'] . PHP_EOL;
+        return null;
+    }
+    
+    /**
+     * _runInfo() - this command will produce information about the setup of this script and
+     * Zend_Tool
+     * 
+     * @return void
+     */
+    protected function _runInfo()
+    {
+        echo 'Zend_Tool & CLI Setup Information' . PHP_EOL
+           . '(available via the command line "zf --info")' 
+           . PHP_EOL;
+        
+        echo '   * ' . implode(PHP_EOL . '   * ', $this->_messages) . PHP_EOL;
+        
+        echo PHP_EOL;
+        
+        echo 'To change the setup of this tool, run: "zf --setup"';
+           
+        echo PHP_EOL;
 
 
-}
+    }
+    
+    /**
+     * _runSetup() - parse the request to see which setup command to run
+     * 
+     * @return void
+     */
+    protected function _runSetup()
+    {
+        $setupCommand = (isset($_SERVER['argv'][2])) ? $_SERVER['argv'][2] : null;
+        
+        switch ($setupCommand) {
+            case 'storage-directory':
+                $this->_runSetupStorageDirectory();
+                break;
+            case 'config-file':
+                $this->_runSetupConfigFile();
+                break;
+            default:
+                $this->_runSetupMoreInfo();
+                break;
+        }
+        
+        return null;
+    }
 
 
-function zf_run($zfConfig) {
-    global $_zf;
-    unset($_zf);
+    /**
+     * _runSetupStorageDirectory() - if the storage directory does not exist, create it
+     * 
+     * @return void
+     */
+    protected function _runSetupStorageDirectory()
+    {
+        $storageDirectory = $this->_detectStorageDirectory(false, false);
+        
+        if (file_exists($storageDirectory)) {
+            echo 'Directory already exists at ' . $storageDirectory . PHP_EOL
+               . 'Cannot create storage directory.';
+            return;
+        }
+        
+        mkdir($storageDirectory);
+        
+        echo 'Storage directory created at ' . $storageDirectory . PHP_EOL;
+    }
+
+    /**
+     * _runSetupConfigFile()
+     * 
+     * @return void
+     */
+    protected function _runSetupConfigFile()
+    {
+        $configFile = $this->_detectConfigFile(false, false);
+        
+        if (file_exists($configFile)) {
+            echo 'File already exists at ' . $configFile . PHP_EOL
+               . 'Cannot write new config file.';
+            return;
+        }
+        
+        $includePath = get_include_path();
+        
+        $contents = 'php.include_path = "' . $includePath . '"';
+        
+        file_put_contents($configFile, $contents);
+        
+        $iniValues = ini_get_all();
+        if ($iniValues['include_path']['global_value'] != $iniValues['include_path']['local_value']) {
+            echo 'NOTE: the php include_path to be used with the tool has been written' . PHP_EOL
+               . 'to the config file, using ZF_INCLUDE_PATH (or other include_path setters)' . PHP_EOL
+               . 'is no longer necessary.' . PHP_EOL . PHP_EOL;
+        }
+        
+        echo 'Config file written to ' . $configFile . PHP_EOL;
+        
+        return null;
+    }
+
+    /**
+     * _runSetupMoreInfo() - return more information about what can be setup, and what is setup
+     * 
+     * @return void
+     */
+    protected function _runSetupMoreInfo()
+    {
+        $homeDirectory    = $this->_detectHomeDirectory(false, false);
+        $storageDirectory = $this->_detectStorageDirectory(false, false);
+        $configFile       = $this->_detectConfigFile(false, false);
+        
+        echo <<<EOS
+
+ZF Command Line Tool - Setup
+----------------------------
+        
+Current Paths (Existing or not):
+    Home Directory: {$homeDirectory}
+    Storage Directory: {$storageDirectory}
+    Config File: {$configFile}
+
+Important Environment Variables:
+    ZF_HOME 
+        - the directory this tool will look for a home directory
+        - directory must exist
+    ZF_STORAGE_DIRECTORY 
+        - where this tool will look for a storage directory
+        - directory must exist
+    ZF_CONFIG_FILE 
+        - where this tool will look for a configuration file
+    ZF_INCLUDE_PATH
+        - set the include_path for this tool to use this value
+    ZF_INCLUDE_PATH_PREPEND
+        - prepend the current php.ini include_path with this value
     
     
-    $configOptions = array();
-    if (isset($zfConfig['CONFIG_FILE'])) {
-        $configOptions['configOptions']['configFilepath'] = $zfConfig['CONFIG_FILE'];
+Search Order:
+    Home Directory:
+        - ZF_HOME, then HOME (*nix), then HOMEPATH (windows)
+    Storage Directory:
+        - ZF_STORAGE_DIR, then {home}/.zf/
+    Config File:
+        - ZF_CONFIG_FILE, then {home}/.zf.ini, then {home}/zf.ini,
+          then {storage}/zf.ini
+
+Commands:
+    zf --setup storage-directory
+        - setup the storage directory, directory will be created
+    zf --setup config-file
+        - create the config file with some default values
+
+
+EOS;
     }
     }
-    if (isset($zfConfig['STORAGE_DIR'])) {
-        $configOptions['storageOptions']['directory'] = $zfConfig['STORAGE_DIR'];
+    
+    /**
+     * _runTool() - This is where the magic happens, dispatch Zend_Tool
+     * 
+     * @return void
+     */
+    protected function _runTool()
+    {
+	    
+	    $configOptions = array();
+	    if (isset($this->_configFile) && $this->_configFile) {
+	        $configOptions['configOptions']['configFilepath'] = $this->_configFile;
+	    }
+	    if (isset($this->_storageDirectory) && $this->_storageDirectory) {
+	        $configOptions['storageOptions']['directory'] = $this->_storageDirectory;
+	    }
+	    
+	    // ensure that zf.php loads the Zend_Tool_Project features
+	    $configOptions['classesToLoad'] = 'Zend_Tool_Project_Provider_Manifest';
+	    
+	    $console = new Zend_Tool_Framework_Client_Console($configOptions);
+	    $console->dispatch();
+		return null;
     }
     }
 
 
-    Zend_Tool_Framework_Client_Console::main($configOptions);    
+    /**
+     * _logMessage() - Internal method used to log setup and information messages.
+     * 
+     * @param $message
+     * @param $storeMessage
+     * @return void
+     */
+    protected function _logMessage($message, $storeMessage = true)
+    {
+        if (!$storeMessage) {
+            return;
+        }
+        
+        $this->_messages[] = $message;
+    }
+    
+    
 }
 }
 
 
+if (!getenv('ZF_NO_MAIN')) {
+    ZF::main();
+}
 
 
 
 

+ 2 - 1
bin/zf.sh

@@ -41,4 +41,5 @@ else
     PHP_DIR="$(dirname "$SELF_LINK")"
     PHP_DIR="$(dirname "$SELF_LINK")"
 fi
 fi
 
 
-"$PHP_BIN" -d safe_mode=Off -f "$PHP_DIR/zf.php" -- $@
+"$PHP_BIN" -d safe_mode=Off -f "$PHP_DIR/zf.php" -- "$@"
+

+ 36 - 17
library/Zend/Tool/Framework/Client/Abstract.php

@@ -21,15 +21,14 @@
  */
  */
 
 
 /**
 /**
- * @see Zend_Tool_Framework_Registry_EnabledInterface
+ * @see Zend_Loader_Autoloader
  */
  */
-require_once 'Zend/Tool/Framework/Registry/EnabledInterface.php';
+require_once 'Zend/Loader/Autoloader.php';
 
 
 /**
 /**
- * @see Zend_Tool_Framework_Registry
+ * @see Zend_Tool_Framework_Registry_EnabledInterface
  */
  */
-require_once 'Zend/Tool/Framework/Registry.php';
-
+require_once 'Zend/Tool/Framework/Registry/EnabledInterface.php';
 
 
 /**
 /**
  * @category   Zend
  * @category   Zend
@@ -62,6 +61,16 @@ abstract class Zend_Tool_Framework_Client_Abstract implements Zend_Tool_Framewor
 
 
     public function __construct($options = array())
     public function __construct($options = array())
     {
     {
+        // require autoloader 
+        Zend_Loader_Autoloader::getInstance();
+
+        // this might look goofy, but this is setting up the
+        // registry for dependency injection into the client
+        $registry = new Zend_Tool_Framework_Registry();
+        $registry->setClient($this);
+
+        // NOTE: at this moment, $this->_registry should contain the registry object
+        
         if ($options) {
         if ($options) {
             $this->setOptions($options);
             $this->setOptions($options);
         }
         }
@@ -96,17 +105,12 @@ abstract class Zend_Tool_Framework_Client_Abstract implements Zend_Tool_Framewor
             return;
             return;
         }
         }
 
 
-        // this might look goofy, but this is setting up the
-        // registry for dependency injection into the client
-        $registry = new Zend_Tool_Framework_Registry();
-        $registry->setClient($this);
-
-        // NOTE: at this moment, $this->_registry should contain
-        // the registry object
-
         // run any preInit
         // run any preInit
         $this->_preInit();
         $this->_preInit();
 
 
+        $manifest = $this->_registry->getManifestRepository();
+        $manifest->addManifest(new Zend_Tool_Framework_Client_Manifest());
+        
         // setup the debug log
         // setup the debug log
         if (!$this->_debugLogger instanceof Zend_Log) {
         if (!$this->_debugLogger instanceof Zend_Log) {
             require_once 'Zend/Log.php';
             require_once 'Zend/Log.php';
@@ -173,6 +177,16 @@ abstract class Zend_Tool_Framework_Client_Abstract implements Zend_Tool_Framewor
         $this->_registry = $registry;
         $this->_registry = $registry;
         return $this;
         return $this;
     }
     }
+    
+    /**
+     * getRegistry();
+     * 
+     * @return Zend_Tool_Framework_Registry_Interface
+     */
+    public function getRegistry()
+    {
+    	return $this->_registry;
+    }
 
 
     /**
     /**
      * hasInteractiveInput() - Convienence method for determining if this
      * hasInteractiveInput() - Convienence method for determining if this
@@ -304,10 +318,15 @@ abstract class Zend_Tool_Framework_Client_Abstract implements Zend_Tool_Framewor
             $methodName .= $specialtyName;
             $methodName .= $specialtyName;
         }
         }
 
 
-        if (method_exists($provider, $methodName)) {
-            call_user_func_array(array($provider, $methodName), $callParameters);
-        } elseif (method_exists($provider, $methodName . 'Action')) {
-            call_user_func_array(array($provider, $methodName . 'Action'), $callParameters);
+        $this->_handleDispatchExecution($provider, $methodName, $callParameters);
+    }
+    
+    protected function _handleDispatchExecution($class, $methodName, $callParameters)
+    {
+        if (method_exists($class, $methodName)) {
+            call_user_func_array(array($class, $methodName), $callParameters);
+        } elseif (method_exists($class, $methodName . 'Action')) {
+            call_user_func_array(array($class, $methodName . 'Action'), $callParameters);
         } else {
         } else {
             require_once 'Zend/Tool/Framework/Client/Exception.php';
             require_once 'Zend/Tool/Framework/Client/Exception.php';
             throw new Zend_Tool_Framework_Client_Exception('Not a supported method.');
             throw new Zend_Tool_Framework_Client_Exception('Not a supported method.');

+ 147 - 8
library/Zend/Tool/Framework/Client/Config.php

@@ -36,6 +36,9 @@ class Zend_Tool_Framework_Client_Config
      */
      */
     protected $_config = null;
     protected $_config = null;
 
 
+    /**
+     * @param array $options
+     */
     public function __config($options = array())
     public function __config($options = array())
     {
     {
         if ($options) {
         if ($options) {
@@ -43,6 +46,9 @@ class Zend_Tool_Framework_Client_Config
         }
         }
     }
     }
 
 
+    /**
+     * @param array $options
+     */
     public function setOptions(Array $options)
     public function setOptions(Array $options)
     {
     {
         foreach ($options as $optionName => $optionValue) {
         foreach ($options as $optionName => $optionValue) {
@@ -53,6 +59,10 @@ class Zend_Tool_Framework_Client_Config
         }
         }
     }
     }
 
 
+    /**
+     * @param  string $configFilepath
+     * @return Zend_Tool_Framework_Client_Config
+     */
     public function setConfigFilepath($configFilepath)
     public function setConfigFilepath($configFilepath)
     {
     {
         if (!file_exists($configFilepath)) {
         if (!file_exists($configFilepath)) {
@@ -61,21 +71,32 @@ class Zend_Tool_Framework_Client_Config
         }
         }
 
 
         $this->_configFilepath = $configFilepath;
         $this->_configFilepath = $configFilepath;
+        $this->loadConfig($configFilepath);
+        
+        return $this;
+    }
 
 
+    /**
+     * Load the configuration from the given path.
+     * 
+     * @param string $configFilepath
+     */
+    protected function loadConfig($configFilepath)
+    {
         $suffix = substr($configFilepath, -4);
         $suffix = substr($configFilepath, -4);
 
 
         switch ($suffix) {
         switch ($suffix) {
             case '.ini':
             case '.ini':
                 require_once 'Zend/Config/Ini.php';
                 require_once 'Zend/Config/Ini.php';
-                $this->_config = new Zend_Config_Ini($configFilepath);
+                $this->_config = new Zend_Config_Ini($configFilepath, null, array('allowModifications' => true));
                 break;
                 break;
             case '.xml':
             case '.xml':
                 require_once 'Zend/Config/Xml.php';
                 require_once 'Zend/Config/Xml.php';
-                $this->_config = new Zend_Config_Xml($configFilepath);
+                $this->_config = new Zend_Config_Xml($configFilepath, null, array('allowModifications' => true));
                 break;
                 break;
             case '.php':
             case '.php':
                 require_once 'Zend/Config.php';
                 require_once 'Zend/Config.php';
-                $this->_config = new Zend_Config(include $configFilepath);
+                $this->_config = new Zend_Config(include $configFilepath, true);
                 break;
                 break;
             default:
             default:
                 require_once 'Zend/Tool/Framework/Client/Exception.php';
                 require_once 'Zend/Tool/Framework/Client/Exception.php';
@@ -83,23 +104,141 @@ class Zend_Tool_Framework_Client_Config
                     . $suffix . ' at location ' . $configFilepath
                     . $suffix . ' at location ' . $configFilepath
                     );
                     );
         }
         }
-
-        return $this;
     }
     }
 
 
+    /**
+     * Return the filepath of the configuration.
+     * 
+     * @return string
+     */
     public function getConfigFilepath()
     public function getConfigFilepath()
     {
     {
         return $this->_configFilepath;
         return $this->_configFilepath;
     }
     }
 
 
-    public function get($name, $defaultValue)
+    /**
+     * Get a configuration value.
+     * 
+     * @param string $name
+     * @param string $defaultValue
+     * @return mixed
+     */
+    public function get($name, $defaultValue=null)
     {
     {
-        return $this->_config->get($name, $defaultValue);
+        return $this->getConfigInstance()->get($name, $defaultValue);
     }
     }
 
 
+    /**
+     * Get a configuration value
+     *
+     * @param string $name
+     * @return mixed
+     */
     public function __get($name)
     public function __get($name)
     {
     {
-        return $this->_config->{$name};
+        return $this->getConfigInstance()->{$name};
+    }
+
+    /**
+     * Check if a configuration value isset.
+     *
+     * @param  string $name
+     * @return boolean
+     */
+    public function __isset($name)
+    {
+        if($this->exists() == false) {
+            return false;
+        }
+        return isset($this->getConfigInstance()->{$name});
+    }
+
+    /**
+     * @param string $name
+     */
+    public function __unset($name)
+    {
+        unset($this->getConfigInstance()->$name);
+    }
+
+    /**
+     * @param string $name
+     * @param mixed $value
+     */
+    public function __set($name, $value)
+    {
+        return $this->getConfigInstance()->$name = $value;
     }
     }
 
 
+    /**
+     * Check if the User profile has a configuration.
+     *
+     * @return bool
+     */
+    public function exists()
+    {
+        return ($this->_config!==null);
+    }
+
+    /**
+     * @throws Zend_Tool_Framework_Client_Exception
+     * @return Zend_Config
+     */
+    public function getConfigInstance()
+    {
+        if(!$this->exists()) {
+            require_once "Zend/Tool/Framework/Client/Exception.php";
+            throw new Zend_Tool_Framework_Client_Exception("Client has no persistent configuration.");
+        }
+
+        return $this->_config;
+    }
+
+    /**
+     * Save changes to the configuration into persistence.
+     *
+     * @return bool
+     */
+    public function save()
+    {
+        if($this->exists()) {
+            $writer = $this->getConfigWriter();
+            $writer->write($this->getConfigFilepath(), $this->getConfigInstance(), true);
+            $this->loadConfig($this->getConfigFilepath());
+
+            return true;
+        }
+        return false;
+    }
+
+    /**
+     * Get the config writer that corresponds to the current config file type.
+     *
+     * @return Zend_Config_Writer_FileAbstract
+     */
+    protected function getConfigWriter()
+    {
+        $suffix = substr($this->getConfigFilepath(), -4);
+        switch($suffix) {
+            case '.ini':
+                require_once "Zend/Config/Writer/Ini.php";
+                $writer = new Zend_Config_Writer_Ini();
+                $writer->setRenderWithoutSections();
+                break;
+            case '.xml':
+                require_once "Zend/Config/Writer/Xml.php";
+                $writer = new Zend_Config_Writer_Xml();
+                break;
+            case '.php':
+                require_once "Zend/Config/Writer/Array.php";
+                $writer = new Zend_Config_Writer_Array();
+                break;
+            default:
+                require_once 'Zend/Tool/Framework/Client/Exception.php';
+                throw new Zend_Tool_Framework_Client_Exception('Unknown config file type '
+                    . $suffix . ' at location ' . $this->getConfigFilepath()
+                    );
+        }
+        return $writer;
+    }
 }
 }

+ 55 - 42
library/Zend/Tool/Framework/Client/Console.php

@@ -21,21 +21,11 @@
  */
  */
 
 
 /**
 /**
- * @see Zend_Loader
- */
-require_once 'Zend/Loader.php';
-
-/**
  * @see Zend_Tool_Framework_Client_Abstract
  * @see Zend_Tool_Framework_Client_Abstract
  */
  */
 require_once 'Zend/Tool/Framework/Client/Abstract.php';
 require_once 'Zend/Tool/Framework/Client/Abstract.php';
 
 
 /**
 /**
- * @see Zend_Tool_Framework_Client_Console_ArgumentParser
- */
-require_once 'Zend/Tool/Framework/Client/Console/ArgumentParser.php';
-
-/**
  * @see Zend_Tool_Framework_Client_Interactive_InputInterface
  * @see Zend_Tool_Framework_Client_Interactive_InputInterface
  */
  */
 require_once 'Zend/Tool/Framework/Client/Interactive/InputInterface.php';
 require_once 'Zend/Tool/Framework/Client/Interactive/InputInterface.php';
@@ -46,11 +36,6 @@ require_once 'Zend/Tool/Framework/Client/Interactive/InputInterface.php';
 require_once 'Zend/Tool/Framework/Client/Interactive/OutputInterface.php';
 require_once 'Zend/Tool/Framework/Client/Interactive/OutputInterface.php';
 
 
 /**
 /**
- * @see Zend_Tool_Framework_Client_Response_ContentDecorator_Separator
- */
-require_once 'Zend/Tool/Framework/Client/Response/ContentDecorator/Separator.php';
-
-/**
  * Zend_Tool_Framework_Client_Console - the CLI Client implementation for Zend_Tool_Framework
  * Zend_Tool_Framework_Client_Console - the CLI Client implementation for Zend_Tool_Framework
  *
  *
  * @category   Zend
  * @category   Zend
@@ -85,37 +70,57 @@ class Zend_Tool_Framework_Client_Console
     protected $_filterFromClientNaming = null;
     protected $_filterFromClientNaming = null;
 
 
     /**
     /**
+     * @var array
+     */
+    protected $_classesToLoad = array();
+    
+    /**
      * main() - This is typically called from zf.php. This method is a
      * main() - This is typically called from zf.php. This method is a
      * self contained main() function.
      * self contained main() function.
      *
      *
      */
      */
     public static function main($options = array())
     public static function main($options = array())
     {
     {
-        ini_set('display_errors', true);
         $cliClient = new self($options);
         $cliClient = new self($options);
         $cliClient->dispatch();
         $cliClient->dispatch();
     }
     }
 
 
+    /**
+     * getName() - return the name of the client, in this case 'console'
+     *
+     * @return string
+     */
+    public function getName()
+    {
+        return 'console';
+    }
+    
+    /**
+     * setConfigOptions()
+     * 
+     * @param $configOptions
+     */
     public function setConfigOptions($configOptions)
     public function setConfigOptions($configOptions)
     {
     {
         $this->_configOptions = $configOptions;
         $this->_configOptions = $configOptions;
         return $this;
         return $this;
     }
     }
 
 
+    /**
+     * setStorageOptions()
+     * 
+     * @param $storageOptions
+     */
     public function setStorageOptions($storageOptions)
     public function setStorageOptions($storageOptions)
     {
     {
         $this->_storageOptions = $storageOptions;
         $this->_storageOptions = $storageOptions;
         return $this;
         return $this;
     }
     }
-
-    /**
-     * getName() - return the name of the client, in this case 'console'
-     *
-     * @return string
-     */
-    public function getName()
+    
+    public function setClassesToLoad($classesToLoad)
     {
     {
-        return 'console';
+    	$this->_classesToLoad = $classesToLoad;
+    	return $this;
     }
     }
 
 
     /**
     /**
@@ -133,26 +138,36 @@ class Zend_Tool_Framework_Client_Console
         $storage = $this->_registry->getStorage();
         $storage = $this->_registry->getStorage();
 
 
         if ($this->_storageOptions != null && isset($this->_storageOptions['directory'])) {
         if ($this->_storageOptions != null && isset($this->_storageOptions['directory'])) {
-            require_once 'Zend/Tool/Framework/Client/Storage/Directory.php';
             $storage->setAdapter(
             $storage->setAdapter(
                 new Zend_Tool_Framework_Client_Storage_Directory($this->_storageOptions['directory'])
                 new Zend_Tool_Framework_Client_Storage_Directory($this->_storageOptions['directory'])
                 );
                 );
         }
         }
 
 
-        // support the changing of the current working directory, necessary for some providers
-        if (isset($_ENV['ZEND_TOOL_CURRENT_WORKING_DIRECTORY'])) {
-            chdir($_ENV['ZEND_TOOL_CURRENT_WORKING_DIRECTORY']);
+        // which classes are essential to initializing Zend_Tool_Framework_Client_Console
+        $classesToLoad = array(
+            'Zend_Tool_Framework_Client_Console_Manifest',    
+            'Zend_Tool_Framework_System_Manifest'
+            );
+            
+        if ($this->_classesToLoad) {
+        	if (is_string($this->_classesToLoad)) {
+        		$classesToLoad[] = $this->_classesToLoad;
+        	} elseif (is_array($this->_classesToLoad)) {
+        		$classesToLoad = array_merge($classesToLoad, $this->_classesToLoad);
+        	}
         }
         }
-
-        // support setting the loader from the environment
-        if (isset($_ENV['ZEND_TOOL_FRAMEWORK_LOADER_CLASS'])) {
-            if (class_exists($_ENV['ZEND_TOOL_FRAMEWORK_LOADER_CLASS'])
-                || Zend_Loader::loadClass($_ENV['ZEND_TOOL_FRAMEWORK_LOADER_CLASS'])
-            ) {
-                $this->_registry->setLoader(new $_ENV['ZEND_TOOL_FRAMEWORK_LOADER_CLASS']);
+        
+        // add classes to the basic loader from the config file basicloader.classes.1 ..
+        if (isset($config->basicloader) && isset($config->basicloader->classes)) {
+            foreach ($config->basicloader->classes as $classKey => $className) {
+                array_push($classesToLoad, $className);
             }
             }
         }
         }
 
 
+        $this->_registry->setLoader(
+            new Zend_Tool_Framework_Loader_BasicLoader(array('classesToLoad' => $classesToLoad))
+            );
+
         return;
         return;
     }
     }
 
 
@@ -164,11 +179,14 @@ class Zend_Tool_Framework_Client_Console
     {
     {
         $response = $this->_registry->getResponse();
         $response = $this->_registry->getResponse();
 
 
+        $response->addContentDecorator(new Zend_Tool_Framework_Client_Console_ResponseDecorator_AlignCenter());
+        $response->addContentDecorator(new Zend_Tool_Framework_Client_Console_ResponseDecorator_Indention());
+        $response->addContentDecorator(new Zend_Tool_Framework_Client_Console_ResponseDecorator_Blockize());
+
         if (function_exists('posix_isatty')) {
         if (function_exists('posix_isatty')) {
-            require_once 'Zend/Tool/Framework/Client/Console/ResponseDecorator/Colorizer.php';
             $response->addContentDecorator(new Zend_Tool_Framework_Client_Console_ResponseDecorator_Colorizer());
             $response->addContentDecorator(new Zend_Tool_Framework_Client_Console_ResponseDecorator_Colorizer());
         }
         }
-
+        
         $response->addContentDecorator(new Zend_Tool_Framework_Client_Response_ContentDecorator_Separator())
         $response->addContentDecorator(new Zend_Tool_Framework_Client_Response_ContentDecorator_Separator())
             ->setDefaultDecoratorOptions(array('separator' => true));
             ->setDefaultDecoratorOptions(array('separator' => true));
 
 
@@ -190,7 +208,6 @@ class Zend_Tool_Framework_Client_Console
         $response = $this->_registry->getResponse();
         $response = $this->_registry->getResponse();
 
 
         if ($response->isException()) {
         if ($response->isException()) {
-            require_once 'Zend/Tool/Framework/Client/Console/HelpSystem.php';
             $helpSystem = new Zend_Tool_Framework_Client_Console_HelpSystem();
             $helpSystem = new Zend_Tool_Framework_Client_Console_HelpSystem();
             $helpSystem->setRegistry($this->_registry)
             $helpSystem->setRegistry($this->_registry)
                 ->respondWithErrorMessage($response->getException()->getMessage(), $response->getException())
                 ->respondWithErrorMessage($response->getException()->getMessage(), $response->getException())
@@ -258,9 +275,6 @@ class Zend_Tool_Framework_Client_Console
     public function convertToClientNaming($string)
     public function convertToClientNaming($string)
     {
     {
         if (!$this->_filterToClientNaming) {
         if (!$this->_filterToClientNaming) {
-            require_once 'Zend/Filter.php';
-            require_once 'Zend/Filter/Word/CamelCaseToDash.php';
-            require_once 'Zend/Filter/StringToLower.php';
             $filter = new Zend_Filter();
             $filter = new Zend_Filter();
             $filter->addFilter(new Zend_Filter_Word_CamelCaseToDash());
             $filter->addFilter(new Zend_Filter_Word_CamelCaseToDash());
             $filter->addFilter(new Zend_Filter_StringToLower());
             $filter->addFilter(new Zend_Filter_StringToLower());
@@ -284,7 +298,6 @@ class Zend_Tool_Framework_Client_Console
     public function convertFromClientNaming($string)
     public function convertFromClientNaming($string)
     {
     {
         if (!$this->_filterFromClientNaming) {
         if (!$this->_filterFromClientNaming) {
-            require_once 'Zend/Filter/Word/DashToCamelCase.php';
             $this->_filterFromClientNaming = new Zend_Filter_Word_DashToCamelCase();
             $this->_filterFromClientNaming = new Zend_Filter_Word_DashToCamelCase();
         }
         }
 
 

+ 43 - 14
library/Zend/Tool/Framework/Client/Console/ArgumentParser.php

@@ -26,6 +26,11 @@
 require_once 'Zend/Console/Getopt.php';
 require_once 'Zend/Console/Getopt.php';
 
 
 /**
 /**
+ * @see Zend_Tool_Framework_Registry_EnabledInterface
+ */
+require_once 'Zend/Tool/Framework/Registry/EnabledInterface.php';
+
+/**
  * @category   Zend
  * @category   Zend
  * @package    Zend_Tool
  * @package    Zend_Tool
  * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
  * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
@@ -271,14 +276,24 @@ class Zend_Tool_Framework_Client_Console_ArgumentParser implements Zend_Tool_Fra
             return;
             return;
         }
         }
 
 
-        // is the action name valid?
-        $actionMetadata = $this->_manifestRepository->getMetadata(array(
+        $actionSearchCriteria = array(
             'type'       => 'Tool',
             'type'       => 'Tool',
             'name'       => 'actionName',
             'name'       => 'actionName',
             'value'      => $consoleActionName,
             'value'      => $consoleActionName,
             'clientName' => 'console'
             'clientName' => 'console'
-            ));
+            );
+        
+        // is the action name valid?
+        $actionMetadata = $this->_manifestRepository->getMetadata($actionSearchCriteria);
 
 
+        // check for normalized names as well (all lower, no separators)
+        if (!$actionMetadata) {
+            $actionSearchCriteria['name']  = 'normalizedActionName';
+            $actionSearchCriteria['value'] = strtolower(str_replace(array('-', '_'), '', $consoleActionName));
+            $actionSearchCriteria['clientName'] = 'all';
+            $actionMetadata = $this->_manifestRepository->getMetadata($actionSearchCriteria);
+        }
+        
         // if no action, handle error
         // if no action, handle error
         if (!$actionMetadata) {
         if (!$actionMetadata) {
             require_once 'Zend/Tool/Framework/Client/Exception.php';
             require_once 'Zend/Tool/Framework/Client/Exception.php';
@@ -314,14 +329,24 @@ class Zend_Tool_Framework_Client_Console_ArgumentParser implements Zend_Tool_Fra
             return;
             return;
         }
         }
 
 
-        // get the cli provider names from the manifest
-        $providerMetadata = $this->_manifestRepository->getMetadata(array(
+        $providerSearchCriteria = array(
             'type'       => 'Tool',
             'type'       => 'Tool',
             'name'       => 'providerName',
             'name'       => 'providerName',
             'value'      => $consoleProviderName,
             'value'      => $consoleProviderName,
             'clientName' => 'console'
             'clientName' => 'console'
-            ));
+            );
+        
+        // get the cli provider names from the manifest
+        $providerMetadata = $this->_manifestRepository->getMetadata($providerSearchCriteria);
 
 
+        // check for normalized names as well (all lower, no separators)
+        if (!$providerMetadata) {
+            $providerSearchCriteria['name']  = 'normalizedProviderName';
+            $providerSearchCriteria['value'] = strtolower(str_replace(array('-', '_'), '', $consoleProviderName));
+            $providerSearchCriteria['clientName'] = 'all';
+            $providerMetadata = $this->_manifestRepository->getMetadata($providerSearchCriteria);
+        }
+            
         if (!$providerMetadata) {
         if (!$providerMetadata) {
             require_once 'Zend/Tool/Framework/Client/Exception.php';
             require_once 'Zend/Tool/Framework/Client/Exception.php';
             throw new Zend_Tool_Framework_Client_Exception(
             throw new Zend_Tool_Framework_Client_Exception(
@@ -337,15 +362,24 @@ class Zend_Tool_Framework_Client_Console_ArgumentParser implements Zend_Tool_Fra
             return;
             return;
         }
         }
 
 
-        $providerSpecialtyMetadata = $this->_manifestRepository->getMetadata(array(
+        $providerSpecialtySearchCriteria = array(
             'type'         => 'Tool',
             'type'         => 'Tool',
             'name'         => 'specialtyName',
             'name'         => 'specialtyName',
             'value'        => $consoleSpecialtyName,
             'value'        => $consoleSpecialtyName,
             'providerName' => $providerMetadata->getProviderName(),
             'providerName' => $providerMetadata->getProviderName(),
             'clientName'   => 'console'
             'clientName'   => 'console'
-            ));
+            );
+        
+        $providerSpecialtyMetadata = $this->_manifestRepository->getMetadata($providerSpecialtySearchCriteria);
 
 
         if (!$providerSpecialtyMetadata) {
         if (!$providerSpecialtyMetadata) {
+            $providerSpecialtySearchCriteria['name'] = 'normalizedSpecialtyName';
+            $providerSpecialtySearchCriteria['value'] = strtolower(str_replace(array('-', '_'), '', $consoleSpecialtyName));
+            $providerSpecialtySearchCriteria['clientName'] = 'all';
+            $providerSpecialtyMetadata = $this->_manifestRepository->getMetadata($providerSpecialtySearchCriteria);
+        }
+        
+        if (!$providerSpecialtyMetadata) {
             require_once 'Zend/Tool/Framework/Client/Exception.php';
             require_once 'Zend/Tool/Framework/Client/Exception.php';
             throw new Zend_Tool_Framework_Client_Exception(
             throw new Zend_Tool_Framework_Client_Exception(
                 'Provider \'' . $consoleSpecialtyName . '\' is not a valid specialty.'
                 'Provider \'' . $consoleSpecialtyName . '\' is not a valid specialty.'
@@ -428,7 +462,7 @@ class Zend_Tool_Framework_Client_Console_ArgumentParser implements Zend_Tool_Fra
 
 
         // if non-option arguments exist, attempt to process them before processing options
         // if non-option arguments exist, attempt to process them before processing options
         $wordStack = array();
         $wordStack = array();
-        while ($wordOnTop = array_shift($this->_argumentsWorking)) {
+        while (($wordOnTop = array_shift($this->_argumentsWorking))) {
             if (substr($wordOnTop, 0, 1) != '-') {
             if (substr($wordOnTop, 0, 1) != '-') {
                 array_push($wordStack, $wordOnTop);
                 array_push($wordStack, $wordOnTop);
             } else {
             } else {
@@ -463,11 +497,6 @@ class Zend_Tool_Framework_Client_Console_ArgumentParser implements Zend_Tool_Fra
             $this->_request->setProviderParameter($providerParamOption, $value);
             $this->_request->setProviderParameter($providerParamOption, $value);
         }
         }
 
 
-        /*
-        $this->_metadataProviderOptionsLong = $actionableMethodLongParamsMetadata;
-        $this->_metadataProviderOptionsShort = $actionableMethodShortParamsMetadata;
-        */
-
         $this->_argumentsWorking = $getoptParser->getRemainingArgs();
         $this->_argumentsWorking = $getoptParser->getRemainingArgs();
 
 
         return;
         return;

+ 3 - 7
library/Zend/Tool/Framework/Client/Console/HelpSystem.php

@@ -63,13 +63,9 @@ class Zend_Tool_Framework_Client_Console_HelpSystem
         // break apart the message into wrapped chunks
         // break apart the message into wrapped chunks
         $errorMessages = explode(PHP_EOL, wordwrap($errorMessage, 70, PHP_EOL, false));
         $errorMessages = explode(PHP_EOL, wordwrap($errorMessage, 70, PHP_EOL, false));
 
 
-        $text = '                       An Error Has Occurred                            ';
-        $this->_response->appendContent($text, array('color' => array('hiWhite', 'bgRed')));
-
-        foreach ($errorMessages as $errorMessage) {
-            $errorMessage = sprintf('%-70s', $errorMessage);
-            $this->_response->appendContent(' ' . $errorMessage . ' ', array('color' => array('white', 'bgRed')));
-        }
+        $text = 'An Error Has Occurred';
+        $this->_response->appendContent($text, array('color' => array('hiWhite', 'bgRed'), 'aligncenter' => true));
+        $this->_response->appendContent($errorMessage, array('indention' => 1, 'blockize' => 72, 'color' => array('white', 'bgRed')));
 
 
         if ($exception && $this->_registry->getRequest()->isDebug()) {
         if ($exception && $this->_registry->getRequest()->isDebug()) {
             $this->_response->appendContent($exception->getTraceAsString());
             $this->_response->appendContent($exception->getTraceAsString());

+ 66 - 0
library/Zend/Tool/Framework/Client/Console/ResponseDecorator/AlignCenter.php

@@ -0,0 +1,66 @@
+<?php
+/**
+ * Zend Framework
+ *
+ * LICENSE
+ *
+ * This source file is subject to the new BSD license that is bundled
+ * with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://framework.zend.com/license/new-bsd
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@zend.com so we can send you a copy immediately.
+ *
+ * @category   Zend
+ * @package    Zend_Tool
+ * @subpackage Framework
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ */
+
+require_once "Zend/Tool/Framework/Client/Response/ContentDecorator/Interface.php";
+
+/**
+ * Try to align a given text central on the screen.
+ *
+ * @category   Zend
+ * @package    Zend_Tool
+ * @subpackage Framework
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ * @version    $Id$
+ */
+class Zend_Tool_Framework_Client_Console_ResponseDecorator_AlignCenter
+    implements Zend_Tool_Framework_Client_Response_ContentDecorator_Interface
+{
+    public function getName()
+    {
+        return "aligncenter";
+    }
+
+    /**
+     * @param string $content
+     * @param integer $lineLength
+     */
+    public function decorate($content, $lineLength)
+    {
+        if(!is_numeric($lineLength)) {
+            $lineLength = 72;
+        }
+        if(strlen($content) < $lineLength) {
+            $append = false;
+            $len = strlen($content);
+            for($i = $len; $i < $lineLength; $i++) {
+                if($append == true) {
+                    $content = $content." ";
+                    $append = false;
+                } else {
+                    $content = " ".$content;
+                    $append = true;
+                }
+            }
+        }
+        return $content;
+    }
+}

+ 69 - 0
library/Zend/Tool/Framework/Client/Console/ResponseDecorator/Blockize.php

@@ -0,0 +1,69 @@
+<?php
+/**
+ * Zend Framework
+ *
+ * LICENSE
+ *
+ * This source file is subject to the new BSD license that is bundled
+ * with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://framework.zend.com/license/new-bsd
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@zend.com so we can send you a copy immediately.
+ *
+ * @category   Zend
+ * @package    Zend_Tool
+ * @subpackage Framework
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ */
+
+require_once "Zend/Tool/Framework/Client/Response/ContentDecorator/Interface.php";
+
+/**
+ * Take a text and block it into several lines of a fixed length.
+ *
+ * @category   Zend
+ * @package    Zend_Tool
+ * @subpackage Framework
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ * @version    $Id$
+ */
+class Zend_Tool_Framework_Client_Console_ResponseDecorator_Blockize
+    implements Zend_Tool_Framework_Client_Response_ContentDecorator_Interface
+{
+    public function getName()
+    {
+        return 'blockize';
+    }
+
+    /**
+     *
+     * @param  string $content
+     * @param  int $lineLength
+     * @return string
+     */
+    public function decorate($content, $lineLength)
+    {
+        if(intval(strval($lineLength)) != $lineLength) {
+            $lineLength = 72;
+        }
+
+        // break apart the message into wrapped chunks
+        $lines = explode(PHP_EOL, wordwrap($content, $lineLength, PHP_EOL, false));
+        $content = array();
+        foreach($lines AS $line) {
+            if(strlen(trim($line)) == 0) {
+                continue;
+            }
+
+            if(strlen($line) < $lineLength) {
+                $line .= str_repeat(" ", $lineLength-strlen($line));
+            }
+            $content[] = $line;
+        }
+        return implode(PHP_EOL, $content);
+    }
+}

+ 56 - 0
library/Zend/Tool/Framework/Client/Console/ResponseDecorator/Indention.php

@@ -0,0 +1,56 @@
+<?php
+/**
+ * Zend Framework
+ *
+ * LICENSE
+ *
+ * This source file is subject to the new BSD license that is bundled
+ * with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://framework.zend.com/license/new-bsd
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@zend.com so we can send you a copy immediately.
+ *
+ * @category   Zend
+ * @package    Zend_Tool
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ * @version    $Id$
+ */
+
+require_once "Zend/Tool/Framework/Client/Response/ContentDecorator/Interface.php";
+
+/**
+ * @category   Zend
+ * @package    Zend_Tool
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ */
+class Zend_Tool_Framework_Client_Console_ResponseDecorator_Indention
+    implements Zend_Tool_Framework_Client_Response_ContentDecorator_Interface
+{
+    public function getName()
+    {
+        return 'indention';
+    }
+
+    /**
+     * @param string $content
+     * @param integer $indention
+     */
+    public function decorate($content, $indention)
+    {
+        if(strval(intval($indention)) != $indention) {
+            return $content;
+        }
+
+        $newContent = "";
+        $lines = preg_split('((\r\n|\r|\n)+)', $content);
+        $lineIndention = str_repeat(' ', $indention);
+        foreach($lines AS $line) {
+            $newContent .= $lineIndention.$line.PHP_EOL;
+        }
+        return rtrim($newContent);
+    }
+}

+ 206 - 0
library/Zend/Tool/Framework/Client/Manifest.php

@@ -0,0 +1,206 @@
+<?php
+/**
+ * Zend Framework
+ *
+ * LICENSE
+ *
+ * This source file is subject to the new BSD license that is bundled
+ * with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://framework.zend.com/license/new-bsd
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@zend.com so we can send you a copy immediately.
+ *
+ * @category   Zend
+ * @package    Zend_Tool
+ * @subpackage Framework
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ * @version    $Id: Manifest.php 18386 2009-09-23 20:44:43Z ralph $
+ */
+
+/**
+ * @see Zend_Tool_Framework_Manifest_MetadataManifestable
+ */
+require_once 'Zend/Tool/Framework/Manifest/MetadataManifestable.php';
+
+/**
+ * @see Zend_Filter
+ */
+require_once 'Zend/Filter.php';
+
+/**
+ * @see Zend_Filter_Word_CamelCaseToDash
+ */
+require_once 'Zend/Filter/Word/CamelCaseToDash.php';
+
+/**
+ * @see Zend_Filter_StringToLower
+ */
+require_once 'Zend/Filter/StringToLower.php';
+
+/**
+ * @see Zend_Tool_Framework_Metadata_Tool
+ */
+require_once 'Zend/Tool/Framework/Metadata/Tool.php';
+
+/**
+ * @see Zend_Tool_Framework_Registry_EnabledInterface
+ */
+require_once 'Zend/Tool/Framework/Registry/EnabledInterface.php';
+
+/**
+ * Zend_Tool_Framework_Client_ConsoleClient_Manifest
+ * @category   Zend
+ * @package    Zend_Tool
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ */
+class Zend_Tool_Framework_Client_Manifest
+    implements Zend_Tool_Framework_Registry_EnabledInterface,
+               Zend_Tool_Framework_Manifest_MetadataManifestable
+{
+
+    /**
+     * @var Zend_Tool_Framework_Registry_Interface
+     */
+    protected $_registry = null;
+
+    /**
+     * setRegistry() - Required for the Zend_Tool_Framework_Registry_EnabledInterface interface
+     *
+     * @param Zend_Tool_Framework_Registry_Interface $registry
+     * @return Zend_Tool_Framework_Client_Console_Manifest
+     */
+    public function setRegistry(Zend_Tool_Framework_Registry_Interface $registry)
+    {
+        $this->_registry = $registry;
+        return $this;
+    }
+
+    /**
+     * getMetadata() is required by the Manifest Interface.
+     *
+     * These are the following metadatas that will be setup:
+     *
+     * normalizedActionName
+     *   - metadata for actions
+     *   - value will be a dashed name for the action named in 'actionName'
+     * normalizedProviderName
+     *   - metadata for providers
+     *   - value will be a dashed-name for the provider named in 'providerName'
+     * normalizedProviderSpecialtyNames
+     *   - metadata for providers
+     * normalizedActionableMethodLongParameters
+     *   - metadata for providers
+     * normalizedActionableMethodShortParameters
+     *   - metadata for providers
+     *
+     * @return array Array of Metadatas
+     */
+    public function getMetadata()
+    {
+        $metadatas = array();
+
+        // setup the camelCase to dashed filter to use since cli expects dashed named
+        $lowerFilter = new Zend_Filter();
+        $lowerFilter->addFilter(new Zend_Filter_StringToLower());
+
+        // get the registry to get the action and provider repository
+        $actionRepository   = $this->_registry->getActionRepository();
+        $providerRepository = $this->_registry->getProviderRepository();
+
+        // loop through all actions and create a metadata for each
+        foreach ($actionRepository->getActions() as $action) {
+            // each action metadata will be called
+            $metadatas[] = new Zend_Tool_Framework_Metadata_Tool(array(
+                'name'            => 'normalizedActionName',
+                'value'           => $lowerFilter->filter($action->getName()),
+                'reference'       => $action,
+                'actionName'      => $action->getName(),
+                'clientName'      => 'all'
+                ));
+        }
+
+        foreach ($providerRepository->getProviderSignatures() as $providerSignature) {
+
+            // create the metadata for the provider's cliProviderName
+            $metadatas[] = new Zend_Tool_Framework_Metadata_Tool(array(
+                'name'            => 'normalizedProviderName',
+                'value'           => $lowerFilter->filter($providerSignature->getName()),
+                'reference'       => $providerSignature,
+                'clientName'      => 'all',
+                'providerName'    => $providerSignature->getName()
+                ));
+
+            // create the metadatas for the per provider specialites in providerSpecaltyNames
+            foreach ($providerSignature->getSpecialties() as $specialty) {
+
+                if ($specialty == '_Global') {
+                    continue;
+                }
+                
+                $metadatas[] = new Zend_Tool_Framework_Metadata_Tool(array(
+                    'name'            => 'normalizedSpecialtyName',
+                    'value'           => $lowerFilter->filter($specialty),
+                    'reference'       => $providerSignature,
+                    'clientName'      => 'all',
+                    'providerName'    => $providerSignature->getName(),
+                    'specialtyName'   => $specialty
+                    ));
+
+            }
+
+            // $actionableMethod is keyed by the methodName (but not used)
+            foreach ($providerSignature->getActionableMethods() as $actionableMethodData) {
+
+                $methodLongParams  = array();
+                $methodShortParams = array();
+
+                // $actionableMethodData get both the long and short names
+                foreach ($actionableMethodData['parameterInfo'] as $parameterInfoData) {
+
+                    // filter to dashed
+                    $methodLongParams[$parameterInfoData['name']] = $lowerFilter->filter($parameterInfoData['name']);
+
+                    // simply lower the character, (its only 1 char after all)
+                    $methodShortParams[$parameterInfoData['name']] = strtolower($parameterInfoData['name'][0]);
+
+                }
+
+                // create metadata for the long name cliActionableMethodLongParameters
+                $metadatas[] = new Zend_Tool_Framework_Metadata_Tool(array(
+                    'name'            => 'normalizedActionableMethodLongParams',
+                    'value'           => $methodLongParams,
+                    'clientName'      => 'console',
+                    'providerName'    => $providerSignature->getName(),
+                    'specialtyName'   => $actionableMethodData['specialty'],
+                    'actionName'      => $actionableMethodData['actionName'],
+                    'reference'       => &$actionableMethodData
+                    ));
+
+                // create metadata for the short name cliActionableMethodShortParameters
+                $metadatas[] = new Zend_Tool_Framework_Metadata_Tool(array(
+                    'name'            => 'normalizedActionableMethodShortParams',
+                    'value'           => $methodShortParams,
+                    'clientName'      => 'console',
+                    'providerName'    => $providerSignature->getName(),
+                    'specialtyName'   => $actionableMethodData['specialty'],
+                    'actionName'      => $actionableMethodData['actionName'],
+                    'reference'       => &$actionableMethodData
+                    ));
+
+            }
+
+        }
+
+        return $metadatas;
+    }
+
+    public function getIndex()
+    {
+        return 100000;
+    }
+
+}

+ 2 - 2
library/Zend/Tool/Framework/Client/Response.php

@@ -44,9 +44,9 @@ class Zend_Tool_Framework_Client_Response
     protected $_exception = null;
     protected $_exception = null;
 
 
     /**
     /**
-     * @var null|array
+     * @var array
      */
      */
-    protected $_decorators = null;
+    protected $_decorators = array();
 
 
     /**
     /**
      * @var array
      * @var array

+ 12 - 6
library/Zend/Tool/Framework/Loader/Abstract.php

@@ -25,13 +25,19 @@
  */
  */
 require_once 'Zend/Tool/Framework/Registry/EnabledInterface.php';
 require_once 'Zend/Tool/Framework/Registry/EnabledInterface.php';
 
 
+require_once 'Zend/Tool/Framework/Loader/Interface.php';
+require_once 'Zend/Tool/Framework/Manifest/Interface.php';
+require_once 'Zend/Tool/Framework/Provider/Interface.php';
+
+
 /**
 /**
  * @category   Zend
  * @category   Zend
  * @package    Zend_Tool
  * @package    Zend_Tool
  * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
  * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
  * @license    http://framework.zend.com/license/new-bsd     New BSD License
  * @license    http://framework.zend.com/license/new-bsd     New BSD License
  */
  */
-abstract class Zend_Tool_Framework_Loader_Abstract implements Zend_Tool_Framework_Registry_EnabledInterface
+abstract class Zend_Tool_Framework_Loader_Abstract 
+    implements Zend_Tool_Framework_Loader_Interface, Zend_Tool_Framework_Registry_EnabledInterface
 {
 {
     /**
     /**
      * @var Zend_Tool_Framework_Repository_Interface
      * @var Zend_Tool_Framework_Repository_Interface
@@ -77,8 +83,8 @@ abstract class Zend_Tool_Framework_Loader_Abstract implements Zend_Tool_Framewor
         $this->_retrievedFiles = $this->getRetrievedFiles();
         $this->_retrievedFiles = $this->getRetrievedFiles();
         $this->_loadedClasses  = array();
         $this->_loadedClasses  = array();
 
 
-        $manifestRegistry = $this->_registry->getManifestRepository();
-        $providerRegistry = $this->_registry->getProviderRepository();
+        $manifestRepository = $this->_registry->getManifestRepository();
+        $providerRepository = $this->_registry->getProviderRepository();
 
 
         $loadedClasses = array();
         $loadedClasses = array();
 
 
@@ -105,15 +111,15 @@ abstract class Zend_Tool_Framework_Loader_Abstract implements Zend_Tool_Framewor
             if ($reflectionClass->implementsInterface('Zend_Tool_Framework_Manifest_Interface')
             if ($reflectionClass->implementsInterface('Zend_Tool_Framework_Manifest_Interface')
                 && !$reflectionClass->isAbstract())
                 && !$reflectionClass->isAbstract())
             {
             {
-                $manifestRegistry->addManifest($reflectionClass->newInstance());
+                $manifestRepository->addManifest($reflectionClass->newInstance());
                 $this->_loadedClasses[] = $loadedClass;
                 $this->_loadedClasses[] = $loadedClass;
             }
             }
 
 
             if ($reflectionClass->implementsInterface('Zend_Tool_Framework_Provider_Interface')
             if ($reflectionClass->implementsInterface('Zend_Tool_Framework_Provider_Interface')
                 && !$reflectionClass->isAbstract()
                 && !$reflectionClass->isAbstract()
-                && !$providerRegistry->hasProvider($reflectionClass->getName(), false))
+                && !$providerRepository->hasProvider($reflectionClass->getName(), false))
             {
             {
-                $providerRegistry->addProvider($reflectionClass->newInstance());
+                $providerRepository->addProvider($reflectionClass->newInstance());
                 $this->_loadedClasses[] = $loadedClass;
                 $this->_loadedClasses[] = $loadedClass;
             }
             }
 
 

+ 157 - 0
library/Zend/Tool/Framework/Loader/BasicLoader.php

@@ -0,0 +1,157 @@
+<?php
+/**
+ * Zend Framework
+ *
+ * LICENSE
+ *
+ * This source file is subject to the new BSD license that is bundled
+ * with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://framework.zend.com/license/new-bsd
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@zend.com so we can send you a copy immediately.
+ *
+ * @category   Zend
+ * @package    Zend_Tool
+ * @subpackage Framework
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ * @version    $Id: IncludePathLoader.php 18386 2009-09-23 20:44:43Z ralph $
+ */
+
+/**
+ * @see Zend_Tool_Framework_Loader_Abstract
+ */
+require_once 'Zend/Tool/Framework/Loader/Interface.php';
+
+/**
+ * @see Zend_Tool_Framework_Registry_EnabledInterface
+ */
+require_once 'Zend/Tool/Framework/Registry/EnabledInterface.php';
+
+/**
+ * @see Zend_Loader
+ */
+require_once 'Zend/Loader.php';
+require_once 'Zend/Tool/Framework/Manifest/Interface.php';
+require_once 'Zend/Tool/Framework/Provider/Interface.php';
+
+/**
+ * @category   Zend
+ * @package    Zend_Tool
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ */
+class Zend_Tool_Framework_Loader_BasicLoader 
+    implements Zend_Tool_Framework_Loader_Interface, Zend_Tool_Framework_Registry_EnabledInterface
+{
+    /**
+     * @var Zend_Tool_Framework_Repository_Interface
+     */
+    protected $_registry = null;
+
+    /**
+     * @var array
+     */
+    protected $_classesToLoad = array();
+    
+    public function __construct($options = array())
+    {
+        if ($options) {
+            $this->setOptions($options);
+        }
+    }
+    
+    public function setOptions(Array $options)
+    {
+        foreach ($options as $optionName => $optionValue) {
+            $setMethod = 'set' . $optionName;
+            if (method_exists($this, $setMethod)) {
+                $this->{$setMethod}($optionValue);
+            }
+        }
+    }
+    
+    /**
+     * setRegistry() - required by the enabled interface to get an instance of
+     * the registry
+     *
+     * @param Zend_Tool_Framework_Registry_Interface $registry
+     * @return Zend_Tool_Framework_Loader_Abstract
+     */
+    public function setRegistry(Zend_Tool_Framework_Registry_Interface $registry)
+    {
+        $this->_registry = $registry;
+        return $this;
+    }
+
+    /**
+     * @param  array $classesToLoad
+     * @return Zend_Tool_Framework_Loader_Abstract
+     */
+    public function setClassesToLoad(array $classesToLoad)
+    {
+        $this->_classesToLoad = $classesToLoad;
+        return $this;
+    }
+    
+    public function load()
+    {
+        $manifestRegistry = $this->_registry->getManifestRepository();
+        $providerRegistry = $this->_registry->getProviderRepository();
+        
+        $loadedClasses = array();
+        
+        // loop through the loaded classes and ensure that
+        foreach ($this->_classesToLoad as $class) {
+            
+            if (!class_exists($class)) {
+                Zend_Loader::loadClass($class);
+            }
+
+            // reflect class to see if its something we want to load
+            $reflectionClass = new ReflectionClass($class);
+            if ($this->_isManifestImplementation($reflectionClass)) {
+                $manifestRegistry->addManifest($reflectionClass->newInstance());
+                $loadedClasses[] = $class;
+            }
+
+            if ($this->_isProviderImplementation($reflectionClass)) {
+                $providerRegistry->addProvider($reflectionClass->newInstance());
+                $loadedClasses[] = $class;
+            }
+
+        }
+
+        return $loadedClasses;
+    }
+
+    /**
+     * @param  ReflectionClass $reflectionClass
+     * @return bool
+     */
+    private function _isManifestImplementation($reflectionClass)
+    {
+        return (
+            $reflectionClass->implementsInterface('Zend_Tool_Framework_Manifest_Interface')
+                && !$reflectionClass->isAbstract()
+        );
+    }
+
+    /**
+     * @param  ReflectionClass $reflectionClass
+     * @return bool
+     */
+    private function _isProviderImplementation($reflectionClass)
+    {
+        $providerRegistry = $this->_registry->getProviderRepository();
+
+        return (
+            $reflectionClass->implementsInterface('Zend_Tool_Framework_Provider_Interface')
+                && !$reflectionClass->isAbstract()
+                && !$providerRegistry->hasProvider($reflectionClass->getName(), false)
+        );
+    }
+    
+}

+ 42 - 0
library/Zend/Tool/Framework/Loader/Interface.php

@@ -0,0 +1,42 @@
+<?php
+/**
+ * Zend Framework
+ *
+ * LICENSE
+ *
+ * This source file is subject to the new BSD license that is bundled
+ * with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://framework.zend.com/license/new-bsd
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@zend.com so we can send you a copy immediately.
+ *
+ * @category   Zend
+ * @package    Tool
+ * @subpackage Framework
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ * @version    $Id$
+ */
+
+/**
+ * Basic Interface for factilities that load Zend_Tool providers or manifests.
+ *
+ * @category   Zend
+ * @package    Tool
+ * @subpackage Framework
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ */
+interface Zend_Tool_Framework_Loader_Interface
+{
+    /**
+     * Load Providers and Manifests
+     *
+     * Returns an array of all loaded class names.
+     *
+     * @return array
+     */
+    public function load();
+}

+ 13 - 0
library/Zend/Tool/Framework/Manifest/Repository.php

@@ -95,6 +95,12 @@ class Zend_Tool_Framework_Manifest_Repository
             }
             }
 
 
             foreach ($providers as $provider) {
             foreach ($providers as $provider) {
+
+                // if provider is a string, try and load it as an object
+                if (is_string($provider)) {
+                    $provider = new $provider();
+                }
+                
                 if (!$provider instanceof Zend_Tool_Framework_Provider_Interface) {
                 if (!$provider instanceof Zend_Tool_Framework_Provider_Interface) {
                     require_once 'Zend/Tool/Framework/Manifest/Exception.php';
                     require_once 'Zend/Tool/Framework/Manifest/Exception.php';
                     throw new Zend_Tool_Framework_Manifest_Exception(
                     throw new Zend_Tool_Framework_Manifest_Exception(
@@ -171,6 +177,13 @@ class Zend_Tool_Framework_Manifest_Repository
                 }
                 }
 
 
                 foreach ($metadatas as $metadata) {
                 foreach ($metadatas as $metadata) {
+                    if (is_array($metadata)) {
+                        if (!class_exists('Zend_Tool_Framework_Metadata_Dynamic')) {
+                            require_once 'Zend/Tool/Framework/Metadata/Dynamic.php';
+                        }
+                        $metadata = new Zend_Tool_Framework_Metadata_Dynamic($metadata);
+                    }
+                    
                     if (!$metadata instanceof Zend_Tool_Framework_Metadata_Interface) {
                     if (!$metadata instanceof Zend_Tool_Framework_Metadata_Interface) {
                         require_once 'Zend/Tool/Framework/Manifest/Exception.php';
                         require_once 'Zend/Tool/Framework/Manifest/Exception.php';
                         throw new Zend_Tool_Framework_Manifest_Exception(
                         throw new Zend_Tool_Framework_Manifest_Exception(

+ 8 - 0
library/Zend/Tool/Framework/Metadata/Attributable.php

@@ -0,0 +1,8 @@
+<?php
+
+interface Zend_Tool_Framework_Metadata_Attributable
+{
+    public function getAttributes();
+}
+
+

+ 7 - 1
library/Zend/Tool/Framework/Metadata/Basic.php

@@ -26,12 +26,18 @@
 require_once 'Zend/Tool/Framework/Metadata/Interface.php';
 require_once 'Zend/Tool/Framework/Metadata/Interface.php';
 
 
 /**
 /**
+ * @see Zend_Tool_Framework_Metadata_Attributable
+ */
+require_once 'Zend/Tool/Framework/Metadata/Attributable.php';
+
+/**
  * @category   Zend
  * @category   Zend
  * @package    Zend_Tool
  * @package    Zend_Tool
  * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
  * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
  * @license    http://framework.zend.com/license/new-bsd     New BSD License
  * @license    http://framework.zend.com/license/new-bsd     New BSD License
  */
  */
-class Zend_Tool_Framework_Metadata_Basic implements Zend_Tool_Framework_Metadata_Interface
+class Zend_Tool_Framework_Metadata_Basic 
+    implements Zend_Tool_Framework_Metadata_Interface, Zend_Tool_Framework_Metadata_Attributable
 {
 {
 
 
     /**#@+
     /**#@+

+ 70 - 5
library/Zend/Tool/Framework/Metadata/Dynamic.php

@@ -26,12 +26,18 @@
 require_once 'Zend/Tool/Framework/Metadata/Interface.php';
 require_once 'Zend/Tool/Framework/Metadata/Interface.php';
 
 
 /**
 /**
+ * @see Zend_Tool_Framework_Metadata_Attributable
+ */
+require_once 'Zend/Tool/Framework/Metadata/Attributable.php';
+
+/**
  * @category   Zend
  * @category   Zend
  * @package    Zend_Tool
  * @package    Zend_Tool
  * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
  * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
  * @license    http://framework.zend.com/license/new-bsd     New BSD License
  * @license    http://framework.zend.com/license/new-bsd     New BSD License
  */
  */
-class Zend_Tool_Framework_Metadata_Dynamic implements Zend_Tool_Framework_Metadata_Interface
+class Zend_Tool_Framework_Metadata_Dynamic 
+    implements Zend_Tool_Framework_Metadata_Interface, Zend_Tool_Framework_Metadata_Attributable
 {
 {
 
 
     /**
     /**
@@ -54,6 +60,33 @@ class Zend_Tool_Framework_Metadata_Dynamic implements Zend_Tool_Framework_Metada
      */
      */
     protected $_dynamicAttributes = array();
     protected $_dynamicAttributes = array();
 
 
+    public function __construct($options = array())
+    {
+        if ($options) {
+            $this->setOptions($options);
+        }
+    }
+    
+    public function setOptions(Array $options = array())
+    {
+        foreach ($options as $optName => $optValue) {
+            $methodName = 'set' . $optName;
+            $this->{$methodName}($optValue);
+        }
+    }
+    
+    /**
+     * setType()
+     * 
+     * @param $type
+     * @return Zend_Tool_Framework_Metadata_Dynamic
+     */
+    public function setType($type)
+    {
+        $this->_type = $type;
+        return $this;
+    }
+    
     /**
     /**
      * getType()
      * getType()
      *
      *
@@ -67,6 +100,18 @@ class Zend_Tool_Framework_Metadata_Dynamic implements Zend_Tool_Framework_Metada
     }
     }
 
 
     /**
     /**
+     * setName()
+     * 
+     * @param $name
+     * @return Zend_Tool_Framework_Metadata_Dynamic
+     */
+    public function setName($name)
+    {
+        $this->_name = $name;
+        return $this;
+    }
+    
+    /**
      * getName()
      * getName()
      *
      *
      * Metadata name
      * Metadata name
@@ -79,6 +124,18 @@ class Zend_Tool_Framework_Metadata_Dynamic implements Zend_Tool_Framework_Metada
     }
     }
 
 
     /**
     /**
+     * setValue()
+     * 
+     * @param $value
+     * @return Zend_Tool_Framework_Metadata_Dynamic
+     */
+    public function setValue($value)
+    {
+        $this->_value = $value;
+        return $this;
+    }
+    
+    /**
      * getValue()
      * getValue()
      *
      *
      * Metadata Value
      * Metadata Value
@@ -90,6 +147,10 @@ class Zend_Tool_Framework_Metadata_Dynamic implements Zend_Tool_Framework_Metada
         return $this->_value;
         return $this->_value;
     }
     }
 
 
+    public function getAttributes()
+    {
+        return $this->_dynamicAttributes;
+    }
 
 
     /**
     /**
      * __isset()
      * __isset()
@@ -127,7 +188,7 @@ class Zend_Tool_Framework_Metadata_Dynamic implements Zend_Tool_Framework_Metada
         if (method_exists($this, 'get' . $name)) {
         if (method_exists($this, 'get' . $name)) {
             return $this->{'get' . $name}();
             return $this->{'get' . $name}();
         } elseif (array_key_exists($name, $this->_dynamicAttributes)) {
         } elseif (array_key_exists($name, $this->_dynamicAttributes)) {
-            return ;
+            return $this->_dynamicAttributes[$name];
         } else {
         } else {
             require_once 'Zend/Tool/Framework/Registry/Exception.php';
             require_once 'Zend/Tool/Framework/Registry/Exception.php';
             throw new Zend_Tool_Framework_Registry_Exception('Property ' . $name . ' was not located in this metadata.');
             throw new Zend_Tool_Framework_Registry_Exception('Property ' . $name . ' was not located in this metadata.');
@@ -144,11 +205,15 @@ class Zend_Tool_Framework_Metadata_Dynamic implements Zend_Tool_Framework_Metada
     {
     {
         if (method_exists($this, 'set' . $name)) {
         if (method_exists($this, 'set' . $name)) {
             $this->{'set' . $name}($value);
             $this->{'set' . $name}($value);
-            return;
+            return $this;
         } else {
         } else {
-            require_once 'Zend/Tool/Framework/Registry/Exception.php';
-            throw new Zend_Tool_Framework_Registry_Exception('Property ' . $name . ' was not located in this registry.');
+            $this->_dynamicAttributes[$name] = $value;
+            return $this;
         }
         }
+//        {
+//            require_once 'Zend/Tool/Framework/Registry/Exception.php';
+//            throw new Zend_Tool_Framework_Registry_Exception('Property ' . $name . ' was not located in this registry.');
+//        }
     }
     }
 
 
 }
 }

+ 1 - 1
library/Zend/Tool/Framework/Metadata/Interface.php

@@ -48,5 +48,5 @@ interface Zend_Tool_Framework_Metadata_Interface
      *
      *
      */
      */
     public function getValue();
     public function getValue();
-
+    
 }
 }

+ 2 - 2
library/Zend/Tool/Framework/Registry.php

@@ -179,10 +179,10 @@ class Zend_Tool_Framework_Registry implements Zend_Tool_Framework_Registry_Inter
     /**
     /**
      * setLoader()
      * setLoader()
      *
      *
-     * @param Zend_Tool_Framework_Loader_Abstract $loader
+     * @param Zend_Tool_Framework_Loader_Interface $loader
      * @return Zend_Tool_Framework_Registry
      * @return Zend_Tool_Framework_Registry
      */
      */
-    public function setLoader(Zend_Tool_Framework_Loader_Abstract $loader)
+    public function setLoader(Zend_Tool_Framework_Loader_Interface $loader)
     {
     {
         $this->_loader = $loader;
         $this->_loader = $loader;
         if ($this->isObjectRegistryEnablable($this->_loader)) {
         if ($this->isObjectRegistryEnablable($this->_loader)) {

+ 1 - 1
library/Zend/Tool/Framework/Registry/Interface.php

@@ -50,7 +50,7 @@ interface Zend_Tool_Framework_Registry_Interface
      * @param Zend_Tool_Framework_Loader_Abstract $loader
      * @param Zend_Tool_Framework_Loader_Abstract $loader
      * @return Zend_Tool_Framework_Registry
      * @return Zend_Tool_Framework_Registry
      */
      */
-    public function setLoader(Zend_Tool_Framework_Loader_Abstract $loader);
+    public function setLoader(Zend_Tool_Framework_Loader_Interface $loader);
 
 
     /**
     /**
      * getLoader()
      * getLoader()

+ 2 - 0
library/Zend/Tool/Framework/System/Manifest.php

@@ -23,6 +23,7 @@
 require_once 'Zend/Tool/Framework/Manifest/ProviderManifestable.php';
 require_once 'Zend/Tool/Framework/Manifest/ProviderManifestable.php';
 require_once 'Zend/Tool/Framework/Manifest/ActionManifestable.php';
 require_once 'Zend/Tool/Framework/Manifest/ActionManifestable.php';
 require_once 'Zend/Tool/Framework/System/Provider/Version.php';
 require_once 'Zend/Tool/Framework/System/Provider/Version.php';
+require_once 'Zend/Tool/Framework/System/Provider/Config.php';
 require_once 'Zend/Tool/Framework/System/Provider/Phpinfo.php';
 require_once 'Zend/Tool/Framework/System/Provider/Phpinfo.php';
 require_once 'Zend/Tool/Framework/System/Provider/Manifest.php';
 require_once 'Zend/Tool/Framework/System/Provider/Manifest.php';
 require_once 'Zend/Tool/Framework/System/Action/Create.php';
 require_once 'Zend/Tool/Framework/System/Action/Create.php';
@@ -42,6 +43,7 @@ class Zend_Tool_Framework_System_Manifest
     {
     {
         $providers = array(
         $providers = array(
             new Zend_Tool_Framework_System_Provider_Version(),
             new Zend_Tool_Framework_System_Provider_Version(),
+            new Zend_Tool_Framework_System_Provider_Config(),
             new Zend_Tool_Framework_System_Provider_Phpinfo(),
             new Zend_Tool_Framework_System_Provider_Phpinfo(),
             new Zend_Tool_Framework_System_Provider_Manifest()
             new Zend_Tool_Framework_System_Provider_Manifest()
             );
             );

+ 311 - 0
library/Zend/Tool/Framework/System/Provider/Config.php

@@ -0,0 +1,311 @@
+<?php
+/**
+ * Zend Framework
+ *
+ * LICENSE
+ *
+ * This source file is subject to the new BSD license that is bundled
+ * with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://framework.zend.com/license/new-bsd
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@zend.com so we can send you a copy immediately.
+ *
+ * @category   Zend
+ * @package    Zend_Tool
+ * @subpackage Framework
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ */
+
+/**
+ * @see Zend_Tool_Framework_Provider_Abstract
+ */
+require_once "Zend/Tool/Framework/Provider/Abstract.php";
+
+/**
+ * @see Zend_Config
+ */
+require_once "Zend/Config.php";
+
+/**
+ * @see Zend_Config_Writer_Ini
+ */
+require_once "Zend/Config/Writer/Ini.php";
+
+/**
+ * @see Zend_Loader
+ */
+require_once "Zend/Loader.php";
+
+/**
+ * Configuration Provider
+ *
+ * @category   Zend
+ * @package    Zend_Tool
+ * @package    Framework
+ * @uses       Zend_Tool_Framework_Provider_Abstract
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ * @version    $Id$
+ */
+class Zend_Tool_Framework_System_Provider_Config extends Zend_Tool_Framework_Provider_Abstract
+{
+    /**
+     * @var array
+     */
+    protected $_levelCompleted = array();
+
+    /**
+     * array of specialties handled by this provider
+     * 
+     * @var array
+     */
+    protected $_specialties = array('Manifest', 'Provider');
+    
+    /**
+     * @param string $type
+     */
+    public function create()
+    {
+        /* @var $userConfig Zend_Tool_Framework_Client_Config */
+        $userConfig = $this->_registry->getConfig();
+
+        $resp = $this->_registry->getResponse();
+        if ($userConfig->exists()) {
+            require_once "Zend/Tool/Framework/Exception.php";
+            throw new Zend_Tool_Framework_Exception(
+                "A configuration already exists, cannot create a new one.");
+        }
+
+        $homeDirectory = $this->_detectHomeDirectory();
+
+        $writer = new Zend_Config_Writer_Ini();
+        $writer->setRenderWithoutSections();
+        $filename = $homeDirectory."/.zf.ini";
+
+        $config = array(
+            'php' => array(
+                'includepath' => get_include_path(),
+            ),
+        );
+        $writer->write($filename, new Zend_Config($config));
+
+        $resp = $this->_registry->getResponse();
+        $resp->appendContent("Successfully written Zend Tool config.");
+        $resp->appendContent("It is located at: ".$filename);
+    }
+
+    /**
+     * @return string
+     */
+    protected function _detectHomeDirectory()
+    {
+        $envVars = array("ZF_HOME", "HOME", "HOMEPATH");
+        foreach($envVars AS $env) {
+            $homeDirectory = getenv($env);
+            if ($homeDirectory != false && file_exists($homeDirectory)) {
+                return $homeDirectory;
+            }
+        }
+        require_once "Zend/Tool/Framework/Exception.php";
+        throw new Zend_Tool_Framework_Exception("Cannot detect user home directory, set ZF_HOME enviroment variable.");
+    }
+
+    /**
+     * Show Zend Tool User Configuration
+     *
+     * @return void
+     */
+    public function show()
+    {
+        $userConfig = $this->_loadUserConfigIfExists();
+        $configArray = $userConfig->getConfigInstance()->toArray();
+
+        $resp = $this->_registry->getResponse();
+
+        $i = 0;
+        $tree = "";
+        foreach($configArray AS $k => $v) {
+            $i++;
+            $tree .= $this->_printTree($k, $v, 1, count($configArray)==$i);
+        }
+        $resp->appendContent("User Configuration: ".$userConfig->getConfigFilepath(), array("color" => "green"));
+        $resp->appendContent($tree, array("indention" => 2));
+    }
+
+    /**
+     *
+     * @param string $key
+     * @param string $value
+     * @param int $level
+     * @return string
+     */
+    protected function _printTree($key, $value, $level=1, $isLast=false)
+    {
+        $this->_levelCompleted[$level] = false;
+
+        $prefix = "";
+        for ($i = 1; $i < $level; $i++) {
+            if ($this->_levelCompleted[$i] == true) {
+                $prefix .= "    ";
+            } else {
+                $prefix .= "|   ";
+            }
+        }
+        if ($isLast) {
+            $pointer = "`-- ";
+        } else {
+            $pointer = "|-- ";
+        }
+
+        $tree = "";
+        if (is_array($value)) {
+            $tree .= $prefix.$pointer.$key.PHP_EOL;
+
+            if ($isLast == true) {
+                $this->_levelCompleted[$level] = true;
+            }
+
+            $i = 0;
+            foreach ($value as $k => $v) {
+                $i++;
+                $tree .= $this->_printTree($k, $v, $level+1, (count($value)==$i));
+            }
+        } else {
+            $tree .= $prefix.$pointer.$key.": ".trim($value).PHP_EOL;
+        }
+
+        return $tree;
+    }
+
+    /**
+     * @param string $className
+     */
+    public function enableProvider($className)
+    {
+        Zend_Loader::loadClass($className);
+        $reflClass = new ReflectionClass($className);
+        if (!in_array("Zend_Tool_Framework_Provider_Interface", $reflClass->getInterfaceNames())) {
+            require_once "Zend/Tool/Framework/Exception.php";
+            throw new Zend_Tool_Framework_Exception("Given class is not a provider");
+        }
+        $this->_doEnable($className);
+    }
+
+    protected function _doEnable($className)
+    {
+
+        $userConfig = $this->_loadUserConfigIfExists();
+
+        if (!isset($userConfig->basicloader)) {
+            $userConfig->basicloader = array();
+        }
+        if (!isset($userConfig->basicloader->classes)) {
+            $userConfig->basicloader->classes = array();
+        }
+
+        $providerClasses = $userConfig->basicloader->classes->toArray();
+        if (!in_array($className, $providerClasses)) {
+            if (count($providerClasses)) {
+                $pos = max(array_keys($providerClasses))+1;
+            } else {
+                $pos = 0;
+            }
+            $userConfig->basicloader->classes->$pos = $className;
+
+            if ($userConfig->save()) {
+                $this->_registry->getResponse()->appendContent(
+                    "Provider/Manifest '".$className."' was enabled for usage with Zend Tool.",
+                    array("color" => "green", "aligncenter" => true)
+                );
+            } else {
+                require_once "Zend/Tool/Framework/Exception.php";
+                throw new Zend_Tool_Framework_Exception(
+                    "Could not write user configuration to persistence."
+                );
+            }
+        } else {
+            require_once "Zend/Tool/Framework/Exception.php";
+            throw new Zend_Tool_Framework_Exception(
+                "Provider/Manifest '".$className."' is already enabled."
+            );
+        }
+    }
+
+    /**
+     * @param string $className
+     */
+    public function enableManifest($className)
+    {
+        Zend_Loader::loadClass($className);
+        $reflClass = new ReflectionClass($className);
+        if (!in_array("Zend_Tool_Framework_Manifest_Interface", $reflClass->getInterfaceNames())) {
+            require_once "Zend/Tool/Framework/Exception.php";
+            throw new Zend_Tool_Framework_Exception("Given class is not a manifest.");
+        }
+        $this->_doEnable($className);
+    }
+
+    /**
+     * @param string $className
+     */
+    public function disableManifest($className)
+    {
+        $this->disableProvider($className);
+    }
+
+    /**
+     * @param string $className
+     */
+    public function disableProvider($className)
+    {
+        $userConfig = $this->_loadUserConfigIfExists();
+
+        if (!isset($userConfig->basicloader)) {
+            $userConfig->basicloader = array();
+        }
+        if (!isset($userConfig->basicloader->classes)) {
+            $userConfig->basicloader->classes = array();
+        }
+
+        $providerClasses = $userConfig->basicloader->classes->toArray();
+        if (($key = array_search($className, $providerClasses)) !== false) {
+            unset($userConfig->basicloader->classes->$key);
+
+            if ($userConfig->save()) {
+                $this->_registry->getResponse()->appendContent(
+                    "Provider/Manifest '".$className."' was disabled.",
+                    array("color" => "green", "aligncenter" => true)
+                );
+            } else {
+                require_once "Zend/Tool/Framework/Exception.php";
+                throw new Zend_Tool_Framework_Exception(
+                    "Could not write user configuration to persistence."
+                );
+            }
+        } else {
+            require_once "Zend/Tool/Framework/Exception.php";
+            throw new Zend_Tool_Framework_Exception(
+                "Provider/Manifest '".$className."' is not enabled."
+            );
+        }
+    }
+
+    /**
+     * @return Zend_Tool_Framework_Client_Config
+     */
+    protected function _loadUserConfigIfExists()
+    {
+        /* @var $userConfig Zend_Tool_Framework_Client_Config */
+        $userConfig = $this->_registry->getConfig();
+
+        $resp = $this->_registry->getResponse();
+        if (!$userConfig->exists()) {
+            $resp->appendContent("User has no config file.", array("aligncenter" => true, "color" => array('hiWhite', 'bgRed')));
+        }
+
+        return $userConfig;
+    }
+}

+ 11 - 1
library/Zend/Tool/Project/Context/Filesystem/Directory.php

@@ -36,10 +36,20 @@ require_once 'Zend/Tool/Project/Context/Filesystem/Abstract.php';
  * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
  * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
  * @license    http://framework.zend.com/license/new-bsd     New BSD License
  * @license    http://framework.zend.com/license/new-bsd     New BSD License
  */
  */
-abstract class Zend_Tool_Project_Context_Filesystem_Directory extends Zend_Tool_Project_Context_Filesystem_Abstract
+class Zend_Tool_Project_Context_Filesystem_Directory extends Zend_Tool_Project_Context_Filesystem_Abstract
 {
 {
 
 
     /**
     /**
+     * getName()
+     * 
+     * @return string
+     */
+    public function getName()
+    {
+        return 'directory';
+    }
+    
+    /**
      * create()
      * create()
      *
      *
      * @return Zend_Tool_Project_Context_Filesystem_Directory;
      * @return Zend_Tool_Project_Context_Filesystem_Directory;

+ 11 - 1
library/Zend/Tool/Project/Context/Filesystem/File.php

@@ -36,10 +36,20 @@ require_once 'Zend/Tool/Project/Context/Filesystem/Abstract.php';
  * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
  * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
  * @license    http://framework.zend.com/license/new-bsd     New BSD License
  * @license    http://framework.zend.com/license/new-bsd     New BSD License
  */
  */
-abstract class Zend_Tool_Project_Context_Filesystem_File extends Zend_Tool_Project_Context_Filesystem_Abstract
+class Zend_Tool_Project_Context_Filesystem_File extends Zend_Tool_Project_Context_Filesystem_Abstract
 {
 {
 
 
     /**
     /**
+     * getName()
+     * 
+     * @return string
+     */
+    public function getName()
+    {
+        return 'file';
+    }
+    
+    /**
      * init()
      * init()
      *
      *
      * @return Zend_Tool_Project_Context_Filesystem_File
      * @return Zend_Tool_Project_Context_Filesystem_File

+ 6 - 2
library/Zend/Tool/Project/Context/Repository.php

@@ -87,8 +87,12 @@ class Zend_Tool_Project_Context_Repository implements Countable
             require_once 'Zend/Loader.php';
             require_once 'Zend/Loader.php';
             Zend_Loader::loadClass($contextClass);
             Zend_Loader::loadClass($contextClass);
         }
         }
-        $context = new $contextClass();
-        return $this->addContext($context);
+        $reflectionContextClass = new ReflectionClass($contextClass);
+        if ($reflectionContextClass->isInstantiable()) {
+            $context = new $contextClass();
+            return $this->addContext($context);
+        }
+        return $this;
     }
     }
 
 
     /**
     /**

+ 39 - 0
library/Zend/Tool/Project/Context/Zf/AbstractClassFile.php

@@ -0,0 +1,39 @@
+<?php
+
+abstract class Zend_Tool_Project_Context_Zf_AbstractClassFile extends Zend_Tool_Project_Context_Filesystem_File
+{
+    
+    public function getFullClassName($localClassName, $classContextName = null)
+    {
+
+        $currentResource = $this->_resource;
+        do {
+            $resourceName = $currentResource->getName();
+            if ($resourceName == 'ApplicationDirectory' || $resourceName == 'ModuleDirectory') {
+                $containingResource = $currentResource;
+                break;
+            }
+        } while ($currentResource instanceof Zend_Tool_Project_Profile_Resource
+            && $currentResource = $currentResource->getParentResource());
+        
+        $fullClassName = '';
+            
+        if (isset($containingResource)) {
+            if ($containingResource->getName() == 'ApplicationDirectory') {
+                $prefix = $containingResource->getAttribute('classNamePrefix');
+                $fullClassName = $prefix;
+            } elseif ($containingResource->getName() == 'ModuleDirectory') {
+                $prefix = $containingResource->getAttribute('moduleName') . '_';
+                $fullClassName = $prefix;    
+            }
+        }
+                
+        if ($classContextName) {
+            $fullClassName .= rtrim($classContextName, '_') . '_';
+        }
+        $fullClassName .= $localClassName;
+                    
+        return $fullClassName;
+    }
+
+}

+ 2 - 0
library/Zend/Tool/Project/Context/Zf/ApplicationConfigFile.php

@@ -91,6 +91,7 @@ includePaths.library = APPLICATION_PATH "/../library"
 bootstrap.path = APPLICATION_PATH "/Bootstrap.php"
 bootstrap.path = APPLICATION_PATH "/Bootstrap.php"
 bootstrap.class = "Bootstrap"
 bootstrap.class = "Bootstrap"
 resources.frontController.controllerDirectory = APPLICATION_PATH "/controllers"
 resources.frontController.controllerDirectory = APPLICATION_PATH "/controllers"
+resources.frontController.params.displayExceptions = 0
 
 
 [staging : production]
 [staging : production]
 
 
@@ -101,6 +102,7 @@ phpSettings.display_errors = 1
 [development : production]
 [development : production]
 phpSettings.display_startup_errors = 1
 phpSettings.display_startup_errors = 1
 phpSettings.display_errors = 1
 phpSettings.display_errors = 1
+resources.frontController.params.displayExceptions = 1
 EOS;
 EOS;
         return $contents;
         return $contents;
     }
     }

+ 25 - 1
library/Zend/Tool/Project/Context/Zf/ApplicationDirectory.php

@@ -41,9 +41,33 @@ class Zend_Tool_Project_Context_Zf_ApplicationDirectory extends Zend_Tool_Projec
 
 
     protected $_filesystemName = 'application';
     protected $_filesystemName = 'application';
 
 
+    protected $_classNamePrefix = 'Application_';
+    
+    /**
+     * getPersistentAttributes
+     *
+     * @return array
+     */
+    public function getPersistentAttributes()
+    {
+        return array(
+            'classNamePrefix' => $this->getClassNamePrefix()
+            );
+    }
+    
     public function getName()
     public function getName()
     {
     {
         return 'ApplicationDirectory';
         return 'ApplicationDirectory';
     }
     }
+    
+    public function setClassNamePrefix($classNamePrefix)
+    {
+        $this->_classNamePrefix = $classNamePrefix;
+    }
+    
+    public function getClassNamePrefix()
+    {
+        return $this->_classNamePrefix;
+    }
 
 
-}
+}

+ 19 - 3
library/Zend/Tool/Project/Context/Zf/BootstrapFile.php

@@ -89,14 +89,30 @@ class Zend_Tool_Project_Context_Zf_BootstrapFile extends Zend_Tool_Project_Conte
      */
      */
     public function getContents()
     public function getContents()
     {
     {
+        $autoloadMethodBody =<<<EOS
+\$autoloader = new Zend_Application_Module_Autoloader(array(
+    'namespace' => 'Application_',
+    'basePath'  => APPLICATION_PATH,
+    ));
+return \$autoloader;
+EOS;
+
+        
+        
         $codeGenFile = new Zend_CodeGenerator_Php_File(array(
         $codeGenFile = new Zend_CodeGenerator_Php_File(array(
             'classes' => array(
             'classes' => array(
                 new Zend_CodeGenerator_Php_Class(array(
                 new Zend_CodeGenerator_Php_Class(array(
                     'name' => 'Bootstrap',
                     'name' => 'Bootstrap',
                     'extendedClass' => 'Zend_Application_Bootstrap_Bootstrap',
                     'extendedClass' => 'Zend_Application_Bootstrap_Bootstrap',
-                )),
-            )
-        ));
+                    'methods' => array(
+                        new Zend_CodeGenerator_Php_Method(array(
+                            'name' => '_initAppAutoloader',
+                            'body' => $autoloadMethodBody,
+                            ))
+                        )
+                    )),
+                )
+            ));
 
 
         return $codeGenFile->generate();
         return $codeGenFile->generate();
     }
     }

+ 23 - 29
library/Zend/Tool/Project/Context/Zf/ControllerFile.php

@@ -21,21 +21,6 @@
  */
  */
 
 
 /**
 /**
- * @see Zend_Tool_Project_Context_Filesystem_File
- */
-require_once 'Zend/Tool/Project/Context/Filesystem/File.php';
-
-/**
- * @see Zend_CodeGenerator_Php_File
- */
-require_once 'Zend/CodeGenerator/Php/File.php';
-
-/**
- * @see Zend_Filter_Word_DashToCamelCase
- */
-require_once 'Zend/Filter/Word/DashToCamelCase.php';
-
-/**
  * This class is the front most class for utilizing Zend_Tool_Project
  * This class is the front most class for utilizing Zend_Tool_Project
  *
  *
  * A profile is a hierarchical set of resources that keep track of
  * A profile is a hierarchical set of resources that keep track of
@@ -57,19 +42,23 @@ class Zend_Tool_Project_Context_Zf_ControllerFile extends Zend_Tool_Project_Cont
     /**
     /**
      * @var string
      * @var string
      */
      */
+    protected $_moduleName = null;
+    
+    /**
+     * @var string
+     */
     protected $_filesystemName = 'controllerName';
     protected $_filesystemName = 'controllerName';
 
 
     /**
     /**
      * init()
      * init()
      *
      *
-     * @return Zend_Tool_Project_Context_Zf_ControllerFile
      */
      */
     public function init()
     public function init()
     {
     {
         $this->_controllerName = $this->_resource->getAttribute('controllerName');
         $this->_controllerName = $this->_resource->getAttribute('controllerName');
+        $this->_moduleName = $this->_resource->getAttribute('moduleName');
         $this->_filesystemName = ucfirst($this->_controllerName) . 'Controller.php';
         $this->_filesystemName = ucfirst($this->_controllerName) . 'Controller.php';
         parent::init();
         parent::init();
-        return $this;
     }
     }
 
 
     /**
     /**
@@ -112,10 +101,11 @@ class Zend_Tool_Project_Context_Zf_ControllerFile extends Zend_Tool_Project_Cont
     public function getContents()
     public function getContents()
     {
     {
 
 
-        $filter = new Zend_Filter_Word_DashToCamelCase();
-
-        $className = $filter->filter($this->_controllerName) . 'Controller';
+        //$filter = new Zend_Filter_Word_DashToCamelCase();
 
 
+        $className = ($this->_moduleName) ? ucfirst($this->_moduleName) . '_' : '';
+        $className .= $this->_controllerName . 'Controller';
+        
         $codeGenFile = new Zend_CodeGenerator_Php_File(array(
         $codeGenFile = new Zend_CodeGenerator_Php_File(array(
             'fileName' => $this->getPath(),
             'fileName' => $this->getPath(),
             'classes' => array(
             'classes' => array(
@@ -126,11 +116,11 @@ class Zend_Tool_Project_Context_Zf_ControllerFile extends Zend_Tool_Project_Cont
                         new Zend_CodeGenerator_Php_Method(array(
                         new Zend_CodeGenerator_Php_Method(array(
                             'name' => 'init',
                             'name' => 'init',
                             'body' => '/* Initialize action controller here */',
                             'body' => '/* Initialize action controller here */',
-                        ))
-                    )
-                ))
-            )
-        ));
+                        	))
+                    	)
+                	))
+            	)
+        	));
 
 
 
 
         if ($className == 'ErrorController') {
         if ($className == 'ErrorController') {
@@ -162,7 +152,11 @@ switch (\$errors->type) {
         break;
         break;
 }
 }
 
 
-\$this->view->exception = \$errors->exception;
+// conditionally display exceptions
+if (\$this->getInvokeArg('displayExceptions') == true) {
+    \$this->view->exception = \$errors->exception;
+}
+
 \$this->view->request   = \$errors->request;
 \$this->view->request   = \$errors->request;
 EOS
 EOS
                                 ))
                                 ))
@@ -185,9 +179,9 @@ EOS
      */
      */
     public function addAction($actionName)
     public function addAction($actionName)
     {
     {
-        $class = $this->getCodeGenerator();
-        $class->setMethod(array('name' => $actionName . 'Action', 'body' => '        // action body here'));
-        file_put_contents($this->getPath(), $codeGenFile->generate());
+        $classCodeGen = $this->getCodeGenerator();
+        $classCodeGen->setMethod(array('name' => $actionName . 'Action', 'body' => '        // action body here'));
+        file_put_contents($this->getPath(), $classCodeGen->generate());
     }
     }
 
 
     /**
     /**

+ 7 - 4
library/Zend/Tool/Project/Context/Zf/DbTableFile.php

@@ -39,6 +39,8 @@ require_once 'Zend/Tool/Project/Context/Filesystem/File.php';
 class Zend_Tool_Project_Context_Zf_DbTableFile extends Zend_Tool_Project_Context_Filesystem_File
 class Zend_Tool_Project_Context_Zf_DbTableFile extends Zend_Tool_Project_Context_Filesystem_File
 {
 {
 
 
+    protected $_dbTableName;
+    
     /**
     /**
      * getName()
      * getName()
      *
      *
@@ -49,9 +51,6 @@ class Zend_Tool_Project_Context_Zf_DbTableFile extends Zend_Tool_Project_Context
         return 'DbTableFile';
         return 'DbTableFile';
     }
     }
 
 
-    /*
-    protected $_dbTableName;
-
     public function getPersistentAttributes()
     public function getPersistentAttributes()
     {
     {
         return array('dbTableName' => $this->_dbTableName);
         return array('dbTableName' => $this->_dbTableName);
@@ -67,6 +66,10 @@ class Zend_Tool_Project_Context_Zf_DbTableFile extends Zend_Tool_Project_Context
     {
     {
         return $this->_dbTableName;
         return $this->_dbTableName;
     }
     }
-    */
 
 
+    public function getContents()
+    {
+        
+    }
+    
 }
 }

+ 109 - 0
library/Zend/Tool/Project/Context/Zf/LayoutScriptFile.php

@@ -0,0 +1,109 @@
+<?php
+/**
+ * Zend Framework
+ *
+ * LICENSE
+ *
+ * This source file is subject to the new BSD license that is bundled
+ * with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://framework.zend.com/license/new-bsd
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@zend.com so we can send you a copy immediately.
+ *
+ * @category   Zend
+ * @package    Zend_Tool
+ * @subpackage Framework
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ * @version    $Id: ViewScriptFile.php 18386 2009-09-23 20:44:43Z ralph $
+ */
+
+/**
+ * @see Zend_Tool_Project_Context_Filesystem_File
+ */
+require_once 'Zend/Tool/Project/Context/Filesystem/File.php';
+
+/**
+ * This class is the front most class for utilizing Zend_Tool_Project
+ *
+ * A profile is a hierarchical set of resources that keep track of
+ * items within a specific project.
+ *
+ * @category   Zend
+ * @package    Zend_Tool
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ */
+class Zend_Tool_Project_Context_Zf_LayoutScriptFile extends Zend_Tool_Project_Context_Filesystem_File
+{
+
+    /**
+     * @var string
+     */
+    protected $_filesystemName = 'layout.phtml';
+
+    /**
+     * @var string
+     */
+    protected $_layoutName = null;
+
+    /**
+     * getName()
+     *
+     * @return string
+     */
+    public function getName()
+    {
+        return 'LayoutScriptFile';
+    }
+
+    /**
+     * init()
+     *
+     * @return Zend_Tool_Project_Context_Zf_ViewScriptFile
+     */
+    public function init()
+    {
+        if ($layoutName = $this->_resource->getAttribute('layoutName')) {
+            $this->_layoutName = $layoutName;
+        } else {
+            throw new Exception('Either a forActionName or scriptName is required.');
+        }
+
+        parent::init();
+        return $this;
+    }
+
+    /**
+     * getPersistentAttributes()
+     *
+     * @return unknown
+     */
+    public function getPersistentAttributes()
+    {
+        $attributes = array();
+
+        if ($this->_layoutName) {
+            $attributes['layoutName'] = $this->_layoutName;
+        }
+
+        return $attributes;
+    }
+
+    /**
+     * getContents()
+     *
+     * @return string
+     */
+    public function getContents()
+    {
+        $contents = <<<EOS
+<?php echo \$this->layout()->content; ?>
+EOS;
+
+        return $contents;
+    }
+
+}

+ 57 - 0
library/Zend/Tool/Project/Context/Zf/LayoutScriptsDirectory.php

@@ -0,0 +1,57 @@
+<?php
+/**
+ * Zend Framework
+ *
+ * LICENSE
+ *
+ * This source file is subject to the new BSD license that is bundled
+ * with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://framework.zend.com/license/new-bsd
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@zend.com so we can send you a copy immediately.
+ *
+ * @category   Zend
+ * @package    Zend_Tool
+ * @subpackage Framework
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ * @version    $Id: ViewScriptsDirectory.php 18386 2009-09-23 20:44:43Z ralph $
+ */
+
+/**
+ * @see Zend_Tool_Project_Context_Filesystem_Directory
+ */
+require_once 'Zend/Tool/Project/Context/Filesystem/Directory.php';
+
+/**
+ * This class is the front most class for utilizing Zend_Tool_Project
+ *
+ * A profile is a hierarchical set of resources that keep track of
+ * items within a specific project.
+ *
+ * @category   Zend
+ * @package    Zend_Tool
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ */
+class Zend_Tool_Project_Context_Zf_LayoutScriptsDirectory extends Zend_Tool_Project_Context_Filesystem_Directory
+{
+
+    /**
+     * @var string
+     */
+    protected $_filesystemName = 'scripts';
+
+    /**
+     * getName()
+     *
+     * @return string
+     */
+    public function getName()
+    {
+        return 'LayoutScriptsDirectory';
+    }
+
+}

+ 68 - 6
library/Zend/Tool/Project/Context/Zf/ModelFile.php

@@ -21,11 +21,6 @@
  */
  */
 
 
 /**
 /**
- * @see Zend_Tool_Project_Context_Filesystem_File
- */
-require_once 'Zend/Tool/Project/Context/Filesystem/File.php';
-
-/**
  * This class is the front most class for utilizing Zend_Tool_Project
  * This class is the front most class for utilizing Zend_Tool_Project
  *
  *
  * A profile is a hierarchical set of resources that keep track of
  * A profile is a hierarchical set of resources that keep track of
@@ -36,10 +31,49 @@ require_once 'Zend/Tool/Project/Context/Filesystem/File.php';
  * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
  * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
  * @license    http://framework.zend.com/license/new-bsd     New BSD License
  * @license    http://framework.zend.com/license/new-bsd     New BSD License
  */
  */
-class Zend_Tool_Project_Context_Zf_ModelFile extends Zend_Tool_Project_Context_Filesystem_File
+class Zend_Tool_Project_Context_Zf_ModelFile extends Zend_Tool_Project_Context_Zf_AbstractClassFile
 {
 {
 
 
     /**
     /**
+     * @var string
+     */
+    protected $_modelName = 'Base';
+
+    /**
+     * @var string
+     */
+    protected $_moduleName = null;
+    
+    /**
+     * @var string
+     */
+    protected $_filesystemName = 'modelName';
+    
+    /**
+     * init()
+     *
+     */
+    public function init()
+    {
+        $this->_modelName = $this->_resource->getAttribute('modelName');
+        //$this->_moduleName = $this->_resource->getAttribute('moduleName');
+        $this->_filesystemName = ucfirst($this->_modelName) . '.php';
+        parent::init();
+    }
+
+    /**
+     * getPersistentAttributes
+     *
+     * @return array
+     */
+    public function getPersistentAttributes()
+    {
+        return array(
+            'modelName' => $this->getModelName()
+            );
+    }
+    
+    /**
      * getName()
      * getName()
      *
      *
      * @return string
      * @return string
@@ -49,4 +83,32 @@ class Zend_Tool_Project_Context_Zf_ModelFile extends Zend_Tool_Project_Context_F
         return 'ModelFile';
         return 'ModelFile';
     }
     }
 
 
+    public function getModelName()
+    {
+        return $this->_modelName;
+    }
+    
+    public function getContents()
+    {
+        
+        $className = $this->getFullClassName($this->_modelName, 'Model');
+        
+        $codeGenFile = new Zend_CodeGenerator_Php_File(array(
+            'fileName' => $this->getPath(),
+            'classes' => array(
+                new Zend_CodeGenerator_Php_Class(array(
+                    'name' => $className,
+                    //'methods' => array(
+                    //    new Zend_CodeGenerator_Php_Method(array(
+                    //        'name' => 'someMethodName',
+                    //        'body' => '/* method body here */',
+                    //    	  ))
+                    //    )
+                    ))
+                )
+            ));
+        return $codeGenFile->generate();
+    }
+    
+    
 }
 }

+ 1 - 1
library/Zend/Tool/Project/Context/Zf/ModulesDirectory.php

@@ -51,7 +51,7 @@ class Zend_Tool_Project_Context_Zf_ModulesDirectory extends Zend_Tool_Project_Co
      */
      */
     public function getName()
     public function getName()
     {
     {
-        return 'ModulesDirectory';
+        return 'modulesDirectory';
     }
     }
 
 
 }
 }

+ 9 - 1
library/Zend/Tool/Project/Context/Zf/ViewControllerScriptsDirectory.php

@@ -57,7 +57,7 @@ class Zend_Tool_Project_Context_Zf_ViewControllerScriptsDirectory extends Zend_T
     public function init()
     public function init()
     {
     {
         $this->_forControllerName = $this->_resource->getAttribute('forControllerName');
         $this->_forControllerName = $this->_resource->getAttribute('forControllerName');
-        $this->_filesystemName = $this->_forControllerName;
+        $this->_filesystemName = $this->_convertControllerNameToFilesystemName($this->_forControllerName);
         parent::init();
         parent::init();
         return $this;
         return $this;
     }
     }
@@ -83,5 +83,13 @@ class Zend_Tool_Project_Context_Zf_ViewControllerScriptsDirectory extends Zend_T
     {
     {
         return 'ViewControllerScriptsDirectory';
         return 'ViewControllerScriptsDirectory';
     }
     }
+    
+    protected function _convertControllerNameToFilesystemName($controllerName)
+    {
+        $filter = new Zend_Filter();
+        $filter->addFilter(new Zend_Filter_Word_CamelCaseToDash())
+            ->addFilter(new Zend_Filter_StringToLower());
+        return $filter->filter($controllerName);
+    }
 
 
 }
 }

+ 10 - 2
library/Zend/Tool/Project/Context/Zf/ViewScriptFile.php

@@ -73,7 +73,7 @@ class Zend_Tool_Project_Context_Zf_ViewScriptFile extends Zend_Tool_Project_Cont
     {
     {
         if ($forActionName = $this->_resource->getAttribute('forActionName')) {
         if ($forActionName = $this->_resource->getAttribute('forActionName')) {
             $this->_forActionName = $forActionName;
             $this->_forActionName = $forActionName;
-            $this->_filesystemName = $forActionName . '.phtml';
+            $this->_filesystemName = $this->_convertActionNameToFilesystemName($forActionName) . '.phtml';
         } elseif ($scriptName = $this->_resource->getAttribute('scriptName')) {
         } elseif ($scriptName = $this->_resource->getAttribute('scriptName')) {
             $this->_scriptName = $scriptName;
             $this->_scriptName = $scriptName;
             $this->_filesystemName = $scriptName . '.phtml';
             $this->_filesystemName = $scriptName . '.phtml';
@@ -126,7 +126,7 @@ class Zend_Tool_Project_Context_Zf_ViewScriptFile extends Zend_Tool_Project_Cont
   <h1>An error occurred</h1>
   <h1>An error occurred</h1>
   <h2><?php echo \$this->message ?></h2>
   <h2><?php echo \$this->message ?></h2>
 
 
-  <?php if ('development' == APPLICATION_ENV): ?>
+  <?php if (isset(\$this->exception)): ?>
 
 
   <h3>Exception information:</h3>
   <h3>Exception information:</h3>
   <p>
   <p>
@@ -201,4 +201,12 @@ EOS;
         return $contents;
         return $contents;
     }
     }
 
 
+    protected function _convertActionNameToFilesystemName($actionName)
+    {
+        $filter = new Zend_Filter();
+        $filter->addFilter(new Zend_Filter_Word_CamelCaseToDash())
+            ->addFilter(new Zend_Filter_StringToLower());
+        return $filter->filter($actionName);
+    }
+    
 }
 }

+ 10 - 2
library/Zend/Tool/Project/Profile/Iterator/ContextFilter.php

@@ -132,6 +132,10 @@ class Zend_Tool_Project_Profile_Iterator_ContextFilter extends RecursiveFilterIt
             $acceptNames = array($acceptNames);
             $acceptNames = array($acceptNames);
         }
         }
 
 
+        foreach ($acceptNames as $n => $v) {
+            $acceptNames[$n] = strtolower($v);
+        }
+        
         $this->_acceptNames = $acceptNames;
         $this->_acceptNames = $acceptNames;
         return $this;
         return $this;
     }
     }
@@ -148,6 +152,10 @@ class Zend_Tool_Project_Profile_Iterator_ContextFilter extends RecursiveFilterIt
             $denyNames = array($denyNames);
             $denyNames = array($denyNames);
         }
         }
 
 
+        foreach ($denyNames as $n => $v) {
+            $denyNames[$n] = strtolower($v);
+        }
+        
         $this->_denyNames = $denyNames;
         $this->_denyNames = $denyNames;
         return $this;
         return $this;
     }
     }
@@ -161,9 +169,9 @@ class Zend_Tool_Project_Profile_Iterator_ContextFilter extends RecursiveFilterIt
     {
     {
         $currentItem = $this->current();
         $currentItem = $this->current();
 
 
-        if (in_array($currentItem->getName(), $this->_acceptNames)) {
+        if (in_array(strtolower($currentItem->getName()), $this->_acceptNames)) {
             return true;
             return true;
-        } elseif (in_array($currentItem->getName(), $this->_denyNames)) {
+        } elseif (in_array(strtolower($currentItem->getName()), $this->_denyNames)) {
             return false;
             return false;
         }
         }
 
 

+ 3 - 0
library/Zend/Tool/Project/Provider/Abstract.php

@@ -83,6 +83,9 @@ abstract class Zend_Tool_Project_Provider_Abstract extends Zend_Tool_Framework_P
             $contextRegistry->addContextsFromDirectory(
             $contextRegistry->addContextsFromDirectory(
                 dirname(dirname(__FILE__)) . '/Context/Zf/', 'Zend_Tool_Project_Context_Zf_'
                 dirname(dirname(__FILE__)) . '/Context/Zf/', 'Zend_Tool_Project_Context_Zf_'
             );
             );
+            $contextRegistry->addContextsFromDirectory(
+                dirname(dirname(__FILE__)) . '/Context/Filesystem/', 'Zend_Tool_Project_Context_Filesystem_'
+            );
             self::$_isInitialized = true;
             self::$_isInitialized = true;
         }
         }
 
 

+ 17 - 4
library/Zend/Tool/Project/Provider/Action.php

@@ -87,8 +87,12 @@ class Zend_Tool_Project_Provider_Action
             throw new Zend_Tool_Project_Provider_Exception('Zend_Tool_Project_Provider_Action::createResource() expects \"controllerName\" is the name of a controller resource to create.');
             throw new Zend_Tool_Project_Provider_Exception('Zend_Tool_Project_Provider_Action::createResource() expects \"controllerName\" is the name of a controller resource to create.');
         }
         }
 
 
-       $controllerFile = self::_getControllerFileResource($profile, $controllerName, $moduleName);
+        $controllerFile = self::_getControllerFileResource($profile, $controllerName, $moduleName);
 
 
+        if ($controllerFile == null) {
+            throw new Zend_Tool_Project_Provider_Exception('Controller ' . $controllerName . ' was not found.');
+        }
+       
         return (($controllerFile->search(array('actionMethod' => array('actionName' => $actionName)))) instanceof Zend_Tool_Project_Profile_Resource);
         return (($controllerFile->search(array('actionMethod' => array('actionName' => $actionName)))) instanceof Zend_Tool_Project_Profile_Resource);
     }
     }
 
 
@@ -117,9 +121,10 @@ class Zend_Tool_Project_Provider_Action
     /**
     /**
      * create()
      * create()
      *
      *
-     * @param string $name
-     * @param string $controllerName
-     * @param bool $viewIncluded
+     * @param string $name           Action name for controller, in camelCase format.
+     * @param string $controllerName Controller name action should be applied to.
+     * @param bool $viewIncluded     Whether the view should the view be included.
+     * @param string $module         Module name action should be applied to.
      */
      */
     public function create($name, $controllerName = 'index', $viewIncluded = true, $module = null)
     public function create($name, $controllerName = 'index', $viewIncluded = true, $module = null)
     {
     {
@@ -130,6 +135,14 @@ class Zend_Tool_Project_Provider_Action
             throw new Zend_Tool_Project_Provider_Exception('This controller (' . $controllerName . ') already has an action named (' . $name . ')');
             throw new Zend_Tool_Project_Provider_Exception('This controller (' . $controllerName . ') already has an action named (' . $name . ')');
         }
         }
 
 
+        // Check that there is not a dash or underscore, return if doesnt match regex
+        if (preg_match('#[_-]#', $name)) {
+            throw new Zend_Tool_Project_Provider_Exception('Action names should be camel cased.');
+        }
+        
+        // ensure it is camelCase (lower first letter)
+        $name = strtolower(substr($name, 0, 1)) . substr($name, 1);
+        
         $actionMethod = self::createResource($this->_loadedProfile, $name, $controllerName, $module);
         $actionMethod = self::createResource($this->_loadedProfile, $name, $controllerName, $module);
 
 
         if ($this->_registry->getRequest()->isPretend()) {
         if ($this->_registry->getRequest()->isPretend()) {

+ 39 - 0
library/Zend/Tool/Project/Provider/Application.php

@@ -0,0 +1,39 @@
+<?php
+/**
+ * Zend Framework
+ *
+ * LICENSE
+ *
+ * This source file is subject to the new BSD license that is bundled
+ * with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://framework.zend.com/license/new-bsd
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@zend.com so we can send you a copy immediately.
+ *
+ * @category   Zend
+ * @package    Zend_Tool
+ * @subpackage Framework
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ * @version    $Id: Model.php 18386 2009-09-23 20:44:43Z ralph $
+ */
+
+/**
+ * @category   Zend
+ * @package    Zend_Tool
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ */
+class Zend_Tool_Project_Provider_Application extends Zend_Tool_Project_Provider_Abstract
+{
+    
+    protected $_specialties = array('ClassNamePrefix');
+    
+    public function changeClassNamePrefix($classNamePrefix, $force = false)
+    {
+        
+    }
+    
+}

+ 13 - 3
library/Zend/Tool/Project/Provider/Controller.php

@@ -81,7 +81,10 @@ class Zend_Tool_Project_Provider_Controller
             throw new Zend_Tool_Project_Provider_Exception($exceptionMessage);
             throw new Zend_Tool_Project_Provider_Exception($exceptionMessage);
         }
         }
 
 
-        $newController = $controllersDirectory->createResource('controllerFile', array('controllerName' => $controllerName));
+        $newController = $controllersDirectory->createResource(
+            'controllerFile', 
+            array('controllerName' => $controllerName, 'moduleName' => $moduleName)
+            );
 
 
         return $newController;
         return $newController;
     }
     }
@@ -125,9 +128,9 @@ class Zend_Tool_Project_Provider_Controller
     }
     }
 
 
     /**
     /**
-     * Enter description here...
+     * Create a new controller
      *
      *
-     * @param string $name The name of the controller to create.
+     * @param string $name The name of the controller to create, in camelCase.
      * @param bool $indexActionIncluded Whether or not to create the index action.
      * @param bool $indexActionIncluded Whether or not to create the index action.
      */
      */
     public function create($name, $indexActionIncluded = true, $module = null)
     public function create($name, $indexActionIncluded = true, $module = null)
@@ -142,6 +145,13 @@ class Zend_Tool_Project_Provider_Controller
             throw new Zend_Tool_Project_Provider_Exception('This project already has a controller named ' . $name);
             throw new Zend_Tool_Project_Provider_Exception('This project already has a controller named ' . $name);
         }
         }
 
 
+        // Check that there is not a dash or underscore, return if doesnt match regex
+        if (preg_match('#[_-]#', $name)) {
+            throw new Zend_Tool_Project_Provider_Exception('Controller names should be camel cased.');
+        }
+        
+        $name = ucwords($name);
+        
         try {
         try {
             $controllerResource = self::createResource($this->_loadedProfile, $name, $module);
             $controllerResource = self::createResource($this->_loadedProfile, $name, $module);
             if ($indexActionIncluded) {
             if ($indexActionIncluded) {

+ 202 - 0
library/Zend/Tool/Project/Provider/DbAdapter.php

@@ -0,0 +1,202 @@
+<?php
+/**
+ * Zend Framework
+ *
+ * LICENSE
+ *
+ * This source file is subject to the new BSD license that is bundled
+ * with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://framework.zend.com/license/new-bsd
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@zend.com so we can send you a copy immediately.
+ *
+ * @category   Zend
+ * @package    Zend_Tool
+ * @subpackage Framework
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ * @version    $Id: View.php 18386 2009-09-23 20:44:43Z ralph $
+ */
+
+/**
+ * @see Zend_Tool_Project_Provider_Abstract
+ */
+require_once 'Zend/Tool/Project/Provider/Abstract.php';
+
+/**
+ * @see Zend_Tool_Framework_Provider_Interactable
+ */
+require_once 'Zend/Tool/Framework/Provider/Interactable.php';
+
+/**
+ * @category   Zend
+ * @package    Zend_Tool
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ */
+class Zend_Tool_Project_Provider_DbAdapter
+    extends Zend_Tool_Project_Provider_Abstract
+    implements Zend_Tool_Framework_Provider_Interactable, Zend_Tool_Framework_Provider_Pretendable
+{
+    
+    protected $_appConfigFilePath = null;
+    
+    protected $_config = null;
+    
+    protected $_sectionName = 'production';
+    
+    public function configure($dsn = null, $interactivelyPrompt = false, $sectionName = 'production')
+    {
+        $profile = $this->_loadProfile(self::NO_PROFILE_THROW_EXCEPTION);
+        
+        $appConfigFileResource = $profile->search('applicationConfigFile');
+                
+        if ($appConfigFileResource == false) {
+            throw new Zend_Tool_Project_Exception('A project with an application config file is required to use this provider.');
+        }
+        
+        $this->_appConfigFilePath = $appConfigFileResource->getPath();
+        
+        $this->_config = new Zend_Config_Ini($this->_appConfigFilePath, null, array('skipExtends' => true, 'allowModifications' => true));
+        
+        if ($sectionName != 'production') {
+            $this->_sectionName = $sectionName;
+        }
+        
+        if (!isset($this->_config->{$this->_sectionName})) {
+            throw new Zend_Tool_Project_Exception('The config does not have a ' . $this->_sectionName . ' section.');
+        }
+        
+        if (isset($this->_config->{$this->_sectionName}->resources->db)) {
+            throw new Zend_Tool_Project_Exception('The config already has a db resource configured in section ' . $this->_sectionName . '.');
+        }
+        
+        if ($dsn) {
+            $this->_configureViaDSN($dsn);
+        } elseif ($interactivelyPrompt) {
+            $this->_promptForConfig();
+        } else {
+            echo 'Nothing to do!';
+        }
+        
+        
+    }
+    
+    protected function _configureViaDSN($dsn)
+    {
+        $dsnVars = array();
+        
+        if (strpos($dsn, '=') === false) {
+            throw new Zend_Tool_Project_Provider_Exception('At least one name value pair is expected, typcially '
+                . 'in the format of "adapter=Mysqli&username=uname&password=mypass&dbname=mydb"' 
+                );
+        }
+        
+        parse_str($dsn, $dsnVars);
+
+        $dbConfigValues = array();
+        
+        if (isset($dsnVars['adapter'])) {
+            $dbConfigValues['adapter'] = $dsnVars['adapter'];
+            unset($dsnVars['adapter']);
+        }
+        
+        $dbConfigValues['params'] = $dsnVars;
+        
+        $isPretend = $this->_registry->getRequest()->isPretend();
+        
+        $content = $this->_writeToApplicationConfig($dbConfigValues, $isPretend);
+        
+        $response = $this->_registry->getResponse();
+        
+        if ($isPretend) {
+            $response->appendContent('A db configuration for the ' . $this->_sectionName
+                . ' would be written to the application config file with the following contents: '
+                );
+            $response->appendContent($content);
+        } else {
+            $response->appendContent('A db configuration for the ' . $this->_sectionName
+                . ' has been written to the application config file.'
+                );
+        }
+    }
+    
+    protected function _promptForConfig()
+    {
+        echo '//@todo';
+    }
+
+    protected function _promtForConfigPdoMysql()
+    {
+        $r = array(
+            'username' => 'Username',
+            'password' => 'Password',
+            'dbname'   => 'Database',
+            'driver_options' => array(
+                
+                )
+            );
+    }
+
+    protected function _writeToApplicationConfig($configValues, $isPretend = false)
+    {
+        $configKeyNames = array('resources', 'db');
+        
+        $newDbLines = array();
+        
+        $rii = new RecursiveIteratorIterator(
+            new RecursiveArrayIterator($configValues),
+            RecursiveIteratorIterator::SELF_FIRST
+            );
+        
+        $lastDepth = 0;
+        
+        foreach ($rii as $name => $value) {
+            if ($lastDepth > $rii->getDepth()) {
+                array_pop($configKeyNames);
+            }
+            
+            $lastDepth = $rii->getDepth();
+            
+            if (is_array($value)) {
+                array_push($configKeyNames, $name);
+            } else {
+                $newDbLines[] = implode('.', $configKeyNames) . '.' . $name . ' = "' . $value . "\"\n";
+            }
+        }
+        
+        $originalLines = file($this->_appConfigFilePath);
+        
+        $newLines = array();
+        $insideSection = false;
+        
+        foreach ($originalLines as $originalLineIndex => $originalLine) {
+            
+            if ($insideSection === false && preg_match('#^\[' . $this->_sectionName . '#', $originalLine)) {
+                $insideSection = true;
+            }
+            
+            if ($insideSection) {
+                if ((trim($originalLine) == null) || ($originalLines[$originalLineIndex + 1][0] == '[')) {
+                    foreach ($newDbLines as $newDbLine) {
+                        $newLines[] = $newDbLine;
+                    }
+                    $insideSection = null;
+                }
+            }
+            
+            $newLines[] = $originalLine;
+        }
+
+        $newConfigContents = implode('', $newLines);
+        
+        if (!$isPretend) {
+            file_put_contents($this->_appConfigFilePath, $newConfigContents);
+        }
+        
+        return $newConfigContents;
+    }
+    
+}

+ 88 - 0
library/Zend/Tool/Project/Provider/DbTable.php

@@ -0,0 +1,88 @@
+<?php
+/**
+ * Zend Framework
+ *
+ * LICENSE
+ *
+ * This source file is subject to the new BSD license that is bundled
+ * with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://framework.zend.com/license/new-bsd
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@zend.com so we can send you a copy immediately.
+ *
+ * @category   Zend
+ * @package    Zend_Tool
+ * @subpackage Framework
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ * @version    $Id: View.php 18386 2009-09-23 20:44:43Z ralph $
+ */
+
+/**
+ * @see Zend_Tool_Project_Provider_Abstract
+ */
+require_once 'Zend/Tool/Project/Provider/Abstract.php';
+
+/**
+ * @category   Zend
+ * @package    Zend_Tool
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ */
+class Zend_Tool_Project_Provider_DbTable extends Zend_Tool_Project_Provider_Abstract
+{
+    
+    protected $_specialties = array('FromDatabase');
+    
+    /**
+     * @var Zend_Filter
+     */
+    protected $_nameFilter = null;
+    
+    public static function createResource(Zend_Tool_Project_Profile $profile, $dbTableName, $moduleName = null)
+    {
+        $profileSearchParams = array();
+
+        if ($moduleName != null && is_string($moduleName)) {
+            $profileSearchParams = array('modulesDirectory', 'moduleDirectory' => array('moduleName' => $moduleName));
+        }
+
+        $profileSearchParams[] = 'modelsDirectory';
+
+        $modelsDirectory = $profile->search($profileSearchParams);
+        
+        if (!($dbTableDirectory = $modelsDirectory->search('DbTableDirectory'))) {
+            $dbTableDirectory = $modelsDirectory->createResource('DbTableDirectory');
+        }
+        
+        $dbTableFile = $dbTableDirectory->createResource('DbTableFile', array('dbTableName' => $dbTableName));
+        
+        return $dbTableFile;
+    }
+      
+    
+    public function create($tableName, $module = null)
+    {
+        //@todo create
+    }
+    
+    public function createFromDatabase($module = null)
+    {
+        //@todo create from db
+    }
+    
+    protected function _convertTableNameToClassName($tableName)
+    {
+        if ($this->_nameFilter == null) {
+            $this->_nameFilter = new Zend_Filter();
+            $this->_nameFilter
+                ->addFilter(new Zend_Filter_Word_UnderscoreToCamelCase());
+        }
+        
+        
+        return $this->_nameFilter->filter($tableName);
+    }
+    
+}

+ 125 - 0
library/Zend/Tool/Project/Provider/Layout.php

@@ -0,0 +1,125 @@
+<?php
+/**
+ * Zend Framework
+ *
+ * LICENSE
+ *
+ * This source file is subject to the new BSD license that is bundled
+ * with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://framework.zend.com/license/new-bsd
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@zend.com so we can send you a copy immediately.
+ *
+ * @category   Zend
+ * @package    Zend_Tool
+ * @subpackage Framework
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ * @version    $Id: View.php 18386 2009-09-23 20:44:43Z ralph $
+ */
+
+/**
+ * @see Zend_Tool_Project_Provider_Abstract
+ */
+require_once 'Zend/Tool/Project/Provider/Abstract.php';
+
+/**
+ * @category   Zend
+ * @package    Zend_Tool
+ * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
+ * @license    http://framework.zend.com/license/new-bsd     New BSD License
+ */
+class Zend_Tool_Project_Provider_Layout extends Zend_Tool_Project_Provider_Abstract
+{
+    
+    public static function prepareApplicationConfig(Zend_Tool_Project_Profile $profile, $section = 'production', $layoutPath = 'layout/scripts/')
+    {
+        $appConfigFileResource = $profile->search('ApplicationConfigFile');
+                
+        if ($appConfigFileResource == false) {
+            throw new Zend_Tool_Project_Exception('A project with an application config file is required to use this provider.');
+        }
+        
+        $appConfigFilePath = $appConfigFileResource->getPath();
+        
+        $config = new Zend_Config_Ini($appConfigFilePath, null, array('skipExtends' => true, 'allowModifications' => true));
+        
+        if (!isset($config->{$section})) {
+            throw new Zend_Tool_Project_Exception('The config does not have a ' . $section . ' section.');
+        }
+        
+        $currentSection = $config->{$section};
+        
+        if (!isset($currentSection->resources)) {
+            $currentSection->resources = array();
+        }
+        
+        $configResources = $currentSection->resources;
+        
+        if (!isset($configResources->layout)) {
+            $configResources->layout = array();
+        }
+        
+        $layout = $configResources->layout;
+        
+        $layout->layoutPath = 'APPLICATION_PATH "layouts/scripts"';
+        
+        $writer = new Zend_Config_Writer_Ini(array(
+            'config' => $config,
+            'filename' => $appConfigFilePath
+            ));
+        $writer->write();
+        
+    }
+    
+    public static function createResource(Zend_Tool_Project_Profile $profile, $layoutName = 'layout')
+    {
+        $applicationDirectory = $profile->search('applicationDirectory');
+        $layoutDirectory = $applicationDirectory->search('layoutsDirectory');
+        
+        if ($layoutDirectory == false) {
+            $layoutDirectory = $applicationDirectory->createResource('layoutsDirectory');
+        }
+        
+        $layoutScriptsDirectory = $layoutDirectory->search('layoutScriptsDirectory');
+        
+        if ($layoutScriptsDirectory == false) {
+            $layoutScriptsDirectory = $layoutDirectory->createResource('layoutScriptsDirectory');
+        }
+        
+        $layoutScriptFile = $layoutScriptsDirectory->search('layoutScriptFile', array('layoutName' => 'layout'));
+
+        if ($layoutScriptFile == false) {
+            $layoutScriptFile = $layoutScriptsDirectory->createResource('layoutScriptFile', array('layoutName' => 'layout'));
+        }
+        
+        return $layoutScriptFile;
+    }
+    
+    public function enable()
+    {
+        $profile = $this->_loadProfile(self::NO_PROFILE_THROW_EXCEPTION);
+        
+        self::prepareApplicationConfig($profile);
+        
+        $layoutScriptFile = self::createResource($profile);
+        
+        $layoutScriptFile->create();
+        
+        $this->_registry->getResponse()->appendContent(
+            'Layouts have been enabled, and a default layout created at ' 
+            . $layoutScriptFile->getPath()
+            );
+            
+        $this->_registry->getResponse()->appendContent('A layout entry has been added to the application config file.');
+        
+    }
+    
+    public function disable()
+    {
+        
+    }
+    
+}

+ 26 - 47
library/Zend/Tool/Project/Provider/Manifest.php

@@ -21,46 +21,6 @@
  */
  */
 
 
 /**
 /**
- * @see Zend_Tool_Framework_Manifest_ProviderManifestable
- */
-require_once 'Zend/Tool/Framework/Manifest/ProviderManifestable.php';
-
-/**
- * @see Zend_Tool_Project_Provider_Profile
- */
-require_once 'Zend/Tool/Project/Provider/Profile.php';
-
-/**
- * @see Zend_Tool_Project_Provider_Project
- */
-require_once 'Zend/Tool/Project/Provider/Project.php';
-
-/**
- * @see Zend_Tool_Project_Provider_Controller
- */
-require_once 'Zend/Tool/Project/Provider/Controller.php';
-
-/**
- * @see Zend_Tool_Project_Provider_Action
- */
-require_once 'Zend/Tool/Project/Provider/Action.php';
-
-/**
- * @see Zend_Tool_Project_Provider_View
- */
-require_once 'Zend/Tool/Project/Provider/View.php';
-
-/**
- * @see Zend_Tool_Project_Provider_Module
- */
-require_once 'Zend/Tool/Project/Provider/Module.php';
-
-/**
- * @see Zend_Tool_Project_Provider_ProjectProvider
- */
-require_once 'Zend/Tool/Project/Provider/ProjectProvider.php';
-
-/**
  * @category   Zend
  * @category   Zend
  * @package    Zend_Tool
  * @package    Zend_Tool
  * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
  * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
@@ -77,14 +37,33 @@ class Zend_Tool_Project_Provider_Manifest implements
      */
      */
     public function getProviders()
     public function getProviders()
     {
     {
+        // the order here will represent what the output will look like when iterating a manifest
+        
         return array(
         return array(
-            new Zend_Tool_Project_Provider_Profile(),
-            new Zend_Tool_Project_Provider_Project(),
-            new Zend_Tool_Project_Provider_Controller(),
-            new Zend_Tool_Project_Provider_Action(),
-            new Zend_Tool_Project_Provider_View(),
-            new Zend_Tool_Project_Provider_Module(),
-            new Zend_Tool_Project_Provider_ProjectProvider()
+            // top level project & profile providers
+            'Zend_Tool_Project_Provider_Profile',
+            'Zend_Tool_Project_Provider_Project',
+        
+            // app layer provider
+            'Zend_Tool_Project_Provider_Application',
+        
+            // MVC layer providers
+            'Zend_Tool_Project_Provider_Model',
+            'Zend_Tool_Project_Provider_View',
+            'Zend_Tool_Project_Provider_Controller',
+            'Zend_Tool_Project_Provider_Action',
+            
+            // hMVC provider
+            'Zend_Tool_Project_Provider_Module',
+        
+            // application problem providers
+            'Zend_Tool_Project_Provider_Layout',
+            'Zend_Tool_Project_Provider_DbAdapter',
+            'Zend_Tool_Project_Provider_DbTable',
+            
+            // provider within project provider
+            'Zend_Tool_Project_Provider_ProjectProvider',
+            
         );
         );
     }
     }
 }
 }

+ 116 - 3
library/Zend/Tool/Project/Provider/Model.php

@@ -29,14 +29,127 @@
 class Zend_Tool_Project_Provider_Model extends Zend_Tool_Project_Provider_Abstract
 class Zend_Tool_Project_Provider_Model extends Zend_Tool_Project_Provider_Abstract
 {
 {
 
 
+    public static function createResource(Zend_Tool_Project_Profile $profile, $modelName, $moduleName = null)
+    {
+        if (!is_string($modelName)) {
+            throw new Zend_Tool_Project_Provider_Exception('Zend_Tool_Project_Provider_Model::createResource() expects \"modelName\" is the name of a model resource to create.');
+        }
+
+        if (!($modelsDirectory = self::_getModelsDirectoryResource($profile, $moduleName))) {
+            if ($moduleName) {
+                $exceptionMessage = 'A model directory for module "' . $moduleName . '" was not found.';
+            } else {
+                $exceptionMessage = 'A model directory was not found.';
+            }
+            throw new Zend_Tool_Project_Provider_Exception($exceptionMessage);
+        }
+
+        $newModel = $modelsDirectory->createResource(
+            'modelFile', 
+            array('modelName' => $modelName, 'moduleName' => $moduleName)
+            );
+
+        return $newModel;
+    }
+
     /**
     /**
-     * create()
+     * hasResource()
+     *
+     * @param Zend_Tool_Project_Profile $profile
+     * @param string $modelName
+     * @param string $moduleName
+     * @return Zend_Tool_Project_Profile_Resource
+     */
+    public static function hasResource(Zend_Tool_Project_Profile $profile, $modelName, $moduleName = null)
+    {
+        if (!is_string($modelName)) {
+            throw new Zend_Tool_Project_Provider_Exception('Zend_Tool_Project_Provider_Model::createResource() expects \"modelName\" is the name of a model resource to check for existence.');
+        }
+
+        $modelsDirectory = self::_getModelsDirectoryResource($profile, $moduleName);
+        return (($modelsDirectory->search(array('modelFile' => array('modelName' => $modelName)))) instanceof Zend_Tool_Project_Profile_Resource);
+    }
+    
+    /**
+     * _getModelsDirectoryResource()
+     *
+     * @param Zend_Tool_Project_Profile $profile
+     * @param string $moduleName
+     * @return Zend_Tool_Project_Profile_Resource
+     */
+    protected static function _getModelsDirectoryResource(Zend_Tool_Project_Profile $profile, $moduleName = null)
+    {
+        $profileSearchParams = array();
+
+        if ($moduleName != null && is_string($moduleName)) {
+            $profileSearchParams = array('modulesDirectory', 'moduleDirectory' => array('moduleName' => $moduleName));
+        }
+
+        $profileSearchParams[] = 'modelsDirectory';
+
+        return $profile->search($profileSearchParams);
+    }
+    
+    /**
+     * Create a new model
      *
      *
      * @param string $name
      * @param string $name
+     * @param string $module
      */
      */
-    public function create($name)
+    public function create($name, $module = null)
     {
     {
-        echo '@todo - create model';
+        $this->_loadProfile(self::NO_PROFILE_THROW_EXCEPTION);
+
+        // determine if testing is enabled in the project
+        $testingEnabled = Zend_Tool_Project_Provider_Test::isTestingEnabled($this->_loadedProfile);
+
+        if (self::hasResource($this->_loadedProfile, $name, $module)) {
+            throw new Zend_Tool_Project_Provider_Exception('This project already has a model named ' . $name);
+        }
+
+        // Check that there is not a dash or underscore, return if doesnt match regex
+        if (preg_match('#[_-]#', $name)) {
+            throw new Zend_Tool_Project_Provider_Exception('Model names should be camel cased.');
+        }
+        
+        $name = ucwords($name);
+        
+        try {
+            $modelResource = self::createResource($this->_loadedProfile, $name, $module);
+
+            if ($testingEnabled) {
+                $testModelResource = null;
+                // $testModelResource = Zend_Tool_Project_Provider_Test::createApplicationResource($this->_loadedProfile, $name, 'index', $module);
+            }
+
+        } catch (Exception $e) {
+            $response = $this->_registry->getResponse();
+            $response->setException($e);
+            return;
+        }
+
+        // do the creation
+        if ($this->_registry->getRequest()->isPretend()) {
+
+            $this->_registry->getResponse()->appendContent('Would create a model at '  . $modelResource->getContext()->getPath());
+
+            if ($testModelResource) {
+                $this->_registry->getResponse()->appendContent('Would create a model test file at ' . $testModelResource->getContext()->getPath());
+            }
+
+        } else {
+
+            $this->_registry->getResponse()->appendContent('Creating a model at ' . $modelResource->getContext()->getPath());
+            $modelResource->create();
+
+            if ($testModelResource) {
+                $this->_registry->getResponse()->appendContent('Creating a model test file at ' . $testModelResource->getContext()->getPath());
+                $testModelResource->create();
+            }
+
+            $this->_storeProfile();
+        }
+
     }
     }
 
 
 
 

+ 5 - 1
library/Zend/Tool/Project/Provider/Project.php

@@ -31,7 +31,9 @@ require_once 'Zend/Tool/Project/Provider/Abstract.php';
  * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
  * @copyright  Copyright (c) 2005-2009 Zend Technologies USA Inc. (http://www.zend.com)
  * @license    http://framework.zend.com/license/new-bsd     New BSD License
  * @license    http://framework.zend.com/license/new-bsd     New BSD License
  */
  */
-class Zend_Tool_Project_Provider_Project extends Zend_Tool_Project_Provider_Abstract
+class Zend_Tool_Project_Provider_Project
+    extends Zend_Tool_Project_Provider_Abstract
+    //implements Zend_Tool_Framework_Provider_DocblockManifestInterface
 {
 {
 
 
     protected $_specialties = array('Info');
     protected $_specialties = array('Info');
@@ -40,6 +42,8 @@ class Zend_Tool_Project_Provider_Project extends Zend_Tool_Project_Provider_Abst
      * create()
      * create()
      *
      *
      * @param string $path
      * @param string $path
+     * @param string $nameOfProfile shortName=n
+     * @param string $fileOfProfile shortName=f
      */
      */
     public function create($path, $nameOfProfile = null, $fileOfProfile = null)
     public function create($path, $nameOfProfile = null, $fileOfProfile = null)
     {
     {

+ 2 - 2
library/Zend/Tool/Project/Provider/View.php

@@ -61,7 +61,7 @@ class Zend_Tool_Project_Provider_View extends Zend_Tool_Project_Provider_Abstrac
             $profileSearchParams = array('modulesDirectory', 'moduleDirectory' => array('moduleName' => $moduleName));
             $profileSearchParams = array('modulesDirectory', 'moduleDirectory' => array('moduleName' => $moduleName));
             $noModuleSearch = null;
             $noModuleSearch = null;
         } else {
         } else {
-            $noModuleSearch = array('ModulesDirectory');
+            $noModuleSearch = array('modulesDirectory');
         }
         }
 
 
         $profileSearchParams[] = 'viewsDirectory';
         $profileSearchParams[] = 'viewsDirectory';
@@ -74,7 +74,7 @@ class Zend_Tool_Project_Provider_View extends Zend_Tool_Project_Provider_Abstrac
 
 
         $profileSearchParams['viewControllerScriptsDirectory'] = array('forControllerName' => $controllerName);
         $profileSearchParams['viewControllerScriptsDirectory'] = array('forControllerName' => $controllerName);
 
 
-        // XXXXXXXXX below is failing b/c of above search params
+        // @todo check if below is failing b/c of above search params
         if (($viewControllerScriptsDirectory = $viewScriptsDirectory->search($profileSearchParams)) === false) {
         if (($viewControllerScriptsDirectory = $viewScriptsDirectory->search($profileSearchParams)) === false) {
             $viewControllerScriptsDirectory = $viewScriptsDirectory->createResource('viewControllerScriptsDirectory', array('forControllerName' => $controllerName));
             $viewControllerScriptsDirectory = $viewScriptsDirectory->createResource('viewControllerScriptsDirectory', array('forControllerName' => $controllerName));
         }
         }