mirror of
https://github.com/windmill-labs/windmill.git
synced 2026-10-12 16:02:56 +00:00
fix(sessions): tell a mounting composer apart from a busy one
The retry that waits for a chat flow's composer could not tell "not there yet" from "the reader is writing": both read as a declined offer, so the proposal stayed pending and would have landed in the box whenever the composer next changed — words appearing long after they were proposed. `composerReady` answers the first question on its own; past it the proposal is settled either way, and a reader's draft is left alone. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Opus 5
parent
daa2a3433d
commit
3ee5ca72f8
@@ -381,16 +381,21 @@
|
||||
seededSeq = seededRun.seq
|
||||
return
|
||||
}
|
||||
// The rest of the proposal goes with it: a chat flow's schema can declare more than
|
||||
// `user_message`, and sending the message alone would run on saved values or schema
|
||||
// defaults — a different run from the one being offered.
|
||||
// The composer mounts a flush or two after the panel does, so until it is there this
|
||||
// effect waits — it reads the host's registration through `composerReady`, and runs
|
||||
// again when that lands. Not latching is what keeps the proposal alive across those
|
||||
// flushes.
|
||||
if (!flowChat?.composerReady()) return
|
||||
// Past that point the answer is final either way. The rest of the proposal goes with
|
||||
// the message: a chat flow's schema can declare more than `user_message`, and sending
|
||||
// the message alone would run on saved values or schema defaults — a different run
|
||||
// from the one being offered. A composer already holding a draft declines, and the
|
||||
// proposal is dropped rather than held: injecting it whenever the reader happens to
|
||||
// clear their draft would put words in the box long after they were proposed. The
|
||||
// card still shows what was asked for.
|
||||
const { user_message: _m, ...inputs } = seededRun.args ?? {}
|
||||
// Only on success. The composer mounts a flush or two after the panel, and a
|
||||
// declined offer here means it is not there yet — this effect tracks the host's
|
||||
// input through `offerMessage` and runs again when it registers. A composer that
|
||||
// already holds a draft also declines, and re-offering on its next change is right:
|
||||
// the reader may clear it, and then the message lands.
|
||||
if (flowChat?.offerMessage(message, inputs)) seededSeq = seededRun.seq
|
||||
seededSeq = seededRun.seq
|
||||
flowChat.offerMessage(message, inputs)
|
||||
} else if (runForm) {
|
||||
seededSeq = seededRun.seq
|
||||
runForm.setArgs(seededRun.args)
|
||||
|
||||
@@ -193,6 +193,14 @@
|
||||
return true
|
||||
}
|
||||
|
||||
/** Whether the conversation on screen has a composer to offer a message to. A caller that
|
||||
* gets `false` from `offerMessage` reads this to tell "mounting, try again" from "the
|
||||
* reader is writing, leave them alone". */
|
||||
export function composerReady(): boolean {
|
||||
const panel = shownKey ? pool?.get(shownKey) : undefined
|
||||
return panel?.host.composerReady ?? false
|
||||
}
|
||||
|
||||
// Derive additional inputs schema (excluding user_message) for chat mode
|
||||
const additionalInputsSchema = $derived.by(() => {
|
||||
const props = inputSchema?.properties ?? {}
|
||||
|
||||
@@ -582,6 +582,13 @@ export class FlowChatViewHost implements ChatViewHost, DraftSender<ComposerAttac
|
||||
this.#takeReturned()
|
||||
})
|
||||
|
||||
/** Whether a composer is mounted and listening for this conversation. Apart from
|
||||
* `offerMessage`'s own answer because the two mean different things to a caller: not ready
|
||||
* is worth waiting for, a composer that declined is not. */
|
||||
get composerReady(): boolean {
|
||||
return !!this.#aiChatInput && !this.#disposed
|
||||
}
|
||||
|
||||
/** Put a message in the composer showing this conversation, for the reader to edit and
|
||||
* send — a chat flow's page has no run form to fill, so this is where a chat tool's
|
||||
* proposed `user_message` lands. Declines when the composer already holds a draft, so it
|
||||
|
||||
Reference in New Issue
Block a user