Skip to content

Instantly share code, notes, and snippets.

@thebearingedge
Last active July 5, 2022 19:29
Show Gist options
  • Save thebearingedge/68052390e79a8a0978df3a2a97c71c02 to your computer and use it in GitHub Desktop.
Save thebearingedge/68052390e79a8a0978df3a2a97c71c02 to your computer and use it in GitHub Desktop.
Result type for Typescript, sorta like rust.
type Result<Ok, Err extends Error = Error> =
| { kind: 'ok', value: Ok }
| { kind: 'err', err: Err }
const Ok = <T>(value: T): Result<T> => {
return {
kind: 'ok',
value
}
}
const Err = <E extends Error = Error>(err: E): Result<never, E> => {
return {
kind: 'err',
err
}
}
type AnyFunction = (...args: any[]) => any
type Safely<F extends AnyFunction> =
(...args: Parameters<F>) => Promise<Result<Awaited<ReturnType<F>>>>
function safely<F extends AnyFunction>(fn: F): Safely<F> {
return async (...args) => {
try {
return Ok(await fn(...args))
} catch (err) {
return Err(err instanceof Error ? err : new Error(`uncaught ${err}`))
}
}
}
async function mayFail() {}
const safelyMayFail = safely(mayFail)
;(async () => {
const result = await safelyMayFail()
if (result.kind === 'ok') {
// result.value is mayFail's return value
} else {
// result.err is the Error object
}
})()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment