PowerShell 模块路径: 可重用的代码,无需复制粘贴

使用PowerShell模块是PowerShell自动化的重要组成部分。当您开始学习PowerShell时,通常首先使用单个命令。这导致构建脚本,然后进一步构建函数。

通过使用函数,您可以使脚本更加模块化。这使您能够在许多地方重复使用相同的代码,而无需到处复制和粘贴代码。使用函数可以让您花费更少的时间在使用到代码的所有地方做相同的修改。而是可以在一个地方改进您的代码。

要将函数提升到更高的水平,您可以将这些函数组合成一个模块。

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.

先决条件

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.

与模块交互

一旦您打开了PowerShell会话,您将首先使用两个模块。第一个是Microsoft.PowerShell.Utility,其中包含您已经使用的许多基本PowerShell函数。另一个模块是PSReadline。您可以使用Get-Module命令查看这些起始模块。

Listing modules with Get-Module

话虽如此,这并不是所有可用模块的完整列表。自PowerShell 3以来,安装的模块将根据需要导入。如果您正在运行较旧版本的PowerShell,则需要在使用任何命令之前使用Import-Module命令先导入模块。

有时,即使在较新版本中,您仍然希望使用Import-Module。如果您想在模块已安装后导入模块,则可以像这样使用Import-Module

Importing modules with Import-Module

虽然 Get-Module 将显示所有已导入的模块,但您将看不到尚未导入的模块。然后,您可以使用 ListAvailable 参数显示所有其他可用的模块。

Listing all available modules with Get-Module -ListAvailable

默认情况下不显示所有命令

ExportedCommands 属性包含从模块导出的所有可用命令的列表。您可能会在此列表与模块文件中的内容之间看到一些差异。导出的命令是模块清单中内置的一个功能,允许作者将函数保留为隐藏状态。模块作者还可以使用 Export-ModuleMember cmdlet,但这超出了本文的范围。

模块作者可能希望将某个函数隐藏起来,因为它的目的是支持其他函数,而不是供用户使用。要将函数保留为隐藏状态,作者将其从清单中的 FunctionsToExport 数组中排除。在这里,您可以看到 ExportedCommands 属性的扩展视图。

Viewing exported commands

导入模块

有许多方法可以开始使用模块。您可以手动使用模块文件的路径导入模块。这使您能够测试和更新模块,而无需做太多工作。但这并不允许太多的可移植性,因为您必须使用确切的模块路径。PowerShell也不会自动导入不在$env:PSModulePath变量中的模块。

选择性导入命令

您可以使用Import-Module仅通过使用Function参数来导入特定函数而不是整个模块。在从远程系统导入模块时,例如 Office 365 模块,这可以节省时间。

所有用户模块

为所有用户安装的模块将放置在C:\Program Files\WindowsPowerShell\Modules中。此目录包含许多预添加的模块,包括使用默认范围AllUsers使用Install-Module安装的任何模块。

当前用户模块

如果您正在安装模块但只想要单个用户使用它,则有一个CurrentUser范围。这会将模块文件放在您的文档文件夹中的C:\Users\<username>\Documents\WindowsPowerShell\Modules。在使用文档文件夹的环境中,这可能很有用。

在这种情况下,您可以在一台计算机上安装模块并在另一台计算机上使用它,因为它们都将共享相同的文档文件夹。

系统模块

为了完整性,还有一个模块目录位于C:\Windows\System32\WindowsPowerShell\1.0\Modules。虽然从技术上讲,放置在此路径的模块将被像其他路径一样导入,但不建议这样做,因为此路径保留供 Microsoft 系统模块使用。

命名很重要

您可以手动将模块放置在这些路径之一,以使其在新会话中默认可用,但必须确保遵循模块所需的命名。放置模块文件的文件夹必须与 psm1 模块文件和 psd1 模块清单(如果有的话)具有相同的名称。

使用我们之前提到的Get-Module -ListAvailable引用这些路径。您可以使用$env:PSModulePath -Split ';'查看所有模块路径。您可能会注意到列表中有其他路径,而不仅仅是此处显示的路径。许多程序在安装时会添加自己的模块路径。其中一个示例是 SQL,它在其自己的模块路径中包含了自己的模块。

Viewing module paths with $env:PSModulePath

