Repository navigation
Combine saved decision answers into one Planner turn and keep them across a restart - #719
Merged
Merged
Conversation
…ross a restart Answering six cards the Planner left open started six Planner turns, and an answer that found no Planner waited only in memory, so a restart dropped it. Answers saved to one document close together now go in one Planner turn that lists each question, saved answer, chosen option and who saved it. The turn starts once nobody has saved another answer for five seconds, or 30 seconds after the first, and never while a Planner turn runs or waits in that Chat, so answers saved meanwhile join the next turn. Chat shows one notice, such as "@ana answered 3 decisions". Each answer is stored first in a new decision_answers table (and the memory adapter), one row per document and decision, so answers that found no Planner are delivered once an owner appears or a Planner attaches, after a restart too. Saving again replaces a waiting answer and reopening makes it stale. A turn's answers are claimed under a fresh id before it starts and marked delivered once Chat accepts it; its Chat notice takes that id, so answers claimed before a crash but not yet marked are recognized as already started and never run twice. Answers a blocking ask or a workflow's question waits for still go straight back and start no turn. Assistant-model: Claude Opus 5.5 (fast) Assistant-workflow: inline (fast subagents) Assistant-verification: bun test (unit, domain and memory storage) Assistant-verification: PostgreSQL storage contract and migration tests Assistant-verification: bun run types and bun run ci Assistant-verification: Chromium decision, hosted, connector and experiment suites Co-authored-by: Alex Lavaee <alexlavaee@microsoft.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Follows #712, which made each saved answer to a decision card the Planner left open (
open_decisions/open_decision) start one Planner turn. That PR reported two gaps: answering six cards started six Planner turns, and an answer that found no Planner waited only in memory, so a restart dropped it.What changes
One turn for answers saved together. Answers saved to the same document close together go into one Planner turn. That turn lists every answer: the question, the saved answer, the chosen option and its description, and who saved it.
@ana answered "…"for a single answer, or@ana and @lee answered 3 decisionsfor several.Answers survive a restart. Every answer is written to storage first, in the new
decision_answerstable (migration 027, plus the memory adapter and a shared contract test). There is one row per document and decision, holding the saved generation, the save time,turn_idanddelivered_at.ownerAvailable(an owner appears, or a Planner attaches) delivers whatever is waiting. That includes answers saved before a restart.No double delivery after a crash.
turn_id).Chat.Instruction.notice). Chat saves the notice before the turn runs.If the process dies between steps 2 and 3, the next process re-sends the claimed rows under the same id.
serverInstructionfinds that the Chat transcript already holds a notice with that id, reports the turn as accepted, and the rows are marked delivered without starting a second turn.Unchanged: answers that a blocking
askor a workflow's question is waiting for still go straight back to the asker and start no turn. Answer turns still run only under the existing owner, and underHARNESS=remoteonly while a Planner is attached.The connector is not changed.
Tests
Written to fail first (
answer-turns.test.ts, against real Chat andserverInstruction):serverInstructionmakes this test fail.askand workflow answers start no turn (unchanged).Storage contract tests, run against both memory and PostgreSQL: newest generation wins; claim, release and delivered; documents kept separate; rows removed with the document.