146 lines
3.3 KiB
PHP
Raw Normal View History

<?php
/*
* This file is part of Git.
*
* (c) Sebastian Bergmann <sebastian@phpunit.de>
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
namespace SebastianBergmann\Git;
use DateTime;
class Git
{
/**
* @var string
*/
private $repositoryPath;
/**
* @param string $repositoryPath
*/
public function __construct($repositoryPath)
{
if (!is_dir($repositoryPath)) {
throw new RuntimeException(
sprintf(
'Directory "%s" does not exist',
$repositoryPath
)
);
}
$this->repositoryPath = realpath($repositoryPath);
}
/**
* @param string $revision
*/
public function checkout($revision)
{
$this->execute(
'checkout --force --quiet ' . $revision
);
}
/**
* @return string
*/
public function getCurrentBranch()
{
$output = $this->execute('symbolic-ref --short HEAD');
return $output[0];
}
/**
* @param string $from
* @param string $to
* @return string
*/
public function getDiff($from, $to)
{
$output = $this->execute(
'diff --no-ext-diff ' . $from . ' ' . $to
);
return implode("\n", $output);
}
/**
* @return array
*/
public function getRevisions()
{
$output = $this->execute(
'log --no-merges --date-order --reverse --format=medium'
);
$numLines = count($output);
$revisions = array();
for ($i = 0; $i < $numLines; $i++) {
$tmp = explode(' ', $output[$i]);
if ($tmp[0] == 'commit') {
$sha1 = $tmp[1];
} elseif ($tmp[0] == 'Author:') {
$author = implode(' ', array_slice($tmp, 1));
} elseif ($tmp[0] == 'Date:' && isset($author) && isset($sha1)) {
$revisions[] = array(
'author' => $author,
'date' => DateTime::createFromFormat(
'D M j H:i:s Y O',
implode(' ', array_slice($tmp, 3))
),
'sha1' => $sha1,
'message' => isset($output[$i+2]) ? trim($output[$i+2]) : ''
);
unset($author);
unset($sha1);
}
}
return $revisions;
}
/**
* @return bool
*/
public function isWorkingCopyClean()
{
$output = $this->execute('status');
return $output[count($output)-1] == 'nothing to commit, working directory clean' ||
$output[count($output)-1] == 'nothing to commit, working tree clean';
}
/**
* @param string $command
*
* @return string
*
* @throws RuntimeException
*/
protected function execute($command)
{
$command = 'cd ' . escapeshellarg($this->repositoryPath) . '; git ' . $command . ' 2>&1';
if (DIRECTORY_SEPARATOR == '/') {
$command = 'LC_ALL=en_US.UTF-8 ' . $command;
}
exec($command, $output, $returnValue);
if ($returnValue !== 0) {
throw new RuntimeException(implode("\r\n", $output));
}
return $output;
}
}