Implement IDF_Scm::getChanges() for Subversion (closes issue 622)

This commit is contained in:
Thomas Keller 2011-06-10 02:23:54 +02:00
parent 7ff6f09f67
commit ac6be0d3c0
2 changed files with 83 additions and 0 deletions

View File

@ -8,6 +8,7 @@ or newer to properly run this version of Indefero!
- Indefero's issue tracker can now bi-directionally link issues with variable, configurable
terms, such as "is related to", "is blocked by" or "is duplicated by" (issue 638)
- Mercurial source views now show parent revisions (if any) and detailed change information
- Subversion source views now show detailed change information (issue 622)
- File download URLs now contain the file name rather than the upload id; old links still work though (issues 559 and 686)
- Display monotone file and directory attributes in the tree and file view
(needs a monotone with an interface version of 13.1 or newer)

View File

@ -479,6 +479,88 @@ class IDF_Scm_Svn extends IDF_Scm
return self::shell_exec('IDF_Scm_Svn::getDiff', $cmd);
}
/**
* @see IDF_Scm::getChanges()
*/
public function getChanges($commit)
{
if ($this->validateRevision($commit) != IDF_Scm::REVISION_VALID) {
return null;
}
$cmd = sprintf(Pluf::f('svn_path', 'svn').' log --xml -v --no-auth-cache -r %s --username=%s --password=%s %s',
escapeshellarg($commit),
escapeshellarg($this->username),
escapeshellarg($this->password),
escapeshellarg($this->repo));
$out = array();
$cmd = Pluf::f('idf_exec_cmd_prefix', '').$cmd;
$out = self::shell_exec('IDF_Scm_Svn::getChanges', $cmd);
$xml = simplexml_load_string($out);
if (count($xml) == 0) {
return null;
}
$entry = current($xml);
$return = (object) array(
'additions' => array(),
'deletions' => array(),
'patches' => array(),
// while SVN has support for attributes, we cannot see their changes
// in the log's XML unfortunately
'properties' => array(),
'copies' => array(),
'renames' => array(),
);
foreach ($entry->paths->path as $p) {
$path = (string) $p;
foreach ($p->attributes() as $k => $v) {
$key = (string) $k;
$val = (string) $v;
if ($key != 'action')
continue;
if ($val == 'M')
$return->patches[] = $path;
else if ($val == 'A')
$return->additions[] = $path;
else if ($val == 'D')
$return->deletions[] = $path;
}
}
// copies are treated as renames if they have an add _and_ a drop;
// only if they only have an add, but no drop, they're treated as copies
foreach ($xml->paths as $path) {
$trg = (string) $path;
$src = null;
foreach ($path->attributes() as $k => $v) {
if ((string) $k == 'copyfrom-path') {
$src = (string) $v;
break;
}
}
if ($src == null)
continue;
$srcidx = array_search($src, $return->deletions);
$trgidx = array_search($trg, $return->additions);
if ($srcidx !== false && $trgidx !== false) {
$return->renames[$src] = $trg;
unset($return->deletions[$srcidx]);
unset($return->additions[$trgidx]);
continue;
}
if ($srcidx === false && $trgidx !== false) {
$return->copies[$src] = $trg;
unset($return->additions[$trgidx]);
continue;
}
// file sutures (counter-operation to copy) not supported
}
return $return;
}
/**
* Get latest changes.