Skip to content

tryOrDefault

Safely executes a function and falls back to a default value if the function throws or rejects. This helper is a pure, zero‑throw alternative to try/catch and is useful when you want to guarantee a safe fallback without interrupting a pipeline.

tryOrDefault never mutates input and never throws. If the callback throws or returns a rejected Promise, tryOrDefault returns the provided default value instead.

Signature

function tryOrDefault<T, A>(
  value: T,
  fn: (value: T) => A | Promise<A>,
  defaultValue: A
): A | Promise<A>

Parameters

Returns

One of:

  • The function result — if it succeeds.
  • A Promise resolving to the function result — if the function is asynchronous.
  • The default value — if the function throws or rejects.
  • A Promise resolving to the default value — if the function is asynchronous and rejects.

Behavior

  • Pure function: no side effects.
  • Never mutates input.
  • Never throws.
  • Converts synchronous throws into safe fallback values.
  • Converts asynchronous rejections into safe fallback values.

Examples

tryOrDefault("123", JSON.parse, null)
// "123" → JSON.parse("123") → 123


tryOrDefault("bad json", JSON.parse, null)
// returns null

await tryOrDefault("id", async id => fetchUser(id), null)

pipe(
  input,
  normalize,
  v => tryOrDefault(v, riskyTransform, v)
)

Notes

  • Intentionally minimal: it only handles success vs. failure.
  • Useful for optional parsing, optional transformations, and defensive pipelines.
  • Works seamlessly with pipe, compose, tap, and maybe.