Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
35 commits
Select commit Hold shift + click to select a range
3ff3d91
fix(translation): report cache writes in Chat Completions as cache_wr…
elyasmnvidian Oct 27, 2026
67f9887
chore(desktop): organize terminal actions by page and add review popups
elyasmnvidian Oct 23, 2026
568cd60
fix(desktop): use each source update review only once
elyasmnvidian Oct 27, 2026
3c1e737
feat(desktop): parse server routes and add the Routes table to the te…
elyasmnvidian Oct 23, 2026
56302ee
feat(desktop): show route details and endpoint status in the terminal…
elyasmnvidian Oct 27, 2026
237cadd
feat(desktop): fetch and cache upstream model lists from the terminal…
elyasmnvidian Oct 23, 2026
5daa6df
test(desktop): cover model-list key scoping, curl reaping, and error …
elyasmnvidian Oct 23, 2026
4acd4ff
feat(desktop): preview route target and algorithm edits in server con…
elyasmnvidian Oct 23, 2026
8cfe1b0
feat(desktop): edit route algorithms and models in the terminal app
elyasmnvidian Oct 23, 2026
a498165
feat(desktop): create, rename, duplicate, and delete routes in the te…
elyasmnvidian Oct 23, 2026
6b0916d
test(desktop): verify route editing preserves shared targets and backups
elyasmnvidian Oct 23, 2026
38fc6ed
test(desktop): verify route review tokens, staleness, and terminal ro…
elyasmnvidian Oct 23, 2026
d69fa21
feat(desktop): inspect harness settings and add the Harnesses page
elyasmnvidian Oct 23, 2026
7984c9a
feat(desktop): preview harness settings for Codex, Claude Code, and Pi
elyasmnvidian Oct 23, 2026
c046060
feat(desktop): install and restore reviewed harness settings
elyasmnvidian Oct 23, 2026
d50996a
feat(desktop): add named harness accounts to the Harnesses page
elyasmnvidian Oct 23, 2026
8856122
test(desktop): verify harness preview, install, and restore edge cases
elyasmnvidian Oct 23, 2026
bef6c7e
test(desktop): cover named accounts and the Windows terminal launcher
elyasmnvidian Oct 23, 2026
26c1ffe
feat(desktop): add the Sessions page and recorded session inventory (…
elyasmnvidian Oct 27, 2026
778120e
feat(desktop): open and clean up worktree sessions in the terminal app
elyasmnvidian Oct 23, 2026
8587c02
test(desktop): verify session launch reviews, cleanup, and account is…
elyasmnvidian Oct 27, 2026
de8f14c
feat(desktop): share usage overview rows and add appearance assets
elyasmnvidian Oct 23, 2026
00422a1
feat(desktop): add the desktop stylesheet, combobox, and ECharts anal…
elyasmnvidian Oct 26, 2026
dcffa92
feat(desktop): add the desktop app pages and route workspace (#1139)
elyasmnvidian Oct 26, 2026
f5c6d02
feat(desktop): add the tray usage popup
elyasmnvidian Oct 23, 2026
7bd9632
test(desktop): verify the desktop app frontend and route drafts (#1118)
elyasmnvidian Oct 27, 2026
d0e47ac
docs(desktop): add the desktop and terminal app quickstart (#1119)
elyasmnvidian Oct 27, 2026
d572c14
chore(desktop): remove remaining shell installers (#1120)
elyasmnvidian Oct 27, 2026
288e263
feat(desktop): record session launches and open harnesses in existing…
eric-liu-nvidia Oct 26, 2026
c092a86
feat(desktop): read harness transcripts for session hand-offs
eric-liu-nvidia Oct 26, 2026
c3bc260
feat(desktop): continue a session in another harness
eric-liu-nvidia Oct 26, 2026
ab6940b
feat(desktop): add a handoff subcommand that continues a session in t…
eric-liu-nvidia Oct 26, 2026
51f4606
feat(desktop): continue sessions with one click from the Sessions pag…
eric-liu-nvidia Oct 26, 2026
7ae89fd
feat(desktop): switch harness from one dropdown per harness on the Se…
eric-liu-nvidia Oct 27, 2026
7d980da
fix(desktop): keep the hand-off prompt out of Claude Code's --add-dir…
eric-liu-nvidia Oct 27, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
149 changes: 130 additions & 19 deletions INSTALLATION.md
Original file line number Diff line number Diff line change
Expand Up @@ -39,19 +39,83 @@ configuration reference.
## Desktop installer

From a source checkout, run `cargo desktop --help` for the commands and
`cargo desktop install --dry-run` to preview installation. This checkout has
the installer helper but does not yet build the desktop app executable, so
full installation cannot complete. Uninstall keeps settings, history, and
recovery copies.
`cargo desktop install --dry-run` to preview installation. Run
`cargo desktop install` to build and install the app and server.

The app opens setup on its first launch before creating app and server config files.
Existing app settings or a default server config skip setup, including after
reinstall. Settings lets you change the selected files or remove app preferences.
On Linux, open the installed app with `~/.switchyard/bin/switchyard-desktop --tui`.
See [Desktop setup](crates/switchyard-desktop/SETUP.md) for these steps.
Uninstall keeps settings, history, and recovery copies.

## Server Keys

In a server config, each LLM client and decision client names its API key
variable with `api_key_env`. A server you start from a terminal reads those
variables from your shell, as it always has. The installed server does not: on
macOS launchd starts it, on Linux systemd, and on Windows Task Scheduler. None
of them runs your shell, so the installed server never sees the variables that
`~/.zshrc` or `~/.bashrc` exports.

The installed server reads each key from the system credential store instead:
macOS Keychain, Windows Credential Manager, or the Linux Secret Service (GNOME
Keyring on Ubuntu and GNOME, KDE Wallet on Plasma). A key is saved under its
variable name, such as `NVIDIA_API_KEY`. Before each start, the installed
helper reads the keys that the config names and passes them to the server. A
saved key replaces any value the service manager passes. If a variable has no
saved key, the server does not start, and the server log names the variable.

To save, replace, or remove a key in the desktop app, open **Settings → Server
keys**. Type or paste the key, or choose **Import from shell** to read the
variable once from your login shell. From a terminal on macOS or Linux, run the
installed helper:

The installer requires the repository's Rust toolchain. macOS uses LaunchAgents;
Linux requires a systemd user session. Windows requires MSVC build tools,
WebView2, and a Task Scheduler user session.
```bash
~/.switchyard/bin/switchyard-desktop-install key status --config ~/.switchyard/composite.toml
~/.switchyard/bin/switchyard-desktop-install key set NVIDIA_API_KEY # prompts without echo
~/.switchyard/bin/switchyard-desktop-install key import NVIDIA_API_KEY # reads it from your login shell
~/.switchyard/bin/switchyard-desktop-install key remove NVIDIA_API_KEY
```

On Windows, run install and uninstall from the source checkout with Cargo.
The installed helper rejects changes to its own installation because Windows
locks running executables. The app's Update command uses a temporary helper
copy. The installed helper still supports `uninstall --dry-run`.
On Windows, the installer puts the helper in
`%LOCALAPPDATA%\Programs\Switchyard`. There `key set` reads the key from
standard input without a prompt, and `key import` reads the variable from your
Windows environment variables. From PowerShell:

```powershell
$helper = "$env:LOCALAPPDATA\Programs\Switchyard\switchyard-desktop-install.exe"
& $helper key status --config "$env:USERPROFILE\.switchyard\composite.toml"
[Net.NetworkCredential]::new('', (Read-Host 'Key' -AsSecureString)).Password | & $helper key set NVIDIA_API_KEY
& $helper key import NVIDIA_API_KEY
& $helper key remove NVIDIA_API_KEY
```

Restart the server after you change a key. If you rename a variable in
`api_key_env`, save a key under the new name. The old key stays saved until you
remove it in Keychain Access, Credential Manager, or Seahorse.

`cargo desktop install` never saves, reads, or changes a key, even when your
terminal sets the variable. It checks the config without keys, then lists each
variable that has no saved key. On a first install, the server starts after you
save those keys in **Settings → Server keys** and restart it. In the terminal
app, press `7` to open the Settings page. There `k` lists the variables that the
config names and whether each has a saved key, `s` saves a key, and `i` imports
it from your login shell. Press `b` and then `y` to restart the server.
Uninstalling keeps the saved keys, the config, and history. Switchyard never
writes keys to app settings, service definitions, or logs. Model-list keys that
you enter in Routes are stored separately.

On macOS, Keychain ties each key to the helper that saved it. Keychain treats a
rebuilt helper as a new program, so after `cargo desktop install` macOS may ask
once per key whether to allow `switchyard-desktop-install`. Choose **Always
Allow**.

On Linux, the login keyring must be unlocked. A desktop login normally unlocks
it. When the server service starts after login, it waits up to a minute for the
keyring to unlock. Over SSH without a desktop session, or with a window manager
that does not unlock the keyring, the server does not start and its log says
the keyring is locked.

## Linux Codex Service

Expand All @@ -63,13 +127,16 @@ port while the service is stopped and receive your login and prompts.
From a checkout, preview or install the service:

```bash
make install-linux-dry-run
make install-linux
cargo desktop install --dry-run
cargo desktop install
systemctl --user status switchyard
codex -p sy
```

The installer builds and installs `~/.switchyard/bin/switchyard-server`.
The installer builds and installs `~/.switchyard/bin/switchyard-server` and
`~/.switchyard/bin/switchyard-desktop`. Run the same command to reinstall from
the current checkout; update the checkout first to install newer code.
Run `~/.switchyard/bin/switchyard-desktop --tui` to open the terminal app.
It creates `~/.switchyard/composite.toml` if missing and keeps existing edits.
It replaces `~/.config/systemd/user/switchyard.service` and restarts the service.
It writes `~/.codex/sy.config.toml`, backing up a changed profile first.
Expand All @@ -79,20 +146,61 @@ The profile format requires [Codex 0.134.0 or newer](https://developers.openai.c
Remove any old `[profiles.sy]` table from `~/.codex/config.toml` before using it.

Set `SY_HOME` or `SY_PORT` to change the server directory or port (default 4123).
`SY_HOME` must not contain whitespace, control characters, or a trailing
backslash; `SY_PORT` must contain only digits. `XDG_CONFIG_HOME` and `CODEX_HOME`
`SY_HOME` must be an absolute UTF-8 path without ASCII control characters.
`SY_PORT` must be a number from 1 to 65535. `XDG_CONFIG_HOME` and `CODEX_HOME`
set the systemd and Codex config directories.

Read server logs with `journalctl --user -u switchyard`. Routing records are
stored in `~/.switchyard/routing.jsonl`. Use `systemctl --user edit switchyard`
for service changes that survive reinstalling.

Remove the service and profile with `make uninstall-linux`. This also removes
Remove the service and profile with `cargo desktop uninstall`. This also removes
marked Codex aliases left by older installs from existing `.bashrc` and
`.zshrc` files. If upgrading an older install, uninstall first and run
`unalias codex` in any open shell. The server directory, routing records,
profile backups, and systemd drop-in files stay in place. Use the same path
overrides when installing and uninstalling.
profile backups, and systemd drop-in files stay in place. Uninstall uses the
recorded installation. Conflicting environment overrides require
`cargo desktop uninstall --settings FILE` to select it explicitly.

## Windows Desktop App

From PowerShell in the repository, run:

```powershell
cargo desktop install --dry-run
cargo desktop install
```

Windows needs the Rust MSVC toolchain, Visual Studio C++ build tools, and
[WebView2](https://v2.tauri.app/start/prerequisites/#windows).
The installer uses Task Scheduler for the current logged-in user. It installs
executables in `%LOCALAPPDATA%\Programs\Switchyard`, falling back to
`%USERPROFILE%\AppData\Local\Programs\Switchyard` when `LOCALAPPDATA` is unset.
It saves that location and adds a Start menu shortcut. Two independent tasks
start the server and desktop app after login with ordinary user privileges.
Quitting the app leaves the server running.

Run `cargo desktop install` again to build and install the current checkout.
This Cargo command waits for installation to finish. The app's source update
uses the saved checkout and runs from a temporary Rust executable so Windows
can release and replace the installed files; read `SY_HOME\logs\update.log` for
its progress and errors. The installed installer cannot install, update, or
uninstall its own installation, because Windows keeps a running program from
being replaced. Use `cargo desktop` from the source checkout instead.
The installer builds and validates before stopping the tasks. If a binary
replacement fails, it tries to restore the previous binaries. If restoration
also fails, the error names the directory containing recovery files.
Rerun installation if a later task or settings operation fails; the complete
installation is not one transaction.

Settings, server config, accounts, and routing history stay in
`%USERPROFILE%\.switchyard` unless `SY_HOME` changes the directory. Server and app
logs are in `SY_HOME\logs`. Model-list keys entered in Routes are saved in the
current user's Windows Credential Manager. Coding tools keep their own login files.

Use `cargo desktop uninstall` to stop and remove both tasks, the shortcut, and
the installed executables. Uninstall preserves settings, accounts, and history,
and makes a recovery copy of the Codex profile before removing it.

## Rust Libraries

Expand Down Expand Up @@ -123,3 +231,6 @@ uv run pytest tests/ -v

The `dev` dependency group contains testing and linting tools and is not exposed
in the published wheel metadata.

See the [desktop and terminal quickstart](crates/switchyard-desktop/README.md) for
first-run setup, reviewed settings changes, usage, recovery, and safe uninstall.
22 changes: 0 additions & 22 deletions Makefile

This file was deleted.

3 changes: 3 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -99,6 +99,9 @@ The standalone server is provided only for demos and local evaluation. It is not

[Evaluate routing locally](docs/operations/local_evaluation.md) with the standalone server and your own model pool, then [verify routing is active](docs/operations/local_evaluation.md#verify-routing-is-active).

The [desktop and terminal quickstart](crates/switchyard-desktop/README.md) covers
local installation, coding-tool connections, sessions, usage, recovery, and uninstall.

Agent-specific guides are available for [pi](docs/integrations/pi.md) and
[Oh My Pi](docs/integrations/oh_my_pi.md).

Expand Down
2 changes: 1 addition & 1 deletion crates/switchyard-desktop/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -55,7 +55,7 @@ windows-sys = { version = "0.61", features = ["Win32_Foundation", "Win32_System_

[target.'cfg(any(target_os = "macos", windows))'.dependencies]
rfd = { version = "0.17", default-features = false }
tauri = { version = "2", features = ["tray-icon", "custom-protocol"] }
tauri = { version = "2", features = ["tray-icon", "custom-protocol", "macos-private-api"] }

[target.'cfg(any(target_os = "macos", windows))'.build-dependencies]
tauri-build = "2"
Expand Down
Loading
Loading