fix(kernel): forward web-UI-initiated delegation results to the home channel (refs #6266)#6286
Merged
Conversation
…channel (#6266) PR #6267 forwards an async-delegation completion to the agent's home channel mid-turn, but only when the originating turn carries an inbound `chat_id`. A delegation started from a web-UI turn has no `chat_id` (the WS sender sets none and uses the canonical session), so the forward was skipped and the result surfaced only in the web-UI session — never on the agent's channel (the "responds in the web UI instead of forwarding to Telegram" symptom in #6266). The mid-turn forward now resolves its destination as: the inbound `entry.chat_id` when present, else the home channel's configured `default_conversation`. A new optional `[[sidecar_channels]].default_conversation` names that fallback conversation. When neither is available the forward stays a no-op — it never guesses a recipient. `resolve_agent_home_channel`'s contract is unchanged (the trigger-dispatch caller is unaffected); the fallback is a separate `resolve_agent_default_conversation` helper. The "session mixing" sub-claim in #6266 is left for reporter confirmation — web-UI and channel sessions are storage-distinct by construction.
…te lines One sentence per line in CHANGELOG bullets per project prose rules. Also collapses the redundant `let kernel_arc = arc;` in task_registry.rs into the `if let Some(kernel_arc) = ...` binding directly.
houko
enabled auto-merge (squash)
June 23, 2026 06:17
…ter one review follow-up: sidecar_default_conversation used find_map, so when an agent's first home channel (the one resolve_agent_home_channel picks) had no default_conversation it skipped ahead to a later channel's default. The forward would then pair the home channel with a different channel's conversation id and deliver to the wrong place. Switch to find().and_then() so it reads only the first agent-matching channel's default, and add a regression test.
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.
Problem (remaining part of #6266)
#6267 (merged) forwards an async-delegation completion to the agent's home channel mid-turn — but only when the originating turn carries an inbound
chat_id. A delegation kicked off from a web-UI turn has nochat_id(the WS sender sets none and uses the canonical session), so the forward was skipped and the delegation result surfaced only in the web-UI session, never on the agent's channel. This is the "agent responds in the web UI instead of forwarding to Telegram" symptom.Fix
The mid-turn forward in
task_registry.rsnow resolves its destination as inboundentry.chat_id(if present) → else the home channel's configureddefault_conversation. A new optional[[sidecar_channels]].default_conversationnames that fallback conversation. If neither resolves, the forward stays a no-op — it never guesses a recipient (delivering to a wrong chat is worse than not delivering).librefang-types/config/types.rs—default_conversation: Option<String>onSidecarChannelConfig(#[serde(default)], additive; existing configs unaffected).librefang-kernel/messaging.rs—resolve_agent_default_conversation+ puresidecar_default_conversationhelper (mirrorssidecar_default_agent).resolve_agent_home_channel's contract is left unchanged, so the trigger-dispatch caller is unaffected.librefang-kernel/task_registry.rs— destination fallback in the mid-turn forward.kernel_config_schema.golden.json— regenerated for the new field.Out of scope / for the reporter
The titular "session mixing" sub-claim is not a shared-session bug: web-UI sessions resolve to the canonical
entry.session_idand channel sessions toSessionId::for_channel(agent,"<channel>:<chat>")— storage-distinct by construction. Left awaiting the reporter's twoSessionIds to confirm (most likely the boot-time web-UI→canonical adoption, not live leakage). The wake-idle forward path is intentionally unchanged (separate from the mid-turn path this issue is about).Verification
cargo check -p librefang-kernel— clean (Docker dev image).cargo clippy -p librefang-kernel --all-targets -- -D warnings— zero warnings.cargo test -p librefang-kernel default_conversation— 6/6 pass (matching-agent resolves; unset/empty → None no-op; non-matching agent doesn't leak; first-match deterministic; serde back-compat).