Move files and folders recursively on Linux

79

13

Consider:

ls -al ../public-back
drwxrwxr-x  4 apache   apache     4096 Apr 19 03:32 templates

ls -al ../public-back/templates

drwxrwxr-x  2 apache   apache    4096 Apr 19 03:33 content
drwxrwxr-x  2 apache   apache   20480 Apr 20 06:14 images
drwxrwxr-x  2 apache   apache    4096 Apr 19 03:35 video

ls -al /public

drwxrwxr-x  4 apache   apache     4096 Apr 20 09:49 templates

ls -al /public/templates

drwxrwxr-x  2 apache   apache    4096 Apr 20 09:50 content
drwxrwxr-x  2 apache   apache    4096 Apr 20 09:50 images
drwxrwxr-x  2 apache   apache    4096 Apr 20 09:50 video

How do I move the contents of /public-back/templates recursively with permissions into /public/templates?

siliconpi

Posted 2011-04-20T10:24:10.717

Reputation: 2 067

mv ../public-back/templates/* public/templates/ – None – 2011-04-20T10:28:23.297

mv -R ../public-back/templates/* public/templates/ I'd still vote to move the question. – None – 2011-04-20T10:33:05.170

2mv: invalid option -- R @Vladislav Zorov – None – 2011-04-20T11:12:34.743

3i did cp -a ../public-back/templates/ public/ – None – 2011-04-20T11:20:08.727

Answers

97

Unless I am misunderstanding the question, this would work:

mv /public-back/templates/* /public/templates

Also, unless you have a huge list of files, adding -i will ask before it overwrites anything, which add some safety when using wildcards like *.

DQdlM

Posted 2011-04-20T10:24:10.717

Reputation: 1 831

14This does not move hidden files. – Arda – 2014-09-26T23:34:31.297

2

See http://askubuntu.com/a/259386/358964 for setting dotglob so hidden files will also be moved.

– mkobit – 2015-08-21T13:58:02.467

3Note: This will not overwrite files in subdirectories. You will get a Directory not empty message. – Armstrongest – 2015-10-16T18:34:37.363

Seems that it flattened the directory hierarchy. Did not preserve folders within the original folder for me. All files ended up in the same folder, rather than literally moving the original folder with the same structure. – Robert Noack – 2016-01-24T17:33:54.950

This solution works, but if you see this error: mv: target '/public/templates' is not a directory just create the destination folder manually: mkdir /public/templates. – Ali Shabdar – 2018-03-02T07:17:06.703

Note: To move the hidden files and folders, use: mv /public-bak/templates/.[!.]* /public/templates. – Ali Shabdar – 2018-03-02T08:24:03.573

10

The man page for cp states:

-p same as --preserve=mode,ownership,timestamps
-r same as --recursive=copy directories recursively

Try;

cp -rp /public-back/templates/* /public/templates/

Himalay

Posted 2011-04-20T10:24:10.717

Reputation: 287

cp is way slower than mv. cp forces the computer to copy everything from the disk to RAM, and then write it to the disk again which may take a long time depending on the size of the files. However, mv always happens instantly because only the links have to be rewritten. – tjespe – 2017-03-07T18:40:58.023

15mv is for move, while cp is for copy – a semantical/etymological distinction. – Marius Butuc – 2013-03-19T17:34:09.463

5

When moving items from my thumb drive to my OSMC system, I've found the following very useful:

find /media/Pi\ Hard\ 16GB/ -name '*' -exec mv -v {} /media/External\ HDD/Videos/ \;

Explanation on how it works below.

BTW, Don't forget to add a backslash before any spaces in the source or destination directory names (see above).

find  finds all files and folders in the destination path.

/media/Pi Hard 16GB/ is the path searched. Escape special char such as spaces.

-name '*' filters on names. If you do not escape or quote this then 
          the shell will expand it before find sees it.

-exec     Executes a command, in our case mv

-v        Verbose, so you can see what's happening (optional)

{}        is replaced by the name of the found object.

Effectively, you are finding all files and all folders and moving them one by one (or if a directory gets found first, you are moving that directory and the contents in it). This starts a new process for each move and is very inefficient. Only use this when the regular commands fail.

Pi Hard

Posted 2011-04-20T10:24:10.717

Reputation: 51

2

cp -a --link ../public-back/* /public/.  &&  rm -rf ../public-back

So create hard links in the destination directory and remove the source dir. 'mv' simply will not work in your case, and in general works only when source dir and dest have no common subtrees.

Note that I'm assuming that the word 'move' in the question means that the source dir should be gone after the operation.

Boudewijn

Posted 2011-04-20T10:24:10.717

Reputation: 21

2

mv doesn't seem to do this. But you can use this little trick, works like a charm:

tar cf - . |(cd /targetdir; tar xvf -)

and preserves permissions and all.

Note: none of the above worked for me, that's why this workaround.

svye

Posted 2011-04-20T10:24:10.717

Reputation: 21