Understanding the provider system
Emdash maintains a registry of CLI agents insrc/shared/providers/registry.ts. Each provider is defined using a ProviderDefinition object that describes:
- How to detect the agent on the user’s system
- How to spawn the agent’s CLI process
- How to pass initial prompts and flags
- Which API keys to pass through
Emdash currently supports 24 providers including Claude Code, Codex, Gemini, Qwen Code, Cursor, OpenCode, and many more.
Provider definition structure
Here’s the complete TypeScript interface:src/shared/providers/registry.ts
Key fields explained
Basic identification
id (required): Unique identifier for the provider (must be added to PROVIDER_IDS array)name (required): Display name shown in the UIicon: Filename of the provider’s icon (placed in src/renderer/assets/images/)docUrl: Link to the provider’s official documentationDetection and installation
commands: Array of command names to check for detection (e.g., ['claude'])versionArgs: Arguments to test command availability (e.g., ['--version'])detectable: Set to false to skip auto-detection (default: true)installCommand: Shell command users can run to install the agentCLI invocation
cli: Binary name to execute (often same as first command in commands array)defaultArgs: Arguments always passed when spawning (e.g., ['run', '-s'] for Goose)autoStartCommand: Alternative command to run instead of interactive CLI (e.g., Rovo Dev uses 'acli rovodev run')Prompt delivery
initialPromptFlag: CLI flag to pass the initial prompt (e.g., '-i' for Gemini, '-p' for Continue)useKeystrokeInjection: Set to true for agents with no prompt flag — Emdash will type the prompt into the TUI after startup (used by Amp, OpenCode)Auto-approval and session management
autoApproveFlag: Flag to skip interactive tool confirmations (e.g., '--dangerously-skip-permissions' for Claude, '--yolo' for Gemini)resumeFlag: Flag to resume previous session (e.g., '-c -r' for Claude, '--resume' for Continue)sessionIdFlag: Flag to assign a unique session ID per conversation (currently only Claude supports '--session-id')Adding a new provider: complete example
Let’s add a fictional agent called “DevBot” to the registry.Add provider ID to the registry
First, add the ID to the
PROVIDER_IDS array:src/shared/providers/registry.ts
Create the provider definition
Add the definition to the
PROVIDERS array:src/shared/providers/registry.ts
Add API keys to environment passthrough
If your agent requires API keys, add them to
AGENT_ENV_VARS in src/main/services/ptyManager.ts:src/main/services/ptyManager.ts
Real-world examples
Example 1: Claude Code (full-featured)
src/shared/providers/registry.ts
Example 2: Amp (keystroke injection)
src/shared/providers/registry.ts
Amp has no CLI flag for passing prompts, so
useKeystrokeInjection: true tells Emdash to type the prompt into the terminal after the agent starts.Example 3: Goose (custom default args)
src/shared/providers/registry.ts
Testing your provider
Verify detection
If the agent is installed on your system, Emdash should detect it automatically when you create a new task.Check the provider dropdown in the task creation modal.
Test task creation
- Create a new task
- Select your provider from the dropdown
- Enter an initial prompt
- Verify the agent launches successfully
Advanced: Session isolation (Claude only)
Claude Code is the only provider that currently supports session isolation via thesessionIdFlag.
When configured, Emdash:
- Generates a deterministic UUID from the conversation ID
- Passes it via
--session-idon startup - Persists the session mapping to
{userData}/pty-session-map.json - Uses the same ID when resuming with
-c -r
Troubleshooting
Provider not detected
Provider not detected
Ensure:
- The binary is in the system
PATH - The
commandsarray matches the actual binary name detectableis not set tofalse- The
versionArgscommand succeeds (e.g.,devbot --version)
API keys not available to agent
API keys not available to agent
Check that the key name is in
AGENT_ENV_VARS in src/main/services/ptyManager.ts.The key must also be set in the user’s shell environment.Initial prompt not delivered
Initial prompt not delivered
Verify:
initialPromptFlagmatches the agent’s CLI docs- If the agent has no prompt flag, set
useKeystrokeInjection: true - The prompt is properly escaped (Emdash handles this automatically)
Auto-approve not working
Auto-approve not working
Double-check the
autoApproveFlag value against the agent’s documentation. Flags vary widely:- Claude:
--dangerously-skip-permissions - Gemini:
--yolo - Cursor:
-f - Copilot:
--allow-all-tools
Next steps
- SSH connection setup — Run agents on remote machines
- Troubleshooting — Common issues and solutions
- Linear and Jira integration — Link tasks to issues