Files
hope-voice-api/.artifacts/20260831-105824-plan-code-ui-audit/iterations/06-request.md
T
2026-08-31 19:50:46 -04:00

3.1 KiB

Iteration 06 Request

  • Task: 20260831-105824-plan-code-ui-audit
  • Requested by: build after inspection of iteration 05
  • Owner: coder
  • Status: changes-requested

Exact Corrections

  1. Remove session.transcriptHandler.clearAll() from ConversationView.startSession(). Starting a conversation must preserve the restored last-50 history; only the explicit Clear button erases it.
  2. Make cross-source dedupe consume the opposite-source record when it suppresses that copy. Otherwise a legitimate second same-text utterance from the currently arriving source is also suppressed within the window. Add a deterministic test: primary final, data duplicate suppressed, second data final with same text accepted. Keep same-source immediate repeats accepted and persistence exact.
  3. Route every final token/connect failure through centralized teardown and set .failed(message) before awaiting disconnect. Change teardownForFailure to accept/set its terminal message idempotently. Use it for non-timeout and exhausted-timeout connect failures, final agent timeout, and remote terminal disconnect. Ensure retry always sees a fresh room.
  4. In explicit disconnect(), do not publish .idle until media and room teardown have completed. This makes idle a truthful readiness signal for server replacement. Set an intentional transitional/teardown guard first so disconnect callbacks are ignored.
  5. Correct server Apply behavior using one of these safe options: (a) disable Apply while session.state != .idle, observe the session in Settings, and explain “End the conversation before changing servers”; or (b) queue exactly one accepted URL and apply it when state becomes idle. Do not immediately disconnect an active call. Add an isReplacingSession/identity guard so repeated Apply cannot race concurrent replacements. Media must continue using the accepted current-session server until replacement.
  6. Actually serialize interruption mic operations. Use one retained operation chain/task: .began waits for the previous operation, mutes, then marks interruption ownership only after successful mute and matching sequence/generation; .ended waits for that begin operation before deciding whether to unmute. A newer begin supersedes stale end via sequence. Remove the current pattern that sets ownership before mute and launches unmute without awaiting the mute task.
  7. Make resource-loader map serialization true in code, not comments: create the pinned URLSession with delegateQueue: OperationQueue.main (or protect every map access with a lock/serial queue). Keep AVAsset delegate on main. Verify successful/error/cancel callbacks all remove tasks on that same serialization domain.
  8. Update inaccurate implementation reports only after verification. Run all discovered tests, separate build, and diff check. Add focused tests for items 1/2 and pure seams where practical.

Deliverables

  • iterations/06-implementation.md, updated implementation.md, appended manifest history.
  • Actual XcodeBuildMCP suite/count/log evidence.
  • No broad UI redesign, reference-project changes, commit, or self-approval.