还有一些您可能会使用不同过程安装的模块。其中一个最显着的示例是ActiveDirectory模块。从 Windows 7 到 Windows 10 1803,您将使用远程服务器管理工具(RSAT)安装程序安装此模块。

在 Windows 10(1809+)的新版本中,此模块仅通过Features On Demand可用。安装 RSAT 将安装ActiveDirectory模块以及许多用于管理其他 Windows 角色的模块。在 Windows 服务器操作系统上,这些模块通过服务器管理器安装。

导入远程模块(隐式远程)

有一些情况下,在本地运行模块并不切实际。相反,最好是连接到远程设备并导入其上安装的模块。这样做时,命令实际上是在远程机器上执行的。这经常用于微软的 Office 365 模块。其中许多模块连接到一个 Office 365 服务器,然后导入一个模块。当你运行任何命令时,它们会在远程服务器上运行,然后将输出发送回你的会话。

导入远程模块的另一用途是当你在本地没有安装模块时。这就是当你尝试导入 ActiveDirectory 模块,但本地没有安装它时的情况。

Module not installed

要导入远程模块,首先必须创建一个 PSSession。你可以使用 New-PSSession 来创建会话。然后,使用带有 Import-ModulePSSession 参数导入远程设备上可用的模块。

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

使用这种导入远程模块的方法可以在分布式环境中实现更快的代码执行。例如,如果你是在本地计算机上工作,但你要操作的服务器在美国各地,本地运行某些命令可能需要更长的时间。而在服务器上运行命令,然后将输出反馈到本地会话则快得多。

添加模块前缀

您还可以在从远程机器导入的函数上添加前缀。在导入本地模块时,此选项可用,但在测试不同版本的模块时很少使用。

如果您运行了上述导入命令,并且这是您查看命令时看到的内容:

Viewing all available commands in a module

在这种情况下,您可以使用前缀来显示它不是本地模块。这可用于导入同时也在本地可用的模块的情况。添加前缀可以减少代码执行位置的混淆。

移除模块

您还可以在当前会话中移除模块,而无需使用Remove-Module。这会从本地会话中移除模块,但不会移除模块文件。您可能希望在使用远程会话使用模块的情况下使用此功能。您可以使用Remove-Module清理会话,然后断开远程会话。

Removing a module from the session

Remove-Module的另一个用途是,如果您正在对模块进行更改,而且不想启动新的PowerShell会话。在这种情况下,您将使用Remove-Module,然后使用Import-Module重新加载到您的会话中。或者,您可以使用Import-ModuleForce参数。这将完成模块的卸载和重新加载。

PowerShell模块的组成

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.

虽然对函数的外观或功能没有具体要求,但有一些指导原则。通常,最好将模块中的所有函数都围绕着相同的概念构建。

模块包含类似功能的函数

例如,ActiveDirectory模块只包含与Active Directory有关的函数。通常,函数名称还包含前缀。以ActiveDirectory模块为例,所有函数名称中的名词都以AD开头。

遵循这些指导原则有助于发现函数。想象一下,你刚刚导入了这个新模块,并且想要通过函数进行标签浏览。如果所有函数都具有类似的命名结构,这样做会更容易。虽然你可能经常看到模块以PS开头,但此前缀仅正式保留给微软模块。如果你在模块名称的开头使用PS,可能不会引起问题,但可能会与另一个模块名称冲突。

按照这些指导原则,如果你有一堆与注册表交互有关的函数,你可以这样做:

function Get-ATARegistryKey {...}

function Set-ATARegistryKey {...}

模块清单

为了进一步完善文本模块文件,你还可以包含一个模块清单。这些文件的扩展名为PSD1,包含有关模块的元数据。在这里,你可以包括关于作者、模块描述、其他所需模块以及许多其他属性的信息。要发布到存储库,必须填写作者描述字段。

这是我们可能在注册模块中拥有的清单示例:

