PowerShell-Modulpfad: Wiederverwendbarer Code ohne Kopieren und Einfügen

Die Arbeit mit PowerShell-Modulen ist ein wichtiger Bestandteil der PowerShell-Automatisierung. Wenn Sie PowerShell lernen, beginnen Sie normalerweise mit einzelnen Befehlen. Dies führt dazu, dass Skripte erstellt werden, was dann zur Erstellung von Funktionen führt.

Durch die Verwendung von Funktionen können Sie Ihre Skripte modularer gestalten. Dadurch können Sie denselben Code an vielen Stellen verwenden, ohne ihn überall kopieren und einfügen zu müssen. Die Verwendung von Funktionen ermöglicht es Ihnen, weniger Zeit damit zu verbringen, dieselbe Änderung an demselben Code an allen Stellen vorzunehmen, an denen er verwendet wird. Stattdessen können Sie daran arbeiten, Ihren Code an einer einzigen Stelle zu verbessern.

Um Funktionen auf die nächste Stufe zu bringen, können Sie diese Funktionen zu einem Modul kombinieren.

A module is a collection of functions in a text file with a psm1 extension. There are some optional additions, such as a module manifest and comment-based or external help that may also be included. These will be covered later on.

Voraussetzungen

I’ll be using Windows PowerShell 5.1 in this article. If you’re using an older version or PowerShell Core, your mileage may vary as to results you see.

Interaktion mit Modulen

Sobald Sie eine PowerShell-Sitzung öffnen, starten Sie mit zwei Modulen. Das erste ist Microsoft.PowerShell.Utility, das viele grundlegende PowerShell-Funktionen enthält, die Sie bereits verwenden. Das andere Modul ist PSReadline. Sie können diese Startmodule mit dem Befehl Get-Module anzeigen.

Listing modules with Get-Module

Das bedeutet jedoch nicht, dass dies eine vollständige Liste aller verfügbaren Module ist. Seit PowerShell 3 werden installierte Module bei Bedarf importiert. Wenn Sie eine ältere Version von PowerShell verwenden, müssen Sie den Befehl Import-Module verwenden, um das Modul zuerst zu importieren, bevor Sie eines der Befehle verwenden können.

Es gibt Situationen, in denen Sie auch in späteren Versionen Import-Module verwenden möchten. Wenn Sie ein Modul importieren möchten, nachdem es bereits installiert wurde, können Sie Import-Module wie folgt verwenden:

Importing modules with Import-Module

Während Get-Module alle importierten Module anzeigt, werden nicht importierte Module nicht angezeigt. Sie können dann den Parameter ListAvailable verwenden, um alle anderen verfügbaren Module anzuzeigen.

Listing all available modules with Get-Module -ListAvailable

Nicht alle Befehle werden standardmäßig angezeigt.

Die Eigenschaft ExportedCommands enthält eine Liste aller verfügbaren Befehle, die aus dem Modul exportiert werden. Es können Unterschiede zwischen dieser Liste und dem Inhalt der Moduldatei auftreten. Exportierte Befehle sind eine Funktion, die in das Modulmanifest eingebaut ist und es dem Autor ermöglicht, eine Funktion als versteckt zu kennzeichnen. Modulautoren können auch das Cmdlet Export-ModuleMember verwenden, aber das ist nicht Gegenstand dieses Artikels.

Modulautoren möchten möglicherweise eine Funktion verstecken, weil sie dazu gedacht ist, andere Funktionen zu unterstützen und nicht für Benutzer sichtbar sein soll. Um eine Funktion zu verstecken, würde der Autor sie aus dem FunctionsToExport-Array im Manifest ausschließen. Hier sehen Sie eine erweiterte Ansicht der ExportedCommands-Eigenschaft.

Viewing exported commands

Module importieren

Es gibt viele Möglichkeiten, Module zu verwenden. Sie können das Modul manuell importieren, indem Sie den Pfad zu den Moduldateien angeben. Dadurch können Sie das Modul testen und aktualisieren, ohne viel Arbeit zu haben. Dies ermöglicht jedoch keine hohe Portabilität, da Sie den genauen Pfad zum Modul verwenden müssten. PowerShell importiert auch keine Module automatisch, die nicht in der Variablen $env:PSModulePath enthalten sind.

Auswahlweises Importieren von Befehlen

Sie können Import-Module verwenden, um nur bestimmte Funktionen anstelle des gesamten Moduls zu importieren, indem Sie den Parameter Function verwenden. Dies kann Zeit sparen, wenn Module von Remote-Systemen importiert werden, wie z. B. die Office 365-Module.

Module für alle Benutzer

Module, die für alle Benutzer installiert sind, werden in C:\Program Files\WindowsPowerShell\Modules abgelegt. Dieses Verzeichnis enthält viele vorinstallierte Module, einschließlich aller mit dem Standardumfang AllUsers installierten Module.

Aktuelle Benutzermodule

Wenn Sie ein Modul installieren, es jedoch nur von einem einzelnen Benutzer verwenden möchten, gibt es einen Gültigkeitsbereich CurrentUser. Dadurch werden die Moduldateien in Ihrem Dokumentenordner unter C:\Users\<Benutzername>\Documents\WindowsPowerShell\Modules abgelegt. Dies kann in einer Umgebung nützlich sein, in der Sie die Ordnerumleitung mit dem Dokumentenordner verwenden.

