Как отключить запланированное задание с помощью Powershell?

8

У меня есть веб-приложение, которое работает на Windows Server 2008 R2, в котором есть большое количество запланированных задач, которые позаботятся обо всех вещах бэкэнда. Когда я делаю развертывание программного обеспечения, которое касается базы данных, мне нужно отключить все запланированные задачи. В настоящее время у меня есть длинный контрольный список, который мне нужно пройти вручную, отключая каждую запланированную задачу по ходу дела - это, безусловно, работа для автоматизации с Powershell.

К сожалению, документация Powershell, кажется, довольно нелицеприятна о том, как отключить существующее запланированное задание (и, конечно же, повторно включить его после успешного завершения выпуска). Я могу получить список готовых, запущенных или отключенных задач, но что дальше?

Дэвид Кивини
источник

Ответы:

14

Вы можете использовать объекты сценариев планировщика заданий на основе COM :

($TaskScheduler = New-Object -ComObject Schedule.Service).Connect("localhost")
$MyTask = $TaskScheduler.GetFolder('\').GetTask("My Task")
$MyTask.Enabled = $false

Чтобы снова включить задачу:

$MyTask.Enabled = $true

Вышеуказанное будет работать только в том случае, если установлена ​​повышенная оболочка, и вы являетесь локальным администратором на сервере. Вы можете создать свой собственный командлет с помощью приведенного выше:

function Disable-ScheduledTask
{
    param([string]$TaskName,
          [string]$ComputerName = "localhost"
         )

    $TaskScheduler = New-Object -ComObject Schedule.Service
    $TaskScheduler.Connect($ComputerName)
    $TaskRootFolder = $TaskScheduler.GetFolder('\')
    $Task = $TaskRootFolder.GetTask($TaskName)
    if(-not $?)
    {
        Write-Error "Task $TaskName not found on $ComputerName"
        return
    }
    $Task.Enabled = $False
}
Матиас Р. Ессен
источник
2
Примечание: это не работает для задач, созданных с помощью at.exe. (Пример:) AT 09:00 /every:SUNDAY shutdown.exe /r /f /d p:4:1 /c "Reboot via SchTask (AT Job)". Вы получите ошибку 0x80041327; Задача имеет свойства, которые не совместимы с предыдущими версиями Windows
Signal15 26.02.15
5

Если вы просто пытаетесь остановить ВСЕ задачи, может быть проще просто остановить службу планировщика задач. Модуль ScheduledTasks недоступен до Windows Server 2012, поэтому управление задачами не так просто, как остановка и запуск службы:

Stop-Service Schedule
Start-Service Schedule

Если это не сработает, вы можете использовать schtasks.exe из PowerShell для управления отдельными задачами:

schtasks.exe /CHANGE /TN "My Task" /DISABLE
schtasks.exe /CHANGE /TN "My Task" /ENABLE
Тим Феррилл
источник
1
Начиная с 2008 / Vista и далее, сама Windows активно использует планировщик задач для широкого спектра системных задач. В зависимости от продолжительности остановки службы планировщика заданий не может быть такой прекрасной идеей (хотя это легко).
Матиас Р. Йессен
Конечно. Данный вариант использования был для отключения задач во время обслуживания, так что это может быть жизнеспособным вариантом. Также дали второй вариант на случай, если это не удовлетворит потребности.
Тим Феррилл
3

Еще лучший способ, когда вам не нужно указывать имена задач:

($TaskScheduler = New-Object -ComObject Schedule.Service).Connect("localhost")
$TaskScheduler.GetFolder('\').GetTasks(0) | % {$_.Enabled = $false}
Димитрий
источник
0

Это потрясающе! Он работает лучше, чем Get-ScheduledTask, так как я нахожусь в смешанной среде 2008/2012. Я добавил несколько строк для запроса AD и вызова этой команды для группы компьютеров. Моей целью было отключить задачу «Диспетчер серверов» при каждом входе пользователя в систему. Presto! все ушли!

$C=Get-ADComputer -SearchBase 'OU=Computers,dc=domain,dc=com' -Filter * | foreach {$_.name}

Invoke-Command $C {
($TaskScheduler = New-Object -ComObject Schedule.Service).Connect("$C")
$TaskScheduler.GetFolder('\Microsoft\Windows\Folder').GetTasks(0) | % {$_.Enabled = $false}
}
hans57sauc
источник
0

Посмотрите на эту функцию

Function Control-Tasks
{
    [CmdletBinding()]
    Param
    (
        [Parameter(Mandatory=$true)][String]$FolderPath,
        [Parameter(Mandatory=$true, ParameterSetname='EnableTask')][Switch]$Enable,
        [Parameter(Mandatory=$true, ParameterSetname='DisableTask')][Switch]$Disable,
        [Parameter()]$TaskScheduler,
        [Parameter()][Switch]$Recursive
    )

    If ($TaskScheduler -eq $null) {
        $TaskScheduler = New-Object -ComObject Schedule.Service
        $TaskScheduler.Connect("localhost")
    }

    $curFolder = $TaskScheduler.GetFolder($FolderPath)

    $curFolder.GetTasks(1) | ForEach-Object {
        If ($Enable) {
            $_.Enabled = $True
            Write-Host "Enable $($_.Path)"
        }

        If ($Disable) {
            $_.Enabled = $False
            Write-Host "Disable $($_.Path)"
        }
    }

    If ($Recursive) {
        $curFolder.GetFolders(1)  | ForEach-Object {
            If ($Enable) {
                Control-Tasks -FolderPath $_.Path -Enable -TaskScheduler $TaskScheduler -Recursive
            }
            If ($Disable) {
                Control-Tasks -FolderPath $_.Path -Disable -TaskScheduler $TaskScheduler -Recursive
            }
        }
    }

}

Например, вы можете отключить все задачи в папке "\ mysql", вызвав Control-Tasks -FolderPath "\mysql" -Disable -Recursive

Фрагменты этого кода приведены в разделе Как отключить / включить запланированное задание в пакетном режиме с помощью PowerShell , вы можете загрузить полный образец архива там.

Эрик
источник
0

это сработало для меня

    Get-ScheduledTask -TaskName "TestJob"  | Stop-ScheduledTask
Саад Эльшазлы
источник