How to create readable streams in Node.js

Creating custom readable streams in Node.js enables dynamic data generation and efficient data production for various applications and data sources. With over 25 years of experience in software development and as the creator of CoreUI, I’ve built numerous readable streams for API data feeds, database cursors, and real-time data generation. From my expertise, the most reliable approach is extending the Readable class and implementing the _read() method to control data production. This pattern provides complete control over data flow timing, batching, and source management for scalable data streaming applications.

Extend the Readable class and implement the _read() method to create custom data-producing streams.

const { Readable } = require('stream')

class NumberStream extends Readable {
  constructor(options = {}) {
    super(options)
    this.current = 1
    this.max = options.max || 100
  }

  _read() {
    if (this.current <= this.max) {
      this.push(`Number: ${this.current}\n`)
      this.current++
    } else {
      this.push(null) // Signal end of stream
    }
  }
}

const numberStream = new NumberStream({ max: 10 })
numberStream.on('data', chunk => console.log(chunk.toString()))

Here the NumberStream class extends Readable and generates sequential numbers. The _read() method is called when the stream needs more data, using this.push() to add data to the internal buffer. Pushing null signals the end of the stream. The constructor accepts options for customization. This pattern is ideal for generating data from databases, APIs, or computational processes without blocking the event loop.

Best Practice Note:

This is the same approach we use in CoreUI data services for streaming large dataset exports, real-time analytics feeds, and paginated API responses. Always implement backpressure handling and consider using async generators for simpler readable stream creation in modern Node.js versions.


Speed up your responsive apps and websites with fully-featured, ready-to-use open-source admin panel templates—free to use and built for efficiency.


About the Author

Subscribe to our newsletter
Get early information about new products, product updates and blog posts.
How to Remove Underline from Link in CSS
How to Remove Underline from Link in CSS

Passing props to child components in React function components
Passing props to child components in React function components

How to replace all occurrences of a string in JavaScript?
How to replace all occurrences of a string in JavaScript?

What is JavaScript Array.pop() Method?
What is JavaScript Array.pop() Method?

Answers by CoreUI Core Team