Skip to content

feat: dialogue confirmation loop for Telegram agents - #5

Draft
Secret297-CODER-SOURCE with Copilot wants to merge 2 commits into
mainfrom
copilot/add-conversational-loop
Draft

feat: dialogue confirmation loop for Telegram agents#5
Secret297-CODER-SOURCE with Copilot wants to merge 2 commits into
mainfrom
copilot/add-conversational-loop

Conversation

Copilot AI commented Mar 6, 2026

Copy link
Copy Markdown

Telegram agents had no mechanism to maintain a confirmation-pending state across turns — each response was stateless with respect to whether the agent was awaiting user agreement. This adds a session-persisted confirmation loop so agents can block progression until the user explicitly confirms or rejects.

Summary

  • Problem: Agents responded to each message independently with no ability to hold a "waiting for your agreement" state; no loop existed to prevent the agent from moving on without user consent.
  • Why it matters: Users need agents that negotiate multi-step actions collaboratively, not agents that proceed unilaterally or drop the thread.
  • What changed: Added pendingConfirmation/confirmationRequired session fields, a new dialogue-confirmation module with English+Russian detection, prompt injection helpers, auto-detection of agent confirmation requests, and /confirm//reject//dialogue commands.
  • What did NOT change: Session file persistence, conversation history loading, or any existing command handler behavior.

Change Type (select all)

  • Bug fix
  • Feature
  • Refactor
  • Docs
  • Security hardening
  • Chore/infra

Scope (select all touched areas)

  • Gateway / orchestration
  • Skills / tool execution
  • Auth / tokens
  • Memory / storage
  • Integrations
  • API / contracts
  • UI / DX
  • CI/CD / infra

Linked Issue/PR

  • Related #

User-visible / Behavior Changes

  • New session state: pendingConfirmation: { task, sentAt } persisted to the session store when an agent response contains a confirmation request (e.g. "Please confirm", "Shall I proceed?", "Подтвердите").
  • Auto-detection loop: When pendingConfirmation is set, the next inbound message is inspected for natural-language yes/no (English + Russian). Confirmed → agent body prepended with [User confirmed the pending action]. Rejected → [User rejected/cancelled the pending action].
  • System prompt injection: While confirmation is pending, the agent receives a [Dialogue state: awaiting user confirmation] note; when confirmationRequired is enabled, it receives [Dialogue mode: confirmation required].
  • New commands:
    • /confirm (aliases: /agree, /yes) — explicitly confirm; clears pendingConfirmation
    • /reject (aliases: /cancel, /no) — explicitly reject; clears pendingConfirmation
    • /dialogue status — show pending state + mode
    • /dialogue confirm-required on|off — toggle session-level confirmation-required mode

Security Impact (required)

  • New permissions/capabilities? No
  • Secrets/tokens handling changed? No
  • New/changed network calls? No
  • Command/tool execution surface changed? No — new commands are info/state-only, no exec surface
  • Data access scope changed? No — writes only to the existing per-session store entry

Repro + Verification

Environment

  • OS: Linux / macOS
  • Runtime/container: Node 22+ / Bun
  • Model/provider: Any
  • Integration/channel: Telegram DM
  • Relevant config (redacted): standard channels.telegram config

Steps

  1. Send a message to a Telegram agent that causes it to respond with "Would you like me to proceed?" or similar.
  2. Observe pendingConfirmation set in session store; agent next turn includes the pending note in system prompt.
  3. Reply "yes" or "да" — agent body is prefixed with confirmed context.
  4. Or reply "no"/"нет" — agent body is prefixed with rejected context.
  5. Or use /confirm / /reject commands explicitly.

Expected

  • Agent keeps the dialogue open until the user explicitly agrees or refuses.
  • Confirmation state is cleared after resolution.

Actual

  • Without this change: agent treats each message independently; no confirmation-pending state.

Evidence

  • Failing test/log before + passing after
  • Trace/log snippets
  • Screenshot/recording
  • Perf numbers (if relevant)

25 new unit tests in dialogue-confirmation.test.ts covering isConfirmationResponse, isRejectionResponse, agentResponseRequestsConfirmation, and prompt builders. All 462 existing auto-reply/reply/ tests and 73 session/Telegram tests continue to pass.

Human Verification (required)

  • Verified scenarios: Unit tests for all detection patterns; confirmed no regressions in existing test suite.
  • Edge cases checked: Cyrillic \b boundary issue (fixed — JS regex \b doesn't work with Cyrillic; replaced with (?:^|\s)…(?:\s|$) anchors). Mixed-case confirmation strings. Empty strings. Sessions without pendingConfirmation set.
  • What you did not verify: Live Telegram end-to-end with a real model response; auto-detection accuracy at scale.

Compatibility / Migration

  • Backward compatible? Yes — new fields are optional on SessionEntry; no existing behavior changes
  • Config/env changes? No
  • Migration needed? No

Failure Recovery (if this breaks)

  • How to disable/revert this change quickly: Remove handleDialogueCommand from the HANDLERS array in commands-core.ts; revert the extraSystemPrompt and applyConfirmationContext additions in get-reply-run.ts.
  • Files/config to restore: src/auto-reply/reply/get-reply-run.ts, src/auto-reply/reply/commands-core.ts
  • Known bad symptoms: Agent receiving spurious [User confirmed] prefixes on unrelated "yes" messages in contexts where pendingConfirmation was never set — not possible by design (guard is if (!pending) return body).

Risks and Mitigations

  • Risk: Natural-language confirmation patterns are too broad — e.g. /\b(yes|confirm|proceed|agree)\b/i could match "I don't agree with that" and incorrectly treat it as a confirmation.
    • Mitigation: Patterns are only evaluated when pendingConfirmation is actively set (not on every message). Short-pattern matches like \b(yes)\b require a pending state to fire. False positives clear the state but don't block the user; the agent sees the full message and can handle ambiguity.
  • Risk: setConfirmationPendingIfRequested fires on every agent response, adding a store write on any response containing common phrases.
    • Mitigation: Guard is a regex scan; only writes when a pattern matches. Store write is the same updateSessionStore used throughout the codebase.

💬 We'd love your input! Share your thoughts on Copilot coding agent in our 2 minute survey.

- Add `pendingConfirmation` and `confirmationRequired` fields to `SessionEntry`
- New `dialogue-confirmation.ts`: confirmation/rejection detection (English + Russian),
  agent confirmation-request detection, prompt injection helpers, session state updaters
- New `commands-dialogue.ts`: /confirm, /reject, /agree, /yes, /no, /cancel and
  /dialogue status|confirm-required on|off command handlers
- Register `handleDialogueCommand` in `commands-core.ts`
- Integrate confirmation loop into `get-reply-run.ts`: inject pending-confirmation
  notes into system prompt, detect natural-language yes/no in user messages, and
  auto-set `pendingConfirmation` when agent response requests confirmation
- 25 new tests in `dialogue-confirmation.test.ts`

Co-authored-by: Secret297-CODER-SOURCE <73541046+Secret297-CODER-SOURCE@users.noreply.github.com>
Copilot AI changed the title [WIP] Add conversational loop for Telegram agents feat: dialogue confirmation loop for Telegram agents Mar 6, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants