%%% sanhedrin.hrl — Record definitions for the Sanhedrin deliberation engine %%% %%% Architecture §3.2: Concurrent deliberation engine. %%% Spawns panels of independent deliberators, collects votes, %%% enforces mandatory dissent on capital decisions, %%% stores minority opinions. %% --- Case complexity levels --- %% simple -> 1 judge %% monetary -> 3 judges (dinei mamonot) %% capital -> 23 judges (dinei nefashot) %% novel -> 71 judges (Sanhedrin Gedolah) -type complexity() :: simple | monetary | capital | novel. %% --- Case outcome --- -type outcome() :: accepted | rejected | teiku. %% --- Unanimous check result --- -type unanimous_check() :: passed | {failed, suspicion_of_consensus}. %% --- Torah reference --- -record(torah_ref, { book :: atom(), %% bereishit | shemot | vayikra | bamidbar | devarim chapter :: pos_integer(), verse :: pos_integer() }). %% --- A root with domain --- -record(root_info, { shoresh :: list(atom()), %% e.g. [bet, resh, aleph] domain :: atom() %% e.g. creation, justice, holiness }). %% --- Case submission (Pipeline → Sanhedrin) --- %% Construction spec §3.2 %% %% The `context` field is a map. Documented keys fall into two groups: %% %% A. Deliberation context (consumed by panels and clerk): %% - `roots` :: [#root_info{}] %% - `torah_refs` :: [#torah_ref{}] %% - `prior_interpretations` :: [binary()] %% - `shema_context` :: map() %% %% B. Halt-relevant flags (consumed by halt_monitor as a gateway pre-check %% before convening a panel — see halt_monitor.erl): %% - `authority_source` :: atom() (e.g. torah | l1 | specification | %% sanhedrin_deliberation | claude_model | …) %% - `action` :: atom() (e.g. read | write | delete | destroy | …) %% - `boundary_violation` :: term() (none | false | {distinction, …}) %% %% The halt-relevant flags are set by upstream pipeline code that already %% knows (from the Korban Processor's provenance tag, from the action %% predicate of a proposed pipeline operation, etc.) what the case carries. %% halt_monitor reads them; it does not re-derive them. -record(sanhedrin_case, { case_ref :: binary(), %% UUID complexity :: complexity(), question :: binary(), context :: map(), %% see record commentary above requested_by :: binary(), submitted_at :: integer() %% erlang:system_time(millisecond) }). %% --- Individual judge vote --- -record(vote, { judge_id :: reference(), position :: binary(), %% The interpretation reasoning :: binary(), %% Why this position torah_refs :: [#torah_ref{}], %% Grounding references verdict :: accept | reject | abstain, cast_at :: integer() }). %% --- Panel record --- -record(panel, { panel_id :: binary(), case_ref :: binary(), size :: pos_integer(), %% 1, 3, 23, or 71 judges :: [pid()], votes :: [#vote{}], status :: convened | deliberating | decided | dissolved, convened_at :: integer(), decided_at :: integer() | undefined }). %% --- Deliberation decision --- %% Construction spec §3.2 — output format -record(decision, { case_ref :: binary(), outcome :: outcome(), majority :: map(), %% #{position, reasoning, torah_refs, vote_count} minority :: map(), %% #{position, reasoning, torah_refs, vote_count} panel_size :: pos_integer(), deliberation_time_ms :: non_neg_integer(), unanimous_check :: unanimous_check() }). %% --- Opinion record (stored by clerk, never deleted) --- -record(opinion, { case_ref :: binary(), judge_id :: reference(), position :: binary(), reasoning :: binary(), torah_refs :: [#torah_ref{}], verdict :: accept | reject | abstain, is_majority :: boolean(), stored_at :: integer() }). %% --- Panel size constants --- -define(PANEL_SIMPLE, 1). -define(PANEL_MONETARY, 3). -define(PANEL_CAPITAL, 23). -define(PANEL_NOVEL, 71). %% --- Deliberation timeouts (Construction spec §2.2) --- -define(TIMEOUT_SIMPLE, 15000). %% 15 seconds -define(TIMEOUT_MONETARY, 15000). %% 15 seconds -define(TIMEOUT_CAPITAL, 120000). %% 120 seconds -define(TIMEOUT_NOVEL, 600000). %% 600 seconds