Skip to content

Writable is destroyed before calling callback in rare case #40377

Description

@szmarczak

Version

v16.10.0

Platform

Linux solus 5.14.7-198.current #1 SMP PREEMPT Wed Sep 22 16:02:46 UTC 2021 x86_64 GNU/Linux

Subsystem

stream

What steps will reproduce the bug?

const {Writable} = require('stream');

class X extends Writable {
    async _destroy(error, callback) {
        (async () => {
            await new Promise(resolve => setTimeout(resolve, 10));
            console.log(w._writableState.closed);

            callback(error);
        })();
    }
}

const w = new X();

w.once('error', error => {
    console.log(error);
});

w.destroy(new Error('oh no!'));

How often does it reproduce? Is there a required condition?

Always.

What is the expected behavior?

false
Error: oh no!

What do you see instead?

true

Additional information

Some undocumented behavior here:

try {
const result = self._destroy(err || null, onDestroy);
if (result != null) {
const then = result.then;
if (typeof then === 'function') {
then.call(
result,
function() {
process.nextTick(onDestroy, null);
},
function(err) {
process.nextTick(onDestroy, err);
});
}
}
} catch (err) {
onDestroy(err);
}

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    confirmed-bugIssues and PRs for confirmed bugs.docIssues and PRs related to Node.js documentation.good first issueIssues that are suitable for first-time contributors.linuxIssues and PRs related to the Linux platform.streamIssues and PRs related to Node.js streams.

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions