Ubuntu – Copy all subdirectory names and files with a particular extension to a new directory

command line

I have the following directory structure:

dir1
    py1.py
    py2.py
    subdir1
        file1.py
        anotherfile.txt
    subdir2
        file2.py
        animage.png

I would like to copy the folder structure and the *.py files (except those belonging directly to dir1) to a new directory at the same level as dir1. That is, I'm looking for this:

dir2
    subdir1
        file1.py
    subdir2
        file2.py

I tried (from the layer above dir1):

mkdir dir2
cp -r *.py ../dir2

But this only copied the *.py files from dir 1 into dir2, and ignored the subdirectories.

Best Answer

You could use a shell glob, with the --parents option of cp

Ex. given

$ tree dir1 dir2
dir1
├── py1.py
├── py2.py
├── subdir1
│   ├── anotherfile.txt
│   └── file1.py
└── subdir2
    ├── animage.png
    └── file2.py
dir2

2 directories, 6 files

(note that dir2 already exists) then

$ cd dir1
$ cp --parents -t ../dir2 **/*.py
$ cd ..

gives

$ tree dir1 dir2
dir1
├── py1.py
├── py2.py
├── subdir1
│   ├── anotherfile.txt
│   └── file1.py
└── subdir2
    ├── animage.png
    └── file2.py
dir2
├── subdir1
│   └── file1.py
└── subdir2
    └── file2.py

4 directories, 8 files

I used the globstar pattern ** but if you only need to descend one level you could use a basic * wildcard for the subdirectories.