In diesem Fall können Sie ein Modul auf einem Computer installieren und es auf einem anderen verwenden, da beide den gleichen Dokumentenordner teilen würden.

Systemmodule

Zur Vollständigkeit gibt es auch ein Modulverzeichnis unter C:\Windows\System32\WindowsPowerShell\1.0\Modules. Technisch gesehen würde ein Modul, das in diesem Pfad platziert wird, wie einer der anderen Pfade importiert werden, jedoch wird dies nicht empfohlen, da dieser Pfad für Microsofts Systemmodule reserviert ist.

Die Namensgebung ist wichtig.

Sie können Ihr Modul manuell in einem dieser Pfade platzieren, um es standardmäßig in einer neuen Sitzung verfügbar zu machen, jedoch müssen Sie sicherstellen, dass Sie die erforderliche Namensgebung für Module einhalten. Der Ordner, in dem die Moduldateien platziert werden, muss den gleichen Namen wie die psm1-Moduldatei und das psd1-Modulmanifest haben, sofern vorhanden.

Die Verwendung von Get-Module -ListAvailable, auf die wir zuvor hingewiesen haben, bezieht sich auf diese Pfade. Sie können alle Modulpfade mit $env:PSModulePath -Split ';' anzeigen. Sie werden möglicherweise andere Pfade in der Liste bemerken als diejenigen, die hier angezeigt werden. Viele Programme fügen beim Installieren ihre eigenen Modulpfade hinzu. Ein Beispiel dafür ist SQL, das eigene Module in seinen eigenen Modulpfaden enthält.

Viewing module paths with $env:PSModulePath

Es gibt auch einige Module, die Sie mit einem anderen Verfahren installieren würden. Ein bedeutendes Beispiel dafür ist das ActiveDirectory-Modul. Von Windows 7 bis Windows 10 1803 würden Sie dies mit dem Remote Server Administration Tools (RSAT) Installer installieren.

Auf neueren Versionen von Windows 10 (1809+) ist dies nur über die Features On Demand verfügbar. Die Installation von RSAT installiert die ActiveDirectory-Module und viele andere, die Sie zur Verwaltung anderer Windows-Rollen verwenden würden. Auf Windows Server-Betriebssystemen werden diese Module über den Server-Manager installiert.

Importieren von Remote-Modulen (Implizites Remoting)

Es gibt Fälle, in denen es nicht praktikabel ist, ein Modul lokal auszuführen. Stattdessen ist es besser, eine Verbindung zu einem Remote-Gerät herzustellen und ein darauf installiertes Modul zu importieren. Dabei werden die Befehle tatsächlich auf der Remote-Maschine ausgeführt. Dies wird häufig mit den Office 365-Modulen von Microsoft verwendet. Viele von ihnen stellen eine Verbindung zu einem Office 365-Server her, der dann ein Modul importiert. Wenn Sie einen beliebigen Befehl ausführen, wird er auf dem Remote-Server ausgeführt und die Ausgabe wird an Ihre Sitzung zurückgesendet.

Eine weitere Verwendung des Imports von Remote-Modulen besteht darin, wenn Sie das Modul lokal nicht installiert haben. Dies wäre der Fall, wenn Sie das ActiveDirectory-Modul nicht installiert hätten, aber versuchen würden, es zu importieren.

Module not installed

Um ein Remote-Modul zu importieren, müssen Sie zunächst eine PSSession erstellen. Sie können New-PSSession verwenden, um die Sitzung zu erstellen. Anschließend importieren Sie das auf dem Remote-Gerät verfügbare Modul unter Verwendung des PSSession-Parameters mit Import-Module.

PS51> $AdminServer = New-PSSession -ComputerName $AdminServerName -Credential (Get-Credential)
PS51> Import-Module -Name ActiveDirectory -PSSession $AdminServer -Prefix 'Rmt'

Durch die Verwendung dieser Methode zum Importieren von Remote-Modulen wird eine schnellere Codeausführung in einer verteilten Umgebung ermöglicht. Wenn Sie beispielsweise von Ihrem Computer aus arbeiten, die Server, auf denen Sie arbeiten, sich jedoch in den USA befinden, kann es erheblich länger dauern, bestimmte Befehle lokal gegen die Server auszuführen. Das Ausführen der Befehle auf einem Server und das Zurücksenden der Ausgabe an Ihre lokale Sitzung ist jedoch viel schneller.

Hinzufügen eines Modulpräfixes

Sie können auch ein Präfix zu den Funktionen hinzufügen, die von der Remote-Maschine importiert werden. Diese Option ist beim Import lokaler Module verfügbar, wird jedoch selten außerhalb des Testens von verschiedenen Versionen eines Moduls nebeneinander verwendet.

Wenn Sie den obigen Importbefehl ausgeführt haben und dies ist das, was Sie sehen, wenn Sie die Befehle anzeigen:

Viewing all available commands in a module

In diesem Fall können Sie ein Präfix verwenden, um anzuzeigen, dass es sich nicht um ein lokales Modul handelt. Dies kann in Fällen verwendet werden, in denen Sie ein Modul importieren, das auch lokal verfügbar ist. Durch das Hinzufügen des Präfixes wird die Verwirrung darüber reduziert, wo der Code ausgeführt wird.

Module entfernen

