Feature
* Operations now return lazy sources ([`6832b91`](https://github.com/rx-modules/bolt-expressions/commit/6832b9173d15ae6a88dd9d7d5b21929b459e41e6))
py
a = 5 + obj["s"] / 2
$2384k242hd495_2 bolt.expr.temp (generated name)
does not emit any command yet
print(a.is_lazy()) True
obj["$value"] = obj["$b"] * a
expanded on expression while it's lazy.
might produce repeated commands if "a" switches
to early evaluation later on.
a.evaluate()
triggers early evaluation of "a".
commands are inserted where "a" was originally evaluated.
print(a.is_lazy()) False
obj["$value2"] = a copies "a"
* Support dicts, lists, arrays and union types as data source types ([`1097f5f`](https://github.com/rx-modules/bolt-expressions/commit/1097f5fedf8a7211c5437deeeac50eadd256ae03))
py
class Item(TypedDict): from the typing module
id: str
Count: Byte from nbtlib
tag: dict[str, Any]
hotbar = storage.hotbar[list[Item]]
first_item = hotbar[0]
first_item.Count = obj["$count"]
execute store result storage ... hotbar[0].Count byte 1 run scoreboard players get ...
* Type checking ([`b031303`](https://github.com/rx-modules/bolt-expressions/commit/b0313037e4428dd5e41cc7c608931cf613c6701f))
py
first_item.id = 5
"Int" does not match "String"
hotbar.append({id: "stone"})
"{id: String}" is missing required key "Count" of type "Byte"
hotbar[0].merge({x:5})
"{x: Int}" has extra key "x" not present in "Item"
hotbar = [1, 2, 3]
Elements of "list[Int]" and "list[Item]" are not compatible
"Int" is not a compound type with fixed keys and is not compatible with "Item"
message = storage.msg[str | list[str]]
message = ["hello", "world"]
fine
message = "hello world"
fine
message = [{a: "b"}, {b: 5}]
"list[{a: String} | {b: Int}]" is not compatible with "String | list[String]"
* Numeric literal casting ([`9874ca9`](https://github.com/rx-modules/bolt-expressions/commit/9874ca91f2c7045ffc8fbf17b06505984f2870c2))
py
storage.pos[list[Double]] = [43, 0, 5]
[43.0d, 0.0d, 5.0d]
storage.item[Item] = {id: "glass", Count: 5, tag: {}}
{id: "glass", Count: 5b, tag: {}}
storage.flag[Byte] = 128
raises an exception because 128 can't be represented as Byte.
storage.number[Byte | Long] = 4 can't cast when write type is a union
"Int" is not compatible with "Byte | Long"
storage.number[Byte | None] = 4 only if it's optional
4b
* Separate data source interfaces for each nbt type ([`dbe9a74`](https://github.com/rx-modules/bolt-expressions/commit/dbe9a74f31f3c58fb1b34a5069edada983535ec9))
py
storage.msg[str] - 1
TypeError: unsupported operand type(s) for -: 'DataSource' and 'int'
storage.value[int].oops
TypeError: Data source of type 'Int' does not have named keys
storage.c[dict[str, Any]][0]
TypeError: Data source of type 'dict[String, typing.Any]' object is not indexable
storage.arr[list[int]]({a: 0})
TypeError: Data source of type 'list[Int]' does not support compound matching
Fix
* Only cast numeric nbt types ([`86d49b1`](https://github.com/rx-modules/bolt-expressions/commit/86d49b1b257996ded2c5becef223c9e6806b3c6a))