async

Higher-order async utility functions for callback, async/await, and promise-based control flow in Node.js and the browser.

Library
npm
v3.2.6
28,132stars
MIT License

Repository Health

Pre-computed score based on development activity, maintenance, community, maturity, and trend momentum.How we score it →
64/100Good
Development Activity44
Maintenance28
Community84
Maturity60
Momentum40

Technical Analysis

AI-assessed by reading the actual repository — architecture, code quality, innovation, and documentation.How we score it →
77/100Good
Architecture80
Code Quality76
Innovation66
Learning Curve85

Async is a widely-used JavaScript utility library providing around 70 functions for managing asynchronous control flow: collection iteration (each, map, filter, reduce, sortBy), control-flow composition (waterfall, series, parallel, auto), and concurrency utilities (queue, cargo, retry). Every function follows Node’s error-first callback convention while also transparently accepting native async functions and Promise-returning functions, and returns a Promise when no callback is supplied.

Originally created in 2010, before Promises or async/await existed in JavaScript, Async remains one of the most depended-upon packages in the npm ecosystem, still receiving maintenance and pulling over 100 million weekly downloads. Version 3 rewrote the internals as ES modules with full async-function support while preserving the same callback-first API that made it a de facto standard for pre-Promise Node.js code.

What You Get

  • Around 70 async utility functions covering collections (each, map, filter, reduce, sortBy), control flow (series, parallel, waterfall, auto, race), and utilities (queue, cargo, retry, memoize)
  • Uniform support for three calling conventions — Node-style error-first callbacks, native async/await functions, and Promises — mixed freely within the same call
  • A dependency-graph task runner (auto/autoInject) that resolves execution order and concurrency automatically from named task requirements
  • Bounded-concurrency primitives (queue, cargo, and *Limit variants) for throttling parallel work against rate limits or resource constraints
  • Both a CommonJS build and a native ESM build (plus the separate async-es package), so the same API works in Node, bundlers, and directly in the browser

Common Use Cases

  • Rate-limiting concurrent API calls with mapLimit/queue so a batch job doesn’t overwhelm a downstream service
  • Orchestrating a multi-step startup sequence with auto, where some steps depend on the results of others finishing first
  • Migrating or maintaining legacy Node.js callback-based codebases without rewriting call sites to promises
  • Iterating over large collections asynchronously with eachSeries/mapSeries when operations must run in strict order, such as sequential file writes

Under The Hood

Architecture Async’s roughly 5,500 lines under lib/ are organized one function per file (lib/auto.js, lib/queue.js, lib/waterfall.js, and so on), each a thin wrapper around shared primitives in lib/internal/: DoublyLinkedList.js backs the queue’s task list, wrapAsync.js/asyncify.js normalize callback-, async-function-, and Promise-returning iteratees into one internal calling convention, and eachOfLimit.js/parallel.js implement the concurrency-limited iteration loop that most collection functions delegate to. lib/index.js re-exports every public function. The dependency-graph runner in auto.js builds an adjacency structure over the tasks object and drives each task’s callback through once()/onlyOnce() guards, starting a task only once all its listed dependencies have resolved. Because nearly every public function is a shim over the same wrapAsync/eachOfLimit internals, a change to the calling-convention normalization or the queue’s internal linked-list would ripple through virtually the entire public API.

Tech Stack The package ships with zero runtime dependencies — a deliberate choice for a foundational utility library — and relies on Babel (preset-es2015/es2017) to transpile the ES-module source under lib/ into the CommonJS dist/async.js published to npm, alongside a separate async-es package for pure-ESM consumers; Rollup produces the browser bundle. Testing runs on Mocha with Chai assertions and nyc coverage in Node, plus a parallel browser pass via Karma (karma-browserify, karma-firefox-launcher, karma-safari-launcher) exercising the same suite in real browsers. ESLint with @babel/eslint-parser enforces style, and GitHub Actions CI runs lint followed by the full test matrix on every push, with Coveralls tracking coverage. Documentation is generated via JSDoc from inline @name/@category annotations in each lib file.

Code Quality The test/ directory mirrors lib/ almost one-to-one, with dozens of individual test cases per function covering callback-style, async-function, and Promise-based invocation paths plus explicit error-propagation and double-callback edge cases. Error handling is explicit throughout: internal helpers like once.js and onlyOnce.js exist specifically to guard against a callback being invoked twice, and wrapAsync.js/asyncify.js branch explicitly on whether a passed function is a plain callback function, an AsyncFunction, or an async generator rather than silently coercing mismatches. There is no static type system — plain ES modules, no TypeScript — but ESLint enforces consistent style, and CI runs the full Node and browser test suites on every push.

