Компьютерный форум OSzone.net  

Компьютерный форум OSzone.net (http://forum.oszone.net/index.php)
-   Скриптовые языки администрирования Windows (http://forum.oszone.net/forumdisplay.php?f=102)
-   -   [решено] Скрипт мониторинга службы или порта (http://forum.oszone.net/showthread.php?t=218839)

bombording 25-10-2011 13:22 1781251

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

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

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

El Sanchez 25-10-2011 15:10 1781334

bombording, если служба присутствует в оснастке services.msc, то в свойствах службы на вкладке Восстановление можно указать действия при сбоях. Если нет, то то же самое через комстроку: sc failure.

bombording 25-10-2011 16:29 1781393

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

El Sanchez 25-10-2011 16:49 1781409

Цитата:

Цитата bombording
её нужно ставить на выполнение в планировщик »

Это просто команда настройки службы, выполняется 1 раз. А там уже все будет зависеть от самой службы и ее взаимодействия с SCM.

bombording 26-10-2011 09:42 1781916

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

Код:

sc failure msftpsvc reset= 20 actions= restart/5000
И как быть, к примеру, если мне нужно что бы служба была выключена в 2 часа ночи на время архивации. Не запустится ли она автоматически после выключения??

Iska 26-10-2011 11:42 1781987

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

Цитата:

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

Останавливайте её из того же задания, что и архивация, после — запускайте.

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

El Sanchez 26-10-2011 11:56 1781999

Цитата:

Цитата bombording
Тоесть если я хочу, что бы служба в случае недоступности в течении 20 секунд, перезапускалась автоматически. Я должен выполнить ?? »

bombording, параметр reset определяет через сколько секунд беспербойной работы службы счетчик ошибок сбрасывается в 0 и этот период должен быть гораздо больше, чем 20 с. Сбрасывайте через несколько часов или раз в сутки.
А в actions у вас записано: при первом сбое рестарт службы с задержкой в 5 с., можно дописать еще действия для второго сбоя и последующих.

Цитата:

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

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

bombording 26-10-2011 14:16 1782132

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

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

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

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

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

Iska 26-10-2011 20:42 1782420

Цитата:

Цитата bombording
И непонятно, как sc failure определяет ошибочное состояние, если службы находятся в состоянии Started при сбое. »

Это и есть главный вопрос: как Вы определяете, что нужен перезапуск служб?

bombording 27-10-2011 09:54 1782718

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

Iska 27-10-2011 16:22 1783009

bombording, давайте уточним общую картину — правильно ли я понял:

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

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

bombording 28-10-2011 10:06 1783480

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 1783724

bombording:

1. Какие имена у этих служб?
Код:

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

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

bombording 28-10-2011 16:48 1783756

Iska,

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

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

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

Iska 29-10-2011 05:07 1784098

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 1785016

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 1785040

Цитата:

Цитата bombording
Единственное не хватает условия что бы при корректном выключении службы (например на время архивации), скрипт не перезапускал службу 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 1785057

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 1785127

bombording, спасибо, ясно. Ближе к ночи поправлю код.

Iska 31-10-2011 07:06 1785461

Попробуйте так:
Код:

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 …». Собственно, так у меня и было изначально, но затем я подумал — «А если служба вдруг будет по каким-то причинам к этому моменту остановлена? Надо сие уметь обрабатывать, и просто запускать службу!».

bombording 31-10-2011 09:48 1785520

Iska, Большое спасибо! Всё работает как надо.


Время: 11:33.

Время: 11:33.
© OSzone.net 2001-