rsync copying directory contents non-recursively

I'm trying to copy the contents of a series of directories non-recursively to another remote system.

/dirA/dir1/file
/dirA/dir2/file
/dirA/dir3/file

dir1, dir2, and dir3 contain many directories that I do not want copied. Copy on the remote host to /dirB maintaining the same directory structure.

I tried:

rsync /dirA/*/ host:/dirB/
rsync /dirA/   host:/dirB/

But they don't do what I want.


rsync allows you to specify patterns that trigger the inclusion or exclusion of files and directories. I think you want to use something like this:

rsync -a -f '- /*/*/' /dirA/ host:/dirB/

Explanation:

  • -a triggers the archive mode that activates both recursion and preservation of "symbolic links, devices, attributes, permissions, ownerships, etc.", according to man rsync.
  • -f is short for --filter=, which adds a file-filtering rule.
    • The pattern is inside single quotes so that the shell does not expand wildcards; double quotes would work equally well in this case.
    • - means this is an exclude pattern.
    • The leading / means the pattern must start at dirA/ (the rsync "transfer-root").
    • The */* part of the pattern refers to anything inside of a subdirectory.
    • The trailing / limits the exclusion to directories. Files inside a subdirectory of dirA/ are not affected.

So in the end, rsync copies nothing more than one level down (and also does not create second-level directories).


The solution above (by PleaseStand) didn't work for me for some reason. This worked though:

rsync -avc --no-r ./source/* ./destination/

There's also this alternative one:

rsync -avc --exclude "/" ./source/ ./destination/


One of the "features" of rsync is how directories are parsed.

rsync /dirA/ host:/dirB/ and rsync /dirA host:/dirB should theoretically be equivalent.

As not wanting to encourage recursiveness, you want to avoid -r, -a which in addition to other things implies -r.

I'm still not quite done with research, but this is my starting answer.