Sie können auch ein Modul aus der aktuellen Sitzung entfernen, ohne Remove-Module zu verwenden. Dadurch wird ein Modul aus der lokalen Sitzung entfernt, ohne die Moduldateien zu löschen. Sie können dies beispielsweise verwenden, wenn Sie eine Remotesitzung verwendet haben, um ein Modul zu verwenden. Sie können Remove-Module verwenden, um Ihre Sitzung aufzuräumen, und dann die Remotesitzung trennen.

Removing a module from the session

Eine weitere Verwendung von Remove-Module besteht darin, wenn Sie Änderungen an einem Modul vornehmen und keine neue PowerShell-Sitzung starten möchten. In diesem Fall würden Sie Remove-Module gefolgt von Import-Module verwenden, um es in Ihre Sitzung neu zu laden. Alternativ können Sie den Parameter Force mit Import-Module verwenden. Dadurch wird das Entladen und Neuladen des Moduls für Sie abgeschlossen.

Was macht ein PowerShell-Modul aus

A module can consist of one or more files. To meet the minimum requirements for a module, you must have a module file. This can be a PSM1 file or any other module file such as a binary module file. To build upon that, your psm1 should have functions defined in it, or it will not be much use to anyone.

Während es keine Anforderungen dafür gibt, wie die Funktionen aussehen oder was sie tun sollen, gibt es einige Richtlinien. Es ist in der Regel bevorzugt, dass sich alle Funktionen in einem Modul um das gleiche Konzept drehen.

Module enthalten funktional verwandte Funktionen.

Zum Beispiel enthält das Modul ActiveDirectory nur Funktionen, die auf irgendeine Weise mit Active Directory interagieren. Normalerweise enthalten die Funktionsnamen auch ein Präfix. Wenn wir das Modul ActiveDirectory als Beispiel nehmen, beginnen alle Substantive in den Funktionsnamen mit AD.

Durch die Verwendung dieser Richtlinien wird die Auffindbarkeit der Funktionen verbessert. Stellen Sie sich vor, Sie haben gerade dieses neue Modul importiert und möchten durch die Funktionen navigieren. Dies ist viel einfacher, wenn alle Funktionen eine ähnliche Namensstruktur haben. Obwohl Sie häufig Module sehen, die mit PS beginnen, ist dieses Präfix offiziell nur für Microsoft-Module reserviert. Sie werden wahrscheinlich kein Problem verursachen, wenn Sie PS am Anfang Ihres Moduls verwenden, aber es könnte zu einem Konflikt mit einem anderen Modulnamen kommen.

Unter Verwendung dieser Richtlinien könnten Sie beispielsweise eine Reihe von Funktionen haben, die alle mit der Interaktion mit der Registrierung zu tun haben:

function Get-ATARegistryKey {...}

function Set-ATARegistryKey {...}

Modulmanifeste

Um das Textmodul-Datei weiter auszubauen, können Sie auch ein Modulmanifest hinzufügen. Diese Dateien haben die Erweiterung PSD1 und enthalten Metadaten über das Modul. Hier würden Sie Informationen zum Autor, zur Beschreibung des Moduls, zu anderen erforderlichen Modulen und vielen anderen Attributen angeben. Um in einem Repository zu veröffentlichen, müssen die Felder Author und Description ausgefüllt sein.

Hier ist ein Beispiel für ein Manifest, das wir für unser Registrierungsmodul haben könnten:

