Praktische PowerShell-Skripte und Hilfswerkzeuge für den IT-Alltag
Im Zuge meiner täglichen Arbeit an komplexen IT-Infrastrukturen und Automatisierungen entstehen nützliche kleine Helfer und Module. Ich teile diese Werkzeuge auf GitHub und über die PowerShell Gallery, um die Administration und Entwicklung für andere zu erleichtern.
Sequenzielle Verarbeitung großer Datenmengen kann lange dauern — gerade bei Cloud-APIs. Die Lösung ist Parallelisierung, und dafür müssen die Daten zuerst in Portionen (Chunks) zerlegt werden.
Damit dieses Rad nicht in jedem Skript neu erfunden wird, übernimmt Split-Array genau diesen Schritt: Es teilt ein Array in ein Array von Arrays — wahlweise nach maximaler Chunk-Größe oder in eine feste Anzahl von Chunks.
Klein, aber fein: Edge Cases sind berücksichtigt, die Eingabe funktioniert als Argument ebenso wie über die Pipeline.
Installation
Das Modul wird direkt aus der PowerShell Gallery installiert:
Vorausgesetzt wird PowerShell 5.1 oder neuer. Alternativ lässt sich das Repository klonen und das Modul über sein Manifest SplitArray.psd1 importieren.
Hinweis: In der PowerShell Gallery veröffentlicht als SplitArray.
Nutzungsbeispiele
1. Aufteilen nach maximaler Chunk-Größe (-ChunkSize)
Bestimmt, wie viele Elemente maximal in einem Unter-Array liegen dürfen. Ideal für API-Batches.
Füllt den letzten Chunk mit einem Wert auf, bis er die Größe des ersten Chunks erreicht — praktisch, wenn nachgelagerter Code gleich große Chunks erwartet.
# Mit $null auf die volle Chunk-Größe auffüllen
Split-Array -InputObject 1..10 -ChunkSize 3 -Pad $null
# Ergebnis: (1,2,3), (4,5,6), (7,8,9), (10,$null,$null)
Verteilungsstrategien
Vergleich der Verteilungsstrategien Greedy und Even
Strategie
Verhalten
Standard für
Greedy
Füllt jeden Chunk bis zum Maximum; der letzte Chunk erhält den verbleibenden Rest.
-ChunkSize
Even
Verteilt den Rest elementweise auf die ersten Chunks; erzeugt immer exakt die gewünschte Anzahl an Chunks.
-MaxChunk
Parameter
Übersicht der Parameter von Split-Array
Parameter
Funktion
InputObject
Das Array bzw. die Elemente, die zerlegt werden. Nimmt Pipeline-Eingabe entgegen.
ChunkSize
Maximale Anzahl Elemente pro Chunk. Schließt -MaxChunk aus.
MaxChunk
Gewünschte Anzahl an Chunks. Schließt -ChunkSize aus.
Distribution
Verteilungsstrategie Greedy oder Even — steuert, wie der Rest verteilt wird.
Pad
Wert, mit dem der letzte Chunk auf einheitliche Größe aufgefüllt wird (z. B. $null, 0, "x").
Innerhalb eines Cmdlets ist die PowerShell-Pipeline elegant. Sobald aber die Ausgaben mehrerer Cmdlets zusammengeführt werden müssen, beginnt die Handarbeit: Schleifen, Zwischenspeicher und von Hand gepflegte Hashtable-Lookups.
Join-Object verbindet die Ausgaben zweier Cmdlets anhand einer gemeinsamen Identität — etwa einer SMTP-Adresse oder GUID — zu einem einzigen Objekt, direkt in der Pipeline.
Jedes Cmdlet wird dabei genau einmal aufgerufen, ganz ohne explizite Schleifen. Das Ergebnis bleibt ein kompakter, lesbarer One-Liner.
Installation
Das Modul wird direkt aus der PowerShell Gallery installiert:
Was DOS-Batchdateien mit ECHO ON immer konnten, fehlt PowerShell bis heute: ein Protokoll, das vor jedem Befehl festhält, was gleich ausgeführt wird. In langen Logs lässt sich Ausgabe deshalb oft nicht mehr dem Befehl zuordnen, der sie erzeugt hat.
Invoke-WithEcho führt einen Scriptblock aus und protokolliert vorab den Befehlstext — zusammen mit Typ und aktuellem Wert jeder Variablen, die der Block liest. In Kombination mit Start-Transcript wird so jede Zeile im Log ihrem Auslöser zuordenbar.
Die Auflösung liest die Variablen nur aus dem Scope des Aufrufers — nichts wird doppelt ausgeführt, keine Nebeneffekte. SecureStrings und Credentials erscheinen maskiert, die Rückgabe des Blocks läuft unverändert durch die Pipeline.
Installation
Das Modul wird direkt aus der PowerShell Gallery installiert:
Hinweis: In der PowerShell Gallery veröffentlicht als InvokeWithEcho.
Nutzungsbeispiele
1. Befehl samt Variablenwerten protokollieren
Der Befehlstext erscheint wörtlich wie geschrieben, darunter Typ und Wert jeder gelesenen Variablen. Die Zuweisung gehört vor den Aufruf — der Block läuft in einem Kindscope, Zuweisungen im Block verpuffen.
Die Echo-Zeilen laufen über den Information-Stream und landen damit im Transkript — jede Ausgabe im Log ist dem Befehl zuordenbar, der sie erzeugt hat.
Start-Transcript deploy.log
Invoke-WithEcho { Copy-Item $source $target -Recurse }
Invoke-WithEcho { Restart-Service $serviceName }
Stop-Transcript
# deploy.log enthält jeden Befehl samt Werten — vor seiner Ausgabe
3. Ausgabe steuern und umlenken
Mit -NoExpand bleibt es beim reinen Befehlstext; per 6> lassen sich die Echo-Zeilen in eine Datei umlenken oder unterdrücken — die Rückgabe bleibt davon unberührt.
# Nur den Befehlstext protokollieren, ohne Variablenwerte
Invoke-WithEcho { Get-Content $configPath } -NoExpand
# Echo-Zeilen in eine Datei umlenken statt in die Konsole
$result = Invoke-WithEcho { Get-Process } 6> echo.log
Parameter
Übersicht der Parameter von Invoke-WithEcho
Parameter
Funktion
ScriptBlock
Der auszuführende Block. Pflichtparameter, auch positional übergebbar.
MaxValueLength
Maximale Länge je protokolliertem Variablenwert (Standard 100); längere Werte enden mit „…“.
NoExpand
Protokolliert nur den Befehlstext, ohne Variablenwerte.
CommandColor
Konsolenfarbe der Befehlszeilen (Standard Cyan) — wirkt nur in der Konsole, das Transkript bleibt unformatiert.
ValueColor
Konsolenfarbe der Variablenzeilen (Standard DarkGray).
NoColor
Gibt die Echo-Zeilen in der Standardfarbe der Konsole aus.
Ausblick
Nach und nach mehr
Ich habe mir vorgenommen, hier nach und nach kleine Helfer aus meinem Arbeitsalltag zu teilen. Was sich in der Praxis bewährt, bekommt seinen Platz auf dieser Seite.