Skip to content

Web Interface ​

polyrepo ui starts a small web server on your own machine and opens a page in the browser. The page runs the same commands as the terminal, with forms, tables, reports and dialogs instead of flags and prompts: see every package and what is wrong with it at a glance, pick packages with checkboxes, watch a run stream in, answer its questions, and approve every change to your repos before it happens. Nothing leaves your machine.

bash
polyrepo ui
text
polyrepo ui is running at http://127.0.0.1:52144/?token=5f3c…
Press Ctrl+C to stop.

The browser opens at that address by itself. The menu on the left has five sections: Packages, Commands, Release, Runs and Settings.

Starting it ​

Run the command anywhere. It reads the same polyrepo.config.json as every other command (--config <path> before the command picks another one), so a folder set up with polyrepo setup works as it is. On a first start with no packages found, the Packages section offers a folder picker and shows which tools (git, npm, gh) were found.

By default the server picks a free port (--port <n> sets one) and listens on 127.0.0.1, so only this machine can reach it. --no-open only prints the address. Ctrl+C stops the server and any run still in progress.

The interface is part of the package, so there is nothing else to install. A command you start from the page runs exactly as it does in a terminal, in the same process rules: reads run in parallel, anything that changes a repo runs one repo at a time.

Safe by design ​

  • Only this machine. The server listens on 127.0.0.1. The address printed on start carries a one-time token: opening it sets a cookie, and every request after that must carry the cookie. A request with a foreign Host or Origin header is refused.
  • Changes need a confirmation. A command that changes repos, or an option that does (such as the branch clean-up of doctor), cannot be started without an explicit confirmation sent with the request. The page shows a summary first: the command, the packages and the options.
  • A preview is one click away. Every command with a dry run offers Preview (dry run) in the confirmation. A finished preview offers Run for real…, which opens the form again with the same settings.
  • Dangerous options say so. An option that discards work, such as throwing away local changes, is red, shows a warning as soon as you tick it, and is repeated in the confirmation.
  • Secrets are not kept. A one-time password typed for npm publish goes to the command and is never written to the run history; it is hidden in the printed command as well.

Packages ​

The overview of everything the config finds. Check packages runs list (the Quick box skips the network checks) and shows its table. The report is kept, so the page shows the last one with its age, and marks it as out of date after a quarter of an hour.

  • Needs attention counts the packages with a problem, each a filter you can click: local changes, off the main branch, not on npm or behind it, different from origin, stale dependencies.
  • Monorepos are blocks. A repo that holds several packages is one colored block with its own header, and the single repos are together in one block above. A header folds its block and selects all of its packages at once; the colors come from a range you choose in Settings.
  • Chips for status. Branch, git state, release, npm state and dependency drift are colored chips, so a problem stands out in a long list.
  • Sort, filter and select. Click a column to sort it, type to filter, tick packages and use Select all or Unselect. With a filter on, Select all takes only the rows that match.
  • Actions on the selection. Bump, Publish, Tag, Sync deps, Switch branch and Run command open that command's form with the selected packages already ticked. Release… opens the wizard.

The page shows the age of the report and not a live view on purpose: a full check goes to the network for every package, so it runs when you press the button. After a command that changes repos, only the packages it touched are refreshed in the background (see The packages stay current).

Commands ​

Every command of the CLI has a form: Packages, Outdated dependencies, Security audit, Open pull requests and Doctor under Inspect; Switch to default branch, Sync local dependency ranges, Commit changes, Run a command and Clone missing repos under Sync; Bump version, Publish to npm, Tag current version and Create releases under Release. The cards are colored by group and show which commands change things.

A form has the options of the command first (the same as the flags, with the same defaults) and the packages below. Where the command takes packages, the list is the same everywhere:

  • Grouped like the overview. Single repos in one block, every monorepo in its own colored block with a header that selects the whole block.
  • Useful columns. The current branch (yellow when it is not master or main), whether the repo has local changes, and the version.
  • Filters. A text filter, Only with local changes and Hide private.
  • Refresh. The Refresh button above the list rereads the branches, the git state and the versions without reloading the page; the ticked packages stay ticked.
  • Where the package stands on npm. In the Publish form and the Release wizard the version splits into Local and On npm. The npm number is green when it matches the local one, yellow and bold when the local version is ahead (ready to publish), and red when npm has a newer one; a package that is not on npm yet shows not published, and a private one has nothing. The filter Only ahead of npm keeps just the packages that are worth publishing. The versions are asked from npm when the form opens (it takes a few seconds for a long list, and the rest of the list is usable meanwhile) and again after every run, so they do not go stale.
  • Tinted rows. A row is tinted red when the repo has local changes, yellow when the local version is ahead of npm, and in the accent color when the package is not on npm at all. A colored strip at the left edge stays on a ticked row. A package with local changes that is also ahead shows both strips.
  • Saved sets. Save as set keeps the current selection under a name, and Saved sets… applies one. Sets are managed in Settings.

Leave the list empty and the command asks for packages itself, in a dialog, exactly like the terminal prompt; for a read-only report, empty means every package.

The Review and run button is pinned to the bottom of the page, so it is always at hand however long the list is. It checks the form (a missing required field is marked at the field), then shows the summary described in Safe by design. Anything the command asks while it runs (which packages to switch, whether to continue) arrives as a dialog on the run page; closing a dialog cancels the run.

One-time password ​

The Publish form and the Release wizard have a field for the one-time password of an npm account with two-factor authentication. The code is valid for about thirty seconds, so type it right before you start. The interface never runs npm login: sign in once in a terminal.

npm asks for a sign-in link, a security key or a passkey only in a real terminal; started from the interface, it cannot, and the publish stops with an error about a one-time password. When a publish fails like this, the report offers Publish in a terminal: a terminal window opens in the package folder with npm publish (pnpm publish for a member of a pnpm workspace) and the same dist-tag the run had, so npm can show the link, open the browser and take the key or the code. Finish the sign-in there, then press Run again or open Publish to npm: the On npm column asks the registry again. Up to five windows open at once, one for each package.

On Windows and macOS the system terminal is used; on Linux the first one found among x-terminal-emulator, gnome-terminal, konsole, xfce4-terminal and xterm. If none can be opened, the command is copied and the interface says so: run it yourself. Another way is a granular access token with the right to publish and the two-factor bypass, kept in your npm configuration: publishing then needs no code at all.

Release wizard ​

Four steps for a release that goes through a branch, a pull request, a merge and a tag, optionally followed by a publish. It runs bump with the answers.

  • Packages. The same list as everywhere. Opening the wizard from the Packages section with a selection skips this step.
  • Version. Patch, minor, major, prerelease (with an id such as alpha) or an exact version, which needs exactly one package. Each kind shows an example of how the version moves.
  • Options. Wait for the CI checks of each pull request before merging, and publish to npm right after tagging.
  • Review. The summary, then Preview (dry run), which goes through every step without pushing, merging or tagging anything, or Release.

Runs ​

Every command you start becomes a run: a page with the report and the log, and an entry in the history.

Report ​

The first thing a finished run shows. Running commands show the log until they finish.

  • Counts. How many checks passed, how many warnings and failures, and for per-package commands how many packages.
  • Needs attention. Every warning and failure in one list, each with the section it came from. A click opens the log at that line. A package named in a message links to it in the Packages section, and a message that is new since the previous run of the same command is marked as new; the number of problems that went away is noted too.
  • Sections and cards. A check with several parts, such as doctor, is one card per part: a part where everything passed is folded, one with problems is open and its lines are highlighted. A command that works package by package, such as bump or exec, has one card per package, with the command's output folded under it (short output is open).
  • Tables. The tables of the read-only commands, with the same sort, filter and monorepo blocks as the overview. The outdated and audit reports have one colored block per package, with the severity counts in its header and one prominent button, Update dependencies… or Fix vulnerabilities…, that runs npm update or npm audit fix for that package after a confirmation. See Fixing what a run found.

Log ​

The complete output, with colors, grouped into a section per package. Search it, show only the sections with problems, fold sections, keep the newest line in view with Follow, and copy or save the whole log as text. The command lines, including the ones it runs for you, are shown with a $, and a dry run marks them.

A run waiting for an answer is marked in the menu and in the tab title, a finished one can send a desktop notification (enable it in Settings), and Cancel run stops a run and everything it started.

History ​

The list of runs, newest first, grouped by day, with the command, the result in a few words (2 packages · 1 failed), the time and the duration. Filter by command, or show only the running ones, the ones with problems, or the finished ones without. Keep last 20 deletes the older finished runs. Run again on a run opens its form with the same packages and options.

A run that was in progress when the interface stopped is shown as failed, with a note, instead of staying “running” for ever.

Fixing what a run found ​

A report does not stop at the problem: next to each one the page offers what you can do about it, so you are never left to guess.

Security audit ​

The audit report has one block per package, colored from the range in Settings, with the number of vulnerabilities by severity and a Fix vulnerabilities… button. The button asks for a confirmation that names the exact command (npm audit fix) and the package, and starts it right away: there is no form to fill in.

When npm audit fix fixes what it safely can but leaves something that needs a breaking update, the run is shown as Partly done, not as a failure, and the card says what is left:

  • What is left groups the remaining vulnerabilities by the update that would fix them (for example, tinypool and @vitest/mocker are both fixed by vitest@5.0.3), with the severity, the affected range and a link to each advisory.
  • Update only this… installs just that one update after a confirmation, instead of everything.
  • Preview --force runs npm audit fix --force --dry-run and shows what would change, changing nothing.
  • Production only runs npm audit --omit=dev, to see which of the findings reach the users of the package and which live only in development tools.
  • Apply --force… applies every breaking update, after a confirmation that says so in red.

