首页 > 解决方案 > C# Powershell BeginInvoke Completed 事件未触发

问题描述

这是测试功能的示例代码,它本身没有用。我想触发 PSDataCollection 对象的完成事件。我在微软发现应该调用 C++ 中的 CloseAll 方法让 BeginInvoke 知道没有剩余命令,我不确定这个概念是否适用于 C#,我在任何地方都找不到这个方法。该代码有效,因为我使用了 InvocationStateChanged 中的 Completed 状态。我不明白为什么这个被解雇而不是另一个。我搜索了几天的答案,但没有太多可找到的。

谢谢

using System.Text;
using System.Threading;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.Management.Automation;
using System.Management.Automation.Runspaces;

namespace PSAsync
{
    public partial class Form1 : Form
    {
        RunspacePool RSPool;
        StringBuilder stringBuilder;
        PowerShell Ping1;
        IAsyncResult Ping1AsyncResult;
        PSDataCollection<PSObject> Output;

        public Form1()
        {
            InitializeComponent();
            RSPool = RunspaceFactory.CreateRunspacePool(1, 4);
            RSPool.Open();
            stringBuilder = new StringBuilder();
        }

    private void btnPing1_Click(object sender, EventArgs e)
    {
        Ping1 = PowerShell.Create();
        //Instead we rely on the InvocationStateChanged event
        lblPing1.Text = "Status:" + Ping1.InvocationStateInfo.State.ToString();
        Ping1.InvocationStateChanged += Ping1_InvocationStateChanged;

        Ping1.RunspacePool = RSPool;
        Ping1.AddCommand("ping").AddArgument("192.168.1.1");            
        
        
        Output = new PSDataCollection<PSObject>();
        Output.Completed += Test_Completed;//never gets fired
        Output.DataAdded += Output_DataAdded;
        Ping1.Streams.Error.DataAdded += Error_DataAdded;
        
        Ping1AsyncResult = Ping1.BeginInvoke<PSObject, PSObject>(null,Output);          
                   
        
    }

    private void Error_DataAdded(object sender, DataAddedEventArgs e)
    {
        throw new NotImplementedException();
    }

    private void Output_DataAdded(object sender, DataAddedEventArgs e)
    {
        PSDataCollection<PSObject> myp = (PSDataCollection<PSObject>)sender;

        Collection<PSObject> results = myp.ReadAll();
        foreach (PSObject result in results)
        {
            this.Invoke((MethodInvoker)delegate
            {
                // Show the current time in the form's title bar.
                this.txtOutput.Text = txtOutput.Text + result.ToString()+Environment.NewLine;
            });                
        }
    }

    private void Test_Completed(object sender, EventArgs e)
    {
        throw new NotImplementedException();
    }

    private void Ping1_InvocationStateChanged(object sender, PSInvocationStateChangedEventArgs e)
    {
        Console.WriteLine("Invocation State Changed:"+e.InvocationStateInfo.State.ToString());
        this.Invoke((MethodInvoker)delegate
        {                
            this.lblPing1.Text = "Status:"+e.InvocationStateInfo.State.ToString();
        });
        if (e.InvocationStateInfo.State == PSInvocationState.Completed)
        {
            this.Invoke((MethodInvoker)delegate
            {                    
                this.txtOutput.Text = txtOutput.Text +"Status:" + e.InvocationStateInfo.State.ToString();
            });
        }                
    }

    private void btnQuit_Click(object sender, EventArgs e)
    {
        RSPool.Close();
        this.Close();
    }            
}

}

标签: c#powershellbegininvoke

解决方案


推荐阅读