Skip to content

Commit

Permalink
buildx: alternative release repos to download buildx
Browse files Browse the repository at this point in the history
Signed-off-by: CrazyMax <crazy-max@users.noreply.github.com>
  • Loading branch information
crazy-max committed Aug 26, 2023
1 parent c674e72 commit 027b3ea
Show file tree
Hide file tree
Showing 3 changed files with 101 additions and 26 deletions.
68 changes: 52 additions & 16 deletions __tests__/buildx/install.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -88,12 +88,6 @@ describe('download', () => {
},
100000
);

it('returns latest buildx GitHub release', async () => {
const release = await Install.getRelease('latest');
expect(release).not.toBeNull();
expect(release?.tag_name).not.toEqual('');
});
});

describe('build', () => {
Expand All @@ -116,30 +110,72 @@ describe('build', () => {
}, 100000);
});

describe('getDownloadVersion', () => {
it('returns official latest download version', async () => {
const version = await Install.getDownloadVersion('latest');
expect(version.key).toEqual('official');
expect(version.version).toEqual('latest');
expect(version.downloadURL).toEqual('https://github.com/docker/buildx/releases/download/v%s/%s');
expect(version.releasesURL).toEqual('https://raw.githubusercontent.com/docker/actions-toolkit/main/.github/buildx-releases.json');
});

it('returns official v0.10.1 download version', async () => {
const version = await Install.getDownloadVersion('v0.10.1');
expect(version.key).toEqual('official');
expect(version.version).toEqual('v0.10.1');
expect(version.downloadURL).toEqual('https://github.com/docker/buildx/releases/download/v%s/%s');
expect(version.releasesURL).toEqual('https://raw.githubusercontent.com/docker/actions-toolkit/main/.github/buildx-releases.json');
});

it('returns lab latest download version', async () => {
const version = await Install.getDownloadVersion('lab:latest');
expect(version.key).toEqual('lab');
expect(version.version).toEqual('latest');
expect(version.downloadURL).toEqual('https://github.com/docker/buildx-desktop/releases/download/v%s/%s');
expect(version.releasesURL).toEqual('https://raw.githubusercontent.com/docker/actions-toolkit/main/.github/buildx-lab-releases.json');
});

it('returns lab v0.11.2-desktop.2 download version', async () => {
const version = await Install.getDownloadVersion('lab:v0.11.2-desktop.2');
expect(version.key).toEqual('lab');
expect(version.version).toEqual('v0.11.2-desktop.2');
expect(version.downloadURL).toEqual('https://github.com/docker/buildx-desktop/releases/download/v%s/%s');
expect(version.releasesURL).toEqual('https://raw.githubusercontent.com/docker/actions-toolkit/main/.github/buildx-lab-releases.json');
});

it('unknown repo', async () => {
await expect(Install.getDownloadVersion('foo:bar')).rejects.toThrow(new Error('Cannot find buildx version for foo:bar'));
});
});

