diff options
Diffstat (limited to 'tests/stdlib/tjsonmacro.nim')
-rw-r--r-- | tests/stdlib/tjsonmacro.nim | 212 |
1 files changed, 152 insertions, 60 deletions
diff --git a/tests/stdlib/tjsonmacro.nim b/tests/stdlib/tjsonmacro.nim index 0521d558c..5a1b4b294 100644 --- a/tests/stdlib/tjsonmacro.nim +++ b/tests/stdlib/tjsonmacro.nim @@ -1,27 +1,45 @@ discard """ output: "" + matrix: "--mm:refc; --mm:orc" + targets: "c js" """ -import json, strutils, options, tables -when true: +import json, strutils, options, tables +import std/assertions + +# The definition of the `%` proc needs to be here, since the `% c` calls below +# can only find our custom `%` proc for `Pix` if defined in global scope. +type + Pix = tuple[x, y: uint8, ch: uint16] +proc `%`(p: Pix): JsonNode = + result = %* { "x" : % p.x, + "y" : % p.y, + "ch" : % p.ch } + +proc testJson() = # Tests inspired by own use case (with some additional tests). # This should succeed. type Point[T] = object x, y: T - ReplayEventKind* = enum + ReplayEventKind = enum FoodAppeared, FoodEaten, DirectionChanged - ReplayEvent* = object + ReplayEvent = object time*: float case kind*: ReplayEventKind of FoodAppeared, FoodEaten: foodPos*: Point[float] + case subKind*: bool + of true: + it: int + of false: + ot: float of DirectionChanged: playerPos*: float - Replay* = ref object + Replay = ref object events*: seq[ReplayEvent] test: int test2: string @@ -33,7 +51,9 @@ when true: ReplayEvent( time: 1.2345, kind: FoodEaten, - foodPos: Point[float](x: 5.0, y: 1.0) + foodPos: Point[float](x: 5.0, y: 1.0), + subKind: true, + it: 7 ) ], test: 18827361, @@ -90,7 +110,7 @@ when true: doAssert result.other == node["other"].getBiggestInt() # TODO: Test object variant with set in of branch. - # TODO: Should we support heterogenous arrays? + # TODO: Should we support heterogeneous arrays? # Tests that verify the error messages for invalid data. block: @@ -241,7 +261,7 @@ when true: colors: array[2, BirdColor] var red = BirdColor(name: "red", rgb: [1.0, 0.0, 0.0]) - var blue = Birdcolor(name: "blue", rgb: [0.0, 0.0, 1.0]) + var blue = BirdColor(name: "blue", rgb: [0.0, 0.0, 1.0]) var b = Bird(age: 3, height: 1.734, name: "bardo", colors: [red, blue]) let jnode = %b let data = jnode.to(Bird) @@ -277,24 +297,26 @@ when true: doAssert parsed.color == Red block: - type - Car = object - engine: tuple[name: string, capacity: float] - model: string + when not defined(js): + # disable on js because of #12492 + type + Car = object + engine: tuple[name: string, capacity: float] + model: string - let j = """ - {"engine": {"name": "V8", "capacity": 5.5}, "model": "Skyline"} - """ + let j = """ + {"engine": {"name": "V8", "capacity": 5.5}, "model": "Skyline"} + """ - var i = 0 - proc mulTest: JsonNode = - i.inc() - return parseJson(j) + var i = 0 + proc mulTest(): JsonNode = + inc i + return parseJson(j) - let parsed = mulTest().to(Car) - doAssert parsed.engine.name == "V8" + let parsed = mulTest().to(Car) + doAssert parsed.engine.name == "V8" - doAssert i == 1 + doAssert i == 1 block: # Option[T] support! @@ -471,8 +493,9 @@ when true: doAssert Table[string,int](t.dict)["a"] == 1 doAssert Table[string,int](t.dict)["b"] == 2 doAssert array[3, float](t.arr) == [1.0,2.0,7.0] + doAssert MyRef(t.person).name == "boney" - doAssert MyObj(t.distFruit).color == 11 + doAssert MyObj(t.distfruit).color == 11 doAssert t.dog.name == "honey" doAssert t.fruit.color == 10 doAssert seq[string](t.emails) == @["abc", "123"] @@ -517,42 +540,111 @@ when true: doAssert v.name == "smith" doAssert MyRef(w).name == "smith" -# TODO: when the issue with the limeted vm registers is solved, the -# exact same test as above should be evaluated at compile time as -# well, to ensure that the vm functionality won't diverge from the -# runtime functionality. Until then, the following test should do it. + block: + # bug #12015 + type + Cluster = object + works: tuple[x, y: uint8, ch: uint16] # working + fails: Pix # previously broken + + let data = (x: 123'u8, y: 53'u8, ch: 1231'u16) + let c = Cluster(works: data, fails: data) + let cFromJson = (% c).to(Cluster) + doAssert c == cFromJson + block: + # bug related to #12015 + type + PixInt = tuple[x, y, ch: int] + SomePix = Pix | PixInt + Cluster[T: SomePix] = seq[T] + ClusterObject[T: SomePix] = object + data: Cluster[T] + RecoEvent[T: SomePix] = object + cluster: seq[ClusterObject[T]] + + let data = @[(x: 123'u8, y: 53'u8, ch: 1231'u16)] + var c = RecoEvent[Pix](cluster: @[ClusterObject[Pix](data: data)]) + let cFromJson = (% c).to(RecoEvent[Pix]) + doAssert c == cFromJson + + + block: + # ref objects with cycles. + type + Misdirection = object + cycle: Cycle + + Cycle = ref object + foo: string + cycle: Misdirection + + let data = """ + {"cycle": null} + """ + + let dataParsed = parseJson(data) + let dataDeser = to(dataParsed, Misdirection) + + block: + # ref object from #12316 + type + Foo = ref Bar + Bar = object + + discard "null".parseJson.to Foo + + block: + # named array #12289 + type Vec = array[2, int] + let arr = "[1,2]".parseJson.to Vec + doAssert arr == [1,2] + + block: + # test error message in exception + + type + MyType = object + otherMember: string + member: MySubType + + MySubType = object + somethingElse: string + list: seq[MyData] + + MyData = object + value: int + + let jsonNode = parseJson(""" + { + "otherMember": "otherValue", + "member": { + "somethingElse": "something", + "list": [{"value": 1}, {"value": 2}, {}] + } + } + """) + + try: + let tmp = jsonNode.to(MyType) + doAssert false, "this should be unreachable" + except KeyError: + doAssert getCurrentExceptionMsg().contains ".member.list[2].value" + + block: + # Enum indexed array test + type Test = enum + one, two, three, four, five + let a = [ + one: 300, + two: 20, + three: 10, + four: 0, + five: -10 + ] + doAssert (%* a).to(a.typeof) == a + + +testJson() static: - var t = parseJson(""" - { - "name":"Bongo", - "email":"bongo@bingo.com", - "list": [11,7,15], - "year": 1975, - "dict": {"a": 1, "b": 2}, - "arr": [1.0, 2.0, 7.0], - "person": {"name": "boney"}, - "dog": {"name": "honey"}, - "fruit": {"color": 10}, - "distfruit": {"color": 11}, - "emails": ["abc", "123"] - } - """) - - doAssert t["name"].getStr == "Bongo" - doAssert t["email"].getStr == "bongo@bingo.com" - doAssert t["list"][0].getInt == 11 - doAssert t["list"][1].getInt == 7 - doAssert t["list"][2].getInt == 15 - doAssert t["year"].getInt == 1975 - doAssert t["dict"]["a"].getInt == 1 - doAssert t["dict"]["b"].getInt == 2 - doAssert t["arr"][0].getFloat == 1.0 - doAssert t["arr"][1].getFloat == 2.0 - doAssert t["arr"][2].getFloat == 7.0 - doAssert t["person"]["name"].getStr == "boney" - doAssert t["distfruit"]["color"].getInt == 11 - doAssert t["dog"]["name"].getStr == "honey" - doAssert t["fruit"]["color"].getInt == 10 - doAssert t["emails"][0].getStr == "abc" - doAssert t["emails"][1].getStr == "123" + testJson() |