Either combinators
Combining, falling back, and validating — map2…map5, alt, orElse, filterOrElse.
Lecture
Either on its own gives you
map, flatMap and fold. These four
methods cover the shapes that kept turning into a flatMap
with an if inside it.
map2 … map5 — combining independent results
When several Eithers have to succeed together —
parse a name and an age and an email —
map2 combines them and keeps the leftmost
failure. The combining callback runs only when every branch is a
Right. Arities run to five, the same cap as
zipOrAccumulate2..5 and
Curry2..Curry5.
"Fail-fast" here is about the reporting, not the work. The
branches are values you already computed, so all of them ran; what stops
at the first failure is the answer you get back. When you want every
failure — a form that highlights all four bad fields at once — that is
accumulation, which reports an
EitherNel instead and needs an accumulate scope.
Reach for map2 when one message is the right answer.
alt and orElse — falling back
alt is the fallback ladder: try this, and if it failed try
that. The alternative is a callback, so nothing beyond the first hit is
touched — cache, then disk, then network, paying only for what you
actually reach. The failure is discarded.
orElse is the same move for when the failure matters: the
handler receives it and may return a different failure type, so it is also
how you translate one error vocabulary into another.
recover is the richer sibling. It
runs the handler inside a fresh raise scope, so the handler writes
straight-line Dart and calls r.raise instead of constructing
an Either by hand. Use alt/orElse
when the replacement Either already exists, and
recover when the handler has real work to do.
filterOrElse — validating in place
Demotes a Right whose value fails a predicate into a
Left that the second callback builds from that value
— so the message can name what was wrong. A Left passes
through untouched and the predicate never runs. Chain them and the first
failing check wins.
It is the Either-value form of
Raise.ensure, which does the same
job inside an either { } builder. Inside a builder, prefer
ensure; on a value you already hold, this.
Demo 1 · map2 and map3
Demo 2 · alt, orElse, filterOrElse
Try it yourself
Exercise: reject an age outside 0..149, with a message of your own.
Either — the type these extend ·
either & Raise — builder scope, ensure and recover ·
accumulation — every failure instead of the first ·
Either × pipelines — carrying Eithers through a chain