30秒学会 JavaScript 片段 · 2022年3月11日

30秒学会 JavaScript 片段 – How can I check if a value implements a stream in Node.js?

A Stream is an abstract interface for working with streaming data in Node.js. It is designed to support many different types of streams, such as readable, writable, and duplex streams.

While specifics differ from one type to another, there are also commonalities that can be used to type check for a stream. On top of that, these classes are well-defined and documented, so we can use that to our advantage to type check for a specific type of stream.

Check if value is a stream

In the most general case, we can check if a value is a stream by checking if it is an object and has a pipe property that is a function.

代码实现

import { createReadStream } from 'fs';

const isStream = val =>
  val !== null && typeof val === 'object' && typeof val.pipe === 'function';

isStream(createReadStream('test.txt')); // true

Check if value is a readable stream

A readable stream needs to have a _read function and a _readableState object. This is in addition to the general stream check, defined previously.

使用样例

import { createReadStream } from 'fs';

const isReadableStream = val =>
  val !== null &&
  typeof val === 'object' &&
  typeof val.pipe === 'function' &&
  typeof val._read === 'function' &&
  typeof val._readableState === 'object';

isReadableStream(createReadStream('test.txt')); // true

Check if value is a writable stream

A writable stream needs to have a _write function and a _writableState object. This is in addition to the general stream check, defined previously.

import { createWriteStream } from 'fs';

const isWritableStream = val =>
  val !== null &&
  typeof val === 'object' &&
  typeof val.pipe === 'function' &&
  typeof val._write === 'function' &&
  typeof val._writableState === 'object';

isWritableStream(createWriteStream('test.txt')); // true

Check if value is a duplex stream

Finally, a duplex stream needs to match the conditions for both a readable and a writable stream, as defined previously.

import Stream from 'stream';

const isDuplexStream = val =>
  val !== null &&
  typeof val === 'object' &&
  typeof val.pipe === 'function' &&
  typeof val._read === 'function' &&
  typeof val._readableState === 'object' &&
  typeof val._write === 'function' &&
  typeof val._writableState === 'object';

isDuplexStream(new Stream.Duplex()); // true

[!NOTE]

Transform streams are a special case of duplex streams, so they will also pass the isDuplexStream check.

翻译自:https://www.30secondsofcode.org/js/s/typecheck-nodejs-streams