#Modul-Manifest für das Modul 'ATARegistry'
#Generiert von: Tyler
#Generiert am: 11.08.2019
@{
	#Skriptmodul oder Binärmodul-Datei, die mit diesem Manifest verknüpft ist.
	RootModule = 'ATARegistry'
	#Versionsnummer dieses Moduls.
	ModuleVersion = '1.0'
	#Unterstützte PSEditions
	#CompatiblePSEditions = @()
	#ID zur eindeutigen Identifizierung dieses Moduls
	GUID = 'fef619fa-016d-4b11-a09d-b222e094de3e'
	#Autor dieses Moduls
	Author = 'Tyler Muir'
	#Unternehmen oder Anbieter dieses Moduls
	CompanyName = 'Adam the Automator'
	#Urheberrechtserklärung für dieses Modul
	Copyright = '(c) 2019 tyler. All rights reserved.'
	#Beschreibung der Funktionalität, die dieses Modul bereitstellt
	Description = 'This is a test module.'
	#Mindestversion des Windows PowerShell-Engines, die von diesem Modul benötigt wird
	#PowerShellVersion = ''
	#Name des Windows PowerShell-Hosts, der von diesem Modul benötigt wird
	#PowerShellHostName = ''
	#Mindestversion des Windows PowerShell-Hosts, die von diesem Modul benötigt wird
	#PowerShellHostVersion = ''
	#Mindestversion des Microsoft .NET Frameworks, die von diesem Modul benötigt wird. Diese Voraussetzung gilt nur für die PowerShell Desktop Edition.
	#DotNetFrameworkVersion = ''
	#Mindestversion der Common Language Runtime (CLR), die von diesem Modul benötigt wird. Diese Voraussetzung gilt nur für die PowerShell Desktop Edition.
	#CLRVersion = ''
	#Prozessorarchitektur (None, X86, Amd64), die von diesem Modul benötigt wird
	#ProcessorArchitecture = ''
	#Module, die in die globale Umgebung importiert werden müssen, bevor dieses Modul importiert wird
	#RequiredModules = @()
	#Assemblys, die vor dem Import dieses Moduls geladen werden müssen
	#RequiredAssemblies = @()
	#Skriptdateien (.ps1), die in der Umgebung des Aufrufers ausgeführt werden, bevor dieses Modul importiert wird.
	#ScriptsToProcess = @()
	#Typdateien (.ps1xml), die beim Import dieses Moduls geladen werden sollen
	#TypesToProcess = @()
	#Formatdateien (.ps1xml), die beim Import dieses Moduls geladen werden sollen
	#FormatsToProcess = @()
	#Module, die als geschachtelte Module des Moduls angegeben in RootModule/ModuleToProcess importiert werden sollen
	#NestedModules = @()
	#Funktionen, die aus diesem Modul exportiert werden sollen. Verwenden Sie aus Leistungsgründen keine Platzhalterzeichen (*) und löschen Sie den Eintrag nicht. Verwenden Sie ein leeres Array, wenn keine Funktionen exportiert werden sollen.
	FunctionsToExport = @('Get-RegistryKey','Set-RegistryKey')
	#Cmdlets, die aus diesem Modul exportiert werden sollen. Verwenden Sie aus Leistungsgründen keine Platzhalterzeichen (*) und löschen Sie den Eintrag nicht. Verwenden Sie ein leeres Array, wenn keine Cmdlets exportiert werden sollen.
	CmdletsToExport = @()
	#Variablen, die aus diesem Modul exportiert werden sollen. VariablesToExport = '*'
	#Aliases, die aus diesem Modul exportiert werden sollen. Verwenden Sie aus Leistungsgründen keine Platzhalterzeichen (*) und löschen Sie den Eintrag nicht. Verwenden Sie ein leeres Array, wenn keine Aliases exportiert werden sollen.
	AliasesToExport = @()
	#DSC-Ressourcen, die aus diesem Modul exportiert werden sollen
	#DscResourcesToExport = @()
	#Liste aller mit diesem Modul verpackten Module
	#ModuleList = @()
	#Liste aller mit diesem Modul verpackten Dateien
	#FileList = @()
	#Private Daten, die an das in RootModule/ModuleToProcess angegebene Modul übergeben werden sollen. Dies kann auch einen PSData-Hashtable mit zusätzlichen Modulmetadaten enthalten, die von PowerShell verwendet werden.
	PrivateData = @{
		PSData = @{
			#Tags, die diesem Modul zugewiesen sind. Diese helfen bei der Modulsuche in Online-Galerien.
			#Tags = @()
			#Eine URL zur Lizenz für dieses Modul.
			#LicenseUri = ''
			#Eine URL zur Hauptwebsite für dieses Projekt.
			#ProjectUri = ''
			#Eine URL zu einem Symbol, das dieses Modul repräsentiert.
			#IconUri = ''
			#ReleaseNotes dieses Moduls
			#ReleaseNotes = ''
		} 
		#Ende des PSData-Hashtable
	} 
	#Ende des PrivateData-Hashtable
	#HelpInfo-URI dieses Moduls
	#HelpInfoURI = ''
	#Standardpräfix für Befehle, die aus diesem Modul exportiert werden. Überschreiben Sie das Standardpräfix mit Import-Module -Prefix.
	#DefaultCommandPrefix = ''
}

Obwohl dies auf den ersten Blick einschüchternd wirken mag, hat Microsoft ein praktisches Cmdlet, das Sie verwenden können, um ein Modulmanifest zu generieren. Der enthaltene Befehl ist New-ModuleManifest. Um das oben gezeigte Manifest zu generieren, könnten Sie Folgendes verwenden:

PS51> New-ModuleManifest -Path .\Scripts\TestModule.psd1 -Author 'Tyler Muir' -CompanyName 'Adam the Automator' -RootModule 'TestModule.psm1' -FunctionsToExport @('Get-RegistryKey','Set-RegistryKey') -Description 'This is a test module.'

Externe Hilfedateien

In einigen Modulen können auch externe Hilfedateien vorhanden sein. Sie können anhand des <Modulname>-Help.xml am Ende des Dateinamens identifiziert werden. Diese externen Hilfedateien enthalten dieselben Informationen, die normalerweise in der Befehlshilfe enthalten wären, die Sie in einer Funktionsdefinition finden könnten.

Dies erfordert auch, dass Sie # .ExternalHelp <Modulpfad>-Help.xml zu Ihrer Funktion hinzufügen, um sicherzustellen, dass sie ordnungsgemäß funktioniert, wenn Sie den Get-Help-Befehl nach dem Importieren des Moduls verwenden. Externe Hilfedateien kommen normalerweise nur bei sehr großen Modulen vor und sind daher nicht relevant.

Obwohl dies die häufigsten Dateitypen sind, die Sie in einem Modul sehen werden, sind dies nicht die einzigen Dateien. Manchmal sehen Sie binäre Dateien zusätzlich zu einem Textmodul, da es auch andere Abhängigkeiten geben kann. Durch das Durchsuchen der Modulpfade können Sie viele Beispiele für zusätzliche Dateitypen in Modulen finden.

Um nicht standardmäßige Moduldateien ordnungsgemäß zu veröffentlichen, sollten Sie weitere Dateien im FileList-Parameter Ihres Modulmanifests angeben.

