git/list[1] front-page[2] threads[3] people[4] search[5] about
 

[PATCH 1/4] git-svn: bugfix and optimize the 'log' command

From
EWEric Wong <normalperson@yhbt.net>
Date
Jun 16, 2006, 17:57 UTC
Message-ID
<11504806472857-git-send-email-normalperson@yhbt.net>
In-Reply-To
<11504806463470-git-send-email-normalperson@yhbt.net>

Revisions with long commit messages were being skipped, since the 'git-svn-id' metadata line was at the end and git-log uses a 32k buffer to print the commits.

Also the last 'git-svn-id' metadata line in a commit is always the valid one, so make sure we use that, as well.

Made the verbose flag work by passing the correct option switch ('--summary') to git-log.

Finally, optimize -r/--revision argument handling by passing the appropriate limits to revision

Signed-off-by: Eric Wong <normalperson@yhbt.net>
---
 contrib/git-svn/git-svn.perl |   60 ++++++++++++++++++++++++++++++++++++------
 1 files changed, 52 insertions(+), 8 deletions(-)
diff --git a/contrib/git-svn/git-svn.perl b/contrib/git-svn/git-svn.perl
index 149149f..417fcf1 100755
--- a/contrib/git-svn/git-svn.perl
+++ b/contrib/git-svn/git-svn.perl
@@ -663,17 +663,15 @@ sub show_log {
 	my $pid = open(my $log,'-|');
 	defined $pid or croak $!;
 	if (!$pid) {
-		my @rl = (qw/git-log --abbrev-commit --pretty=raw
-				--default/, "remotes/$GIT_SVN");
-		push @rl, '--raw' if $_verbose;
-		exec(@rl, @args) or croak $!;
+		exec(git_svn_log_cmd($r_min,$r_max), @args) or croak $!;
 	}
 	setup_pager();
 	my (@k, $c, $d);
+
 	while (<$log>) {
 		if (/^commit ($sha1_short)/o) {
 			my $cmt = $1;
-			if ($c && defined $c->{r} && $c->{r} != $r_last) {
+			if ($c && cmt_showable($c) && $c->{r} != $r_last) {
 				$r_last = $c->{r};
 				process_commit($c, $r_min, $r_max, \@k) or
 								goto out;
@@ -692,8 +690,7 @@ sub show_log {
 		} elsif ($d) {
 			push @{$c->{diff}}, $_;
 		} elsif (/^    (git-svn-id:.+)$/) {
-			my ($url, $rev, $uuid) = extract_metadata($1);
-			$c->{r} = $rev;
+			(undef, $c->{r}, undef) = extract_metadata($1);
 		} elsif (s/^    //) {
 			push @{$c->{l}}, $_;
 		}
@@ -715,6 +712,52 @@ out:
 
 ########################### utility functions #########################
 
+sub cmt_showable {
+	my ($c) = @_;
+	return 1 if defined $c->{r};
+	if ($c->{l} && $c->{l}->[-1] eq "...\n" &&
+				$c->{a_raw} =~ /\@([a-f\d\-]+)>$/) {
+		my @msg = safe_qx(qw/git-cat-file commit/, $c->{c});
+		shift @msg while ($msg[0] ne "\n");
+		shift @msg;
+		@{$c->{l}} = grep !/^git-svn-id: /, @msg;
+
+		(undef, $c->{r}, undef) = extract_metadata(
+				(grep(/^git-svn-id: /, @msg))[-1]);
+	}
+	return defined $c->{r};
+}
+
+sub git_svn_log_cmd {
+	my ($r_min, $r_max) = @_;
+	my @cmd = (qw/git-log --abbrev-commit --pretty=raw
+			--default/, "refs/remotes/$GIT_SVN");
+	push @cmd, '--summary' if $_verbose;
+	return @cmd unless defined $r_max;
+	if ($r_max == $r_min) {
+		push @cmd, '--max-count=1';
+		if (my $c = revdb_get($REVDB, $r_max)) {
+			push @cmd, $c;
+		}
+	} else {
+		my ($c_min, $c_max);
+		$c_max = revdb_get($REVDB, $r_max);
+		$c_min = revdb_get($REVDB, $r_min);
+		if ($c_min && $c_max) {
+			if ($r_max > $r_max) {
+				push @cmd, "$c_min..$c_max";
+			} else {
+				push @cmd, "$c_max..$c_min";
+			}
+		} elsif ($r_max > $r_min) {
+			push @cmd, $c_max;
+		} else {
+			push @cmd, $c_min;
+		}
+	}
+	return @cmd;
+}
+
 sub fetch_child_id {
 	my $id = shift;
 	print "Fetching $id\n";
@@ -2206,6 +2249,7 @@ sub setup_pager { # translated to Perl f
 sub get_author_info {
 	my ($dest, $author, $t, $tz) = @_;
 	$author =~ s/(?:^\s*|\s*$)//g;
+	$dest->{a_raw} = $author;
 	my $_a;
 	if ($_authors) {
 		$_a = $rusers{$author} || undef;
@@ -2440,7 +2484,7 @@ sub svn_grab_base_rev {
 	close $fh;
 	if (defined $c && length $c) {
 		my ($url, $rev, $uuid) = extract_metadata((grep(/^git-svn-id: /,
-			safe_qx(qw/git-cat-file commit/, $c)))[0]);
+			safe_qx(qw/git-cat-file commit/, $c)))[-1]);
 		return ($rev, $c);
 	}
 	return (undef, undef);
-- 
1.4.0
Previous: Eric WongNext: Eric Wong
Message 5 of 8 in “git-svn: avoid creating some small files”
  1. 1/3 git-svn: avoid creating some small filesEric Wong, Jun 15, 2006
  2. 2/3 git-svn: fix several small bugs, enable branch optimizationEric Wong, Jun 15, 2006
  3. 3/3 git-svn: Eliminate temp file usage in libsvn_get_file()Eric Wong, Jun 15, 2006
  4. 0/4 git-svn: more improvementsEric Wong, Jun 16, 2006
  5. 1/4 git-svn: bugfix and optimize the 'log' commandEric Wong, Jun 16, 2006
  6. 2/4 git-svn: tests no longer fail if LC_ALL is not a UTF-8 localeEric Wong, Jun 16, 2006
  7. 3/4 git-svn: svn (command-line) 1.0.x compatibilityEric Wong, Jun 16, 2006
  8. 4/4 git-svn: rebuild convenience and bugfixesEric Wong, Jun 16, 2006

Read the whole thread, see it on lore, or plain text.

$ cat FOOTERMessages come from the public archive at lore.kernel.org/git, fetched every hour. The front page is chosen and written each morning by an AI editor and can be wrong; the threads themselves are the record. About and API. For agents: an MCP server at https://gitlist.dev/mcp, and any thread, story or person page as Markdown by adding .md to its URL (or sending Accept: text/markdown). Details in /llms.txt.