-module(tagg). -compile([no_auto_import, nowarn_unused_vars, nowarn_unused_function, nowarn_nomatch]). -export([replace_text_vars/3, get_html_rec/3, get_html/3, default_component_func/3, render/3]). -spec get_default_tag_config() -> gleam@dict:dict(binary(), fun((tagg_config:tagg(), section:section(), cx:context()) -> {ok, list(section:section())} | {error, tagg_error:tagg_error()})). get_default_tag_config() -> maps:from_list( [{<<"component"/utf8>>, fun tags@component_tag:create_sections/3}, {<<"for"/utf8>>, fun tags@for_loop_component:create_sections/3}, {<<"include"/utf8>>, fun tags@include_tag:create_sections/3}, {<<"if"/utf8>>, fun tags@if_tag:create_sections/3}, {<<"ifn"/utf8>>, fun tags@ifn_tag:create_sections/3}] ). -spec get_var_name(binary()) -> {binary(), binary()}. get_var_name(S) -> grapheme_util:get_chars_matching_func( S, <<""/utf8>>, fun grapheme_util:is_alphanumeric_or_dash_or_underscore_or_period/1 ). -spec replace_text_vars(binary(), cx:context(), binary()) -> binary(). replace_text_vars(S, Context, Acc) -> case S of <<"@"/utf8, Rest/binary>> -> {Var_name, Rest1} = get_var_name(Rest), case gleam@string:is_empty(Var_name) of true -> replace_text_vars(Rest1, Context, <<"@"/utf8, Acc/binary>>); false -> case cx:get_string(Context, Var_name) of {ok, Value} -> replace_text_vars( Rest1, Context, <> ); {error, _} -> replace_text_vars( Rest1, Context, <<<>/binary, Var_name/binary>> ) end end; _ -> case gleam@string:pop_grapheme(S) of {ok, {Grapheme, Rest@1}} -> replace_text_vars( Rest@1, Context, <> ); {error, _} -> Acc end end. -spec get_html_rec(list(section:section()), tagg_config:tagg(), binary()) -> {ok, binary()} | {error, tagg_error:tagg_error()}. get_html_rec(Sections, Tagg, Acc) -> case gleam@list:first(Sections) of {ok, Doc_section} -> case Doc_section of {text, Value, _, Context} -> get_html_rec( gleam@list:drop(Sections, 1), Tagg, <>))/binary>> ); {tag, Name, _, _, _, Context@1} -> case gleam@dict:get(erlang:element(3, Tagg), Name) of {ok, Tag_fn} -> case Tag_fn(Tagg, Doc_section, Context@1) of {ok, New_sections} -> get_html_rec( gleam@list:fold( New_sections, gleam@list:drop(Sections, 1), fun gleam@list:prepend/2 ), Tagg, Acc ); {error, Err} -> {error, Err} end; {error, _} -> {error, tag_config_missing_error} end end; {error, _} -> {ok, Acc} end. -spec get_html(list(section:section()), cx:context(), tagg_config:tagg()) -> {ok, binary()} | {error, tagg_error:tagg_error()}. get_html(Children, Context, Tagg) -> case get_html_rec(gleam@list:map(Children, fun(Child) -> case Child of {text, Value, Start, _} -> {text, Value, Start, Context}; {tag, Name, Attrs, Children@1, Start@1, _} -> {tag, Name, Attrs, Children@1, Start@1, Context} end end), Tagg, <<""/utf8>>) of {ok, Html} -> {ok, Html}; {error, Err} -> {error, Err} end. -spec default_component_func( tagg_config:tagg(), section:section(), cx:context() ) -> {ok, list(section:section())} | {error, tagg_error:tagg_error()}. default_component_func(_, Doc_section, Context) -> case Doc_section of {text, Text, Start, _} -> {ok, [{text, Text, Start, Context}]}; {tag, _, _, Children, _, _} -> {ok, gleam@list:map(Children, fun(Child) -> case Child of {text, Value, Start@1, _} -> {text, Value, Start@1, Context}; {tag, Name, Attrs, Children@1, Start@2, _} -> {tag, Name, Attrs, Children@1, Start@2, Context} end end)} end. -spec render(tagg_config:tagg(), binary(), cx:context()) -> {ok, binary()} | {error, tagg_error:tagg_error()}. render(Tagg, Filepath, Context) -> case simplifile:read(filepath:join(erlang:element(2, Tagg), Filepath)) of {ok, Html_content} -> Tag_config = gleam@dict:merge( get_default_tag_config(), erlang:element(3, Tagg) ), case pre_section:get_raw_sections( Html_content, gleam@set:from_list(gleam@dict:keys(Tag_config)) ) of {ok, Raw_sections} -> _pipe = Raw_sections, _pipe@1 = section:get_sections(_pipe), get_html( _pipe@1, Context, erlang:setelement(3, Tagg, Tag_config) ); {error, Err} -> {error, Err} end; {error, Err@1} -> {error, {template_file_not_found_error, <<<<(simplifile:describe_error(Err@1))/binary, "; path: "/utf8>>/binary, Filepath/binary>>}} end.