Liste os arquivos temporários por valor numérico com um número maior que um nome de arquivo variado constantemente

2

Eu tenho um diretório tendo constantemente mudando nomes de arquivos (por valor numérico) listado como:

    -rw-rw----. 1 root root 10493952 May  7 10:39 A0000000.LOG
    -rw-rw----. 1 root root 10493952 May  7 08:38 A0000001.LOG
    -rw-rw----. 1 root root 10493952 May  7 08:38 A0000002.LOG
    ...
    ...
    -rw-rw----. 1 root root 10493952 May  7 08:38 A0000582.LOG
    ...
    and so on...

Agora, a qualquer momento, meu aplicativo exibe um nome de arquivo desses arquivos listados. Eu tenho que descartar esse arquivo e qualquer outro arquivo com maior valor numérico que esse arquivo de rsyncing para remotehost

Diga que o aplicativo lança o arquivo A0000096.LOG . E se eu ver o A0000097.LOG sendo criado também, eu faria:

rsync A* --exclude A0000096.LOG --exclude A0000097.LOG user@remoteHost:/somedir/
  • Pontos a serem observados:

    • O aplicativo lança um nome de arquivo diferente para a tarefa cron do rsync em execução a cada hora. Neste exemplo, o nome do arquivo é A0000096.LOG

    • Arquivos com valor numérico maior do que o nome do arquivo de saída do aplicativo ( A0000096.LOG no exemplo acima) podem ter a mesma data de criação / registro de data e hora como o nome do arquivo de saída do App

    • No momento em que o rsync é iniciado, o nome do arquivo de saída do App pode ter data / registro de data e hora alterados mais recentes do que arquivos com valor numérico mais alto.

    • Pode haver a possibilidade de que arquivos de valores numéricos mais altos não sejam criados ou possam ser criados mais do que apenas 1 (pode ser de 10 a 20)

Pergunta : Com essas restrições, não consigo encontrar como posso fornecer todos os arquivos de valores numéricos mais altos ao meu script bash do rsync para que eu possa excluí-los.

Qualquer ajuda é apreciada.

    
por Raman Kathpalia 27.08.2015 / 01:07

3 respostas

1

Se eu entendi a pergunta corretamente, você deseja rsync todos os arquivos no intervalo A0000000 a A0000095 . Bem, então, não diga A* ; use uma lista de curingas positivos (a.k.a. globs ou padrões de expansão de nome de arquivo) que geram os nomes dos arquivos que você deseja em vez de identificar os que você deseja excluir. Faça isso decompondo o intervalo em sub-intervalos:

         Subrange                         Wildcard
    A0000000-A0000089                 A00000[0-8][0-9]
    A0000090-A0000095                 A000009[0-5]

Então você diria

rsync A00000[0-8][0-9] A000009[0-5] user@remoteHost:/somedir/

Caso você tenha problemas para generalizar essa abordagem a partir de um exemplo, considere 97169.

         Subrange                           Wildcard
    A0000000-A0089999                 A00[0-8][0-9][0-9][0-9][0-9]
    A0090000-A0096999                 A009[0-6][0-9][0-9][0-9]
    A0097000-A0097099                 A00970[0-9][0-9]
    A0097100-A0097159                 A00971[0-5][0-9]
    A0097160-A0097168                 A009716[0-8]

É concebível que alguns desses curingas não corresponderá a nenhum arquivo existente. Nesse caso, faça

shopt -s nullglob

para dizer ao shell para ir em frente e executar o comando rsync com os wildcards com falha ignorados (isto é, expandidos para null).

    
por 27.08.2015 / 04:49
0

Como os números são preenchidos com zeros na mesma largura, a ordem numérica é idêntica à ordem lexicográfica. Portanto, seu problema é equivalente a remover os arquivos que começam com um determinado arquivo na ordem lexical.

Você pode fazer isso criando uma cadeia contendo os nomes de arquivos separados por novas linhas e usando a substituição de cadeia para remover o final da cadeia e, em seguida, confiando na expansão sem aspas para transformar a cadeia truncada novamente em uma lista. Eu suponho que não há novas linhas em nomes de arquivos e que seu shell é bash ou ksh (com sh simples, você precisa usar parâmetros posicionais em vez de um array nomeado).

nl=$'\n'                              # newline, we use it as a separator
cut_from=A0000096.LOG
log_files=(A???????.LOG)
set -f; IFS="$nl"                     # disable wildcard expansion and set the word separator to newline only
log_files="$nl${log_files[*]}$nl"     # turn the array into a string with newlines separating elements
log_files=(${log_files%"$nl$cut_from$nl"})    # remove elements from $cut_from onwards and split the string into an array
unset IFS; set +f
rsnyc -a "${log_files[@]}" … elsewhere:/some/dir
    
por 27.08.2015 / 02:12
0

Respondendo minha própria pergunta:

  CUT_LOG=A0000096.LOG        #Actually, Logic goes here to determine name of file. 

   LISTLOG='ls -1 /Source_Dir/A*.LOG | sed "/$CUT_LOG/,$ d"'       # Create a list that has only relevant entries 
                                                                   # sed deletes all lines starting from pattern matching line till the end.(here pattern=CUT_LOG) 

      rsync -a 'echo "${LISTLOG[@]}"' user@remoteHost:/somedir/    # This would be faster than using loop (explained next)

ou usando loop

        for line in 'echo "${LISTLOG[@]}"'; do                     # Recursively loop through the array and rsync each entry
                rsync -a $line user@remoteHost:/somedir/
        done
    
por 03.09.2015 / 00:45