Im Modulmanifest finden Sie viele andere Parameter, die derzeit leer sind. Sie können diese verwenden, um andere Anforderungen für die Verwendung Ihres Moduls festzulegen. Zum Beispiel können Sie die Versionen von PowerShell definieren, mit denen das Modul funktionieren kann. Wenn Sie versuchen, das Modul in einer nicht unterstützten Version von PowerShell zu importieren, sehen Sie Folgendes:

Requiring certain versions of PowerShell

PSRepositories

Eine der wichtigsten Vertriebsoptionen für Module ist ein PSRepository. Aus einer Entfernung von 1000 Fuß betrachtet ist ein PSRepository ein Ort, an dem mehrere Personen oder Geräte auf die Moduldateien zugreifen können. Dabei handelt es sich häufig um Webserver, auf denen Sie Dateien veröffentlichen können.

Sie können auch ein Verzeichnis für das Repository verwenden, dies schränkt jedoch die Funktionalität Ihres Repositorys ein. Sie können ein PSRepository selbst hosten oder eine der vielen im Internet verfügbaren Optionen wie die PowerShell Gallery nutzen. Sie können Ihre PSRepositories mit dem Befehl Get-PSRepository anzeigen.

Default PowerShell NuGet repositories

Standardmäßig haben Sie nur einen Eintrag und dieser bezieht sich auf die PowerShell Gallery. Sie werden möglicherweise feststellen, dass er als nicht vertrauenswürdig gekennzeichnet ist. Dies liegt daran, dass PowerShell Sie darauf hinweist, dass Sie möglicherweise Code verwenden, der nicht von Microsoft geschrieben und genehmigt wurde. Dies bedeutet, dass Sie vor der Installation von Modulen aus diesem Repository eine explizite Berechtigung erteilen müssen.

Hinzufügen von PSRepositories

Sie können auch Ihre eigenen Repositories hinzufügen. Um der PowerShell Gallery zu vertrauen, können Sie Get-PSRepository -Name PSGallery | Set-PSRepository -InstallationPolicy Trusted ausführen oder Sie akzeptieren die Warnung beim ersten Mal, wenn Sie ein Modul aus der PowerShell Gallery installieren.

Alle Befehle, die Sie verwenden würden, um mit diesen PSRepositories zu interagieren, finden Sie im PowerShellGet-Modul. Sie können die Funktionen hier sehen:

Commands in the PowerShellGet module

Es kann erforderlich sein, das PowerShellGet-Modul zu aktualisieren, bevor Sie mit bestimmten Repositories interagieren.

Module finden

Ein weiteres wichtiges Feature bei der Verwendung eines PSRepository ist die Möglichkeit, nach Modulen zu suchen. Dies wird mit dem Befehl „Find-Module“ erreicht. Es gibt mehrere Möglichkeiten, um nach spezifischen Modulen zu suchen, aber vorerst können Sie nach den VMware-Modulen suchen, indem Sie Folgendes eingeben:

Finding modules on the PowerShell Gallery

Dadurch werden alle Module angezeigt, die mit VMware beginnen. Obwohl die meisten davon von VMware stammen, müssen Sie das Autor-Attribut überprüfen, um zu sehen, wer das Modul veröffentlicht hat.

Da jeder in die PowerShell Gallery hochladen kann, stehen Tausende von Modulen zur Verfügung. Dies bedeutet, dass Sie möglicherweise Module finden, die für Ihren Anwendungsfall nicht ordnungsgemäß funktionieren. Viele Module, die Sie finden, sind Open Source, sodass Sie zu ihrer Verbesserung beitragen können.

Module installieren

Um den Befehl „Install-Module“ verwenden zu können, müssen Sie ein vertrauenswürdiges PSRepository haben, das das Modul hostet. Dies kann die PowerShell Gallery, ein anderes Internet-PSRepository oder eine selbst gehostete Site sein. Sie können den Befehl „Find-Module“ verwenden, um das Modul vor der Installation zu überprüfen.

Finding modules installed from a PSRepository

Sie können auch die Version eines Moduls festlegen, indem Sie die Parameter „MinimumVersion“, „MaximumVersion“ oder „RequiredVersion“ verwenden.

Um alle mit Install-Module installierten Module anzuzeigen, können Sie Get-InstalledModule verwenden. Dadurch werden alle Module aufgelistet, die im AllUsers– oder CurrentUser-Bereich installiert sind.

Deinstallation von Modulen

Wie Sie ein Modul installieren können, können Sie es auch deinstallieren. Wenn das Modul nicht über den Befehl Install-Module installiert wurde, können Sie es nicht mit dem Befehl Uninstall-Module deinstallieren.

Uninstalling modules installed from a PSRepository with Uninstall-Module

Wie Sie hier sehen können, versuchen wir, das Modul ActiveDirectory zu deinstallieren. Da dieses Modul nicht mit Install-Module installiert wurde, erhalten Sie einen Fehler, wenn Sie Uninstall-Module verwenden. Um dieses Modul zu deinstallieren, müssten Sie es rückgängig machen, wie Sie es installiert haben.

Um eine erfolgreiche Deinstallation eines Moduls zu sehen, können Sie das zuvor installierte Modul VMware.PowerCLI deinstallieren.

