Skip to content

fix(ui): preserve other pending answers on needs-input submit - #641

Open
emrahzunicaplab wants to merge 5 commits into
andresharpe:mainfrom
emrahzunicaplab:bugfix/needs-input-clears-other-answers
Open

fix(ui): preserve other pending answers on needs-input submit#641
emrahzunicaplab wants to merge 5 commits into
andresharpe:mainfrom
emrahzunicaplab:bugfix/needs-input-clears-other-answers

Conversation

@emrahzunicaplab

@emrahzunicaplab emrahzunicaplab commented Jul 13, 2026

Copy link
Copy Markdown
Contributor

Linked issue

Closes #622

Summary of changes

renderActionItems fully rebuilds the action-required panel's DOM after any
question submit (container.innerHTML = ...), so submitting one question in
a pending_questions batch wiped the .selected state and free-text drafts
on sibling, un-submitted questions — the only place that state lived.

Added a small client-side draft store (taskQuestionDrafts) in
src/ui/static/modules/actions.js that records each un-submitted
selection/free-text as the user makes it, and re-applies it whenever
renderTaskQuestionsItem repaints. The draft for a question is cleared once
the server confirms it's answered. No API or backend changes — this keeps
the existing per-question submit/resume contract documented in
PRD-029 (pending_questions[]: "mark answered per question; move when all
done"), rather than moving to a single "Submit all" action.

Screenshots / recordings

Before/after recording: on main, submitting one question in the 4-question batch wipes the in-progress selections on the other pending questions; on this branch, sibling selections/drafts are preserved across submits until each question is answered.

Before.mp4
After.mp4

Testing notes

Repro'd with a seeded needs-input task carrying 4 pending_questions
(extensions.runner.pending_questions) against a local dotbot serve
instance:

  1. Open the action-required panel — 4 questions shown.
  2. Select an option on Q2 and Q3 (don't submit).
  3. Click "Submit Q1".
  4. After the panel re-renders (~1.5s), Q2/Q3 selections are preserved —
    previously they were wiped.
  5. Continue submitting Q2 → Q3 → Q4; panel correctly resolves to
    "No pending actions" once the last question is answered.

Checklist

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Fixes the UI behavior where submitting one question in a pending_questions batch causes the action panel to fully re-render and lose unsubmitted selections/free-text drafts on sibling questions. This stays entirely client-side by persisting per-question drafts in module state and re-applying them on re-render.

Changes:

  • Added an in-memory draft store for task-level batch questions (taskQuestionDrafts) keyed by task/question id.
  • Updated renderTaskQuestionsItem to restore option selection and free-text from the draft store on every paint.
  • Updated action handlers to record draft state on option selection / free-text input, and clear it once a question is successfully submitted.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment thread src/ui/static/modules/actions.js
Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com>
Copilot AI review requested due to automatic review settings July 13, 2026 14:04

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Copilot reviewed 1 out of 1 changed files in this pull request and generated 1 comment.

Comment thread src/ui/static/modules/actions.js Outdated
Comment on lines +410 to +414
${questions.map((q, idx) => {
// Restore any un-submitted selection for this question so a
// re-render (e.g. after a sibling question is submitted)
// does not wipe it — see taskQuestionDrafts (issue #622).
const draft = (taskQuestionDrafts[taskId] || {})[q.id] || {};
Copilot AI review requested due to automatic review settings August 3, 2026 09:08

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🟡 Not ready to approve

The new free-text input handler can clear the stored draft on whitespace-only input while leaving an option selected, which can still cause selections to be lost after a subsequent re-render.

Once you've addressed the issues Copilot identified, you can request another Copilot review.

This review doesn't count toward merge requirements. Sign up for the private preview to control whether Copilot approvals count.

Review details

Suppressed comments (1)

src/ui/static/modules/actions.js:993

  • The free-text input handler clears the stored draft whenever textarea.value.trim() is empty, but it does not account for the case where the user types only whitespace while an option is still selected. In that case, the option remains selected in the DOM, but the stored draft is removed, so a subsequent panel re-render will lose the selection again.
        textarea.addEventListener('input', () => {
            const questionBlock = textarea.closest('.task-question-block');
            if (questionBlock?.classList.contains('answered')) return;
            if (textarea.value.trim()) {
                questionBlock?.querySelectorAll('.answer-option').forEach(opt => opt.classList.remove('selected'));
  • Files reviewed: 1/1 changed files
  • Comments generated: 0 new
  • Review effort level: Lite

We're testing this review assessment. Please use 👍 or 👎 to tell us if it's correct.

@carlospedreira carlospedreira left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The draft is still lost in one reproducible path: choose an option, then enter only whitespace in the custom-answer textarea. The option remains visually selected, but the input handler sees an empty trimmed value and clears taskQuestionDrafts; the next panel re-render then drops the selection. Preserve the option draft when a selected option exists (or clear the selection consistently) before this can be merged.

Copilot AI review requested due to automatic review settings August 3, 2026 12:06

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🟢 Ready to approve

The changes are scoped to client-side UI state management, include pruning/cleanup to avoid stale restoration, and align with the existing per-question submit contract without introducing backend/API changes.

This review doesn't count toward merge requirements. Sign up for the private preview to control whether Copilot approvals count.

Review details
  • Files reviewed: 1/1 changed files
  • Comments generated: 0 new
  • Review effort level: Lite

We're testing this review assessment. Please use 👍 or 👎 to tell us if it's correct.

Copilot AI review requested due to automatic review settings August 4, 2026 10:54

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🟡 Not ready to approve

The behavior change isn’t covered by the existing automated UI tests, so a Playwright E2E regression test for “submit Q1 preserves Q2/Q3 drafts” should be added to prevent future regressions.

Once you've addressed the issues Copilot identified, you can request another Copilot review.

This review doesn't count toward merge requirements. Sign up for the private preview to control whether Copilot approvals count.

Review details

Suppressed comments (1)

src/ui/static/modules/actions.js:15

  • The new client-side draft store for task batch questions fixes a subtle UI regression, but there’s no automated coverage for the cross-submit persistence scenario (select answers on Q2/Q3, submit Q1, verify Q2/Q3 drafts persist after the panel re-renders). The existing Playwright E2E suite doesn’t appear to exercise the action-required slideout / task-questions flow, so this could regress without being caught.
// Un-submitted selections for task-level batch questions (the "task-questions"
// action item). Keyed { taskId: { questionId: { key, customText } } }. Selections
// for a batch of pending_questions otherwise live only in the DOM's `.selected`
// class, so submitting one question — which triggers a full panel re-render —
// wipes the choices lined up on the sibling questions (issue #622). This store
  • Files reviewed: 1/1 changed files
  • Comments generated: 0 new
  • Review effort level: Lite

We're testing this review assessment. Please use 👍 or 👎 to tell us if it's correct.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

Status: Inbox

Development

Successfully merging this pull request may close these issues.

needs-input: submitting one answer clears the others

3 participants