From 5d59f93a5d191cc3c159748c550562d2f1a45c71 Mon Sep 17 00:00:00 2001 From: Lily Shen <115414357+lilyshen0722@users.noreply.github.com> Date: Sun, 25 Oct 2026 22:21:53 -0700 Subject: [PATCH 1/2] fix(scout): propose the connect card once the tool and OS are known, never ask first The stranger journey failed its card step on 2026-10-26 02:17Z. Scout's runs show the card was never sent, not sent late: told "macOS" after "Claude Code", Scout wrote the listener steps into chat and ended with "Want me to open that page with your claude command already filled in?", then finished its run at 02:18:26 and waited for a yes. The run 21 minutes earlier, on the same model and question, proposed on that turn. The prompt let both readings stand: the "both halves" rule asked for the Terminal command in text, and the card rule fired only "when the user wants their local agent in the workspace". Scout now proposes in the turn it learns the tool and a supported OS, and the card stands in for the Terminal half. Co-Authored-By: Claude Opus 5.5 Claude-Session: https://claude.ai/code/session_013ENddpGzhE7S8qjDSYAMuu --- .../unit/config/nativeAgents.scoutKnowledge.test.js | 13 +++++++++++++ backend/config/native-agents/scout.ts | 12 +++++++++++- 2 files changed, 24 insertions(+), 1 deletion(-) diff --git a/backend/__tests__/unit/config/nativeAgents.scoutKnowledge.test.js b/backend/__tests__/unit/config/nativeAgents.scoutKnowledge.test.js index ab38f08955..5a06e419e4 100644 --- a/backend/__tests__/unit/config/nativeAgents.scoutKnowledge.test.js +++ b/backend/__tests__/unit/config/nativeAgents.scoutKnowledge.test.js @@ -141,6 +141,19 @@ describe('Scout onboarding knowledge', () => { expect(prompt).toMatch(/and the MCP line/); }); + // Stranger journey 2026-10-26: Scout wrote the Terminal steps and asked + // "Want me to open that page?" instead of proposing, and no card came. + test('proposes the connect card once it knows the tool and OS, without asking first', () => { + expect(prompt).toMatch( + /Propose the connect card in the same turn you learn both what they run and an OS where it can be connected/, + ); + expect(prompt).toMatch(/Do not ask whether to: the card is the question/); + expect(prompt).toMatch(/Do not write the Terminal steps in chat instead of the card/); + expect(prompt).toMatch( + /Where the connect card applies, the card is the Terminal half: propose it and give only the MCP line/, + ); + }); + test('cites developer docs that exist in the repository', () => { const repo = path.resolve(__dirname, '../../../..'); for (const doc of [ diff --git a/backend/config/native-agents/scout.ts b/backend/config/native-agents/scout.ts index 0c18feeae1..d2c4701a27 100644 --- a/backend/config/native-agents/scout.ts +++ b/backend/config/native-agents/scout.ts @@ -203,6 +203,14 @@ export const scoutApp = { + 'to the page with the command and what it needs, so do not post the steps ' + 'again; at most one short line that the command is on the page that opened. ' + 'You never see their key and must never ask them to paste one into chat.\n' + // Stranger journey 2026-10-26 02:18Z: told "macOS" after "Claude Code", + // Scout pasted the listener steps and asked "Want me to open that page?", + // then waited. No card ever came, and a stranger who does not answer that + // question never gets one. The run 21 minutes earlier proposed on that turn. + + '- Propose the connect card in the same turn you learn both what they run ' + + 'and an OS where it can be connected. Do not ask whether to: the card ' + + 'is the question, and they answer it by approving. Do not write the ' + + 'Terminal steps in chat instead of the card.\n' + '- commonly_agent_status tells you every agent\'s live state. Use it ' + 'whenever the user asks whether an agent is connected or why it is ' + 'silent: never-connected means the connect-page step was never finished ' @@ -226,7 +234,9 @@ export const scoutApp = { + '- When their own tool can call agents or command-line tools, or they ' + 'ask about both directions, give both halves: the Terminal command (their agent ' + 'answers @mentions here) and the MCP line (their agent uses Commonly ' - + 'from its own sessions). Say that MCP alone does not answer @mentions.\n' + + 'from its own sessions). Say that MCP alone does not answer @mentions. ' + + 'Where the connect card applies, the card is the Terminal half: propose ' + + 'it and give only the MCP line in your text.\n' + '- End with one next step they can take right now.\n' + '- The facts above are verified: give them without hedging. For ' + 'anything they do not cover, say you are not sure, give the closest ' From 2dc92ecd3bad51b001651d892c9929f3b8af74ec Mon Sep 17 00:00:00 2001 From: Lily Shen <115414357+lilyshen0722@users.noreply.github.com> Date: Sun, 25 Oct 2026 22:43:34 -0700 Subject: [PATCH 2/2] fix(scout): give Codex its own MCP line beside the connect card With a card proposed, Scout gives only the MCP line in text, and the prompt named an MCP line for Claude Code only. A Codex user would get the Claude command, which does not configure Codex. The Codex line is the documented codex mcp add form. Co-Authored-By: Claude Opus 5.5 Claude-Session: https://claude.ai/code/session_013ENddpGzhE7S8qjDSYAMuu --- .../unit/config/nativeAgents.scoutKnowledge.test.js | 10 ++++++++++ backend/config/native-agents/scout.ts | 9 ++++++--- 2 files changed, 16 insertions(+), 3 deletions(-) diff --git a/backend/__tests__/unit/config/nativeAgents.scoutKnowledge.test.js b/backend/__tests__/unit/config/nativeAgents.scoutKnowledge.test.js index 5a06e419e4..dc744441ac 100644 --- a/backend/__tests__/unit/config/nativeAgents.scoutKnowledge.test.js +++ b/backend/__tests__/unit/config/nativeAgents.scoutKnowledge.test.js @@ -154,6 +154,16 @@ describe('Scout onboarding knowledge', () => { ); }); + // A card gets only the MCP line in text, so Codex needs a line of its own: + // the Claude Code one does not configure Codex. + test('gives an MCP line for each tool the card connects', () => { + expect(prompt).toContain('`claude mcp add commonly -e COMMONLY_API_URL=... ' + + '-e COMMONLY_AGENT_TOKEN=... -- npx -y @commonlyai/mcp`'); + expect(prompt).toContain('`codex mcp add commonly --env COMMONLY_API_URL=... ' + + '--env COMMONLY_AGENT_TOKEN=... -- npx -y @commonlyai/mcp`'); + expect(prompt).toMatch(/Give the line for the tool they run/); + }); + test('cites developer docs that exist in the repository', () => { const repo = path.resolve(__dirname, '../../../..'); for (const doc of [ diff --git a/backend/config/native-agents/scout.ts b/backend/config/native-agents/scout.ts index d2c4701a27..2f22c35e8b 100644 --- a/backend/config/native-agents/scout.ts +++ b/backend/config/native-agents/scout.ts @@ -104,10 +104,13 @@ export const scoutApp = { + 'tool gets a clear error instead of quietly starting the other one. That ' + 'last command is what makes their agent answer @mentions, and its Terminal ' + 'window must stay open. The page turns green when the agent first checks in.\n' - + ' * An MCP line for Claude Code (`claude mcp add commonly -e ' + + ' * An MCP line gives their agent Commonly tools inside their own ' + + 'sessions. For Claude Code: `claude mcp add commonly -e ' + 'COMMONLY_API_URL=... -e COMMONLY_AGENT_TOKEN=... -- npx -y ' - + '@commonlyai/mcp`) gives their agent Commonly tools inside their own ' - + 'sessions. MCP alone does NOT answer @mentions; only the listener does. ' + + '@commonlyai/mcp`. For Codex: `codex mcp add commonly --env ' + + 'COMMONLY_API_URL=... --env COMMONLY_AGENT_TOKEN=... -- npx -y ' + + '@commonlyai/mcp`. Give the line for the tool they run. ' + + 'MCP alone does NOT answer @mentions; only the listener does. ' + 'Say exactly this when someone set up MCP and asks why their agent is ' + 'silent.\n' // Walked 2026-10-19 (CLI 0.1.108, OpenCode 1.19.3, macOS, a non-admin