Reputation: 914
I have a directory structure as below:
base
├── config.yml
├── build
│ └── output.yml
│ └── <multiple level sub-directories each having many files including *.c and *.h files>
├── <source directories - having many sub-directories with various files including *.c and *.h files>
│ ├── <xyz>
| │ ├── <x1>
| │ .
│ | └── <xy>
│ .
│ .
│ └── <abc>
├── <more directories, each having multiple files including *.c and *.h files>
I need to sync this directory to remote, but I only need *.c and *.h files. Also complete 'build' directory needs to be excluded. I am running below command:
rsync -avm --include '*/' --include='*.c' --include='*.h' --exclude='*' base "$target_loc"
This is syncing all *.c and *.h files which is desired but it also syncs *.c and *.h files from build and its sub directories
I tried
rsync -avm --include '*/' --include='*.c' --include='*.h' --exclude='build' --exclude='*' base "$target_loc"
. It still syncs files from build and it's sub directories.
How can I fix this?
Upvotes: 2
Views: 2392
Reputation: 126048
You need to put --exclude='build'
before --include '*/'
. Both of these rules could apply to the "build" directory, and whichever is given first takes precedence, so to get the --exclude
rule to override the --include
rule, you need to list it first.
From the rsync
man page, in the FILTER RULES section (with my emphasis):
As the list of files/directories to transfer is built, rsync checks each name to be transferred against the list of include/exclude patterns in turn, and the first matching pattern is acted on: if it is an exclude pattern, then that file is skipped; if it is an include pattern then that filename is not skipped; if no matching pattern is found, then the filename is not skipped.
Upvotes: 4