-
Notifications
You must be signed in to change notification settings - Fork 29.7k
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
stream: add _end method to write streams (equivilent to _flush) #2314
Conversation
doc/api/stream.markdown
Outdated
by child classes, and if so, will be called by the internal Writable | ||
class methods only. | ||
|
||
When the stream ends this function will be called before the stream the stream |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
double the stream
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
fixed thanks!
b90efef
to
d5db2c1
Compare
Is it the same as indutny@f3503ba ? Or do we need to replace this in io.js? |
The difference is that it blocks prefinish to make it more predictable when On Sat, Aug 8, 2015, 6:44 PM Fedor Indutny notifications@github.com wrote:
|
Oh I like this, very useful when a written stream needs footer data. |
This seems (superficially) very close to Slightly more worrying to me: the problem this solves is "the writable needs to produce data before it closes." This seems antithetical to what a writable should be doing — consuming data. It could be achieved by putting a transform between the readable source of data and its ultimate destination (or by nesting the transform inside the readable and piping directly from readable → writable.) Maybe it's a matter of documenting this more explicitly: "Node does not offer a mechanism for writable streams to produce their own data, or otherwise write to themselves, absent a transform stream." |
transform would be able to make use of it, and that would likely be something prefinish things would want to move to, but it's not backwards compatible. you can get this behavior with a transform stream but it's somewhat more complex as you need to write to the transform stream but listen to the finish event from the writable stream, if you want to make this available as a purely writable stream (from an api consumers perspective) there are some hacky work arounds to do so. Some concrete examples include
some less concrete examples include writing to a data source where you need to close it asynchronously at the end or add a trailer to some sort of data source with non streaming access, the key is not that it is hard to do it inside of your own app, the hard part is when exposing it as a reusable api, what I'm trying to avoid is where when you stream to a file you listen for |
@indutny there is a difference between your implementations besides timing, yours is on _writableState with the signature |
1c38a26
to
149d3ae
Compare
@indutny added the test from your commit into this (modified to not use writableState) and fixed this so it will actually pass that (previously didn't handle ._write callbacks) |
LGTM |
@@ -144,6 +145,9 @@ function Writable(options) { | |||
|
|||
if (typeof options.writev === 'function') | |||
this._writev = options.writev; | |||
|
|||
if (typeof options.end === 'function') | |||
this._end = options.end; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we use a Symbol here instead of this._end
?
The thought is that we can encourage new-style constructor use while also avoiding overloading a property that might be in use in the wild.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We could but
- it would be inconsistent with how the other methods work
- after making the change the next thing I'd have to do is make a regex to undo it for readable-stream
I'm still not 100% comfortable with this change. My discomfort stems from:
In both stated cases, the problem seems like it could be solved by nesting a transform and a writable inside an exposed writable:
The writable side of the Transform stream is exposed on the |
The difference between this and prefinish/flush is that this acts like people tend to assume flush works and how you'd probably make flush work if you could do it all over. I don't advocate keeping both this and flush long term for different uses rather a next step could be to depreciated flush and replace it with end in the documentation. |
I don't think it's how I would make flush work — writable streams currently don't hold onto any data that would necessitate a flush. They also don't generate data (IOW, they don't |
I was referring to how unintuitive it is that the finish event is not blocked by flush meaning that the semantics of whether a stream you are writing to is done are different depending on whether it is a transform or a writable leading to a refactor hazard. The other thing besides just caching and batching is resource shutdown, nesting stream primitives would likely be overkill for a 'shut this down async' in a writable stream. |
so still think this is a good idea, if for no other reason than whatwg streams also support this method for the purpose of 'asynchronously closing the underlying resources' |
@chrisdickinson @calvinmetcalf ... any further thoughts on this one? |
I'm still in favor of this and would find it super useful |
@calvinmetcalf ... could I ask you to take a moment to rebase and update then? |
a50f752
to
3aea1c6
Compare
@mcollina thanks for that link. @nodejs/streams is the streams working group? How do I join it? |
@olalonde open an issue on https://github.com/nodejs/readable-stream, and we'll move it from there! :) Just start contributing. Moving this forward would be a nice contribution! |
I see this is tagged as a minor bump. This should be a major bump IMO. I have a bunch of streams that use |
Just a heads up, as a semver-major if the hope is to land this in v7.x, it would need to land today before noon. It could land after the v7.x branch is cut with CTC approval but the goal is to set that bar very high so that we can get v7.x as stable as possible before the release in October. |
@jasnell this will likely go into v8, there is definitely no time for v7. |
I would like this (or similar) to land in Node.js v8. @calvinmetcalf what do you think? should we do a fresh PR/implementations, or update this? |
c133999
to
83c7a88
Compare
@mcollina are you still thinking about this? |
@thealphanerd definitely yes. It should happen, it would fix a lot of issues on implementations. |
Any progress on this? ping @calvinmetcalf |
Feel free to reopen this, if you get back to working on it. |
@fhinkel, this is something we are still discussing and we would like to do, I'm reopening. cc @nodejs/streams. |
from the @nodejs/streams wg meeting:
|
superseded by #12828 |
Adds the ability to for write streams to have an _end method which acts
similarly to the _flush method that transform streams have but is called before
the finish event is emitted and if asynchronous delays the stream from
finishing. The
end
option may also be passed in order to set it.Inspired to finally write this after losing a day to an error that ended up being because I was listening to finish but writing something in flush.
Method name is bikeshedable
previous discussion here nodejs/readable-stream#112