Changes this run made ​

After a command that changes dependencies (npm install, npm update, npm audit fix and the like), the package's card shows what changed in package.json and the lock files, with the number of lines added and removed and the change to package.json as a diff. Nothing is committed on its own.

  • Commit… opens the commit dialog (below).
  • Discard… puts the files back to the last commit, after a confirmation. The installed packages in node_modules are not touched; run npm ci to make them match again.
  • Run tests runs npm test in the package at once.

The commit dialog reads the rules of the branch you are on before you choose. On a feature branch the commit goes there. On the default branch it shows whether the host accepts direct commits and recommends a route: a new branch and a pull/merge request when a review is required or the rules cannot be read, a direct commit otherwise. You can override it; a direct commit that the host refuses is moved to a branch for you. The same flow is the polyrepo commit command, and the run it starts ends with a link to the pull request.

What to do next ​

  • After a problem. Under each warning or failure the report offers the next steps for that situation. For a skipped bump because the working tree is dirty: commit or discard the manifest changes, show what changed, stash everything, run the bump again. For a refused publish: publish in a terminal, check the npm sign-in, publish again with a one-time password, copy npm login. Likewise for a missing git remote, a pull request that is still open, a missing tag before a release, a branch that is not the default, and a sign-in that has expired. Anything else that fails offers to read the log around the line and to run again.
  • After a success. A finished bump offers to publish and to create a release; a tag offers a release; a publish offers a release; a commit that opened a pull request offers to open it, to update the default branch once it is merged, and to bump a version.
  • When a run did not finish. A cancelled run, or one that stopped unexpectedly, offers to run again, to read the log and to check your setup with doctor. A run that finished but did nothing, such as a bump that skipped every package, is marked Needs attention instead of Done.
  • When the server is gone. If polyrepo ui was stopped, the page says so and offers to reload once you start it again; your runs and settings are kept.

The packages stay current ​

When a command that changes repos finishes, the page refreshes just the packages it touched in the background, so the Packages table shows their new branch, version and git state without a full check. The rows pulse while they update. If the touched packages could not be told apart, the table says it may be out of date and offers a refresh.

Settings ​

  • Roots, Packages, GitLab hosts. The three lists of the config, edited in place. A folder picker browses your disk and marks the repos. Save writes polyrepo.config.json; Revert discards the edit. Found packages below them updates as you type, so you see right away what the settings find.
  • Monorepo colors. Two colors, and each monorepo gets a shade from the range between them, by its place in the alphabetical list, so one repo always has the same color in every screen. The preview shows the shades; Reset brings back the default range.
  • Signed in. Whether gh, glab and npm are signed in, and as whom, with the command to run when not.
  • Saved sets. The package sets saved from the forms, with a delete button.
  • Notifications. Allows desktop notifications for runs that finish while you are in another window.
  • Tools. The versions of Node.js, git, npm, pnpm, gh and glab found on this machine.

The color range and the saved sets are not part of the config: they are kept next to the run history.

Command palette ​

Ctrl+K, or the search field in the menu, opens a palette. Type to find a page, a command, one of the last runs or a package; Enter opens it, and a package takes you to the overview filtered to it.

Where things are kept ​

  • ~/.polyrepo/runs/ — the history: one small file per run with its settings and result, and a second with the whole log. About a hundred runs are kept, the oldest are removed. POLYREPO_HOME moves ~/.polyrepo elsewhere.
  • ~/.polyrepo/ui.json — the saved sets and the color range.
  • polyrepo.config.json — as before; Settings is only another way to edit it.

Options ​

--port <n> ​

The port to listen on. The default, 0, picks a free one.

--host <address> ​

The address to listen on. The default, 127.0.0.1, keeps the interface on this machine. Anything else makes it reachable from the network, over plain HTTP, protected only by the token: leave it alone unless you know why you need it.

--no-open ​

Print the address and do not open the browser.

--token <value> ​

Use this access token instead of a random one. For development.

Problems and exit codes ​

  • A port that is taken: Port 4000 is already in use — pick another with --port, or leave it out., exit code 1.
  • A port that is not a whole number from 0 to 65535: exit code 2.
  • Another start failure is printed as Could not start the interface: …, exit code 1.
  • Stopping with Ctrl+C is a normal exit, code 0.
  • If the page cannot reach the server any more (it was stopped), start it again and open the address it prints.
  • If the page says the interface is not built, run npm run build:ui in the polyrepo-cli folder; a normal install already has it.