What's wrong with my exclude rules?

Danny Sauer rsync at danny.teleologic.net
Thu Feb 24 00:42:30 GMT 2005


On Wednesday 23 February 2005 03:03 pm, John Van Essen wrote:
> On Wed, 23 Feb 2005, Eberhard Moenkeberg <emoenke at gwdg.de> wrote:
> > On Wed, 23 Feb 2005, Danny Sauer wrote:
> >> It's not the inclusion of '/' - I took that out, and it still tries to
> >> sync /proc.  Thoughts?
> >
> > Probably the shell's wildcard expansion is striking across.
> >   --exclude="/proc/a /proc/b" does neither exclude /proc/a nor /proc/b.
>
> Good point.  I missed that.

Well, I'm not doing that, so it's not likely the problem. :)  It's related, 
though.

> I always use the '=' format to connect the option to the argument
> (e.g. --exclude=/proc/*).  That way, there's no wildcard expansion
> because no filenames will match that combined pattern.
>
> Maybe all man page examples should use the '=' format?

Ok, *that* led me to the solution.  Well, that, and figuring out that I 
can't quote the filenames used for the --exclude-from argument.  What I 
needed to do was remove the double quotes.  Quoting arguments is standard 
practice in my shell scripts (and most, AFAIK).  That way, if there's a 
space or something in the thing being specified, everything's cool.  It 
appears, though, that rsync somehow gets those quotes (I thought bash was 
supposed to take them out), and it's literally trying to match "/proc/*", 
quotes and all.  Argh.

So, I can take the quotes out, and use = to connect the terms to the 
argument.  That's fine, as I don't have any spaces in filenames anyway.  
However, what happens if I want to exclude a file with spaces, or similar?  
One of these machines is a file server for Win32 and MacOS X clients, and 
those users like spaces.  What about other special shell chars?  I'd *like* 
for my script to not just randomly break if shell meta chars happen to 
appear in a filename somehow.

I guess this turns into a question for the bash developes - though I'm up to 
date with that, as well.  Here's what I do, basically:

RSYNC="/usr/bin/rsync"
ARGS="-a -b -c -d -etc"
EXCLUDES=`mount | 
  perl -ane'if ($F[4] !~ /^ext[23]) print "--exclude=\"$F[2]\" "'`
$RSYNC $ARGS $EXCLUDES $SRC $DEST

Oh, I see.  That made it clear.  The quotes are inside the $EXCLUDES var, 
and are therefore not seen by the shell.  If I had just typed in what was 
posted earlier, it *would* have worked.  The problem is that the quotes 
aren't handled after the variables are interpreted - they're passed as part 
of the argument, so rsync sees them as part of the filename.  OK, that's 
cool, since it means I shouldn't have to worry about the metachars anyway.  
Back to shell-scripting 101 for me, eh?  Maybe 201? :)

Thanks for leading me in the right direction, all who did so (however 
inadvertently it may have been).

--Danny


More information about the rsync mailing list