Translations of this page:

NRPE-basiertes Starten von Prozessen unter einem bestimmten AD-User mit Hilfe von runasspc

Um was gehts?

Das entfernte Starten von Windows-Diensten über NRPE wurde im Wiki ja bereits beschrieben. Hier beschreibe ich, wie ich über NRPE Windows-Applikationen unter einem bestimmten User starte.

Warum so?

Das Problem / meine Situation: In unserer Firma gibt es einige Windows-Applikationen, die verschiedene Konvertierungen/Emails2DB/usw/usf-Funktionen ausführen. Konkret sieht das so aus, dass auf diesen Rechnern ein spezieller Benutzer (mit minimal-Rechten) angemeldet ist, und dort die Applikationen (GUI-basiert) vor sich hin werkeln (dass das alles auch als Windows-Service machbar wäre, sei hier nicht das Thema - meins ist es gottseidank auch nicht, ich bin nur fürs Monitoring da :-).
Diese Programme fahren sich des öfteren fest (auch nicht mein Problem :-) ), was ich zwar über Nagios erfahre, aber nun über Eventhandler „selbst heilen“ will, sprich: Nagios soll per NRPE den jew. Prozess abschießen und neu starten.
Mein erster Ansatz war, mit einem als Eventhandler über NRPE ausgelösten Script auf dieser Maschine den Prozess einfach zu killen und neu zu starten. Doch der neue Prozess läuft fortan dann im selben Benutzerkontext wie der NSClient++ (er wurde von ihm ja gestartet), nämlich SYSTEM. Folge: der Prozess läuft, aber die GUI ist nicht mehr sichtbar.

Die Anforderung

Es musste also eine Lösung her, mit der ich per NRPE eine Anwendung auf der Maschine abschießen und neu starten konnte, sodass diese in einem ganz bestimmten Benutzerkontext läuft.

Die Lösung?

Vorweg: nicht der Weisheit letzter Schluss, aber sie funktioniert, und zwar ohne die Benutzerdaten im Klartext hinterlegen zu müssen.
Ich bediene mich des Tools runasspc.exe (für private Nutzung kostenlos). Auszug aus der Hilfe:

"Runas Spc startet Programme unter einer anderen Benutzerkennung als dem derzeit angemeldeten Benutzer.\\
Welches Programm unter welcher Kennung gestartet werden soll liest Runas Spc aus einer mit runasspc.exe oder
Runasspcadmin.exe erstellten verschlüsselten Datei.\\
Jede verschlüsselte Datei erhält aus Sicherheitsgründen Ihr eigenes Verschlüsselungspasswort,
ähnlich eines Fingerabdruckes.\\
Die freigegebene Anwendung wird auf Bitebene überprüft ob Sie gestartet werden darf.\\
Runasspc erfordert keine Installation. Runas Spc kann zusammen mit einer Cryptdatei auf einen Rechner kopiert und
von dort direkt gestartet werden.

Voraussetzung

  • irgendein Windows-Host (im folgenden: „Problem-Host“)
  • Darauf installierter NSClient++ incl. aktiviertem NRPE

Einrichtung

1. runasspc einrichten

  • entzippe den Inhalt in c:\programme\runasspc\ auf dem Problemhost
  • Crypt-Datei für die Problemanwendung erzeugen: starte C:\programme\runasspcadmin.exe
  1. Pfad zur .exe der Problemanwendung
  2. Userdaten, unter dem die Anwendung laufen soll.
  3. (*) Pfad zum Cryptfile, in dem die Userdaten verschlüsselt abgelegt werden. Ich wähle hier das Scripts-Verzeichnis vom NSClient++, als Dateiname [anwendungsname.exe_runasspc.spc]. (das “.exe“ nicht vergessen!) Auf diese Crypt-Datei müssen wir später im vbs-Script zugreifen können.
  4. Hier sollte der Name der *.spc-Datei dann stehen.
  5. „Test Cryptfile“ anklicken - runasspc sollte nun imstande sein, mit den im Cryptfile verschlüsselt hinterlegten Zugangsdaten die unter 1) genannte Anwendung zu starten (was zukünftig das vb-Script für uns erledigt). Ist dies nicht möglich, sind entweder der Pfad zur Problemanwendung, die Userdaten, oder die NTFS-Berechtigungen auf die Problemanwendung oder den Pfad zum Cryptfile falsch.

  • Nun sind wir also schon mal imstande, die Anwendung unter einem anderen User zu starten.

2. NRPE-Kommando definieren

Ich habe mich dazu entschlossen, per Eventhandler über check_nrpe direkt auf dem Problemhost ein vbscript zu starten, in welchem dann die Logik steckt, was in welchem Servicezustand zu tun ist.

  • kopiere restart_proc.vbs in c:\programme\nsclient\scripts
  • Erweitere c:\programme\nsclient\nsc.ini um das Kommando „restart_proc“. $ARG1$ wird alle vier Parameter beinhalten, die Nagios gemäß Eventhandler-Definition an check_nrpe übergibt.
restart_proc=cscript.exe //NoLogo scripts\restart_proc.vbs $ARG1$

