-
Notifications
You must be signed in to change notification settings - Fork 4.8k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
API Proposal: PipeReader and PipeWriter implementations over a Stream #25087
Comments
FYI I have working tested versions of these in |
I wrote up extension methods to do this: dotnet/Nerdbank.Streams#11 |
We need an API design for this. We'll do this in 3.0. |
public static (Pipe left, Pipe right) CreateDuplexPipe(PipeOptions oneOptions, PipeOptions twoOptions); It looks like you're divided between calling the pipes |
I expect we'll spend the most time on this in the API review meeting. It was one of the more contentious APIs: |
💡 According to the latest API Design Review video, public APIs that return Tuples should use PropertyCase for naming their elements. Also, I feel like naming them "left" and "right" is rather unintuitive. Since it makes a duplex pipe, why not return one already initialized as the "Reader" and the other as the "Writer"? |
Or |
Notes are here: dotnet/apireviews#90 |
@terrajobst After implementing this I think we should have an overload of CopyFromAsync should take a cc @pakrym |
@stephentoub @terrajobst what are your thoughts on making the stream wrappers public? That way, we can derive them and disable Synchronous IO for our implementations in ASP.NET Core. |
We discussed this in the API review, and @davidfowl seemed comfortable with not exposing them. I think the general sentiment was that it'd be better to start with just these virtuals, and if exposing the concrete types seemed useful in the future, we could choose to do so subsequently. That said, I'm ok with it if it's valuable. But I suggest we treat that as a separate API issue that's proposed/reviewed like any other, even if it's prioritized. |
We'll do it once we finish this initial pass, there are a few API tweaks I want to add/make after finishing this implementation. |
@davidfowl, is this done such that this issue can be closed, or is it tracking additional work beyond dotnet/corefx#35399? |
There’s one part of the work that I still have to do. That is write the stream -> pipe adapter |
This will help with adoption of pipelines. The usual adapter code involves creating 2 pipes and creating 2 async loops that read from the stream and write into the pipe and reading from the pipe and writing into the Stream.
There are 2 directions: Stream -> Pipe and Pipe -> Stream.
NOTES:
Most of the per read/write costs can be mitigated by using CopyToAsync (if overridden by the Stream) but there are some downsides there as well.
We can avoid some of these overheads if we implement a PipeReader on top of CopyToAsync that doesn't use the Pipe internally. The idea here is that we call CopyToAsync on a fake stream that forwards WriteAsync calls to the PipeReader consumer. This implementation would pass buffers directly from the Stream to the consumer. If the consumer doesn't process the entire buffer, only the unconsumed buffer is copied into an internal buffer for the next read.
The write side isn't as problematic because we need to be able to allocate memory to write into the Stream so reusing the pipe isn't so bad here. The implementation here would likely be using a Pipe internally, then writing to the Stream on FlushAsync.
Other implementations
The text was updated successfully, but these errors were encountered: