Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Better handling of functions returning false #320

Merged
merged 1 commit into from
Dec 14, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
47 changes: 40 additions & 7 deletions src/Configuration/Loader.php
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
namespace Churn\Configuration;

use InvalidArgumentException;
use Symfony\Component\Yaml\Exception\ParseException;
use Symfony\Component\Yaml\Yaml;

/**
Expand All @@ -15,26 +16,58 @@ class Loader
/**
* @param string $confPath Path of the configuration file to load.
* @param boolean $isDefaultValue Indicates whether $confPath contains the default value.
* @throws InvalidArgumentException If the configuration file cannot be read.
* @throws InvalidArgumentException If the configuration file cannot be loaded.
*/
public static function fromPath(string $confPath, bool $isDefaultValue): Config
{
$originalConfPath = $confPath;
$confPath = self::normalizePath($confPath);

if (false !== $confPath && \is_readable($confPath)) {
$yaml = self::loadYaml($confPath);

return Config::create($yaml, $confPath);
}

if ($isDefaultValue) {
return Config::createFromDefaultValues();
}

throw new InvalidArgumentException('The configuration file can not be read at ' . $originalConfPath);
}

/**
* @param string $confPath Path to normalize.
* @return string|false
*/
private static function normalizePath(string $confPath)
{
if (\is_dir($confPath)) {
$confPath = \rtrim($confPath, '/\\') . '/churn.yml';
}

if (\is_readable($confPath)) {
$content = (string) \file_get_contents($confPath);
return \realpath($confPath);
}

/**
* @param string $confPath Path of the yaml file to load.
* @return array<mixed>
* @throws InvalidArgumentException If the configuration file is invalid.
*/
private static function loadYaml(string $confPath): array
{
$content = (string) \file_get_contents($confPath);

return Config::create(Yaml::parse($content) ?? [], \realpath($confPath));
try {
$yaml = Yaml::parse($content) ?? [];
} catch (ParseException $e) {
$yaml = null;
}

if ($isDefaultValue) {
return Config::createFromDefaultValues();
if (!\is_array($yaml)) {
throw new InvalidArgumentException('The content of the configuration file is invalid');
}

throw new InvalidArgumentException('The configuration file can not be read at ' . $originalConfPath);
return $yaml;
}
}
16 changes: 15 additions & 1 deletion src/Process/ConcreteProcessFactory.php
Original file line number Diff line number Diff line change
Expand Up @@ -68,7 +68,7 @@ private function getChangesCountProcessBuilder(string $vcs, string $commitsSince
*/
private function getCyclomaticComplexityProcessBuilder(): Closure
{
$phpExecutable = (string)(new PhpExecutableFinder())->find();
$phpExecutable = $this->getPhpExecutable();
$command = \array_merge([$phpExecutable], $this->getAssessorArguments());

return static function (File $file) use ($command): CyclomaticComplexityInterface {
Expand All @@ -79,6 +79,20 @@ private function getCyclomaticComplexityProcessBuilder(): Closure
};
}

/**
* @return string The PHP executable.
*/
private function getPhpExecutable(): string
{
$php = 'php';
$executableFound = (new PhpExecutableFinder())->find();
if (false !== $executableFound) {
$php = $executableFound;
}

return $php;
}

/** @return array<string> */
private function getAssessorArguments(): array
{
Expand Down
9 changes: 8 additions & 1 deletion tests/Unit/Configuration/LoaderTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,13 @@ public function it_returns_the_default_values_if_there_is_no_default_file()
public function it_throws_if_the_chosen_file_is_missing()
{
$this->expectException(InvalidArgumentException::class);
$config = Loader::fromPath('non-existing-config-file.yml', false);
Loader::fromPath('non-existing-config-file.yml', false);
}

/** @test */
public function it_throws_if_the_content_is_invalid()
{
$this->expectException(InvalidArgumentException::class);
Loader::fromPath(__FILE__, false);
}
}