@zokugun/xtry 0.2.0 → 0.4.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -119,19 +119,21 @@ API reference
119
119
  ### Result helpers
120
120
 
121
121
  ```typescript
122
- export type Success<T> = { fails: false; value: T; error: null };
123
- export type Failure<E> = { fails: true; value: null; error: E };
124
- export type Result<T, E> = Success<T> | Failure<E>;
122
+ type Success<T> = { fails: false; value: T; error: undefined };
123
+ type Failure<E> = { fails: true; value: undefined; error: E };
124
+ type Result<T, E> = Success<T> | Failure<E>;
125
125
 
126
- export function ok<T>(value: T): Success<T>;
127
- export function err<E>(error: E): Failure<E>;
126
+ function ok<T>(value: T): Success<T>;
127
+ function err<E>(error: E): Failure<E>;
128
128
  ```
129
129
 
130
130
  ### Try helpers
131
131
 
132
132
  ```typescript
133
- export function xtry<T, E>(func: () => Exclude<T, Promise<unknown>>, handler?: (error: E) => void): Result<T, E>;
134
- export function xatry<T, E>(func: (() => Exclude<T, Promise<unknown>>) | Promise<Exclude<T, Promise<unknown>>>, handler?: (error: E) => void): Promise<Result<T, E>>;
133
+ function xtry<T, E>(func: () => Exclude<T, Promise<unknown>>, handler?: (error: unknown) => void | E): Result<T, E>;
134
+ function xatry<T, E>(func: (() => Exclude<T, Promise<unknown>>) | Promise<Exclude<T, Promise<unknown>>>, handler?: (error: unknown) => void | E): Promise<Result<T, E>>;
135
+
136
+ function stringifyError(error: unknown): string;
135
137
  ```
136
138
 
137
139
  Both helpers:
@@ -143,12 +145,15 @@ Both helpers:
143
145
  ### Partial helpers
144
146
 
145
147
  ```typescript
146
- export type YSuccess<T> = Success<T> & { success: true };
147
- export type YFailure<S> = { fails: false; success: false; type: S; value: null; error: null };
148
- export type YResult<T, E, S> = Failure<E> | YSuccess<T> | YFailure<S>;
149
-
150
- export function yok<T>(value: T): YSuccess<T>;
151
- export function yerr<S>(type: S): YFailure<S>;
148
+ type YSuccess<T> = Success<T> & { success: true };
149
+ type YFailure<M> = { fails: false; success: false; miscue: M; value: undefined; error: undefined };
150
+ type YResult<T, E, M> = Failure<E> | YSuccess<T> | YFailure<M>;
151
+
152
+ function yok<T>(value: T): YSuccess<T>;
153
+ function yerr<M>(type: M): YFailure<M>;
154
+ function yress<T, E>(result: Result<T, E>): Failure<E> | YSuccess<T>;
155
+ function yresa<T, E>(promise: Promise<Result<T, E>>): Promise<Failure<E> | YSuccess<T>>;
156
+ function yep<T>(result: Success<T>): YSuccess<T>;
152
157
  ```
153
158
 
154
159
  These helpers are useful when you need to separate soft rejections (`success: false`) from hard failures (`fails: true`).
package/lib/index.d.ts CHANGED
@@ -1,3 +1,4 @@
1
1
  export * from './partial.js';
2
2
  export * from './result.js';
3
+ export * from './stringify-error.js';
3
4
  export * from './try.js';
package/lib/index.js CHANGED
@@ -1,3 +1,4 @@
1
1
  export * from './partial.js';
2
2
  export * from './result.js';
3
+ export * from './stringify-error.js';
3
4
  export * from './try.js';
package/lib/partial.d.ts CHANGED
@@ -1,14 +1,17 @@
1
- import { type Failure, type Success } from './result.js';
2
- export type YResult<T, E, S> = Failure<E> | YSuccess<T> | YFailure<S>;
1
+ import { type Result, type Failure, type Success } from './result.js';
2
+ export type YResult<T, E, M> = Failure<E> | YSuccess<T> | YFailure<M>;
3
3
  export type YSuccess<T> = Success<T> & {
4
4
  success: true;
5
5
  };
6
- export type YFailure<S> = {
6
+ export type YFailure<M> = {
7
7
  fails: false;
8
8
  success: false;
9
- type: S;
10
- value: null;
11
- error: null;
9
+ miscue: M;
10
+ value: undefined;
11
+ error: undefined;
12
12
  };
13
13
  export declare function yok<T>(value: T): YSuccess<T>;
14
- export declare function yerr<S>(type: S): YFailure<S>;
14
+ export declare function yerr<M>(miscue: M): YFailure<M>;
15
+ export declare function yress<T, E>(result: Result<T, E>): Failure<E> | YSuccess<T>;
16
+ export declare function yresa<T, E>(promise: Promise<Result<T, E>>): Promise<Failure<E> | YSuccess<T>>;
17
+ export declare function yep<T>(result: Success<T>): YSuccess<T>;
package/lib/partial.js CHANGED
@@ -3,15 +3,30 @@ export function yok(value) {
3
3
  fails: false,
4
4
  success: true,
5
5
  value,
6
- error: null,
6
+ error: undefined,
7
7
  };
8
8
  }
