Script de bash: monitore o hotfolder e arquivos parciais

3

Eu tenho um cliente que envia arquivos via FTP, eu fiz um script que basicamente monitora a pasta ftp e move o arquivo em uma máquina de produção. Como posso verificar se o arquivo foi completamente transferido do cliente através do ftp antes de iniciar meu comando scp para evitar a transferência de arquivos parciais?

    
por 0wn3r 24.02.2013 / 16:02

3 respostas

3

Se o seu sistema operacional oferecer suporte, você pode dar uma olhada em incrond . Os eventos que podem ser monitorados são definidos no incrontab Talvez o evento que você está procurando seja

IN_CLOSE_WRITE File opened for writing was closed (*)

ou em combinação com

IN_CREATE File/directory created in watched directory (*)

Note que

When monitoring a directory, ... the events above can occur for files in the directory, in which case the name field in the returned event data identifies the name of the file within the directory.

    
por 24.02.2013 / 16:17
4

Você não poderá fazer isso corretamente a partir do bash sem a ajuda do seu cliente.

No lado do servidor FTP, vários servidores FTP têm métodos para executar um programa assim que um upload é finalizado (poderia ter sido terminado ou o cliente poderia ter sido desconectado, o servidor FTP não tem como saber se realmente foi feito ou não).

Para fazer isso da maneira certa, a melhor solução é fazer com que o cliente carregue o arquivo com um nome temporário e renomeie o arquivo assim que terminar com o nome correto. Então você exclui todos os arquivos chamados "whatever.tmp" do processamento. Caso contrário, faça o cliente fazer o upload de um arquivo de bloqueio de zero bytes, faça o upload do arquivo real e, em seguida, exclua o arquivo de bloqueio. Você pode então verificar a existência do arquivo de bloqueio

filelist = ...
if [ -e /home/ftp/incoming/lockfile ]; then exit; fi
... process $filelist ...

Se o cliente carregar muito, o arquivo de bloqueio pode estar lá toda vez que você executar o script e nada for feito. Nesse caso, você terá que verificar os registros de data e hora dos arquivos em relação ao arquivo de bloqueio. Arquivos mais antigos que o arquivo de bloqueio devem estar completos:

for f in ...; do
    if [ ! -e /home/ftp/incoming/lockfile -o $f -ot /home/ftp/incoming/lockfile ]; then
         ... process $f
    fi
done

Se nem o seu servidor FTP nem o seu cliente participar com você, você pode fazer algo como

  1. crie uma lista de arquivos e arquivos.
  2. Compare esta lista com a lista anterior de arquivos
  3. processa os arquivos na lista atual que são idênticos aos arquivos da lista anterior
  4. salva a lista atual de arquivos na lista anterior
  5. aguarde 5 minutos e volte para 1.

Arquivos que não ficaram maiores em 5 minutos provavelmente estão prontos. Fazer isso em bash é deixado como um exercício para o leitor.

    
por 24.02.2013 / 16:21
2

A solução que eu uso (que não é à prova de balas, mas funcionou para mim 100% do tempo até agora) é consultar o tamanho do arquivo a cada 10 segundos, e se ele não mudou desde a última consulta, suponha que é feito e comece a transferência.

Com certeza, é possível que a rede tenha 10 + segundos segundos e que não tenha terminado de transferir tudo, mas isso é uma ocorrência bastante rara, e é para isso que os checksums como o MD5 servem.

    
por 24.02.2013 / 16:17