API Design Async’s defining design choice is accepting three different calling conventions — error-first callbacks, native async functions, and Promise-returning functions — through every one of its roughly 70 functions via the wrapAsync/asyncify normalization layer, and returning a Promise itself when no callback is supplied. Function naming is highly consistent: a base verb (each, map, filter, sortBy) composes with Series (strict sequential) and Limit (bounded concurrency) suffixes, so learning one function’s variants teaches the pattern for the rest of the library. This uniformity is also the biggest cost for newcomers today: because the library predates Promises and async/await in the language, much of its surface area (waterfall, auto, series) now solves a problem the language itself later absorbed. Documentation stays thorough regardless — a JSDoc-generated per-function reference plus inline @example blocks in every source file keep the boilerplate for adopting any single function low.

Used by 23 apps in this directory

Python
50%
Other

Airbyte

Developer Tools · Data Engineering

21,998

Open-source ELT platform with 600+ connectors for moving data from any source to warehouses, lakes, and AI agents.

View details
95
Repo Health
80
Technical
66
Dependency
Built with
Python50%
Kotlin41%
Updated today
TypeScript
49%
MPL 2.0

Artillery

Devops · Developer Tools

9,071

Cloud-scale load testing and functional testing for APIs, WebSockets, gRPC, and headless browsers, distributed across AWS Lambda or Fargate with zero infrastructure to manage.

View details
88
Repo Health
73
Technical
68
Dependency
Built with
TypeScript49%
JavaScript48%
Updated 1 weeks ago
TypeScript
97%
AGPL 3.0

Bigcapital

Invoicing Finance

3,884

Self-hostable double-entry accounting platform with invoicing, inventory, multi-currency, and real-time financial reporting for small and medium businesses.

View details
91
Repo Health
77
Technical
61
Dependency
Built with
TypeScript97%
Updated yesterday
TypeScript
96%
Other

Cal.diy

Scheduling

48,218

The 100% MIT-licensed, community-driven scheduling platform — self-host your own booking infrastructure with no enterprise strings attached.

View details
95
Repo Health
86
Technical
65
Dependency
Built with
TypeScript96%
Updated yesterday
C++
51%
Other

Cocos Engine

Developer Tools · Game Development · Design Tools

9,798

Open-source, cross-platform 2D/3D game engine with Vulkan, Metal, and WebGL support for web, mobile, and instant gaming platforms

View details
87
Repo Health
79
Technical
71
Dependency
Built with
C++51%
TypeScript35%
Updated 3 days ago
TypeScript
98%
Apache 2.0

Codebuff

AI Code Assistants

11,750

An open-source AI coding assistant that coordinates specialized agents to edit your codebase from natural language — including Freebuff, a free, ad-supported version powered entirely by open-source models like DeepSeek and Kimi.

View details
85
Repo Health
71
Technical
67
Dependency
Built with
TypeScript98%
Updated yesterday
JavaScript
90%
Other

CodeSandbox

Code Editors · Developer Tools

13,640

Instantly ready browser-based IDE that runs full npm dependency resolution and transpilation entirely client-side, with no server needed.

View details
69
Repo Health
76
Technical
62
Dependency
Built with
JavaScript90%
Updated 1 weeks ago
JavaScript
83%
Other

Countly

Analytics · Marketing

5,896

Privacy-first, self-hosted analytics and customer engagement platform with full data ownership, GDPR compliance, and AI-powered insights across mobile, web, desktop, and IoT.

View details
95
Repo Health
82
Technical
65
Dependency
Built with
JavaScript83%
Updated 3 days ago
TypeScript
81%
Other

Directus

CMS · Low Code Platforms

37,783

Connect any SQL database and get instant REST and GraphQL APIs, a visual management Studio, and a native MCP server for AI agents — free for most organizations.

View details
92
Repo Health
82
Technical
76
Dependency
Built with
TypeScript81%
Vue18%
Updated 3 days ago

Join founders buildingwith open source

Opinionated takes, migration guides, cost-saving tips, and insights from the open source ecosystem.

Subscribe on Substack
Join 750+ subscribers

Search