Como faço para esperar em um programa iniciado em outro shell

17

Eu tenho um programa que faz uma grande quantidade de trabalho (leva de 4 a 5 horas) que é iniciado pelo cron quando todos os dados com os quais ele trabalha ficam disponíveis. Às vezes, quando estou esperando que isso termine, gostaria de poder iniciar outro programa (interativo) quando terminar. a chamada de espera parece promissora, mas só espera crianças.

    
por hildred 05.12.2013 / 15:30

3 respostas

9

Definitivamente, prefiro a solução EDIT # 3 (veja abaixo).

se não estiver no mesmo shell, use um laço while com a condição em ps -p retornando true. Coloque um sleep no loop para reduzir o uso do processador.

while ps -p <pid> >/dev/null 2>&1
do
   sleep 10
done 

ou se o seu UNIX estiver suportando / proc (por exemplo, o HP-UX ainda não suporta).

while [[ -d /proc/<pid> ]]
do 
    sleep 10
done

Se você quiser um tempo limite

timeout=6  # timeout after 1mn  
while ((timeout > 0)) && ps -p <pid> >/dev/null 2>&1
do
   sleep 10
   ((timeout -= 1))
done 

EDIT # 1

Existe uma outra maneira: não use cron . Use o comando lote para empilhar seus trabalhos.

Por exemplo, você pode acumular diariamente todos os seus trabalhos. O lote pode ser ajustado para permitir algum paralelismo, portanto, um trabalho bloqueado não interromperá toda a pilha (depende do sistema operacional).

EDIT # 2

Crie um fifo no seu diretório pessoal:

$ mkfifo ~/tata

no final do seu trabalho:

echo "it's done" > ~/tata

no início do outro trabalho (aquele que está esperando):

cat ~/tata 

Não é polling que é um bom bloqueio IO.

EDIT # 3

Usando sinais:

No início do (s) script (s) que estão aguardando:

echo $$ >>~/WeAreStopped
kill -STOP $$

no final do seu longo trabalho:

if [[ -f ~/WeAreStopped ]] ; then
    xargs kill -CONT < ~/WeAreStopped
    rm ~/WeAreStopped
fi
    
por 05.12.2013 / 15:36
4

Você pode modificar seu cron job para usar algum sinalizador.

Em vez de

2  2 * * *           /path/my_binary

Você pode usar

2  2 * * *           touch /tmp/i_m_running; /path/my_binary; rm /tmp/i_m_running

E apenas monitore esse arquivo no script ou até mesmo manualmente. Se existir, seu programa está em execução; caso contrário sinta-se livre para fazer o que quiser.

O exemplo de script:

while [[ -f /tmp/i_m_running ]] ; do
   sleep 10 ;
done
launch_whatever_you_want

Caso você não goste de usar sleep , você pode modificar o script e executá-lo via cron uma vez por X minutos.

Nesse exemplo, o script de script será:

[[ -f /tmp/i_m_running ]] && { echo "Too early" ; exit ; }
launch_whatever_you_want

Desta forma é um pouco mais fácil, já que você não precisa encontrar o PID do seu processo cron.

    
por 05.12.2013 / 16:13
3

Não há nenhum recurso para um processo aguardar a conclusão de outro processo, exceto por um pai esperar que um de seus processos filhos seja concluído. Se você puder, inicie o programa através de um script:

do_large_amount_of_work
start_interactive_program

Se você não puder fazer isso, por exemplo, antes de começar a grande quantidade de trabalho de um cron job, mas o programa interativo do contexto de sua sessão, faça isso

do_large_amount_of_work
notify_completion

Existem várias maneiras de implementar notify_completion . Alguns ambientes de desktop fornecem um mecanismo de notificação ( Abrir uma janela em um display X remoto (por que" Não é possível abrir a tela ")? pode ser útil). Você também pode criar uma usando notificações de alteração de arquivo. No Linux, o recurso de notificação de alteração de arquivo é inotify .

do_large_amount_of_work
echo $? >/path/to/finished.stamp

Para reagir à criação de /path/to/finished.stamp :

inotifywait -e close_write -q /path/to/finished.stamp
start_interactive_program

Se você não pode alterar a maneira como do_large_amount_of_work é invocado, mas você sabe qual arquivo modifica por último, você pode usar o mesmo mecanismo para reagir quando esse arquivo é fechado. Você também pode reagir a outros eventos, como a renomeação de um arquivo (consulte o manual inotifywait para obter uma lista de possibilidades).

    
por 06.12.2013 / 03:20