-module(handles@engine). -compile([no_auto_import, nowarn_unused_vars, nowarn_unused_function, nowarn_nomatch]). -export([get_as_string/2, get_as_bool/2, get_as_list/2, run/2]). -export_type([runtime_error/0]). -type runtime_error() :: {unexpected_type_error, list(binary()), binary(), list(binary())} | {unknown_property_error, list(binary())}. -spec get_from_ctx(gleam@dynamic:dynamic_(), list(binary())) -> {ok, gleam@dynamic:dynamic_()} | {error, runtime_error()}. get_from_ctx(Root_ctx, Path) -> _pipe = Path, gleam@list:fold( _pipe, {ok, Root_ctx}, fun(Ctx, It) -> gleam@result:'try'(Ctx, fun(Ctx@1) -> _pipe@1 = Ctx@1, _pipe@2 = (gleam@dynamic:field( It, fun gleam@dynamic:dynamic/1 ))(_pipe@1), gleam@result:map_error( _pipe@2, fun(_) -> {unknown_property_error, Path} end ) end) end ). -spec get_as_string(gleam@dynamic:dynamic_(), list(binary())) -> {ok, binary()} | {error, runtime_error()}. get_as_string(Root_ctx, Path) -> _pipe = get_from_ctx(Root_ctx, Path), gleam@result:'try'( _pipe, fun(Value) -> case gleam@dynamic:classify(Value) of <<"String"/utf8>> -> _pipe@1 = Value, _pipe@2 = gleam@dynamic:string(_pipe@1), gleam@result:map_error( _pipe@2, fun(Err) -> gleam@io:debug(Err), erlang:error(#{gleam_error => panic, message => <<"TypeConvertionError"/utf8>>, module => <<"handles/engine"/utf8>>, function => <<"get_as_string"/utf8>>, line => 41}) end ); <<"Int"/utf8>> -> _pipe@3 = Value, _pipe@4 = gleam@dynamic:int(_pipe@3), _pipe@5 = gleam@result:map( _pipe@4, fun gleam@int:to_string/1 ), gleam@result:map_error( _pipe@5, fun(Err@1) -> gleam@io:debug(Err@1), erlang:error(#{gleam_error => panic, message => <<"TypeConvertionError"/utf8>>, module => <<"handles/engine"/utf8>>, function => <<"get_as_string"/utf8>>, line => 50}) end ); <<"Float"/utf8>> -> _pipe@6 = Value, _pipe@7 = gleam@dynamic:float(_pipe@6), _pipe@8 = gleam@result:map( _pipe@7, fun gleam@float:to_string/1 ), gleam@result:map_error( _pipe@8, fun(Err@2) -> gleam@io:debug(Err@2), erlang:error(#{gleam_error => panic, message => <<"TypeConvertionError"/utf8>>, module => <<"handles/engine"/utf8>>, function => <<"get_as_string"/utf8>>, line => 59}) end ); Typ -> {error, {unexpected_type_error, Path, Typ, [<<"String"/utf8>>, <<"Int"/utf8>>, <<"Float"/utf8>>]}} end end ). -spec get_as_bool(gleam@dynamic:dynamic_(), list(binary())) -> {ok, boolean()} | {error, runtime_error()}. get_as_bool(Root_ctx, Path) -> _pipe = get_from_ctx(Root_ctx, Path), gleam@result:'try'( _pipe, fun(Value) -> case gleam@dynamic:classify(Value) of <<"Bool"/utf8>> -> _pipe@1 = Value, _pipe@2 = gleam@dynamic:bool(_pipe@1), gleam@result:map_error( _pipe@2, fun(Err) -> gleam@io:debug(Err), erlang:error(#{gleam_error => panic, message => <<"TypeConvertionError"/utf8>>, module => <<"handles/engine"/utf8>>, function => <<"get_as_bool"/utf8>>, line => 79}) end ); Typ -> {error, {unexpected_type_error, Path, Typ, [<<"Bool"/utf8>>]}} end end ). -spec get_as_list(gleam@dynamic:dynamic_(), list(binary())) -> {ok, list(gleam@dynamic:dynamic_())} | {error, runtime_error()}. get_as_list(Root_ctx, Path) -> _pipe = get_from_ctx(Root_ctx, Path), gleam@result:'try'( _pipe, fun(Value) -> case gleam@dynamic:classify(Value) of <<"List"/utf8>> -> _pipe@1 = Value, _pipe@2 = gleam@dynamic:shallow_list(_pipe@1), gleam@result:map_error( _pipe@2, fun(Err) -> gleam@io:debug(Err), erlang:error(#{gleam_error => panic, message => <<"TypeConvertionError"/utf8>>, module => <<"handles/engine"/utf8>>, function => <<"get_as_list"/utf8>>, line => 99}) end ); Typ -> {error, {unexpected_type_error, Path, Typ, [<<"List"/utf8>>]}} end end ). -spec run(list(handles@parser:ast()), gleam@dynamic:dynamic_()) -> {ok, binary()} | {error, runtime_error()}. run(Ast, Ctx) -> _pipe@8 = (gleam@list:fold( Ast, {ok, gleam@string_builder:new()}, fun(Acc, It) -> gleam@result:'try'(Acc, fun(Acc@1) -> case It of {constant, Value} -> {ok, gleam@string_builder:append(Acc@1, Value)}; {property, Path} -> _pipe = get_as_string(Ctx, Path), gleam@result:map( _pipe, fun(_capture) -> gleam@string_builder:append(Acc@1, _capture) end ); {block, Kind, Path@1, Children} -> case Kind of <<"if"/utf8>> -> _pipe@1 = get_as_bool(Ctx, Path@1), _pipe@2 = gleam@result:'try'( _pipe@1, fun(_capture@1) -> eval_if(_capture@1, Children, Ctx) end ), gleam@result:map( _pipe@2, fun(_capture@2) -> gleam@string_builder:append( Acc@1, _capture@2 ) end ); <<"unless"/utf8>> -> _pipe@3 = get_as_bool(Ctx, Path@1), _pipe@4 = gleam@result:map( _pipe@3, fun gleam@bool:negate/1 ), _pipe@5 = gleam@result:'try'( _pipe@4, fun(_capture@3) -> eval_if(_capture@3, Children, Ctx) end ), gleam@result:map( _pipe@5, fun(_capture@4) -> gleam@string_builder:append( Acc@1, _capture@4 ) end ); <<"each"/utf8>> -> _pipe@6 = get_as_list(Ctx, Path@1), _pipe@7 = gleam@result:'try'( _pipe@6, fun(_capture@5) -> eval_each(_capture@5, Children) end ), gleam@result:map( _pipe@7, fun(_capture@6) -> gleam@string_builder:append( Acc@1, _capture@6 ) end ); _ -> erlang:error(#{gleam_error => panic, message => <<"Unknown block"/utf8>>, module => <<"handles/engine"/utf8>>, function => <<"run"/utf8>>, line => 161}) end end end) end )), gleam@result:map(_pipe@8, fun gleam@string_builder:to_string/1). -spec eval_if(boolean(), list(handles@parser:ast()), gleam@dynamic:dynamic_()) -> {ok, binary()} | {error, runtime_error()}. eval_if(Condition, Children, Ctx) -> case Condition of false -> {ok, <<""/utf8>>}; true -> run(Children, Ctx) end. -spec eval_each(list(gleam@dynamic:dynamic_()), list(handles@parser:ast())) -> {ok, binary()} | {error, runtime_error()}. eval_each(Ctx_list, Children) -> _pipe@1 = (gleam@list:fold( Ctx_list, {ok, gleam@string_builder:new()}, fun(Acc, Ctx) -> gleam@result:'try'(Acc, fun(Acc@1) -> _pipe = run(Children, Ctx), gleam@result:map( _pipe, fun(_capture) -> gleam@string_builder:append(Acc@1, _capture) end ) end) end )), gleam@result:map(_pipe@1, fun gleam@string_builder:to_string/1).