Você terá que copiá-los para o destino e depois excluir a fonte, usando os comandos cp -r * ..
seguido por rm -rf *
.
Eu não acho que você pode "mesclar" diretórios usando mv
.
Eu tenho uma tonelada de arquivos e dirs em um subdiretório que eu quero mover para o diretório pai. Já existem alguns arquivos e dirs no diretório de destino que precisam ser sobrescritos. Arquivos que estão presentes apenas no destino devem ser deixados intactos. Posso forçar o mv
a fazer isso? Ele ( mv * ..
) reclama
mv: cannot move 'xyz' to '../xyz': Directory not empty
O que estou perdendo?
rsync
provavelmente seria a melhor opção aqui. É tão simples quanto rsync -a subdir/ ./
.
Minha árvore de teste em filename
: contents
format:
./file1:root
./file2:root
./dir/file3:dir
./dir/file4:dir
./subdir/dir/file3:subdir
./subdir/file1:subdir
Executando rsync
:
$ rsync -a -v subdir/ ./
sending incremental file list
./
file1
dir/
dir/file3
Dá:
./file1:subdir
./file2:root
./dir/file3:subdir
./dir/file4:dir
./subdir/dir/file3:subdir
./subdir/file1:subdir
E, em seguida, para emular mv
, você provavelmente deseja remover o diretório de origem:
$ rm -r subdir/
Dando:
./file1:subdir
./file2:parent
./dir/file3:subdir
./dir/file4:dir
Se isso estiver errado, você pode fornecer um exemplo semelhante (por exemplo, usando minha árvore de teste de perto do topo desta resposta) com o resultado desejado?
rsync
pode excluir a fonte após as cópias com o parâmetro --remove-source-files
.
Esta deve ser uma maneira conveniente de fazer o que você gostaria.
Do rsync man page
:
--remove-source-files sender removes synchronized files (non-dir)
Você pode fazer isso com cp
e rm
, mas sem copiar a enorme quantidade de dados que você está (presumivelmente) tentando evitar a transferência. @mattdm fez alusão a isso em seu comentário e uma resposta para outra pergunta tem uma discussão mais completa sobre várias opções.
cp -rlf source destination
rm -r source
Essencialmente, a opção -l
do comando cp
cria links físicos para arquivos em vez de copiar seus dados para novos arquivos.
Aqui está um script que move os arquivos de /path/to/source/root
para o caminho correspondente em /path/to/destination/root
.
Cuidado, código não testado.
export dest='/path/to/destination/root'
cd /path/to/source/root
find . -type d \( -exec sh -c '[ -d "$dest/$0" ]' \; -o \
-exec sh -c 'mv "$0" "$dest/$0"' {} \; -prune \) \
-o -exec sh -c '
if ! [ -e "$dest/$0" ]; then
mv -f "$0" "$dest/$0"
fi
' {} \;
Este segmento está lá fora há anos e ainda ocupa o primeiro lugar no google, então eu queria adicionar outro método. Como eu costumo fazer isso: empacotando o conteúdo do subdiretório em um tarball, movendo o tarball para o diretório pai e então extraí-lo com o comportamento padrão --overwrite. Isso faz exatamente o que você está procurando. Depois você pode remover seu subdiretório.
cd xyz
tar -cvzpf tmp.tar.gz *
mv tmp.tar.gz ../tmp.tar.gz
cd ..
tar -xvzpf tmp.tar.gz
rm -rf xyz
rm -f tmp.tar.gz
Se você tiver armazenamento suficiente, poderá fazê-lo da seguinte maneira:
mv -bfv directory_1/* directory_2/ # all duplicate source files/directories
# will have ~ appended to them
find -name "*~" -delete # will recursively find and delete all files
# with ~ on the end
Verifique se não há arquivos importantes com um ~ no final, mas se houver, você pode adicionar --suffix=whateveryouwant
em vez do padrão.
Tags command-line rename shell