react-window-infinite-loader
A React hook and component that adds batched infinite-scroll data loading to react-window virtualized lists.
Repository Health
Technical Analysis
react-window-infinite-loader is a companion library for react-window that adds infinite-scroll loading to virtualized lists and grids. It exposes both a useInfiniteLoader hook (the recommended API since v2) and a legacy InfiniteLoader render-prop component, both of which track which rows have been loaded, detect which rows are about to scroll into view, and call a loadMoreRows callback with a batched range of indices to fetch — so consumers never have to manually wire up scroll-position math to know when to fetch more data.
Internally the library was rewritten for react-window’s version 2 API and ships its own bundled TypeScript definitions, replacing the previously separate @types package. It’s maintained by Brian Vaughn, the original author of react-window and react-virtualized, and is a common building block in apps that render long or unbounded lists — feeds, search results, data tables — where fetching everything upfront isn’t practical.
What You Get
- useInfiniteLoader hook — the modern, recommended API that returns an onRowsRendered handler to pass straight into a react-window List.
- InfiniteLoader render-prop component — a backwards-compatible alternative for codebases not yet migrated to the hook.
- Automatic request batching — unloaded row ranges are coalesced via minimumBatchSize so you don’t fire one network request per row.
- Configurable pre-fetch threshold — rows begin loading before they’re actually visible, controlled via the threshold prop.
- Bundled TypeScript types — no separate @types package needed.
Common Use Cases
- Infinite-scrolling feeds — load the next page of posts or items as the user scrolls near the end of a virtualized list.
- Paginated search results rendered in a virtualized list, fetched in chunks as the user scrolls.
- Data tables and grids backed by react-window that stream rows from a paginated API instead of loading the full dataset upfront.
- Chat or activity logs that lazily backfill older messages as the user scrolls up through a virtualized list.
Under The Hood
Architecture
The library is a small, single-purpose codebase split across five files: types.ts defines the shared Props/Indices shapes, useInfiniteLoader.ts is the primary hook that memoizes a pending-rows cache and produces the onRowsRendered callback, scanForUnloadedIndices.ts is a pure function that computes contiguous unloaded ranges while respecting minimumBatchSize, InfiniteLoader.ts is a thin render-prop wrapper kept for v1 backwards compatibility, and index.ts re-exports both public entry points. Data flow is one-directional — a onRowsRendered scroll event triggers a range scan, which drives loadMoreRows calls — and the pure algorithm is fully decoupled from the stateful hook, so the range-scanning logic can be tested and reasoned about independently of React.
Tech Stack
Written in TypeScript with React 18/19 as peer dependencies only (no runtime dependencies). Built with Vite plus vite-plugin-dts to produce dual CJS/ESM output with bundled .d.ts files, tested with Vitest, @testing-library/react, and jsdom, linted with a flat ESLint config (typescript-eslint, react-hooks, react-refresh) and formatted with Prettier, all wired together via pnpm, Husky, and lint-staged for pre-commit checks.
Code Quality
Real unit tests exist for both the hook and the pure scanning function, covering already-loaded rows, batched loading, and callback memoization across re-renders. Four separate GitHub Actions workflows run on every pull request — TypeScript compilation, ESLint, Prettier, and Vitest — so regressions are caught before merge. Naming is consistent, the codebase is fully typed with no observed use of any, and error handling is minimal by design since the library performs index arithmetic rather than I/O.
API Design
The useInfiniteLoader hook is the primary, ergonomic v2 API — one hook call wires directly into react-window’s onRowsRendered prop with no glue code required. The older InfiniteLoader render-prop component is retained only for v1 compatibility. The prop surface is minimal (isRowLoaded, loadMoreRows, rowCount, optional minimumBatchSize/threshold), every field carries a JSDoc comment in types.ts, and the README documents both the v1-to-v2 migration path and a full prop table.
Used by 8 apps in this directory
Appsmith
Developer Tools · Automation · No Code Platforms
Open-source low-code platform to build admin panels, dashboards, and internal tools connected to any database or API.
Convex Backend
Developer Tools · Databases
Open-source reactive database that lets developers build live-updating apps with pure TypeScript, strong consistency, and real-time subscriptions—no separate API layer required.
Grafana
Monitoring · Analytics
The open-source observability platform that unifies metrics, logs, and traces from any data source into dynamic, queryable dashboards.
ILLA Builder
Developer Tools · Low Code Platforms · No Code Platforms
Open-source low-code platform for building internal tools with drag-and-drop UI, reactive data bindings, and real-time collaboration.
Kibana
Analytics · Monitoring
Your open source window into the Elastic Stack — query, visualize, and act on data stored in Elasticsearch with real-time dashboards, AI-assisted search, and automated alerting.
Label Studio
AI Development · Data Engineering
Label Studio is an open-source, multi-type data labeling platform that lets teams annotate images, text, audio, video, and time series data with a configurable XML-based UI and export annotations in formats ready for any ML framework.
Mattermost
Team Chat · Collaboration · Devops
Open core, self-hosted team collaboration with chat, AI agents, voice calling, and deep DevOps integrations — all under your control.
Worklenz
Project Management · Product Management · Collaboration
All-in-one open source project management for teams who want full control — plan projects, track tasks, manage resources, and monitor finances without the SaaS lock-in.