You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Windows PowerShell currently supports the foreach language keyword with the -parallel switch flag, but only for workflow scripts.
15
+
16
+
```powershell
17
+
18
+
workflow wf1 {
19
+
$list = 1..5
20
+
foreach -parallel -throttlelimit 5 ($item in $list) {
21
+
Start-Sleep -Seconds 1
22
+
Write-Output "Output $item"
23
+
}
24
+
}
25
+
26
+
```
27
+
28
+
This will run the script block with each value in the `$list` array, in parallel using workflow jobs.
29
+
However, workflow is not supported in PowerShell Core 6, partly because it is a Windows only solution but also because it is cumbersome to use.
30
+
In addition the workflow implementation is very heavy weight, using lots of system resources.
31
+
32
+
This is a proposal to re-implement `foreach -parallel` in PowerShell Core, using PowerShell's support for concurrency via Runspaces.
33
+
It is similar to the [ThreadJob module](https://www.powershellgallery.com/packages/ThreadJob/1.1.2) except that it becomes part of the PowerShell language via `foreach -parallel`.
34
+
35
+
## Motivation
36
+
37
+
As a PowerShell User,
38
+
I can do simple fan-out concurrency from within the language, without having to obtain and load a separate module or deal with PowerShell jobs.
39
+
40
+
## Specification
41
+
42
+
The PowerShell `foreach -parallel` language keyword will be re-implemented to perform invoke script blocks in parallel, similar to how it works for workflow functions except that script blocks will be invoked on threads within the same process rather than in workflow jobs running in separate processes.
43
+
The default behavior is to fan-out script block execution to multiple threads, and then wait for all threads to finish.
44
+
However, a `-asjob` switch will also be supported that returns a PowerShell job object for asynchronous use.
45
+
If the number of foreach iterations exceed the throttle limit value, then only the throttle limit number of threads are created at a time and the rest are queued until a running thread becomes available.
46
+
47
+
### Supported foreach parameters
48
+
49
+
-`-parallel`
50
+
-`-throttlelimit`
51
+
-`-timeout`
52
+
-`-asjob`
53
+
54
+
### P0 Features
55
+
56
+
-`foreach -parallel` fans out script block execution to threads, along with a bound single foreach iteration value
57
+
58
+
-`-throttlelimit` parameter value specifies the maximum number of threads that can run at one time
Not sure. I think it should be something other than infinite. One suggestion is to base it on system processor cores. But I am inclined to give it a 'reasonable' default value (10-50) since many scripts may not be compute intensive and simply wait for a result. The user can customize it for specific needs.
Code has comments. Press enter to view.
59
+
60
+
-`-timeout` parameter value specifies a maximum time to wait for all iterations to complete, after which 'stop' will be called on all running script blocks to terminate execution
To start with I feel we should only allow the single iteration variable as I feel it would satisfy most use cases. e.g.,
foreach-parallel ($itemin$list) { "This is the only variable passed in: $item" }
#orGet-Process|ForEach-Object-Parallel { "This is the only variable passed in: $_" }
In the future we could look at support for a "using" directive to pass other variables to the parallel running script block:
0 commit comments