如何在 C# 中使用 powershell invoke-command?

How to use powershell invoke-command within C#?

如果我 运行 在 Powershell 中执行以下命令,它会按预期工作

invoke-command -computername [name] -scriptblock { ipconfig.exe > c:\ipconfig.txt }

但是当我尝试将其合并到 c# 函数中时,出现了这个错误

{"Cannot bind parameter 'ScriptBlock'. Cannot convert the \"ipconfig.exe > c:\ipconfig.txt\" value of type \"System.String\" to type \"System.Management.Automation.ScriptBlock\"."}

即使我将脚本块参数值转换为 System.Management.Automation.ScriptBlock 对象?我做错了什么?

    private void btnInstallTest_Click(object sender, EventArgs e)
    {
        List<string> commands = new List<string>();

        commands.Add("invoke-command");
        List<Tuple<String, String>> parameters = new List<Tuple<string, string>>();
        parameters.Add(new Tuple<string, string>("computername", @"server"));
        parameters.Add(new Tuple<string, string>("ScriptBlock", @"ipconfig.exe > c:\ipconfig.txt"));

        Collection<PSObject> psobject = runRemotePowerShellCommands(commands, parameters, "server", @"domain\user", convertToSecureString("password"));          
    }

    private Collection<PSObject> runRemotePowerShellCommands(List<string> commands, List<Tuple<String, String>> parameters, string remoteMachineName, string domainAndUsername, SecureString securePW)
    {
        Collection<PSObject> psobjs = new Collection<PSObject>();
        string result = "";
        string shellUri = "http://schemas.microsoft.com/powershell/Microsoft.PowerShell";
        PSCredential psCredential = new PSCredential(domainAndUsername, securePW);
        WSManConnectionInfo connectionInfo = new WSManConnectionInfo(false, remoteMachineName, 5985, "/wsman", shellUri, psCredential);
        connectionInfo.AuthenticationMechanism = AuthenticationMechanism.Kerberos; //.Basic;

        using (Runspace runspace = RunspaceFactory.CreateRunspace(connectionInfo))
        {
            PowerShell powershell = PowerShell.Create();
            for (int i = 0; i < commands.Count; i++)
            {
                if (commands[i].Contains(";"))
                {

                    string[] commandsSplit = commands[i].Split(';');
                }
                else
                {
                    powershell.AddCommand(commands[i]);
                }

                System.Management.Automation.ScriptBlock sb = null;
                if (parameters != null)
                {
                    foreach (Tuple<string, string> param in parameters)
                    {
                        if (param.Item1.ToLower() == "scriptblock")
                        {
                            sb = ScriptBlock.Create(param.Item2);                                
                            powershell.AddParameter(param.Item1, sb);
                            //powershell.AddParameter(param.Item1, param.Item2);
                        }
                        else
                        {
                            powershell.AddParameter(param.Item1, param.Item2);
                        }
                    }
                }

                if (runspace.RunspaceStateInfo.State == RunspaceState.Opened)
                {
                    // do nothing, the runspace is already open
                }
                else
                {
                    runspace.Open();                        
                    powershell.Runspace = runspace;
                }

                try
                {
                    psobjs = powershell.Invoke();

                    if (powershell.HadErrors == true)
                    {
                        result = "Failed - " + powershell.Streams.Error[0].ToString();
                        result = result.Replace("\"", "*");
                        psobjs.Add(result);
                    }
                }
                catch (Exception ex)
                {
                    result = "Failed: " + ex.Message;
                    psobjs.Add(result);
                }
            }

            powershell.Commands.Clear();                
        }

        return psobjs;
    }

我觉得你太复杂了:

using (PowerShell ps = PowerShell.Create())
{
    ps.AddScript($@"Invoke-Command -ComputerName {name} -ScriptBlock {{ipconfig > C:\ipconfig.txt}}")
    ps.Invoke()
}

或者你可以链接 .AddCommand().AddParameter()