Skip to content

Commit

Permalink
git-svn log: handle unreachable revisions like "svn log"
Browse files Browse the repository at this point in the history
When unreachable revisions are given to "svn log", it displays all commit
logs in the given range that exist in the current tree.  (If no commit
logs are found in the current tree, it simply prints a single commit log
separator.)  This patch makes "git-svn log" behave the same way.

Ten tests added to t/t9116-git-svn-log.sh.

Signed-off-by: David D Kilzer <ddkilzer@kilzer.net>
Acked-by: Eric Wong <normalperson@yhbt.net>
  • Loading branch information
David D Kilzer authored and Eric Wong committed Nov 17, 2007
1 parent 60f3ff1 commit 111947e
Show file tree
Hide file tree
Showing 2 changed files with 110 additions and 19 deletions.
63 changes: 44 additions & 19 deletions git-svn.perl
Original file line number Diff line number Diff line change
Expand Up @@ -2399,10 +2399,15 @@ sub rev_db_get {
$ret;
}

# Finds the first svn revision that exists on (if $eq_ok is true) or
# before $rev for the current branch. It will not search any lower
# than $min_rev. Returns the git commit hash and svn revision number
# if found, else (undef, undef).
sub find_rev_before {
my ($self, $rev, $eq_ok) = @_;
my ($self, $rev, $eq_ok, $min_rev) = @_;
--$rev unless $eq_ok;
while ($rev > 0) {
$min_rev ||= 1;
while ($rev >= $min_rev) {
if (my $c = $self->rev_db_get($rev)) {
return ($rev, $c);
}
Expand All @@ -2411,6 +2416,23 @@ sub find_rev_before {
return (undef, undef);
}

# Finds the first svn revision that exists on (if $eq_ok is true) or
# after $rev for the current branch. It will not search any higher
# than $max_rev. Returns the git commit hash and svn revision number
# if found, else (undef, undef).
sub find_rev_after {
my ($self, $rev, $eq_ok, $max_rev) = @_;
++$rev unless $eq_ok;
$max_rev ||= $self->rev_db_max();
while ($rev <= $max_rev) {
if (my $c = $self->rev_db_get($rev)) {
return ($rev, $c);
}
++$rev;
}
return (undef, undef);
}

sub _new {
my ($class, $repo_id, $ref_id, $path) = @_;
unless (defined $repo_id && length $repo_id) {
Expand Down Expand Up @@ -3701,6 +3723,7 @@ package Git::SVN::Log;
use strict;
use warnings;
use POSIX qw/strftime/;
use constant commit_log_separator => ('-' x 72) . "\n";
use vars qw/$TZ $limit $color $pager $non_recursive $verbose $oneline
%rusers $show_commit $incremental/;
my $l_fmt;
Expand Down Expand Up @@ -3794,19 +3817,19 @@ sub git_svn_log_cmd {
push @cmd, $c;
}
} elsif (defined $r_max) {
my ($c_min, $c_max);
$c_max = $gs->rev_db_get($r_max);
$c_min = $gs->rev_db_get($r_min);
if (defined $c_min && defined $c_max) {
if ($r_max > $r_min) {
push @cmd, "--boundary", "$c_min..$c_max";
} else {
push @cmd, "--boundary", "$c_max..$c_min";
}
} elsif ($r_max > $r_min) {
push @cmd, $c_max;
if ($r_max < $r_min) {
($r_min, $r_max) = ($r_max, $r_min);
}
my (undef, $c_max) = $gs->find_rev_before($r_max, 1, $r_min);
my (undef, $c_min) = $gs->find_rev_after($r_min, 1, $r_max);
# If there are no commits in the range, both $c_max and $c_min
# will be undefined. If there is at least 1 commit in the
# range, both will be defined.
return () if !defined $c_min || !defined $c_max;
if ($c_min eq $c_max) {
push @cmd, '--max-count=1', $c_min;
} else {
push @cmd, $c_min;
push @cmd, '--boundary', "$c_min..$c_max";
}
}
return (@cmd, @files);
Expand Down Expand Up @@ -3914,7 +3937,7 @@ sub show_commit_changed_paths {

sub show_commit_normal {
my ($c) = @_;
print '-' x72, "\nr$c->{r} | ";
print commit_log_separator, "r$c->{r} | ";
print "$c->{c} | " if $show_commit;
print "$c->{a} | ", strftime("%Y-%m-%d %H:%M:%S %z (%a, %d %b %Y)",
localtime($c->{t_utc})), ' | ';
Expand Down Expand Up @@ -3975,6 +3998,10 @@ sub cmd_show_log {

config_pager();
@args = git_svn_log_cmd($r_min, $r_max, @args);
if (!@args) {
print commit_log_separator unless $incremental || $oneline;
return;
}
my $log = command_output_pipe(@args);
run_pager();
my (@k, $c, $d, $stat);
Expand Down Expand Up @@ -4023,14 +4050,12 @@ sub cmd_show_log {
process_commit($c, $r_min, $r_max, \@k);
}
if (@k) {
my $swap = $r_max;
$r_max = $r_min;
$r_min = $swap;
($r_min, $r_max) = ($r_max, $r_min);
process_commit($_, $r_min, $r_max) foreach reverse @k;
}
out:
close $log;
print '-' x72,"\n" unless $incremental || $oneline;
print commit_log_separator unless $incremental || $oneline;
}

package Git::SVN::Migration;
Expand Down
66 changes: 66 additions & 0 deletions t/t9116-git-svn-log.sh
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,12 @@ test_expect_success 'setup repository and import' "
git reset --hard trunk &&
echo aye >> README &&
git commit -a -m aye &&
git svn dcommit &&
git reset --hard b &&
echo spy >> README &&
git commit -a -m spy &&
echo try >> README &&
git commit -a -m try &&
git svn dcommit
"

Expand Down Expand Up @@ -59,4 +65,64 @@ test_expect_success 'test descending revision range' "
git svn log -r 4:1 | grep '^r[0-9]' | cut -d'|' -f1 | diff -u expected-range-r4-r2-r1 -
"

printf 'r1 \nr2 \n' > expected-range-r1-r2

test_expect_success 'test ascending revision range with unreachable revision' "
git reset --hard trunk &&
git svn log -r 1:3 | grep '^r[0-9]' | cut -d'|' -f1 | diff -u expected-range-r1-r2 -
"

printf 'r2 \nr1 \n' > expected-range-r2-r1

test_expect_success 'test descending revision range with unreachable revision' "
git reset --hard trunk &&
git svn log -r 3:1 | grep '^r[0-9]' | cut -d'|' -f1 | diff -u expected-range-r2-r1 -
"

printf 'r2 \n' > expected-range-r2

test_expect_success 'test ascending revision range with unreachable upper boundary revision and 1 commit' "
git reset --hard trunk &&
git svn log -r 2:3 | grep '^r[0-9]' | cut -d'|' -f1 | diff -u expected-range-r2 -
"

test_expect_success 'test descending revision range with unreachable upper boundary revision and 1 commit' "
git reset --hard trunk &&
git svn log -r 3:2 | grep '^r[0-9]' | cut -d'|' -f1 | diff -u expected-range-r2 -
"

printf 'r4 \n' > expected-range-r4

test_expect_success 'test ascending revision range with unreachable lower boundary revision and 1 commit' "
git reset --hard trunk &&
git svn log -r 3:4 | grep '^r[0-9]' | cut -d'|' -f1 | diff -u expected-range-r4 -
"

test_expect_success 'test descending revision range with unreachable lower boundary revision and 1 commit' "
git reset --hard trunk &&
git svn log -r 4:3 | grep '^r[0-9]' | cut -d'|' -f1 | diff -u expected-range-r4 -
"

printf -- '------------------------------------------------------------------------\n' > expected-separator

test_expect_success 'test ascending revision range with unreachable boundary revisions and no commits' "
git reset --hard trunk &&
git svn log -r 5:6 | diff -u expected-separator -
"

test_expect_success 'test descending revision range with unreachable boundary revisions and no commits' "
git reset --hard trunk &&
git svn log -r 6:5 | diff -u expected-separator -
"

test_expect_success 'test ascending revision range with unreachable boundary revisions and 1 commit' "
git reset --hard trunk &&
git svn log -r 3:5 | grep '^r[0-9]' | cut -d'|' -f1 | diff -u expected-range-r4 -
"

test_expect_success 'test descending revision range with unreachable boundary revisions and 1 commit' "
git reset --hard trunk &&
git svn log -r 5:3 | grep '^r[0-9]' | cut -d'|' -f1 | diff -u expected-range-r4 -
"

test_done

0 comments on commit 111947e

Please sign in to comment.