unpack · execute · debug
Any git ref, running locally in one command
Point uxd at a pull request, a branch, or a link someone pasted in chat. You get the code checked out, dependencies installed, and a port of your own — while the work you already have open stays exactly where it is.
Terminal
uxd my-project 42 code
uxd my-project 42 run dev
uxd my-project clean --merged
Every command is the same three steps
Learn it once and the whole tool is predictable. There is no special case to remember.
- resolve the refYou point at something — a pull request number, a branch, a commit, a link from chat. uxd works out what you meant.
- materialize the workspaceA folder appears with the code checked out, dependencies installed, your local files copied in, and a free port reserved. Ask again and you get the same folder back straight away.
- act on itOpen your editor, start the dev server, run a one-off command, or just print the path. Whatever you asked for, the workspace is ready before it runs.
Any ref you can name
If you can point at it, uxd can run it. No cloning, no stashing, no "let me finish what I'm doing first".
- Six kinds of refPull request numbers, branch names, commit hashes, GitHub links, local paths — and a dash when you mean the one you were just on.
- Paste the linkA GitHub link already says which project and which pull request. Paste it in and that is the entire command.
Six ways to name the same thing
uxd my-project 42 # pull request
uxd my-project feat/login # branch
uxd my-project 1a2b3c… # 40-char SHA
uxd my-project - shell # last used ref
uxd …/pull/42 code # straight from a URL
Run three at once, nothing collides
Three branches can run at the same time without fighting over a port, a node_modules, or a database file.
- A port of its ownEvery workspace gets its own free ports, and uxd hands them to your commands. Ask for two if your app needs an API alongside it.
- The files git never seesYour local env file, a certificate, a scratch config — copied into every new workspace, and never written over one you already have. How seeding works.
- Setup that remembersDependencies install on the first checkout and stay installed. uxd only runs them again when your lockfile actually changes.
~/.uxd/my-project.toml
ports = 2
[setup]
run = "pnpm install --frozen-lockfile"
cache_key = ["pnpm-lock.yaml"]
seed_files = [".env.local"]
[env]
PORT = "{port}"
API_PORT = "{port+1}"
Your commands know where they are
Paths, ports and your own variables are worked out before anything runs, so one command behaves correctly in every workspace.
- The details, handed overEverything uxd runs for you — setup, hooks, your dev server, a shell — is told the workspace's path, ports, branch and data directory. Anything you set yourself sits on top and wins.
- Write it once, with placeholdersDrop a placeholder for the port, the path or the branch into any command, environment value or hook, and uxd fills it in per workspace. Template variables.
- See it before you run itA dry run prints the exact environment and the exact command, then stops. Useful on the day something behaves differently than you expected.
From opened to cleaned up
A workspace has a lifespan. uxd covers all of it, and clears up after itself at the end.
- One word per intentOpen an editor, start a server, get a shell, read the diff. Each one sets the workspace up first, so there is no wrong order to do things in.
- See the whole boardOne list of everything you have open — the branch, the port, how old it is, and whether its pull request is still alive.
- Catch up without starting overPull a workspace back up to date with its branch. If you have uncommitted work, uxd stops and tells you, rather than quietly throwing it away.
- Room for your own stepsStart a container before the dev server, drop a scratch database on the way out, or block a removal that is not safe yet. Commands and hooks.
- Get the disk backClear out the workspaces whose pull requests have merged or closed. uxd shows you the list, asks before deleting, and skips anything with uncommitted work in it.
- Fine inside your own scriptsThe commands that produce data can print JSON instead, with progress kept out of the way — so you can wrap uxd without parsing around it. Script with uxd.
Runs on the stack you already have
No new runtime, no daemon, no account.
- Stock Node, plain gitNode 18 or newer and git 2.38 or newer. Install it with npm, pnpm or yarn — there is nothing else to add.
- GitHub's CLI, if you have itWith it you get pull request status, CI results, and true pull request diffs. Without it, everything else still works.
- One small file per projectYour commands, environment and hooks live in one readable text file, and uxd can check it for mistakes before you rely on it.
Try it on the next pull request you review
One setup command writes your config, scaffolds your first project, and tells you exactly what to run next.