Created
February 24, 2025 14:31
-
-
Save emilien-jegou/82e5bb4f134d4921745bbdc4fcf67b18 to your computer and use it in GitHub Desktop.
Typescript error handling
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import type { Prettify } from 'ts-essentials'; | |
export type Result<T = unknown, E = unknown> = Success<T> | Failure<E>; | |
export interface Success<T> { | |
kind: 'success'; | |
value: T; | |
} | |
export interface Failure<E> { | |
kind: 'failure'; | |
error: E; | |
} | |
export const success = <T>(value: T): Success<T> => { | |
return { | |
kind: 'success', | |
value: value, | |
}; | |
}; | |
export const failure = <E>(error: E): Failure<E> => { | |
return { | |
kind: 'failure', | |
error: error, | |
}; | |
}; | |
// run code in a 'failable' context where thrown exception are converted to a result error | |
// e.g. failable(() => {throw 'uncaught'; return 123}) | |
export const failable = <const T>(cb: () => T): Result<T, unknown> => { | |
try { | |
return success(cb()); | |
} catch (e: unknown) { | |
return failure<unknown>(e); | |
} | |
}; | |
// e.g. failableAsync(() => {throw 'uncaught'; return Promise.resolve(123)}) | |
export const failableAsync = async <const T>(cb: () => Promise<T>): Promise<Result<T, unknown>> => { | |
try { | |
return success(await cb()); | |
} catch (e: unknown) { | |
return failure<unknown>(e); | |
} | |
}; | |
// transform a throwable function into a function that return a result type | |
// | |
// e.g.: | |
// const myFunction = (t: boolean): number => { | |
// if (t) { throw 'invalid' } | |
// else { return 123 } | |
// } | |
// const mySafeFunction = safeify(myFunction) | |
// mySafeFunction(false) // Success<number> | |
export const safeify = <const CB extends (...args: any) => any>( | |
cb: CB, | |
): ((...args: Parameters<CB>) => Result<Prettify<ReturnType<CB>>, unknown>) => { | |
return (...args: any) => failable(() => cb(args)); | |
}; | |
export const safeifyAsync = <const Args extends any[], const Ret>( | |
cb: (...args: Args) => Promise<Ret>, | |
): ((...args: Args) => Promise<Result<Ret, unknown>>) => { | |
return (...args: any) => failableAsync(() => cb(...args)); | |
}; |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment