Launch targets

September 16, 2026 · View on GitHub

This document defines how edgee launch <target> names are chosen and how they relate to credentials, transport, and the hidden edgee relay command.

Read this before adding a new agent.

Why the catalogue matters

Wrapping the agent itself — with no code change on the user's side — is Edgee's core differentiator against app-oriented gateways. Every target added here widens the surface Edgee can route, meter, and govern. The catalogue below is also the foundation the upcoming desktop app builds on: it will wrap the whole local AI stack, CLI agents and desktop apps alike, from these same definitions.

So target names are long-lived public API. Renaming one breaks user aliases, desktop wrappers, scripts, and docs at once. Get the name right the first time.

Three layers (do not conflate them)

LayerWhat it isExamples
Launch targetPublic CLI name (edgee launch …)claude, cursor, copilot-vscode, claude-desktop, later copilot
Provider keyEdgee credentials / console API key slotclaude, claude_desktop, cursor, copilot
TransportHow traffic reaches the gatewayCLI env-injection, MITM relay, …

Users only see launch targets. Transport stays an implementation detail (edgee relay remains hide = true). Several targets may share one provider key (e.g. copilot-vscode today and future copilot CLI → provider copilot). Surfaces may instead be split into their own backend agent when their usage should be metered separately: claude-desktop is a dedicated claude_desktop agent (own key + compression), distinct from claude (Claude Code).

Naming convention

1. Bare name = primary surface

Usually the official CLI of that product:

claude | codex | opencode | codebuddy | crush | pi | omp | kimi | kilo | copilot | …

Reserve the bare product name for the CLI even if the CLI ships later. If only an IDE/app surface exists today, use a suffixed name (see below) so the bare name stays free.

Exception: copilot-cli deliberately breaks this rule — see its section for why. Bare copilot stays unclaimed rather than pointing at it.

2. Suffixed name = another surface of the same product

Pattern: <product>-<surface>

copilot-vscode
claude-desktop
claude-vscode
codex-desktop

Do not overload the bare name with flags (edgee launch claude --desktop). Each surface gets its own subcommand so help, scripts, and aliases stay obvious.

3. Distinct product = distinct bare name

When the product is not “another skin” of an existing CLI:

cursor     # Cursor IDE (no separate CLI target yet)

Avoid ambiguous host-only names like bare vscode as a canonical target — VS Code can host Copilot, Claude Code, etc. Prefer copilot-vscode, and later claude-vscode, not a single vscode catch-all.

Exception: intellij is the chosen public target for IntelliJ IDEA. It currently routes the GitHub Copilot plugin, shares the copilot provider key, and does not imply support for other AI plugins in the IDE.

4. Aliases are optional discoverability only

Aliases may exist for muscle memory (vscode-copilotcopilot-vscode) but the canonical name in docs, README tables, and new code is the one above.

Do not alias a reserved bare CLI name (copilot) to a suffixed surface.

Current catalogue

CLI agents (env → gateway)

TargetProductProvider key
claudeClaude Code CLIclaude
codexCodex CLIcodex
opencodeOpenCode CLIopencode
codebuddyCodeBuddy CLIcodebuddy
crushCrush CLIcrush
piPi CLIpi
ompOh My Pi CLIpi
kimiKimi Code CLIkimi
kiloKilo Code CLIkilo

Apps & editors (relay today)

TargetProductProvider keyNotes
cursorCursor IDEcursorRelays the cursor binary
intellijGitHub Copilot in IntelliJ IDEAcopilotDirect IDE launch with proxy env + Node CA; live-session validation pending
copilot-vscodeGitHub Copilot in VS CodecopilotRelays code; aliases: vscode-copilot, vscode, code
copilot-desktopGitHub Copilot app (macOS, local sessions)copilotDirect app-bundle launch; proxy env + dedicated system-trusted Copilot CA
copilot-cliGitHub Copilot CLIcopilotRelays the copilot binary directly (TUI, no --wait) — deliberately not env-injected; see below
claude-desktopClaude Desktop (Claude Code only)claude_desktopLaunches the Claude app bundle behind the relay; dedicated agent (own key + Claude compression flavor), not shared with claude (Claude Code). Routes api.anthropic.com/v1/messages; the app's own chat goes to claude.ai and is not covered — see below
codex-desktopChatGPT desktop app (Codex tab only)codexNo relay. Its backend is a bundled codex app-server reading $CODEX_HOME/config.toml; the Edgee provider is written there, the app is launched, and the file is restored when the app quits. See below.

