Skip to content

Commit

Permalink
feat(stdlib): Json value access utils (#2150)
Browse files Browse the repository at this point in the history
  • Loading branch information
alex-snezhko authored Nov 7, 2024
1 parent 1e5f921 commit 72cc978
Show file tree
Hide file tree
Showing 3 changed files with 863 additions and 0 deletions.
135 changes: 135 additions & 0 deletions compiler/test/stdlib/json.test.gr
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,7 @@ from "result" include Result
from "buffer" include Buffer
from "char" include Char
from "list" include List
from "option" include Option
use Json.*
module Validation {
// Valid
Expand Down Expand Up @@ -1099,3 +1100,137 @@ module ToString {
) ==
Ok(Ok(comprehensiveJsonObject))
}

module Lenses {
let num = JsonNumber(123)
let str = JsonString("abc")
let bool = JsonBoolean(true)
let arr = JsonArray([JsonNumber(1), JsonNumber(2), JsonNumber(3)])
let obj = JsonObject(
[
("num", num),
("string", str),
("bool", bool),
("array", arr),
("null", JsonNull),
],
)
let nestedObj = JsonObject([("object", JsonObject([("nested", obj)]))])
let simpleObj = JsonObject([("property", JsonNumber(10))])

use Json.Lenses.*

assert get(json, num) == Some(num)
assert set(json, JsonString("hi"), num) == Some(JsonString("hi"))
assert map(json, x => JsonArray([x, x]), num) == Some(JsonArray([num, num]))

assert get(number, num) == Some(123)
assert get(string, num) == None
assert set(string, "hi", num) == Some(JsonString("hi"))
assert map(number, x => x * 2, num) == Some(JsonNumber(246))

assert get(string, str) == Some("abc")
assert get(number, str) == None

assert get(boolean, bool) == Some(true)
assert get(number, bool) == None

assert get(array, arr) == Some([JsonNumber(1), JsonNumber(2), JsonNumber(3)])
assert get(number, arr) == None

assert get(objectProperties, obj) ==
Some(
[
("num", num),
("string", str),
("bool", bool),
("array", arr),
("null", JsonNull),
],
)
assert get(number, obj) == None

assert get(property("num"), obj) == Some(num)
assert get(property("string"), obj) == Some(str)
assert get(property("oops"), obj) == None
assert get(property("oops"), num) == None
assert set(property("bool"), JsonBoolean(false), obj) ==
Some(
JsonObject(
[
("num", num),
("string", str),
("bool", JsonBoolean(false)),
("array", arr),
("null", JsonNull),
],
),
)
assert set(property("new"), JsonString("newVal"), obj) ==
Some(
JsonObject(
[
("num", num),
("string", str),
("bool", bool),
("array", arr),
("null", JsonNull),
("new", JsonString("newVal")),
],
),
)
assert map(property("property"), x => JsonArray([x, x]), simpleObj) ==
Some(
JsonObject([("property", JsonArray([JsonNumber(10), JsonNumber(10)]))]),
)

assert get(property("num") ||> number, obj) == Some(123)
assert get(property("null") ||> number, obj) == None
assert set(property("object") ||> number, 3, nestedObj) ==
Some(JsonObject([("object", JsonNumber(3))]))
assert set(property("new") ||> number, 1, JsonObject([])) == None
assert map(property("property") ||> number, val => val * 2, simpleObj) ==
Some(JsonObject([("property", JsonNumber(20))]))
assert map(property("property") ||> string, val => val ++ val, simpleObj) ==
None

assert get(nullable(number), num) == Some(Some(123))
assert get(nullable(number), JsonNull) == Some(None)
assert get(nullable(number), str) == None
assert set(nullable(number), Some(3), str) == Some(JsonNumber(3))
assert get(property("num") ||> nullable(number), obj) == Some(Some(123))
assert get(property("null") ||> nullable(number), obj) == Some(None)
assert set(property("object") ||> nullable(number), Some(3), nestedObj) ==
Some(JsonObject([("object", JsonNumber(3))]))
assert set(property("object") ||> nullable(number), None, nestedObj) ==
Some(JsonObject([("object", JsonNull)]))
assert set(property("new") ||> nullable(number), Some(1), JsonObject([])) ==
None
assert map(
property("property") ||> nullable(number),
val => Option.map(val => val * 2, val),
simpleObj
) ==
Some(JsonObject([("property", JsonNumber(20))]))
assert map(property("property") ||> nullable(number), val => None, simpleObj) ==
Some(JsonObject([("property", JsonNull)]))

assert get(propertyPath(["object", "nested"]), nestedObj) == Some(obj)
assert get(propertyPath(["object", "nested"]), nestedObj) ==
get(property("object") ||> property("nested"), nestedObj)
assert get(propertyPath(["num"]), obj) == Some(num)
assert get(propertyPath([]), obj) == Some(obj)
assert get(propertyPath([]), num) == Some(num)
assert get(propertyPath(["oops"]), num) == None
assert get(propertyPath(["object", "nested", "oops"]), nestedObj) == None
assert map(
propertyPath(["object", "nested"]) ||> objectProperties,
props => List.take(1, props),
nestedObj
) ==
Some(
JsonObject(
[("object", JsonObject([("nested", JsonObject([("num", num)]))]))],
),
)
}
Loading

0 comments on commit 72cc978

Please sign in to comment.