-
Notifications
You must be signed in to change notification settings - Fork 4
/
install.ts
145 lines (119 loc) Β· 4.08 KB
/
install.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
import * as core from "@actions/core";
import * as tc from "@actions/tool-cache";
import * as github from "@actions/github";
import os from "os";
import path from "path";
const octokit = github.getOctokit(core.getInput("github-token"));
const downloadURL = "https://github.com/spacelift-io/spacectl/releases/download";
/**
* Downloads the Spacectl binary from GitHub.
* It also caches it, so that subsequent runs of the action can use the cached version.
* @returns The path of the extracted binary.
*/
export async function installAndGetFolder(): Promise<string> {
const version = await getVersion();
const arch = getArchitecture();
core.setOutput("version", version);
const cached = tc.find("spacectl", version, arch);
if (cached) {
core.info(`Found cached Spacectl at ${cached}`);
return cached;
}
const assetURL = await getAssetURL(version, arch);
core.info(`Downloading Spacectl from ${assetURL}`);
const zipPath = await tc.downloadTool(assetURL);
const extractedFolder = await tc.extractZip(zipPath, path.join(os.homedir(), "spacectl"));
core.info(`Extracted Spacectl to ${extractedFolder}`);
await saveToCache(extractedFolder, version, arch);
return extractedFolder;
}
/**
* Saves the extracted binary's parent folder to the cache.
*/
async function saveToCache(extractedFolder: string, version: string, arch: string): Promise<void> {
const cachedPath = await tc.cacheDir(extractedFolder, "spacectl", version, arch);
core.info(`Cached Spacectl to ${cachedPath}`);
}
/**
* Returns the URL of the Spacectl zip file for the given version and architecture.
* @returns The URL of the Spacectl zip file.
* @example "https://github.com/spacelift-io/spacectl/releases/download/v0.12.0/spacectl_0.12.0_linux_arm64.zip"
*/
async function getAssetURL(version: string, arch: string): Promise<string> {
const versionWithoutLeadingV = version.substring(1);
const platform = getPlatform();
return `${downloadURL}/${version}/spacectl_${versionWithoutLeadingV}_${platform}_${arch}.zip`;
}
/**
* Determines the version of Spacectl to download.
* If the user didn't explicitly provide any, we'll use the latest version.
* @returns The version of Spacectl to download.
* @example "v0.1.0"
*/
async function getVersion(): Promise<string> {
let version = core.getInput("version");
// If version is specified, let's prepend a "v" to it
if (version && version !== "latest" && version[0] !== "v") {
version = `v${version}`;
}
// If version is not specified, we default to the latest
if (!version || version === "latest") {
version = await getLatestVersion();
}
core.info(`Installing version ${version} of Spacectl`);
return version;
}
/**
* Gets the latest version of Spacectl from GitHub.
* We filter out drafts and pre-releases.
* @returns The latest version of Spacectl with a "v" prefix.
* @example "v0.1.0"
*/
async function getLatestVersion(): Promise<string> {
const releaseResponse = await octokit.rest.repos.listReleases({
owner: "spacelift-io",
repo: "spacectl",
});
const releaseList = releaseResponse.data;
if (!releaseList) {
const errMsg = "Could not find any releases for Spacectl";
core.setFailed(errMsg);
throw new Error(errMsg);
}
const filteredReleases = releaseList.filter((release) => !release.draft && !release.prerelease);
return filteredReleases[0].tag_name;
}
/**
* Copy-pasta of:
* https://github.com/actions/setup-go/blob/30b9ddff1180797dbf0efc06837929f98bdf7af7/src/system.ts
* @returns The platform name.
* @example "linux"
*/
function getPlatform(): string {
let platform = os.platform().toString();
if (platform === "win32") {
platform = "windows";
}
return platform;
}
/**
* Copy-pasta of:
* https://github.com/actions/setup-go/blob/30b9ddff1180797dbf0efc06837929f98bdf7af7/src/system.ts
* @returns The architecture name.
* @example "amd64"
*/
function getArchitecture(): string {
let arch = os.arch();
switch (arch) {
case "x64":
arch = "amd64";
break;
case "x32":
arch = "386";
break;
case "arm":
arch = "armv6l";
break;
}
return arch;
}