3. Eventhandler definieren

  • Nun legen wir für den Eventhandler ein command-Objekt an. Achtet auf
    • die DoubleQuotes sonst kommt im NRPEListener als $ARG1$ nur der Servicestate an
    • den Timeout -t 15; das vbscript enthält sleep-Kommandos, die die Ausführung des Scriptes verzögern. Der Default-Timeout von 10 Sekunden ist in diesem Fall auf 15 Sekunden verlängert worden.
# (als Argument ARG1 wird die "problemanwendung.exe" übergeben)
# eh_win_restart_proc
define command{
        command_name    eh_win_restart_proc
        command_line    $USER1$/check_nrpe -H $HOSTADDRESS$ -p 5666 -t 15 -c restart_proc -a "$SERVICESTATE$ $SERVICESTATETYPE$ $SERVICEATTEMPT$ $ARG1$"
}
  • Den Eventhandler knüpfen wir an den Problemservice:
define service{
        use                             templ_s_urservice
        service_description             s_converter
        host_name                       win_therex
        check_command                   check_converter!60000!300000!28120
        contact_groups                  cg_edv_email
        **event_handler                 eh_win_restart_proc!converter.exe**
        }

4. Ablauf / Test

Wir starten den NSClient++ neu durch, um das neu definierte Kommando zu laden. Zunächst testen wir manuell:

nagios@vmnagios:/usr/local/nagios/libexec$ ./check_nrpe -H 192.168.0.45 -p 5666 -c restart_proc -a "WARNING SOFT 1 converter.exe"

Die Anwendung (egal, ob sie läuft oder nicht, bzw. abgestürzt ist oder nicht) sollte ggf. beendet und in jedem Fall neu gestartet werden.
Im Fehlerfall besser mal ein

nagios@vmnagios:/usr/local/nagios/libexec$ ./check_nrpe -H 192.168.0.45 -p 5666 -c check_ok

absetzen, um die NRPE-Funktion generell zu testen.

VB-Script

Das folgende Script restart_proc.vbs ist unter C:\programme\nsclient\scripts abzulegen. Wenn Ihr Anregungen oder auch Kritik habt, immer nur her damit :-)


' Region Description
' Arguments: 
' 1) Status (ok, warning, critical, unknown)
' 2) Statetype (hard, soft)
' 3) Attempt (1...n)
' 4) Process name
' EndRegion

'full path to runasspc (get from 
runasspc="c:\programme\runasspc\runasspc.exe"
'directory of the spc-crypt files
cryptfile="C:\programme\nsclient\scripts\"

'runasspc available?
Dim fso
Set fso = CreateObject("Scripting.FileSystemObject")
If Not fso.FileExists(runasspc) Then
	WScript.Echo "ERROR: runasspc.exe not found. Check file path on destination host."
	WScript.Quit 
End If


On Error Resume Next
i = 0
' Servicestate (ok, warning, critical, unknown)
	state = LCase(WScript.Arguments(i))
	i = i + 1
' Servicestatetype (hard, soft)
	statetype = LCase(WScript.Arguments(i))
	i = i + 1
' Serviceattemt (1...n)
	attempt = LCase(WScript.Arguments(i))
	i = i + 1
' Process name
' Win2k only displays the first 15 chars of the process name in task manager
	procname = LCase(WScript.Arguments(i))
    If Len(procname) > 15 Then
		procname2kill = Left(procname, 15)
	Else
		procname2kill = procname
    End If
	
	If Err.number > 0 Then
		WScript.Echo "ERROR: invalid (number of) arguments."
		WScript.Quit
	End If

On Error Goto 0


' modify this section to your needs
Select Case state
	Case "ok"			' nothing to do
	Case "warning"		
		if statetype = "soft" then restartProcess procname,procname2kill
	Case "critical"		' nothing to do
		if statetype = "soft" then restartProcess procname,procname2kill
	Case "unknown"		' nothing to do
End Select



Sub restartProcess(instrProcessName,instrProcess2kill)
' search for running instances of the process
	strComputer = "."
	Set objWMIService = GetObject("winmgmts:" _
    & "{impersonationLevel=impersonate}!\\" & strComputer & "\root\cimv2")
	Set colItems = objWMIService.ExecQuery _
    ("Select * from Win32_Process Where Name = '" & instrProcessName & "' OR Name = '" & instrProcess2kill & "'")
	For Each objItem In colItems
			objItem.terminate
	Next	
	' Wait a few seconds before restarting process
	WScript.Sleep(5000)
	' restart process
	Dim shell, command
	command = runasspc & " /cryptfile:" & Chr(34) & cryptfile & procname & "_runasspc.spc" & Chr(34) & " /quiet"
	Set shell = CreateObject("WScript.Shell")
	On Error Resume Next
		shell.Run command
		If Err.number = 0 Then
			WScript.Echo "OK: Process " & instrProcessName & " successfully restarted."
		Else
			WScript.Echo "ERROR: restarting process " & instrProcessName & " failed."
		End If
	On Error Goto 0
' tidy up
	Set objWMIService = Nothing
	Set colItems = Nothing
	Set shell = Nothing
End Sub
nagios/howtos/nrpe_win_appl_user.txt · Zuletzt geändert: 2009/12/21 08:22 von simmerl
CC Attribution-Noncommercial-Share Alike 3.0 Unported
www.chimeric.de Valid CSS Driven by DokuWiki do yourself a favour and use a real browser - get firefox!! Recent changes RSS feed Valid XHTML 1.0