Benachrichtigung beim Herunterfahren von Zertifikatsdiensten per Mail

Betreut man eine PKI Umgebung und möchte bei bestimmten Events als Admin per Mail benachrichtigt werden, gibt es die Möglichkeit, dies relativ einfach ohne Hilfe weiterer Tools wie SCOM oder ähnliches zu bewerkstelligen. 

Die Event ID 4881 ist im Windows Event Viewer hierbei für das Logging von gestoppten ADCS (Active Directory Certificate Services) Diensten hinzuzuziehen.

Eine ausführliche Liste aller IDs findet man auf der Website von Microsoft und das nachfolgende Skript kann sehr einfach auch auf alle anderen IDs umgeschrieben werden.

Das folgende PowerShell Skript sendet eine E-Mail mit Daten aus dem Event Viewer zu der Event ID 4881 an einen festgelegten Empfänger, sobald das Skript ausgeführt wird.

try{
$EventId = 4881
$Nachricht = “Certificate Services stopped.”

$A = Get-WinEvent -FilterHashTable @{Logname = “Security” ; ID = $EventId} | Where-Object {$_.Message -match $Nachricht} | Select-object -First 1
if($A -ne $null){
Invoke-Command -ComputerName SMTPServer -ScriptBlock {
$Message = $using:A.Message
$EventID = $using:A.Id
$MachineName = $using:A.MachineName
$Source = $using:A.ProviderName

$Sender = “<emailsender>”
$Empfaenger = “<emailempfaenger>”
$SMTPServer = “<smtpgateway>”

$Client = New-Object ([System.Net.Mail.SmtpClient]::new())
$Client.Host = $SMTPServer

$Mail = New-Object ([System.Net.Mail.MailMessage]::new())
$Mail.ReplyTo = $sender
$Mail.From = $Sender
#$Mail.CC.Add($Empfaenger)
$Mail.To.Add($Empfaenger)

$Mail.Body = “EventID: $EventID`nUrsprung: $Source`nServer: $MachineName `nNachricht: $Message`n`nBitte Dienst neu starten!”
#$Mail.IsBodyHtml = $true
$Mail.Subject = “CA-Dienst auf $MachineName gestoppt!”
$Client.Send($Mail)
}
}
}
catch{
exit
}

Da das Skript jedoch nicht von selbst auf die Idee kommt, beim Auslösen des Events 4881 eine Email zu versenden, ist noch ein Trigger für das Starten des Skriptes erforderlich. Dies ist ganz einfach über den Task Scheduler zu lösen, den man auf bestimmte Events aus dem Event Viewer einstellen kann, um Aktionen auszuführen.

Folgender Textinhalt ist hierfür in einem beliebigen Editor mit der Endung XML abzuspeichern, sodass dieser anschließend als Task im Task Scheduler importiert werden kann und somit eine Art Template ist:

<?xml version=”1.0″ encoding=”UTF-16″?>
<Task version=”1.2″ xmlns=”http://schemas.microsoft.com/windows/2004/02/mit/task”>
<RegistrationInfo>
<Date>2022-03-23T09:57:34.9052718</Date>
<Author>administrator</Author>
<URI>\BenachrichtigungBeiStoppenVonADCS</URI>
</RegistrationInfo>
<Triggers>
<EventTrigger>
<Enabled>true</Enabled>
<Subscription>&lt;QueryList&gt;&lt;Query Id=”0″ Path=”Security”&gt;&lt;Select Path=”Security”&gt;*[System[EventID=4881]]&lt;/Select&gt;&lt;/Query&gt;&lt;/QueryList&gt;</Subscription>
</EventTrigger>
</Triggers>
<Principals>
<Principal id=”Author”>
<UserId>S-0-0-00-0000000000-000000000-0000000000-000000</UserId>
<LogonType>Password</LogonType>
<RunLevel>HighestAvailable</RunLevel>
</Principal>
</Principals>
<Settings>
<MultipleInstancesPolicy>Queue</MultipleInstancesPolicy>
<DisallowStartIfOnBatteries>true</DisallowStartIfOnBatteries>
<StopIfGoingOnBatteries>true</StopIfGoingOnBatteries>
<AllowHardTerminate>true</AllowHardTerminate>
<StartWhenAvailable>false</StartWhenAvailable>
<RunOnlyIfNetworkAvailable>false</RunOnlyIfNetworkAvailable>
<IdleSettings>
<StopOnIdleEnd>true</StopOnIdleEnd>
<RestartOnIdle>false</RestartOnIdle>
</IdleSettings>
<AllowStartOnDemand>true</AllowStartOnDemand>
<Enabled>true</Enabled>
<Hidden>false</Hidden>
<RunOnlyIfIdle>false</RunOnlyIfIdle>
<WakeToRun>false</WakeToRun>
<ExecutionTimeLimit>PT1H</ExecutionTimeLimit>
<Priority>7</Priority>
</Settings>
<Actions Context=”Author”>
<Exec>
<Command>powershell</Command>
<Arguments>-executionpolicy bypass -file “\\netzlaufwerk\g$\Scripts\BenachrichtigungBeiStoppenVonADCS.ps1″</Arguments>
</Exec>
</Actions>
</Task>

Weiterführende Informationen zu den Skripten

In diesem Beispiel wird das Skript auf einem Netzlaufwerk unter dem Pfad \\netzlaufwerk\g$\Scripts\BenachrichtigungBeiStoppenVonADCS.ps1 gespeichert.

Das wurde bewusst so gewählt, damit man das Skript an einer zentralen Stelle ablegen kann und anschließend bei Bedarf nur noch den Task im Task Scheduler auf mehreren Systemen importieren muss.
Auf diese Weise können mehrere Server auf das gleiche Skript zugreifen (sofern diese dazu berechtigt sind) und der Aufwand für die Pflege der Tasks verringert sich immens.
Ein Skript auszuführen, welches auf einem anderen Laufwerk als auf dem lokalen abliegt, ist nur leider nicht so trivial, wie man vielleicht meinen könnte.
Aus diesem Grund ist in der XML-Vorlage für den Task Scheduler die Zeile
<Arguments>-executionpolicy bypass -file “\\netzlaufwerk\g$\Tracking\Scripts\BenachrichtigungBeiStoppenVonADCS.ps1″</Arguments>
da, welche die Richtlinien für eine Ausführung umgeht. Nutzt man das Skript also nur auf einem System und die Datei liegt auch lokal ab, kann man das Argument -executionpolicy bypass entfernen.

Die Art der Authentifizierung und Privilegien muss je nach Umgebung auch angepasst werden, in unseren Beispiel in einer Testumgebung hat es nur mit einem Adminkonto und höchsten Privilegien funktioniert. Mit den richtigen AD-Rechten sollte hier aber auch die Nutzung eines technischen Systemkontos möglich sein.

Mit der Menge an Möglichkeiten und Parametern die je nach Bedarf sehr spezifisch sein können und angepasst werden müssen, gilt also: Probieren geht über Studieren.