Last Updated: 3/6/2026
.otherwise()
Runs the pattern-matching expression with a default handler which will be called if no previous .with() clause matches the input value, and returns the result.
Signature
function otherwise(defaultHandler: (value: TInput) => TOutput): TOutput;Arguments
defaultHandler: (value: TInput) => TOutput
- Required
- Function called if no pattern matched the input value.
- Think of it as the
default:case ofswitchstatements. - All handlers on a single
matchcase must return values of the same type,TOutput.
Example
import { match, P } from 'ts-pattern';
const toString = (value: unknown): string =>
match(value)
.with(P.string, (str) => str)
.with(P.number, (num) => num.toFixed(2))
.with(P.boolean, (bool) => `${bool}`)
.otherwise(() => 'Unknown');
console.log(toString('hello')); // 'hello'
console.log(toString(42)); // '42.00'
console.log(toString(true)); // 'true'
console.log(toString(null)); // 'Unknown'Comparison with .exhaustive()
.otherwise() is useful when:
- You don’t need exhaustiveness checking
- You want to provide a catch-all case
- Your input type is
unknownor very broad
.exhaustive() is better when:
- You want compile-time guarantees that all cases are handled
- You’re working with discriminated unions
- You want TypeScript to catch missing cases
// Using .otherwise() - no exhaustiveness checking
const handleStatus1 = (status: 'idle' | 'loading') =>
match(status)
.with('idle', () => 'Ready')
.otherwise(() => 'Not ready'); // Catches 'loading'
// Using .exhaustive() - compile-time checking
const handleStatus2 = (status: 'idle' | 'loading') =>
match(status)
.with('idle', () => 'Ready')
.with('loading', () => 'Loading...') // Must handle all cases
.exhaustive();