Repository navigation
Description
Follow-up to #2312 (first deliverable of #1730). Chat reads a Letta Code pane's transcript only when Ovis can tie the pane to one conversation, and otherwise shows the terminal's text. The tie is still circumstantial: three known edge cases can make Chat show a conversation the pane is no longer on. The owner chose to merge #2312 as is and test it himself.
Root cause
No fact Ovis can read says which conversation a running letta process is on now:
- herdr 0.9.5 keeps the first session report of a letta process. Its Letta integration (
herdr integration install letta) reports the conversation from Letta'sSessionStarthook. After/newor/resume, herdr still names the conversation the pane left: a laterpane report-agent-sessionwith a higher--seq, even one sent from inside the pane, was ignored on a real run. herdr's own docs say an integration should "report it again whenever your agent switches sessions". - Letta Code 0.34.27 records its conversation per folder, not per process. It writes
.letta/settings.local.json(sessionsByServer) in its current folder on start and on every switch. It skips the write when the conversation is unchanged, and it carries on after a failed write. It keeps no file open and no lock that names its conversation.
So #2312 binds only from circumstantial facts:
- herdr's first report;
- a project record older than the letta process;
- the process still being in the folder it started in, judged by the
PWDits environment keeps; - no other letta pane in that folder;
- the local store naming the agent.
Known wrong-conversation cases (in #2312's PR body)
- Stale
PWD. A letta started withenv -C <dir>(or by any parent that changes the child's folder without updatingPWD) has aPWDnaming another folder. If it later moves into exactly that folder (SetWorkingDirectory, EnterWorktree) after/new, and that folder's older record names the conversation herdr still reports, Chat shows that old conversation. - An excursion Ovis did not see. A letta leaves its start folder (SetWorkingDirectory), runs
/newthere (recording the new conversation in the other folder's record), and comes back before Ovis looks at the pane again. Its start folder's older record and herdr's stale report still agree on the old conversation, so Chat shows it. - "Seen elsewhere" is forgotten on restart. The memory of letta processes seen outside their start folder lives only in the Ovis server process, so a server restart loses it. Combined with case 2, a process that moved and came back binds again.
Each needs a folder move by Letta's own tools plus a conversation switch Ovis cannot see.
Real fix
Bind from a fact Letta or herdr reports about the running process, not from shared per-folder state:
- herdr: accept a later
herdr:lettasession report from the same process. Letta's hook already fires on everySessionStart, including after/newand/resume. Then the herdr report alone names the current conversation, and the record/folder cross-checks can go. - or Letta: a per-process record of the open conversation (for example a session lock naming the pid, as Muse writes).
Until one of those exists, the three cases above stay documented limits. Refs #1730, #2312.
Activity
devswha commentedon Oct 29, 2026
Also from CodeRabbit on #2312 (server/letta-store.ts, lettaInStartFolder): the 'seen elsewhere' memory is keyed on processStartLowerBound, which can shift between lookups after a backward wall-clock step on Linux; key it on processStartedAt (the stable process identity) instead.
devswha commentedon Oct 29, 2026
Upstream: herdr's Letta support landed in herdrdev/herdr#3107 (merged 2026-09-13; detection, restore and the opt-in
herdr integration install lettasession hook). In that thread Letta users report this root cause: after/new, Letta's hook emits the new conversation id, but herdr keeps the previous one. leonardschneider has two fixes:herdr:lettareports fornew/resumeupdate the same process's stored conversation id./resumeemitsSessionStart.herdr's maintainers plan to take the herdr fix after their agent-registry PR.
Plan: once a herdr release ships it, Ovis binds Letta Chat from herdr's report alone and drops the folder/record heuristics from #2312 (
lettaInStartFolder, the record-age and peer checks), which also closes the edge cases above.docs(guide): match 0.4.20 and main: Letta chat and its limits, Sign i…
fix(chat): remember a letta seen outside its start folder by its stab…