Hi,
I’ve been playing a bit with Mongoc
which is a thin layer on top of the MongoDB C library. MongoDB is leaning heavily into JSON, which makes for non-intuitive code (from the Mongoc docs):
create_indexes_cmd = Mongoc.BSON(
"createIndexes" => collection_name,
"indexes" => [ Mongoc.BSON("key" => Mongoc.BSON("group" => 1), "name" => "group_index") ]
)
Julia is an amazing language for making your own DSL. I’m wondering why no one implemented a JSON DSL? This seems quite easy.
It took me ~ 30 minutes to hack the following (I’ve never written a Julia macro before):
parse_expr(e) = e
function parse_expr(e::Expr)
if e.head == :braces
d = Dict()
for f in e.args
f isa Expr || error("not a valid JSON")
if f.head == :call
f.args[1] == :(:) || error("not a valid JSON")
f2 = f.args[2]
typeof(f2) ∈ (Symbol, String) || error("not a valid JSON")
v = parse_expr(f.args[3])
d[f2] = v
end
end
return d
elseif e.head == :vect
v = similar(e.args)
for i in eachindex(e.args)
a =
v[i] = parse_expr(e.args[i])
end
return v
end
end
macro json(e)
return parse_expr(e)
end
@json { a: [{"b": "c"}, 5, 2.0] }
# returns:
# Dict{Any, Any} with 1 entry:
# :a => Any[Dict{Any, Any}("b"=>"c"), 5, 2.0]
The Mongoc example from above then becomes:
j = @json {"createIndexes": "collname",
"indexes" : [ { "key": {"group": 1}, "name" : "group_index" } ] }
@show j
#j = Dict{Any, Any}("createIndexes" => "collname", "indexes" => Any[Dict{Any, Any}("key" => Dict{Any, Any}("group" => 1), "name" => "group_index")])