Desktop chat apps route the coding surface, not the chat surface

Both vendor desktop apps ship two things: a coding agent that speaks the public API, and a chat client that speaks the vendor's consumer web backend. Edgee routes the first and cannot see the second. This is one pattern, not two bugs, and it is worth checking for on any future app target.

TargetRoutedNot routedWhy
claude-desktopClaude Code → api.anthropic.com/v1/messagesthe app's chat → claude.ai/api/organizations/{org}/chat_conversations/{uuid}/completionclaude.ai is absent from INFERENCE_HOSTS, and the System-keychain CA is name-constrained to anthropic.com
codex-desktopCodex tab → config.toml model_providerChatGPT tab → chatgpt.com/backend-api/f/conversationthe ChatGPT tab never enters codex app-server, so no config surface reaches it

Both verified by packet capture on 2026-08-26. In each case a full chat exchange produced zero requests on the routed path.

Neither is a host-list edit away from working:

  • claude-desktop would need the CA widened from anthropic.com to cover claude.ai. That CA is a persistent, machine-wide trust root, deliberately constrained so that a leak could vouch for nothing else. claude.ai hosts the user's entire Claude web session. Security decision, not configuration.
  • codex-desktop would need a relay plus gateway support for the ChatGPT thread protocol, and re-originates a session guarded by sentinel/heartbeat and device attestation.

What the two chat surfaces report differs, and it matters for what is even worth building. Neither reports token counts — Claude Desktop uses the standard Anthropic SSE envelope with usage stripped out. But Claude's message_limit event carries authoritative quota utilization per 5-hour and 7-day window on every turn, whereas the ChatGPT tab exposes only feature quotas (deep_research, image_gen). If chat routing is ever revisited, Claude Desktop is the stronger candidate.

Keep the surface limit in the launch hints (print_claude_desktop_hint, codex_desktop::print_launch_hint). Without it, "launching the app through Edgee" reads as covering the whole app — which is exactly how this was first reported as a bug.

codex-desktop — config patch, not relay

The ChatGPT desktop app embeds Codex (ChatGPT.app/Contents/Resources/codex, launched as app-server over stdio) and honors base_url + http_headers from a model_providers entry — the very settings launch codex passes as -c overrides. So this target needs no proxy, no MITM CA and no system-keychain trust.

Scope: the Codex tab, not the whole app

The app's ChatGPT tab is out of reach of this mechanism and always will be. It is the ChatGPT web client running in the app's bundled Chromium: it POSTs chatgpt.com/backend-api/f/conversation from Chromium's own network stack and never enters codex app-server, so it never reads config.toml and model_provider cannot route it. Those turns bill OpenAI directly and are invisible to Edgee.

Established by packet capture (2026-08-26, codex 0.147.0 / Codex Desktop 0.149.0-alpha.4.3). Over 37 minutes spanning a complete ChatGPT-tab exchange, the app-server sent the gateway nothing but its 3-minute GET /v1/models poll — no POST /v1/responses — and wrote no sessions/**/rollout-*.jsonl, which it does for every conversation it actually runs. A Codex-tab turn in the same session produced both, with model_provider = edgee-cli.

Do not try to fix this with a wider config patch; there is no config surface to patch. Routing it would take a relay MITM'ing chatgpt.com, and two things make that a product decision rather than a port of claude-desktop:

  • Different wire format. f/conversation is the ChatGPT thread protocol (conversation_id / parent_message_id, server-held state), not the Responses API, so it cannot simply be added to REROUTE_MAP in relay/handler.rs — the gateway would have to speak it and translate both directions.
  • Anti-automation. A single ChatGPT-tab turn carries POST /backend-api/sentinel/heartbeat and GET /backend-api/ios/attestation_challenge. The Codex tab's /backend-api/codex/responses path carries neither. Rewriting or re-originating those requests is what that machinery exists to detect, and the exposure lands on the user's ChatGPT account.

print_launch_hint states the limitation at launch. Keep it there: without it, "launching the ChatGPT desktop app through Edgee" reads as covering the whole app, which is exactly how this got reported as a bug.

