Comparing version 1.0.0 to 1.1.0
@@ -1,1 +0,7 @@ | ||
export { Ok, Err } from "./main"; | ||
"use strict"; | ||
Object.defineProperty(exports, "__esModule", { value: true }); | ||
exports.Err = exports.Ok = void 0; | ||
var main_1 = require("./main"); | ||
Object.defineProperty(exports, "Ok", { enumerable: true, get: function () { return main_1.Ok; } }); | ||
Object.defineProperty(exports, "Err", { enumerable: true, get: function () { return main_1.Err; } }); | ||
//# sourceMappingURL=index.js.map |
@@ -0,1 +1,4 @@ | ||
"use strict"; | ||
Object.defineProperty(exports, "__esModule", { value: true }); | ||
exports.Err = exports.Ok = void 0; | ||
// --- Note --- | ||
@@ -33,7 +36,15 @@ // `throw` is a reserved keyword | ||
} | ||
export function Ok(data) { | ||
return { ok: true, data, throw: throwErr, else: elseDo, or }; | ||
function and(callback) { | ||
if (this.ok) { | ||
callback(this.data); | ||
} | ||
} | ||
export function Err(error) { | ||
return { ok: false, error, throw: throwErr, else: elseDo, or }; | ||
function Ok(data) { | ||
return { ok: true, data, throw: throwErr, else: elseDo, or, and }; | ||
} | ||
exports.Ok = Ok; | ||
function Err(error) { | ||
return { ok: false, error, throw: throwErr, else: elseDo, or, and }; | ||
} | ||
exports.Err = Err; | ||
//# sourceMappingURL=main.js.map |
type ThrowType = <T, E extends ErrType>(this: Result<T, E>, message?: string) => T; | ||
type ElseType = <T, E extends ErrType>(this: Result<T, E>, callback: (error: E) => T) => T; | ||
type OrType = <T, E extends ErrType>(this: Result<T, E>, orValue: T) => T; | ||
type AndType = <T, E extends ErrType>(this: Result<T, E>, callback: (result: T) => void) => void; | ||
type ThrowMethod = { | ||
@@ -94,3 +95,27 @@ /** | ||
}; | ||
type ResultMethods = ThrowMethod & ElseMethod & OrMethod; | ||
type AndMethod = { | ||
/** | ||
* @method `and` handles result in a callback ignoring the error | ||
* @param {(result: T) => void} callback - callback which will be executed if result ok field will is true. Callback is provided with `result` argument with the data type provided as `T` in `Result<T, E>` | ||
* @returns void | ||
* @example | ||
* ```ts | ||
* function tryReadFile(): Result<string, void> { | ||
* const text = fs.readFile('~/file.txt'); | ||
* | ||
* if (!text) { | ||
* return Err(); | ||
* } | ||
* | ||
* return Ok(text); | ||
* } | ||
* | ||
* tryReadFile.and((text) => { | ||
* console.log(text); | ||
* }) | ||
* ``` | ||
* */ | ||
and: AndType; | ||
}; | ||
type ResultMethods = ThrowMethod & ElseMethod & OrMethod & AndMethod; | ||
export type ErrType = string | Error | undefined | void; | ||
@@ -97,0 +122,0 @@ /** |
@@ -1,1 +0,3 @@ | ||
export {}; | ||
"use strict"; | ||
Object.defineProperty(exports, "__esModule", { value: true }); | ||
//# sourceMappingURL=types.js.map |
@@ -51,2 +51,11 @@ import { ErrType, Result } from "./types"; | ||
function and<T, E extends ErrType>( | ||
this: Result<T, E>, | ||
callback: (result: T) => void | ||
): void { | ||
if (this.ok) { | ||
callback(this.data); | ||
} | ||
} | ||
/** | ||
@@ -81,3 +90,3 @@ * @method Ok - Returns a value with a type `T` of `Result<T, E>` signifying success of an operation. If the `T` type is `void` or `undefined` can be used without a value. | ||
export function Ok<T>(data?: T): Result<T | undefined, never> { | ||
return { ok: true, data, throw: throwErr, else: elseDo, or }; | ||
return { ok: true, data, throw: throwErr, else: elseDo, or, and }; | ||
} | ||
@@ -118,3 +127,3 @@ | ||
): Result<never, E | undefined> { | ||
return { ok: false, error, throw: throwErr, else: elseDo, or }; | ||
return { ok: false, error, throw: throwErr, else: elseDo, or, and }; | ||
} |
@@ -10,2 +10,6 @@ type ThrowType = <T, E extends ErrType>( | ||
type OrType = <T, E extends ErrType>(this: Result<T, E>, orValue: T) => T; | ||
type AndType = <T, E extends ErrType>( | ||
this: Result<T, E>, | ||
callback: (result: T) => void | ||
) => void; | ||
@@ -105,4 +109,29 @@ type ThrowMethod = { | ||
type ResultMethods = ThrowMethod & ElseMethod & OrMethod; | ||
type AndMethod = { | ||
/** | ||
* @method `and` handles result in a callback ignoring the error | ||
* @param {(result: T) => void} callback - callback which will be executed if result ok field will is true. Callback is provided with `result` argument with the data type provided as `T` in `Result<T, E>` | ||
* @returns void | ||
* @example | ||
* ```ts | ||
* function tryReadFile(): Result<string, void> { | ||
* const text = fs.readFile('~/file.txt'); | ||
* | ||
* if (!text) { | ||
* return Err(); | ||
* } | ||
* | ||
* return Ok(text); | ||
* } | ||
* | ||
* tryReadFile.and((text) => { | ||
* console.log(text); | ||
* }) | ||
* ``` | ||
* */ | ||
and: AndType; | ||
}; | ||
type ResultMethods = ThrowMethod & ElseMethod & OrMethod & AndMethod; | ||
export type ErrType = string | Error | undefined | void; | ||
@@ -109,0 +138,0 @@ |
{ | ||
"name": "ts-res", | ||
"version": "1.0.0", | ||
"version": "1.1.0", | ||
"description": "TypeScript Result", | ||
@@ -9,5 +9,5 @@ "repository": "https://github.com/Slava-Ini/ts-result", | ||
"types": "build/index.d.ts", | ||
"tags": ["typescript", "result", "rust"], | ||
"keywords": ["typescript", "result", "rust"], | ||
"scripts": { | ||
"clean": "rimraf dist && rimraf tsconfig.tsbuildinfo", | ||
"clean": "rimraf build && rimraf tsconfig.tsbuildinfo", | ||
"build": "npm run clean && tsc", | ||
@@ -14,0 +14,0 @@ "test": "jest" |
@@ -14,5 +14,5 @@ # ts-res | ||
- Using npm - `npm install -D ts-result` | ||
- Using yarn - `yarn add --dev ts-result` | ||
- Using pnpm - `pnpm add -D ts-result` | ||
- Using npm - `npm install ts-result` | ||
- Using yarn - `yarn add ts-result` | ||
- Using pnpm - `pnpm add ts-result` | ||
@@ -73,2 +73,3 @@ ## Result Type | ||
- `else(callback: (error: E) => T)` - returns an unwrapped result or executes callback that returns back-up value which can be based on provided error | ||
- `and(callback: (result: T) => void)` - handles a result in a callback while ignoring an error, doesn't return anything | ||
@@ -87,3 +88,11 @@ ```ts | ||
mayFail(true).else((error) => 200); // returns 123 | ||
mayFail(false).else((error) => 200); // returns 100 (error can be used for some extra logic) | ||
mayFail(false).else((error) => 200); // returns 200 (error can be used for some extra logic) | ||
// -- and() | ||
mayFail(true).and((result) => { | ||
console.log(result); | ||
}); // logs 123 | ||
mayFail(false).and((result) => { | ||
console.log(result); | ||
}); // doesn't do anything | ||
``` | ||
@@ -95,25 +104,2 @@ | ||
- Use `Result<T, E>` and `throw()` for handling JSON parse | ||
```ts | ||
type DataType = { | ||
a: number; | ||
b: number; | ||
}; | ||
function parse(data: string): Result<DataType, Error> { | ||
let result: DataType; | ||
try { | ||
result = JSON.parse(data); | ||
} catch (err) { | ||
throw new Error("Couldn't parse JSON"); | ||
} | ||
return Ok(result); | ||
} | ||
const data: DataType = parse('{"a":100,"b":200}').throw(); // Returns {a: 100, b: 200} | ||
const data: DataType = parse('"a":100,"b":200').throw(); // Throws Error("Couldn't parse JSON") | ||
``` | ||
- Use `throw()` to unwrap the value after parsing a number | ||
@@ -191,1 +177,19 @@ | ||
``` | ||
- Use `and()` to handle a result of writing data to `localStorage` and ignore the error | ||
```ts | ||
function readLocalStorage(key: string): Result<string, void> { | ||
const data = localStorage.getItem(key); | ||
if (!data) { | ||
return Err(); | ||
} | ||
return Ok(data); | ||
} | ||
readLocalStorage.and((data) => { | ||
const parsedData = JSON.parse(data); | ||
console.log(parsedData); | ||
}) | ||
``` |
@@ -70,2 +70,15 @@ import { Result, Ok, Err } from "../lib"; | ||
}); | ||
test("and", () => { | ||
const mockFn = jest.fn(); | ||
toNumber("123").and((result) => { | ||
expect(result).toBe(123); | ||
}); | ||
toNumber("abc").and((_) => { | ||
mockFn(); | ||
}); | ||
expect(mockFn).not.toHaveBeenCalled(); | ||
}); | ||
}); | ||
@@ -134,2 +147,15 @@ | ||
}); | ||
test("and", () => { | ||
const mockFn = jest.fn(); | ||
getEmptyResult(true).and((result) => { | ||
expect(result).toBe(undefined); | ||
}); | ||
getEmptyResult(false).and((_) => { | ||
mockFn(); | ||
}); | ||
expect(mockFn).not.toHaveBeenCalled(); | ||
}); | ||
}); | ||
@@ -199,2 +225,15 @@ | ||
}); | ||
test("and", () => { | ||
const mockFn = jest.fn(); | ||
getCustomError(ErrorType.A).and((result) => { | ||
expect(result).toBe(undefined); | ||
}); | ||
getCustomError(ErrorType.A).and((_) => { | ||
mockFn(); | ||
}); | ||
expect(mockFn).not.toHaveBeenCalled(); | ||
}); | ||
}); |
@@ -6,5 +6,9 @@ { | ||
"rootDir": "./lib", | ||
"module": "CommonJS", | ||
"composite": true, | ||
"strict": true, | ||
"allowSyntheticDefaultImports": true, | ||
"downlevelIteration": true, | ||
"esModuleInterop": true, | ||
"sourceMap": true, | ||
"moduleResolution": "node", | ||
@@ -11,0 +15,0 @@ "declaration": true |
33073
20
748
191