-module(galchemy@session@runtime). -compile([no_auto_import, nowarn_unused_vars, nowarn_unused_function, nowarn_nomatch, inline]). -define(FILEPATH, "src\\galchemy\\session\\runtime.gleam"). -export([new/1, rollback/1, tracked_entities/1, get/3, pending_changes/1, flush/2, commit/2, track/2, stage_with_hooks/3, stage/2, attach_with_hooks/3, attach/2, detach/2, refresh_with_hooks/3, refresh/2]). -export_type([session/0, track_error/0, hook_track_error/1, session_execution_error/1]). -type session() :: {session, galchemy@schema@model:schema_snapshot(), galchemy@session@unit_of_work:session(), galchemy@orm@identity_map:identity_map(), galchemy@orm@identity_map:identity_map()}. -type track_error() :: {entity_error, galchemy@orm@entity:entity_error()} | {identity_map_error, galchemy@orm@identity_map:identity_map_error()} | {unknown_tracked_entity, galchemy@schema@relation:table_ref(), galchemy@session@unit_of_work:identity()}. -type hook_track_error(KRS) :: {track_failure, track_error()} | {hook_failure, KRS}. -type session_execution_error(KRT) :: {track_error, track_error()} | {execution_error, galchemy@session@execution:execution_error(KRT)}. -file("src\\galchemy\\session\\runtime.gleam", 36). -spec new(galchemy@schema@model:schema_snapshot()) -> session(). new(Snapshot) -> {session, Snapshot, galchemy@session@unit_of_work:new(Snapshot), galchemy@orm@identity_map:empty(), galchemy@orm@identity_map:empty()}. -file("src\\galchemy\\session\\runtime.gleam", 240). -spec rollback(session()) -> session(). rollback(Session) -> {session, erlang:element(2, Session), galchemy@session@unit_of_work:new(erlang:element(2, Session)), erlang:element(5, Session), erlang:element(5, Session)}. -file("src\\galchemy\\session\\runtime.gleam", 248). -spec tracked_entities(session()) -> list(galchemy@orm@entity:entity()). tracked_entities(Session) -> galchemy@orm@identity_map:values(erlang:element(4, Session)). -file("src\\galchemy\\session\\runtime.gleam", 252). -spec get( session(), galchemy@schema@relation:table_ref(), galchemy@session@unit_of_work:identity() ) -> gleam@option:option(galchemy@orm@entity:entity()). get(Session, Table, Identity) -> galchemy@orm@identity_map:get(erlang:element(4, Session), Table, Identity). -file("src\\galchemy\\session\\runtime.gleam", 260). -spec pending_changes(session()) -> galchemy@session@unit_of_work:session(). pending_changes(Session) -> erlang:element(3, Session). -file("src\\galchemy\\session\\runtime.gleam", 293). -spec map_track_error({ok, KTN} | {error, track_error()}) -> {ok, KTN} | {error, hook_track_error(any())}. map_track_error(Value) -> case Value of {ok, Inner} -> {ok, Inner}; {error, Error} -> {error, {track_failure, Error}} end. -file("src\\galchemy\\session\\runtime.gleam", 302). -spec map_hook_error({ok, galchemy@orm@entity:entity()} | {error, KTU}) -> {ok, galchemy@orm@entity:entity()} | {error, hook_track_error(KTU)}. map_hook_error(Value) -> case Value of {ok, Inner} -> {ok, Inner}; {error, Error} -> {error, {hook_failure, Error}} end. -file("src\\galchemy\\session\\runtime.gleam", 317). -spec normalize_entities( list(galchemy@orm@entity:entity()), galchemy@orm@identity_map:identity_map() ) -> galchemy@orm@identity_map:identity_map(). normalize_entities(Entities, Acc) -> case Entities of [] -> Acc; [Next_entity | Rest] -> Next_map = case galchemy@orm@entity:status(Next_entity) of deleted -> Acc; _ -> Updated_map@1 = case galchemy@orm@identity_map:upsert( Acc, galchemy@orm@entity:mark_clean(Next_entity) ) of {ok, Updated_map} -> Updated_map; _assert_fail -> erlang:error(#{gleam_error => let_assert, message => <<"Pattern match failed, no pattern matched the value."/utf8>>, file => <>, module => <<"galchemy/session/runtime"/utf8>>, function => <<"normalize_entities"/utf8>>, line => 327, value => _assert_fail, start => 8368, 'end' => 8465, pattern_start => 8379, pattern_end => 8394}) end, Updated_map@1 end, normalize_entities(Rest, Next_map) end. -file("src\\galchemy\\session\\runtime.gleam", 311). -spec normalize_tracked(galchemy@orm@identity_map:identity_map()) -> galchemy@orm@identity_map:identity_map(). normalize_tracked(Tracked) -> normalize_entities( galchemy@orm@identity_map:values(Tracked), galchemy@orm@identity_map:empty() ). -file("src\\galchemy\\session\\runtime.gleam", 205). -spec flush( session(), fun((galchemy@ast@query:'query'()) -> {ok, KST} | {error, KSU}) ) -> {ok, {galchemy@session@execution:flush_execution(KST), session()}} | {error, session_execution_error(KSU)}. flush(Session, Executor) -> case galchemy@session@execution:execute( erlang:element(3, Session), Executor ) of {error, Error} -> {error, {execution_error, Error}}; {ok, {Flush_result, Cleared_pending}} -> Normalized = normalize_tracked(erlang:element(4, Session)), {ok, {Flush_result, {session, erlang:element(2, Session), Cleared_pending, Normalized, Normalized}}} end. -file("src\\galchemy\\session\\runtime.gleam", 230). -spec commit( session(), fun((galchemy@ast@query:'query'()) -> {ok, KTB} | {error, KTC}) ) -> {ok, {galchemy@session@execution:flush_execution(KTB), session()}} | {error, session_execution_error(KTC)}. commit(Session, Executor) -> flush(Session, Executor). -file("src\\galchemy\\session\\runtime.gleam", 338). -spec map_entity_error({ok, KUB} | {error, galchemy@orm@entity:entity_error()}) -> {ok, KUB} | {error, track_error()}. map_entity_error(Value) -> case Value of {ok, Inner} -> {ok, Inner}; {error, Error} -> {error, {entity_error, Error}} end. -file("src\\galchemy\\session\\runtime.gleam", 347). -spec map_identity_error( {ok, KUG} | {error, galchemy@orm@identity_map:identity_map_error()} ) -> {ok, KUG} | {error, track_error()}. map_identity_error(Value) -> case Value of {ok, Inner} -> {ok, Inner}; {error, Error} -> {error, {identity_map_error, Error}} end. -file("src\\galchemy\\session\\runtime.gleam", 264). -spec stage_persisted( galchemy@orm@identity_map:identity_map(), galchemy@orm@entity:entity() ) -> {ok, galchemy@orm@identity_map:identity_map()} | {error, track_error()}. stage_persisted(Persisted, Next_entity) -> case galchemy@orm@entity:status(Next_entity) of new -> {ok, Persisted}; clean -> _pipe = galchemy@orm@identity_map:upsert( Persisted, galchemy@orm@entity:mark_clean(Next_entity) ), map_identity_error(_pipe); {dirty, _} -> case galchemy@orm@entity:identity(Next_entity) of {error, Error} -> {error, {entity_error, Error}}; {ok, Next_identity} -> case galchemy@orm@identity_map:get( Persisted, erlang:element(2, erlang:element(2, Next_entity)), Next_identity ) of {some, _} -> {ok, Persisted}; none -> _pipe@1 = galchemy@orm@identity_map:upsert( Persisted, galchemy@orm@entity:mark_clean(Next_entity) ), map_identity_error(_pipe@1) end end; deleted -> case galchemy@orm@entity:identity(Next_entity) of {error, Error} -> {error, {entity_error, Error}}; {ok, Next_identity} -> case galchemy@orm@identity_map:get( Persisted, erlang:element(2, erlang:element(2, Next_entity)), Next_identity ) of {some, _} -> {ok, Persisted}; none -> _pipe@1 = galchemy@orm@identity_map:upsert( Persisted, galchemy@orm@entity:mark_clean(Next_entity) ), map_identity_error(_pipe@1) end end end. -file("src\\galchemy\\session\\runtime.gleam", 356). -spec result_try( {ok, KUL} | {error, KUM}, fun((KUL) -> {ok, KUP} | {error, KUM}) ) -> {ok, KUP} | {error, KUM}. result_try(Value, Next) -> case Value of {ok, Inner} -> Next(Inner); {error, Error} -> {error, Error} end. -file("src\\galchemy\\session\\runtime.gleam", 45). -spec track(session(), galchemy@orm@entity:entity()) -> {ok, session()} | {error, track_error()}. track(Session, Next_entity) -> Clean_entity = galchemy@orm@entity:mark_clean(Next_entity), result_try( begin _pipe = galchemy@orm@identity_map:upsert( erlang:element(4, Session), Clean_entity ), map_identity_error(_pipe) end, fun(Tracked) -> result_try( begin _pipe@1 = galchemy@orm@identity_map:upsert( erlang:element(5, Session), Clean_entity ), map_identity_error(_pipe@1) end, fun(Persisted) -> {ok, {session, erlang:element(2, Session), erlang:element(3, Session), Tracked, Persisted}} end ) end ). -file("src\\galchemy\\session\\runtime.gleam", 74). -spec stage_with_hooks( session(), galchemy@orm@entity:entity(), galchemy@orm@hook:entity_hooks(KRY) ) -> {ok, session()} | {error, hook_track_error(KRY)}. stage_with_hooks(Session, Next_entity, Hooks) -> result_try( begin _pipe = galchemy@orm@hook:before_stage(Hooks, Next_entity), map_hook_error(_pipe) end, fun(Hooked_entity) -> result_try( begin _pipe@1 = galchemy@orm@entity:stage( erlang:element(3, Session), Hooked_entity ), _pipe@2 = map_entity_error(_pipe@1), map_track_error(_pipe@2) end, fun(Pending) -> result_try( begin _pipe@3 = galchemy@orm@identity_map:upsert( erlang:element(4, Session), Hooked_entity ), _pipe@4 = map_identity_error(_pipe@3), map_track_error(_pipe@4) end, fun(Tracked) -> result_try( begin _pipe@5 = stage_persisted( erlang:element(5, Session), Hooked_entity ), map_track_error(_pipe@5) end, fun(Persisted) -> {ok, {session, erlang:element(2, Session), Pending, Tracked, Persisted}} end ) end ) end ) end ). -file("src\\galchemy\\session\\runtime.gleam", 63). -spec stage(session(), galchemy@orm@entity:entity()) -> {ok, session()} | {error, track_error()}. stage(Session, Next_entity) -> case stage_with_hooks(Session, Next_entity, galchemy@orm@hook:none()) of {ok, Value} -> {ok, Value}; {error, {track_failure, Error}} -> {error, Error}; {error, {hook_failure, _}} -> erlang:error(#{gleam_error => panic, message => <<"unreachable hook error for hook.none()"/utf8>>, file => <>, module => <<"galchemy/session/runtime"/utf8>>, function => <<"stage"/utf8>>, line => 70}) end. -file("src\\galchemy\\session\\runtime.gleam", 114). -spec attach_with_hooks( session(), galchemy@orm@entity:entity(), galchemy@orm@hook:entity_hooks(KSF) ) -> {ok, session()} | {error, hook_track_error(KSF)}. attach_with_hooks(Session, Next_entity, Hooks) -> result_try( begin _pipe = galchemy@orm@hook:after_attach(Hooks, Next_entity), map_hook_error(_pipe) end, fun(Hooked_entity) -> _pipe@1 = track(Session, Hooked_entity), map_track_error(_pipe@1) end ). -file("src\\galchemy\\session\\runtime.gleam", 103). -spec attach(session(), galchemy@orm@entity:entity()) -> {ok, session()} | {error, track_error()}. attach(Session, Next_entity) -> case attach_with_hooks(Session, Next_entity, galchemy@orm@hook:none()) of {ok, Value} -> {ok, Value}; {error, {track_failure, Error}} -> {error, Error}; {error, {hook_failure, _}} -> erlang:error(#{gleam_error => panic, message => <<"unreachable hook error for hook.none()"/utf8>>, file => <>, module => <<"galchemy/session/runtime"/utf8>>, function => <<"attach"/utf8>>, line => 110}) end. -file("src\\galchemy\\session\\runtime.gleam", 128). -spec detach(session(), galchemy@orm@entity:entity()) -> {ok, session()} | {error, track_error()}. detach(Session, Next_entity) -> result_try( begin _pipe = galchemy@orm@entity:identity(Next_entity), map_entity_error(_pipe) end, fun(Next_identity) -> Table = erlang:element(2, erlang:element(2, Next_entity)), {ok, {session, erlang:element(2, Session), galchemy@session@unit_of_work:discard_entity_changes( erlang:element(3, Session), Table, Next_identity, erlang:element(3, Next_entity) ), galchemy@orm@identity_map:remove( erlang:element(4, Session), Table, Next_identity ), galchemy@orm@identity_map:remove( erlang:element(5, Session), Table, Next_identity )}} end ). -file("src\\galchemy\\session\\runtime.gleam", 363). -spec unwrap_identity_map( {ok, galchemy@orm@identity_map:identity_map()} | {error, galchemy@orm@identity_map:identity_map_error()} ) -> galchemy@orm@identity_map:identity_map(). unwrap_identity_map(Value) -> Map@1 = case Value of {ok, Map} -> Map; _assert_fail -> erlang:error(#{gleam_error => let_assert, message => <<"Pattern match failed, no pattern matched the value."/utf8>>, file => <>, module => <<"galchemy/session/runtime"/utf8>>, function => <<"unwrap_identity_map"/utf8>>, line => 366, value => _assert_fail, start => 9247, 'end' => 9273, pattern_start => 9258, pattern_end => 9265}) end, Map@1. -file("src\\galchemy\\session\\runtime.gleam", 164). -spec refresh_with_hooks( session(), galchemy@orm@entity:entity(), galchemy@orm@hook:entity_hooks(KSO) ) -> {ok, session()} | {error, hook_track_error(KSO)}. refresh_with_hooks(Session, Next_entity, Hooks) -> result_try( begin _pipe = galchemy@orm@entity:identity(Next_entity), _pipe@1 = map_entity_error(_pipe), map_track_error(_pipe@1) end, fun(Next_identity) -> Table = erlang:element(2, erlang:element(2, Next_entity)), case galchemy@orm@identity_map:get( erlang:element(5, Session), Table, Next_identity ) of none -> {error, {track_failure, {unknown_tracked_entity, Table, Next_identity}}}; {some, Persisted_entity} -> result_try( begin _pipe@2 = galchemy@orm@hook:after_refresh( Hooks, Persisted_entity ), map_hook_error(_pipe@2) end, fun(Refreshed_entity) -> {ok, {session, erlang:element(2, Session), galchemy@session@unit_of_work:discard_entity_changes( erlang:element(3, Session), Table, Next_identity, erlang:element(3, Next_entity) ), begin _pipe@3 = galchemy@orm@identity_map:upsert( galchemy@orm@identity_map:remove( erlang:element(4, Session), Table, Next_identity ), Refreshed_entity ), unwrap_identity_map(_pipe@3) end, erlang:element(5, Session)}} end ) end end ). -file("src\\galchemy\\session\\runtime.gleam", 153). -spec refresh(session(), galchemy@orm@entity:entity()) -> {ok, session()} | {error, track_error()}. refresh(Session, Next_entity) -> case refresh_with_hooks(Session, Next_entity, galchemy@orm@hook:none()) of {ok, Value} -> {ok, Value}; {error, {track_failure, Error}} -> {error, Error}; {error, {hook_failure, _}} -> erlang:error(#{gleam_error => panic, message => <<"unreachable hook error for hook.none()"/utf8>>, file => <>, module => <<"galchemy/session/runtime"/utf8>>, function => <<"refresh"/utf8>>, line => 160}) end.