What you'll know
- Whether one named service is running. Running is healthy. Starting, stopping, pausing or resuming is a warning, because a service caught in that state for long is stuck. Stopped or paused is a problem, and so is a service that no longer exists, for example after an uninstall.
Each service gets a short script of its own and a check of its own, so each alert names the service that stopped. A service restarting for an update won't wake anyone: once a check turns into a problem, Gryphon checks it every minute and alerts only when three results in a row agree.
What this can't tell you: whether the program inside the service is doing its job. A service can be running and hung. Pair this with a check on what the service provides: a web endpoint, a port, or for SQL Server, a query.
Before you start
- The Windows machine, added as a host in Gryphon, with the Gryphon agent installed on it and connected: the host's page says Connected.
- An administrator's PowerShell on that machine.
The example watches IIS, whose service is W3SVC. Any other service works the same way.
Steps
1Find the service's name
Scripts use a service's name, not the display name shown in Services. This lists both:
Get-Service | Sort-Object DisplayName | Format-Table Name, DisplayName, Status
World Wide Web Publishing Service is W3SVC, SQL Server (MSSQLSERVER) is
MSSQLSERVER, and Print Spooler is Spooler.
2Turn on script checks
Script checks are off until the agent is told which folder to run them from. In an administrator's
PowerShell, open C:\ProgramData\Gryphon\agent.env in Notepad, uncomment the
GWC_SCRIPTS_DIR line, and restart the agent:
GWC_SCRIPTS_DIR=C:\ProgramData\Gryphon\scripts
Restart-Service GryphonAgent
3Add a script for the service
Create the script in the scripts folder, from the same administrator's PowerShell:
notepad C:\ProgramData\Gryphon\scripts\service-w3svc.ps1
Paste this, change $Name to your service's name, and save:
# Is one Windows service running? Running is healthy; starting, stopping or
# pausing is a warning; stopped or paused is a problem.
$Name = 'W3SVC' # the service's name, as Get-Service shows it
try {
$service = Get-Service -Name $Name -ErrorAction Stop
} catch {
if ($_.CategoryInfo.Category -eq 'ObjectNotFound') {
Write-Output "There is no service called $Name on this machine."
exit 2
}
Write-Output ('Cannot read the service {0}: {1}' -f $Name, $_.Exception.Message)
exit 3
}
$status = [string]$service.Status
$message = '{0} is {1}.' -f $service.DisplayName, $status
switch ($status) {
'Running' { Write-Output $message; exit 0 }
'StartPending' { Write-Output $message; exit 1 }
'StopPending' { Write-Output $message; exit 1 }
'ContinuePending' { Write-Output $message; exit 1 }
'PausePending' { Write-Output $message; exit 1 }
default { Write-Output $message; exit 2 }
}
For another service, make another file with another name, such as service-spooler.ps1. File
names may use letters, digits, dots, hyphens and underscores, so name the file for a service like
MSSQL$SQLEXPRESS without the $: service-sqlexpress.ps1.
Create each file in the folder like this rather than copying it in. A new file takes the folder's
permissions, which only administrators can change. A file moved in from elsewhere keeps its own, and the
agent refuses to run it, with a message naming the icacls command that fixes it.
4Add the check
Open the host, go to Manage Services, choose Add service, and pick Script (agent):
- Name
- IIS
- Script
- service-w3svc.ps1 — with the extension
- Check Interval
- Every 3 Minutes
The script's first line of output, such as World Wide Web Publishing Service is Running., becomes the check's message. Exit code 0 is healthy, 1 a warning, 2 a problem, and 3 unknown: anything that stops the script reading the service, other than the service not existing, is unknown rather than a problem.
Test it
- Run the script yourself to see what it says:
powershell -NoProfile -ExecutionPolicy Bypass -File C:\ProgramData\Gryphon\scripts\service-w3svc.ps1; $LASTEXITCODE - Use the check's Check now button in Gryphon. That runs it as the agent does, under the agent's own account.
- On a machine where it's safe, stop the service:
Stop-Service W3SVC. On its next run the check is a problem. Gryphon checks every minute from then on, and alerts after three in a row, so warn whoever gets the alerts first.Start-Service W3SVCbrings it back, and three healthy results announce the recovery.
Variations
Every service set to start automatically
One check for the whole machine: any service whose startup type is Automatic and isn't running is a
problem. Some automatic services start, do their work and stop again by design, so run it by hand first and
add anything it lists that's normal on your machine to $Ignore.
# Is every service set to start automatically actually running? Some start,
# do their work and stop again by design: list those in $Ignore.
$Ignore = @('gupdate', 'edgeupdate', 'MapsBroker', 'sppsvc', 'RemoteRegistry', 'WbioSrvc')
$stopped = @(Get-Service | Where-Object {
$_.StartType -eq 'Automatic' -and $_.Status -ne 'Running' -and $Ignore -notcontains $_.Name
})
if ($stopped.Count -gt 0) {
Write-Output ('Not running: ' + (($stopped | ForEach-Object { $_.Name }) -join ', '))
exit 2
}
Write-Output 'Every automatic service is running.'
exit 0
It names every stopped service in one message, but it's one check, so a second service stopping while the first is still down doesn't send a second alert. Use one script per service for the ones that matter.
SQL Server Agent
When SQL Server Agent stops, nothing scheduled runs, backups included, and SQL Server itself keeps
answering. Watch it with $Name = 'SQLSERVERAGENT', or 'SQLAgent$NAME' for a named
instance. For SQL Server itself, see Monitor SQL Server on Windows.