Utilities for ReScript. Includes:
- Sequences are now in a separate repository.
- A lazy-promise
TaskandTaskResult - Untagged
UnionandLiteralto construct and pattern match on discriminated unions of any kind - Useful extensions to
Option,Result, andArray NonEmptyArrayfor arrays with at least 1 item- A simple
Testrunner - Comparison utilities
Trampolinemodule to remove recursion
npm install @jmagaram/rescript-extrasAdd to your rescript.json...
{
...
+ "bs-dependencies": ["@jmagaram/rescript-extras"]
}Everything is accessible in the root-level Extras module.
let arr = "abc" -> Extras.NonEmptyArray.of1
let opt = Some(1) -> Extras.Option.isSomeAnd(i => i >= 1)Inspired by TaskEither in fp-ts, a Task is a lazy promise that never fails. The Task.Result works with lazy promises that always return an Error or an Ok. Just like a regular result, you can transform it before execution with map, mapError, flatMap, and toOption. When ready to execute, call toPromise.
The Union module provides functors to create tagged and untagged discriminated unions of 2, 3, 4, or 5 items. This is useful for interop with JavaScript libraries that produce or expect simple types like string | number and more complex types where the choices are tagged differently than how ReScript does it. See usage examples. Capabilities:
- Discriminate (pattern match) on any programmable criteria, like
typeof,instance of, lightweight shape detection (such as a tag), or parsing with a JSON parsing library. - All types can participate in a union.
- Custom equality
- Literal values like
Null,Undefined,True,False,-1, and custom literals viaMakeString,MakeInt, etc. - Built-in support for
Int,String,Bool,Float,option<t>,nullable<t>,null<t>, and tuples of length 2 and 3
This implementation does not utilize any special compiler support and so there are some limitations:
- Pattern matching must rely on a
matchfunction, not the usual matching syntax. Each case is distinguished byA|B|C|D. This can be easily improved by extending or wrapping the produced module; see the test file for examples. - Literal support and functors are a bit cumbersome
- No genType support
- No recursive type definition
Note: It is possible to create untagged unions with a library like rescript-struct and not use the functors defined in this package. See the usage examples for a comparision of the two approaches. This works very well and avoids abstractions, but requires a bit more code.
Note: The Rescript compiler has a new feature for untagged unions that works great with pattern matching support. There are limitations on which types can be included in the union, literal support is very nice, pattern matching is not customizable, and custom equality is not provided.
Functors to create Literal types of various kinds using MakeString and MakeInt and others. Includes built-in literals for True, False, and Null. You can create literals from reference types, and provide a custom equality operator to do things like case-insensitive string comparison. This implementation is completely type safe because each literal is its own unique type; you can't just cast any string to a "yes" for example.
Existential quanitifiers isSomeAnd and isNoneOr. Create an option from a function that may fail using fromTryCatch. Combine options with concat, map2, map3, and map4. "Add" an option to a regular value using fold and foldBack. Includes lazy forms such as orElseWith.
An array that must have at least one item in it. Include many of the usual functions like reduce, maxBy, minBy, map, mapi, concat, head, etc. Convert toArray and fromArray.
Generate an array from a generator function using unfold. Various utilities like head, last, lastIndex, isEmpty, and prepend.
Convert an array of results to a single result using fromArray and fromArrayMap. Create a result from a function that may fail with fromTryCatch. Transform an error with mapError.
Similar to the Types module, includes functions to safely inspect unknown values like toString and toInt that returns an option. Can inspect properties on objects as well. Not intended for full-featured JSON parsing.
Cmp.t is the ('a,'a) => float comparison function. The Cmp module provides comparison utilities such as as eq, neq, lt, gte, min, and max. fromMap makes it easy to generate a comparison function for an object based on a specific property in it. Or use reverse to change direction.
Functors MakeCompare and MakeEquals add sorting and equality functions to your custom data types.
Simple tools to remove recursion and avoid stack overflows.
Super-simple test runner. Make tests using make and makeAsync. Run them using runSuite.