fix: add hint text and keybinding guidance to setup options prompt#2556
Closed
AhmedTMM wants to merge 36 commits intoOpenRouterTeam:mainfrom
Closed
fix: add hint text and keybinding guidance to setup options prompt#2556AhmedTMM wants to merge 36 commits intoOpenRouterTeam:mainfrom
AhmedTMM wants to merge 36 commits intoOpenRouterTeam:mainfrom
Conversation
Adds separate "Telegram" and "WhatsApp" checkboxes to the OpenClaw setup screen: - Telegram: prompts for bot token from @Botfather, injects into OpenClaw config via `openclaw config set` - WhatsApp: reminds user to scan QR code via the web dashboard after launch (no CLI setup possible) Updates USER.md with channel-specific guidance when either is selected. Bump CLI version to 0.16.16. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Instead of punting WhatsApp setup to "after launch", runs `openclaw channels login --channel whatsapp` as an interactive SSH session between gateway start and TUI launch. The user scans the QR code with their phone during provisioning setup. Flow: gateway starts → tunnel set up → WhatsApp QR scan → TUI launch Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Signed-off-by: Ahmed Abushagur <ahmed@abushagur.com>
The `openclaw config set` calls for browser and Telegram settings were re-serializing openclaw.json and dropping the gateway.auth.token field, causing the dashboard to show "Unauthorized" when auto-opened via tunnel. Now all config (gateway auth, browser, channels) is built as a single JSON object and written once via uploadConfigFile. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Adds 40 new tests across 2 files: openclaw-config.test.ts (30 tests): - Gateway auth token written correctly and matches browserUrl - Atomic config write (no `openclaw config set` commands) - Browser config gated by enabledSteps - Telegram bot token included/omitted based on input - USER.md messaging channel content - Tunnel config targeting port 18791 orchestrate-messaging.test.ts (10 tests): - SPAWN_ENABLED_STEPS parsing and threading - WhatsApp QR scan session triggered before agent launch - GitHub auth gated by enabledSteps - preLaunchMsg output behavior Also adds SPAWN_TELEGRAM_BOT_TOKEN env var override for non-interactive/CI Telegram setup (avoids prompt in tests). Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
…ccount limit (OpenRouterTeam#2518) Previously, _digitalocean_max_parallel() always returned 3, assuming all quota slots were available. When pre-existing droplets occupy slots, the batch-3 parallel runs fail with "droplet limit exceeded" API errors. Now queries /v2/account for the actual droplet_limit and subtracts the current droplet count to compute available capacity. Falls back to 3 if the API is unreachable. -- qa/e2e-tester Co-authored-by: spawn-qa-bot <qa@openrouter.ai>
…rrors (OpenRouterTeam#2520) When provisioning hits a 422 "droplet limit exceeded" response, wait 30s and retry up to 3 times. Makes E2E suite resilient to transient limit hits during parallel batch provisioning. Fixes OpenRouterTeam#2516 Agent: code-health Co-authored-by: B <6723574+louisgv@users.noreply.github.com> Co-authored-by: Claude Sonnet 4.5 <noreply@anthropic.com>
Instead of punting WhatsApp setup to "after launch", runs `openclaw channels login --channel whatsapp` as an interactive SSH session between gateway start and TUI launch. The user scans the QR code with their phone during provisioning setup. Flow: gateway starts → tunnel set up → WhatsApp QR scan → TUI launch Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
…am#2519) * test: add cron-triggered Telegram reminder to soak test Tests OpenClaw's ability to stay alive and execute scheduled tasks. Installs a one-shot cron on the VM before the 1h soak wait that sends a Telegram message at ~55 min, then verifies the message was sent after the wait completes. Also moves Telegram config injection before the soak wait so the cron can use the bot token immediately. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> * test: use OpenClaw's cron scheduler instead of system crontab Replaces the raw system cron approach with OpenClaw's built-in cron scheduler (`openclaw cron add`). This properly tests that OpenClaw's gateway stays alive after 1 hour and can execute scheduled tasks. The test now: 1. Injects Telegram config + schedules an OpenClaw cron job (--at +55min) 2. Waits 1 hour (soak) 3. Verifies the job fired via `openclaw cron runs` and `openclaw cron list` Uses --delete-after-run for one-shot semantics. Verification checks both the run history and the auto-deletion as proof of execution. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> * test: verify cron message on Telegram side via forwardMessage Instead of trusting OpenClaw's self-reported cron status, we now verify the message actually exists in the Telegram chat: 1. Extract message_id from OpenClaw's cron execution logs (tries `openclaw cron runs`, then ~/.openclaw/cron/ directory) 2. Call Telegram's forwardMessage API with that message_id 3. If Telegram can forward it → message EXISTS in the chat (proof from Telegram itself, not OpenClaw) This catches cases where OpenClaw reports success but the message never actually reached Telegram. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> * fix: address security review findings in soak test - Add validate_positive_int() and validate SOAK_WAIT_SECONDS + SOAK_CRON_DELAY_SECONDS at startup (prevents command injection via crafted env vars) - Validate TELEGRAM_TEST_CHAT_ID is numeric in soak_validate_telegram_env - Use per-app marker file /tmp/.spawn-cron-scheduled-${app} to avoid race conditions when multiple soak tests run on the same VM Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
…n gcp.ts (OpenRouterTeam#2524) Fixes OpenRouterTeam#2521 - Add path traversal and argument injection protection for localPath Fixes OpenRouterTeam#2522 - Add validation for cmd parameter before SSH execution Agent: security-auditor Co-authored-by: B <6723574+louisgv@users.noreply.github.com> Co-authored-by: Claude Sonnet 4.5 <noreply@anthropic.com>
…RouterTeam#2525) Replace `if (!r.ok) { expect(...) }` and `if (result.ok) { return }` guards with unconditional assertions using toThrow() or toMatchObject(). These conditional blocks silently skipped assertions when the condition evaluated the wrong way, providing false confidence. Also remove now-unused tryCatch imports from prompt-file-security.test.ts and security.test.ts. Co-authored-by: spawn-qa-bot <qa@openrouter.ai> Co-authored-by: Claude Sonnet 4.6 <noreply@anthropic.com>
…th) (OpenRouterTeam#2528) Add explicit base64 character validation in _digitalocean_exec after encoding the command, matching the existing pattern in provision.sh. This ensures the encoded value contains only [A-Za-z0-9+/=] before embedding it in the SSH command string. Note: OpenRouterTeam#2527 (provision.sh base64 validation) was already fixed in a prior commit — the validation at lines 284-289 already rejects non-base64 characters and empty output. Fixes OpenRouterTeam#2526 Agent: security-auditor Co-authored-by: B <6723574+louisgv@users.noreply.github.com> Co-authored-by: Claude Sonnet 4.6 <noreply@anthropic.com>
…n-depth) (OpenRouterTeam#2532) Add base64 character validation ([A-Za-z0-9+/=]) before use in SSH command strings for gcp.sh, aws.sh, and hetzner.sh cloud_exec functions -- matching the existing fix in digitalocean.sh (OpenRouterTeam#2528). Also add a validated _encode_b64 helper to soak.sh and use it for all Telegram bot token encoding, preventing corrupted base64 from breaking out of single-quoted SSH command strings. Closes OpenRouterTeam#2527 Agent: security-auditor Co-authored-by: B <6723574+louisgv@users.noreply.github.com> Co-authored-by: Claude Sonnet 4.5 <noreply@anthropic.com>
…terTeam#2530) The identical generateCsrfState() helper existed in both digitalocean/digitalocean.ts and shared/oauth.ts. Export it from oauth.ts (which digitalocean.ts already imports) and remove the duplicate copy. Co-authored-by: spawn-qa-bot <qa@openrouter.ai> Co-authored-by: Claude Sonnet 4.6 <noreply@anthropic.com> Co-authored-by: L <6723574+louisgv@users.noreply.github.com>
Consolidate 8 fragmented pipe-to-bash/sh tests in validatePrompt into 2 data-driven tests covering all inputs (with/without whitespace, complex pipelines, and standalone word acceptance). Merge 3 backtick tests into 1. Merge 2 whitespace tests into 1. Removes 19 lines of duplicate test setup. Co-authored-by: spawn-qa-bot <qa@openrouter.ai> Co-authored-by: Claude Sonnet 4.6 <noreply@anthropic.com> Co-authored-by: L <6723574+louisgv@users.noreply.github.com>
…penRouterTeam#2533) - Add null-byte rejection to shellQuote (defense-in-depth) - Export shellQuote for testability - Refactor interactiveSession to use shellQuote instead of inline escaping - Add comprehensive test suite for shellQuote security properties Fixes OpenRouterTeam#2529 Agent: security-auditor Co-authored-by: B <6723574+louisgv@users.noreply.github.com> Co-authored-by: Claude Sonnet 4.5 <noreply@anthropic.com>
Consolidate 9 per-credential-type it() blocks in prompt-file-security.test.ts into a single data-driven test covering all 17 sensitive path patterns. Merge 2 validatePromptFileStats "accept" tests into one. Consolidate 4 unicode/encoding-attack it() blocks in security.test.ts into a single data-driven test. Merge 3 "accept identifier" it() blocks into one. Removes 19 redundant tests (1400 → 1381) with no loss of coverage. Co-authored-by: spawn-qa-bot <qa@openrouter.ai> Co-authored-by: Claude Sonnet 4.6 <noreply@anthropic.com>
…OpenRouterTeam#2535) PR OpenRouterTeam#2533 hardened GCP with shellQuote() and null-byte rejection, but left Hetzner, DigitalOcean, AWS, and connect.ts using inline .replace(/'/g, "'\\''") without null-byte validation. - Move shellQuote to shared/ui.ts as the single source of truth - Add null-byte validation to runServer in Hetzner, DO, and AWS - Replace inline shell escaping with shellQuote in interactiveSession across all clouds, connect.ts, and agents.ts buildEnvBlock - Re-export shellQuote from gcp.ts for backwards compatibility Agent: security-auditor Co-authored-by: B <6723574+louisgv@users.noreply.github.com> Co-authored-by: Claude Sonnet 4.5 <noreply@anthropic.com>
…eam#2536) Three root-cause bugs in input test functions: 1. Stdin pass-through broken: cloud_exec uses "printf '...' | base64 -d | bash" on the remote, meaning bash reads the script from its own stdin — not the outer process's stdin. "PROMPT=$(base64 -d)" inside the script was reading from the already-consumed pipe, always producing an empty prompt. Fix: embed the base64-encoded prompt directly in the remote command string. Base64 output is [A-Za-z0-9+/=] only — safe to embed in single-quoted strings. 2. Zeroclaw flag wrong: "zeroclaw agent -p" was passing the prompt as --provider (not --prompt). The correct flag for non-interactive single-message mode is "-m"/"--message". 3. Codex model stale: "openai/gpt-5-codex" does not exist on OpenRouter. Updated to "openai/gpt-5.1-codex" which is available. Co-authored-by: spawn-qa-bot <qa@openrouter.ai> Co-authored-by: Claude Sonnet 4.6 <noreply@anthropic.com>
* security: add DO_CLIENT_SECRET env var override Allows users/organizations to supply their own DigitalOcean OAuth client secret via DO_CLIENT_SECRET env var rather than relying on the bundled default. The bundled secret remains as fallback. Fixes OpenRouterTeam#2537 Agent: security-auditor Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com> * chore: bump CLI version to 0.16.19 Agent: security-auditor Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com> --------- Co-authored-by: B <6723574+louisgv@users.noreply.github.com> Co-authored-by: Claude Sonnet 4.5 <noreply@anthropic.com>
Remove redundant existsSync check inside icon-integrity "is actual PNG data" tests — the file existence is already verified in the preceding test, and isPng() will throw if the file is missing. Remove the "should detect multiple dangerous patterns" test from validatePrompt — it retests the same $(…), backtick, ; rm, and |bash/sh patterns that each have their own dedicated it() block immediately above. Fix misleading test description: "should accept scripts with comments containing dangerous patterns" — the test actually expects a throw (documented as a known trade-off). Rename to "should reject…". Removes 1 test (1381 → 1380) and 18 expect() calls. Co-authored-by: spawn-qa-bot <qa@openrouter.ai> Co-authored-by: Claude Sonnet 4.6 <noreply@anthropic.com>
The `openclaw config set` calls for browser and Telegram settings were re-serializing openclaw.json and dropping the gateway.auth.token field, causing the dashboard to show "Unauthorized" when auto-opened via tunnel. Now all config (gateway auth, browser, channels) is built as a single JSON object and written once via uploadConfigFile. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Adds 40 new tests across 2 files: openclaw-config.test.ts (30 tests): - Gateway auth token written correctly and matches browserUrl - Atomic config write (no `openclaw config set` commands) - Browser config gated by enabledSteps - Telegram bot token included/omitted based on input - USER.md messaging channel content - Tunnel config targeting port 18791 orchestrate-messaging.test.ts (10 tests): - SPAWN_ENABLED_STEPS parsing and threading - WhatsApp QR scan session triggered before agent launch - GitHub auth gated by enabledSteps - preLaunchMsg output behavior Also adds SPAWN_TELEGRAM_BOT_TOKEN env var override for non-interactive/CI Telegram setup (avoids prompt in tests). Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Junie was added as a fully implemented agent (manifest, agent scripts, agent-setup.ts) but the packer/tarball pipeline was never updated. This meant the nightly agent-tarballs workflow could not build a pre-built tarball for Junie, forcing all deployments to do a live npm install. - Add junie entry to packer/agents.json (tier: node, @jetbrains/junie-cli) - Add junie to capture-agent.sh allowlist and path-capture case (npm-based, same as codex/kilocode — captures /root/.npm-global/) Agent: code-health Co-authored-by: B <6723574+louisgv@users.noreply.github.com> Co-authored-by: Claude Sonnet 4.5 <noreply@anthropic.com>
…penRouterTeam#2543) Adds --model / -m CLI flag to override the agent's default LLM model: spawn codex gcp --model openai/gpt-5.3-codex Also supports persistent per-agent model preferences via config file at ~/.config/spawn/preferences.json: { "models": { "codex": "openai/gpt-5.3-codex" } } Priority: --model flag > preferences file > agent default. This enables a future web UI to pass model selection via CLI args when invoking spawn programmatically to provision machines. Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com> Co-authored-by: L <6723574+louisgv@users.noreply.github.com>
…reference (OpenRouterTeam#2540) The previous PR (OpenRouterTeam#2536) set the Codex default to gpt-5.1-codex, but the latest available on OpenRouter is gpt-5.3-codex. Also adds a rules file documenting each agent's default model to prevent future regressions. Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com> Co-authored-by: L <6723574+louisgv@users.noreply.github.com>
… defense (OpenRouterTeam#2546) Agent: code-health Co-authored-by: B <6723574+louisgv@users.noreply.github.com> Co-authored-by: Claude Sonnet 4.5 <noreply@anthropic.com>
…Team#2547) - soak.sh: SOAK_CLOUD env var makes cloud configurable (default: sprite) - qa.sh: load TELEGRAM_BOT_TOKEN, TELEGRAM_TEST_CHAT_ID, SOAK_CLOUD from /etc/spawn-qa-auth.env in soak mode - qa.yml: add weekly Monday 3am UTC scheduled soak trigger - fix: bun eval → bun -e across soak.sh, key-request.sh, github-auth.sh (bun eval is not a valid subcommand in bun 1.3.9) - fix: export _TOKEN via env prefix so process.env._TOKEN works in bun -e - docs: update shell-scripts.md rule to say bun -e (not bun eval) Verified: 3/4 Telegram tests pass in smoke test on DigitalOcean (120s wait) getMe ✓ sendMessage ✓ getWebhookInfo ✓; cron test needs full 55-min window. Co-authored-by: spawn-qa-bot <qa@openrouter.ai> Co-authored-by: Claude Sonnet 4.6 <noreply@anthropic.com>
…ents (OpenRouterTeam#2548) Set every agent's featured_cloud to ["digitalocean", "sprite"] — one primary recommendation (DigitalOcean) and one fallback (Sprite). Co-authored-by: Claude <claude@anthropic.com> Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com> Co-authored-by: L <6723574+louisgv@users.noreply.github.com>
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Add hint to GitHub CLI setup option ("install gh + authenticate on the
remote server") and show keybinding instructions in the multiselect
prompt message.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
1 task
Collaborator
Author
|
Closing — created in error. |
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.
Summary
Depends on #2523 (feat/messaging-setup).
Test plan
spawnand verify all setup options show hint text🤖 Generated with Claude Code