O que é uma boa estratégia para gerar e copiar arquivos atomicamente

5

Eu tenho um arquivo myfile que deve ser gerado periodicamente. A nova geração leva alguns segundos. Por outro lado, tenho que ler periodicamente o último (ou o último ao último) arquivo gerado. Qual é a melhor maneira de garantir que estou lendo um arquivo completamente gerado e que, assim que começar a lê-lo, poderei lê-lo completamente?

Uma possível solução é

  1. myfile é na verdade um link para o último arquivo gerado, digamos myfile.last .
  2. a regeneração é feita em um novo arquivo, digamos myfile.new
  3. após a regeneração, myfile.new é movido para myfile.last

O problema que vejo (e não sei a resposta) é: se outro script estiver copiando myfile enquanto o mv ocorre, o cp é concluído corretamente?

Outra possível solução seria gerar arquivos com um registro de data e hora em seu nome, por exemplo, myfile-2014-09-03_12:34 e myfile é novamente um link flexível para o último arquivo criado. Este link deve ser alterado após a criação para apontar para o novo arquivo. Novamente: quais são as chances de que algo como

cp myfile anotherfile

copia um arquivo corrompido?

    
por matiasg 04.09.2014 / 21:01

2 respostas

5

Se você está se movendo dentro do mesmo sistema de arquivos, mv é atômico - é apenas um renomear, não copiar o conteúdo. Então, se o último passo da sua geração for:

mv myfile.new myfile.last

Os processos de leitura sempre verão a versão antiga ou nova do arquivo, nunca algo incompleto.

    
por 04.09.2014 / 22:40
2

Você pode simplificar sua primeira solução proposta: regenere o arquivo em myfile.new e renomeie ( mv ) para myfile .

Se você estava substituindo myfile pelos novos dados, um leitor assíncrono poderia obter dados corrompidos (ou, pelo menos, incompletos) - mas você já sabe disso. Tenho certeza de que qualquer uma das suas soluções propostas estaria segura. Se outro processo abrir a versão 12:34 do arquivo às 12:38, então ele continuará tendo aquele arquivo aberto para leitura depois de renomear a versão 12:39 do arquivo para myfile , mesmo que não apareça mais em nenhum diretório. Isso é ainda mais claro no segundo caso, onde a versão 12:34 fica no diretório depois de alterar o link simbólico para apontar para o arquivo 12:39.

    
por 04.09.2014 / 23:06

Tags