63 lines
1.7 KiB
Perl
Executable File
63 lines
1.7 KiB
Perl
Executable File
#!/usr/bin/perl
|
|
# Uses symlinks to merge the files contained in a set of vcs
|
|
# checkouts to into a single directory. Keeps track of when files are
|
|
# removed from the merged directories and removes the symlinks.
|
|
#
|
|
# Only merges files that match the specified pattern.
|
|
#
|
|
# Note that the directories given to merge should be paths that will work
|
|
# for symlink targets from the destination directory (so either full paths,
|
|
# or they should be right inside the destination directory).
|
|
#
|
|
# Note that other files in the destination directory will be left as-is.
|
|
#
|
|
# Copyright 2006 by Joey Hess, licensed under the GPL.
|
|
|
|
if (! @ARGV) {
|
|
die "usage: dircombine include-pattern dest dir1 [dir2 ...]\n";
|
|
}
|
|
|
|
my $pattern=shift;
|
|
my $dest=shift;
|
|
|
|
foreach my $dir (@ARGV) {
|
|
my %known;
|
|
|
|
# Link in each thing from the dir.
|
|
opendir(DIR, $dir) || die "opendir: $!";
|
|
while ($_=readdir(DIR)) {
|
|
next if $_ eq '.' || $_ eq '..' || $_ eq 'known' || $_ eq '.svn' || $_ eq '.git' || $_ eq '.gitignore' || $_ eq '_darcs';
|
|
next unless /$pattern/;
|
|
|
|
$known{$_}=1;
|
|
|
|
if (! -l "$dest/$_" && -e "$dest/$_") {
|
|
print STDERR "$_ in $dir is also in $dest\n";
|
|
}
|
|
elsif (! -l "$dest/$_") {
|
|
system("ln", "-svf", "$dir/$_", $dest);
|
|
}
|
|
}
|
|
closedir(DIR);
|
|
|
|
# Remove anything that was previously linked in but is not in the
|
|
# dir anymore.
|
|
if (-e "$dir/known") {
|
|
open(KNOWN, "$dir/known") || die "open $dir/known: $!";
|
|
while (<KNOWN>) {
|
|
chomp;
|
|
if (! $known{$_}) {
|
|
system("rm", "-vf", "$dest/$_");
|
|
}
|
|
}
|
|
close KNOWN;
|
|
}
|
|
|
|
# Save state for next time.
|
|
open(KNOWN, ">$dir/known") || die "write $dir/known: $!";
|
|
foreach my $file (sort keys %known) {
|
|
print KNOWN "$file\n";
|
|
}
|
|
close KNOWN;
|
|
}
|