powershell - 在 PowerShell v3 中运行并行 Invoke-WebRequest 作业

标签 powershell background-process powershell-3.0 download cmdlet

在 PowerShell 中以非常简单的方式同时运行后台作业,但我似乎无法使用新的(在 v3 中)cmdlet Invoke-WebRequest。

我有几千个文件,我正在通过 PowerShell 以脚本方式下载。效果很好,但连续执行它们需要几天时间:

for($f=0;$f -lt $urlList.Count;$f++)
{
    $remote = $urlList[$f] + $fileList[$f]
    $local = 'C:\folder\' + $fileList[$f]
    Invoke-WebRequest $remote -Method Get -OutFile $local -UserAgent FireFox
}

我已经多次尝试利用 'AsJob' 方法,但它们要么出错,要么完成得很好,但没有保存本地文件。下面是后者的一个例子:
for($f=0;$f -lt $urlList.Count;$f++)
{
    $remote = $urlList[$f] + $fileList[$f]
    $local = 'C:\folder\' + $fileList[$f]
    $command = "Invoke-WebRequest $remote -Method Get -OutFile $local -UserAgent FireFox"
    Start-Job {Invoke-Expression -Command $command}
}
Get-Job|Wait-Job

输出示例:
Id     Name            PSJobTypeName   State         HasMoreData     Location             Command                  
--     ----            -------------   -----         -----------     --------             -------                  
339    Job339          BackgroundJob   Running       True            localhost            Invoke-Expression -Com...
341    Job341          BackgroundJob   Running       True            localhost            Invoke-Expression -Com...
343    Job343          BackgroundJob   Running       True            localhost            Invoke-Expression -Com...
339    Job355          BackgroundJob   Completed     True            localhost            Invoke-Expression -Com...
341    Job357          BackgroundJob   Completed     True            localhost            Invoke-Expression -Com...
343    Job359          BackgroundJob   Completed     True            localhost            Invoke-Expression -Com...

奇怪的是,上面的作业完成的速度与下载相关文件所需的速度差不多……所以数据似乎正在某个地方——只是没有到我的保存位置。我假设它会进入内存但被转储而不被保存。尝试添加和删除“PassThru”选项,但无论哪种方式都得到相同的结果。还尝试将其通过管道传输到 Out-File,但仍然不高兴。不知道为什么这个特定的 cmdlet 如此糟糕。

最佳答案

您需要以它们实际进入作业的方式传入参数。在 V3 中,您可以使用 $using: 语法来执行此操作:

for($f=0;$f -lt $urlList.Count;$f++)
{
    $remote = $urlList[$f] + $fileList[$f]
    $local = 'C:\folder\' + $fileList[$f]
    Start-Job {Invoke-WebRequest $using:remote -Method Get -OutFile $using:local -UserAgent FireFox}
}
Get-Job|Wait-Job

顺便说一句,您不需要使用 Invoke-Expression。只需将要在作业中运行的代码放在脚本块中,即一组花括号 {...} .

关于powershell - 在 PowerShell v3 中运行并行 Invoke-WebRequest 作业,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15182577/

相关文章:

powershell - 如何在同一文件夹中使用Powershell生成Zip

powershell - Get-Content -Wait 在读取文件时锁定文件,防止 Add-Content 写入数据

arrays - 比较两个数组并获取不常见的值

powershell - 获取子项 : Cannot find path 'env' because it does not exist

iphone - 我怎样才能让 NSTimer 在用户使用应用程序的整个过程中一直运行?

javascript - 建立内容脚本和后台页面之间的通信链接

java - 如何查找所有文本文件而不考虑仅包含逗号和数字的扩展名?

Powershell-SetForegroundWindow

iOS - 在后台运行的应用程序可以将触摸/手势事件发送到前台的另一个应用程序吗?

powershell - 使用 PowerShell v3 的 Invoke-RestMethod 来 PUT/POST X Mb 的二进制文件