Three constraints are load-bearing, each established empirically:

  • The config file is the only lever. The app supplies its own argv (-c features.code_mode_host=true app-server), so -c injection is impossible. --profile <name> is the design you'd want — it layers $CODEX_HOME/<name>.config.toml and never touches the user's config.toml — but it is argv-only: no CODEX_PROFILE env var exists, and the legacy profile = "…" config key is a fatal startup error in 0.147 ("no longer supported; use --profile"). If a future codex honors an env var for this, switch to it — it removes the only invasive part of this integration.
  • Never point CODEX_HOME at a private copy. It does propagate into the spawned child, but a second home means a second auth.json, and the ChatGPT OAuth refresh token is single-use/rotating — whichever copy refreshes first invalidates the other and the user must sign in again. Symlink/hardlink does not help either: codex removes and atomically replaces the file. And auth cannot come from the environment — CODEX_ACCESS_TOKEN is an agent-identity slot, so it would force API-key billing instead of the user's ChatGPT plan.
  • The app re-reads config.toml on every new conversation. The app-server builds a fresh Config per conversation rather than caching one at startup, so the patch has to stay in place for as long as the app runs. This was originally implemented the other way — patch, wait ~10s, revert — and only the first auto-opened conversation went through Edgee while every later tab silently billed OpenAI directly. ~/.codex/sessions/**/rollout-*.jsonl is the ground truth: each file's session_meta.model_provider is edgee-cli or openai, per conversation. Check it before changing this lifecycle again.

So the lifecycle is patch → spawn → supervise until the app quits → restore. Three consequences fall out of holding the patch that long:

  • The command runs as long as the app does. The terminal must stay open; the launch hint says so.
  • Ctrl-C restores and exits without killing the app. Killing an app the user is working in would be worse than degrading to direct OpenAI, so it warns instead that new tabs are no longer routed.
  • A bare codex CLI run is routed too, on the desktop key. edgee launch codex is unaffected — its -c overrides win over the config file.

A stranded patch (terminal closed, crash) is undone by the leftover-backup recovery at the top of run() on the next launch, so the invasive window is bounded even though it is no longer short.

The grace period is a timer, not a signal — we cannot observe codex reading the file. It polls so the single-instance handoff is caught early. If a cold start ever exceeded it, the app would read the reverted config and talk to OpenAI directly: no compression, no metering, nothing broken, but also no warning.

Restore is surgical, not a rollback: codex rewrites config.toml at runtime (project trust_levels, plugin state, [desktop] prefs), so the managed block is stripped from the current file rather than restoring the backup snapshot, which would discard the user's session. The backup remains for crash recovery and for the case where codex reserializes the file and drops our marker comments.

The gateway must match the app's User-Agent (Codex Desktop/…) case-insensitively for the Responses passthrough to fire; a case-sensitive starts_with("codex") sent every desktop request down the keyed pipeline, which authenticates from Authorization — the app's ChatGPT OAuth JWT — and 401'd.

opencode — Edgee provider or existing subscription

edgee launch opencode adds Edgee as a provider in a temporary merged config. OpenCode sends those requests directly to the gateway using the Edgee key.

The hidden edgee relay opencode path serves a different use case: it launches OpenCode with the user's config unchanged and proxies supported inference traffic through Edgee in passthrough mode. Existing provider credentials remain attached to the request, including a GitHub Copilot token selected through OpenCode. The relay uses the opencode Edgee key for agent attribution and also intercepts the Copilot inference and token-discovery hosts.

pi and omp — additive provider in each agent's own config

opencode and crush build a merged config in $TMPDIR and point the agent at it (OPENCODE_CONFIG, CRUSH_GLOBAL_CONFIG), so the user's files are never touched. Pi has no such lever, and the one that looks like it is a trap: PI_CODING_AGENT_DIR relocates the entire agent directory — models.json but also auth.json, settings.json, keybindings.json, sessions/, themes/, tools/, prompts/, bin/, plus extension, skill and plugin discovery. Pointing it at a temp dir launches pi with no history, no logins, no settings and none of the user's plugins. --models is not an alternative: it takes model patterns for Ctrl+P cycling, not a config path.

So pi writes into ~/.pi/agent/models.json, while omp writes into ~/.omp/agent/models.yml. Both use two managed keys: providers.edgee for Chat Completions and providers.edgee-anthropic for Anthropic Messages. Custom providers merge into pi's built-in catalog by provider + id, so the block is purely additive — nothing the user already had is overridden. That is what makes it safe to leave in place, and why there is no patch-and-revert dance like codex-desktop: this adds a provider rather than hijacking one the user depends on.

OMP is Pi-compatible and reuses the pi coding-agent key. Sessions therefore share Pi's backend attribution and settings rather than provisioning another key.

