135ea21a61
Fixes the v0.3.4 fresh-box failures: silent CLI under bare-word PATH invocation (SEA argv detection), bootstrap dying on venv creation without an actionable hint (poisoned-partial-venv recovery + apt hint + doctor venv-capability probe + preflight), installer falsely 'verifying' a silent binary, and localhost-only server binding (network mode: 0.0.0.0 + wildcard CORS + hostname-derived API URL — remote browsing zero-config). 38 CLI tests, 3 web tests, 409 ai-service tests green; build/typecheck/lint clean. ---ci--- phase: hotfix milestone: v0.4 status: complete type: hotfix requirements: covered: [REQ-4-001, REQ-4-002, REQ-4-003, REQ-4-004, REQ-4-005] partial: [] ---/ci---
100 lines
4.2 KiB
Bash
Executable File
100 lines
4.2 KiB
Bash
Executable File
#!/bin/sh
|
|
# Nextcraft CLI installer — the one-liner:
|
|
# curl -fsSL https://git.coreci.dev/coreci/nextcraft/raw/main/scripts/install.sh | sh
|
|
# Resolves the latest release from the Gitea API, downloads the linux x64 binary
|
|
# + sha256 sidecar, verifies the checksum, installs to ~/.local/bin.
|
|
# Any failure degrades to printed source-bootstrap instructions (G-103) — never
|
|
# installs an unverified artifact. Checksum mismatch = hard stop (exit 1).
|
|
set -eu
|
|
|
|
FORGE_BASE="${NEXTCRAFT_FORGE_BASE:-https://git.coreci.dev}"
|
|
OWNER="coreci"
|
|
REPO="nextcraft"
|
|
DEST="${DEST:-$HOME/.local/bin}"
|
|
API="$FORGE_BASE/api/v1/repos/$OWNER/$REPO/releases/latest"
|
|
|
|
say() { printf '%s\n' "$*"; }
|
|
die() { printf '%s\n' "$*" >&2; exit 1; }
|
|
|
|
[ "$(uname -s)" = "Linux" ] && [ "$(uname -m)" = "x86_64" ] || {
|
|
say "nextcraft: no binary for $(uname -s)/$(uname -m) (linux x64 only for now)."
|
|
say "Source bootstrap instead:"
|
|
say " git clone $FORGE_BASE/$OWNER/$REPO.git && cd $REPO"
|
|
say " pnpm --filter @nextcraft/cli dev -- doctor # or scripts/bootstrap.sh path"
|
|
exit 0
|
|
}
|
|
|
|
command -v curl >/dev/null 2>&1 || {
|
|
say "nextcraft: curl is required. Install curl, or source bootstrap:"
|
|
say " git clone $FORGE_BASE/$OWNER/$REPO.git"
|
|
exit 0
|
|
}
|
|
|
|
RELEASE_JSON="$(curl -fsSL "$API" 2>/dev/null)" || {
|
|
say "nextcraft: could not reach $API."
|
|
say "Source bootstrap instead: git clone $FORGE_BASE/$OWNER/$REPO.git"
|
|
exit 0
|
|
}
|
|
|
|
TAG="$(printf '%s' "$RELEASE_JSON" | sed -n 's/.*"tag_name":"\([^"]*\)".*/\1/p' | head -1)"
|
|
BIN_URL="$(printf '%s' "$RELEASE_JSON" | sed -n 's/.*"browser_download_url":"\([^"]*nextcraft-linux-x64\)".*/\1/p' | head -1)"
|
|
SUM_URL="$(printf '%s' "$RELEASE_JSON" | sed -n 's/.*"browser_download_url":"\([^"]*nextcraft-linux-x64\.sha256\)".*/\1/p' | head -1)"
|
|
|
|
if [ -z "$TAG" ] || [ -z "$BIN_URL" ] || [ -z "$SUM_URL" ]; then
|
|
say "nextcraft: latest release ($TAG) has no linux x64 binary assets yet."
|
|
say "Source bootstrap instead:"
|
|
say " git clone $FORGE_BASE/$OWNER/$REPO.git && cd $REPO"
|
|
say " pnpm install && pnpm --filter @nextcraft/cli dev -- doctor"
|
|
exit 0
|
|
fi
|
|
|
|
TMP="$(mktemp -d)"
|
|
trap 'rm -rf "$TMP"' EXIT
|
|
say "nextcraft: downloading $TAG ..."
|
|
curl -fsSL "$BIN_URL" -o "$TMP/nextcraft-linux-x64" || {
|
|
say "nextcraft: download failed. Source bootstrap: git clone $FORGE_BASE/$OWNER/$REPO.git"
|
|
exit 0
|
|
}
|
|
curl -fsSL "$SUM_URL" -o "$TMP/nextcraft-linux-x64.sha256" || {
|
|
say "nextcraft: checksum download failed — refusing to install unverified binary."
|
|
say "Source bootstrap instead: git clone $FORGE_BASE/$OWNER/$REPO.git"
|
|
exit 0
|
|
}
|
|
|
|
EXPECTED="$(sed 's/ .*$//' "$TMP/nextcraft-linux-x64.sha256" | tr -d '[:space:]')"
|
|
if command -v sha256sum >/dev/null 2>&1; then
|
|
ACTUAL="$(sha256sum "$TMP/nextcraft-linux-x64" | sed 's/ .*$//')"
|
|
elif command -v shasum >/dev/null 2>&1; then
|
|
ACTUAL="$(shasum -a 256 "$TMP/nextcraft-linux-x64" | sed 's/ .*$//')"
|
|
else
|
|
die "nextcraft: no sha256 tool available — cannot verify. DO NOT install an unverified binary. Install sha256sum (coreutils) and retry."
|
|
fi
|
|
[ "$ACTUAL" = "$EXPECTED" ] || die "nextcraft: CHECKSUM MISMATCH for $TAG — do not run this binary. Aborting."
|
|
|
|
mkdir -p "$DEST"
|
|
mv "$TMP/nextcraft-linux-x64" "$DEST/nextcraft"
|
|
chmod +x "$DEST/nextcraft"
|
|
|
|
say "nextcraft: installed $DEST/nextcraft ($TAG)"
|
|
INSTALLED_VERSION="$("$DEST/nextcraft" --version 2>/dev/null || true)"
|
|
if [ -z "$INSTALLED_VERSION" ]; then
|
|
die "nextcraft: installed binary produced no output for --version — it is broken. Do not use it; remove $DEST/nextcraft, report the issue, and fall back to source bootstrap (git clone $FORGE_BASE/$OWNER/$REPO.git)."
|
|
fi
|
|
if [ "$INSTALLED_VERSION" != "$TAG" ]; then
|
|
die "nextcraft: binary reports version $INSTALLED_VERSION but release is $TAG — integrity mismatch. Remove $DEST/nextcraft and re-run the installer."
|
|
fi
|
|
say "nextcraft: verified binary version: $INSTALLED_VERSION"
|
|
case ":$PATH:" in
|
|
*":$DEST:"*) ;;
|
|
*)
|
|
say ""
|
|
say "$DEST is not on your PATH. Add it:"
|
|
say " echo 'export PATH=\"$DEST:\$PATH\"' >> ~/.profile && source ~/.profile"
|
|
;;
|
|
esac
|
|
say ""
|
|
say "Next steps:"
|
|
say " nextcraft doctor # check prerequisites"
|
|
say " git clone $FORGE_BASE/$OWNER/$REPO.git && cd nextcraft"
|
|
say " nextcraft bootstrap # set up the monorepo"
|
|
say " nextcraft verify && nextcraft dev" |