Skip to content

Commit c55f3ff

Browse files
kwibergJunio C Hamano
authored andcommitted
svnimport: Convert the svn:ignore property
Put the value of the svn:ignore property in a regular file when converting a Subversion repository to GIT. The Subversion and GIT ignore syntaxes are similar enough that it often just works to set the filename to .gitignore and do nothing else. Signed-off-by: Karl Hasselström <kha@treskal.com> Signed-off-by: Junio C Hamano <junkio@cox.net>
1 parent 4802426 commit c55f3ff

File tree

2 files changed

+64
-4
lines changed

2 files changed

+64
-4
lines changed

Documentation/git-svnimport.txt

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@ SYNOPSIS
1313
[ -C <GIT_repository> ] [ -i ] [ -u ] [-l limit_rev]
1414
[ -b branch_subdir ] [ -T trunk_subdir ] [ -t tag_subdir ]
1515
[ -s start_chg ] [ -m ] [ -r ] [ -M regex ]
16-
<SVN_repository_URL> [ <path> ]
16+
[ -I <ignorefile_name> ] <SVN_repository_URL> [ <path> ]
1717

1818

1919
DESCRIPTION
@@ -65,6 +65,12 @@ When importing incrementally, you might need to edit the .git/svn2git file.
6565
Prepend 'rX: ' to commit messages, where X is the imported
6666
subversion revision.
6767

68+
-I <ignorefile_name>::
69+
Import the svn:ignore directory property to files with this
70+
name in each directory. (The Subversion and GIT ignore
71+
syntaxes are similar enough that using the Subversion patterns
72+
directly with "-I .gitignore" will almost always just work.)
73+
6874
-m::
6975
Attempt to detect merges based on the commit message. This option
7076
will enable default regexes that try to capture the name source

git-svnimport.perl

Lines changed: 57 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -29,19 +29,21 @@
2929
$SIG{'PIPE'}="IGNORE";
3030
$ENV{'TZ'}="UTC";
3131

32-
our($opt_h,$opt_o,$opt_v,$opt_u,$opt_C,$opt_i,$opt_m,$opt_M,$opt_t,$opt_T,$opt_b,$opt_r,$opt_s,$opt_l,$opt_d,$opt_D);
32+
our($opt_h,$opt_o,$opt_v,$opt_u,$opt_C,$opt_i,$opt_m,$opt_M,$opt_t,$opt_T,
33+
$opt_b,$opt_r,$opt_I,$opt_s,$opt_l,$opt_d,$opt_D);
3334

3435
sub usage() {
3536
print STDERR <<END;
3637
Usage: ${\basename $0} # fetch/update GIT from SVN
3738
[-o branch-for-HEAD] [-h] [-v] [-l max_rev]
3839
[-C GIT_repository] [-t tagname] [-T trunkname] [-b branchname]
39-
[-d|-D] [-i] [-u] [-r] [-s start_chg] [-m] [-M regex] [SVN_URL]
40+
[-d|-D] [-i] [-u] [-r] [-I ignorefilename] [-s start_chg]
41+
[-m] [-M regex] [SVN_URL]
4042
END
4143
exit(1);
4244
}
4345

44-
getopts("b:C:dDhil:mM:o:rs:t:T:uv") or usage();
46+
getopts("b:C:dDhiI:l:mM:o:rs:t:T:uv") or usage();
4547
usage if $opt_h;
4648

4749
my $tag_name = $opt_t || "tags";
@@ -130,6 +132,24 @@ sub file {
130132
return ($name, $mode);
131133
}
132134

135+
sub ignore {
136+
my($self,$path,$rev) = @_;
137+
138+
print "... $rev $path ...\n" if $opt_v;
139+
my (undef,undef,$properties)
140+
= $self->{'svn'}->get_dir($path,$rev,undef);
141+
if (exists $properties->{'svn:ignore'}) {
142+
my ($fh, $name) = tempfile('gitsvn.XXXXXX',
143+
DIR => File::Spec->tmpdir(),
144+
UNLINK => 1);
145+
print $fh $properties->{'svn:ignore'};
146+
close($fh);
147+
return $name;
148+
} else {
149+
return undef;
150+
}
151+
}
152+
133153
package main;
134154
use URI;
135155

@@ -341,6 +361,34 @@ ($$$)
341361
return [$mode, $sha, $path];
342362
}
343363

364+
sub get_ignore($$$$$) {
365+
my($new,$old,$rev,$branch,$path) = @_;
366+
367+
return unless $opt_I;
368+
my $svnpath = revert_split_path($branch,$path);
369+
my $name = $svn->ignore("$svnpath",$rev);
370+
if ($path eq '/') {
371+
$path = $opt_I;
372+
} else {
373+
$path = File::Spec->catfile($path,$opt_I);
374+
}
375+
if (defined $name) {
376+
my $pid = open(my $F, '-|');
377+
die $! unless defined $pid;
378+
if (!$pid) {
379+
exec("git-hash-object", "-w", $name)
380+
or die "Cannot create object: $!\n";
381+
}
382+
my $sha = <$F>;
383+
chomp $sha;
384+
close $F;
385+
unlink $name;
386+
push(@$new,['0644',$sha,$path]);
387+
} else {
388+
push(@$old,$path);
389+
}
390+
}
391+
344392
sub split_path($$) {
345393
my($rev,$path) = @_;
346394
my $branch;
@@ -546,6 +594,9 @@ sub commit {
546594
my $opath = $action->[3];
547595
print STDERR "$revision: $branch: could not fetch '$opath'\n";
548596
}
597+
} elsif ($node_kind eq $SVN::Node::dir) {
598+
get_ignore(\@new, \@old, $revision,
599+
$branch,$path);
549600
}
550601
} elsif ($action->[0] eq "D") {
551602
push(@old,$path);
@@ -554,6 +605,9 @@ sub commit {
554605
if ($node_kind eq $SVN::Node::file) {
555606
my $f = get_file($revision,$branch,$path);
556607
push(@new,$f) if $f;
608+
} elsif ($node_kind eq $SVN::Node::dir) {
609+
get_ignore(\@new, \@old, $revision,
610+
$branch,$path);
557611
}
558612
} else {
559613
die "$revision: unknown action '".$action->[0]."' for $path\n";

0 commit comments

Comments
 (0)