@asterite For sure. Let me create an example:
Okay got something: https://play.crystal-lang.org/#/r/6k6c
Please read my comments, starting at line 28, then comment line 17
, and use line 18
. Then run. You will see more errors and not only that, but it breaks code.
A much better solution would be something like this:
https://play.crystal-lang.org/#/r/6k6g
require "json"
struct Level
JSON.map_keys({
amount: Int32,
mob_id: Int32,
name: String,
position: String,
size: String,
type: String
})
end
Levels = Hash(String, Level).new
Levels["testarea"] = Level.from_json(%({"entities":[{"amount":5,"mob_id":"Null","name":"crate_pack","position":"1053.91,861.24","size":"144.18,45.52","type":null},{"amount":5,"mob_id":"Null","name":"crate_pack2","position":"681.33,916.61","size":"144.18,45.52","type":null},{"amount":5,"mob_id":"9","name":"mob_pack","position":"1352.06,971.27","size":"190.91,90.42","type":"normal"}]}))
Levels["testarea"].entities.each do |entity|
amount = entity["amount"] # we don't need to do .to_i on this, it's statically typed as an Int32
# And, if ANY key is shown up in this dynamic JSON data, ANYWHERE (outside of the entities array), it will be
# statically typed. This way, no matter the dynamic JSON structure, static typing is ensured.
amount.times do |x|
puts x
end
end
Obviously we need to include entities
somewhere in the map_keys
macro, so the compiler knows it’s an array. But you get the idea
In the example above, the map_keys
macro could work with JSON.parse, doesn’t have to be bound within a Struct
The developer shouldn’t have to worry about the JSON structure, they should just explicitly write the keys and their types, and that’s it. That’s all I’m trying to convey