Como copiar todos os arquivos em uma pasta, excluindo os arquivos que estão sendo gravados?

12

Eu faço o download de vários arquivos para uma pasta downloading via HTTPie . Um script bash tem como objetivo processar arquivos baixados, e eu tentei copiar os arquivos baixados para outra pasta como

find /folder/downloading -type f -exec mv '{}' /folder/downloaded \;

mas isso também copia os arquivos, que ainda não foram concluídos. Tentei limitar a transferência para arquivos mais antigos, adicionando -mmin +5 ao comando. Qual é o comando eficiente para deixar os arquivos sendo gravados e transferir apenas arquivos baixados?

    
por Googlebot 29.05.2017 / 16:47

1 resposta

11

Não é muito eficiente, mas você pode:

find /folder/downloading -type f -exec sh -c '
  for file do
    lsof -F a "$file" | grep -q w || mv "$file" /folder/downloaded
  done' sh {} +

Verifique se o arquivo não está listado com o modo de acesso w rite a em l i s t de o pen f iles antes de m o v ing.

A implementação psmisc de fuser normalmente encontrada em sistemas operacionais baseados em Linux tem uma função -w (para verificar se há arquivos abertos para gravação) mas infelizmente funciona apenas com -k para eliminar os processos correspondentes . No entanto, parece que você ainda pode usá-lo usando o pseudo-sinal 0 que não faz nada:

find /folder/downloading -type f -exec sh -c '
  for file do
    fuser -s -w -k -0 "$file"  || mv "$file" /folder/downloaded
  done' sh {} +

Remova o -s (ou substitua-o por -v ) se quiser ver que processo (es) está impedindo a mudança.

Observe que, se você não estiver executando esses comandos como superusuário, só receberá informações sobre seus processos. Se os processos de download dos arquivos estiverem sendo executados como um usuário diferente, eles permanecerão sem serem detectados.

Observe também que, a menos que você esteja movendo os arquivos para um sistema de arquivos diferente, mover os arquivos não impedirá que qualquer processo que esteja atualmente gravando no arquivo termine de gravar nele.

No entanto, dependendo do que eles foram projetados para fazer depois, eles podem ficar confusos se depois de terminarem de escrever, o arquivo não estiver mais lá (por exemplo, se eles quiserem alterar alguns atributos do arquivo depois de baixá-lo e faça isso não através do descritor de arquivo (como chmod() vs fchmod() , ou utimes() que não pode ser feito através de um descritor de arquivo)).

    
por 29.05.2017 / 17:06