Logo faq-o-matic.net
Logo faq-o-matic.net

Powershell: Dynamische Logikabfragen

von veröffentlicht am2. April 2019, 07:35 Uhr Kurzlink und Zitatlink einblenden
Kategorie Kategorie: PowerShell   Translate with Google Translate Translate EN   Die angezeigte Seite drucken

Bei einem aktuellen Projekt benötigte ich die Möglichkeit, mehrere Werte aus einer XML-Datei mit einem ebenfalls darin definierten Logikoperator zu vergleichen. Das Szenario dazu: In dem Projekt ist eine leichtgewichtige Softwareverteilung auf Skriptbasis im Einsatz, die beim Systemstart verschiedene Applikationen aktualisiert. Hier war noch etwas mehr Logik erwünscht, um Aktivitäten nur dann auszuführen, wenn bestimmte Bedingungen erfüllt sind.

Da der Code möglichst dynamisch und gut erweiterbar sein sollte, stellte sich heraus, dass der Logikoperator durch einen Scriptblock dynamisch in den Code eingefügt werden musste. Um dies zu ermöglichen, habe ich die Funktion Apply-CustomLogic() entworfen, welche aktuell die Operatoren „like“, „is“, „isnot“, „startswith“, „notstartswith“, „endswith“ und „notendswith“ unterstützt.

Drei kurze Cmdlet Beispiele dazu, die mit einer Funktion auf dieser Basis arbeiten:

Apply-CustomLogic(„startswith“,“faq-o-matic.de“,“faq“)  <- Ergebnis: $true

Apply-CustomLogic(„endswith“,“faq-o-matic.de“,“.de“)  <- Ergebnis: $true

Apply-CustomLogic(„notendswith“,“faq-o-matic.de“,“.de“) <- Ergebnis: $false

Ein typisches Code-Szenario dafür wäre: Mehrere Konditionen sowie Referenzwerte müssen aus einer XML-Datei ausgelesen und dann in Powershell interpretiert werden.

Die XML Datei beinhaltet dann folgendes:

<check type="RegistryValue" logic="StartsWith">
   <path>Registry::HKEY_LOCAL_MACHINE\SOFTWARE\Wow6432Node\TeamViewer\</path>
   <key>Version</key>
   <value>14</value>
</check>
<check type="RegistryPathPresent" logic="Is">
   <path>Registry::HKEY_LOCAL_MACHINE\SOFTWARE\TeamViewer\</path>
</check>

Der Script-Part dazu sähe wie folgt aus:

[..]
#Check if a registry path is present
if($checkType -eq "RegistryPathPresent"){
   if(
	   !(Apply-CustomLogic -condition $check.Logic -V1 $true -V2 (Get-ItemProperty -Path $Check.Path -ErrorAction SilentlyContinue))
	 ){
	   Write-CustomWarning("Check $checkType for $($Check.Path)$($check.Key) is $IgnoreSoftware, supposed value is $($Check.Value), current value is $($Path.$($Check.Key))")
   }else{
	   Write-CustomLog("Check $checkType for $($Check.Path)$($check.Key) is $IgnoreSoftware, supposed value is $($Check.Value), current value is $($Path.$($Check.Key))")                
   }
}

#Check for a specific registry value
if($checkType -eq "RegistryValue"){
   if(
	   !($Path = Get-ItemProperty -Path $Check.Path -ErrorAction SilentlyContinue) -or
	   !(Apply-CustomLogic -condition $check.Logic -V1 $Path.$($Check.Key) -V2 $Check.Value)
   ){
	   Write-CustomWarning("Check $checkType for $($Check.Path)$($check.Key) is $IgnoreSoftware, supposed value is $($Check.Value), current value is $($Path.$($Check.Key))")
   }else{
		Write-CustomLog("Check $checkType for $($Check.Path)$($check.Key) is $IgnoreSoftware, supposed value is $($Check.Value), current value is $($Path.$($Check.Key))")
	}
}
[..]

Hierbei werden nun die Konditionen und Referenzwerte aus der XML-Datei gegen reale, per Powershell abrufbare Funktion oder Variablen geprüft. Um den Code dynamisch zu generieren, nutzt die Funktion die Funktion Create([string]) auf der Klasse [Scriptblock], um aus einem vorher zusammengesetzten String einen ausführbaren Code zu generieren. Dieser Code wird im Anschluss durch $scriptblock.Invoke() ausgeführt und wendet den vorher generierten Logikcode aus.

Zu finden ist diese Funktion hier:

https://github.com/RobinBeismann/PowerShell-Scripts/blob/master/Scripts/Snippets/Apply-CustomLogic.ps1

© 2005-2019 bei faq-o-matic.net. Alle Rechte an den Texten liegen bei deren Autorinnen und Autoren.

Jede Wiederveröffentlichung der Texte oder von Auszügen daraus - egal ob kommerziell oder nicht - bedarf der ausdrücklichen Genehmigung durch die jeweiligen Urheberinnen oder Urheber.

Das Impressum findet sich unter: http://www.faq-o-matic.net/impressum/

Danke, dass du faq-o-matic.net nutzt. Du hast ein einfaches Blog sehr glücklich gemacht!