#ATARegistry模块清单
#由Tyler生成
#生成日期:2019年8月11日
@{
	#与此清单关联的脚本模块或二进制模块文件
	RootModule = 'ATARegistry'
	#此模块的版本号
	ModuleVersion = '1.0'
	#支持的PSEditions
	#CompatiblePSEditions = @()
	#用于唯一标识此模块的ID
	GUID = 'fef619fa-016d-4b11-a09d-b222e094de3e'
	#此模块的作者
	Author = 'Tyler Muir'
	#此模块的公司或供应商
	CompanyName = 'Adam the Automator'
	#此模块的版权声明
	Copyright = '(c) 2019 tyler. All rights reserved.'
	#此模块提供的功能的描述
	Description = 'This is a test module.'
	#此模块所需的Windows PowerShell引擎的最低版本
	#PowerShellVersion = ''
	#导入此模块所需的Windows PowerShell主机的名称
	#PowerShellHostName = ''
	#导入此模块所需的Windows PowerShell主机的最低版本
	#PowerShellHostVersion = ''
	#此模块所需的Microsoft .NET Framework的最低版本。此前提条件仅对PowerShell桌面版有效。
	#DotNetFrameworkVersion = ''
	#此模块所需的公共语言运行时(CLR)的最低版本。此前提条件仅对PowerShell桌面版有效。
	#CLRVersion = ''
	#此模块所需的处理器架构(None、X86、Amd64)
	#ProcessorArchitecture = ''
	#必须在导入此模块之前导入到全局环境中的模块
	#RequiredModules = @()
	#必须在导入此模块之前加载的程序集
	#RequiredAssemblies = @()
	#在调用方环境中运行的脚本文件(.ps1)
	#ScriptsToProcess = @()
	#在导入此模块时加载的类型文件(.ps1xml)
	#TypesToProcess = @()
	#在导入此模块时加载的格式文件(.ps1xml)
	#FormatsToProcess = @()
	#作为根模块/ModuleToProcess指定的模块的嵌套模块导入的模块
	#NestedModules = @()
	#从此模块导出的函数,为了获得最佳性能,不要使用通配符,不要删除该条目,如果没有要导出的函数,请使用一个空数组。
	FunctionsToExport = @('Get-RegistryKey','Set-RegistryKey')
	#从此模块导出的Cmdlet,为了获得最佳性能,不要使用通配符,不要删除该条目,如果没有要导出的Cmdlet,请使用一个空数组。
	CmdletsToExport = @()
	#从此模块导出的变量,VariablesToExport = '*'
	#从此模块导出的别名,为了获得最佳性能,不要使用通配符,不要删除该条目,如果没有要导出的别名,请使用一个空数组。
	AliasesToExport = @()
	#从此模块导出的DSC资源
	#DscResourcesToExport = @()
	#此模块打包的所有模块的列表
	#ModuleList = @()
	#此模块打包的所有文件的列表
	#FileList = @()
	#传递给RootModule/ModuleToProcess中指定的模块的私有数据。这也可能包含一个带有PowerShell使用的其他模块元数据的PSData哈希表。
	PrivateData = @{
		PSData = @{
			#应用于此模块的标签。这有助于在线库中发现模块。
			#Tags = @()
			#此模块的许可证URL
			#LicenseUri = ''
			#此项目的主要网站的URL
			#ProjectUri = ''
			#代表此模块的图标的URL
			#IconUri = ''
			#此模块的ReleaseNotes
			#ReleaseNotes = ''
		} 
		#PSData哈希表结束
	} 
	#PrivateData哈希表结束
	#此模块的HelpInfo URI
	#HelpInfoURI = ''
	#从此模块导出的命令的默认前缀。使用Import-Module -Prefix覆盖默认前缀。
	#DefaultCommandPrefix = ''
}

虽然一开始可能看起来有点吓人,但微软提供了一个方便的 cmdlet 用于生成模块清单。包含的命令是 New-ModuleManifest。要生成上面显示的清单,你可以使用:

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.'

外部帮助文件

你也可能在一些模块中看到外部帮助文件。它们可以通过文件名末尾的 <ModuleName>-Help.xml 来识别。这些外部帮助文件包含的信息与通常在函数定义中找到的基于命令的帮助相同。

这还需要你在函数中添加 # .ExternalHelp <ModulePath>-Help.xml,以使其在导入模块后使用 Get-Help 命令时正常工作。通常只有在非常大的模块中才会看到外部帮助文件,因此它们超出了范围。

虽然这些是模块中最常见的文件类型,但并不是唯一的文件类型。有时,除了文本模块外,还会看到二进制文件,因为存在其他依赖关系。通过浏览模块路径,你可以找到模块中许多其他文件类型的示例。

