user1751825 user1751825 - 5 months ago 36
Perl Question

rsync - exclude files in folders but include subfolders



I'm trying to setup a Perl web deployment script using rsync.

I need to exclude some files based on wildcards, but only from specific folders and not their subfolders.

If I list just the filenames to exclude then they'll be excluded from any directory, but if I include the full path (source, or destination) I can't get them to match, so they're not excluded.

The rsync commands I've tried look like this

rsync --recursive --force --delete --progress --exclude='$SOURCE_DIR/index.cgi' --exclude='$SOURCE_DIR/*.pm' "$SOURCE_DIR" "$DEST_DIR"


and

rsync --recursive --force --delete --progress --exclude='$DEST_DIR/index.cgi' --exclude='$DEST_DIR/*.pm' "$SOURCE_DIR" "$DEST_DIR"


Neither of these seems to work, and if I try this

rsync --recursive --force --delete --progress --exclude='index.cgi' --exclude='*.pm' "$SOURCE_DIR" "$DEST_DIR"


then it will exclude the files in all folders.

What do I need to do to exclude these files just from the
$DEST_DIR folder
, but not its subfolders?

Answer

The problem is that $SOURCE_DIR is used in the exclusion pattern itself. I think rsync is only seeing the relative paths deeper than $SOURCE_DIR, so the exclusion is not working.

Solution is to sync from one level up.

test_rsync.sh

#!/bin/bash

BASE=testing
SRC=src
DEST=dest

rm -rf $BASE

mkdir -p $BASE/$SRC/foo/bar/baz/qux
mkdir -p $BASE/$SRC/abc/def/ghi
mkdir -p $BASE/$SRC/qwe/rty

for dir in $( find $BASE/$SRC -type d | grep "[a-z]" ); do
    touch $dir/index.cgi
    touch $dir/Foo.pm
    touch $dir/Bar.pm
done

rsync --recursive --force --delete --exclude=index.cgi --exclude=$SRC/*.pm $BASE/$SRC $BASE/$DEST

diff -r $BASE/$SRC $BASE/$DEST/$SRC | sort -r

Output

Only in testing/src/qwe/rty: index.cgi
Only in testing/src/qwe: index.cgi
Only in testing/src: index.cgi
Only in testing/src: Foo.pm
Only in testing/src/foo: index.cgi
Only in testing/src/foo/bar: index.cgi
Only in testing/src/foo/bar/baz/qux: index.cgi
Only in testing/src/foo/bar/baz: index.cgi
Only in testing/src: Bar.pm
Only in testing/src/abc: index.cgi
Only in testing/src/abc/def: index.cgi
Only in testing/src/abc/def/ghi: index.cgi
Comments