2015-01-06 28 views
4

我有一个接受3个命名参数的PowerShell脚本。请让我知道如何从命令行传递相同的内容。我尝试了下面的代码,但同样不工作。它仅将整个值分配给P3。我的要求是P1应该包含1,P2应该2和P3应该被分配3.PowerShell将参数传递给参数列表

Invoke-Command -ComputerName server -FilePath "D:\test.ps1" -ArgumentList {-P1 1 -P2 2 -P3 3} 

以下是脚本文件代码。

Param (
    [string]$P3, 
    [string]$P2, 
    [string]$P1 
) 
Write-Output "P1 Value :" $P1 
Write-Output "P2 Value:" $P2 
Write-Output "P3 Value :" $P3 
+0

可能重复http://stackoverflow.com/questions/4225748/how-do-i-pass- named-parameters-with-invoke-command) –

回答

9

一个选项:

$params = @{ 
P1 = 1 
P2 = 2 
P3 = 3 
} 

$ScriptPath = 'D:\Test.ps1' 

$sb = [scriptblock]::create(".{$(get-content $ScriptPath -Raw)} $(&{$args} @params)") 

Invoke-Command -ComputerName server -ScriptBlock $sb 
+0

是的我能够使用上面的代码实现结果。 –

+1

您可以让我知道如何使用C#代码实现相同的功能,因为我的要求是从C#运行此PowerShell脚本。 –

+0

对不起,不知道C#足够好转换为你。 – mjolinor

3

使用哈希表:

icm -ComputerName test -ScriptBlock{$args} -ArgumentList @{"p1"=1;"p2"=2;"p3"=3} 
+0

可以请你提供更多的细节。 –

+0

看这个帖子http://stackoverflow.com/a/4226027/381149 –

2

通过mjolinor代码的伟大工程,但我花了几分钟的时间去了解它。

的代码,使一个简单的事情 - 生成脚本块带有内置参数的内容:

&{ 
    Param (
     [string]$P3, 
     [string]$P2, 
     [string]$P1 
    ) 
    Write-Output "P1 Value:" $P1 
    Write-Output "P2 Value:" $P2 
    Write-Output "P3 Value:" $P3 
} -P1 1 -P2 2 -P3 3 

那么这个脚本块被传递给调用命令。

为了简化代码:

".{$(get-content $ScriptPath -Raw)} $(&{$args} @params)" 

$scriptContent = Get-Content $ScriptPath -Raw 
$formattedParams = &{ $args } @params 
# The `.{}` statement could be replaced with `&{}` here, because we don't need to persist variables after script call. 
$scriptBlockContent = ".{ $scriptContent } $formattedParams" 
$sb = [scriptblock]::create($scriptBlockContent) 

让我们做一个基本的C#实现:

void Run() 
{ 
    var parameters = new Dictionary<string, string> 
    { 
     ["P1"] = "1", 
     ["P2"] = "2", 
     ["P3"] = "3" 
    }; 

    var scriptResult = InvokeScript("Test.ps1", "server", parameters) 
    Console.WriteLine(scriptResult); 
} 

string InvokeScript(string filePath, string computerName, Dictionary<string, string> parameters) 
{ 
    var innerScriptContent = File.ReadAllText(filePath); 
    var formattedParams = string.Join(" ", parameters.Select(p => $"-{p.Key} {p.Value}")); 
    var scriptContent = "$sb = { &{ " + innerScriptContent + " } " + formattedParams + " }\n" + 
     $"Invoke-Command -ComputerName {computerName} -ScriptBlock $sb"; 

    var tempFile = Path.Combine(Path.GetTempPath(), Guid.NewGuid() + ".ps1"); 
    File.WriteAllText(tempFile, scriptContent); 

    var psi = new ProcessStartInfo 
     { 
      FileName = "powershell", 
      Arguments = [email protected]"-ExecutionPolicy Bypass -File ""{tempFile}""", 
      RedirectStandardOutput = true, 
      UseShellExecute = false 
     }; 

    var process = Process.Start(psi); 
    var responseText = process.StandardOutput.ReadToEnd(); 

    File.Delete(tempFile); 

    return responseText; 
} 

的代码生成临时脚本并执行它。

示例脚本:

$sb = { 
    &{ 
     Param (
      [string]$P3, 
      [string]$P2, 
      [string]$P1 
     ) 
     Write-Output "P1 Value:" $P1 
     Write-Output "P2 Value:" $P2 
     Write-Output "P3 Value:" $P3 
    } -P1 1 -P2 2 -P3 3 
} 
Invoke-Command -ComputerName server -ScriptBlock $sb 
的[?我如何通过与调用命令的命名参数(