Hosting der Windows PowerShell in .NET-Anwendungen

Die oftmals sehr prägnanten Commandlets der Windows PowerShell kann man sich auch in .NET-Anwendungen zu nutze machen.

vorlesen Druckansicht
Lesezeit: 2 Min.
Von
  • Dr. Holger Schwichtenberg

Die Windows PowerShell zeichnet sich oft durch prägnante Befehle aus, zum Beispiel

gps | where { $_.ws -gt 1MB } | sort ws -desc | select -first 15   

Dieser Befehl bedeutet: Hole die Liste aller Prozesse, filtere diejenigen aus, die mehr als ein MByte Speicher nutzen, sortiere die Liste absteigend nach der Speichernutzung und begrenze die Liste auf die ersten 15.

Auch viele Microsoft-Services und -Server unterstützen Commandlets, ein gutes Beispiel ist das Commandlet New-Mailbox" zum Anlegen von Postfächern für Microsoft Exchange.

Windows PowerShell basiert auf .NET, und daher kann man PowerShell als Skriptumgebung auch innerhalb von .NET-Anwendungen (C#, Visual Basic, C++/CLI, F#, u.v.a.m.) nutzen.

Das Listing zeigt eine Hilfsmethode zum AusfĂĽhren eines PowerShell-Befehls in einer .NET-Anwendung. Voraussetzung ist es, die System.Management.Automation.dll zu referenzieren und ein using System.Management.Automation ist auch hilfreich. Die Methode liefert die Ergebnisobjekte im RĂĽckgabewert und ĂĽber den Out-Parameter-Status aufgetretene Fehler. Zentral ist in der Methode die Instanziierung der Klasse PowerShell mit der statische Methode Create(), die Ăśbergabe der Befehle mit AddScript() und die AusfĂĽhrung mit Invoke().

  public Collection<PSObject> Run(string Command, out string Status)
{
string e = "";
PowerShell ps = PowerShell.Create();

// Befehl hinzufĂĽgen
ps.AddScript(Command);
   // Befehl ausfĂĽhren
Collection<PSObject> ErgebnisMenge = ps.Invoke();
   // Fehler?
if (ps.Streams.Error.Count == 0)
{ // Nein
Status = "OK";
return ErgebnisMenge;
}
else
{ // Es gab einen Fehler
foreach (var dr in ps.Streams.Error)
{
e += dr.Exception.Message;
}
Status = e;
return null;
}
}

Das zweite Listing zeigt den Aufruf der Hilfsmethode an einem Beispiel. Es lassen sich wahlweise Befehlsketten oder ein Pfad zu einer PowerShell-Skriptdatei ĂĽbergeben.

   string Status = "";
string Demo = (gps | where { $_.ws -gt 1MB } | sort ws -desc
| select -first 15 ");
var ErgebnisMenge = new WPSHostLib.WPSHost().Run(Demo, out Status);
   if (Status != "OK")
{
Console.WriteLine("Fehler: " + Status);
}
else
{
// Ergebnismenge darstellen
foreach (System.Management.Automation.PSObject Ergebnis in ErgebnisMenge)
{
Console.WriteLine(
"{0,-24}{1,-10}{2}",
Ergebnis.Members["ProcessName"].Value,
Ergebnis.Members["Id"].Value,
Ergebnis.Members["WorkingSet64"].Value);
}
}

FĂĽr einen Kunden schreibe ich gerade einen Webservice, der PowerShell-Skripte auf einem Application Server ausfĂĽhrt. Die obige Hilfsroutine ist dabei ein wesentlicher Baustein.

()