Получение контроля над системными службами на неподатливых виртуальных машинах

Опубликовано: 17 Апреля, 2023
Получение контроля над системными службами на неподатливых виртуальных машинах

Одна из проблем, с которой я долгое время сталкивался в своей среде Hyper-V, — это виртуальные машины, которые отказываются запускать определенные системные службы во время загрузки виртуальной машины. Я не говорю об ошибках, связанных с диспетчером управления службами на виртуальной машине, которая страдает от проблем. Я говорю об исправной виртуальной машине, службы которой не запускаются автоматически.

Ускоренный курс по системным службам

Операционная система Windows использует ряд различных системных служб, многие из которых предназначены для автоматического запуска во время загрузки операционной системы. Многие сторонние приложения также используют службы, которые обычно также запускаются при загрузке операционной системы.

Службы отображаются через диспетчер управления службами. Вы можете получить доступ к диспетчеру управления службами, введя Services.msc в командной строке сервера. Вы можете увидеть, как это выглядит на рисунке ниже.

Изображение 14539
Любая служба, тип запуска которой установлен на автоматический, должна запускаться автоматически при загрузке виртуальной машины. У меня не было проблем со службами операционной системы, но я обнаружил, что когда виртуальная машина работает на старом (медленном) оборудовании, службы, специфичные для приложений, очень часто не запускаются автоматически.

Честно говоря, запустить эти службы вручную не так уж и сложно. Вы можете просто открыть Диспетчер управления службами, щелкнуть правой кнопкой мыши службу и выбрать команду «Пуск» в контекстном меню. Это почти всегда заставляет службу запускаться. Тем не менее, каждый раз, когда вы загружаете виртуальную машину, приходится идти и проверять, какие службы запущены, а какие нет.

Запуск упрямых сервисов

Один из способов обойти эту проблему — создать сценарий PowerShell, предназначенный для запуска служб, которые обычно не запускаются сами по себе. Я буду первым, кто признает, что это временное решение, но оно работает. Если службы не запускаются автоматически, как предполагалось, то, на мой взгляд, использование автоматизированного сценария для запуска служб является лучшим решением, чем проверка каждой службы вручную.

Когда дело доходит до использования PowerShell для запуска служб, которые должны были запускаться автоматически, но не запустились, вы можете придумать что угодно. Вы можете даже создать сценарий, содержащий специальные функции для каждой службы, и сделать так, чтобы сценарий не переходил к следующей функции до тех пор, пока не запустится служба текущей функции. Этот подход хорошо работает, если у вас сложный набор зависимостей и вам нужно быть на 100% уверенным, что каждый сервис запускается каждый раз. Однако в большинстве случаев гораздо более простой сценарий будет работать так же хорошо.

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

Первая из этих команд представляет собой временную задержку. Вы не хотите, чтобы ваш скрипт инициировал команду для запуска первой службы, а затем выполнял оставшиеся команды до того, как служба даже успела запуститься. Мне нравится использовать для этого команду Start-Sleep. Команда Start-Sleep инициирует временную задержку на указанный вами период. Например, если вам нужна 10-секундная задержка, тогда команда будет такой:

Start-Sleep -S 10

Второй тип команды, которая потребуется, — это команда, которая фактически запускает службу. Имя команды, которую вам нужно будет использовать, — Start-Service. Вот очень простой пример использования этой команды:

Start-Service -Name "eventlog"

В этом случае я использую командлет Start-Service для запуска службы Eventlog. Это, однако, поднимает важный момент. Когда вы используете PowerShell для запуска службы, вам нужно знать имя службы, которую вы хотите запустить. Самый простой способ получить имя службы — открыть окно PowerShell и ввести командлет Get-Service.

Когда вы вводите командлет Get-Service сам по себе, командлет возвращает три элемента информации: имя службы, состояние службы и описание службы. Имя, отображаемое командлетом Get-Service, — это имя, которое вы будете использовать с командлетом Start-Service.

Список системных служб, возвращаемых командлетом Get-Service, может быть довольно длинным, но есть несколько способов сократить его. Если, например, вы хотите увидеть список остановленных служб, вы можете ввести;

Get-Service | Where {$_.Status -eq ‘Stopped’}

Проблема с результирующим списком заключается в том, что не каждая отображаемая служба настроена на автоматический запуск. Если вы хотите увидеть службы с автоматическим типом запуска, которые не запущены, вы можете использовать эту команду:

Get-Service | Where {$_.StartType-eq "Automatic" -and $_.Status -eq "Stopped"} | Select-Object Name, StartType, Status

Вы можете увидеть, как это выглядит на рисунке ниже:

С помощью командлетов Start-Sleep и Start-Service можно создать сценарий, который может запускать службы, которые обычно не запускаются сами по себе. Конечно, единственное, чего по-прежнему не хватает, — это механизма запуска скрипта. Вы можете войти в систему, открыть окно PowerShell и запустить сценарий вручную, но это не намного эффективнее, чем запуск отказавших служб вручную.

Существует несколько различных способов принудительного запуска сценария PowerShell. Например, вы можете настроить планировщик заданий Windows для периодического запуска вашего сценария или настроить сценарий для выполнения в качестве элемента автозагрузки.