find: suprimir “Diretório não vazio”

2

Para excluir todos os arquivos e diretórios não ocultos que foram modificados pela última vez há mais de 2 semanas, estou usando:

find ~ -mindepth 1 -mtime +14 -name "[!.]*" -delete

Às vezes, isso imprimirá mensagens de erro "Diretório não vazio".

Gostaria de silenciar esses erros (à medida que sou notificado sobre eles quando executado como um cronjob), mas ainda gostaria que find apagasse os diretórios quando eles estivessem vazios e com mais de 2 semanas.

    
por AndreKR 04.10.2017 / 10:32

1 resposta

1

Se o seu find for compatível com as extensões -maxdepth e -delete não padrão, é provável que ele também ofereça suporte a -empty , para que você possa fazer isso:

find ~ -mindepth 1 -mtime +14 ! -name '.*' \( ! -type d -o -empty \) -delete

(isto é, apenas tente excluir diretórios que estão vazios)

Observe que -delete implica em -depth (o que você esperaria que você desejasse excluir um arquivo antes do diretório que o contém).

No entanto, a exclusão de um arquivo de um diretório atualiza o horário de modificação desse diretório. Isso significa que os diretórios não serão excluídos se contiverem arquivos antigos que foram excluídos com sucesso, mesmo que eles fossem antigos inicialmente.

Aqui, talvez você não queira excluir nenhum diretório:

find ~ -mtime +14 ! -name '.*' ! -type d -delete

Ou grave a lista de diretórios antigos antes de excluir qualquer arquivo, exclua os arquivos que não são de diretório e exclua os diretórios da lista gravada:

tmp=$(mktemp) &&
{
  rm -f -- "$tmp"
  find ~ -depth -mindepth 1 ! -name '.*' -mtime +14 -type d -print0 >&3
  find ~ -mtime +14 ! -name '.*' ! -type d -delete
  xargs -r0 rmdir <&4 2> /dev/null
} 3> "$tmp" 4< "$tmp"

Ou usando moreutils sponge (embora isso signifique armazenar toda a lista de arquivos na memória):

 find ~ -depth -mindepth 1 ! -name '.*' -mtime +14 -type d -print0 |
   sponge sh -c '
     find ~ -mtime +14 ! -name ".*" ! -type d -delete
     xargs -r0 rmdir'

Ou zsh ' =(...) forma de substituição de processo:

{
  find ~ -mtime +14 ! -name ".*" ! -type d -delete
  xargs -r0 rmdir
} < =(find ~ -depth -mindepth 1 ! -name '.*' -mtime +14 -type d -print0)

Ou você pode excluir todos os diretórios vazios, independentemente de serem antigos ou não:

find ~ -mindepth 1 ! -name '.*' \( -mtime +14 ! -type d -o -type d -empty \) -delete
    
por 04.10.2017 / 10:40

Tags