要使非标准模块文件正确发布,你需要在模块清单中的 FileList 参数中包含其他文件。

在模块清单中,您会注意到许多其他目前为空的参数。您可以使用这些参数来定义对使用您的模块的其他要求。例如,您可以定义模块可与之配合的 PowerShell 版本。如果尝试在不支持的 PowerShell 版本上导入模块,您将看到以下内容:

Requiring certain versions of PowerShell

PSRepositories

模块的关键分发选项之一是PSRepository。从 1000 英尺的高度来看,PSRepository 是一个本地位置,多个人或多个设备可以访问模块文件。这些通常是 Web 服务器,您可以在其中发布文件。

您还可以使用目录作为存储库,但这会限制存储库的功能。您可以自己托管PSRepository,或者您可以利用互联网上像 PowerShell Gallery 这样的许多选项。您可以使用 Get-PSRepository 命令查看您的PSRepositories

Default PowerShell NuGet repositories

默认情况下,您只会有一个条目,它将是 PowerShell Gallery。您可能会注意到它会显示为不受信任。这是因为 PowerShell 让您意识到通过使用 PowerShell Gallery,您可能正在使用未经 Microsoft 编写和批准的代码。这意味着在从中安装任何模块之前,您必须明确授予权限。

添加 PSRepositories

您还可以添加自己的存储库。要信任 PowerShell Gallery,您可以运行 Get-PSRepository -Name PSGallery | Set-PSRepository -InstallationPolicy Trusted,或者您可以在第一次从 PowerShell Gallery 安装模块时接受警告。

你可以在PowerShellGet模块中找到与这些PSRepositories交互所需的所有命令。你可以在这里看到函数:

Commands in the PowerShellGet module

与某些存储库交互之前,可能需要更新PowerShellGet模块。

查找模块

使用Find-Module命令可以实现搜索模块的关键功能。有多种方法可以过滤并找到你需要的模块,但现在你可以像这样搜索VMware模块:

Finding modules on the PowerShell Gallery

这将显示以VMware开头的所有模块。虽然其中大部分来自VMware,但你需要查看作者属性以确定模块的发布者。

由于任何人都可以上传到PowerShell Gallery,因此有成千上万的模块可用。这意味着你可能会找到对你的用例不起作用的模块。你将找到的许多模块都是开源的,因此你可以为其贡献以改进模块的功能。

安装模块

要使用Install-Module命令,你必须有一个可信的托管模块的PSRepository。这可以是PowerShell Gallery、另一个InternetPSRepository或自托管站点。你可以从Find-Module命令导出管道以在安装之前轻松确认模块。

Finding modules installed from a PSRepository

你还可以使用MinimumVersionMaximumVersionRequiredVersion参数定义模块的版本。

要查看使用Install-Module安装的所有模块,您可以使用Get-InstalledModule。这将列出安装到AllUsers范围或CurrentUser范围的所有模块。

卸载模块

就像您可以安装模块一样,您也可以卸载模块。如果模块不是通过Install-Module命令安装的,则无法使用Uninstall-Module命令卸载它。

Uninstalling modules installed from a PSRepository with Uninstall-Module

正如您在这里看到的,我们正在尝试卸载ActiveDirectory模块。由于此模块未与Install-Module一起安装,因此在尝试使用Uninstall-Module时会收到错误。要卸载此模块,我们必须通过撤消安装模块时所使用的操作来卸载它。

要查看模块成功卸载的情况,您可以卸载您之前安装的VMware.PowerCLI模块。

Uninstalling a module downloaded from the PowerShell Gallery

即使您卸载了VMware.PowerCLI,您会发现仍然安装了许多依赖项。如果您想卸载所有模块,我们可以使用Get-InstalledModule VMware.* | Uninstall-Module -Force

您会遇到如此多的困难来完全卸载此模块的原因是它具有如此多的依赖项。此外,其中一些模块是彼此的依赖项,这就是为什么需要Force参数的原因。

更新模块

现在你知道如何安装和卸载模块了,可能想知道如何更新已安装的模块。

和其他过程一样,如果模块不是使用Install-Module安装的,你就不能使用 PowerShell 命令来更新它。你可以使用Update-Module来将模块更新到最新版本,或者更新到更新的特定版本。