Uninstalling a module downloaded from the PowerShell Gallery

Auch wenn Sie VMware.PowerCLI deinstalliert haben, können Sie sehen, dass immer noch viele Abhängigkeiten installiert sind. Wenn Sie alle Module deinstallieren möchten, könnten Sie Get-InstalledModule VMware.* | Uninstall-Module -Force verwenden.

Der Grund, warum Sie Schwierigkeiten haben, dieses Modul vollständig zu deinstallieren, liegt darin, dass es so viele Abhängigkeiten hat. Zusätzlich sind einige dieser Module voneinander abhängig, weshalb der Parameter Force erforderlich ist.

Aktualisieren von Modulen

Nun, da Sie wissen, wie Sie ein Modul installieren und deinstallieren können, fragen Sie sich vielleicht, wie Sie ein Modul aktualisieren, das Sie installiert haben.

Genau wie bei anderen Vorgängen können Sie das Modul, wenn es nicht mit Install-Module installiert wurde, nicht mit den PowerShell-Befehlen aktualisieren. Sie können Update-Module verwenden, um ein Modul auf die neueste Version oder eine neuere bestimmte Version zu aktualisieren.

Es gibt auch einen Schalter für AllowPreRelease, mit dem Sie auf eine Version aktualisieren können, die noch nicht offiziell veröffentlicht wurde. Manchmal kann dies hilfreich sein, da möglicherweise ein Fehler behoben wurde, den Sie erleben, oder eine neue Funktion hinzugefügt wurde, die Sie verwenden möchten.

Updating modules with Update-Module

Prüfen/Speichern eines Moduls

Einer der weniger verwendeten Befehle, der beim Überprüfen von Modulen vor der Verwendung sehr hilfreich ist, ist Save-Module. Mit diesem Befehl können Sie ein Modul herunterladen, ohne es zu installieren.

Sie können dann die Dateien überprüfen, und wenn es sich nicht um ein binäres Modul handelt, können Sie den Code des Moduls öffnen und anzeigen. Dies ist nicht nur gut, um sicherzustellen, dass ein Modul nichts Böswilliges tut, sondern auch um zu lernen, wie andere ihre Module strukturieren.

Downloading modules with Save-Module

In diesem Beispiel wird nicht nur das Modul VMware.PowerCLI heruntergeladen, sondern auch alle Abhängigkeiten. Hier ist, was in dem Ordner VMware.PowerCLI angezeigt wird:

VMware.PowerCLI module contents

Dies ist ein gutes Beispiel dafür, dass manchmal nicht standardmäßige Moduldateien im Modul enthalten sind, wie beispielsweise die Endbenutzer-Lizenzvereinbarung.

Erstellen eines eigenen Moduls

Sie haben nun gesehen, wie Sie mit einem Modul eines anderen Benutzers interagieren können. Jetzt möchten Sie lernen, wie Sie Ihr eigenes erstellen können, um Ihren Code für Skalierbarkeit zu optimieren.

Erstellen von Vorlagendateien

Zunächst müssen Sie einen Ordner für alle Ihre Moduldateien erstellen. Nachdem Sie den Container erstellt haben, müssen Sie Ihre Moduldatei erstellen. Sie müssen sicherstellen, dass Ihre Moduldatei den gleichen Namen wie Ihr Ordner hat, sonst erkennt PowerShell das Modul beim Veröffentlichen nicht korrekt.

PS51> New-Item -Path .\Scripts -Name ATARegistry -ItemType Directory
PS51> New-Item -Path .\Scripts\ATARegistry -Name ATARegistry.psm1

Jetzt möchten Sie auch ein Manifest verwenden, das Sie ebenfalls mit dem Container- und Moduldateinamen benennen müssen.

PS51> New-ModuleManifest -Path .\Scripts\ATARegistry\ATARegistry.psd1 -Author 'Tyler Muir' -CompanyName 'Adam the Automator' -RootModule ATARegistry.psm1 -Description 'Used for interacting with registry keys'

Mit dem Container, der Moduldatei und der Manifestdatei haben Sie ein voll funktionsfähiges Modul. Sie könnten dieses Modul in einem PSRepository veröffentlichen und es überall installieren, wo Sie möchten. Da die Moduldatei jedoch leer ist, wird es Ihnen wahrscheinlich nicht viel nützen. Sie können diese Dateien dennoch verwenden, um das Veröffentlichen zu testen und sicherzustellen, dass Ihr Repository funktioniert.

Registrierung eines PSRepository

Vor dem Veröffentlichen Ihres Moduls müssen Sie Ihrer Sitzung ein weiteres PSRepository hinzufügen. Für Tests können Sie einen lokalen Pfad als Ihr PSRepository verwenden, da es einfach einzurichten und abzubauen ist.

Normalerweise würden Sie, wenn Sie ein PSRepository mit einem Verzeichnis einrichten würden, sicherstellen wollen, dass mehrere Computer darauf zugreifen können. Sie können ein lokales Repository wie folgt erstellen:

PS51> New-Item -Path C:\ -Name Repo -ItemType Directory
PS51> Register-PSRepository -Name 'LocalRepo' -SourceLocation 'C:\Repo' -PublishLocation 'C:\Repo' -InstallationPolicy Trusted

Wenn Sie nur aus dem PSRepository herunterladen und nie veröffentlichen würden, könnten Sie den Parameter PublishLocation ausschließen.

