Nesta aula, vamos explorar um dos recursos mais poderosos do Windows para automação: as tarefas agendadas. Com o PowerShell, você pode criar, modificar e monitorar tarefas agendadas de forma programática, o que é essencial para administradores de sistemas e desenvolvedores que precisam automatizar rotinas. Você aprenderá desde o básico, como registrar uma tarefa simples, até técnicas avançadas de agendamento e monitoramento.

As tarefas agendadas permitem executar scripts, programas ou comandos em horários específicos, em intervalos regulares ou em resposta a eventos do sistema. O PowerShell oferece cmdlets nativos que facilitam a criação e o gerenciamento dessas tarefas, integrando-se perfeitamente ao Agendador de Tarefas do Windows. Vamos mergulhar nos detalhes e exemplos práticos.

Register-ScheduledTask

O cmdlet Register-ScheduledTask é a porta de entrada para criar tarefas agendadas no PowerShell. Ele permite definir a ação a ser executada, o gatilho (quando executar) e as condições opcionais, como o usuário sob o qual a tarefa será executada. A sintaxe básica é:

Register-ScheduledTask -TaskName "MeuScript" -Action (New-ScheduledTaskAction -Execute "powershell.exe" -Argument "-File C:\Scripts\meuscript.ps1") -Trigger (New-ScheduledTaskTrigger -Daily -At "09:00")

Neste exemplo, criamos uma tarefa chamada "MeuScript" que executa o PowerShell com um script específico todos os dias às 9 horas. Observe que usamos New-ScheduledTaskAction para definir a ação e New-ScheduledTaskTrigger para o gatilho. É importante entender que o cmdlet aceita objetos de ação e gatilho, que podem ser combinados de várias maneiras para criar tarefas complexas.

Além de ações e gatilhos, você pode especificar o usuário que executará a tarefa, usando o parâmetro -User e -Password. Se a tarefa precisar ser executada com privilégios elevados, use -RunLevel Highest. A seguir, um exemplo com essas opções:

$action = New-ScheduledTaskAction -Execute "powershell.exe" -Argument "-File C:\Scripts\backup.ps1" -WorkingDirectory "C:\Scripts"
$trigger = New-ScheduledTaskTrigger -Weekly -DaysOfWeek Monday,Friday -At "02:00"
Register-ScheduledTask -TaskName "BackupSemanal" -Action $action -Trigger $trigger -User "DOMINIO\usuario" -Password "senha" -RunLevel Highest

Dessa forma, você pode criar tarefas robustas e personalizadas. Lembre-se de que, ao usar -User e -Password, a senha fica armazenada de forma insegura no registro; em cenários de produção, considere usar contas de serviço gerenciadas ou autenticação baseada em certificados.

Agendamento

O agendamento é o coração das tarefas agendadas. O PowerShell oferece o cmdlet New-ScheduledTaskTrigger para criar vários tipos de gatilhos: diário, semanal, mensal, em logon, em ociosidade e até mesmo em eventos específicos. Vamos explorar os principais:

  • Diário: New-ScheduledTaskTrigger -Daily -At "06:30" – executa todos os dias no horário especificado.
  • Semanal: New-ScheduledTaskTrigger -Weekly -DaysOfWeek Monday,Wednesday,Friday -At "09:00" – executa nos dias da semana escolhidos.
  • Mensal: New-ScheduledTaskTrigger -Monthly -DaysOfMonth 1,15 -At "03:00" – executa nos dias do mês especificados.
  • Em logon: New-ScheduledTaskTrigger -AtLogOn – executa sempre que o usuário faz logon.
  • Na inicialização: New-ScheduledTaskTrigger -AtStartup – executa quando o sistema é iniciado.

Além disso, você pode combinar gatilhos com repetições. Por exemplo, para executar uma tarefa a cada 30 minutos por um período de 2 horas:

$trigger = New-ScheduledTaskTrigger -Once -At (Get-Date) -RepetitionInterval (New-TimeSpan -Minutes 30) -RepetitionDuration (New-TimeSpan -Hours 2)
Register-ScheduledTask -TaskName "Repeticao" -Action $action -Trigger $trigger

É fundamental entender que o agendamento pode ser complexo, mas o PowerShell simplifica a criação de gatilhos com parâmetros nomeados. Sempre teste seus agendamentos em um ambiente controlado para garantir que eles se comportem como esperado.

Executando scripts

Uma das tarefas mais comuns é agendar a execução de scripts PowerShell. Isso é feito definindo a ação como powershell.exe e passando o script como argumento. No entanto, é importante considerar a política de execução do PowerShell, que pode bloquear scripts. Para evitar problemas, você pode usar o parâmetro -ExecutionPolicy Bypass no argumento:

$action = New-ScheduledTaskAction -Execute "powershell.exe" -Argument "-ExecutionPolicy Bypass -File C:\Scripts\meuscript.ps1"
Register-ScheduledTask -TaskName "ExecutarScript" -Action $action -Trigger $trigger

Além disso, você pode querer que o script seja executado em um diretório específico, usando -WorkingDirectory. Isso é útil se o script depende de arquivos relativos. Outra dica é redirecionar a saída para um arquivo de log, para monitorar a execução:

$action = New-ScheduledTaskAction -Execute "powershell.exe" -Argument "-ExecutionPolicy Bypass -File C:\Scripts\meuscript.ps1 *> C:\Logs\script.log"
Register-ScheduledTask -TaskName "ScriptComLog" -Action $action -Trigger $trigger