还有一个开关AllowPreRelease,允许你更新到尚未正式发布的版本。有时这很有帮助,因为可能已修复了你遇到的错误或者添加了你想使用的新功能。

Updating modules with Update-Module

检查/保存模块

在使用模块之前进行检查时非常有帮助的一个很少使用的命令是Save-Module。使用此命令,你可以将模块下载到路径而不安装它。

然后你可以检查文件,如果模块不是二进制模块,你可以打开并查看组成模块的代码。这不仅可以确保模块没有做任何恶意操作,还可以学习其他人如何构建模块。

Downloading modules with Save-Module

在这个示例中,不仅下载了VMware.PowerCLI模块,还下载了所有依赖项。以下是VMware.PowerCLI文件夹中显示的内容:

VMware.PowerCLI module contents

这是一个很好的例子,展示了有时模块中包含非标准模块文件,比如最终用户许可协议。

编写自己的模块

你现在已经看到了如何与别人的模块进行交互。现在你想学习如何创建自己的模块,以便开始优化你的代码以实现可伸缩性。

创建模板文件

首先,你需要为你所有的模块文件创建一个文件夹。在你创建了容器之后,你需要创建你的模块文件。你必须确保你的模块文件与你的文件夹同名,否则在尝试发布模块时,PowerShell将无法正确发现模块。

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

现在你还想使用一个清单,你还需要将它命名为与容器和模块文件相同的名称。

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'

有了容器、模块文件和清单文件,你就有了一个完整的功能模块。你可以将这个模块发布到一个PSRepository,并开始在任何你想要的地方安装它。尽管模块文件是空的,但你仍然可以使用这些文件进行测试发布,以确保你的存储库正常工作。

注册一个PSRepository

在你可以发布你的模块之前,你需要将另一个PSRepository添加到你的会话中。对于测试,你可以使用本地路径作为你的PSRepository,因为这样设置和清理都很容易。

通常,如果你要设置一个带有目录的PSRepository,你会希望确保多台计算机可以访问它。你可以像这样创建一个本地存储库:

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

如果你只是从PSRepository下载,而从不发布,你可以排除PublishLocation参数。

发布你的模块

由于您已将安装策略设置为受信任,因此您将不会收到确认以允许从存储库安装模块。现在您有一个新的PSRepository可用,您可以使用Publish-Module -Name .\Scripts\ATARegistry -Repository LocalRepo来发布您的模块。

发布模块后,您可以使用上述命令来查找并安装该模块。

现在您已经安装了模块,您可以使用Get-Module来查看已导入到本地会话中的模块。由于您没有将任何函数添加到清单中的FunctionsToExport数组中,因此ExportedCommands属性为空。

No exported commands

添加到您的模块

现在您知道可以发布和安装您的模块,您可以开始向其中添加一些功能。您可以添加一个函数来返回一个注册表键,使其看起来像这样:

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

如果您保留清单不变,并尝试上传您的新模块,您将遇到两个问题。首先,您将收到一个错误,指出清单文件中的模块版本已存在于您的存储库中。这是因为您尚未在清单文件中更改模块版本。

导出模块函数

另一个问题是,在导入模块后,您仍然看不到ExportedCommands属性中的任何函数,因为您尚未将新函数添加到清单中。

虽然您的函数可以在不将其列在FunctionsToExport列表中的情况下使用,但这将使定位变得更加困难。

只要你不定义一个空数组@(),对于你的FunctionsToExport所有函数、变量和别名都会默认导出。

要解决这两个问题,你可以像这样更新你的模块文件:

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

现在你已经向你的模块添加了一个函数,并且更新了清单以反映这些更改,你可以使用与之前相同的命令发布模块的新版本。

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

在FunctionsToExport和Export-ModuleMember之间做出决定

在导出模块成员时,PowerShell有两个类似的特性。挑战在于在两者之间做出选择。两者都是正确的,但根据你的需求,其中一个可能更适合你。

当你希望动态控制导出哪些函数时,使用Export-ModuleMember,因为你可以传递要导出的函数列表。通常情况下,当使用点源多个单独的函数 PS1 文件时,会使用这个功能。通过将内部函数分成一个私有文件夹和一个可导出函数的公共文件夹,你可以通过将所有公共函数传递给Export-ModuleMember函数轻松导出这些函数。

