From: Junio C Hamano <gitster@pobox.com>
To: Johannes Schindelin <Johannes.Schindelin@gmx.de>
Cc: git@vger.kernel.org, Martin Langhoff <martin@catalyst.net.nz>,
Robin Rosenberg <robin.rosenberg@dewire.com>
Subject: Re: [PATCH] cvsexportcommit: be graceful when "cvs status" reorders the arguments
Date: Sun, 17 Feb 2008 19:03:14 -0800 [thread overview]
Message-ID: <7vbq6fvudp.fsf@gitster.siamese.dyndns.org> (raw)
In-Reply-To: <alpine.LSU.1.00.0802180127100.30505@racer.site> (Johannes Schindelin's message of "Mon, 18 Feb 2008 01:31:36 +0000 (GMT)")
Johannes Schindelin <Johannes.Schindelin@gmx.de> writes:
> I finally tracked it down to two filenames having the same basename.
Wonderful.
> Feel free to criticise/educate me on my Perl style.
Here it goes ;-)
> + # "cvs status" reorders the parameters, notably when there are multiple
> + # arguments with the same basename. So be precise here.
> + while (@canstatusfiles) {
> + my @canstatusfiles2 = ();
> + my %basenames = ();
> + for (my $i = 0; $i <= $#canstatusfiles; $i++) {
The "$index <= $#array" termination condition feels so Perl4-ish.
for (my $i = 0; $i < @canstatusfiles; $i++) {
> + my $name = $canstatusfiles[$i];
> + my $basename = $name;
> + $basename =~ s/.*\///;
The script uses File::Basename upfront so perhaps just simply...
my $basename = basename($name);
> + $basename = "no file " . $basename if (grep {$_ eq $basename} @afiles);
Huh? Perl or no Perl that is too ugly a hack... What special
treatment do "added files" need? We would want to make sure
that the files are not reported from "cvs status"?
> + chomp($basename);
Huh? Perhaps you wanted to chomp at the very beginning of the loop?
> + if (!defined($basenames{$basename})) {
> + $basenames{$basename} = $name;
> + push (@canstatusfiles2, $name);
> + splice (@canstatusfiles, $i, 1);
> + $i--;
> }
> + }
> + my @cvsoutput;
> + @cvsoutput = xargs_safe_pipe_capture([@cvs, 'status'], @canstatusfiles2);
> + foreach my $l (@cvsoutput) {
> + chomp $l;
> + if ( $l =~ /^File:\s+(.*\S)\s+Status: (.*)$/ ) {
> + $cvsstat{$basenames{$1}} = $2 if defined($basenames{$1});
> + }
> + }
I think "exists $hash{$index}" would be easier to read and more
logical here and also if () condition above.
Without understanding what is really going on with the "added
files" case, here is how I would write your patch.
Side note. I personally do not like naming hashes and arrays
plural, and call a hash of paths and list of files %path and
@file respectively. That convention makes it easier to read
things like these:
$file[4] ;# fourth file, not $files[4]
$path{'hello.c'} ;# path for 'hello.c', not $paths{'hello.c'}
---
git-cvsexportcommit.perl | 43 ++++++++++++++++++++++++++++++++++---------
1 files changed, 34 insertions(+), 9 deletions(-)
diff --git a/git-cvsexportcommit.perl b/git-cvsexportcommit.perl
index 2a8ad1e..06e7fda 100755
--- a/git-cvsexportcommit.perl
+++ b/git-cvsexportcommit.perl
@@ -197,15 +197,40 @@ if (@canstatusfiles) {
my @updated = xargs_safe_pipe_capture([@cvs, 'update'], @canstatusfiles);
print @updated;
}
- my @cvsoutput;
- @cvsoutput = xargs_safe_pipe_capture([@cvs, 'status'], @canstatusfiles);
- my $matchcount = 0;
- foreach my $l (@cvsoutput) {
- chomp $l;
- if ( $l =~ /^File:/ and $l =~ /Status: (.*)$/ ) {
- $cvsstat{$canstatusfiles[$matchcount]} = $1;
- $matchcount++;
- }
+
+ my %added = map { $_ => 1 } @afiles;
+
+ while (@canstatusfiles) {
+ my %basename = ();
+ my @status = ();
+ my @leftover = ();
+ for (my $i = 0; $i < @canstatusfiles; $i++) {
+ my $name = $canstatusfiles[$i];
+ my $basename = basename($name);
+ if (exists $basename{$basename}) {
+ push @leftover, $name;
+ next;
+ }
+ if (exists $added{$name}) {
+ # Hmph...
+ next;
+ }
+ $basename{$basename} = $name;
+ push @status, $name;
+ }
+ my @cvsoutput = xargs_safe_pipe_capture([@cvs, 'status'], @status);
+ for my $l (@cvsoutput) {
+ chomp $l;
+ if ($l =~ /^File:\s+(.*\S)\s+Status: (.*)$/) {
+ my ($n, $s) = ($1, $2);
+ if (!exists $basename{$n}) {
+ print STDERR "Huh ($n)?\n";
+ } else {
+ $cvsstat{$basename{$n}} = $s;
+ }
+ }
+ }
+ @canstatusfiles = @leftover;
}
}
next prev parent reply other threads:[~2008-02-18 3:04 UTC|newest]
Thread overview: 15+ messages / expand[flat|nested] mbox.gz Atom feed top
2008-02-18 1:31 [PATCH] cvsexportcommit: be graceful when "cvs status" reorders the arguments Johannes Schindelin
2008-02-18 3:03 ` Junio C Hamano [this message]
2008-02-18 3:20 ` Junio C Hamano
2008-02-18 15:25 ` Martin Langhoff
2008-02-18 16:27 ` Johannes Schindelin
2008-02-18 16:33 ` Martin Langhoff
2008-02-18 17:43 ` Johannes Schindelin
2008-02-18 17:55 ` [PATCH v2] " Johannes Schindelin
2008-02-18 17:54 ` [PATCH] " Johannes Schindelin
2008-02-18 18:36 ` Junio C Hamano
2008-02-18 18:50 ` Johannes Schindelin
2008-02-18 18:55 ` Martin Langhoff
2008-02-18 19:42 ` Johannes Schindelin
2008-02-18 20:06 ` Martin Langhoff
2008-02-18 20:29 ` Johannes Schindelin
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=7vbq6fvudp.fsf@gitster.siamese.dyndns.org \
--to=gitster@pobox.com \
--cc=Johannes.Schindelin@gmx.de \
--cc=git@vger.kernel.org \
--cc=martin@catalyst.net.nz \
--cc=robin.rosenberg@dewire.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).