Compile Ready
Module 14 · Machine Coding

Build: Infinite Scroll

Intermediate12m read35m practice47m total
Machine CodingIntersectionObserverPaginationPerformance

Introduction

Infinite scroll loads the next page when the user approaches the end of the current list. The modern browser primitive for this is IntersectionObserver, not a raw scroll listener.

A strong implementation prevents duplicate loads, stops when there are no more pages, renders errors without losing existing content, and exposes a cleanup method.

Why This Matters

This challenge tests browser API judgment and async state discipline. Many candidates attach a scroll handler and accidentally issue overlapping page requests. A production answer uses a sentinel element, observes intersection, and guards loading state.

Theory

Sentinel approach

Place a lightweight sentinel element after the list. When it intersects the viewport, call loadNext. The browser decides when to notify you, which is more efficient than running code on every scroll event.

State machine

The feature has three important booleans: loading, done, and sometimes error. loading prevents duplicate page requests while the sentinel remains visible. done disconnects the observer once the API says there is no next page. Existing items stay rendered if a later page fails.

API contract

A clean loadPage(page) returns { items, hasMore }. The scroller owns page numbering and rendering. The caller owns data fetching and item rendering. This separation makes the component testable and reusable.

Visual Diagrams

Infinite scroll state machine
sentinel visible
   |
   v
loading? yes -> ignore
   |
   no
   v
load page N
   |
   +--> success with hasMore -> append, N = N + 1
   +--> success without more -> append, disconnect
   +--> failure -> show retryable error

The loading guard is what prevents duplicate page requests.

Code Examples

Complete IntersectionObserver infinite scroller

The DOM implementation uses a sentinel element and keeps data loading separate from item rendering.

Loading…

Playground

Loading editor…
Console

Press Run to execute the code and see output here.

Output Prediction

Predict the output #1

javascript
1function createPaginator(items, pageSize) {
2 var page = 0;
3
4 return {
5 next: function () {
6 var start = page * pageSize;
7 var slice = items.slice(start, start + pageSize);
8 page += 1;
9
10 return {
11 items: slice,
12 hasMore: page * pageSize < items.length
13 };
14 }
15 };
16}
17
18var paginator = createPaginator(['a', 'b', 'c', 'd', 'e'], 2);
19console.log(paginator.next().items.join(','));
20console.log(paginator.next().items.join(','));
21var last = paginator.next();
22console.log(last.items.join(',') + ':' + last.hasMore);

Coding Exercises

Implement an IntersectionObserver infinite scroller

Medium

Build createInfiniteScroller(options).

Requirements:

  • Accept { list, sentinel, status, loadPage, renderItem, root, rootMargin, startPage, loadImmediately }.
  • Use IntersectionObserver on the sentinel.
  • Prevent overlapping page requests.
  • Append new items without rerendering the full list.
  • Stop observing when hasMore is false.
  • Keep existing content if a later page fails.
  • Return { loadNextPage, destroy }.

Constraints:

  • Do not use scroll event polling.
  • Do not assume the API always succeeds.

Interview Questions

1Why is `IntersectionObserver` preferred over a scroll event listener?

IntersectionObserver is browser-optimized and evented. It avoids running JavaScript on every scroll frame and makes it easy to observe a sentinel near the bottom of the list. Scroll listeners require throttling, manual geometry calculations, and careful cleanup.

Asked at:NetflixAmazon

Follow-ups

  • How would you support older browsers?
  • How would you preserve scroll position when prepending items?
2How do you prevent duplicate page requests?

Keep a loading flag. If the sentinel fires again while a page request is in flight, return early. Clear the flag in finally so both success and failure unblock future attempts.

Quiz

1. What should happen when the API returns `hasMore: false`?

Summary

  • Use a sentinel plus `IntersectionObserver` for modern infinite scroll.
  • `loading` prevents overlapping requests; `done` stops observation after the final page.
  • Append new page nodes instead of rerendering the whole list.
  • Keep loading concerns separate from item rendering.

Cheat Sheet

Infinite scroll checklist

  • Sentinel after the list.
  • IntersectionObserver with helpful rootMargin.
  • loading guard for duplicate intersections.
  • done guard for final page.
  • API contract: { items, hasMore }.
  • Append only new nodes.
  • Show status and preserve existing items on error.
  • Return destroy().