describe('getRelease', () => {
it('returns latest buildx GitHub release', async () => {
const release = await Install.getRelease('latest');
it('returns latest official GitHub release', async () => {
const version = await Install.getDownloadVersion('latest');
const release = await Install.getRelease(version);
expect(release).not.toBeNull();
expect(release?.tag_name).not.toEqual('');
});

it('returns v0.10.1 buildx GitHub release', async () => {
const release = await Install.getRelease('v0.10.1');
it('returns v0.10.1 official GitHub release', async () => {
const version = await Install.getDownloadVersion('v0.10.1');
const release = await Install.getRelease(version);
expect(release).not.toBeNull();
expect(release?.id).toEqual(90346950);
expect(release?.tag_name).toEqual('v0.10.1');
expect(release?.html_url).toEqual('https://github.com/docker/buildx/releases/tag/v0.10.1');
});

it('returns v0.2.2 buildx GitHub release', async () => {
const release = await Install.getRelease('v0.2.2');
it('returns v0.11.2-desktop.2 lab GitHub release', async () => {
const version = await Install.getDownloadVersion('lab:v0.11.2-desktop.2');
const release = await Install.getRelease(version);
expect(release).not.toBeNull();
expect(release?.id).toEqual(17671545);
expect(release?.tag_name).toEqual('v0.2.2');
expect(release?.html_url).toEqual('https://github.com/docker/buildx/releases/tag/v0.2.2');
expect(release?.id).toEqual(90346950);
expect(release?.tag_name).toEqual('v0.11.2-desktop.2');
expect(release?.html_url).toEqual('https://github.com/docker/buildx-desktop/releases/tag/v0.11.2-desktop.2');
});

it('unknown release', async () => {
await expect(Install.getRelease('foo')).rejects.toThrow(new Error('Cannot find Buildx release foo in https://raw.githubusercontent.com/docker/actions-toolkit/main/.github/buildx-releases.json'));
const version = await Install.getDownloadVersion('foo');
await expect(Install.getRelease(version)).rejects.toThrow(new Error('Cannot find Buildx release foo in https://raw.githubusercontent.com/docker/actions-toolkit/main/.github/buildx-releases.json'));
});
});
52 changes: 42 additions & 10 deletions src/buildx/install.ts
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@ import {Docker} from '../docker/docker';
import {Git} from '../git';
import {Util} from '../util';

import {DownloadVersion} from '../types/buildx';
import {GitHubRelease} from '../types/github';

export interface InstallOpts {
Expand All @@ -50,7 +51,10 @@ export class Install {
* @param version semver version or latest
* @returns path to the buildx binary
*/
public async download(version: string): Promise<string> {
public async download(v: string): Promise<string> {
const version: DownloadVersion = await Install.getDownloadVersion(v);
core.debug(`Install.download version: ${version.version}`);

const release: GitHubRelease = await Install.getRelease(version);
core.debug(`Install.download release tag name: ${release.tag_name}`);

Expand All @@ -62,15 +66,15 @@ export class Install {
throw new Error(`Invalid Buildx version "${vspec}".`);
}

const installCache = new InstallCache('buildx-dl-bin', vspec);
const installCache = new InstallCache(version.key != 'official' ? `buildx-dl-bin-${version.key}` : 'buildx-dl-bin', vspec);

const cacheFoundPath = await installCache.find();
if (cacheFoundPath) {
core.info(`Buildx binary found in ${cacheFoundPath}`);
return cacheFoundPath;
}

const downloadURL = util.format('https://github.com/docker/buildx/releases/download/v%s/%s', vspec, this.filename(vspec));
const downloadURL = util.format(version.downloadURL, vspec, this.filename(vspec));
core.info(`Downloading ${downloadURL}`);

const htcDownloadPath = await tc.downloadTool(downloadURL);
Expand Down Expand Up @@ -253,20 +257,48 @@ export class Install {
return hash;
}

public static async getRelease(version: string): Promise<GitHubRelease> {
const url = `https://raw.githubusercontent.com/docker/actions-toolkit/main/.github/buildx-releases.json`;
public static async getDownloadVersion(v: string): Promise<DownloadVersion> {
let [repoKey, version] = v.split(':');
if (!version) {
version = repoKey;
repoKey = 'official';
}
switch (repoKey) {
case 'official': {
return {
key: repoKey,
version: version,
downloadURL: 'https://github.com/docker/buildx/releases/download/v%s/%s',
releasesURL: 'https://raw.githubusercontent.com/docker/actions-toolkit/main/.github/buildx-releases.json'
};
}
case 'lab': {
return {
key: repoKey,
version: version,
downloadURL: 'https://github.com/docker/buildx-desktop/releases/download/v%s/%s',
releasesURL: 'https://raw.githubusercontent.com/docker/actions-toolkit/main/.github/buildx-lab-releases.json'
};
}
default: {
throw new Error(`Cannot find buildx version for ${v}`);
}
}
}

public static async getRelease(version: DownloadVersion): Promise<GitHubRelease> {
const http: httpm.HttpClient = new httpm.HttpClient('docker-actions-toolkit');
const resp: httpm.HttpClientResponse = await http.get(url);
const resp: httpm.HttpClientResponse = await http.get(version.releasesURL);
const body = await resp.readBody();
const statusCode = resp.message.statusCode || 500;
if (statusCode >= 400) {
throw new Error(`Failed to get Buildx release ${version} from ${url} with status code ${statusCode}: ${body}`);
throw new Error(`Failed to get Buildx releases from ${version.releasesURL} with status code ${statusCode}: ${body}`);
}
const releases = <Record<string, GitHubRelease>>JSON.parse(body);
if (!releases[version]) {
throw new Error(`Cannot find Buildx release ${version} in ${url}`);
if (!releases[version.version]) {
throw new Error(`Cannot find Buildx release ${version.version} in ${version.releasesURL}`);
}
return releases[version];
return releases[version.version];
}
}

Expand Down
7 changes: 7 additions & 0 deletions src/types/buildx.ts
Original file line number Diff line number Diff line change
Expand Up @@ -19,3 +19,10 @@ export interface Cert {
cert?: string;
key?: string;
}

export interface DownloadVersion {
key: string;
version: string;
downloadURL: string;
releasesURL: string;
}

0 comments on commit 027b3ea

Please sign in to comment.