diff --git a/PHPCI/Application.php b/PHPCI/Application.php index 9bacd78d..0723c2ad 100644 --- a/PHPCI/Application.php +++ b/PHPCI/Application.php @@ -32,11 +32,14 @@ class Application extends b8\Application $externalAction = in_array($this->controllerName, array('Bitbucket', 'Github', 'Gitlab', 'BuildStatus')); $skipValidation = ($externalAction || $sessionAction); - if($skipValidation || $this->validateSession()) { + if ($skipValidation || $this->validateSession()) { parent::handleRequest(); } } catch (\Exception $ex) { - $content = '
Please paste the details below into a new bug report so that we can investigate and fix it.
'; + $content = 'Please paste the details below into a + new bug report + so that we can investigate and fix it.
'; ob_start(); var_dump(array( diff --git a/PHPCI/Builder.php b/PHPCI/Builder.php index 0667a551..42f98ee1 100644 --- a/PHPCI/Builder.php +++ b/PHPCI/Builder.php @@ -52,12 +52,7 @@ class Builder /** * @var bool */ - protected $verbose = false; - - /** - * @var bool[] - */ - protected $plugins = array(); + protected $verbose = true; /** * @var \PHPCI\Model\Build @@ -84,7 +79,6 @@ class Builder * interpolation and environment variables * @var array * @see setInterpolationVars() - * @see getInterpolationVars() */ protected $interpolation_vars = array(); @@ -93,19 +87,21 @@ class Builder */ protected $store; + /** + * @var bool + */ + public $quiet = false; + /** * Set up the builder. * @param \PHPCI\Model\Build * @param callable */ - public function __construct(Build $build, $logCallback = null) + public function __construct(Build $build, callable $logCallback) { $this->build = $build; $this->store = Store\Factory::getStore('Build'); - - if (!is_null($logCallback) && is_callable($logCallback)) { - $this->logCallback = $logCallback; - } + $this->logCallback = $logCallback; } /** @@ -123,7 +119,13 @@ class Builder */ public function getConfig($key) { - return isset($this->config[$key]) ? $this->config[$key] : null; + $rtn = null; + + if (isset($this->config[$key])) { + $rtn = $this->config[$key]; + } + + return $rtn; } /** @@ -136,29 +138,11 @@ class Builder return Config::getInstance()->get($key); } - /** - * Access the build. - * @param Build - */ - public function getBuild() - { - return $this->build; - } - /** * @return string The title of the project being built. */ public function getBuildProjectTitle() { - return $this->getBuild()->getProject()->getTitle(); - } - - /** - * Indicates if the build has passed or failed. - * @return bool - */ - public function getSuccessStatus() - { - return $this->success; + return $this->build->getProject()->getTitle(); } /** @@ -173,47 +157,41 @@ class Builder $this->build->sendStatusPostback(); try { - if ($this->setupBuild()) { - // Run setup steps: - $this->executePlugins('setup'); + // Set up the build: + $this->setupBuild(); - // Run the any tests: - $this->executePlugins('test'); + // Run the core plugin stages: + foreach (array('setup', 'test', 'complete') as $stage) { + $this->executePlugins($stage); $this->log(''); - - // Run build complete steps: - $this->executePlugins('complete'); - - // Run success or failure plugins: - if ($this->success) { - $this->build->setStatus(2); - - $this->executePlugins('success'); - $this->logSuccess('BUILD SUCCESSFUL!'); - } else { - $this->build->setStatus(3); - - $this->executePlugins('failure'); - $this->logFailure('BUILD FAILED!'); - } - - $this->log(''); - } else { - $this->build->setStatus(3); } + + // Failed build? Execute failure plugins and then mark the build as failed. + if (!$this->success) { + $this->executePlugins('failure'); + throw new \Exception('BUILD FAILED!'); + } + + // If we got this far, the build was successful! + if ($this->success) { + $this->build->setStatus(2); + $this->executePlugins('success'); + $this->logSuccess('BUILD SUCCESSFUL!'); + } + } catch (\Exception $ex) { $this->logFailure($ex->getMessage()); $this->build->setStatus(3); } // Clean up: - $this->removeBuild(); + $this->log('Removing build.'); + shell_exec(sprintf('rm -Rf "%s"', $this->buildPath)); // Update the build in the database, ping any external services, etc. $this->build->sendStatusPostback(); $this->build->setFinished(new \DateTime()); $this->build->setLog($this->log); - $this->build->setPlugins(json_encode($this->plugins)); $this->store->save($this->build); } @@ -223,8 +201,10 @@ class Builder public function executeCommand() { $command = call_user_func_array('sprintf', func_get_args()); - - $this->log('Executing: ' . $command, ' '); + + if (!$this->quiet) { + $this->log('Executing: ' . $command, ' '); + } $status = 0; exec($command, $this->lastOutput, $status); @@ -233,7 +213,14 @@ class Builder $this->log($this->lastOutput, ' '); } - return ($status == 0) ? true : false; + + $rtn = false; + + if ($status == 0) { + $rtn = true; + } + + return $rtn; } /** @@ -251,25 +238,16 @@ class Builder */ public function log($message, $prefix = '') { - if (is_array($message)) { - foreach ($message as $item) { - if (is_callable($this->logCallback)) { - call_user_func_array($this->logCallback, array($prefix . $item)); - } - - $this->log .= $prefix . $item . PHP_EOL; - } - } else { - $message = $prefix . $message; - $this->log .= $message . PHP_EOL; + if (!is_array($message)) { + $message = array($message); + } - if (isset($this->logCallback) && is_callable($this->logCallback)) { - call_user_func_array($this->logCallback, array($message)); - } + foreach ($message as $item) { + call_user_func_array($this->logCallback, array($prefix . $item)); + $this->log .= $prefix . $item . PHP_EOL; } $this->build->setLog($this->log); - $this->build->setPlugins(json_encode($this->plugins)); $this->store->save($this->build); } @@ -291,15 +269,6 @@ class Builder $this->log("\033[0;31m" . $message . "\033[0m"); } - /** - * Get an array key => value pairs that are used for interpolation - * @return array - */ - public function getInterpolationVars() - { - return $this->interpolation_vars; - } - /** * Replace every occurance of the interpolation vars in the given string * Example: "This is build %PHPCI_BUILD%" => "This is build 182" @@ -308,12 +277,9 @@ class Builder */ public function interpolate($input) { - $trans_table = array(); - foreach ($this->getInterpolationVars() as $key => $value) { - $trans_table['%'.$key.'%'] = $value; - $trans_table['%PHPCI_'.$key.'%'] = $value; - } - return strtr($input, $trans_table); + $keys = array_keys($this->interpolation_vars); + $values = array_values($this->interpolation_vars); + return str_replace($keys, $values, $input); } /** @@ -322,15 +288,28 @@ class Builder */ protected function setInterpolationVars() { - $this->interpolation_vars = array( - 'PHPCI' => 1, - 'COMMIT' => $this->build->getCommitId(), - 'PROJECT' => $this->build->getProject()->getId(), - 'BUILD' => $this->build->getId(), - 'PROJECT_TITLE' => $this->build->getProject()->getTitle(), - 'BUILD_PATH' => $this->buildPath, - 'BUILD_URI' => PHPCI_URL . "build/view/" . $this->build->getId(), - ); + $this->interpolation_vars = array(); + $this->interpolation_vars['%PHPCI%'] = 1; + $this->interpolation_vars['%COMMIT%'] = $this->build->getCommitId(); + $this->interpolation_vars['%PROJECT%'] = $this->build->getProjectId(); + $this->interpolation_vars['%BUILD%'] = $this->build->getId(); + $this->interpolation_vars['%PROJECT_TITLE%'] = $this->getBuildProjectTitle(); + $this->interpolation_vars['%BUILD_PATH%'] = $this->buildPath; + $this->interpolation_vars['%BUILD_URI%'] = PHPCI_URL . "build/view/" . $this->build->getId(); + $this->interpolation_vars['%PHPCI_COMMIT%'] = $this->interpolation_vars['%COMMIT%']; + $this->interpolation_vars['%PHPCI_PROJECT%'] = $this->interpolation_vars['%PROJECT%']; + $this->interpolation_vars['%PHPCI_BUILD%'] = $this->interpolation_vars['%BUILD%']; + $this->interpolation_vars['%PHPCI_PROJECT_TITLE%'] = $this->interpolation_vars['%PROJECT_TITLE%']; + $this->interpolation_vars['%PHPCI_BUILD_PATH%'] = $this->interpolation_vars['%BUILD_PATH%']; + $this->interpolation_vars['%PHPCI_BUILD_URI%'] = $this->interpolation_vars['%BUILD_URI%']; + + putenv('PHPCI=1'); + putenv('PHPCI_COMMIT='.$this->interpolation_vars['%COMMIT%']); + putenv('PHPCI_PROJECT='.$this->interpolation_vars['%PROJECT%']); + putenv('PHPCI_BUILD='.$this->interpolation_vars['%BUILD%']); + putenv('PHPCI_PROJECT_TITLE='.$this->interpolation_vars['%PROJECT_TITLE%']); + putenv('PHPCI_BUILD_PATH='.$this->interpolation_vars['%BUILD_PATH%']); + putenv('PHPCI_BUILD_URI='.$this->interpolation_vars['%BUILD_URI%']); } /** @@ -338,28 +317,20 @@ class Builder */ protected function setupBuild() { - $commitId = $this->build->getCommitId(); $buildId = 'project' . $this->build->getProject()->getId() . '-build' . $this->build->getId(); $this->ciDir = dirname(__FILE__) . '/../'; $this->buildPath = $this->ciDir . 'build/' . $buildId . '/'; $this->setInterpolationVars(); - // Setup environment vars that will be accessible during exec() - foreach ($this->getInterpolationVars() as $key => $value) { - putenv($key.'='.$value); - } - // Create a working copy of the project: if (!$this->build->createWorkingCopy($this, $this->buildPath)) { - return false; + throw new \Exception('Could not create a working copy.'); } // Does the project's phpci.yml request verbose mode? if (!isset($this->config['build_settings']['verbose']) || !$this->config['build_settings']['verbose']) { $this->verbose = false; - } else { - $this->verbose = true; } // Does the project have any paths it wants plugins to ignore? @@ -390,78 +361,55 @@ class Builder $options['allow_failures'] = false; } - $class = str_replace('_', ' ', $plugin); - $class = ucwords($class); - $class = 'PHPCI\\Plugin\\' . str_replace(' ', '', $class); + // Try and execute it: + if ($this->executePlugin($plugin, $options)) { - if (!class_exists($class)) { - $this->logFailure('Plugin does not exist: ' . $plugin); + // Execution was successful: + $this->logSuccess('PLUGIN STATUS: SUCCESS!'); - if ($stage == 'test') { - $this->plugins[$plugin] = false; + } else { - if (!$options['allow_failures']) { - $this->success = false; - } - } - - continue; - } - - try { - $obj = new $class($this, $options); - - if (!$obj->execute()) { - if ($stage == 'test') { - $this->plugins[$plugin] = false; - - if (!$options['allow_failures']) { - $this->success = false; - } - } - - $this->logFailure('PLUGIN STATUS: FAILED'); - continue; - } - } catch (\Exception $ex) { - $this->logFailure('EXCEPTION: ' . $ex->getMessage()); - - if ($stage == 'test') { - $this->plugins[$plugin] = false; - - if (!$options['allow_failures']) { - $this->success = false; - } + // If we're in the "test" stage and the plugin is not allowed to fail, + // then mark the build as failed: + if ($stage == 'test' && !$options['allow_failures']) { + $this->success = false; } $this->logFailure('PLUGIN STATUS: FAILED'); - continue; } - - if ($stage == 'test') { - $this->plugins[$plugin] = true; - } - - $this->logSuccess('PLUGIN STATUS: SUCCESS!'); } } /** - * Clean up our working copy. - */ - protected function removeBuild() - { - $this->log('Removing build.'); - shell_exec(sprintf('rm -Rf "%s"', $this->buildPath)); - } - - /** - * Store build meta data + * Executes a given plugin, with options and returns the result. */ - public function storeBuildMeta($key, $value) + protected function executePlugin($plugin, $options) { - $value = json_encode($value); - $this->store->setMeta($this->build->getProjectId(), $this->build->getId(), $key, $value); + // Figure out the class name and check the plugin exists: + $class = str_replace('_', ' ', $plugin); + $class = ucwords($class); + $class = 'PHPCI\\Plugin\\' . str_replace(' ', '', $class); + + if (!class_exists($class)) { + $this->logFailure('Plugin does not exist: ' . $plugin); + return false; + } + + $rtn = true; + + // Try running it: + try { + $obj = new $class($this, $this->build, $options); + + if (!$obj->execute()) { + $rtn = false; + } + } catch (\Exception $ex) { + $this->logFailure('EXCEPTION: ' . $ex->getMessage()); + $rtn = false; + } + + return $rtn; } /** diff --git a/PHPCI/Command/DaemonCommand.php b/PHPCI/Command/DaemonCommand.php index 94ecb464..d6458f2b 100644 --- a/PHPCI/Command/DaemonCommand.php +++ b/PHPCI/Command/DaemonCommand.php @@ -66,7 +66,7 @@ class DaemonCommand extends Command protected function startDaemon() { - if ( file_exists(PHPCI_DIR.'/daemon/daemon.pid') ) { + if (file_exists(PHPCI_DIR.'/daemon/daemon.pid')) { echo "Already started\n"; return "alreadystarted"; } @@ -80,7 +80,7 @@ class DaemonCommand extends Command protected function stopDaemon() { - if ( !file_exists(PHPCI_DIR.'/daemon/daemon.pid') ) { + if (!file_exists(PHPCI_DIR.'/daemon/daemon.pid')) { echo "Not started\n"; return "notstarted"; } @@ -94,14 +94,14 @@ class DaemonCommand extends Command protected function statusDaemon() { - if ( !file_exists(PHPCI_DIR.'/daemon/daemon.pid') ) { + if (!file_exists(PHPCI_DIR.'/daemon/daemon.pid')) { echo "Not running\n"; return "notrunning"; } $pid = trim(file_get_contents(PHPCI_DIR.'/daemon/daemon.pid')); $pidcheck = sprintf("/proc/%s", $pid); - if ( is_dir($pidcheck) ) { + if (is_dir($pidcheck)) { echo "Running\n"; return "running"; } diff --git a/PHPCI/Command/DaemoniseCommand.php b/PHPCI/Command/DaemoniseCommand.php index f46e6948..3c490d75 100644 --- a/PHPCI/Command/DaemoniseCommand.php +++ b/PHPCI/Command/DaemoniseCommand.php @@ -57,7 +57,7 @@ class DaemoniseCommand extends Command if (0 == $buildCount && $this->sleep < 15) { $this->sleep++; - } else if (1 < $this->sleep) { + } elseif (1 < $this->sleep) { $this->sleep--; } echo '.'.(0 === $buildCount?'':'build'); diff --git a/PHPCI/Command/GenerateCommand.php b/PHPCI/Command/GenerateCommand.php index 54a729ca..3a97f70c 100644 --- a/PHPCI/Command/GenerateCommand.php +++ b/PHPCI/Command/GenerateCommand.php @@ -14,6 +14,8 @@ use Symfony\Component\Console\Input\InputArgument; use Symfony\Component\Console\Input\InputInterface; use Symfony\Component\Console\Input\InputOption; use Symfony\Component\Console\Output\OutputInterface; +use b8\Database; +use b8\Database\CodeGenerator; /** * Generate console command - Reads the database and generates models and stores. @@ -35,7 +37,7 @@ class GenerateCommand extends Command */ protected function execute(InputInterface $input, OutputInterface $output) { - $gen = new \b8\Database\CodeGenerator(\b8\Database::getConnection(), 'PHPCI', PHPCI_DIR . '/PHPCI/'); + $gen = new CodeGenerator(Database::getConnection(), 'PHPCI', PHPCI_DIR . '/PHPCI/', false); $gen->generateModels(); $gen->generateStores(); } diff --git a/PHPCI/Command/InstallCommand.php b/PHPCI/Command/InstallCommand.php index dea4e560..7f9daf6d 100644 --- a/PHPCI/Command/InstallCommand.php +++ b/PHPCI/Command/InstallCommand.php @@ -44,7 +44,8 @@ class InstallCommand extends Command $conf['b8']['database']['name'] = $this->ask('Enter the database name PHPCI should use: '); $conf['b8']['database']['username'] = $this->ask('Enter your MySQL username: '); $conf['b8']['database']['password'] = $this->ask('Enter your MySQL password: ', true); - $conf['phpci']['url'] = $this->ask('Your PHPCI URL (without trailing slash): ', false, array(FILTER_VALIDATE_URL,"/[^\/]$/i")); + $ask = 'Your PHPCI URL (without trailing slash): '; + $conf['phpci']['url'] = $this->ask($ask, false, array(FILTER_VALIDATE_URL,"/[^\/]$/i")); $conf['phpci']['github']['id'] = $this->ask('(Optional) Github Application ID: ', true); $conf['phpci']['github']['secret'] = $this->ask('(Optional) Github Application Secret: ', true); @@ -54,7 +55,9 @@ class InstallCommand extends Command $conf['phpci']['email_settings']['smtp_username'] = $this->ask('(Optional) Smtp Username: ', true); $conf['phpci']['email_settings']['smtp_password'] = $this->ask('(Optional) Smtp Password: ', true); $conf['phpci']['email_settings']['from_address'] = $this->ask('(Optional) Email address to send from: ', true); - $conf['phpci']['email_settings']['default_mailto_address'] = $this->ask('(Optional) Default address to email notifications to: ', true); + + $ask = '(Optional) Default address to email notifications to: '; + $conf['phpci']['email_settings']['default_mailto_address'] = $this->ask($ask, true); $dbUser = $conf['b8']['database']['username']; $dbPass = $conf['b8']['database']['password']; @@ -126,7 +129,7 @@ class InstallCommand extends Command return $rtn; } - protected function controlFormat($valueToInspect,$filter,&$statusMessage) + protected function controlFormat($valueToInspect, $filter, &$statusMessage) { $filters = !(is_array($filter))? array($filter) : $filter; $statusMessage = ''; @@ -148,13 +151,13 @@ class InstallCommand extends Command switch ($filter) { - case FILTER_VALIDATE_URL : + case FILTER_VALIDATE_URL: $statusMessage = 'Incorrect url format.' . PHP_EOL; break; - case FILTER_VALIDATE_EMAIL : + case FILTER_VALIDATE_EMAIL: $statusMessage = 'Incorrect e-mail format.' . PHP_EOL; break; - case FILTER_VALIDATE_REGEXP : + case FILTER_VALIDATE_REGEXP: $statusMessage = 'Incorrect format.' . PHP_EOL; break; } diff --git a/PHPCI/Command/RunCommand.php b/PHPCI/Command/RunCommand.php index abd30c6c..94d191d3 100644 --- a/PHPCI/Command/RunCommand.php +++ b/PHPCI/Command/RunCommand.php @@ -52,7 +52,9 @@ class RunCommand extends Command if ($input->getOption('verbose')) { $builder = new Builder($build, array($this, 'logCallback')); } else { - $builder = new Builder($build); + $builder = new Builder($build, function () { + // Empty stub function. + }); } $builder->execute(); diff --git a/PHPCI/Controller.php b/PHPCI/Controller.php index e344a613..d95c24e0 100644 --- a/PHPCI/Controller.php +++ b/PHPCI/Controller.php @@ -19,46 +19,49 @@ class Controller extends \b8\Controller */ protected $view; - public function init() {} + public function init() + { + // Extended by actual controllers. + } - public function __construct(Config $config, Request $request, Response $response) - { - parent::__construct($config, $request, $response); + public function __construct(Config $config, Request $request, Response $response) + { + parent::__construct($config, $request, $response); - $class = explode('\\', get_class($this)); - $this->className = substr(array_pop($class), 0, -10); - $this->setControllerView(); - } + $class = explode('\\', get_class($this)); + $this->className = substr(array_pop($class), 0, -10); + $this->setControllerView(); + } - protected function setControllerView() - { - if (View::exists($this->className)) { - $this->controllerView = new View($this->className); - } else { - $this->controllerView = new View\UserView('{@content}'); - } - } + protected function setControllerView() + { + if (View::exists($this->className)) { + $this->controllerView = new View($this->className); + } else { + $this->controllerView = new View\UserView('{@content}'); + } + } - protected function setView($action) - { - if (View::exists($this->className . '/' . $action)) { - $this->view = new View($this->className . '/' . $action); - } - } + protected function setView($action) + { + if (View::exists($this->className . '/' . $action)) { + $this->view = new View($this->className . '/' . $action); + } + } - public function handleAction($action, $actionParams) - { - $this->setView($action); - $response = parent::handleAction($action, $actionParams); + public function handleAction($action, $actionParams) + { + $this->setView($action); + $response = parent::handleAction($action, $actionParams); - if (is_string($response)) { - $this->controllerView->content = $response; - } elseif (isset($this->view)) { - $this->controllerView->content = $this->view->render(); - } + if (is_string($response)) { + $this->controllerView->content = $response; + } elseif (isset($this->view)) { + $this->controllerView->content = $this->view->render(); + } - $this->response->setContent($this->controllerView->render()); + $this->response->setContent($this->controllerView->render()); - return $this->response; - } -} \ No newline at end of file + return $this->response; + } +} diff --git a/PHPCI/Controller/BuildController.php b/PHPCI/Controller/BuildController.php index cd8007b1..8c183774 100644 --- a/PHPCI/Controller/BuildController.php +++ b/PHPCI/Controller/BuildController.php @@ -38,7 +38,7 @@ class BuildController extends \PHPCI\Controller $build = $this->buildStore->getById($buildId); $this->view->plugins = $this->getUiPlugins(); $this->view->build = $build; - $this->view->data = $this->getBuildData($buildId); + $this->view->data = $this->getBuildData($build); } protected function getUiPlugins() @@ -63,7 +63,7 @@ class BuildController extends \PHPCI\Controller */ public function data($buildId) { - die($this->getBuildData($buildId)); + die($this->getBuildData($this->buildStore->getById($buildId))); } /** @@ -86,10 +86,8 @@ class BuildController extends \PHPCI\Controller /** * Get build data from database and json encode it: */ - protected function getBuildData($buildId) + protected function getBuildData($build) { - $build = $this->buildStore->getById($buildId); - $data = array(); $data['status'] = (int)$build->getStatus(); $data['log'] = $this->cleanLog($build->getLog()); diff --git a/PHPCI/Controller/PluginController.php b/PHPCI/Controller/PluginController.php index 2d9d74fe..0dd3f2b4 100644 --- a/PHPCI/Controller/PluginController.php +++ b/PHPCI/Controller/PluginController.php @@ -68,7 +68,7 @@ class PluginController extends \PHPCI\Controller $this->setComposerJson($json); if ($this->canInstall) { - $res = shell_exec($this->composerPath . ' update --working-dir=' . APPLICATION_PATH . ' > /dev/null 2>&1 &'); + shell_exec($this->composerPath . ' update --working-dir=' . APPLICATION_PATH . ' > /dev/null 2>&1 &'); } header('Location: ' . PHPCI_URL . 'plugin?r=' . $package); @@ -89,7 +89,7 @@ class PluginController extends \PHPCI\Controller $this->setComposerJson($json); if ($this->canInstall) { - $res = shell_exec($this->composerPath . ' update --working-dir=' . APPLICATION_PATH . ' > /dev/null 2>&1 &'); + shell_exec($this->composerPath . ' update --working-dir=' . APPLICATION_PATH . ' > /dev/null 2>&1 &'); header('Location: ' . PHPCI_URL . 'plugin?i=' . $package); die; @@ -141,10 +141,10 @@ class PluginController extends \PHPCI\Controller public function packagistSearch() { - $q = $this->getParam('q', ''); + $searchQuery = $this->getParam('q', ''); $http = new \b8\HttpClient(); $http->setHeaders(array('User-Agent: PHPCI/1.0 (+http://www.phptesting.org)')); - $res = $http->get('https://packagist.org/search.json', array('q' => $q)); + $res = $http->get('https://packagist.org/search.json', array('q' => $searchQuery)); die(json_encode($res['body'])); } diff --git a/PHPCI/Controller/ProjectController.php b/PHPCI/Controller/ProjectController.php index 2d61b882..db684051 100644 --- a/PHPCI/Controller/ProjectController.php +++ b/PHPCI/Controller/ProjectController.php @@ -173,7 +173,7 @@ class ProjectController extends \PHPCI\Controller $values = $form->getValues(); if ($values['type'] == "gitlab") { - preg_match('`^(.*)@(.*):(.*)/(.*)\.git`',$values['reference'],$matches); + preg_match('`^(.*)@(.*):(.*)/(.*)\.git`', $values['reference'], $matches); $info = array(); $info["user"] = $matches[1]; $info["domain"] = $matches[2]; @@ -238,7 +238,8 @@ class ProjectController extends \PHPCI\Controller $values['key'] = $values['git_key']; if ($values['type'] == "gitlab") { $accessInfo = $project->getAccessInformation(); - $values['reference'] = $accessInfo["user"].'@'.$accessInfo["domain"].':' . $project->getReference().".git"; + $reference = $accessInfo["user"].'@'.$accessInfo["domain"].':' . $project->getReference().".git"; + $values['reference'] = $reference; } } @@ -259,12 +260,12 @@ class ProjectController extends \PHPCI\Controller $values['git_key'] = $values['key']; if ($values['type'] == "gitlab") { - preg_match('`^(.*)@(.*):(.*)/(.*)\.git`',$values['reference'],$matches); + preg_match('`^(.*)@(.*):(.*)/(.*)\.git`', $values['reference'], $matches); $info = array(); $info["user"] = $matches[1]; $info["domain"] = $matches[2]; $values['access_information'] = serialize($info); - $values['reference'] = $matches[3]."/".$matches[4]; + $values['reference'] = $matches[3] . "/" . $matches[4]; } $project->setValues($values); @@ -314,44 +315,9 @@ class ProjectController extends \PHPCI\Controller $form->addField($field); } - $referenceValidator = function ($val) use ($values) { - $type = $values['type']; - - switch($type) { - case 'hg': - if (!preg_match('/^(https?):\/\//', $val)) { - throw new \Exception('Mercurial repository URL must be start with http:// or https://.'); - } - break; - case 'remote': - if (!preg_match('/^(git|https?):\/\//', $val)) { - throw new \Exception('Repository URL must be start with git://, http:// or https://.'); - } - break; - case 'local': - if (!is_dir($val)) { - throw new \Exception('The path you specified does not exist.'); - } - break; - case 'gitlab': - if (!preg_match('`^(.*)@(.*):(.*)/(.*)\.git`', $val)) { - throw new \Exception('GitLab Repository name must be in the format "user@domain.tld:owner/repo.git".'); - } - break; - case 'github': - case 'bitbucket': - if (!preg_match('/^[a-zA-Z0-9_\-]+\/[a-zA-Z0-9_\-\.]+$/', $val)) { - throw new \Exception('Repository name must be in the format "owner/repo".'); - } - break; - } - - return true; - }; - $field = new Form\Element\Text('reference'); $field->setRequired(true); - $field->setValidator($referenceValidator); + $field->setValidator($this->getReferenceValidator($values)); $field->setLabel('Repository Name / URL (Remote) or Path (Local)'); $field->setClass('form-control'); $field->setContainerClass('form-group'); @@ -401,4 +367,42 @@ class ProjectController extends \PHPCI\Controller return $rtn; } + + protected function getReferenceValidator($values) + { + return function ($val) use ($values) { + $type = $values['type']; + + $validators = array( + 'hg' => array( + 'regex' => '/^(https?):\/\//', + 'message' => 'Mercurial repository URL must be start with http:// or https://' + ), + 'remote' => array( + 'regex' => '/^(git|https?):\/\//', + 'message' => 'Repository URL must be start with git://, http:// or https://' + ), + 'gitlab' => array( + 'regex' => '`^(.*)@(.*):(.*)/(.*)\.git`', + 'message' => 'GitLab Repository name must be in the format "user@domain.tld:owner/repo.git"' + ), + 'github' => array( + 'regex' => '/^[a-zA-Z0-9_\-]+\/[a-zA-Z0-9_\-\.]+$/', + 'message' => 'Repository name must be in the format "owner/repo"' + ), + 'bitbucket' => array( + 'regex' => '/^[a-zA-Z0-9_\-]+\/[a-zA-Z0-9_\-\.]+$/', + 'message' => 'Repository name must be in the format "owner/repo"' + ), + ); + + if (in_array($type, $validators) && !preg_match($validators[$type]['regex'], $val)) { + throw new \Exception($validators[$type]['message']); + } elseif ($type == 'local' && !is_dir($val)) { + throw new \Exception('The path you specified does not exist.'); + } + + return true; + }; + } } diff --git a/PHPCI/Controller/UserController.php b/PHPCI/Controller/UserController.php index e0cbd5e5..ad41aff6 100644 --- a/PHPCI/Controller/UserController.php +++ b/PHPCI/Controller/UserController.php @@ -10,8 +10,9 @@ namespace PHPCI\Controller; use b8; -use PHPCI\Model\User; use b8\Form; +use PHPCI\Controller; +use PHPCI\Model\User; /** * User Controller - Allows an administrator to view, add, edit and delete users. @@ -19,7 +20,7 @@ use b8\Form; * @package PHPCI * @subpackage Web */ -class UserController extends \PHPCI\Controller +class UserController extends Controller { /** * @var \PHPCI\Store\UserStore diff --git a/PHPCI/Model/Base/BuildBase.php b/PHPCI/Model/Base/BuildBase.php index e620452f..52a549d5 100644 --- a/PHPCI/Model/Base/BuildBase.php +++ b/PHPCI/Model/Base/BuildBase.php @@ -7,6 +7,7 @@ namespace PHPCI\Model\Base; use b8\Model; +use b8\Store\Factory; /** * Build Base Model @@ -43,12 +44,13 @@ class BuildBase extends Model 'finished' => null, 'plugins' => null, 'committer_email' => null, - ); + ); /** * @var array */ protected $getters = array( + // Direct property getters: 'id' => 'getId', 'project_id' => 'getProjectId', 'commit_id' => 'getCommitId', @@ -60,13 +62,16 @@ class BuildBase extends Model 'finished' => 'getFinished', 'plugins' => 'getPlugins', 'committer_email' => 'getCommitterEmail', + + // Foreign key getters: 'Project' => 'getProject', - ); + ); /** * @var array */ protected $setters = array( + // Direct property setters: 'id' => 'setId', 'project_id' => 'setProjectId', 'commit_id' => 'setCommitId', @@ -78,8 +83,10 @@ class BuildBase extends Model 'finished' => 'setFinished', 'plugins' => 'setPlugins', 'committer_email' => 'setCommitterEmail', + + // Foreign key setters: 'Project' => 'setProject', - ); + ); /** * @var array @@ -87,69 +94,63 @@ class BuildBase extends Model public $columns = array( 'id' => array( 'type' => 'int', - 'length' => '11', + 'length' => 11, 'primary_key' => true, 'auto_increment' => true, 'default' => null, - ), + ), 'project_id' => array( 'type' => 'int', - 'length' => '11', + 'length' => 11, 'default' => null, - ), + ), 'commit_id' => array( 'type' => 'varchar', - 'length' => '50', + 'length' => 50, 'nullable' => true, 'default' => null, - ), + ), 'status' => array( 'type' => 'tinyint', - 'length' => '4', - 'default' => '0', - ), + 'length' => 4, + ), 'log' => array( 'type' => 'longtext', - 'length' => '', 'nullable' => true, 'default' => null, - ), + ), 'branch' => array( 'type' => 'varchar', - 'length' => '50', + 'length' => 50, 'default' => 'master', - ), + ), 'created' => array( 'type' => 'datetime', - 'length' => '', 'nullable' => true, 'default' => null, - ), + ), 'started' => array( 'type' => 'datetime', - 'length' => '', 'nullable' => true, 'default' => null, - ), + ), 'finished' => array( 'type' => 'datetime', - 'length' => '', 'nullable' => true, 'default' => null, - ), + ), 'plugins' => array( 'type' => 'text', - 'length' => '', 'nullable' => true, 'default' => null, - ), + ), 'committer_email' => array( 'type' => 'varchar', - 'length' => '512', + 'length' => 512, 'nullable' => true, 'default' => null, - ), - ); + ), + ); /** * @var array @@ -158,7 +159,7 @@ class BuildBase extends Model 'PRIMARY' => array('unique' => true, 'columns' => 'id'), 'project_id' => array('columns' => 'project_id'), 'idx_status' => array('columns' => 'status'), - ); + ); /** * @var array @@ -171,8 +172,7 @@ class BuildBase extends Model 'table' => 'project', 'col' => 'id' ), - ); - + ); /** * Get the value of Id / id. @@ -183,7 +183,6 @@ class BuildBase extends Model { $rtn = $this->data['id']; - return $rtn; } @@ -196,7 +195,6 @@ class BuildBase extends Model { $rtn = $this->data['project_id']; - return $rtn; } @@ -209,7 +207,6 @@ class BuildBase extends Model { $rtn = $this->data['commit_id']; - return $rtn; } @@ -222,7 +219,6 @@ class BuildBase extends Model { $rtn = $this->data['status']; - return $rtn; } @@ -235,7 +231,6 @@ class BuildBase extends Model { $rtn = $this->data['log']; - return $rtn; } @@ -248,7 +243,6 @@ class BuildBase extends Model { $rtn = $this->data['branch']; - return $rtn; } @@ -261,11 +255,9 @@ class BuildBase extends Model { $rtn = $this->data['created']; - if (!empty($rtn)) { $rtn = new \DateTime($rtn); } - return $rtn; } @@ -279,11 +271,9 @@ class BuildBase extends Model { $rtn = $this->data['started']; - if (!empty($rtn)) { $rtn = new \DateTime($rtn); } - return $rtn; } @@ -297,11 +287,9 @@ class BuildBase extends Model { $rtn = $this->data['finished']; - if (!empty($rtn)) { $rtn = new \DateTime($rtn); } - return $rtn; } @@ -315,7 +303,6 @@ class BuildBase extends Model { $rtn = $this->data['plugins']; - return $rtn; } @@ -328,7 +315,6 @@ class BuildBase extends Model { $rtn = $this->data['committer_email']; - return $rtn; } @@ -342,6 +328,7 @@ class BuildBase extends Model { $this->_validateNotNull('Id', $value); $this->_validateInt('Id', $value); + if ($this->data['id'] === $value) { return; } @@ -361,6 +348,7 @@ class BuildBase extends Model { $this->_validateNotNull('ProjectId', $value); $this->_validateInt('ProjectId', $value); + if ($this->data['project_id'] === $value) { return; } @@ -377,8 +365,8 @@ class BuildBase extends Model */ public function setCommitId($value) { - $this->_validateString('CommitId', $value); + if ($this->data['commit_id'] === $value) { return; } @@ -398,6 +386,7 @@ class BuildBase extends Model { $this->_validateNotNull('Status', $value); $this->_validateInt('Status', $value); + if ($this->data['status'] === $value) { return; } @@ -414,8 +403,8 @@ class BuildBase extends Model */ public function setLog($value) { - $this->_validateString('Log', $value); + if ($this->data['log'] === $value) { return; } @@ -435,6 +424,7 @@ class BuildBase extends Model { $this->_validateNotNull('Branch', $value); $this->_validateString('Branch', $value); + if ($this->data['branch'] === $value) { return; } @@ -451,8 +441,8 @@ class BuildBase extends Model */ public function setCreated($value) { - $this->_validateDate('Created', $value); + if ($this->data['created'] === $value) { return; } @@ -469,8 +459,8 @@ class BuildBase extends Model */ public function setStarted($value) { - $this->_validateDate('Started', $value); + if ($this->data['started'] === $value) { return; } @@ -487,8 +477,8 @@ class BuildBase extends Model */ public function setFinished($value) { - $this->_validateDate('Finished', $value); + if ($this->data['finished'] === $value) { return; } @@ -505,8 +495,8 @@ class BuildBase extends Model */ public function setPlugins($value) { - $this->_validateString('Plugins', $value); + if ($this->data['plugins'] === $value) { return; } @@ -523,8 +513,8 @@ class BuildBase extends Model */ public function setCommitterEmail($value) { - $this->_validateString('CommitterEmail', $value); + if ($this->data['committer_email'] === $value) { return; } @@ -553,7 +543,7 @@ class BuildBase extends Model $rtn = $this->cache->get($cacheKey, null); if (empty($rtn)) { - $rtn = \b8\Store\Factory::getStore('Project')->getById($key); + $rtn = Factory::getStore('Project')->getById($key); $this->cache->set($cacheKey, $rtn); } @@ -600,6 +590,6 @@ class BuildBase extends Model */ public function getBuildBuildMetas() { - return \b8\Store\Factory::getStore('BuildMeta')->getByBuildId($this->getId()); + return Factory::getStore('BuildMeta')->getByBuildId($this->getId()); } } diff --git a/PHPCI/Model/Base/BuildMetaBase.php b/PHPCI/Model/Base/BuildMetaBase.php index 939c66fd..9ef0f457 100644 --- a/PHPCI/Model/Base/BuildMetaBase.php +++ b/PHPCI/Model/Base/BuildMetaBase.php @@ -7,6 +7,7 @@ namespace PHPCI\Model\Base; use b8\Model; +use b8\Store\Factory; /** * BuildMeta Base Model @@ -37,31 +38,37 @@ class BuildMetaBase extends Model 'build_id' => null, 'meta_key' => null, 'meta_value' => null, - ); + ); /** * @var array */ protected $getters = array( + // Direct property getters: 'id' => 'getId', 'project_id' => 'getProjectId', 'build_id' => 'getBuildId', 'meta_key' => 'getMetaKey', 'meta_value' => 'getMetaValue', + + // Foreign key getters: 'Build' => 'getBuild', - ); + ); /** * @var array */ protected $setters = array( + // Direct property setters: 'id' => 'setId', 'project_id' => 'setProjectId', 'build_id' => 'setBuildId', 'meta_key' => 'setMetaKey', 'meta_value' => 'setMetaValue', + + // Foreign key setters: 'Build' => 'setBuild', - ); + ); /** * @var array @@ -69,34 +76,32 @@ class BuildMetaBase extends Model public $columns = array( 'id' => array( 'type' => 'int', - 'length' => '10', + 'length' => 10, 'primary_key' => true, 'auto_increment' => true, 'default' => null, - ), + ), 'project_id' => array( 'type' => 'int', - 'length' => '11', + 'length' => 11, 'default' => null, - ), + ), 'build_id' => array( 'type' => 'int', - 'length' => '11', + 'length' => 11, 'nullable' => true, 'default' => null, - ), + ), 'meta_key' => array( 'type' => 'varchar', - 'length' => '255', - 'default' => '', - ), + 'length' => 255, + ), 'meta_value' => array( 'type' => 'text', - 'length' => '', 'nullable' => true, 'default' => null, - ), - ); + ), + ); /** * @var array @@ -104,7 +109,7 @@ class BuildMetaBase extends Model public $indexes = array( 'PRIMARY' => array('unique' => true, 'columns' => 'id'), 'idx_meta_id' => array('unique' => true, 'columns' => 'build_id, meta_key'), - ); + ); /** * @var array @@ -117,8 +122,7 @@ class BuildMetaBase extends Model 'table' => 'build', 'col' => 'id' ), - ); - + ); /** * Get the value of Id / id. @@ -129,7 +133,6 @@ class BuildMetaBase extends Model { $rtn = $this->data['id']; - return $rtn; } @@ -142,7 +145,6 @@ class BuildMetaBase extends Model { $rtn = $this->data['project_id']; - return $rtn; } @@ -155,7 +157,6 @@ class BuildMetaBase extends Model { $rtn = $this->data['build_id']; - return $rtn; } @@ -168,7 +169,6 @@ class BuildMetaBase extends Model { $rtn = $this->data['meta_key']; - return $rtn; } @@ -181,7 +181,6 @@ class BuildMetaBase extends Model { $rtn = $this->data['meta_value']; - return $rtn; } @@ -195,6 +194,7 @@ class BuildMetaBase extends Model { $this->_validateNotNull('Id', $value); $this->_validateInt('Id', $value); + if ($this->data['id'] === $value) { return; } @@ -214,6 +214,7 @@ class BuildMetaBase extends Model { $this->_validateNotNull('ProjectId', $value); $this->_validateInt('ProjectId', $value); + if ($this->data['project_id'] === $value) { return; } @@ -230,8 +231,8 @@ class BuildMetaBase extends Model */ public function setBuildId($value) { - $this->_validateInt('BuildId', $value); + if ($this->data['build_id'] === $value) { return; } @@ -251,6 +252,7 @@ class BuildMetaBase extends Model { $this->_validateNotNull('MetaKey', $value); $this->_validateString('MetaKey', $value); + if ($this->data['meta_key'] === $value) { return; } @@ -267,8 +269,8 @@ class BuildMetaBase extends Model */ public function setMetaValue($value) { - $this->_validateString('MetaValue', $value); + if ($this->data['meta_value'] === $value) { return; } @@ -297,7 +299,7 @@ class BuildMetaBase extends Model $rtn = $this->cache->get($cacheKey, null); if (empty($rtn)) { - $rtn = \b8\Store\Factory::getStore('Build')->getById($key); + $rtn = Factory::getStore('Build')->getById($key); $this->cache->set($cacheKey, $rtn); } diff --git a/PHPCI/Model/Base/ProjectBase.php b/PHPCI/Model/Base/ProjectBase.php index 6fc1a422..f23e1d7f 100644 --- a/PHPCI/Model/Base/ProjectBase.php +++ b/PHPCI/Model/Base/ProjectBase.php @@ -7,6 +7,7 @@ namespace PHPCI\Model\Base; use b8\Model; +use b8\Store\Factory; /** * Project Base Model @@ -39,12 +40,13 @@ class ProjectBase extends Model 'type' => null, 'token' => null, 'access_information' => null, - ); + ); /** * @var array */ protected $getters = array( + // Direct property getters: 'id' => 'getId', 'title' => 'getTitle', 'reference' => 'getReference', @@ -52,12 +54,15 @@ class ProjectBase extends Model 'type' => 'getType', 'token' => 'getToken', 'access_information' => 'getAccessInformation', - ); + + // Foreign key getters: + ); /** * @var array */ protected $setters = array( + // Direct property setters: 'id' => 'setId', 'title' => 'setTitle', 'reference' => 'setReference', @@ -65,7 +70,9 @@ class ProjectBase extends Model 'type' => 'setType', 'token' => 'setToken', 'access_information' => 'setAccessInformation', - ); + + // Foreign key setters: + ); /** * @var array @@ -73,59 +80,56 @@ class ProjectBase extends Model public $columns = array( 'id' => array( 'type' => 'int', - 'length' => '11', + 'length' => 11, 'primary_key' => true, 'auto_increment' => true, 'default' => null, - ), + ), 'title' => array( 'type' => 'varchar', - 'length' => '250', - 'default' => '', - ), + 'length' => 250, + ), 'reference' => array( 'type' => 'varchar', - 'length' => '250', - 'default' => '', - ), + 'length' => 250, + ), 'git_key' => array( 'type' => 'text', - 'length' => '', 'nullable' => true, 'default' => null, - ), + ), 'type' => array( 'type' => 'varchar', - 'length' => '50', - 'default' => '1', - ), + 'length' => 50, + 'default' => 1, + ), 'token' => array( 'type' => 'varchar', - 'length' => '50', + 'length' => 50, 'nullable' => true, 'default' => null, - ), + ), 'access_information' => array( 'type' => 'varchar', - 'length' => '250', + 'length' => 250, 'nullable' => true, 'default' => null, - ), - ); + ), + ); /** * @var array */ public $indexes = array( 'PRIMARY' => array('unique' => true, 'columns' => 'id'), - ); + 'idx_project_title' => array('columns' => 'title'), + ); /** * @var array */ public $foreignKeys = array( - ); - + ); /** * Get the value of Id / id. @@ -136,7 +140,6 @@ class ProjectBase extends Model { $rtn = $this->data['id']; - return $rtn; } @@ -149,7 +152,6 @@ class ProjectBase extends Model { $rtn = $this->data['title']; - return $rtn; } @@ -162,7 +164,6 @@ class ProjectBase extends Model { $rtn = $this->data['reference']; - return $rtn; } @@ -175,7 +176,6 @@ class ProjectBase extends Model { $rtn = $this->data['git_key']; - return $rtn; } @@ -188,7 +188,6 @@ class ProjectBase extends Model { $rtn = $this->data['type']; - return $rtn; } @@ -201,7 +200,6 @@ class ProjectBase extends Model { $rtn = $this->data['token']; - return $rtn; } @@ -214,7 +212,6 @@ class ProjectBase extends Model { $rtn = $this->data['access_information']; - return $rtn; } @@ -228,6 +225,7 @@ class ProjectBase extends Model { $this->_validateNotNull('Id', $value); $this->_validateInt('Id', $value); + if ($this->data['id'] === $value) { return; } @@ -247,6 +245,7 @@ class ProjectBase extends Model { $this->_validateNotNull('Title', $value); $this->_validateString('Title', $value); + if ($this->data['title'] === $value) { return; } @@ -266,6 +265,7 @@ class ProjectBase extends Model { $this->_validateNotNull('Reference', $value); $this->_validateString('Reference', $value); + if ($this->data['reference'] === $value) { return; } @@ -282,8 +282,8 @@ class ProjectBase extends Model */ public function setGitKey($value) { - $this->_validateString('GitKey', $value); + if ($this->data['git_key'] === $value) { return; } @@ -303,6 +303,7 @@ class ProjectBase extends Model { $this->_validateNotNull('Type', $value); $this->_validateString('Type', $value); + if ($this->data['type'] === $value) { return; } @@ -319,8 +320,8 @@ class ProjectBase extends Model */ public function setToken($value) { - $this->_validateString('Token', $value); + if ($this->data['token'] === $value) { return; } @@ -337,8 +338,8 @@ class ProjectBase extends Model */ public function setAccessInformation($value) { - $this->_validateString('AccessInformation', $value); + if ($this->data['access_information'] === $value) { return; } @@ -357,6 +358,6 @@ class ProjectBase extends Model */ public function getProjectBuilds() { - return \b8\Store\Factory::getStore('Build')->getByProjectId($this->getId()); + return Factory::getStore('Build')->getByProjectId($this->getId()); } } diff --git a/PHPCI/Model/Base/UserBase.php b/PHPCI/Model/Base/UserBase.php index 8fad4ea1..e8035660 100644 --- a/PHPCI/Model/Base/UserBase.php +++ b/PHPCI/Model/Base/UserBase.php @@ -7,6 +7,7 @@ namespace PHPCI\Model\Base; use b8\Model; +use b8\Store\Factory; /** * User Base Model @@ -37,29 +38,35 @@ class UserBase extends Model 'hash' => null, 'is_admin' => null, 'name' => null, - ); + ); /** * @var array */ protected $getters = array( + // Direct property getters: 'id' => 'getId', 'email' => 'getEmail', 'hash' => 'getHash', 'is_admin' => 'getIsAdmin', 'name' => 'getName', - ); + + // Foreign key getters: + ); /** * @var array */ protected $setters = array( + // Direct property setters: 'id' => 'setId', 'email' => 'setEmail', 'hash' => 'setHash', 'is_admin' => 'setIsAdmin', 'name' => 'setName', - ); + + // Foreign key setters: + ); /** * @var array @@ -67,33 +74,30 @@ class UserBase extends Model public $columns = array( 'id' => array( 'type' => 'int', - 'length' => '11', + 'length' => 11, 'primary_key' => true, 'auto_increment' => true, 'default' => null, - ), + ), 'email' => array( 'type' => 'varchar', - 'length' => '250', - 'default' => '', - ), + 'length' => 250, + ), 'hash' => array( 'type' => 'varchar', - 'length' => '250', - 'default' => '', - ), + 'length' => 250, + ), 'is_admin' => array( 'type' => 'tinyint', - 'length' => '1', - 'default' => '0', - ), + 'length' => 1, + ), 'name' => array( 'type' => 'varchar', - 'length' => '250', + 'length' => 250, 'nullable' => true, 'default' => null, - ), - ); + ), + ); /** * @var array @@ -101,14 +105,13 @@ class UserBase extends Model public $indexes = array( 'PRIMARY' => array('unique' => true, 'columns' => 'id'), 'idx_email' => array('unique' => true, 'columns' => 'email'), - ); + ); /** * @var array */ public $foreignKeys = array( - ); - + ); /** * Get the value of Id / id. @@ -119,7 +122,6 @@ class UserBase extends Model { $rtn = $this->data['id']; - return $rtn; } @@ -132,7 +134,6 @@ class UserBase extends Model { $rtn = $this->data['email']; - return $rtn; } @@ -145,7 +146,6 @@ class UserBase extends Model { $rtn = $this->data['hash']; - return $rtn; } @@ -158,7 +158,6 @@ class UserBase extends Model { $rtn = $this->data['is_admin']; - return $rtn; } @@ -171,7 +170,6 @@ class UserBase extends Model { $rtn = $this->data['name']; - return $rtn; } @@ -185,6 +183,7 @@ class UserBase extends Model { $this->_validateNotNull('Id', $value); $this->_validateInt('Id', $value); + if ($this->data['id'] === $value) { return; } @@ -204,6 +203,7 @@ class UserBase extends Model { $this->_validateNotNull('Email', $value); $this->_validateString('Email', $value); + if ($this->data['email'] === $value) { return; } @@ -223,6 +223,7 @@ class UserBase extends Model { $this->_validateNotNull('Hash', $value); $this->_validateString('Hash', $value); + if ($this->data['hash'] === $value) { return; } @@ -242,6 +243,7 @@ class UserBase extends Model { $this->_validateNotNull('IsAdmin', $value); $this->_validateInt('IsAdmin', $value); + if ($this->data['is_admin'] === $value) { return; } @@ -258,8 +260,8 @@ class UserBase extends Model */ public function setName($value) { - $this->_validateString('Name', $value); + if ($this->data['name'] === $value) { return; } diff --git a/PHPCI/Model/Build.php b/PHPCI/Model/Build.php index e60ff64e..bc814560 100644 --- a/PHPCI/Model/Build.php +++ b/PHPCI/Model/Build.php @@ -9,8 +9,8 @@ namespace PHPCI\Model; +use b8\Store\Factory; use PHPCI\Model\Base\BuildBase; -use PHPCI\Builder; /** * Build Model @@ -21,6 +21,11 @@ use PHPCI\Builder; */ class Build extends BuildBase { + const STATUS_NEW = 0; + const STATUS_RUNNING = 1; + const STATUS_SUCCESS = 2; + const STATUS_FAILED = 3; + /** * Get link to commit from another source (i.e. Github) */ @@ -46,9 +51,19 @@ class Build extends BuildBase } /** - * Create a working copy by cloning, copying, or similar. - */ - public function createWorkingCopy(Builder $builder, $buildPath) + * Store build metadata + */ + public function storeMeta($key, $value) { + $value = json_encode($value); + Factory::getStore('Build')->setMeta($this->getProjectId(), $this->getId(), $key, $value); + } + + /** + * Is this build successful? + */ + public function isSuccessful() + { + return ($this->getStatus() === self::STATUS_SUCCESS); } } diff --git a/PHPCI/Model/Build/LocalBuild.php b/PHPCI/Model/Build/LocalBuild.php index 07698d42..6804f437 100644 --- a/PHPCI/Model/Build/LocalBuild.php +++ b/PHPCI/Model/Build/LocalBuild.php @@ -29,44 +29,68 @@ class LocalBuild extends Build $reference = $this->getProject()->getReference(); $reference = substr($reference, -1) == '/' ? substr($reference, 0, -1) : $reference; $buildPath = substr($buildPath, 0, -1); - $yamlParser = new YamlParser(); - - if(is_file($reference.'/config')) { - //We're probably looing at a bare repository. We'll open the config and check - $gitConfig = parse_ini_file($reference.'/config',TRUE); - if($gitConfig["core"]["bare"]) { - // Looks like we're right. We need to extract the archive! - $guid = uniqid(); - $builder->executeCommand('mkdir "/tmp/%s" && git --git-dir="%s" archive master | tar -x -C "/tmp/%s"', $guid, $reference, $guid); - $reference = '/tmp/'.$guid; - } + + // If there's a /config file in the reference directory, it is probably a bare repository + // which we'll extract into our build path directly. + if(is_file($reference.'/config') && $this->handleBareRepository($builder, $reference, $buildPath) === true) { + return true; } - if (!is_file($reference . '/phpci.yml')) { - $builder->logFailure('Project does not contain a phpci.yml file.'); + $buildSettings = $this->handleConfig($builder, $reference); + + if ($buildSettings === false) { return false; } - $yamlFile = file_get_contents($reference . '/phpci.yml'); - $builder->setConfigArray($yamlParser->parse($yamlFile)); - - $buildSettings = $builder->getConfig('build_settings'); - if (isset($buildSettings['prefer_symlink']) && $buildSettings['prefer_symlink'] === true) { - if (is_link($buildPath) && is_file($buildPath)) { - unlink($buildPath); - } - - $builder->log(sprintf('Symlinking: %s to %s', $reference, $buildPath)); - - if (!symlink($reference, $buildPath)) { - $builder->logFailure('Failed to symlink.'); - return false; - } + return $this->handleSymlink($builder, $reference, $buildPath); } else { $builder->executeCommand('cp -Rf "%s" "%s/"', $reference, $buildPath); } return true; } + + protected function handleBareRepository(Builder $builder, $reference, $buildPath) + { + $gitConfig = parse_ini_file($reference.'/config', true); + + // If it is indeed a bare repository, then extract it into our build path: + if($gitConfig['core']['bare']) { + $builder->executeCommand('git --git-dir="%s" archive master | tar -x -C "%s"', $reference, $buildPath); + return true; + } + + return false; + } + + protected function handleSymlink(Builder $builder, $reference, $buildPath) + { + if (is_link($buildPath) && is_file($buildPath)) { + unlink($buildPath); + } + + $builder->log(sprintf('Symlinking: %s to %s', $reference, $buildPath)); + + if (!symlink($reference, $buildPath)) { + $builder->logFailure('Failed to symlink.'); + return false; + } + + return true; + } + + protected function handleConfig(Builder $builder, $reference) + { + /** @todo Add support for database-based yml definition */ + if (!is_file($reference . '/phpci.yml')) { + $builder->logFailure('Project does not contain a phpci.yml file.'); + return false; + } + + $yamlParser = new YamlParser(); + $yamlFile = file_get_contents($reference . '/phpci.yml'); + $builder->setConfigArray($yamlParser->parse($yamlFile)); + return $builder->getConfig('build_settings'); + } } diff --git a/PHPCI/Model/Build/MercurialBuild.php b/PHPCI/Model/Build/MercurialBuild.php index de95c06b..dbfcf4e2 100644 --- a/PHPCI/Model/Build/MercurialBuild.php +++ b/PHPCI/Model/Build/MercurialBuild.php @@ -52,8 +52,8 @@ class MercurialBuild extends Build /** * Use an mercurial clone. */ - protected function cloneByHttp(Builder $builder, $to) + protected function cloneByHttp(Builder $builder, $cloneTo) { - return $builder->executeCommand('hg clone %s "%s" -r %s', $this->getCloneUrl(), $to, $this->getBranch()); + return $builder->executeCommand('hg clone %s "%s" -r %s', $this->getCloneUrl(), $cloneTo, $this->getBranch()); } } diff --git a/PHPCI/Model/Build/RemoteGitBuild.php b/PHPCI/Model/Build/RemoteGitBuild.php index 490b92ef..c4b03d2c 100644 --- a/PHPCI/Model/Build/RemoteGitBuild.php +++ b/PHPCI/Model/Build/RemoteGitBuild.php @@ -63,21 +63,21 @@ class RemoteGitBuild extends Build /** * Use an HTTP-based git clone. */ - protected function cloneByHttp(Builder $builder, $to) + protected function cloneByHttp(Builder $builder, $cloneTo) { - return $builder->executeCommand('git clone -b %s %s "%s"', $this->getBranch(), $this->getCloneUrl(), $to); + return $builder->executeCommand('git clone -b %s %s "%s"', $this->getBranch(), $this->getCloneUrl(), $cloneTo); } /** * Use an SSH-based git clone. */ - protected function cloneBySsh(Builder $builder, $to) + protected function cloneBySsh(Builder $builder, $cloneTo) { // Copy the project's keyfile to disk: - $keyPath = realpath($to); + $keyPath = realpath($cloneTo); if ($keyPath === false) { - $keyPath = dirname($to); + $keyPath = dirname($cloneTo); } $keyFile = $keyPath . '.key'; @@ -87,7 +87,7 @@ class RemoteGitBuild extends Build // Use the key file to do an SSH clone: $cmd = 'eval `ssh-agent -s` && ssh-add "%s" && git clone -b %s %s "%s" && ssh-agent -k'; - $success = $builder->executeCommand($cmd, $keyFile, $this->getBranch(), $this->getCloneUrl(), $to); + $success = $builder->executeCommand($cmd, $keyFile, $this->getBranch(), $this->getCloneUrl(), $cloneTo); // Remove the key file: unlink($keyFile); diff --git a/PHPCI/Plugin.php b/PHPCI/Plugin.php index 5aa06e9e..a924b39a 100644 --- a/PHPCI/Plugin.php +++ b/PHPCI/Plugin.php @@ -9,12 +9,15 @@ namespace PHPCI; +use PHPCI\Builder; +use PHPCI\Model\Build; + /** * PHPCI Plugin Interface - Used by all build plugins. * @author Dan Cryer%s", $logText) ); - } - else { + } else { $sendFailures = $this->sendSeparateEmails( $addresses, sprintf($subjectTemplate, $projectName, "Failing Build"), @@ -93,14 +83,9 @@ class Email implements \PHPCI\Plugin } // This is a success if we've not failed to send anything. - $this->phpci->log(sprintf( - "%d emails sent", - (count($addresses) - count($sendFailures))) - ); - $this->phpci->log(sprintf( - "%d emails failed to send", - count($sendFailures)) - ); + $this->phpci->log(sprintf("%d emails sent", (count($addresses) - count($sendFailures)))); + $this->phpci->log(sprintf("%d emails failed to send", count($sendFailures))); + return (count($sendFailures) == 0); } @@ -126,9 +111,9 @@ class Email implements \PHPCI\Plugin public function sendSeparateEmails(array $toAddresses, $subject, $body) { $failures = array(); - foreach($toAddresses as $address) { + foreach ($toAddresses as $address) { $newFailures = $this->sendEmail($address, $subject, $body); - foreach($newFailures as $failure) { + foreach ($newFailures as $failure) { $failures[] = $failure; } } @@ -151,13 +136,11 @@ class Email implements \PHPCI\Plugin protected function getMailConfig($configName) { - if (isset($this->emailConfig[$configName]) - && $this->emailConfig[$configName] != "") - { + if (isset($this->emailConfig[$configName]) && $this->emailConfig[$configName] != "") { return $this->emailConfig[$configName]; - } - // Check defaults - else { + } else { + // Check defaults + switch($configName) { case 'smtp_address': return "localhost"; @@ -178,7 +161,7 @@ class Email implements \PHPCI\Plugin protected function getEmailAddresses() { $addresses = array(); - $committer = $this->phpci->getBuild()->getCommitterEmail(); + $committer = $this->build->getCommitterEmail(); if (isset($this->options['committer']) && !empty($committer)) { $addresses[] = $committer; @@ -196,4 +179,4 @@ class Email implements \PHPCI\Plugin } return $addresses; } -} \ No newline at end of file +} diff --git a/PHPCI/Plugin/Env.php b/PHPCI/Plugin/Env.php index e09d3dbf..09ffbb5a 100644 --- a/PHPCI/Plugin/Env.php +++ b/PHPCI/Plugin/Env.php @@ -9,6 +9,9 @@ namespace PHPCI\Plugin; +use PHPCI\Builder; +use PHPCI\Model\Build; + /** * Environment variable plugin * @author Steve Kamerman
Important! You need to run composer to install dependencies before running the installer.
++ Important! + You need to run composer to install dependencies before running the installer. +
-Important! ./PHPCI/config.yml needs to be writeable to continue.
++ Important! + ./PHPCI/config.yml needs to be writeable to continue. +
@@ -391,30 +401,3 @@ switch ($installStage) {