Monads

Option, Result, and Either types for TypeScript - Inspired by Rust

README

Monads Logo

monads


If you use this repo, star it ✨


Option, Result, and Either types for JavaScript


🦀 Inspired by Rust


Zero dependenciesLightweightFunctional



Install


  1. ```sh
  2. npm install @sniptt/monads
  3. ```

Getting started


### The `Option` type

Option represents an optional value: every Option is either Some and contains a value, or None, and does not.

[!NOTE]

Full documentation here: Option


  1. ```ts
  2. import { Option, Some, None } from '@sniptt/monads';

  3. const divide = (numerator: number, denominator: number): Option<number> => {
  4.   if (denominator === 0) {
  5.     return None;
  6.   } else {
  7.     return Some(numerator / denominator);
  8.   }
  9. };

  10. // The return value of the function is an option
  11. const result = divide(2.0, 3.0);

  12. // Pattern match to retrieve the value
  13. const message = result.match({
  14.   some: (res) => `Result: ${res}`,
  15.   none: 'Cannot divide by 0',
  16. });

  17. console.log(message); // "Result: 0.6666666666666666"
  18. ```

### The `Result` type

Result represents a value that is either a success (Ok) or a failure (Err).

[!NOTE]

Full documentation here: Result


  1. ```ts
  2. import { Result, Ok, Err } from '@sniptt/monads';

  3. const getIndex = (values: string[], value: string): Result<number, string> => {
  4.   const index = values.indexOf(value);

  5.   switch (index) {
  6.     case -1:
  7.       return Err('Value not found');
  8.     default:
  9.       return Ok(index);
  10.   }
  11. };

  12. const values = ['a', 'b', 'c'];

  13. getIndex(values, 'b'); // Ok(1)
  14. getIndex(values, 'z'); // Err("Value not found")
  15. ```

### The `Either` type

Either represents a value that is either Left or Right. It is a powerful way to handle operations that can result in two distinctly different types of outcomes.

[!NOTE]

Full documentation here: Either


  1. ```ts
  2. import { Either, Left, Right } from '@sniptt/monads';

  3. const divide = (numerator: number, denominator: number): Either<string, number> => {
  4.   if (denominator === 0) {
  5.     return Left('Cannot divide by 0');
  6.   } else {
  7.     return Right(numerator / denominator);
  8.   }
  9. };

  10. const result = divide(2.0, 3.0);

  11. const message = result.match({
  12.   left: (err) => `Error: ${err}`,
  13.   right: (res) => `Result: ${res}`,
  14. });

  15. console.log(message); // "Result: 0.6666666666666666"
  16. ```