托管PowerShell:PowerShell与Runspace vs. RunspacePool与Pipeline

时间:2013-05-02 02:33:10

标签: powershell powershell-hosting

我尝试在我的应用程序中添加一些相当有限的PowerShell支持:我希望能够定期运行用户定义的PowerShell脚本并显示任何输出,并且(最终)能够处理进度通知和用户提示请求。我需要命令行样式的交互支持,或者(我认为)远程访问或运行多个同时脚本的能力,除非用户脚本在我托管的shell中自行完成。我最终想要异步或在后台线程上运行脚本,并且可能使用一些初始变量和可能一个cmdlet来播种shell,但这可能是“幻想”,因为这个特性可能会得到。

我一直在阅读MSDN documentation about writing host application code,但很高兴解释如何创建PowerShell对象,或Runspace或{{1} }或RunspacePool,没有迹象表明为什么会选择其中任何一种方法而不是另一种方法。

认为我是这两个中的一个,但是我想要一些关于哪种方法更好的方法的反馈:

Pipeline

或:

PowerShell shell = PowerShell.Create();
shell.AddCommand(/* set initial state here? */);
shell.AddStatement();
shell.AddScript(myScript);
shell.Invoke(/* can set host! */);

(其中一个必需的Runspace runspace = RunspaceFactory.CreateRunspace(/* can set host and initial state! */); PowerShell shell = PowerShell.Create(); shell.Runspace = runspace; shell.AddScript(myScript); shell.Invoke(/* can set host here, too! */); 派生类方法是PSHost,我不知道我运行的用户定义脚本是否会导致它被调用。如果可以,那么我将负责“开始一个新的嵌套输入循环”(as per here)......如果这会影响上面的路径,那么这也是一件好事。)

谢谢!

2 个答案:

答案 0 :(得分:0)

你正在思考它。您在样本中显示的代码是一个良好的开端。现在您只需要读取Invoke()的结果并检查错误和警告流。

PowerShell主机提供了一些RunSpace可用于与用户通信的钩子,如流和格式输出,显示进度,报告错误等。对于您想要做的事情,您不需要PowerShell主机。您可以使用PowerShell类从脚本执行中读取结果,检查错误,警告,读取输出流并使用应用程序的工具向用户显示通知。如果检测到错误,这将比编写整个PowerShell主机以显示消息框更简单有效。

此外,PowerShell对象在创建时具有Runspace,您不需要给它一个。如果您需要保留运行空间以保留环境,则只需保留整个PowerShell对象,并在每次调用Invoke后清除命令和所有Streams。

您应该问的下一个问题是如何处理PowerShell :: Invoke()的结果并阅读PowerShell :: Streams。

答案 1 :(得分:0)

他们是什么?

  • 管道

管道是在Powershell脚本中串联命令的一种方式。示例:您将Get-ChildeItem的输出从Where-Object“管道”到|进行过滤:

Get-ChildItem | Where-Object {$_}
  • PowerShell对象

PowerShell对象引用一个powershell会话,就像启动powershell.exe时将得到的那样。

  • 运行空间

每个powershell会话都有其自己的运行空间(您将始终从Get-Runspace获取输出)。它定义了powershell会话的状态。因此,运行空间的InitialSessionState对象/属性。您可能决定创建一个新的Powershell会话,并在Powershell中使用其自己的运行空间来启用一种多线程。

  • RunspacePool

最后但并非最不重要的RunspacePool。顾名思义,它是一个运行空间(或Powershell会话)池,可用于处理许多复杂的任务。一旦池中的运行空间之一完成了它的任务,它可能会执行下一个任务,直到一切完成。 (与10个运行空间有关的100件事:平均而言,它们每个处理10个,但一个可能处理8个,而另外两个可能处理11个...)


什么时候使用什么?

  • 管道

该管道用于脚本。这样可以更轻松地构建复杂的脚本,应尽可能频繁地使用它。

  • PowerShell对象

当您需要新的powershell会话时,将使用powershell对象。您可以在现有脚本(C#或Powershell)中创建一个。它对于轻松实现多线程很有用。它会自行创建一个默认会话。

  • 运行空间

如果要创建Powershell的非标准会话,则可以在使用Runspace对象创建Powershell会话之前对其进行操作。当您要在额外的运行空间中共享同步的变量,函数或类时,这很有用。多线程稍微复杂一点。

  • RunspacePool

就像之前提到的那样,它是繁重工作的繁重工具。如果一次执行脚本要花费几个小时,那么您就需要经常执行一次。结合远程处理,您可以同时在大型群集等的每个节点上安装一些东西。