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
I am wondering if PowerShell has or will have in the future native support for the Task-based Asynchronous pattern in C#.
It would be nice to have some sugar for async and await but also just being able to work with .NET apps that rely heavily on this pattern (such as Kestrel) without having to worry about managing runspaces would be very nice.
The referenced code takes a subset of the PowerShell syntax and turns it into .NET delegates but it is essentially a different language (e.g. no commands) . PowerShell concurrency is fundamentally based on runspaces. I wrote an RFC for a task(ish) based model of concurrency a while back Native Support for Concurrent Programming in PowerShell but it hasn't gone anywhere. As far as await goes, I suspect doing the lift-and-split that C# does would be tricky in PowerShell (but I haven't looked at it a whole lot.) Now I do like Golang's model of concurrency with tasks and channels - maybe we should do that :-)
Anyway, can you provide more specific scenarios/examples of what you'd like to do? Even if we can't do a fully general implementation, I sure there's something useful we can do.
Sure thing! So we are in the middle of a rewrite of https://github.com/PowerShell/Polaris to a pure PowerShell implementation and are currently using HttpListener which works fine cross-platform for now but as HttpListener doesn't seem to be getting any development love lately we're looking at the new hotness Kestrel.
We are currently working with HttpListener's event based asynchronous support and using Oisin Grehan (@oising)'s marvelous function New-ScriptBlockCallback to provide an AsyncCallback. I was hoping to find the same thing in Kestrel but it appears that they only support the task based asynchronous pattern which I can't see an easy way to convert to an event based pattern.
The sample code that I would love to write and just have work is this sample: (simplified from this sample in C#)
This is my specific use-case at the moment but I think there are quite a few other .Net projects that rely heavily on the task based asynchronous pattern that are currently fairly complex to work with natively in PowerShell.
So, back when I had more ideas than the focus to complete most of them, I wrote a threads/tasks prototype extension to my old PSEventing library that could handle tasks, apm (iasyncresult) and callbacks. It got annoying as I tried to deal with runspaces, and while I had solutions, it just seemed to unwieldy and inelegant so I just got bored with it. Anyway, you may have some luck if you grok System.Threading.Tasks.Task.FromAsync (APM to Task methods) and the non-public static class System.Threading.Tasks.TaskToApm which goes in the other direction: Task to APM.
The referenced code takes a subset of the PowerShell syntax and turns it into .NET delegates but it is essentially a different language (e.g. no commands) .
The referenced code was an earlier attempt with a similar idea, but it just creates an lambda expression that invokes the script block against a RunspacePool.
Next, If you ever need to invoke a method on a type via reflection and that method could be async, we have a helper that we use everywhere in the http://ASP.NET Core code base that is highly optimized and flexible. The ObjectMethodExecutor
Would it be possible to implement await as a cmdlet instead of a keyword? The problem I see with JS's await is that it ruins chaining and would have similar impact to PowerShell pipelines. I think the semantics around Jobs circumvent this issue--perhaps we can use similar semantics for Tasks.
Also, when working with tasks and parallel stuff, a lot of functionality is implemented as extension methods, so easy, straight forward access to extension methods would be great in this context.
This issue has not had any activity in 6 months, if this is a bug please try to reproduce on the latest version of PowerShell and reopen a new issue and reference this issue if this is still a blocker for you.
microsoft-github-policy-service commented on Nov 16, 2023
This issue has not had any activity in 6 months, if this is a bug please try to reproduce on the latest version of PowerShell and reopen a new issue and reference this issue if this is still a blocker for you.
microsoft-github-policy-service commented on Nov 16, 2023
This issue has not had any activity in 6 months, if this is a bug please try to reproduce on the latest version of PowerShell and reopen a new issue and reference this issue if this is still a blocker for you.
Couldn't a Task continuation be represented by a specialization of a ThreadJob?
Oisin Grehan (@oising) For what it's worth, I tried exactly this and it works. I'm not yet sure how usable Task-based concurrency can be made in PowerShell, but it looks promising, at least. It's certainly working better than manually managing the dysfunctional preponderance of ThreadJobs and .Net Tasks that I so often end up with in PowerShell.
My basic "JobTask" implementation spans at least hundreds if not thousands of lines of code by the time all of the .Net/PowerShell interop is complete, though. If there's still interest in this, I think I could contrive a toy version to post.
Reacted by Oisin Grehan, Micah Rairdon, JosephColvin and Erik Rose
Activity
BrucePay commentedon Apr 24, 2018
The referenced code takes a subset of the PowerShell syntax and turns it into .NET delegates but it is essentially a different language (e.g. no commands) . PowerShell concurrency is fundamentally based on runspaces. I wrote an RFC for a task(ish) based model of concurrency a while back Native Support for Concurrent Programming in PowerShell but it hasn't gone anywhere. As far as
awaitgoes, I suspect doing the lift-and-split that C# does would be tricky in PowerShell (but I haven't looked at it a whole lot.) Now I do like Golang's model of concurrency with tasks and channels - maybe we should do that :-)Anyway, can you provide more specific scenarios/examples of what you'd like to do? Even if we can't do a fully general implementation, I sure there's something useful we can do.
Tiberriver256 commentedon Apr 24, 2018
Sure thing! So we are in the middle of a rewrite of https://github.com/PowerShell/Polaris to a pure PowerShell implementation and are currently using HttpListener which works fine cross-platform for now but as HttpListener doesn't seem to be getting any development love lately we're looking at the new hotness Kestrel.
We are currently working with HttpListener's event based asynchronous support and using Oisin Grehan (@oising)'s marvelous function New-ScriptBlockCallback to provide an AsyncCallback. I was hoping to find the same thing in Kestrel but it appears that they only support the task based asynchronous pattern which I can't see an easy way to convert to an event based pattern.
The sample code that I would love to write and just have work is this sample: (simplified from this sample in C#)
This is my specific use-case at the moment but I think there are quite a few other .Net projects that rely heavily on the task based asynchronous pattern that are currently fairly complex to work with natively in PowerShell.
Thanks for your thoughts!
BrucePay commentedon Apr 24, 2018
Micah Rairdon (@Tiberriver256) Thanks!
oising commentedon Apr 27, 2018
So, back when I had more ideas than the focus to complete most of them, I wrote a threads/tasks prototype extension to my old PSEventing library that could handle tasks, apm (iasyncresult) and callbacks. It got annoying as I tried to deal with runspaces, and while I had solutions, it just seemed to unwieldy and inelegant so I just got bored with it. Anyway, you may have some luck if you grok
System.Threading.Tasks.Task.FromAsync(APM to Task methods) and the non-public static classSystem.Threading.Tasks.TaskToApmwhich goes in the other direction: Task to APM.oising commentedon Apr 27, 2018
Ok, so that works.
Obviously I'm not suggesting a dependency on my Poke module, but it's just to facilitate the proof of concept here :)
SeeminglyScience commentedon Apr 27, 2018
Bruce Payette (@BrucePay)
I believe you're thinking of PSLambda :)
The referenced code was an earlier attempt with a similar idea, but it just creates an lambda expression that invokes the script block against a
RunspacePool.fMichaleczek commentedon Apr 6, 2019
I found this tweet today from David Fowl from AspNet Core Team :
https://twitter.com/davidfowl/status/1004237863913906176
https://github.com/aspnet/Extensions/blob/ff87989d893b000aac1bfef0157c92be1f04f714/shared/Microsoft.Extensions.ObjectMethodExecutor.Sources/ObjectMethodExecutor.cs
Do you think this code could be implemented as keyword "await" in PowerShell ?
chriskuech commentedon Jul 6, 2019
Would it be possible to implement
awaitas a cmdlet instead of a keyword? The problem I see with JS'sawaitis that it ruins chaining and would have similar impact to PowerShell pipelines. I think the semantics aroundJobs circumvent this issue--perhaps we can use similar semantics for Tasks.Bartolomeus-649 commentedon Jul 26, 2019
Also, when working with tasks and parallel stuff, a lot of functionality is implemented as extension methods, so easy, straight forward access to extension methods would be great in this context.
oising commentedon Sep 5, 2019
Couldn't a Task continuation be represented by a specialization of a ThreadJob?
microsoft-github-policy-service commentedon Nov 16, 2023
This issue has not had any activity in 6 months, if this is a bug please try to reproduce on the latest version of PowerShell and reopen a new issue and reference this issue if this is still a blocker for you.
microsoft-github-policy-service commentedon Nov 16, 2023
This issue has not had any activity in 6 months, if this is a bug please try to reproduce on the latest version of PowerShell and reopen a new issue and reference this issue if this is still a blocker for you.
microsoft-github-policy-service commentedon Nov 16, 2023
This issue has not had any activity in 6 months, if this is a bug please try to reproduce on the latest version of PowerShell and reopen a new issue and reference this issue if this is still a blocker for you.
microsoft-github-policy-service commentedon Nov 23, 2023
This issue has been marked as "No Activity" as there has been no activity for 6 months. It has been closed for housekeeping purposes.
alx9r commentedon Nov 30, 2024
Oisin Grehan (@oising) For what it's worth, I tried exactly this and it works. I'm not yet sure how usable Task-based concurrency can be made in PowerShell, but it looks promising, at least. It's certainly working better than manually managing the dysfunctional preponderance of ThreadJobs and .Net Tasks that I so often end up with in PowerShell.
My basic "JobTask" implementation spans at least hundreds if not thousands of lines of code by the time all of the .Net/PowerShell interop is complete, though. If there's still interest in this, I think I could contrive a toy version to post.