PageRenderTime 50ms CodeModel.GetById 22ms RepoModel.GetById 0ms app.codeStats 0ms

/_piecrust/src/PieCrust/Chef/Chef.php

https://bitbucket.org/AndreasLoew/piecrust
PHP | 220 lines | 197 code | 13 blank | 10 comment | 17 complexity | 79af4d5524ebd35c69bad7e3344e28d5 MD5 | raw file
Possible License(s): GPL-3.0, BSD-3-Clause, Apache-2.0
  1. <?php
  2. namespace PieCrust\Chef;
  3. require_once 'Log.php';
  4. require_once 'Console/CommandLine.php';
  5. require_once 'Console/Getopt.php';
  6. use \Log;
  7. use \Exception;
  8. use \Console_CommandLine;
  9. use \Console_CommandLine_Result;
  10. use \Console_Getopt;
  11. use PieCrust\PieCrust;
  12. use PieCrust\PieCrustDefaults;
  13. use PieCrust\PieCrustException;
  14. use PieCrust\Plugins\PluginLoader;
  15. use PieCrust\Util\PathHelper;
  16. /**
  17. * The PieCrust Chef application.
  18. */
  19. class Chef
  20. {
  21. public function __construct()
  22. {
  23. }
  24. public function run($userArgc = null, $userArgv = null)
  25. {
  26. try
  27. {
  28. return $this->runUnsafe($userArgc, $userArgv);
  29. }
  30. catch (Exception $e)
  31. {
  32. echo "Fatal Error: " . $e->getMessage() . PHP_EOL;
  33. echo $e->getFile() . ":" . $e->getLine() . PHP_EOL;
  34. echo $e->getTraceAsString() . PHP_EOL;
  35. return 2;
  36. }
  37. }
  38. public function runUnsafe($userArgc = null, $userArgv = null)
  39. {
  40. // Get the arguments.
  41. if ($userArgc == null || $userArgv == null)
  42. {
  43. $userArgv = Console_Getopt::readPHPArgv();
  44. // `readPHPArgv` returns a `PEAR_Error` (or something like it) if
  45. // it can't figure out the CLI arguments.
  46. if (!is_array($userArgv))
  47. throw new PieCrustException($userArgv->getMessage());
  48. $userArgc = count($userArgv);
  49. }
  50. // Find whether the '--root' parameter was given.
  51. $rootDir = null;
  52. foreach ($userArgv as $arg)
  53. {
  54. if (substr($arg, 0, strlen('--root=')) == '--root=')
  55. {
  56. $rootDir = substr($arg, strlen('--root='));
  57. break;
  58. }
  59. }
  60. if ($rootDir == null)
  61. {
  62. // No root given. Find it ourselves.
  63. $rootDir = PathHelper::getAppRootDir(getcwd());
  64. }
  65. else
  66. {
  67. // The root was given.
  68. $rootDir = PathHelper::getAbsolutePath($rootDir);
  69. if (!is_dir($rootDir))
  70. throw new PieCrustException("The given root directory doesn't exist: " . $rootDir);
  71. }
  72. // Build the appropriate app.
  73. if ($rootDir == null)
  74. {
  75. $pieCrust = new NullPieCrust();
  76. }
  77. else
  78. {
  79. $pieCrust = new PieCrust(array(
  80. 'root' => $rootDir,
  81. 'cache' => !in_array('--nocache', $userArgv)
  82. ));
  83. }
  84. // Set up the command line parser.
  85. $parser = new Console_CommandLine(array(
  86. 'name' => 'chef',
  87. 'description' => 'The PieCrust chef manages your website.',
  88. 'version' => PieCrustDefaults::VERSION
  89. ));
  90. // Sort commands by name.
  91. $sortedCommands = $pieCrust->getPluginLoader()->getCommands();
  92. usort($sortedCommands, function ($c1, $c2) { return strcmp($c1->getName(), $c2->getName()); });
  93. // Add commands to the parser.
  94. foreach ($sortedCommands as $command)
  95. {
  96. $commandParser = $parser->addCommand($command->getName());
  97. $command->setupParser($commandParser);
  98. $this->addCommonOptionsAndArguments($commandParser);
  99. }
  100. // Parse the command line.
  101. try
  102. {
  103. $result = $parser->parse($userArgc, $userArgv);
  104. }
  105. catch (Exception $e)
  106. {
  107. $parser->displayError($e->getMessage());
  108. return 1;
  109. }
  110. // If no command was given, use `help`.
  111. if (empty($result->command_name))
  112. {
  113. $result = $parser->parse(2, array('chef', 'help'));
  114. }
  115. // Create the log.
  116. $debugMode = $result->command->options['debug'];
  117. $quietMode = $result->command->options['quiet'];
  118. if ($debugMode && $quietMode)
  119. {
  120. $parser->displayError("You can't specify both --debug and --quiet.");
  121. return 1;
  122. }
  123. $log = Log::singleton('console', 'Chef', '', array('lineFormat' => '%{message}'));
  124. // Run the command.
  125. foreach ($pieCrust->getPluginLoader()->getCommands() as $command)
  126. {
  127. if ($command->getName() == $result->command_name)
  128. {
  129. try
  130. {
  131. if ($rootDir == null && $command->requiresWebsite())
  132. {
  133. $cwd = getcwd();
  134. throw new PieCrustException("No PieCrust website in '{$cwd}' ('_content/config.yml' not found!).");
  135. }
  136. $context = new ChefContext($pieCrust, $result, $log);
  137. $context->setVerbosity($debugMode ?
  138. 'debug' :
  139. ($quietMode ? 'quiet' : 'default')
  140. );
  141. $command->run($context);
  142. return;
  143. }
  144. catch (Exception $e)
  145. {
  146. $log->emerg(self::getErrorMessage($e, $debugMode));
  147. return 1;
  148. }
  149. }
  150. }
  151. }
  152. public static function getErrorMessage(Exception $e, $debugMode = false)
  153. {
  154. $message = $e->getMessage();
  155. if ($debugMode)
  156. {
  157. $message .= PHP_EOL;
  158. $message .= PHP_EOL;
  159. $message .= "Debug Information" . PHP_EOL;
  160. while ($e)
  161. {
  162. $message .= "-----------------" . PHP_EOL;
  163. $message .= $e->getMessage() . PHP_EOL;
  164. $message .= $e->getTraceAsString();
  165. $message .= PHP_EOL;
  166. $e = $e->getPrevious();
  167. }
  168. $message .= "-----------------" . PHP_EOL;
  169. }
  170. return $message;
  171. }
  172. protected function addCommonOptionsAndArguments(Console_CommandLine $parser)
  173. {
  174. $parser->addOption('root', array(
  175. 'long_name' => '--root',
  176. 'description' => "The root directory of the website (defaults to the first parent of the current directory that contains a '_content' directory).",
  177. 'default' => null,
  178. 'help_name' => 'ROOT_DIR'
  179. ));
  180. $parser->addOption('debug', array(
  181. 'long_name' => '--debug',
  182. 'description' => "Show debug information.",
  183. 'default' => false,
  184. 'help_name' => 'DEBUG',
  185. 'action' => 'StoreTrue'
  186. ));
  187. $parser->addOption('nocache', array(
  188. 'long_name' => '--nocache',
  189. 'description' => "When applicable, disable caching.",
  190. 'default' => false,
  191. 'help_name' => 'NOCACHE',
  192. 'action' => 'StoreTrue'
  193. ));
  194. $parser->addOption('quiet', array(
  195. 'long_name' => '--quiet',
  196. 'description' => "Print only important information.",
  197. 'default' => false,
  198. 'help_name' => 'QUIET',
  199. 'action' => 'StoreTrue'
  200. ));
  201. }
  202. }