我的项目的结构如下:
MyScript.ps1
classes\
Car.ps1
Tesla.ps1
Car.ps1是Tesla.ps1的基类。我试图在Tesla.ps1中这样定义Tesla:
. "$PSScriptRoot\Car.ps1"
class Tesla : Car
{
}
MyScript.ps1需要使用Tesla类,但不必知道它是从Car继承的。
. "$PSScriptRoot\classes\Tesla.ps1"
$tesla = [Tesla]::new()
将点源采购到
classes\Tesla.ps1
效果很好,但是从Tesla文件中抛出了此错误:如果我以正确的顺序将所有文件导入MyScript.ps1,则可以正常工作。例子:
. "$PSScriptRoot\classes\Car.ps1"
. "$PSScriptRoot\classes\Tesla.ps1"
$tesla = [Tesla]::new()
这很麻烦,尤其是随着复杂性的增长。我的网点采购不正确吗?有没有更好的方法可以使用PSModulePath中没有的相对路径导入自定义PowerShell类?
最佳答案
PetSerAl像以前一样无数次,在对该问题的简短评论中提供了关键的指针:
由于使用了类,因此必须使用模块并将其与using module
语句一起导入才能使用它们。
不幸的是,在撰写本文时, using module
中仍未提及Get-Help about_Modules
。
具体来说,为了在class
定义中引用类型(类),PowerShell在解析时必须知道该类型。
在您的示例中,为了从类Tesla
派生Car
,在执行脚本之前,PowerShell在解析脚本之前必须知道Car
类型,这是执行开始之前的原因-这就是来点导入源包含其脚本的Car
的尝试来不及了(. "$PSScriptRoot\Car.ps1"
)
PowerShell在解析时会通过以下两种方式之一了解引用的类型:
using module
语句,该语句引用定义了类型(类)的模块(请注意,还有一个using assembly
语句用于从DLL加载类型,而using namespace
可以通过其名称来引用类型)。Import-Module
cmdlet在这种情况下不起作用,因为它在运行时执行。 因此,正如PetSerAl建议的那样:
*.psm1
文件)using module
来使Tesla
模块导入Car
模块,并且MyScript.ps1
脚本使用相对于封闭脚本/模块位置的路径来导入Tesla
模块。\
用作using module
的相对路径中的路径分隔符,即使在类似Unix的平台上,通常使用/
。 MyScript.ps1
classes\
Car.psm1 # Note the .psm1 extension
Tesla.psm1 # Ditto
Car.psm1
:class Car {}
Tesla.psm1
:using module .\Car.psm1
class Tesla : Car {}
MyScript.ps1
:using module .\classes\Tesla.psm1
$tesla = [Tesla]::new()
关于点源文件中的PowerShell点源-导入类,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/51622808/