Persists agent conversations to disk as JSON files.
Each session is saved as {session_id}.json in the sessions directory
(~/.config/minga/agent/sessions/ by default). Files are written
atomically via a temp file + rename to avoid corruption on crash.
Manager-owned remote identity is stored separately under .remote_tokens/.
The store is stateless: all functions operate directly on the filesystem.
The Session GenServer calls save/2 on a debounced timer, and the
picker calls list/0 to scan the directory for past sessions.
Summary
Types
Full session data for save/load.
Session metadata for the picker (without full message content).
Functions
Deletes all saved session transcripts. Durable remote identities are retained.
Deletes a saved session transcript. Durable remote identity is retained.
Establishes manager-owned remote session identity.
Lists all saved sessions as metadata (without full messages).
Loads a persisted session transcript.
Prunes session transcripts older than days days.
Saves a session to disk.
Returns the sessions directory path.
Types
@type session_data() :: %{ :id => String.t(), :timestamp => String.t(), :model_name => String.t(), :messages => [MingaAgent.Message.t()], :usage => MingaAgent.TurnUsage.t(), optional(:last_message_at) => String.t(), optional(:title) => String.t(), optional(:provider_name) => String.t(), optional(:branches) => [MingaAgent.Branch.t()], optional(:message_ids) => [pos_integer()], optional(:pinned_ids) => MapSet.t(pos_integer()), optional(:memory) => String.t() | nil }
Full session data for save/load.
@type session_meta() :: %{ id: String.t(), timestamp: String.t(), last_message_at: String.t(), title: String.t(), model_name: String.t(), provider_name: String.t(), preview: String.t(), recent_messages: String.t(), message_count: non_neg_integer(), turn_count: non_neg_integer(), cost: float() }
Session metadata for the picker (without full message content).
Functions
@spec clear_all(String.t() | nil) :: :ok
Deletes all saved session transcripts. Durable remote identities are retained.
Deletes a saved session transcript. Durable remote identity is retained.
@spec establish_remote_token(String.t(), String.t(), String.t() | nil) :: {:ok, String.t()} | {:error, term()}
Establishes manager-owned remote session identity.
Existing canonical identity wins over legacy transcript identity and the candidate. A new identity is persisted before it is returned.
@spec list(String.t() | nil) :: [session_meta()]
Lists all saved sessions as metadata (without full messages).
Returns sessions sorted by last message timestamp, most recent first.
@spec load(String.t(), String.t() | nil) :: {:ok, session_data()} | {:error, term()}
Loads a persisted session transcript.
Returns {:ok, session_data} or {:error, reason}.
@spec prune(non_neg_integer(), String.t() | nil) :: non_neg_integer()
Prunes session transcripts older than days days.
Returns the number of transcripts deleted. Durable remote identities are retained.
@spec save(session_data(), String.t() | nil) :: :ok | {:error, term()}
Saves a session to disk.
Creates the sessions directory if it doesn't exist. Writes atomically via a temp file to avoid corruption.
Returns the sessions directory path.