feat: in-app info modal with version archives and MR preview deploys

Follows the !7 (merged) policy — no version bump on the branch; the merger adds the `Release vX.Y.Z` commit just before merging.

Summary

Adds an in-app info modal (top-right info button) that surfaces:

  • the running build's version + deploy target (`main` / `v<X.Y.Z>` / `mr-` / `dev`)
  • About blurb + external links (Phabricator project, GitLab repo) — replaces the two icon-only top-bar buttons
  • list of past releases with one-click rollback to a permanent `/v<X.Y.Z>/` archive
  • list of open MRs with one-click preview at `/mr-/`
  • pretty-rendered live copy of `CHANGELOG.md`

CI changes — two new deploy paths

  • Every push to `main` → publishes to both `/` (the live site) and `/v<X.Y.Z>/` (kept indefinitely).
  • Every MR pipeline → publishes a preview to `/mr-/`. GitLab's `environment.on_stop` hook removes the directory when the MR is merged or closed.
  • Root-deploy now uses `--exclude='/v*/' --exclude='/mr-*/'` so the new sibling directories survive `--delete`.

Changed

  • `vite.config.js` reads `VITE_BASE_PATH` and exposes `APP_VERSION` (from `package.json`) and `DEPLOY_TARGET` as compile-time defines.
  • `src/api/gitlab.js` — small unauthenticated read-only GitLab helper for fetching open MRs and the live `CHANGELOG.md` (verified CORS-enabled).

Verification

  • `npm run build`
  • Manual: dev server + modal open/close, version display reads `APP_VERSION`/`DEPLOY_TARGET` correctly.
  • CI deploy jobs: not yet exercised end-to-end against Toolforge — review carefully and watch the first pipeline.

Test plan for reviewer

  • Top-right info button opens the modal; close button + escape both dismiss.
  • Modal version line shows the right version + deploy target.
  • Past-releases list links to `/v<X.Y.Z>/` and the rendered page identifies itself with that target.
  • Open-MRs list populates and links to `/mr-/`.
  • CHANGELOG section renders the live file with formatting (headings, links, code).
  • CI: first pipeline deploys correctly to both `/` and `/v<X.Y.Z>/`; `/mr-/` cleanup fires on merge.

🤖 Generated with Claude Code

Merge request reports

Loading