Learn monads with practical JavaScript examples. Understand Maybe, map, flatMap, Promise chains, and how monads simplify computations involving missing values and async results.
Updated August 2026 — full tutorial restored for this URL.
TL;DR
-
Monads provide a pattern for chaining computations while keeping values inside a context such as nullable or asynchronous data.
-
Maybe helps handle missing values without deeply nested null checks.
-
maptransforms a value inside a Maybe, whileflatMapchains functions that already return a Maybe. -
Promises follow a similar chaining idea, with
then()behaving likeflatMapfor asynchronous values. -
You can learn and use monadic patterns without needing category theory or advanced functional programming knowledge.
A monad is a pattern for chaining computations inside a context (nullable values, async results, errors) without nested if soup. We stay practical: Maybe / Optional style code in JavaScript.
Related: Currying for Beginners.
- The problem monads solve
- Maybe with map and flatMap
- Chaining example
- Promises are monadic too
- Takeaways
1. The problem monads solve
const city = user && user.address && user.address.city;
Nested null checks get messy. A Maybe wraps “value or nothing” and lets you chain safely.
2. Maybe with map and flatMap
class Maybe {
constructor(value) { this.value = value; }
static of(v) { return new Maybe(v); }
static none() { return new Maybe(null); }
isNothing() { return this.value == null; }
map(fn) {
return this.isNothing() ? Maybe.none() : Maybe.of(fn(this.value));
}
flatMap(fn) {
return this.isNothing() ? Maybe.none() : fn(this.value);
}
getOr(fallback) {
return this.isNothing() ? fallback : this.value;
}
}
map transforms a value still inside Maybe. flatMap (bind) is for functions that already return a Maybe — avoids Maybe<Maybe<T>>.
3. Chaining example
const user = { address: { city: "Lagos" } };
const city = Maybe.of(user)
.map(u => u.address)
.map(a => a.city)
.getOr("unknown");
console.log(city); // Lagos
4. Promises are monadic too
Promise.then behaves like flatMap for async values. That is why promise chains feel similar to Maybe chains — same “compute in a context” idea.
5. Takeaways
- You do not need category theory to use the pattern.
- Start with Optional/Maybe and Promise; add Either/Result for errors later.
- Prefer clear names over saying “monad” in business code reviews.
Final Thought
Monads can sound intimidating, but the practical idea is much simpler: keep a value inside a context and provide a consistent way to continue working with it. Maybe handles missing values, while Promise chains handle asynchronous results.
The important part is not memorizing the formal definition or using the word “monad” everywhere. Start with practical patterns such as Maybe, Optional, and Promise, understand how map and flatMap work, and focus on how they make chained computations easier to reason about.
Once the pattern clicks, concepts such as Either and Result become easier to understand when you need more explicit error handling.