Skip to content

Deep links

Open Claude Code in the right repository with a pre-filled prompt from a claude-cli:// URL in a runbook, alert, dashboard or shell script.

A deep link is a claude-cli:// URL. Clicking one opens a new terminal window running Claude Code, optionally in a chosen directory, with a prompt already typed into the input box. Nothing is sent until the person clicking reads it and presses Enter.

Because it is just a URL, you can put a starting point for a task wherever links go:

  • An incident runbook step that opens the affected service with a diagnosis prompt.
  • A Grafana or Datadog panel that links to "investigate this metric".
  • An onboarding wiki page that opens the project with a "give me a tour" prompt.
  • A CI failure message that names the broken job in the prompt.

What happens when you click

claude-cli:// is a custom URL scheme that Claude Code registers with the operating system, in the same way mailto: is tied to your mail client. On click:

  1. The browser or app hands the URL to the OS.
  2. The OS recognises the scheme and launches Claude Code locally.
  3. A new terminal window opens in the requested directory with the prompt pre-filled.
  4. You review, edit if you like, and press Enter.

The link can live anywhere, but the session always runs on the machine where it was clicked. The page showing the link must allow custom URL schemes (GitHub does not; see troubleshooting).

Safety

A deep link cannot run anything by itself. It only picks a folder and fills the prompt box, so even a link from an untrusted page does nothing until you press Enter.

When a session opens from a link, a warning under the input reads Prompt from an external link until you send or clear it. For prompts longer than 1,000 characters the warning adds the character count and tells you to scroll through the whole thing, since long text can hide instructions off screen. Permission rules, CLAUDE.md and the folder trust prompt all apply as normal.

Every link starts with claude-cli://open. On its own that opens Claude Code in your home directory with an empty prompt. Paste it into a browser address bar to test.

ParameterPurposeRules
qPrompt text to pre-fillURL-encode it; %0A for a new line; up to 5,000 characters
cwdWorking directoryAbsolute path. Rejected if it is a network or UNC path, contains .. segments, or contains invisible or bidirectional control characters
repoGitHub owner/name slugResolved to a local clone Claude Code has seen; falls back to your home directory if none

If you pass both cwd and repo, cwd wins and repo is ignored, even when the cwd path does not exist.

A worked example for a hypothetical northwind/billing-api repo with a two-line prompt:

claude-cli://open?repo=northwind/billing-api&q=Invoices%20for%20EU%20customers%20show%20the%20wrong%20VAT%20rate.%0AFind%20where%20the%20rate%20is%20chosen%20and%20list%20recent%20changes%20to%20it.

Clicking opens the local clone of northwind/billing-api with this in the prompt box:

Invoices for EU customers show the wrong VAT rate.
Find where the rate is chosen and list recent changes to it.

To encode your own prompt, run it through encodeURIComponent in a browser console, or in a shell:

python3 -c 'import urllib.parse,sys; print(urllib.parse.quote(sys.argv[1]))' "Summarise yesterday's failed jobs"

cwd or repo?

  • cwd when everyone has the project at the same absolute path, for example a standard dev container or VM image.
  • repo for links shared across a team where people clone to different places.

How repo resolves: every time you run claude inside a Git repository, Claude Code records that directory against the repository's GitHub slug, tracking clones and worktrees separately. The link opens the clone or worktree where you most recently ran claude. It does not switch branches; you get whatever is checked out there. The welcome header shows which path was chosen so you can confirm it.

Examples

In a runbook

## Checkout latency above 2s

1. Check the status page and acknowledge the alert.
2. [Start Claude Code in the checkout service](claude-cli://open?repo=northwind/checkout&q=p95%20checkout%20latency%20is%20over%202s.%20Look%20at%20deploys%20in%20the%20last%20hour%2C%20slow%20query%20logs%20and%20any%20open%20incidents.)
3. Post findings in the incident channel.

Anyone with Claude Code and a local clone can click step 2 and start with a ready-made prompt. Remember the hosting platform must allow the scheme: GitHub-rendered Markdown (READMEs, issues, PRs, wikis) does not. Confluence, Notion and most internal tools I have tried render it fine, but check yours.

From a shell or script

Use the OS's URL opener. This relies on the handler being registered (see below).

OSCommand
macOSopen "claude-cli://open?repo=northwind/checkout&q=triage%20open%20PRs"
Linuxxdg-open "claude-cli://open?repo=northwind/checkout&q=triage%20open%20PRs"
Windows PowerShellStart-Process "claude-cli://open?repo=northwind/checkout&q=triage%20open%20PRs"
Windows cmd.exestart "" "claude-cli://open?repo=northwind/checkout&q=triage%20open%20PRs"

In cmd.exe the empty "" matters: start treats its first quoted argument as a window title.

I keep a shell function that turns a failing CI job name into a link, so a notification bot can post "open in Claude Code" alongside each failure.

Handler registration

Claude Code registers the handler on macOS, Linux and Windows the first time you send a prompt in an interactive session. Launching and quitting without sending anything does not register it, and there is no separate install step. Everything is written at user level:

OSLocation
macOS~/Applications/Claude Code URL Handler.app
Linuxclaude-code-url-handler.desktop in $XDG_DATA_HOME/applications (default ~/.local/share/applications)
WindowsHKEY_CURRENT_USER\Software\Classes\claude-cli

Which terminal opens:

  • macOS: the terminal from your most recent interactive session. Supported: iTerm2, Ghostty, kitty, Alacritty, WezTerm and Terminal.app.
  • Linux: $TERMINAL, then x-terminal-emulator, then a list of common emulators.
  • Windows: Windows Terminal, then PowerShell, then cmd.exe.

To stop registration, set disableDeepLinkRegistration to "disable" in settings.json. Put it in managed settings to enforce it for an organisation. It only covers claude-cli:// links. See the settings reference.

  • VS Code: the extension registers vscode://anthropic.claude-code/open, which opens a Claude Code editor tab instead of a terminal. Parameters are covered in VS Code.
  • Desktop app: Claude Desktop handles its own claude:// links, including opening a session on a remote machine over SSH. See Desktop.

Troubleshooting

Nothing happens on click. The handler is probably not registered. Start claude interactively, send any prompt, quit and try again. On Linux without a desktop environment, xdg-open may have nothing to hand the URL to.

xdg-open not found. It ships in xdg-utils, which minimal images, containers and WSL often omit. Install it (sudo apt install xdg-utils on Debian/Ubuntu). If it then runs but nothing opens, see the previous point.

The link shows as plain text. Some Markdown renderers only allow http and https. GitHub turns [label](claude-cli://...) into just label with the URL stripped. On those platforms put the URL in a code block so readers can copy it into their address bar.

It opened my home directory, not the repo. repo only resolves to clones Claude Code has seen. Run claude once inside the clone, or use cwd with an absolute path.

Wrong terminal. On macOS, start claude once in the terminal you want. On Linux set $TERMINAL. On Windows the order is fixed, so install Windows Terminal if you want links to land there.

Tip: Long runbook prompts make ugly URLs. Store the procedure as a skill in the repository and keep the link's q short, for example q=%2Fincident-triage%20checkout.