Three details are load-bearing:

  • Env references are $NAME, and this requires pi ≥ 0.79.4. That release deliberately reversed the syntax (upstream #5661): before it, the whole value was the variable name (bare EDGEE_API_KEY) and an unset variable fell through to the literal string; from it, bare uppercase values are literals and $NAME is the only env reference. The two spellings are mutually exclusive — each is an inert literal on the other side of that boundary — and both fail identically, with the gateway answering 401 because it was handed EDGEE_API_KEY or $EDGEE_API_KEY as a credential. Check the pi version first when debugging a 401 here.
  • The Edgee key is therefore never written to disk — the config stores the references $EDGEE_API_KEY / $EDGEE_SESSION_ID and launch supplies the values. This is strictly better than the OpenCode and Crush temp configs, which embed the key. The trade-off: a bare pi run sees the Edgee models but cannot authenticate them.
  • An empty gateway model list is fatal here, unlike for OpenCode. A pi custom provider is defined by its models, so registering one with none opens the session on "No models available". fetch_gateway_models is best-effort and returns empty on any failure (an unreachable gateway, e.g. a dev profile pointing at a localhost port with nothing on it), so launch bails before writing rather than leaving a dead provider in the user's config.
  • The catalog is split by ingress protocol. Models whose IDs start with anthropic/ use api = "anthropic-messages" with the gateway root as their base URL, so Pi appends /v1/messages and applies its native prompt caching. Every other model uses api = "openai-completions" with a /v1 base URL, so Pi appends /chat/completions. Gateway reroutes still work from either ingress.

Reasoning-capable models are declared with reasoning: true and a model-level thinkingLevelMap generated from the catalog. Unsupported Pi levels are set to null, so the picker hides and skips them; catalog none maps to Pi's off slot. On the Anthropic provider, compat.forceAdaptiveThinking is enabled: Pi sends thinking.type=adaptive plus the exact effort, and the gateway translates that canonical control for whichever provider ultimately serves the request.

kimi — the env-only channel Kimi Code leaves open

Kimi Code refuses to read provider credentials from the shell on purpose: api_key / base_url come from config.toml (or its [providers.<n>.env] sub-table), and export KIMI_API_KEY=… does nothing. So the lever every other CLI target uses is closed here — except for one documented exception, the KIMI_MODEL_* family, "an explicit channel that does read credentials from the shell".

Setting KIMI_MODEL_NAME makes kimi synthesize a provider and a model alias in memory, outranking default_model in config.toml and evaporating with the process. Four variables are all this target needs:

KIMI_MODEL_NAME=moonshotai/kimi-k2.7-code   # also the enable switch
KIMI_MODEL_API_KEY=<edgee key>
KIMI_MODEL_BASE_URL=https://api.edgee.ai    # no /v1 — the SDK appends it
KIMI_MODEL_PROVIDER_TYPE=anthropic

That makes kimi the cleanest CLI target after claude: nothing is written to the user's files, so there is no additive block to maintain (pi) and no patch-and-revert dance (codex-desktop), and a bare kimi run afterwards is completely unaffected.

Three details are load-bearing:

  • base_url takes no /v1. KIMI_MODEL_PROVIDER_TYPE=anthropic selects Kimi's Anthropic Messages implementation, which appends /v1/messages itself — the same rule as ANTHROPIC_BASE_URL for Claude Code and baseUrl for pi.
  • The Edgee key travels as the provider credential, not as x-edgee-api-key. The gateway resolves a key from x-api-key or Authorization: Bearer, and answers 401 to x-edgee-api-key on its own. KIMI_MODEL_API_KEY lands in the former, so it authenticates; there is nothing to add.
  • KIMI_MODEL_NAME is the enable switch, and a missing required variable is fatal. Kimi fails at startup rather than quietly falling back to Moonshot, so a half-configured launch is loud instead of silently unmetered.

Session attribution rides KIMI_CODE_CUSTOM_HEADERS

KIMI_MODEL_* carries no headers of its own, but Kimi Code 0.20.2 added KIMI_CODE_CUSTOM_HEADERS — one Name: Value per line, applied to outbound LLM requests. Same shape as ANTHROPIC_CUSTOM_HEADERS, so this target sends the full Edgee header set and sessions group in the console exactly as they do for Claude Code.

The variable was not in the docs site's environment-variables reference at the time of writing — only in the 0.20.2 release notes. Verified on the wire against a loopback server: x-edgee-api-key, x-edgee-session-id and x-edgee-repo all arrive on POST /v1/messages?beta=true, alongside the x-api-key that KIMI_MODEL_API_KEY produces. If a future release drops the variable, the fallback is an additive [providers.edgee] block with custom_headers in the user's config.toml, the way pi.rs writes models.json — but note custom_headers values take no $NAME env references, so the key would then sit on disk, and a per-launch session id in a shared file races between concurrent launches.

kilo — inline config, nothing written anywhere

The Kilo Code CLI is an OpenCode fork: same config schema, same lowercase tool names, same 32k OUTPUT_TOKEN_MAX clamp. So the obvious implementation is opencode.rs with KILO_CONFIG swapped in for OPENCODE_CONFIG.

Kilo has a better lever. KILO_CONFIG_CONTENT takes the config as an inline JSON string and sits near the top of the precedence chain:

remote well-known → ~/.config/kilo/kilo.json → KILO_CONFIG → ./kilo.json
  → .kilo/kilo.json → KILO_CONFIG_CONTENT → managed      (deep-merged, later wins)

Two things follow, neither available to the $TMPDIR targets:

  • The key never touches disk. opencode and crush write the Edgee key into a temp config and unlink it on exit; a crash in between leaves it on disk. Here it exists only in the child's environment.
  • Kilo does the merge. opencode.rs has to find and parse the user's opencode.json/.jsonc itself — that is what its JSONC stripper is for — so it can re-emit their settings alongside ours. KILO_CONFIG_CONTENT is merged over whatever the user already has, so this target emits one provider.edgee key and reads nothing. Sitting above the project layer also means a repo-local kilo.json cannot shadow the Edgee provider.

KILO_CONFIG_DIR is a trap, and an unusually well-disguised one: the configuration reference embedded in the binary calls it "appended to the search list", which would make it the natural home for delivered skills and agents. The binary resolves config: KILO_CONFIG_DIR ?? Hc.config — it replaces the global config root, hiding the user's own commands, agents and skills. Where the docs and the binary disagree, the binary wins.

Like opencode and crush, and unlike claude and codex, this target runs entirely on Edgee-supplied credentials — it does not redirect an agent the user already authenticated. kilo auth is left alone and unused on this path.

copilot-cli — relay, not env injection: the BYOK lever costs the user their plan

The obvious lever, COPILOT_PROVIDER_BASE_URL (+ COPILOT_PROVIDER_TYPE / COPILOT_PROVIDER_API_KEY / COPILOT_PROVIDER_HEADERS), is real and works — verified end to end against a loopback mock: it POSTs standard /v1/messages Anthropic-shaped requests carrying whatever headers COPILOT_PROVIDER_HEADERS sets. But per copilot help environment, setting it "uses this provider instead of GitHub Copilot's model routing. GitHub authentication is not required." That's the same trap as codex-desktop's ChatGPT tab, just in CLI form: the env-injection path doesn't meter the user's paid Copilot seat, it replaces it with a bare BYOK shell pointed at Edgee — architecturally identical to kimi/pi, not to claude/codex.

So this target relays instead, following copilot-vscode (they share the copilot provider key and both MITM COPILOT_ONLY_HOSTSgithubcopilot.com + api.github.com). That's also why it's named copilot-cli rather than bare copilot, breaking rule 1's "reserve the bare name for the primary CLI": its transport and passthrough semantics pair it with copilot-vscode as another surface of the same product, not with the direct-env-injection CLIs (claude, codex, kimi, …). Bare copilot stays unclaimed.

Two things made relay viable here, verified directly against the installed @github/copilot 1.0.83 binary (no real GitHub account available, so the verification stops at the transport layer — TLS trust and proxying — not the full authenticated request/response cycle):

  • Native (non-BYOK) traffic honors HTTPS_PROXY. With a well-formed but invalid fine-grained PAT (GITHUB_TOKEN=github_pat_…), the CLI issued CONNECT api.github.com:443 straight through a logging proxy before failing on the token check — confirming the standard proxy env is read before GitHub auth is attempted, not bypassed by some hardcoded transport.
  • It honors NODE_EXTRA_CA_CERTS. A BYOK request pointed at a local HTTPS mock signed by a throwaway CA failed TLS verification until NODE_EXTRA_CA_CERTS was set to that CA's cert, then succeeded — the same mechanism claude, copilot-vscode, and cursor already rely on for relay MITM trust (see spawn_agent). Native model requests use a stricter platform verifier, so the dedicated, name-constrained Copilot CA is also installed in the macOS system keychain on first launch.

Net effect: edgee launch copilot-cli spawns copilot directly (TUI-style, no --wait, same as claude/codex) with the relay's proxy env and CA, and its real Copilot-billed traffic to githubcopilot.com/api.github.com reroutes through the gateway — preserving the user's actual GitHub Copilot subscription, which the BYOK lever cannot do.

Planned targets (same rules)

TargetProductLikely providerLikely transport
claude-vscodeClaude Code in VS CodeclaudeRelay or native config

Checklist for a new target

  1. Pick the canonical launch name with the rules above.
  2. Add src/commands/launch/<name>.rs (use underscores in the module file, hyphens in the clap name when needed — e.g. copilot_vscode.rscopilot-vscode).
  3. Register it under launch/mod.rs:
    • CLI targets first, then Apps & editors.
    • Set next_help_heading on the first variant of each group.
    • Keep about text product-clear (… CLI, … IDE, …).
  4. Map to the correct provider key in auth / credentials (may already exist).
  5. Choose transport:
    • CLI with base URL / headers → follow claude.rs / codex.rs.
    • App that cannot be pointed at the gateway → thin wrapper calling relay::run_for_agent("<canonical>") (see cursor.rs, copilot_vscode.rs).
  6. If relay: accept only the canonical name from launch; put legacy spellings in relay::canonicalize_target as aliases, not as new public targets. Never alias a reserved bare CLI name to an app surface.
  7. Update the root README.md supported-setups table.
  8. edgee alias covers both CLI and apps under one command:
    • CLI → PATH shims / shell aliases
    • Apps → desktop wrappers (macOS .app, Linux .desktop, Windows .lnk), only if the host app is already installed Register new app targets in commands/alias/desktop.rs (AppSpec + detection).

Anti-patterns

  • Exposing transport in the public UX (edgee launch foo --relay as the main path for apps that only work via relay — prefer a dedicated target that always relays).
  • Using the IDE host name as the only public target when multiple products share that host (vscode alone).
  • One subcommand with many surface flags (--desktop, --vscode, --cli).
  • Forcing launch target name == provider key when multiple surfaces share billing/pipeline.
  • Taking the bare product name for a non-CLI surface when a CLI is planned (copilot for VS Code).

copilot-desktop — local app sessions through the Copilot relay

macOS app 1.1.20 ships Copilot CLI 1.0.84-5. Launch GitHub Copilot.app/Contents/MacOS/github directly so proxy env and NODE_EXTRA_CA_CERTS reach that runtime. Native /responses traffic and a bash tool round trip were verified on 2026-09-14. The released app explicitly ignores COPILOT_CLI_PATH; BYOK replaces the user's subscription, so neither is used. The bundled CLI's native model client also uses the dedicated, name-constrained Copilot CA in the macOS system keychain.

This surface shares the established copilot key, settings and metering, as do copilot-cli and copilot-vscode. No new backend slug or gateway strategy is needed for this launcher. Its default port is 41600. App exit stops the relay; Ctrl-C closes the app before stopping the relay. Quit an existing app first to avoid singleton handoff.

Remote/cloud runtimes do not inherit local proxy settings. Plugin delivery remains unverified for all four component kinds and is reported as unsupported. Windows/Linux app paths and transport remain unverified; this launch target currently supports macOS only.

intellij — GitHub Copilot in IntelliJ IDEA

Quit IntelliJ IDEA completely, then run edgee launch intellij /path/to/project. The GitHub Copilot plugin must be installed and signed in. The launch shares Copilot credentials, settings and usage attribution with the other Copilot targets. It uses a separate local port (41700) so it can run alongside them.

The IDE executable inherits proxy environment variables and NODE_EXTRA_CA_CERTS, which GitHub documents for Copilot. An explicit IDE HTTP Proxy setting takes precedence; select No proxy in the IDE to let Copilot use the launch environment. Certificate verification remains enabled. No IDE configuration files or system trust stores are changed.

Standard macOS application bundles are detected in /Applications and ~/Applications; elsewhere the launcher must be on PATH (idea / idea.sh on Linux, idea64.exe / idea.exe on Windows). For Toolbox or custom installations, set EDGEE_INTELLIJ_BINARY to the executable path (on macOS, the app bundle's Contents/MacOS/idea, not the .app directory).

edgee alias intellij installs a desktop wrapper when the IDE is detected. Keep the launch command running for the session and quit the IDE before stopping Edgee. A launcher can hand off to an existing IDE and exit, so Edgee keeps serving until Ctrl-C. Live Copilot traffic still needs validation with an installed IDE; this target is experimental until then. Other AI plugins and remote/cloud agent sessions are outside this target's supported scope.