Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
22 changes: 3 additions & 19 deletions install.sh
Original file line number Diff line number Diff line change
Expand Up @@ -4,23 +4,14 @@ set -e # Exit on any error

# Define the GitHub repository and the name of the binary.
GITHUB_REPO="sfcompute/cli"
# Allow the caller to override the binary name / install dir so an in-place
# upgrade lands wherever the existing binary actually lives (e.g. `sf-old`,
# or an `sf` that's not under ~/.local/bin). The TS CLI sets these from
# process.execPath when it shells out to this script.
BINARY_NAME="${SF_CLI_BINARY_NAME:-sf}"
BINARY_NAME="sf"

# Check the operating system
OS="$(uname -s)"
ARCH="$(uname -m)"

if [ -n "${SF_CLI_TARGET_DIR}" ]; then
TARGET_DIR="${SF_CLI_TARGET_DIR}"
TARGET_DIR_UNEXPANDED="${SF_CLI_TARGET_DIR}"
else
TARGET_DIR_UNEXPANDED="\${HOME}/.local/bin"
TARGET_DIR="${HOME}/.local/bin"
fi
TARGET_DIR_UNEXPANDED="\${HOME}/.local/bin"
TARGET_DIR="${HOME}/.local/bin"

# Function to check if a command exists
command_exists() {
Expand Down Expand Up @@ -139,13 +130,6 @@ if [ -f "${TARGET_FILE}" ]; then
echo "Successfully installed '${BINARY_NAME}' CLI."
echo "The binary is located at '${TARGET_FILE}'."

# In-place upgrades (TARGET_DIR overridden by the caller) skip the PATH
# onboarding nudge — the user is already running the binary, so they
# obviously have it on PATH.
if [ -n "${SF_CLI_TARGET_DIR}" ]; then
exit 0
fi

# Provide instructions for adding the target directory to the PATH.
printf "\033[0;32m\\n"
printf "To use the '%s' command, add '%s' to your PATH.\\n" "${BINARY_NAME}" "${TARGET_DIR_UNEXPANDED}"
Expand Down
23 changes: 7 additions & 16 deletions src/checkVersion.ts
Original file line number Diff line number Diff line change
Expand Up @@ -93,35 +93,30 @@ async function checkProductionCLIVersion() {
}
}

/**
* Returns true if an upgrade banner was shown (or an auto-upgrade was
* performed), false otherwise. Callers can use this to decide whether to
* show a different banner instead.
*/
export async function checkVersion(): Promise<boolean> {
export async function checkVersion() {
// Disable auto-upgrade if env var is set
if (process.env.SF_CLI_DISABLE_AUTO_UPGRADE) {
return false;
return;
}

// Skip version check if running upgrade command
const args = process.argv.slice(2);
if (args[0] === "upgrade") return false;
if (args[0] === "upgrade") return;

const version = pkg.version;
const latestVersion = await checkProductionCLIVersion();

if (!latestVersion) return false;
if (!latestVersion) return;

if (version === latestVersion) return false;
if (version === latestVersion) return;

// Don't upgrade from stable to prerelease
const currentIsStable = !semver.prerelease(version);
const latestIsPrerelease = semver.prerelease(latestVersion);
if (currentIsStable && latestIsPrerelease) return false;
if (currentIsStable && latestIsPrerelease) return;

const isOutdated = semver.lt(version, latestVersion);
if (!isOutdated) return false;
if (!isOutdated) return;

// Only auto-upgrade for patch changes and when not going to a prerelease
const isPatchUpdate = semver.diff(version, latestVersion) === "patch";
Expand Down Expand Up @@ -154,7 +149,6 @@ export async function checkVersion(): Promise<boolean> {
} catch {
// Silent error, just run the command the user wanted to run
}
return true;
} else if (!latestIsPrerelease) {
// Only show update message for non-prerelease versions
const message = `
Expand All @@ -172,8 +166,5 @@ Run 'sf upgrade' to update to the latest version
borderStyle: "round",
}),
);
return true;
}

return false;
}
30 changes: 1 addition & 29 deletions src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,6 @@ import { registerDev } from "./lib/dev.ts";
import { registerImages } from "./lib/images/index.ts";
import { registerLogin } from "./lib/login.ts";
import { registerMe } from "./lib/me.ts";
import { registerMigrate, showMigrateBanner } from "./lib/migrate.ts";
import { registerNodes } from "./lib/nodes/index.ts";
import { analytics, IS_TRACKING_DISABLED } from "./lib/posthog.ts";
import { registerScale } from "./lib/scale/index.tsx";
Expand All @@ -34,34 +33,8 @@ import { registerZones } from "./lib/zones.tsx";
async function main() {
const program = new Command();

// `sf migrate` replaces this binary outright, so auto-upgrading the legacy
// CLI first would be wasted work — and worse, the install scripts target
// the same `~/.local/bin/sf` path, so racing them risks clobbering the new
// Rust binary the user is about to install.
if (process.argv[2] === "migrate") {
process.env.SF_CLI_DISABLE_AUTO_UPGRADE = "1";
}

if (!process.argv.includes("--json")) {
const [shownUpgradeBanner] = await Promise.all([
checkVersion(),
getAppBanner(),
]);
// If the user is already on the latest version of the legacy CLI, nudge
// them toward the new Rust CLI instead of showing nothing. We avoid
// double-stacking with the upgrade banner since users on outdated builds
// need to upgrade before migrating, and skip the banner for the
// `upgrade` / `migrate` commands themselves (where it'd just be noise)
// and for users who've opted out via SF_CLI_DISABLE_MIGRATE_BANNER.
const subcommand = process.argv[2];
if (
!shownUpgradeBanner &&
subcommand !== "migrate" &&
subcommand !== "upgrade" &&
!process.env.SF_CLI_DISABLE_MIGRATE_BANNER
) {
showMigrateBanner();
}
await Promise.all([checkVersion(), getAppBanner()]);
}

program
Expand Down Expand Up @@ -90,7 +63,6 @@ async function main() {
registerBalance(program);
registerTokens(program);
registerUpgrade(program);
registerMigrate(program);
await registerScale(program);
registerMe(program);
await registerVM(program);
Expand Down
124 changes: 0 additions & 124 deletions src/lib/migrate.ts

This file was deleted.

12 changes: 1 addition & 11 deletions src/lib/upgrade.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
import { spawn } from "node:child_process";
import * as console from "node:console";
import { basename, dirname } from "node:path";
import process from "node:process";
import type { Command } from "@commander-js/extra-typings";
import ora from "ora";
Expand Down Expand Up @@ -71,18 +70,9 @@ export async function handleUpgrade(
// Execute the script with bash
spinner.start("Installing upgrade");

// Tell the install script to write back to this exact binary's path. Without
// this, the installer hardcodes ~/.local/bin/sf — which would clobber the
// Rust `sf` if we're running as `sf-old`, and would silently drop a
// duplicate copy when `sf` is installed somewhere else (e.g. /usr/local/bin).
const bashProcess = spawn("bash", [], {
stdio: ["pipe", "pipe", "pipe"],
env: {
...process.env,
...(version ? { SF_CLI_VERSION: version } : {}),
SF_CLI_TARGET_DIR: dirname(process.execPath),
SF_CLI_BINARY_NAME: basename(process.execPath),
},
env: version ? { ...process.env, SF_CLI_VERSION: version } : process.env,
});

let stdout = "";
Expand Down
Loading