Veröffentlichen Ihres Moduls

Da Sie die Installationsrichtlinie bereits auf „vertrauenswürdig“ gesetzt haben, erhalten Sie keine Bestätigung, um die Installation eines Moduls aus dem Repository zuzulassen. Jetzt, da Sie ein neues PSRepository zur Verfügung haben, können Sie Ihr Modul mit dem Befehl Publish-Module -Name .\Scripts\ATARegistry -Repository LocalRepo veröffentlichen.

Nachdem Sie Ihr Modul veröffentlicht haben, können Sie die oben genannten Befehle verwenden, um das Modul zu finden und zu installieren.

Jetzt, da Sie das Modul installiert haben, können Sie den Befehl Get-Module verwenden, um das Modul in Ihre lokale Sitzung zu importieren. Da Sie keine Funktionen zum Array FunctionsToExport im Manifest hinzugefügt haben, ist die Eigenschaft ExportedCommands leer.

No exported commands

Hinzufügen zu Ihrem Modul

Jetzt, da Sie wissen, dass Sie Ihr Modul veröffentlichen und installieren können, können Sie damit beginnen, einige Funktionen hinzuzufügen. Sie könnten eine Funktion hinzufügen, die einen Registrierungsschlüssel zurückgibt, sodass es wie folgt aussieht:

function Get-ATARegistryKey {
    param (
        [string]$Path
    )
    Get-Item $Path
}

Wenn Sie das Manifest unverändert lassen und versuchen, Ihr neues Modul hochzuladen, würden Sie auf zwei Probleme stoßen. Erstens würden Sie einen Fehler erhalten, der besagt, dass die Version Ihres Moduls bereits in Ihrem Repository vorhanden ist. Dies liegt daran, dass Sie die Modulversion nicht in der Manifestdatei geändert haben.

Exportieren von Modulfunktionen

Das andere Problem wäre, dass Sie nach dem Importieren des Moduls immer noch keine Funktionen in der Eigenschaft ExportedCommands sehen würden, da Sie Ihre neue Funktion nicht zum Manifest hinzugefügt haben.

Obwohl Ihre Funktion ohne Auflistung in der Liste FunctionsToExport verwendet werden könnte, wäre es viel schwieriger, sie zu finden.

Solange Sie kein leeres Array, @(), für Ihre FunctionsToExport definieren, werden standardmäßig alle Funktionen, Variablen und Aliase exportiert.

Um diese beiden Probleme zu beheben, können Sie Ihre Moduldatei wie folgt aktualisieren:

ModuleVersion = '1.1'
FunctionsToExport = 'Get-RegistryKey'

Jetzt, da Sie eine Funktion zu Ihrem Modul hinzugefügt haben und Ihre Manifestdatei aktualisiert haben, um diese Änderungen widerzuspiegeln, können Sie die neue Version Ihres Moduls mit demselben Befehl wie zuvor veröffentlichen.

PS51> Publish-Module -Name .\Scripts\ATARegistry -Repository LocalRepo.

Entscheidung zwischen FunctionsToExport und Export-ModuleMember

Beim Exportieren von Modulmitgliedern gibt es zwei ähnliche Funktionen in PowerShell. Die Herausforderung besteht darin, zwischen den beiden zu wählen. Beide sind korrekt, aber je nach Ihren Anforderungen kann eine besser funktionieren als die andere.

Wenn Sie die exportierten Funktionen dynamisch steuern möchten, verwenden Sie Export-ModuleMember, da Sie eine Liste der zu exportierenden Funktionen übergeben können. Dies wird in der Regel verwendet, wenn mehrere einzelne Funktionen-PS1-Dateien dot-sourced werden. Indem Sie die internen Funktionen in einen privaten Ordner und exportierbare Funktionen in einen öffentlichen Ordner aufteilen, können Sie diese leicht exportieren, indem Sie alle öffentlichen Funktionen an die Funktion Export-ModuleMember übergeben.

A few notes about Export-ModuleMember:

  • Es überschreibt das Verhalten von FunctionsToExport, daher hat FunctionsToExport keine Auswirkungen, wenn ein Export-ModuleMember-Befehl verwendet wird.
  • Export-ModuleMember exportiert Variablen und Aliase nicht automatisch, es sei denn, sie werden explizit definiert. Im Gegensatz dazu exportiert FunctionsToExport diese Werte.
  • Mehrere Export-ModuleMember-Befehle können verwendet werden und sie werden gestapelt anstatt die Priorität zu haben.

Wenn Sie keine Änderungen an Ihrer Funktionenliste erwarten, funktioniert die Verwendung der FunctionsToExport-Konfiguration in der Modulmanifestdatei gut und erfordert nicht, dass Sie Variablen und Aliase explizit exportieren.

Das Aktualisieren Ihres Moduls

Der letzte Schritt besteht darin, Ihr Modul in Ihrer Sitzung zu aktualisieren, um die aktualisierten Dateien verwenden zu können. Verwenden Sie Update-Module ATARegistry, um das Update herunterzuladen, das Sie gerade im Repository veröffentlicht haben.

Exported commands now show up

Jetzt können Sie sehen, dass Sie die neue Version des Moduls haben und die Funktion sehen können, die Sie in der Manifestdatei definiert haben.

Erstellen von Hilfsinhalten

