bufferWhen collects values emitted from the source observable into cache without passing them down to an observer until the
notifier observable emits (buffering). The buffer then sends the cached values as a group, resets and starts buffering again until the provided observable emits once more.
This operator is very similar to buffer, but once the buffer is flushed, it unsubscribes from the notifier observable and will re-subscribe once a new value arrives.
One interesting behavior of the
bufferWhen operator is that it can send empty set of values to the observer if the
notifier observable emits a value and the cache is empty.
The operator works in the following way:
- Subscribe to a source observable
- When a new value arrives from a source observable, put it in a cache
- If there’s no active subscription to a notifier observable, subscribe to it
- When a notifier observable emits a value, send all values from the cache to the observer, even if the cache is empty
- Unsubscribe from the notifier observable
- Once the source completes, send the complete notification to the observer
- If any of the source observables throws an error, send the error notification to the observer.
The following diagram demonstrates this sequence of steps:
UsageLink to this section
bufferWhen is often used when the batching technique is required. For example, sometimes you need to repeatedly perform a very expensive operation within a very small time frame, such as re-rendering a DOM tree on updates from a stream, batching can help collect updates and render them at once.
Here’s an example of using
bufferWhen to emit array of most recent interval events on every click:
const clicks = fromEvent(document, 'click'); const intervalEvents = interval(1000); const buffered = intervalEvents.pipe(bufferWhen(() => clicks)); buffered.subscribe(x => console.log(x));