Como faço para remover recursivamente subdiretórios e arquivos, mas não o primeiro diretório pai?

10

Eu sou capaz de usar o seguinte para remover o diretório de destino e recursivamente todos os seus subdiretórios e conteúdos.

find '/target/directory/' -type d -name '*' -print0 | xargs -0 rm -rf

No entanto, não quero que o diretório de destino seja removido. Como posso remover apenas os arquivos no destino, os subdiretórios e seu conteúdo?

Michael Prescott
fonte

Respostas:

11

A resposta anterior está quase correta. No entanto, você não deve citar o caracteres glob glob se você quer que eles funcionem. Então, este é o comando que você está procurando:

rm -rf "/target/directory with spaces/"*

Note que o * está fora das aspas duplas. Este formulário também funcionaria:

rm -rf /target/directory\ with\ spaces/*

Se você tem o * entre aspas, como mostrado acima, então ele tentará apenas remover o arquivo único literalmente chamado * dentro do diretório de destino.

pioto
fonte
1
Isso não funciona com arquivos e pastas ocultos. Eu tive que fazer mais uma vez com um
The Unfun Cat
7

Mais três opções.

  1. Usar find com -mindepth 1 e -delete:

    −mindepth levels
    Não aplique nenhum teste ou ação em níveis menores que os níveis (um inteiro não negativo).
    −mindepth 1 significa processar todos os arquivos, exceto os argumentos da linha de comando.

    -excluir
    Deletar arquivos; true se a remoção foi bem-sucedida. Se a remoção falhar, uma mensagem de erro será emitida.   Se −elelete falhar, o status de saída do Find será diferente de zero (quando finalmente sair). Uso de   −delete ativa automaticamente a opção −depth.
    Teste cuidadosamente com a opção -depth antes de usar esta opção.

    # optimal?
    # -xdev      don't follow links to other filesystems
    find '/target/dir with spaces/' -xdev -mindepth 1 -delete
    
    # Sergey's version
    # -xdev      don't follow links to other filesystems
    # -depth    process depth-first not breadth-first
    find '/target/dir with spaces/' -xdev -depth -mindepth1 -exec rm -rf {} \;
    



2. Use find, mas com arquivos, não diretórios. Isso evita a necessidade de rm -rf:

    # delete all the files;
    find '/target/dir with spaces/' -type f -exec rm {} \;

    # then get all the dirs but parent
    find '/target/dir with spaces/' -mindepth 1 -depth -type d -exec rmdir {} \;

    # near-equivalent, slightly easier for new users to remember
    find '/target/dir with spaces/' -type f -print0 | xargs -0 rm
    find '/target/dir with spaces/' -mindepth 1 -depth -type d -print0 | xargs -0 rmdir



3. Vá em frente e remova o diretório pai, mas recrie-o. Você poderia criar uma função bash para fazer isso com um comando; aqui está um simples one-liner:

    rm -rf '/target/dir with spaces' ; mkdir '/target/dir with spaces'
quack quixote
fonte
2

E se

rm -rf /target/directory\ path/*

Se houver arquivos começando com. no diretório de destino.

rm -rf "/target/directory path/*" "/target/directory path/.??*"

Este segundo vai combinar tudo começando com um., Exceto. e .. Ele falhará em nomes como .a, mas isso não é muito comum. Pode ser ajustado, se necessário, para cobrir todos os casos.

KeithB
fonte
Eu tentei os dois e eles não funcionam para mim. Talvez seja porque meu caminho de diretório de destino tem espaços nele? rm -rf '/ target / caminho do diretório / *' Não dá erro, mas os subdiretórios permanecem.
Michael Prescott
Você precisa escapar dos espaços, com uma barra invertida (\) antes do espaço, ou colocando o nome do diretório inteiro entre aspas ("). Eu editei os exemplos para mostrar isso.
KeithB
Obrigado, eu tentei isso como mostrado no meu comentário anterior e ainda não ir. (Estou usando o OS X, isso importa?)
Michael Prescott
OS X deve funcionar bem, é isso que estou usando. Certifique-se de não usar as barras invertidas e aspas. Apenas um ou outro.
KeithB
Sim, apenas usando as aspas. Se eu remover o * e por isso estou usando apenas rm -rf "/ target / directory path /" o diretório "directory path" será removido junto com os subdiretórios "directory path". Se eu usar o rm -rf "/ target / directory path / *", nada acontece.
Michael Prescott
2
find /target/directory/ -xdev -depth -mindepth 1 -exec rm -Rf {} \;
Sergey
fonte