A few notes about Export-ModuleMember:

  • 这会覆盖FunctionsToExport的行为,因此如果使用Export-ModuleMember命令,FunctionsToExport就不起作用了。
  • Export-ModuleMember不会导出变量和别名,除非显式定义,而FunctionsToExport会导出这些值。
  • 可以使用多个Export-ModuleMember命令,并且它们会堆叠而不是优先。

如果您不希望在功能列表中进行更改,可以使用模块清单中的FunctionsToExport配置,这样就可以正常运行,而无需显式导出变量和别名。

更新您的模块

最后一步是在会话中更新您的模块,以便能够使用已更新的文件。使用Update-Module ATARegistry下载您刚刚发布到存储库的更新。

Exported commands now show up

现在您可以看到您的模块的新版本,并且可以查看在清单中定义的函数。

构建帮助内容

之前忽略的选项之一是内置到PowerShell中的帮助系统。您可能曾在某个时候使用Get-Help查看函数的帮助信息。此信息可以通过两种主要方式添加。

第一种方式是将基于注释的帮助添加到函数定义中。这通常是许多模块作者的实现方式。另一种方式是使用外部帮助文件。您可以使用Full参数显示帮助提供的所有内容。

Finding help with Get-Help

正如您所看到的,实际上没有太多信息,而且您得到的少量信息很可能对任何人都没有帮助。

您可以向模块文件添加一些基于注释的帮助,以填充帮助系统中的这些字段。您可以使用Get-Help about_Comment_Based_Help了解有关基于注释的帮助的所有选项。

目前,您可以将函数更新为以下形式。这是一个最常用的帮助参数列表,但所有这些仍然是可选的,也可以添加其他参数。

现在您的函数看起来是这样的:

 function Get-RegistryKey {
	<#
    .概要
    使用提供的路径返回注册表键。
    .描述
    该函数使用 Get-Item 命令返回提供的注册表键的信息。
    .参数 路径
    将要搜索注册表键的路径。
    .示例
    Get-RegistryKey -Path 'HKLM:\HARDWARE\DESCRIPTION\System'
    .输入
    System.String
    .输出
    Microsoft.Win32.RegistryKey
    .备注
    此模块是一个良好文档化函数的示例。
    .链接
    
ATA Learning
#>
param( [string]$Path ) Get-Item $Path }

还有一些特殊的帮助参数,比如.FORWARDHELPTARGETNAME。此选项将所有传入的帮助请求转发到另一个命令。这可以用在帮助应显示多个命令相同信息的情况下。

现在您已经添加了帮助,您可以更新模块清单中的版本,发布新版本,并像之前一样更新会话中安装的版本。

现在您可以查看函数的帮助,可以看到有更多信息可用。这是一个很好的方式,特别是对于一些经验较少的人,通过查看代码可能无法快速理解模块正在做什么,可以在文档中包含如何使用函数的说明。

Getting full help content with Get-Help

在外部帮助文件的情况下,添加的信息是相同的,但该信息被放置在一个单独的文件中,并在函数内部进行链接。

如果你查看AllUsers模块路径,你可以看到模块的版本以及你已安装的所有模块文件。

Folder name is the module version

如果你返回到之前创建的PSRepository路径C:\Repo,你会看到一堆NUPKG文件。每个发布的版本都会有一个对应的文件。这些是在使用Publish-Module时发布的内容的压缩版本。

摘要

一旦你掌握了PowerShell控制台、PowerShell作为一种语言以及编写脚本的技能,构建自己的模块就是最后一步。模块允许你开始在PowerShell中开发有用的工具。如果通过创建用于单一目的的模块进行正确设计和构建,你将不可避免地发现自己在时间推移中编写的代码越来越少。你将开始在更多的代码中引用你的模块函数,并从那里构建。

模块函数允许你抽象出在脚本中重复的代码。它们代表着以后在代码中引用的“标签”,可以随时调用,而不是重新发明轮子并尝试弄清楚以前如何实现目标的方式。模块是PowerShell代码的最终“打包”,将类似的代码组合在一起,以防止在已经解决过的问题上浪费时间。

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