Eine der Optionen, die zuvor übersehen wurde, ist das Hilfesystem, das in PowerShell integriert ist. Sie haben wahrscheinlich irgendwann Get-Help für eine Funktion verwendet. Diese Informationen können auf zwei Hauptarten hinzugefügt werden.

Die erste Möglichkeit besteht darin, kommentarbasierte Hilfe in die Funktionsdefinition aufzunehmen. Dies ist in der Regel die Art und Weise, wie viele Modulautoren es umsetzen. Der andere Weg besteht darin, eine externe Hilfedatei zu verwenden. Sie können den Parameter Full verwenden, um alles anzuzeigen, was die Hilfe zu bieten hat.

Finding help with Get-Help

Wie Sie sehen können, gibt es wirklich nicht viele Informationen und die wenigen Informationen, die Sie erhalten, wären wahrscheinlich für niemanden hilfreich.

Sie können einige kommentarbasierte Hilfe zu Ihrer Moduldatei hinzufügen, um diese Felder im Hilfesystem zu füllen. Sie können alle Optionen für kommentarbasierte Hilfe lesen, indem Sie Get-Help about_Comment_Based_Help verwenden.

Jetzt können Sie Ihre Funktion wie folgt aktualisieren. Dies ist eine Liste der am häufigsten verwendeten Hilfsparameter, aber alle diese sind immer noch optional und es können andere hinzugefügt werden.

Jetzt sieht Ihre Funktion so aus:

 function Get-RegistryKey {
	<#
    .ZUSAMMENFASSUNG
    Gibt den Registrierungsschlüssel anhand des angegebenen Pfads zurück.
    .BESCHREIBUNG
    Die Funktion verwendet den Get-Item-Befehl, um die Informationen für einen angegebenen Registrierungsschlüssel zurückzugeben.
    .PARAMETER Pfad
    Der Pfad, nach dem ein Registrierungsschlüssel gesucht wird.
    .BEISPIEL
    Get-RegistryKey -Path 'HKLM:\HARDWARE\DESCRIPTION\System'
    .EINGABEN
    System.String
    .AUSGABEN
    Microsoft.Win32.RegistryKey
    .ANMERKUNGEN
    Dieses Modul ist ein Beispiel dafür, wie eine gut dokumentierte Funktion aussehen könnte.
    .LINK
    
ATA Learning
#>
param( [string]$Path ) Get-Item $Path }

Es gibt einige spezielle Hilfsparameter wie .FORWARDHELPTARGETNAME. Diese Option leitet alle eingehenden Hilfsanfragen an einen anderen Befehl weiter. Dies könnte in einem Fall verwendet werden, in dem die Hilfe dieselben Informationen für mehrere Befehle anzeigen soll.

Jetzt, da Sie die Hilfe hinzugefügt haben, können Sie die Version in der Modulmanifestdatei aktualisieren, die neue Version veröffentlichen und die installierte Version für Ihre Sitzung wie zuvor aktualisieren.

Wenn Sie sich jetzt die Hilfe für die Funktion ansehen, sehen Sie, dass viel mehr Informationen verfügbar sind. Dies ist eine großartige Möglichkeit, Dokumentation zur Verwendung der Funktionen einzuschließen, insbesondere für jemanden, der weniger Erfahrung hat und möglicherweise nicht schnell verstehen kann, was das Modul durch Betrachten des Codes macht.

Getting full help content with Get-Help

Im Falle einer externen Hilfedatei ist die hinzugefügte Information dieselbe, aber die Informationen werden in einer separaten Datei platziert und innerhalb der Funktion verlinkt.

Wenn Sie im Modulpfad AllUsers nachsehen, können Sie die Version des Moduls und alle Moduldateien sehen, die Sie installiert haben.

Folder name is the module version

Wenn Sie zu Ihrem PSRepository-Pfad C:\Repo zurückkehren, den Sie zuvor erstellt haben, können Sie eine Reihe von NUPKG-Dateien sehen. Es wird eine für jede veröffentlichte Version geben. Dies sind komprimierte Versionen dessen, was Sie veröffentlicht haben, wenn Sie Publish-Module verwenden.

Zusammenfassung

Sobald Sie mit der PowerShell-Konsole, PowerShell als Sprache und dem Schreiben von Skripten vertraut sind, ist das Erstellen eigener Module der letzte Schritt. Module ermöglichen es Ihnen, nützliche Tools in PowerShell zu entwickeln. Wenn Sie Module für einen bestimmten Zweck entwerfen und korrekt erstellen, werden Sie im Laufe der Zeit immer weniger Code schreiben. Sie werden Ihre Modulfunktionen in immer mehr Code einbinden und von dort aus weiterentwickeln.

Modulfunktionen ermöglichen es Ihnen, den Code, den Sie in Skripten wiederholen, abstrakt zu gestalten. Sie stellen „Labels“ dar, auf die später im Code verwiesen werden kann und die jederzeit aufgerufen werden können, anstatt das Rad neu zu erfinden und zu versuchen herauszufinden, wie Sie Ihr Ziel bereits erreicht haben. Module sind die endgültige „Verpackung“ von PowerShell-Code, der ähnlichen Code gruppiert, um Zeitverschwendung bei bereits gelösten Problemen zu vermeiden.

Source:
https://adamtheautomator.com/powershell-modules/