feat: Check for existing bun before downloading

Check for existing bun with same version number, if it exists we skip any futher actions. This avoids downloading cache or bun over the network.
This commit is contained in:
Erik Axel Nielsen 2025-09-15 11:35:00 +02:00
parent 22457c87c1
commit 8876d4f857
2 changed files with 149 additions and 114 deletions

194
dist/setup/index.js generated vendored

File diff suppressed because one or more lines are too long

View File

@ -7,6 +7,7 @@ import {
symlinkSync, symlinkSync,
renameSync, renameSync,
copyFileSync, copyFileSync,
existsSync,
} from "node:fs"; } from "node:fs";
import { addPath, info, warning } from "@actions/core"; import { addPath, info, warning } from "@actions/core";
import { isFeatureAvailable, restoreCache } from "@actions/cache"; import { isFeatureAvailable, restoreCache } from "@actions/cache";
@ -73,6 +74,18 @@ export default async (options: Input): Promise<Output> => {
let revision: string | undefined; let revision: string | undefined;
let cacheHit = false; let cacheHit = false;
// Check if Bun executable already exists and matches requested version
if (!options.customUrl && existsSync(bunPath)) {
const existingRevision = await getRevision(bunPath);
if (existingRevision && isVersionMatch(existingRevision, options.version)) {
revision = existingRevision;
cacheHit = true; // Treat as cache hit to avoid unnecessary network requests
info(`Using existing Bun installation: ${revision}`);
}
}
if (!revision) {
if (cacheEnabled) { if (cacheEnabled) {
const cacheKey = createHash("sha1").update(url).digest("base64"); const cacheKey = createHash("sha1").update(url).digest("base64");
@ -95,6 +108,7 @@ export default async (options: Input): Promise<Output> => {
// TODO: remove this, temporary fix for https://github.com/oven-sh/setup-bun/issues/73 // TODO: remove this, temporary fix for https://github.com/oven-sh/setup-bun/issues/73
revision = await retry(async () => await downloadBun(url, bunPath), 3); revision = await retry(async () => await downloadBun(url, bunPath), 3);
} }
}
if (!revision) { if (!revision) {
throw new Error( throw new Error(
@ -122,6 +136,27 @@ export default async (options: Input): Promise<Output> => {
}; };
}; };
function isVersionMatch(
existingRevision: string,
requestedVersion?: string,
): boolean {
// If no version specified, default is "latest" - don't match existing
if (!requestedVersion) {
return false;
}
// Non-pinned versions should never match existing installations
if (/^(latest|canary|action)$/i.test(requestedVersion)) {
return false;
}
const [existingVersion] = existingRevision.split("+");
const normalizeVersion = (v: string) => v.replace(/^v/i, "");
return normalizeVersion(existingVersion) === normalizeVersion(requestedVersion);
}
async function downloadBun( async function downloadBun(
url: string, url: string,
bunPath: string, bunPath: string,