Skip to content

Agendamento cron

Cron @reboot: rodar uma tarefa na inicialização

@reboot no lugar dos cinco campos de horário roda o comando uma vez quando o daemon do cron inicia, o que normalmente quer dizer uma vez por boot: @reboot /usr/local/bin/on-boot.sh. Não há expressão de horário, e os agendadores hospedados não têm equivalente.

Na inicialização (@reboot)
ExpressãoNão existe no cron padrão de 5 campos
Macro@reboot

Como funciona

O crontab(5) lista o @reboot junto com as outras macros, mas, ao contrário delas, ele não vira um horário. Ele dispara quando o próprio cron inicia. Num sistema normal isso acontece durante o boot, então a tarefa roda uma vez por inicialização.

Reiniciar só o daemon é onde as implementações divergem. O cronie grava um arquivo de trava na primeira vez que roda as tarefas @reboot e, nos reinícios seguintes do daemon, registra “@reboot jobs will be run at computer’s startup” e pula. Outros crons podem rodar de novo, então deixe o comando seguro para rodar duas vezes.

Como o cron sobe cedo e com um ambiente mínimo, tarefas @reboot costumam rodar antes da rede, das montagens remotas ou da sessão gráfica existirem. Em máquinas com systemd, um serviço oneshot com After=network-online.target é a alternativa confiável.

Próximas execuções

Não há o que calcular: o @reboot não tem campos de horário. Ele dispara uma vez a cada início do daemon do cron, o que num sistema normal significa uma vez por boot.

Versões prontas para colar

O mesmo agendamento em cada agendador, com o que muda em cada um.

crontab (Linux, macOS, BSD)

crontab -e
@reboot /usr/local/bin/on-boot.sh >> /var/log/on-boot.log 2>&1

# Crude wait for the network and mounts:
@reboot sleep 60 && /usr/local/bin/on-boot.sh
  • O @reboot roda quando o daemon do cron inicia. O cronie cria um arquivo de trava na primeira inicialização e pula as tarefas @reboot quando o daemon só é reiniciado (o log diz “@reboot jobs will be run at computer’s startup”).

GitHub Actions(Não suportado)

  • Não há equivalente: os runners são criados a cada job, então não existe um boot seu para usar.

CronJob do Kubernetes(Não suportado)

  • Não há equivalente em CronJob. Para algo no início do Pod, use um init container ou o próprio comando do contêiner; para uma vez por nó, um DaemonSet.

Cron Jobs da Vercel(Não suportado)

  • Não há equivalente: funções não têm evento de boot. Faça a preparação no build ou sob demanda na primeira requisição.

Cloudflare Workers(Não suportado)

  • Não há equivalente: Workers não têm um boot persistente. Use um passo de deploy no CI ou inicialize na primeira requisição.

node-cron (Node.js)

scheduler.js
import cron from 'node-cron';

// node-cron has no @reboot: just run it when the process starts,
// then schedule the recurring part.
await runOnStartup();

cron.schedule('0 3 * * *', runNightly);
  • Um processo Node “inicia” toda vez que sobe, inclusive quando o gerenciador de processos o reinicia, o que não é o mesmo que reiniciar a máquina.

Timer do systemd

on-boot.service
# /etc/systemd/system/on-boot.service
[Unit]
Description=Run once after boot
Wants=network-online.target
After=network-online.target

[Service]
Type=oneshot
ExecStart=/usr/local/bin/on-boot.sh

[Install]
WantedBy=multi-user.target

# Or a timer that fires a fixed time after boot:
# [Timer]
# OnBootSec=2min
  • Um serviço oneshot ordenado depois de network-online.target é o substituto confiável do @reboot: espera a rede e registra no journal. OnBootSec= num timer atrasa a execução por um tempo fixo depois do boot.

Spring @Scheduled e Quartz

Java
@EventListener(ApplicationReadyEvent.class)
public void onStartup() {
    // runs once when the application has started
}
  • O Spring não tem cron @reboot; o ApplicationReadyEvent dispara uma vez a cada início da aplicação. O Quartz também não tem gatilho de boot; um SimpleTrigger único na inicialização é o padrão comum.

Armadilhas

A rede pode não estar pronta

O cron pode subir antes do DHCP terminar ou das montagens NFS aparecerem. Uma tarefa @reboot que chama uma API ou grava num caminho montado falha de forma intermitente. sleep 60 && é a solução tosca; uma unit do systemd com o After= certo é a de verdade.

Ambiente mínimo

Tarefas do cron recebem um PATH curto (muitas vezes /usr/bin:/bin) e nenhum DISPLAY nem sessão de usuário. Use caminhos absolutos, defina as variáveis no script e não conte com programas gráficos.

Processos de longa duração

O @reboot inicia um processo mas não o supervisiona. Se ele cair, ninguém o reinicia. Para daemons, use um serviço do systemd com Restart=on-failure ou um orquestrador de contêineres.

Perguntas frequentes

O que o @reboot faz no crontab?
Roda o comando uma vez quando o daemon do cron inicia, o que num sistema normal quer dizer uma vez por boot. Ele substitui os cinco campos de horário.
O @reboot roda quando o cron é reiniciado?
Não no cronie: ele mantém um arquivo de trava e pula as tarefas @reboot quando só o daemon reinicia. Outras implementações podem rodar de novo, então a tarefa deve tolerar isso.
Por que meu cron @reboot não funciona?
Normalmente porque roda antes da rede ou das montagens estarem prontas, ou depende de PATH e variáveis de ambiente que o cron não define. Acrescente um atraso, use caminhos absolutos e grave a saída num arquivo de log.
Qual é o equivalente do @reboot no systemd?
Um serviço oneshot habilitado com WantedBy=multi-user.target, ou um timer com OnBootSec= para começar com atraso.

Revisado em por Arielton Oberek.