Files
rdbms-playground/docs/adr/0055-curl-sh-install-script.md
T
claude@clouddev1 ef99e6c676
ci / gate (push) Successful in 3m19s
website / deploy (push) Successful in 1m58s
feat(install): curl|sh installer script (ADR-0055)
scripts/install.sh — POSIX sh, shellcheck-clean: detects uname OS/arch ->
target triple (Linux uses the static musl build; Windows rejected with a
Scoop/winget pointer), resolves the latest release (or RDBMS_VERSION),
downloads the asset + its .sha256 and verifies it, installs to
~/.local/bin with a PATH hint. RDBMS_OS/RDBMS_ARCH + --print-target are
testing seams. Verified end-to-end against the live public v0.1.0 (all
mappings, pinned + latest, checksum incl. tamper-rejection, install+run).

ADR-0055 + README index; plan-doc step 2 done + decisions recorded
(crates.io=yes, releases public, tracking via doc+ADR).
2026-06-17 19:41:34 +00:00

3.7 KiB

ADR-0055: curl | sh install script (scripts/install.sh)

Status

Accepted — implemented 2026-06-17 (plan: docs/plans/20260616-public-availability.md, step 2). Step 2 on the road to public availability, building on ADR-0054 (versioned releases) and ADR-ci-001/003 (the Gitea releases it downloads from). Tracked by the plan + this ADR (no Gitea issue — user decision, 2026-06-17).

Context

Until now, installing meant: find the releases page, work out which of the six assets matches your machine, download it, chmod +x, move it onto PATH, and (on macOS) wonder about Gatekeeper. That is too much friction for a teaching tool aimed at beginners. The Gitea releases are publicly downloadable (confirmed), with deterministic asset names (rdbms-playground-<tag>-<target>[.exe]) and .sha256 sidecars (ADR-ci-003), and a releases/latest API — enough to script a one-liner install.

Decision

Ship scripts/install.sh, run as curl -fsSL <gitea-raw>/scripts/install.sh | sh:

  • POSIX sh (no bashisms) — it runs under the sh of curl | sh; kept shellcheck-clean (-s sh).
  • Platform detection from uname → target triple: Linux → <arch>-unknown-linux-musl (the fully-static build — one universal Linux artifact, no glibc/version coupling), macOS → <arch>-apple-darwin; x86_64/amd64 and aarch64/arm64 both map. Windows is rejected with a pointer to Scoop/winget/the releases page (the binary is a .exe, not a curl|sh target).
  • Version: the releases/latest API tag by default; RDBMS_VERSION pins a specific tag.
  • Integrity: always download the .sha256 sidecar and verify (sha256sum/shasum -a 256); a mismatch aborts the install. HTTPS only.
  • Install location: ~/.local/bin by default (user-writable, no sudo), overridable via RDBMS_INSTALL_DIR; prints a PATH hint if the dir isn't on PATH.
  • macOS note: a curl download is not Gatekeeper-quarantined, so the binary runs as-is even while it is only ad-hoc-signed; proper Developer-ID signing + notarization (for browser downloads) is a separate, postponed task (see the plan's signing item).
  • Testing seams: RDBMS_OS/RDBMS_ARCH force detection and --print-target prints the resolved triple and exits — so the mapping is checkable without a download.

Rejected / deferred

  • Hosting the script on the website domain (Cloudflare): nicer URL, but adds a moving part; the Gitea repo raw URL is simplest and the binaries live there anyway (user decision). The website may later reference the same command.
  • install.ps1 (Windows): deferred — Windows users go via Scoop / winget (D3, §3).
  • Uploading install.sh as a release asset for a stable link: optional; the branch raw URL is fine for now.

Consequences

  • A first-time user runs one line and gets a checksum-verified binary on PATH. The website's install copy (website branch, separate agent) can point at this command.
  • Verified end-to-end (2026-06-17) against the live public v0.1.0: all four Linux/macOS platform mappings + Windows/unknown-arch rejection; pinned and latest paths; checksum verification incl. a tamper-rejection check; install + run on Linux x86_64. (The installed v0.1.0 predates --version, ADR-0054 — a non-issue, and the reason to cut a new release.)
  • No automated regression guard in CI yet: shellcheck isn't in the flake, and there's no shell-test harness here (no bats). Recommended follow-up: add a shellcheck scripts/*.sh gate (touches ADR-ci-002 — needs shellcheck in the devShell). For now the guard is local shellcheck + the documented end-to-end verification.