Tar usando barra de progresso e manipulando multi-volumes

4

Estou tentando criar um tar de um grande volume LVM em várias unidades externas. Essa parte está resolvida. Agora, porque é um processo longo, eu gostaria de uma barra de progresso. Dos excelentes artigos aqui, cheguei perto.

O problema é que a barra PV é encerrada depois que o primeiro volume é preenchido. Eu gostaria de PV para continuar atualizando depois que os discos são trocados. Alguém tem uma ideia sobre como abordar isso?

Veja o que eu tentei. Eu acho que o problema está na última linha de código. Não tenho certeza se essa estratégia funcionará com vários volumes.

Código ExtBackup.sh:

#!/bin/sh

changedisk()
{
# This routine is called when tar runs out of disk space
# It simply waits for operator to change and mount disks
# then updates the file handle with a new volume number.
echo "Change disks now!" 
read -p "Press <enter> when new disk is mounted. ..." NULL
echo ""

# Update the file name with the new volume number
name='expr $TAR_ARCHIVE : '\(.*\)-.*''
echo ${name:-$TAR_ARCHIVE}-Vol$TAR_VOLUME.tar >&$TAR_FD
}

###########
## MAIN  ##
###########

# Test for recursive call to change disks
if [ "$1" = 'changedisk' ]; then 
        changedisk
        exit 0;
fi

# If this is initial call, set SIZE to calculate bytes in source    
SIZE='du -sb *Folder_Name* | cut -f 1'

# Now TAR it, using Multi-volume option and pipe through PV for progress bar
tar -cM -F 'sh ExtBackup.sh changedisk' *Folder_Name* | \
pv -s ${SIZE} > LVMBackup-$(date +%m-%d-%y)-Vol1.tar
    
por Glen Kauffman 08.11.2014 / 21:09

1 resposta

1

Tudo bem, levei algum tempo para entender o que o tar -F realmente faz (isso é documentado em qualquer lugar? Acabei de ler a fonte), mas acho que encontrei uma solução muito boa para você.

Como pv não suporta fingir que um certo progresso já foi feito, eu precisei substituí-lo por uma ferramenta similar chamada bar (disponível no Debian com esse nome, ou ver sua horrível homepage ).

A solução que encontrei passa os dados de todos os volumes adicionais por meio de um pipe nomeado (FIFO) para injetar a invocação bar no fluxo. Para evitar imprimir a barra de progresso de cada volume em uma nova linha, eu uso 'tput' para mover o cursor de volta após cada volume.

No seu código, você substituiria a última linha em changedisk() pelo seguinte. (Isso é um pouco hacky por questão de brevidade; basta personalizá-lo uma vez que você tenha a idéia)

tput cuu1 >&2 # clear previous progress bar
(cat somefifo | bar -ns \
    --size "$SIZE" \
    --completed $(((${TAR_VOLUME}-1)*${VOLSIZE})) \
    > ${name:-$TAR_ARCHIVE}-Vol$TAR_VOLUME.tar) &
echo somefifo >&$TAR_FD

E substitua a invocação pv na última linha do seu script por bar -ns --size ${SIZE} .

Para que isso funcione, você precisa colocar export na frente da definição SIZE e, é claro, ter executado mkfifo somefifo em algum momento antes. Certifique-se de também proteger os bits de permissão do FIFO. Você também pode considerar usar mktemp para criar um canal temporário com segurança. Depende do seu cenário, eu acho.

Eu usei uma variável ainda não definida $VOLSIZE que deve se expandir para o tamanho de seus volumes em bytes. Não tenho certeza de como isso é determinado em sua configuração. Talvez você precise fazer algo mais elaborado aqui, como acompanhar a soma cumulativa de todos os tamanhos de volume anteriores.

    
por 11.12.2014 / 20:22