Skip to content

feat(thermidor): lock surfaces while a request is in flight instead of queuing gestures (PoC) - #8709

Draft
fbeaudoincoveo wants to merge 2 commits into
mainfrom
poc/lock-surfaces-while-busy
Draft

fbeaudoincoveo wants to merge 2 commits into
mainfrom
poc/lock-surfaces-while-busy

Conversation

@fbeaudoincoveo

Copy link
Copy Markdown
Contributor

Jira

None. This is a proof of concept to show the experience and the code it removes. It isn't meant to merge as is.

Motivation

Thermidor lets the shopper keep clicking while an action is in flight: it queues the gestures, coalesces them, and holds optimistic values across several outstanding requests. The Agent Gateway accepts one turn per session anyway, and a facet action is a Commerce API round trip, not an agent turn. So the wait is short and the queue mostly hides it.

This PoC tries the simpler model: disable the active surface while a state-changing request is in flight, so at most one gesture is ever outstanding. Then it removes the code that model makes redundant.

Changes

1. Lock the surface while a request is in flight (demo-schema-react)

  • The active turn's fieldset is disabled from the moment an action or follow-up is sent until its stream closes.
  • The clicked value still shows immediately. Controls dim only after 150 ms, so a fast answer never flashes.
  • Focus returns to the control that was used: a disabled control loses focus, which would otherwise send keyboard users back to the top of the page.
  • Facet search typing never locks, because a lookup changes no state.
  • A toggle in the bottom-right corner, or ?lockSurfaces=off, turns the lock off for comparison.

2. Drop what the lock makes redundant (@coveo/thermidor, demo-schema-react), 3.3k lines

  • @coveo/thermidor: the dispatch coordinator and tracker (coalescing, dispatch ids and outcomes), Session.actions, the optimistic value controller, and stale scopes. The session keeps a plain promise chain, so an action sent alongside a lookup still goes out in order. The 409 retry from feat(thermidor): retry Agent Gateway 409 AGENT:ACTION_IN_FLIGHT rejections j:KIT-6296 #8665 now runs on that chain.
  • demo-schema-react: pending-dispatch, every coalesce and invalidates declaration, and the numeric facet's landing-value logic. useOptimisticValue now holds a value until the next request ends. The results dim while an action is in flight. Facet search is debounced (200 ms) instead of superseding queued searches.
  • The README and docs/architecture.md describe "one action at a time" instead of the queue.

Known trade-off: with the lock off, a second click during a request is dropped and its checkmark reverts when the first request ends. The toggle compares the lock with no protection at all, not with the old queue.

Validation

  • @coveo/thermidor: typecheck, unit tests and test:dts pass. The 409 session tests now go through dispatchAction.
  • demo-schema-react: typecheck and unit tests pass. Each commit was checked on its own. Tests that only covered coalescing were removed. The six env.test.ts failures fail the same way on main; they come from a local .env.
  • Manually, against the mock Converse API:
    • a facet click checks at once, locks the surface and dims the results, then unlocks with the Breadbox updated;
    • typing in facet search stays unlocked and sends one search per pause;
    • focus comes back to the clicked checkbox.
  • Not run against a real Agent Gateway.

Checklist

  • PR title follows Conventional Commits 1.0.0 format (feat(<scope>): <description>)
  • No changeset: @coveo/thermidor and the sample are private

🤖 Generated with Claude Code

fbeaudoincoveo and others added 2 commits October 16, 2026 12:32
…PoC)

Disables the active turn's controls from the moment a state-changing action
or follow-up is sent until its stream closes, instead of queuing gestures.
The dimming waits 150 ms so fast answers never flash, focus returns to the
control that was used, and facet search typing never locks. A toggle in the
corner (or `?lockSurfaces=off`) switches the lock off for comparison.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…dundant (PoC)

With the active surface disabled while a request is in flight, at most one
gesture is outstanding at a time, so the machinery built to queue several
has nothing left to do:

- @coveo/thermidor: the dispatch coordinator and tracker (coalescing,
  dispatch ids and outcomes), `Session.actions`, the optimistic value
  controller, and stale scopes. The session keeps a plain promise chain so
  an action sent alongside a lookup still goes out in order.
- demo-schema-react: `pending-dispatch`, every `coalesce`/`invalidates`
  declaration, the numeric facet's landing-value logic, and the trace
  helper. An optimistic value now holds until the next request ends, and
  the results dim while an action is in flight. Facet search is debounced
  instead of superseding queued searches.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@changeset-bot

changeset-bot Bot commented Oct 16, 2026

Copy link
Copy Markdown

⚠️ No Changeset found

Latest commit: 36e373d

Merging this PR will not cause a version bump for any packages. If these changes should not result in a new version, you're good to go. If these changes should result in a version bump, you need to add a changeset.

This PR includes no changesets

When changesets are added to this PR, you'll see the packages that this PR includes changesets for and the associated semver types

Click here to learn what changesets are, and how to add one.

Click here if you're a maintainer who wants to add a changeset to this PR

@svcsnykcoveo

svcsnykcoveo commented Oct 16, 2026 •

Copy link
Copy Markdown

✅ Snyk checks have passed. No issues have been found so far.

Status Scan Engine Critical High Medium Low Total (0)
✅ Open Source Security 0 0 0 0 0 issues
✅ Licenses 0 0 0 0 0 issues
✅ Code Security 0 0 0 0 0 issues

💻 Catch issues earlier using the plugins for VS Code, JetBrains IDEs, Visual Studio, and Eclipse.

@pkg-pr-new

pkg-pr-new Bot commented Oct 16, 2026

Copy link
Copy Markdown

commit: 36e373d

@chromatic-com

chromatic-com Bot commented Oct 16, 2026 •

Copy link
Copy Markdown

Tip

All tests passed and all changes approved!

🟢 UI Tests: 439 tests unchanged
🟢 UI Review: 471 stories published -- no changes
Storybook icon Storybook Publish: 471 stories published

This branch was successfully deployed

2 active deployments
PR Artifacts — 36e373df Deployed Oct 16, 2026 by fbeaudoincoveo via Build & commit missing generated files #20105
pr-workflows — 36e373df Deployed Oct 16, 2026 by fbeaudoincoveo via label #9740
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants