Interactive Mode (REPL)
Interactive mode is the default when you run yoyo in a terminal. It gives you a read-eval-print loop where you can have a multi-turn conversation with the agent.
Starting
yoyo
# or
cargo run
The prompt
The prompt shows your current git branch (if you're in a git repo):
main π βΊ _
If you're not in a git repo, you get a plain prompt:
π βΊ _
Line editing & history
yoyo uses rustyline for a full readline experience:
- Arrow keys: Navigate within the current line (β β) and through command history (β β)
- Inline hints: As you type a slash command, a dimmed suggestion appears after the cursor showing the completion and a short description β e.g. typing
/heshowslp β Show help for commands. Press Tab or β to accept. - Tab completion: Type
/and press Tab to see available slash commands with descriptions β each command is shown alongside a short summary of what it does. Partial matches work too β/he<Tab>suggests/helpand/health. After typing a command + space, argument-aware completions kick in:/model <Tab>β suggests known model names (Claude, GPT, Gemini, etc.)/provider <Tab>β suggests known provider names (anthropic, openai, google, etc.)/think <Tab>β suggests thinking levels (off, minimal, low, medium, high)/git <Tab>β suggests git subcommands (status, log, add, diff, branch, stash)/pr <Tab>β suggests PR subcommands (list, view, diff, comment, create, checkout)/save <Tab>and/load <Tab>β suggest.jsonsession files in the current directory- File paths also complete β type
src/ma<Tab>to getsrc/main.rs, orCargo<Tab>to getCargo.toml. Directories complete with a trailing/for easy continued navigation.
- History recall: Previous inputs are saved across sessions
- Keyboard shortcuts: Ctrl-A (start of line), Ctrl-E (end of line), Ctrl-K (kill to end), Ctrl-W (delete word back)
- History file: Stored at
$XDG_DATA_HOME/yoyo/history(defaults to~/.local/share/yoyo/history)
How it works
- You type a message
- yoyo sends it to the LLM along with conversation history
- The LLM may call tools (read files, run commands, etc.)
- Tool results are streamed back β you see each tool as it executes
- The final text response is printed
- Token usage and cost are shown after each turn
Auto-continue
If the model stops mid-work (e.g., it says "Next, I'll fix the tests..." but stops), yoyo automatically sends a follow-up prompt to continue. You'll see:
β‘ auto-continuing (1/3 β response appears incomplete)...
This happens up to 3 times per user turn. Auto-continue won't fire if:
- The model encountered an error
- The session budget is exhausted
- The response doesn't show clear signs of being incomplete
Shell passthrough
Prefix a line with ! to run a shell command directly β no API call, no tokens, no confirmation prompt:
π βΊ !git status
π βΊ !ls -la src/
Output streams live to your terminal (via sh -c on Unix, cmd /C on Windows), and the exit code is shown only when non-zero. A bare ! prints a usage hint.
!? β ask about the last command's output
! commands never enter the conversation, but sometimes you want yoyo to look at what just happened. Type !? to feed the last ! command β its command line, exit code, and output tail (last ~200 lines / 8KB, captured as a tee while it streamed) β into the conversation:
π βΊ !cargo test
... (output streams live) ...
exit 101
command failed (exit 101) β type !? to ask yoyo about the output
π βΊ !? why did the second test fail
- Bare
!?uses a default question: after a failure, "explain what went wrong and how to fix it"; after a success, "summarize this output". !? <question>asks your own question about the output.- Works after successful commands too (the failure hint just doesn't appear).
- If no
!command has run yet,!?prints a one-liner and does nothing. - The capture is non-consuming β you can ask
!?follow-ups about the same output more than once.
This is fully opt-in: nothing enters the conversation (and no tokens are spent) unless you type !?.
Tool output
When yoyo uses tools, you'll see status indicators:
βΆ $ cargo test β (2.1s)
βΆ read src/main.rs β (42ms)
βΆ edit src/lib.rs β (15ms)
βΆ $ cargo test β (1.8s)
βmeans the tool succeededβmeans the tool returned an error- The duration shows how long the tool took
Token usage
After each response, you'll see a compact token summary:
β³ 3.2s Β· 1523β842 tokens Β· $0.0234
Use --verbose (or -v) for the full breakdown including session totals and cache info.
This shows:
- Wall-clock time for the response
- Inputβoutput tokens for this turn
- Estimated cost for this turn
Interrupting
Press Ctrl+C to cancel the current response. The agent will stop and you can type a new prompt. Press Ctrl+C again to exit.
Completion notifications
When a prompt takes more than a few seconds, yoyo rings the terminal bell so you notice the finish even if you switched windows (disable with no_bell = true or --no-bell).
For an actionable desktop alert, set the opt-in notify_command config key β a shell command yoyo runs (fire-and-forget) whenever a long prompt finishes, at the same threshold as the bell:
# .yoyo.toml β Linux
notify_command = "notify-send 'yoyo' 'done'"
# macOS
notify_command = "osascript -e 'display notification \"done\" with title \"yoyo\"'"
Or set it from inside the REPL:
/config set notify_command notify-send 'yoyo' 'done'
Details:
- Opt-in and inert by default β when the key is absent (or empty), nothing is spawned and no tools are probed.
- Runs via
sh -con Unix andcmd /Con Windows, fully detached: yoyo never waits on it and its output is discarded, so it can never block the REPL. - The command receives two environment variables so one script can serve multiple purposes:
YOYO_EVENT=prompt_completedandYOYO_ELAPSED_SECS=<seconds>. - If the command fails to spawn, yoyo stays silent by default (one-line warning with
--verbose). - Setting it to an empty string clears it:
/config set notify_command "".
Inline @file mentions
You can reference files directly in your prompts using @path syntax. The file content is automatically read and injected into the conversation β no need for a separate /add command.
> explain @src/main.rs
β added src/main.rs (250 lines)
(1 file inlined from @mentions)
> refactor @src/cli.rs:50-100
β added src/cli.rs (lines 50-100) (51 lines)
(1 file inlined from @mentions)
> compare @Cargo.toml and @README.md
β added Cargo.toml (35 lines)
β added README.md (120 lines)
(2 files inlined from @mentions)
How it works:
@pathβ injects the entire file@path:start-endβ injects a specific line range- If the path doesn't exist, the
@mentionis left as-is (it might be a username) - Email-like patterns (
user@example.com) are not treated as file mentions - Images work too:
@screenshot.pnginlines the image into the conversation