Executa manualmente um cron job / simula um trabalho cron em execução? [duplicado]

13

Eu sou novo no cron e quero testar se o material de correspondência do cron após uma tarefa executada e coisas assim funcionam. Existe uma maneira mais elegante de testar isso e, em seguida, definir um cron job para executar a cada poucos segundos? Então, existe alguma maneira de simular a execução de um cron job / iniciar um cron job manualmente, mas com o mesmo comportamento que teria ao ser executado automaticamente pelo cron?

    
por stefan.at.wpf 28.09.2012 / 22:03

3 respostas

9

A principal diferença entre a execução de um cron job na linha de comando e dentro do cron é seu ambiente. Outras possíveis diferenças incluem o diretório atual, a disponibilidade de um terminal e qual shell é usado.

Esta é uma simulação bastante precisa da execução de um cron job via cron. Para evitar diferenças devido ao shell, coloque seu trabalho em um script e coloque apenas o caminho para esse script no crontab. Observe que o conjunto e os valores exatos das variáveis de ambiente transmitidas pelo cron dependem da implementação; verifique a página crontab(5) man no seu sistema. ifne é um comando que executa o comando especificado em argumentos se receber alguma entrada; há um em moreutils .

env -i HOME="$HOME" LOGNAME="$LOGNAME" PATH=/usr/bin:/bin SHELL=/bin/sh USER="$USER" \
    /path/to/script </dev/null 2>&1 |
ifne mail -r "Cron Daemon" -s "Cron <$USER@$(hostname)> /path/to/script" "$USER"

Outra maneira de criar uma configuração do tipo cron é através de at . Mas at cuida de executar o comando com as variáveis de ambiente que o processo at recebeu, portanto, você ainda precisa emular essa parte.

echo /path/to/script |
env -i HOME="$HOME" LOGNAME="$LOGNAME" PATH=/usr/bin:/bin SHELL=/bin/sh USER="$USER" \
    at now
    
por 29.09.2012 / 02:33
3

Veja como eu fiz isso para simular a execução do cron de um script que criei anos atrás, mas que começou a falhar recentemente.

Eu criei um script chamado dumpenv :

#!/bin/sh

base=$(basename $0)

env -0 > /tmp/$base.$$.dump

Isso despeja todas as variáveis de ambiente em um arquivo em /tmp/ . Então modifiquei meu crontab para adicionar:

*/1 * * * *  [path to newly created script]

Isso faz com que o script seja executado a cada minuto. Então, depois de um minuto, recebi um dump do ambiente visto pelas tarefas executadas no cron. Se a linha crontab for deixada em execução por mais de um minuto, ela criará um monte de arquivos idênticos com nomes que diferem apenas na parte pid do nome do arquivo ( $$ ). Não é nada demais. Eu poderia ter codificado para esta eventualidade de modo a obter apenas um arquivo, mas o principal princípio aqui é "bom o suficiente", e eu poderia querer usar dumpenv em outros contextos onde vários despejos são úteis. De qualquer forma, é aconselhável remover a linha crontab que foi adicionada para evitar o preenchimento de /tmp com muitos lixo.

Então eu criei um arquivo adicional que eu chamei de /tmp/command que continha o comando que eu queria executar, em uma única linha terminada por um caractere nulo. O caractere nulo é necessário.

Então eu publiquei:

cat [path to dumpfile crated earlier] /tmp/command | xargs -0 -x env -i

E isso replicou a falha que vi quando meu comando foi executado a partir do cron. O que xargs faz é criar um comando do formulário:

env -i [list of environment variables] [command to execute]

e executa. A lista de variáveis de ambiente vem do arquivo de despejo. O comando que env executa vem do arquivo /tmp/command .

Os argumentos -0 para env e xargs e o caractere nulo necessário que eu mencionei acima são para evitar a desconfiguração do ambiente enquanto as variáveis estão sendo passadas. Nos casos em que o ambiente não contém nenhuma variável de ambiente com uma nova linha, -0 poderia ser omitido da invocação de env no script dumpenv e do comando xargs , e o arquivo /tmp/command seria não requer um caractere nulo como um terminador de linha.

Eu não faço redirecionamento explícito de stdin para / dev / null porque xargs faz isso por mim. Eu também não me importo em redirecionar stdout / stderr, e não quero receber um email se o comando falhar. Para casos em que esses recursos são desejados, a resposta de Gilles fornece os meios para fazê-lo.

    
por 07.02.2013 / 17:13
1

A resposta de Louis é ótima. Eu proponho uma pequena melhora possível.

Em vez de criar um arquivo /tmp/command , que contém o caminho para o script que você deseja executar, como Louis sugeriu no código a seguir:

cat [path to dumpfile crated earlier] /tmp/command | xargs -0 -x env -i

Em vez disso, você pode nomear o script diretamente no comando por meio do seguinte comando alternativo (anote o \x00 anexado ao caminho do script cron, que é essencial:

printf "/path/to/cron/script\x00" | cat /path/to/dumpfile/created/earlier - | xargs -0 -x env -i

Isso evita qualquer necessidade de criar um arquivo /tmp/command .

    
por 19.08.2014 / 02:02

Tags