UNPKG

@superbuilders/errors

Version:

Type-safe error handling library with error chaining, wrapping, and utilities inspired by Go

69 lines 3.47 kB
type Success<T> = { data: T; error: undefined; }; type Failure<E extends Error> = { data: undefined; error: E; }; type Result<T, E extends Error = Error> = Success<T> | Failure<E>; /** * Represents an error that wraps another error, establishing a cause chain. * @template C The type of the direct cause of this error. */ export interface WrappedError<C extends Error> extends Error { readonly cause: C; } /** * Recursively unwraps `WrappedError` types to find the type of the ultimate underlying cause. * If the error is not a `WrappedError` or the chain ends, it returns the type of that error. * * @example * type T0 = DeepestCause<WrappedError<Error>>; // Error * type T1 = DeepestCause<WrappedError<TypeError>>; // TypeError * type T2 = DeepestCause<WrappedError<WrappedError<SyntaxError>>>; // SyntaxError * type T3 = DeepestCause<RangeError>; // RangeError */ export type DeepestCause<E extends Error> = E extends WrappedError<infer NextCause> ? DeepestCause<NextCause> : E; declare function newError(message: string): Readonly<Error>; declare function wrap<E extends Error>(originalError: E, message: string): Readonly<WrappedError<E>>; /** * Returns the underlying cause of the error. * It traverses the error chain by accessing the `cause` property of each error, * returning the first error in the chain that does not have a further `cause` * that is an `Error` instance, or the error itself if it has no cause. * * If `error` is a `WrappedError<T>`, the return type will be the `DeepestCause<T>`, * providing a precise type for the root cause. * For other error types, it returns `Error`. */ declare function cause<T extends Error>(error: WrappedError<T>): DeepestCause<T>; declare function cause<T extends Error>(error: T): Error; /** * Reports whether any error in err's chain matches target. * The chain consists of err itself followed by the sequence of errors * obtained by repeatedly accessing the `cause` property. * An error is considered a match if it is identical (===) to target. */ declare function isError<T extends Error>(err: WrappedError<T>, target: T): boolean; declare function isError<T extends Error, U extends Error>(err: WrappedError<T>, target: U): boolean; declare function isError<T extends Error, U extends Error>(err: T, target: U): boolean; /** * Returns the first error in err's chain that matches `ErrorClass`. * The chain consists of err itself followed by the sequence of errors * obtained by repeatedly accessing the `cause` property. */ declare function asError<T extends Error, U extends Error>(err: WrappedError<T>, ErrorClass: new (...args: any[]) => U): U | undefined; declare function asError<T extends Error, U extends Error>(err: T, ErrorClass: new (...args: any[]) => U): U | undefined; /** * Wraps a Promise to return a Result object, discriminating between success (data) and failure (error). * If the promise rejects, the caught error is cast to type E. */ declare function tryCatch<T, E extends Error = Error>(promise: Promise<T>): Promise<Result<T, E>>; /** * Wraps a synchronous function to return a Result object, discriminating between success (data) and failure (error). * If the function throws, the caught error is cast to type E. */ declare function trySync<T, E extends Error = Error>(fn: () => T): Result<T, E>; export { newError as new, tryCatch as try, trySync, wrap, cause, isError as is, asError as as }; //# sourceMappingURL=index.d.ts.map