Merged with develop

This commit is contained in:
Ozzie Gooen 2022-04-28 16:51:02 -04:00
commit f7afbf9c39
4 changed files with 204 additions and 51 deletions

View File

@ -20,7 +20,7 @@
], ],
"suffix": ".bs.js", "suffix": ".bs.js",
"namespace": true, "namespace": true,
"bs-dependencies": ["@glennsl/rescript-jest", "rationale", "bisect_ppx"], "bs-dependencies": ["@glennsl/rescript-jest", "bisect_ppx"],
"gentypeconfig": { "gentypeconfig": {
"language": "typescript", "language": "typescript",
"module": "commonjs", "module": "commonjs",

View File

@ -35,30 +35,22 @@
"bisect_ppx": "^2.7.1", "bisect_ppx": "^2.7.1",
"jstat": "^1.9.5", "jstat": "^1.9.5",
"lodash": "4.17.21", "lodash": "4.17.21",
"mathjs": "10.5.0",
"pdfast": "^0.2.0",
"rationale": "0.2.0",
"rescript": "^9.1.4", "rescript": "^9.1.4",
"rescript-fast-check": "^1.1.1", "rescript-fast-check": "^1.1.1",
"@glennsl/rescript-jest": "^0.9.0", "@glennsl/rescript-jest": "^0.9.0",
"@istanbuljs/nyc-config-typescript": "^1.0.2", "@istanbuljs/nyc-config-typescript": "^1.0.2",
"@types/jest": "^27.4.0", "@types/jest": "^27.4.0",
"babel-plugin-transform-es2015-modules-commonjs": "^6.26.2", "babel-plugin-transform-es2015-modules-commonjs": "^6.26.2",
"bisect_ppx": "^2.7.1",
"chalk": "^5.0.1", "chalk": "^5.0.1",
"codecov": "3.8.3", "codecov": "3.8.3",
"fast-check": "2.25.0", "fast-check": "2.25.0",
"gentype": "^4.3.0", "gentype": "^4.3.0",
"jest": "^27.5.1", "jest": "^27.5.1",
"jstat": "^1.9.5",
"lodash": "4.17.21",
"mathjs": "10.5.0", "mathjs": "10.5.0",
"moduleserve": "0.9.1", "moduleserve": "0.9.1",
"nyc": "^15.1.0", "nyc": "^15.1.0",
"pdfast": "^0.2.0", "pdfast": "^0.2.0",
"rationale": "0.2.0",
"reanalyze": "^2.19.0", "reanalyze": "^2.19.0",
"rescript": "^9.1.4",
"ts-jest": "^27.1.4", "ts-jest": "^27.1.4",
"ts-loader": "^9.2.8", "ts-loader": "^9.2.8",
"ts-node": "^10.7.0", "ts-node": "^10.7.0",

View File

@ -1,4 +1,7 @@
open Rationale.Function.Infix /*
Some functions from modules `L`, `O`, and `R` below were copied directly from
running `rescript convert -all` on Rationale https://github.com/jonlaing/rationale
*/
module FloatFloatMap = { module FloatFloatMap = {
module Id = Belt.Id.MakeComparable({ module Id = Belt.Id.MakeComparable({
type t = float type t = float
@ -55,17 +58,59 @@ module O = {
| None => rFn() | None => rFn()
} }
() ()
let fmap = Rationale.Option.fmap let fmap = (f: 'a => 'b, x: option<'a>): option<'b> => {
let bind = Rationale.Option.bind switch x {
let default = Rationale.Option.default | None => None
let isSome = Rationale.Option.isSome | Some(x') => Some(f(x'))
let isNone = Rationale.Option.isNone }
let toExn = Rationale.Option.toExn }
let some = Rationale.Option.some let bind = (o, f) =>
let firstSome = Rationale.Option.firstSome switch o {
let toExt = Rationale.Option.toExn // wanna flag this-- looks like a typo but `Rationale.OptiontoExt` doesn't exist. | None => None
let flatApply = (fn, b) => Rationale.Option.apply(fn, Some(b)) |> Rationale.Option.flatten | Some(a) => f(a)
let flatten = Rationale.Option.flatten }
let default = (d, o) =>
switch o {
| None => d
| Some(a) => a
}
let isSome = o =>
switch o {
| Some(_) => true
| _ => false
}
let isNone = o =>
switch o {
| None => true
| _ => false
}
let toExn = (err, o) =>
switch o {
| None => raise(Failure(err))
| Some(a) => a
}
let some = a => Some(a)
let firstSome = (a, b) =>
switch a {
| None => b
| _ => a
}
let toExt = toExn
let flatten = o =>
switch o {
| None => None
| Some(x) => x
}
let apply = (o, a) =>
switch o {
| Some(f) => bind(a, b => some(f(b)))
| _ => None
}
let flatApply = (fn, b) => apply(fn, Some(b)) |> flatten
let toBool = opt => let toBool = opt =>
switch opt { switch opt {
@ -113,6 +158,11 @@ module O2 = {
/* Functions */ /* Functions */
module F = { module F = {
let pipe = (f, g, x) => g(f(x))
let compose = (f, g, x) => f(g(x))
let flip = (f, a, b) => f(b, a)
let always = (x, _y) => x
let apply = (a, e) => a |> e let apply = (a, e) => a |> e
let flatten2Callbacks = (fn1, fn2, fnlast) => let flatten2Callbacks = (fn1, fn2, fnlast) =>
@ -160,7 +210,12 @@ exception Assertion(string)
/* R for Result */ /* R for Result */
module R = { module R = {
let result = Rationale.Result.result open Belt.Result
let result = (okF, errF, r) =>
switch r {
| Ok(a) => okF(a)
| Error(err) => errF(err)
}
let id = e => e |> result(U.id, U.id) let id = e => e |> result(U.id, U.id)
let isOk = Belt.Result.isOk let isOk = Belt.Result.isOk
let getError = (r: result<'a, 'b>) => let getError = (r: result<'a, 'b>) =>
@ -168,8 +223,18 @@ module R = {
| Ok(_) => None | Ok(_) => None
| Error(e) => Some(e) | Error(e) => Some(e)
} }
let fmap = Rationale.Result.fmap let fmap = (f: 'a => 'b, r: result<'a, 'c>): result<'b, 'c> => {
let bind = Rationale.Result.bind switch r {
| Ok(r') => Ok(f(r'))
| Error(err) => Error(err)
}
}
let bind = (r, f) =>
switch r {
| Ok(a) => f(a)
| Error(err) => Error(err)
}
let toExn = (msg: string, x: result<'a, 'b>): 'a => let toExn = (msg: string, x: result<'a, 'b>): 'a =>
switch x { switch x {
| Ok(r) => r | Ok(r) => r
@ -196,14 +261,17 @@ module R = {
let errorIfCondition = (errorCondition, errorMessage, r) => let errorIfCondition = (errorCondition, errorMessage, r) =>
errorCondition(r) ? Error(errorMessage) : Ok(r) errorCondition(r) ? Error(errorMessage) : Ok(r)
let ap = Rationale.Result.ap let ap = (r, a) =>
switch r {
| Ok(f) => Ok(f(a))
| Error(err) => Error(err)
}
let ap' = (r, a) => let ap' = (r, a) =>
switch r { switch r {
| Ok(f) => fmap(f, a) | Ok(f) => fmap(f, a)
| Error(err) => Error(err) | Error(err) => Error(err)
} }
// (a1 -> a2 -> r) -> m a1 -> m a2 -> m r // not in Rationale
let liftM2: (('a, 'b) => 'c, result<'a, 'd>, result<'b, 'd>) => result<'c, 'd> = (op, xR, yR) => { let liftM2: (('a, 'b) => 'c, result<'a, 'd>, result<'b, 'd>) => result<'c, 'd> = (op, xR, yR) => {
ap'(fmap(op, xR), yR) ap'(fmap(op, xR), yR)
} }
@ -253,7 +321,7 @@ module S = {
} }
module J = { module J = {
let toString = \"||>"(Js.Json.decodeString, O.default("")) let toString = F.pipe(Js.Json.decodeString, O.default(""))
let fromString = Js.Json.string let fromString = Js.Json.string
let fromNumber = Js.Json.number let fromNumber = Js.Json.number
@ -266,7 +334,7 @@ module J = {
let toString = (str: option<'a>) => let toString = (str: option<'a>) =>
switch str { switch str {
| Some(str) => Some(str |> \"||>"(Js.Json.decodeString, O.default(""))) | Some(str) => Some(str |> F.pipe(Js.Json.decodeString, O.default("")))
| _ => None | _ => None
} }
} }
@ -281,34 +349,132 @@ module JsDate = {
/* List */ /* List */
module L = { module L = {
module Util = {
let eq = (a, b) => a == b
}
let fmap = List.map let fmap = List.map
let get = Belt.List.get let get = Belt.List.get
let toArray = Array.of_list let toArray = Array.of_list
let fmapi = List.mapi let fmapi = List.mapi
let concat = List.concat let concat = List.concat
let drop = Rationale.RList.drop let concat' = (xs, ys) => List.append(ys, xs)
let remove = Rationale.RList.remove
let rec drop = (i, xs) =>
switch (i, xs) {
| (_, list{}) => list{}
| (i, _) if i <= 0 => xs
| (i, list{_, ...b}) => drop(i - 1, b)
}
let append = (a, xs) => List.append(xs, list{a})
let take = {
let rec loop = (i, xs, acc) =>
switch (i, xs) {
| (i, _) if i <= 0 => acc
| (_, list{}) => acc
| (i, list{a, ...b}) => loop(i - 1, b, append(a, acc))
}
(i, xs) => loop(i, xs, list{})
}
let takeLast = (i, xs) => List.rev(xs) |> take(i) |> List.rev
let splitAt = (i, xs) => (take(i, xs), takeLast(List.length(xs) - i, xs))
let remove = (i, n, xs) => {
let (a, b) = splitAt(i, xs)
\"@"(a, drop(n, b))
}
let find = List.find let find = List.find
let filter = List.filter let filter = List.filter
let for_all = List.for_all let for_all = List.for_all
let exists = List.exists let exists = List.exists
let sort = List.sort let sort = List.sort
let length = List.length let length = List.length
let filter_opt = Rationale.RList.filter_opt
let uniqBy = Rationale.RList.uniqBy let filter_opt = xs => {
let join = Rationale.RList.join let rec loop = (l, acc) =>
let head = Rationale.RList.head switch l {
let uniq = Rationale.RList.uniq | list{} => acc
| list{hd, ...tl} =>
switch hd {
| None => loop(tl, acc)
| Some(x) => loop(tl, list{x, ...acc})
}
}
List.rev(loop(xs, list{}))
}
let containsWith = f => List.exists(f)
let uniqWithBy = (eq, f, xs) =>
List.fold_left(
((acc, tacc), v) =>
containsWith(eq(f(v)), tacc) ? (acc, tacc) : (append(v, acc), append(f(v), tacc)),
(list{}, list{}),
xs,
) |> fst
let uniqBy = (f, xs) => uniqWithBy(Util.eq, f, xs)
let join = j => List.fold_left((acc, v) => String.length(acc) == 0 ? v : acc ++ (j ++ v), "")
let head = xs =>
switch List.hd(xs) {
| exception _ => None
| a => Some(a)
}
let uniq = xs => uniqBy(x => x, xs)
let flatten = List.flatten let flatten = List.flatten
let last = Rationale.RList.last let last = xs => xs |> List.rev |> head
let append = List.append let append = List.append
let getBy = Belt.List.getBy let getBy = Belt.List.getBy
let dropLast = Rationale.RList.dropLast let dropLast = (i, xs) => take(List.length(xs) - i, xs)
let contains = Rationale.RList.contains let containsWith = f => List.exists(f)
let without = Rationale.RList.without let contains = x => containsWith(Util.eq(x))
let update = Rationale.RList.update
let reject = pred => List.filter(x => !pred(x))
let tail = xs =>
switch List.tl(xs) {
| exception _ => None
| a => Some(a)
}
let init = xs => {
O.fmap(List.rev, xs |> List.rev |> tail)
}
let singleton = (x: 'a): list<'a> => list{x}
let adjust = (f, i, xs) => {
let (a, b) = splitAt(i + 1, xs)
switch a {
| _ if i < 0 => xs
| _ if i >= List.length(xs) => xs
| list{} => b
| list{a} => list{f(a), ...b}
| a =>
O.fmap(
concat'(b),
O.bind(init(a), x =>
O.fmap(F.flip(append, x), O.fmap(fmap(f), O.fmap(singleton, last(a))))
),
) |> O.default(xs)
}
}
let without = (exclude, xs) => reject(x => contains(x, exclude), xs)
let update = (x, i, xs) => adjust(F.always(x), i, xs)
let iter = List.iter let iter = List.iter
let findIndex = Rationale.RList.findIndex
let findIndex = {
let rec loop = (pred, xs, i) =>
switch xs {
| list{} => None
| list{a, ...b} => pred(a) ? Some(i) : loop(pred, b, i + 1)
}
(pred, xs) => loop(pred, xs, 0)
}
let headSafe = Belt.List.head let headSafe = Belt.List.head
let tailSafe = Belt.List.tail let tailSafe = Belt.List.tail
let headExn = Belt.List.headExn let headExn = Belt.List.headExn
@ -370,7 +536,7 @@ module A = {
Belt.Array.getUnsafe(a, index), Belt.Array.getUnsafe(a, index),
Belt.Array.getUnsafe(a, index + 1), Belt.Array.getUnsafe(a, index + 1),
)) ))
|> Rationale.Result.return |> (x => Ok(x))
} }
let tail = Belt.Array.sliceToEnd(_, 1) let tail = Belt.Array.sliceToEnd(_, 1)
@ -434,8 +600,8 @@ module A = {
module O = { module O = {
let concatSomes = (optionals: array<option<'a>>): array<'a> => let concatSomes = (optionals: array<option<'a>>): array<'a> =>
optionals optionals
|> Js.Array.filter(Rationale.Option.isSome) |> Js.Array.filter(O.isSome)
|> Js.Array.map(Rationale.Option.toExn("Warning: This should not have happened")) |> Js.Array.map(O.toExn("Warning: This should not have happened"))
let defaultEmpty = (o: option<array<'a>>): array<'a> => let defaultEmpty = (o: option<array<'a>>): array<'a> =>
switch o { switch o {
| Some(o) => o | Some(o) => o
@ -634,7 +800,7 @@ module A2 = {
module JsArray = { module JsArray = {
let concatSomes = (optionals: Js.Array.t<option<'a>>): Js.Array.t<'a> => let concatSomes = (optionals: Js.Array.t<option<'a>>): Js.Array.t<'a> =>
optionals optionals
|> Js.Array.filter(Rationale.Option.isSome) |> Js.Array.filter(O.isSome)
|> Js.Array.map(Rationale.Option.toExn("Warning: This should not have happened")) |> Js.Array.map(O.toExn("Warning: This should not have happened"))
let filter = Js.Array.filter let filter = Js.Array.filter
} }

View File

@ -13889,11 +13889,6 @@ range-parser@^1.2.1, range-parser@~1.2.1:
resolved "https://registry.yarnpkg.com/range-parser/-/range-parser-1.2.1.tgz#3cf37023d199e1c24d1a55b84800c2f3e6468031" resolved "https://registry.yarnpkg.com/range-parser/-/range-parser-1.2.1.tgz#3cf37023d199e1c24d1a55b84800c2f3e6468031"
integrity sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg== integrity sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==
rationale@0.2.0:
version "0.2.0"
resolved "https://registry.yarnpkg.com/rationale/-/rationale-0.2.0.tgz#555ed4f3cc7cd0245faeac041d3769f1857e4f3d"
integrity sha512-Pd8w5Inv1JhTfRyx03zs486CEAn6UKXvvOtxVRLsewngsBSffo3MQwUKYS75L/8vPt98wmf7iaZROx362/f7Bw==
raw-body@2.4.3: raw-body@2.4.3:
version "2.4.3" version "2.4.3"
resolved "https://registry.yarnpkg.com/raw-body/-/raw-body-2.4.3.tgz#8f80305d11c2a0a545c2d9d89d7a0286fcead43c" resolved "https://registry.yarnpkg.com/raw-body/-/raw-body-2.4.3.tgz#8f80305d11c2a0a545c2d9d89d7a0286fcead43c"