Dashboard › cli › Distillation
8419c9f7-7644-4f12-8da4-430ca0df8bcf["lore_tm_v1_iu3czcifjmhEUwR9VeokwGIOF_E_jPUosEdKnYIw1Bw","lore_tm_v1_JwZxvJZZyO6EmNk-VKy9EQYvUnNIayH5kZDvM2LhMk4","lore_tm_v1_Pib9tMRsWWzNFchFT0Xno0SN8DcV8tI-1RCZ97S4xuE"]
packages/cli/src/lib/upgrade.ts: always flush/close the writer.packages/cli/src/lib/upgrade.ts: after writer.write() returns false, a stream that has already failed may never emit "drain".packages/cli/src/lib/upgrade.ts: if the stream already failed, surface that original stream error; an error encountered while flushing/closing the writer must not mask it.UpgradeError when the file never becomes visible or stays empty.packages/cli/src/lib/upgrade.ts polls for a visible, non-zero-size file using exponential backoff; retries log the path, delay in milliseconds, current attempt, and VERIFY_MAX_ATTEMPTS.isNightlyVersion; failure of the compressed nightly path falls back to the raw binary URL.clearPatchCache() asynchronously, with cache-clear failure treated as non-fatal.packages/cli/src/lib/binary.ts defines InstallationMethod as "curl" | "brew" | "npm" | "pnpm" | "bun" | "yarn" | "unknown"; valid --method values exclude "unknown" and are ordered curl, brew, npm, pnpm, bun, yarn.parseInstallationMethod(value) lowercases input, validates it against VALID_METHODS, and throws Invalid method: ${value}. Must be one of: ${VALID_METHODS.join(", ")} for an unsupported method.isMusl() in packages/cli/src/lib/binary.ts returns false outside Linux and caches its Linux result in cachedIsMusl. Detection order is: 1. test /lib/ld-musl-${muslArch}.so.1, where x64 maps to x86_64 and all other supported architectures map to aarch64; 2. run spawnSync("ldd", ["--version"], { stdio: ["ignore", "pipe", "pipe"] }), concatenate stdout and stderr, and case-insensitively search for "musl"; if ldd fails or is absent, assume glibc.getPlatformBinaryName() produces sentry-<os>-<arch>[-musl][.exe]: darwin, windows, or linux; arm64 or x64; optional -musl; and .exe only on Windows.getBinaryDownloadUrl(version) returns https://github.com/getsentry/cli/releases/download/${version}/${getPlatformBinaryName()}; GITHUB_RELEASES_URL is https://api.github.com/repos/getsentry/cli/releases.isNightlyVersion(version) identifies a nightly when the version contains "-dev.", corresponding to X.Y.Z-dev.<unix-seconds>.compareVersions(a, b) is implemented with compare imported from the semver package as semverCompare, returning -1 | 0 | 1; isDowngrade(current, target) returns true when compareVersions(current, target) === 1. The accompanying comment still refers to Bun.semver.order.getBinaryFilename() returns "sentry.exe" on Windows and "sentry" elsewhere.getBinaryPaths(installPath) derives { installPath, tempPath: \${installPath}.download`, oldPath: `${installPath}.old`, lockPath: `${installPath}.lock` }`.determineInstallDir(homeDir, env) chooses a curl installation directory in this order: 1. env.SENTRY_INSTALL_DIR; 2. ~/.local/bin if it exists and appears exactly in PATH; 3. ~/bin under the same conditions; 4. ~/.sentry/bin, with setup responsible for PATH modification.getGitHubHeaders() returns Accept: "application/vnd.github.v3+json" and "User-Agent": getUserAgent().fetchWithUpgradeError(url, init, serviceName) calls customFetch; it rethrows an AbortError unchanged, maps TLS certificate failures to new UpgradeError("network_error", buildTlsErrorDetail(error)), and maps other failures to new UpgradeError("network_error", \Failed to connect to ${serviceName}: ${stringifyUnknown(error)}`)`.replaceBinarySync(tempPath, installPath) is intentionally synchronous so its multi-step replacement cannot be interrupted. On Unix it atomically calls renameSync(tempPath, installPath). On Windows it first tries renameSync(installPath, \${installPath}.old`); on failure it removes an existing .old` and retries, tolerates another failure as a fresh install, then renames the downloaded temp file into place.cleanupOldBinary() is intended to remove .old files left by Windows upgrades on later CLI startup. Startup intentionally does not remove .download files because another process may be upgrading; .download cleanup occurs inside the upgrade flow while holding the exclusive lock.GHCR_BLOB_TIMEOUT of 30_000 ms and retry logic in fetchWithRetry; the rationale is observed GHCR cold-start latency spikes from 126ms to 30s for identical requests.externalSignal?.aborted && error.name === "AbortError" rather than relying on runtime-dependent error-message text.ghcr.io/getsentry/cli supports anonymous access; no user credential is required beyond the registryβs anonymous token flow.UpgradeError including the tag and HTTP status when manifest retrieval fails.Authorization header because the redirect contains signed query-string credentials and retaining authorization can produce HTTP 404.&last=${encodeURIComponent(lastTag)} when lastTag is present; tag listing supports an optional prefix such as "nightly-" for versioned nightlies.