9
- export function yerr(type) {
9
+ export function yerr(miscue) {
10
10
  return {
11
11
  fails: false,
12
12
  success: false,
13
- type,
14
- value: null,
15
- error: null,
13
+ miscue,
14
+ value: undefined,
15
+ error: undefined,
16
+ };
17
+ }
18
+ export function yress(result) {
19
+ if (result.fails) {
20
+ return result;
21
+ }
22
+ return yep(result);
23
+ }
24
+ export async function yresa(promise) {
25
+ return promise.then(yress);
26
+ }
27
+ export function yep(result) {
28
+ return {
29
+ ...result,
30
+ success: true,
16
31
  };
17
32
  }
package/lib/result.d.ts CHANGED
@@ -1,11 +1,11 @@
1
1
  export type Success<T> = {
2
2
  fails: false;
3
3
  value: T;
4
- error: null;
4
+ error: undefined;
5
5
  };
6
6
  export type Failure<E> = {
7
7
  fails: true;
8
- value: null;
8
+ value: undefined;
9
9
  error: E;
10
10
  };
11
11
  export type Result<T, E> = Success<T> | Failure<E>;
package/lib/result.js CHANGED
@@ -2,13 +2,13 @@ export function ok(value) {
2
2
  return {
3
3
  fails: false,
4
4
  value,
5
- error: null,
5
+ error: undefined,
6
6
  };
7
7
  }
8
8
  export function err(error) {
9
9
  return {
10
10
  fails: true,
11
- value: null,
11
+ value: undefined,
12
12
  error,
13
13
  };
14
14
  }
@@ -0,0 +1 @@
1
+ export declare function stringifyError(error: unknown): string;
@@ -0,0 +1,18 @@
1
+ export function stringifyError(error) {
2
+ if (typeof error === 'string') {
3
+ return error;
4
+ }
5
+ if (error instanceof Error) {
6
+ return error.message ?? String(error);
7
+ }
8
+ try {
9
+ const json = JSON.stringify(error);
10
+ if (typeof json === 'string') {
11
+ return json;
12
+ }
13
+ }
14
+ catch {
15
+ // fallthrough
16
+ }
17
+ return String(error);
18
+ }
package/lib/try.d.ts CHANGED
@@ -1,3 +1,3 @@
1
1
  import { type Result } from './result.js';
2
- export declare function xtry<T, E>(func: () => Exclude<T, Promise<unknown>>, handler?: ((error: E) => void)): Result<T, E>;
3
- export declare function xatry<T, E>(func: (() => Exclude<T, Promise<unknown>>) | Promise<Exclude<T, Promise<unknown>>>, handler?: ((error: E) => void)): Promise<Result<T, E>>;
2
+ export declare function xtry<T, E = unknown>(func: () => Exclude<T, Promise<unknown>>, handler?: (error: unknown) => E | undefined): E extends void ? Result<T, unknown> : Result<T, E>;
3
+ export declare function xatry<T, E = unknown>(func: (() => Exclude<T, Promise<unknown>>) | Promise<Exclude<T, Promise<unknown>>>, handler?: (error: unknown) => E | undefined): Promise<E extends void ? Result<T, unknown> : Result<T, E>>;
package/lib/try.js CHANGED
@@ -2,24 +2,36 @@ import { err, ok } from './result.js';
2
2
  export function xtry(func, handler) {
3
3
  try {
4
4
  const value = func();
5
+ // eslint-disable-next-line @typescript-eslint/no-unsafe-return
5
6
  return ok(value);
6
7
  }
7
8
  catch (error) {
8
9
  if (handler) {
9
- handler(error);
10
+ const newError = handler(error);
11
+ if (newError !== undefined) {
12
+ // eslint-disable-next-line @typescript-eslint/no-unsafe-return
13
+ return err(newError);
14
+ }
10
15
  }
16
+ // eslint-disable-next-line @typescript-eslint/no-unsafe-return
11
17
  return err(error);
12
18
  }
13
19
  }
14
20
  export async function xatry(func, handler) {
15
21
  try {
16
22
  const value = await (func instanceof Promise ? func : Promise.resolve().then(func));
23
+ // eslint-disable-next-line @typescript-eslint/no-unsafe-return
17
24
  return ok(value);
18
25
  }
19
26
  catch (error) {
20
27
  if (handler) {
21
- handler(error);
28
+ const newError = handler(error);
29
+ if (newError !== undefined) {
30
+ // eslint-disable-next-line @typescript-eslint/no-unsafe-return
31
+ return err(newError);
32
+ }
22
33
  }
34
+ // eslint-disable-next-line @typescript-eslint/no-unsafe-return
23
35
  return err(error);
24
36
  }
25
37
  }
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@zokugun/xtry",
3
3
  "description": "simple try/catch wrapper returning Result",
4
- "version": "0.2.0",
4
+ "version": "0.4.0",
5
5
  "author": {
6
6
  "name": "Baptiste Augrain",
7
7
  "email": "daiyam@zokugun.org"