Войти

Показать полную графическую версию : [решено] Скрипт мониторинга службы или порта


Страниц : [1] 2

bombording
25-10-2011, 13:22
Добрый день.
Имеется некая служба (она так же имеет свой порт и свой процесс), которая иногда зависает...
Требуется скрипт, который будет запускаться каждую минуту, и будет мониторить эту службу\порт. И если он не будет получать ответ от службы на протяжении, скажем 2-3 секунд, последует команда на перезапуск службы.

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

Помогите пожалуйста в написании данного скрипта.
Спасибо.

El Sanchez
25-10-2011, 15:10
bombording, если служба присутствует в оснастке services.msc, то в свойствах службы на вкладке Восстановление можно указать действия при сбоях. Если нет, то то же самое через комстроку: sc failure (http://technet.microsoft.com/ru-ru/library/cc742019(WS.10).aspx).

bombording
25-10-2011, 16:29
El Sanchez, спасибо за наводку на sc failure. Я сейчас знакомлюсь с синтаксисом.
Я так понял у данной комманды нет рассписания выполнения и её нужно ставить на выполнение в планировщик?

El Sanchez
25-10-2011, 16:49
её нужно ставить на выполнение в планировщик »
Это просто команда настройки службы, выполняется 1 раз. А там уже все будет зависеть от самой службы и ее взаимодействия с SCM.

bombording
26-10-2011, 09:42
El Sanchez, понятно.
Тоесть если я хочу, что бы служба в случае недоступности в течении 20 секунд, перезапускалась автоматически. Я должен выполнить ?? :

sc failure msftpsvc reset= 20 actions= restart/5000

И как быть, к примеру, если мне нужно что бы служба была выключена в 2 часа ночи на время архивации. Не запустится ли она автоматически после выключения??

Iska
26-10-2011, 11:42
bombording, всё упирается в определение, что Вы подразумеваете под: «некая служба, … которая иногда зависает...» и «служба в случае недоступности…». Как Вы определяете. что она «зависает» и что она «недоступна»?

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

Я чую, Вам надо почитать что-нибудь по службам: что это такое, как работает, как с ними взаимодействовать.

El Sanchez
26-10-2011, 11:56
Тоесть если я хочу, что бы служба в случае недоступности в течении 20 секунд, перезапускалась автоматически. Я должен выполнить ?? »
bombording, параметр reset определяет через сколько секунд беспербойной работы службы счетчик ошибок сбрасывается в 0 и этот период должен быть гораздо больше, чем 20 с. Сбрасывайте через несколько часов или раз в сутки.
А в actions у вас записано: при первом сбое рестарт службы с задержкой в 5 с., можно дописать еще действия для второго сбоя и последующих.

если мне нужно что бы служба была выключена в 2 часа ночи на время архивации. Не запустится ли она автоматически после выключения?? »
Ну и останавливайте по расписанию через планировщик. Остановленная служба - нормальное состояние, а не ошибочное.

bombording
26-10-2011, 14:16
Iska,
Вообщем ситуация такая. Имеется сервер баз данных "Первасив" он имеет две службы и 1 процесс.
Иногда, пользователи с привилегиями могут создать в базе данных такой запрос... который выводит из строя базу данных.

Под выводом из строя подразумевается то что процесс сервера баз данных убивается. Службы при этом находятся в состоянии Started.

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

Сейчас стоит задача отслеживать падение базы данных и перезапускать службы в случае выхода из строя базы.

El Sanchez,
А если мне необходимо одно действие на все сбои службы.
И непонятно, как sc failure определяет ошибочное состояние, если службы находятся в состоянии Started при сбое.

Iska
26-10-2011, 20:42
И непонятно, как sc failure определяет ошибочное состояние, если службы находятся в состоянии Started при сбое. »
Это и есть главный вопрос: как Вы определяете, что нужен перезапуск служб?

bombording
27-10-2011, 09:54
Iska, когда пропадает процесс(предположим base.exe) сервера базы данных. Ну и следовательно в саму базу данный зайти нельзя. Привсём при этом службы находятся в состоянии Started, но сам сервер баз данных в дауне.

Iska
27-10-2011, 16:22
bombording, давайте уточним общую картину — правильно ли я понял:

1. Сервер баз данных состоит из двух служб [приведите их имена, пути к исполняемым файлам, командные строки процессов, их реализующих, и зависимости других служб от данных служб] и процесса «base.exe» [он существует в единственном экземпляре? В каком контексте он запускается изначально? Приведите путь к исполняемому файлу «base.exe», командную строку процесса].

2. Визуальным основанием для перезапуска служб является аварийное завершение процесса «base.exe». Для восстановления работоспособности сервера баз данных достаточно перезапустить обе службы [очерёдность перезапуска важна?]. После перезапуска служб, процесс «base.exe» стартует автоматически [его запускает какая-то из служб?].

bombording
28-10-2011, 10:06
Iska,

Общая картина верна. Вот описание служб.

Pervasive.SQL 2000 (relational)
Путь к исп. файлу: "C:\PVSW\BIN\W3SQLMGR.EXE" (данный файл так же висит в процессах.)
Зависимостей нет

Pervasive.SQL 2000 (transactional)
Путь к исп. файлу: "C:\PVSW\BIN\NTBTRV.EXE" (данный файл так же висит в процессах.)
Зависимостей нет

Командной строки, как я понял у данных служб нет.

Теперь по процессу:
Процесс base.exe существует в единственном экземпляре и находится в C:\PVSW\Bin. Данный процесс запускается службой Pervasive.SQL 2000 (transactional). Запускается автоматически.

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

Впринципе всё.
Я так же пробовал задавать в свойствах служб режим восстановления в виде рестарта службы. Но при падении base.exe они не перезапускаются, а вот при аварийном завершении своих исполняемых файлов, служба перезапускается.

Iska
28-10-2011, 16:02
bombording:

1. Какие имена у этих служб?
wmic.exe service get name

2. Важен ли порядок, в котором будут перезапускаться службы?

Update:
3. Может быть вопрос п.2 излишен — достаточным ли будет для восстановления работоспособности сервера баз данных перезапуск только службы «Pervasive.SQL 2000 (transactional)»?

bombording
28-10-2011, 16:48
Iska,

1. службы так и называются.

2. Не важен порядок.

3. Да, для восстановления работоспособности сервера баз данных достаточно перезапустить только Pervasive.SQL 2000 (transactional)

Iska
29-10-2011, 05:07
bombording, попробуйте так (запускать под «cscript.exe»):
Option Explicit

Dim strProcessName
Dim strServiceNamePrimary
Dim strServiceNameSecondary

Dim strComputer

Dim objSWbemLocator
Dim objSWbemServicesEx
Dim objSWbemEventSource

Dim objSWbemObjectEx_ServicePrimary
Dim objSWbemObjectEx_ServiceSecondary

Dim collSWbemObjectSet


strProcessName = "base.exe" ' "notepad.exe"
strServiceNamePrimary = "Pervasive.SQL 2000 (transactional)" ' "aspnet_state"
strServiceNameSecondary = "Pervasive.SQL 2000 (relational)" ' "SwPrv"


strComputer = "."

Set objSWbemLocator = WScript.CreateObject("WbemScripting.SWbemLocator")
Set objSWbemServicesEx = objSWbemLocator.ConnectServer(strComputer, "root\cimv2")
Set collSWbemObjectSet = objSWbemServicesEx.ExecQuery("SELECT Name FROM Win32_Service WHERE Name = '" & strServiceNamePrimary & "'")

If collSWbemObjectSet.Count = 1 Then
Set objSWbemObjectEx_ServicePrimary = objSWbemServicesEx.Get("Win32_Service.Name='" & strServiceNamePrimary & "'")
Set objSWbemObjectEx_ServiceSecondary = objSWbemServicesEx.Get("Win32_Service.Name='" & strServiceNameSecondary & "'")

WScript.StdOut.Write "Скрипт ожидает выполнения условий для начала работы..."

Do
objSWbemObjectEx_ServicePrimary.Refresh_
objSWbemObjectEx_ServiceSecondary.Refresh_

Set collSWbemObjectSet = objSWbemServicesEx.ExecQuery("SELECT Name FROM Win32_Process WHERE Name = '" & strProcessName & "'")

If objSWbemObjectEx_ServicePrimary.Started And _
objSWbemObjectEx_ServiceSecondary.Started And _
collSWbemObjectSet.Count > 0 Then

WScript.StdOut.WriteLine " Условия выполнены"

Exit Do
Else
WScript.Sleep 100
End If
Loop

WScript.StdOut.WriteLine "Скрипт работает"

Set objSWbemObjectEx_ServicePrimary = objSWbemServicesEx.Get("Win32_Service.Name='" & strServiceNamePrimary & "'")
Set objSWbemObjectEx_ServiceSecondary = objSWbemServicesEx.Get("Win32_Service.Name='" & strServiceNameSecondary & "'")

Set objSWbemEventSource = objSWbemServicesEx.ExecNotificationQuery( _
"SELECT * FROM __InstanceDeletionEvent " & _
"WITHIN 1 WHERE TargetInstance ISA 'Win32_Process' AND " & _
"TargetInstance.Name = '" & strProcessName & "'")

Do
With objSWbemEventSource.NextEvent.TargetInstance
WScript.StdOut.WriteLine "Процесс [" & .Name & "] (PID: " & CStr(.ProcessID) & ") был остановлен"
End With

With objSWbemObjectEx_ServicePrimary
WScript.StdOut.WriteLine "Служба [" & .Name & "] (PID: " & CStr(.ProcessId) & ")"

.Refresh_

If .Started Then
WScript.StdOut.Write " Служба останавливается"

If .StopService() = 0 Then
Do
WScript.Sleep 100
WScript.StdOut.Write "."

.Refresh_
Loop While .Started

WScript.StdOut.WriteLine
Else
WScript.StdOut.WriteLine "Невозможно остановить службу"
End If
End If

WScript.StdOut.Write " Служба запускается"

If .StartService() = 0 Then
Do
WScript.Sleep 100
WScript.StdOut.Write "."

.Refresh_
Loop Until .Started

WScript.StdOut.WriteLine
Else
WScript.StdOut.WriteLine "Невозможно запустить службу"
End If
End With
Loop
Else
WScript.StdOut.WriteLine "Служба [" & strServiceNamePrimary & "] не установлена"
End If

WScript.Quit 0

В комментариях скрипта — то, на чём я тренировался. Примерный вывод скрипта:
Скрипт ожидает выполнения условий для начала работы... Условия выполнены
Скрипт работает
Процесс [notepad.exe] (PID: 22884) был остановлен
Служба [aspnet_state] (PID: 18568)
Служба останавливается............................
Служба запускается.
Процесс [notepad.exe] (PID: 22988) был остановлен
Служба [aspnet_state] (PID: 22940)
Служба останавливается..................
Служба запускается.
«Блокнот» я, разумеется, запускал сам, имитируя службу «Pervasive.SQL 2000 (transactional)».

bombording
30-10-2011, 15:57
Iska, Спасибо большое. Всё работает.

Единственное не хватает условия что бы при корректном выключении службы (например на время архивации), скрипт не перезапускал службу Pervasive.SQL 2000 (transactional).

К примеру можно ли сделать так, что бы скрипт проверял:

1. Если служба Pervasive.SQL 2000 (transactional) запущена а процесс base.exe нет - значит произошёл сбой и необходимо перезапустить Pervasive.SQL 2000 (transactional)
2. Если служба Pervasive.SQL 2000 (transactional) остановлена и процесса base.exe нет - значит сбоя нет и служба просто остановлена, перезапуск не нужен

Iska
30-10-2011, 16:21
Единственное не хватает условия что бы при корректном выключении службы (например на время архивации), скрипт не перезапускал службу Pervasive.SQL 2000 (transactional).
К примеру можно ли сделать так, что бы скрипт проверял:
1. Если служба Pervasive.SQL 2000 (transactional) запущена а процесс base.exe нет - значит произошёл сбой и необходимо перезапустить Pervasive.SQL 2000 (transactional)
2. Если служба Pervasive.SQL 2000 (transactional) остановлена и процесса base.exe нет - значит сбоя нет и служба просто остановлена, перезапуск не нужен »
Суть в том, что скрипт сидит и ждёт события, когда будет завершён процесс «base.exe». Вы уверены в том, что процесс «base.exe» завершается после остановки службы «Pervasive.SQL 2000 (transactional)»? Проверьте сие с помощью «Process Monitor», выставив фильтр по «Process Close», и отпишитесь сюда.

bombording
30-10-2011, 16:36
Iska, судя по Process Monitor. Процесс base.exe запускается любой из двух служб. Точнее одним из исполняемым файлом, той или иной службы.
Если, к примеру все службы остановлены и я запускаю Pervasive.SQL 2000 (relational) первой, то её исполняемый файл C:\PVSW\BIN\W3SQLMGR.EXE запускает base.exe. Соответственно если я остановлю эту службу, то процесс C:\PVSW\BIN\W3SQLMGR.EXE пропадёт и base.exe так же с ним пропадёт.

Такая же ситуация если я запущу первой 2-ю службу Pervasive.SQL 2000 (transactional), её исполняемый файл "C:\PVSW\BIN\NTBTRV.EXE" запустит процесс base.exe и остановит его в случае остановки службы.

Iska
30-10-2011, 17:50
bombording, спасибо, ясно. Ближе к ночи поправлю код.

Iska
31-10-2011, 07:06
Попробуйте так:
Option Explicit

Dim strProcessName
Dim strServiceNamePrimary
Dim strServiceNameSecondary

Dim strComputer

Dim objSWbemLocator
Dim objSWbemServicesEx
Dim objSWbemEventSource

Dim objSWbemObjectEx_ServicePrimary
Dim objSWbemObjectEx_ServiceSecondary

Dim collSWbemObjectSet


strProcessName = "base.exe" ' "notepad.exe"
strServiceNamePrimary = "Pervasive.SQL 2000 (transactional)" ' "aspnet_state"
strServiceNameSecondary = "Pervasive.SQL 2000 (relational)" ' "SwPrv"


strComputer = "."

Set objSWbemLocator = WScript.CreateObject("WbemScripting.SWbemLocator")
Set objSWbemServicesEx = objSWbemLocator.ConnectServer(strComputer, "root\cimv2")
Set collSWbemObjectSet = objSWbemServicesEx.ExecQuery("SELECT Name FROM Win32_Service WHERE Name = '" & strServiceNamePrimary & "'")

If collSWbemObjectSet.Count = 1 Then
Set objSWbemObjectEx_ServicePrimary = objSWbemServicesEx.Get("Win32_Service.Name='" & strServiceNamePrimary & "'")
Set objSWbemObjectEx_ServiceSecondary = objSWbemServicesEx.Get("Win32_Service.Name='" & strServiceNameSecondary & "'")

WScript.StdOut.Write "Скрипт ожидает выполнения условий для начала работы..."

Do
objSWbemObjectEx_ServicePrimary.Refresh_
objSWbemObjectEx_ServiceSecondary.Refresh_

Set collSWbemObjectSet = objSWbemServicesEx.ExecQuery("SELECT Name FROM Win32_Process WHERE Name = '" & strProcessName & "'")

If objSWbemObjectEx_ServicePrimary.Started And _
objSWbemObjectEx_ServiceSecondary.Started And _
collSWbemObjectSet.Count > 0 Then

WScript.StdOut.WriteLine " Условия выполнены"

Exit Do
Else
WScript.Sleep 100
End If
Loop

WScript.StdOut.WriteLine "Скрипт работает"

Set objSWbemObjectEx_ServicePrimary = objSWbemServicesEx.Get("Win32_Service.Name='" & strServiceNamePrimary & "'")
Set objSWbemObjectEx_ServiceSecondary = objSWbemServicesEx.Get("Win32_Service.Name='" & strServiceNameSecondary & "'")

Set objSWbemEventSource = objSWbemServicesEx.ExecNotificationQuery( _
"SELECT * FROM __InstanceDeletionEvent " & _
"WITHIN 1 WHERE TargetInstance ISA 'Win32_Process' AND " & _
"TargetInstance.Name = '" & strProcessName & "'")

Do
With objSWbemEventSource.NextEvent.TargetInstance
WScript.StdOut.WriteLine "Процесс [" & .Name & "] (PID: " & CStr(.ProcessID) & ") был остановлен"
End With

With objSWbemObjectEx_ServicePrimary
WScript.StdOut.WriteLine "Служба [" & .Name & "] (PID: " & CStr(.ProcessId) & ")"

.Refresh_

If .Started Then
WScript.StdOut.Write " Служба останавливается"

If .StopService() = 0 Then
Do
WScript.Sleep 100
WScript.StdOut.Write "."

.Refresh_
Loop While .Started

WScript.StdOut.WriteLine
Else
WScript.StdOut.WriteLine "Невозможно остановить службу"
End If

WScript.StdOut.Write " Служба запускается"

If .StartService() = 0 Then
Do
WScript.Sleep 100
WScript.StdOut.Write "."

.Refresh_
Loop Until .Started

WScript.StdOut.WriteLine
Else
WScript.StdOut.WriteLine "Невозможно запустить службу"
End If
Else
' Nothing to do
End If
End With
Loop
Else
WScript.StdOut.WriteLine "Служба [" & strServiceNamePrimary & "] не установлена"
End If

WScript.Quit 0
Я просто передвинул запуск службы внутрь условия «If .Started …». Собственно, так у меня и было изначально, но затем я подумал — «А если служба вдруг будет по каким-то причинам к этому моменту остановлена? Надо сие уметь обрабатывать, и просто запускать службу!».




© OSzone.net 2001-2012