Function PowerShell模块设计-导出模块成员

Function PowerShell模块设计-导出模块成员,function,powershell,powershell-module,Function,Powershell,Powershell Module,我正在构建一个模块,该模块导出我希望通过我的配置文件使其可用的cmdlet。此cmdlet的实现分布在多个包含我不想公开的实现函数的实现文件中。所以我常常把它们藏起来 文件get_something.psm1 然后我将get_something.psm1添加到我的个人资料中。通过仅导出Get,我的所有实现函数都保持“私有” 我遇到的问题是,在使用Export ModuleMember命令时,每当我需要在实现文件中导入一个模块时,我都必须在其中导入一个函数。例如,假设我有一个模块person.ps

我正在构建一个模块,该模块导出我希望通过我的配置文件使其可用的cmdlet。此cmdlet的实现分布在多个包含我不想公开的实现函数的实现文件中。所以我常常把它们藏起来

文件get_something.psm1 然后我将get_something.psm1添加到我的个人资料中。通过仅导出Get,我的所有实现函数都保持“私有”

我遇到的问题是,在使用Export ModuleMember命令时,每当我需要在实现文件中导入一个模块时,我都必须在其中导入一个函数。例如,假设我有一个模块person.psm1,其中有一个函数Get person,我需要在所有实现文件中调用该函数。现在,我必须在需要调用Get person的每个文件中导入person.psm1。这是使用Export ModuleMember函数获取内容的结果。如果没有它,我只需要导入person.psm1一次,它就可以使用了

从本质上讲,Export ModuleMember不仅阻止了我的外部实现。它阻止了我自己的实现


这是设计PowerShell模块的一个正常方面吗?

这实际上是模块开发过程中的一个争论点。最初,导出任何函数都需要导出模块成员。这变得单调乏味,限制性很强。因此,默认情况下,模块中的所有函数都可见,但变量和别名不可见,只要您从未在
.PSM1
中使用过
Export ModuleMember

如果使用导出模块成员,它将开始限制该列表。导出数量较少的函数可能不是一个坏主意,但您必须谨慎使用它

你可以写:

导出模块成员-函数a、b、c
它导出了一些函数

导出模块成员-函数*
后者相当于完全忽略导出模块成员

如果您愿意,可以使用限制性更强的通配符,但我发现99%的情况下,您根本不需要为此烦恼

您似乎要问的另一件事是如何最好地处理模块依赖关系。现在,编写脚本时导入一两个模块是相当常见的,就像在C#项目中包含一两个程序集一样。如果在模块内部执行此操作,则可以使用
导入模块
上的
-Global
标志,并避免使用
-Force
(这将重新加载模块)。这使得在不同的功能中重用模块更加有效。这也使得它不太可能出现“循环”(卸载和重新加载)模块的问题,不幸的是,许多模块做得不好

在每个函数中引用模块的替代方法是使用模块清单(
Get Help New ModuleManifest
)。模块清单非常有趣,模块开发的许多部分都需要学习。如果在模块清单的
RequiredModules
列表中包含模块,则在导入模块之前会自动加载该模块(至少在PowerShell 3及更高版本中)。如果在模块清单的
NestedModules
列表中包含模块,则该模块将作为模块的一部分加载,模块导出的命令将由您的模块导出

模块设计是一个棘手的问题,但做得好是非常值得的。祝你好运。

你能详细介绍一下“循环”模块的内容并举例说明模块如何做得不好吗?为什么
导入模块-Global
是一个神奇的解决方案?我相信“骑自行车”的问题在下面的GitHub问题中有所涉及(但可能有更多的细微差别):
import-module .\get_something_impl.psm1

function Get-Something {
    [cmdletbinding()]
    Get-SomethingImplementation
}

Export-ModuleMember -Function Get-Something