No exemplo acima, usamos *> para redirecionar todas as streams (saída, erro, aviso) para o arquivo de log. Isso é essencial para depuração e monitoramento. Lembre-se de que o caminho do log deve ter permissões de escrita para o usuário que executa a tarefa.

Outra consideração é que, ao agendar scripts, você pode querer que eles sejam executados mesmo se o usuário não estiver logado. Para isso, a tarefa deve ser registrada com as opções -User e -Password (ou usar uma conta de serviço). O Agendador de Tarefas cuidará de iniciar o processo em segundo plano.

Monitoramento

Depois de criar tarefas agendadas, é crucial monitorá-las para garantir que estão funcionando corretamente. O PowerShell oferece cmdlets para consultar e gerenciar tarefas existentes. O cmdlet Get-ScheduledTask lista todas as tarefas, e Get-ScheduledTaskInfo fornece informações detalhadas sobre a última execução, próxima execução e status.

Get-ScheduledTask -TaskName "MeuScript" | Get-ScheduledTaskInfo | Select-Object TaskName, LastRunTime, LastTaskResult, NextRunTime

O LastTaskResult é um código de status que indica se a execução foi bem-sucedida. Um valor 0 indica sucesso; outros valores podem indicar erros. Você pode verificar esses códigos para detectar falhas. Além disso, você pode habilitar o histórico de tarefas no Agendador de Tarefas para obter logs detalhados.

Outra técnica de monitoramento é criar uma tarefa que envia um e-mail ou escreve em um log quando outra tarefa falha. Isso pode ser feito usando um script que verifica o status e dispara uma notificação. Por exemplo:

$task = Get-ScheduledTask -TaskName "BackupSemanal"
$info = $task | Get-ScheduledTaskInfo
if ($info.LastTaskResult -ne 0) {
    Send-MailMessage -To "admin@empresa.com" -From "scheduler@empresa.com" -Subject "Falha na tarefa BackupSemanal" -SmtpServer "smtp.empresa.com" -Body "A tarefa falhou com código $($info.LastTaskResult)"
}

Esse script pode ser agendado para rodar periodicamente e verificar o status de todas as tarefas críticas. Também é possível usar o cmdlet Export-ScheduledTask para exportar a definição de uma tarefa em XML, facilitando o backup e a replicação em outros servidores.

Boas práticas

Ao trabalhar com tarefas agendadas no PowerShell, algumas boas práticas ajudam a evitar problemas: sempre teste a tarefa manualmente antes de agendar; use caminhos absolutos para scripts e arquivos; configure a política de execução de forma segura (evite Bypass em produção, se possível); monitore o status regularmente e implemente alertas para falhas; e documente suas tarefas para facilitar a manutenção.

Referências

Exercícios

  1. Exercício 1: Crie uma tarefa agendada chamada "ExercicioDiario" que execute o script C:\Scripts\diario.ps1 todos os dias às 8 horas da manhã, usando o PowerShell com política de execução Bypass.

    ✓ Resposta:
    $action = New-ScheduledTaskAction -Execute "powershell.exe" -Argument "-ExecutionPolicy Bypass -File C:\Scripts\diario.ps1"
    $trigger = New-ScheduledTaskTrigger -Daily -At "08:00"
    Register-ScheduledTask -TaskName "ExercicioDiario" -Action $action -Trigger $trigger
  2. Exercício 2: Crie uma tarefa que execute o script C:\Scripts\backup.ps1 toda segunda-feira e quinta-feira às 23:30, com privilégios elevados, usando o usuário atual (sem especificar senha).

    ✓ Resposta:
    $action = New-ScheduledTaskAction -Execute "powershell.exe" -Argument "-File C:\Scripts\backup.ps1"
    $trigger = New-ScheduledTaskTrigger -Weekly -DaysOfWeek Monday,Thursday -At "23:30"
    Register-ScheduledTask -TaskName "BackupSemanal" -Action $action -Trigger $trigger -RunLevel Highest
  3. Exercício 3: Escreva um script que verifique se a tarefa "BackupSemanal" foi executada com sucesso na última execução e exiba uma mensagem de alerta se o código de resultado não for 0.

    ✓ Resposta:
    $task = Get-ScheduledTask -TaskName "BackupSemanal"
    $info = $task | Get-ScheduledTaskInfo
    if ($info.LastTaskResult -ne 0) {
        Write-Host "ALERTA: A tarefa BackupSemanal falhou com código $($info.LastTaskResult)" -ForegroundColor Red
    } else {
        Write-Host "A tarefa BackupSemanal foi executada com sucesso."
    }
  4. Exercício 4: Crie uma tarefa que execute um script a cada 15 minutos por 1 hora, começando a partir de agora, usando um gatilho único com repetição.

    ✓ Resposta:
    $action = New-ScheduledTaskAction -Execute "powershell.exe" -Argument "-File C:\Scripts\monitor.ps1"
    $trigger = New-ScheduledTaskTrigger -Once -At (Get-Date) -RepetitionInterval (New-TimeSpan -Minutes 15) -RepetitionDuration (New-TimeSpan -Hours 1)
    Register-ScheduledTask -TaskName "Monitoramento" -Action $action -Trigger $trigger
  5. Exercício 5: Exporte a tarefa "ExercicioDiario" para um arquivo XML chamado exercicio.xml no diretório atual.

    ✓ Resposta:
    Export-ScheduledTask -TaskName "ExercicioDiario" | Out-File -FilePath "exercicio.xml"