How to debounce an input while skipping the first entry

Post Editor

I was recently working on a task requiring filtering and sorting data on the frontend side. I came across an issue that I wanted to debounce user input in order to decrease a number of filter and sort operations, however initial operation should be performed as soon as possible (without debounce).

1 min read
0 comments
post

How to debounce an input while skipping the first entry

I was recently working on a task requiring filtering and sorting data on the frontend side. I came across an issue that I wanted to debounce user input in order to decrease a number of filter and sort operations, however initial operation should be performed as soon as possible (without debounce).

post
post
1 min read
0 comments
0 comments

I was recently working on a task requiring filtering and sorting data on the frontend side. I came across an issue that I wanted to debounce user input in order to decrease a number of filter and sort operations, however initial operation should be performed as soon as possible (without debounce).

Let’s see how RxJS library helped me out!

Debounce every entry
Link to this section

Without the need for performing initial operation immediately, the solution might look like this:

<>Copy
import { of, BehaviorSubject, combineLatest } from 'rxjs'; import { debounceTime, delay, tap, map } from 'rxjs/operators'; class FrameworksService { private querySubject = new BehaviorSubject<string>(''); private query$ = this.querySubject.pipe( debounceTime(2000) ); private collection$ = of([ 'Angular', 'React', 'Vue' ]).pipe( delay(10) ); filteredCollection$ = combineLatest( this.query$, this.collection$ ).pipe( tap(() => console.log('filtering')), map(([query, collection]) => collection.filter(item => item.includes(query))) ); filter(query: string) { this.querySubject.next(query); } } const frameworksService = new FrameworksService(); frameworksService.filter('a'); frameworksService.filteredCollection$.subscribe(console.log); setTimeout(() => { frameworksService.filter('Angular'); frameworksService.filter('React'); frameworksService.filter('Vue'); frameworksService.filter('React'); }, 5000);

Note that, each entry is debounced, hence you need to wait 2s (debounce time) for the first console.log (a sign of performing filtering action) to appear.

However, I wanted to perform the initial operation ASAP.

Debounce every entry except for the first one
Link to this section

Here comes the power of RxJS operators.

I simply created two streams representing query, namely:

<>Copy
private querySubject = new BehaviorSubject<string>(''); private initialQuery$ = this.querySubject.pipe( first() ); private debouncedQuery$ = this.querySubject.pipe( skip(1), debounceTime(2000) );

and combined them as follows:

<>Copy
private query$ = merge( this.initialQuery$, this.debouncedQuery$ );

The rest of the FrameworksService class remained unchanged.

With the above solution you will see the first console.log immediately, while further queries will be debounced.

Comments (0)

Be the first to leave a comment

Share

About the author

author_image

I'm a Frontend Developer freelancer. Passionate of Angular and reactive programming who is always seeking for new coding challenges. Chocolate lover.

author_image

About the author

Wojciech Trawiński

I'm a Frontend Developer freelancer. Passionate of Angular and reactive programming who is always seeking for new coding challenges. Chocolate lover.

About the author

author_image

I'm a Frontend Developer freelancer. Passionate of Angular and reactive programming who is always seeking for new coding challenges. Chocolate lover.

Featured articles