我不明白Invoke-Expression
是否有内部缺陷,使它更危险,或者问题是它将文本合并到代码,代码合并到执行,可能还在本地范围内执行,所有这些都在一个命令中。
我想要做的是通过Add-Type
创建一个带有public event EventHandler MyEvent;
事件的C#类,然后在PowerShell中继承该类,方法是将PowerShell编写为字符串@'class psMessages: csMessages{<code for clas>}'@
,将字符串转换为脚本块,然后执行它。
我发现这些创建脚本块的方法可以工作:
$ScriptBlock = ([System.Management.Automation.Language.Parser]::ParseInput($psMessages, [ref]$null, [ref]$null)).GetScriptBlock()
# or
$ScriptBlock = [scriptblock]::Create($psMessages)
并且这些命令中的任何一个都将在当前作用域中执行脚本块:
. $ScriptBlock
# or
Invoke-Command -NoNewScope $ScriptBlock
**附加信息:**这些命令失败,我相信是因为它们在新的作用域中执行脚本块-如果我说错了,请纠正我:
& $ScriptBlock
# or
$ScriptBlock.Invoke()
# or
Invoke-Command $ScriptBlock
那么,这些方法中有没有比Invoke-Expression
更安全的?或者它们都一样危险?如果有更安全的,为什么?
1条答案
按热度按时间31moq8wy1#
Invoke-Expression
-即generally to be avoided-* 是 * 可接受的。Invoke-Expression
执行的代码总是在 * current * 作用域中运行;可以将输入字符串 Package 在& { ... }
中,以便在 * child * 作用域中执行它。[scriptblock]::Create()
实现了一个 * 中间地带*:[scriptblock]::Create()
返回的script block示例允许按需进行潜在的可重用调用,可以选择在 * current * 作用域中使用.
(点源操作符)执行它,或者在 * child * 作用域中使用&
(调用操作符)执行它。至于"附加信息:"下面列出的命令
.Invoke()
方法,因为它在几个方面改变了调用的语义-参见this answer。Invoke-Command
来(本地)调用脚本块也没有什么好理由-参见this answer。