PowerShell模块清单文件格式(.psd1)本质上是一个具有预期某些键的Hashtable文字。这是PowerShell脚本的配置文件的理想选择。我最终想要做的是读取一个.psd1文件,其中包含一组特定于该脚本的键。
例如(MyScriptConfig.psd1):
@{
FTPHost = "ftp.blah.com"
FTPUserName = "blah"
FTPPassword = "blah"
}
我没有理由不能使用XML,INI,JSON等来获取这些信息,但我宁愿使用与PowerShell模块清单相同的基本数据格式。
显然,最简单的方法是阅读文本并将其传递给Invoke-Expression
,这会返回一个Hashtable,但是它会调用文件中的任何内容,这很容易出错并且可能不安全。
我以为我召回了一个用于使用PowerShell cmdlet的“安全”子集读取此数据的cmdlet,但我想到的是ConvertFrom-StringData
和DATA
部分,这些部分都不允许我读取任意文件包含Hashtable文字。
PowerShell中是否有内置功能可以让我这样做?如果没有内置任何东西,那么我可能会使用ConvertFrom-StringData
去JSON或Key = Value的路线。
答案 0 :(得分:25)
Powershell版本5添加了Cmdlet Import-PowershellDataFile以安全地解析PSD1文件。
在第5版之前,至少有三种解决方案:
Cmdlet Import-LocalizedData。虽然用于处理语言文件,但它将读取任何PSD1格式的文件。
# Create a test PSD1 file
@'
@{
a1 = 'a1'
a2 = 2
a3 = @{
b1 = 'b1'
}
}
'@ | Set-Content -Path .path\example.psd1
# Read the file
Import-LocalizedData -BaseDirectory .\path -FileName example.psd1 -BindingVariable Data
# Use the data
$Data.a1
$Data.a3.b1
也可以使用Data Section处理内联数据(内联类型会失败)。
# Safely parse data
$Data2 = DATA {
@{
a1 = 'a1'
a2 = 2
a3 = @{
b1 = 'b1'
}
}
}
# Use the data
$Data2.a1
$Data2.a3.b1
第三个是PowerShell DSC parameter transformation attribute mentioned by @Jakub Berezanski。
答案 1 :(得分:13)
PowerShell DSC定义了一个参数转换属性,用于支持在调用配置时将路径传递给.psd1文件作为ConfigurationData参数的值。此属性是公共属性,可以在自定义函数中使用,例如:
function Parse-Psd1
{
[CmdletBinding()]
Param (
[Parameter(Mandatory = $true)]
[Microsoft.PowerShell.DesiredStateConfiguration.ArgumentToConfigurationDataTransformation()]
[hashtable] $data
)
return $data
}
Parse-Psd1 C:\MyData.psd1
属性实现调用内部帮助程序,该辅助程序在受限语言上下文中评估文件的内容,其中只允许以下cmdlet:
Import-LocalizedData
ConvertFrom-StringData
Write-Host
Out-Host
Join-Path
答案 2 :(得分:1)
模块清单专门设计为仅使用PSH的受限子集,但是 1 没有直接的方式来处理该模式中的内容(并获取所有数据)。但是,您可以使用Test-ModuleManifest
2 验证清单,然后仅评估文件的内容。
1 至少就 PowerShell In Action 第二版Ed所涵盖的那样。
2 不幸的是,本书的在线副本使用图像作为源代码(允许注释),所以不能在这里复制。