【问题标题】:Powershell runspace: write-output calls made form inside a cmdlet that was called from scriptblock doesn't show as outputPowershell 运行空间:在从 scriptblock 调用的 cmdlet 中形成的写入输出调用不显示为输出
【发布时间】:2021-05-30 02:09:18
【问题描述】:

我直接在脚本块中的写入输出调用显示在运行空间输出中。但是我从该脚本块调用的 cmdlet 也会进行写入输出调用,但它们不会最终出现在运行空间输出中。

为了获得输出,我调用了 PowerShell.EndInvoke(Job)。

下面是一些示例代码,相同的代码刚刚从 powershell 运行 一些示例代码

非运行空间代码

Function Do-Output{
 [CmdletBinding()]
    Param(
    [int]$n)
    Process{ 
    write-output "Output from inside Do-Output($($n))"
    }
}
write-output "Output from before Do-Output(1) call"
Do-Output -n 1
write-output "Output from before Do-Output(2) call"
Do-Output -n 2
write-output "Output from before Do-Output(3) call"
Do-Output -n 3
write-output "Done"

非运行空间输出

Output from before Do-Output(1) call
Output from inside Do-Output(1)
Output from before Do-Output(2) call
Output from inside Do-Output(2)
Output from before Do-Output(3) call
Output from inside Do-Output(3)
Done

从运行空间运行的脚本块中的代码

Function Do-Output{
 [CmdletBinding()]
    Param(
    [int]$n)
    Process{ 
    write-output "Output from inside Do-Output($($n))"
    }
}


$Scriptblock = {

write-output "Output from before Do-Output(1) call"
Do-Output -n 1
write-output "Output from before Do-Output(2) call"
Do-Output -n 2
write-output "Output from before Do-Output(3) call"
Do-Output -n 3
write-output "Done"
}

从运行空间输出运行脚本块

Do-Output cmdlet 内部的写入输出调用均未显示在输出中。

Output from before Do-Output(1) call
Output from before Do-Output(2) call
Output from before Do-Output(3) call
Done

我知道 cmdlet 正在被调用,就好像我在其中抛出异常一样,该异常会显示出来。

【问题讨论】:

标签: powershell runspace


【解决方案1】:

您必须在 ScriptBlock 中包含该函数。

【讨论】:

  • 它在我在 ScriptBlock 中导入的模块中,我知道正在调用该函数。好像我在里面扔了一条消息,它确实显示为输出。
  • 模块是否安装在目标计算机本地?您的问题并没有说该功能在模块中。它是在 ScriptBlock 之上声明的。你也可以分享例外吗?另外,请分享您正在使用的确切代码...如果您不这样做,那将毫无用处。
  • 更奇怪的行为。如果该函数返回一个值并且调用者未将其分配给变量,则所有写入输出都会显示在输出中。如果调用者确实将值分配给变量,则 cmdlet 中的写入输出不会显示在输出中。如果我将该功能从我更大的模块(6000 多行代码)中移出并移到它自己的模块中,则 cmdlet 中的所有写入输出在所有场景中都按预期工作。但目标是让更大的模块在 RunSpace 中工作。一切都在本地系统上运行。
  • 要注意的是我目前只使用了更大模块的1个功能。
  • 当我将 1 函数放在它自己的模块中并且该函数返回一个值并且调用者将其分配给一个值时,它也显示非 cmdlet 内部写入输出。如果我删除该变量 assignment ,所有写入输出都会再次显示。我在上面错误地指出它适用于所有场景。所以我很确定从这里去哪里。我正在使用 PSVersion 5.1.19041.906
【解决方案2】:

我的解决方案是创建一个 ScriptBlock 包装器。这个脚本块包装器将在开始真正的脚本块之前开始一个脚本(我无法控制那个)。然后在包装脚本块中使用 Invoke-Command 启动真正的脚本块。

这有几个好处。 然后我继续在我的模块中使用 write-host。
它还捕获详细输出。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2015-11-17
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多