diff --git a/.eslintrc.json b/.eslintrc.json index d097bf7..f8f61db 100644 --- a/.eslintrc.json +++ b/.eslintrc.json @@ -1,17 +1,19 @@ { - "env": { - "commonjs": true, - "es6": true, - "node": true - }, - "extends": "eslint:recommended", - "globals": { - "Atomics": "readonly", - "SharedArrayBuffer": "readonly" - }, - "parserOptions": { - "ecmaVersion": 2018 - }, - "rules": { - } -} \ No newline at end of file + "env": { + "commonjs": true, + "es6": true, + "node": true + }, + "extends": "eslint:recommended", + "globals": { + "Atomics": "readonly", + "SharedArrayBuffer": "readonly" + }, + "parser": "@typescript-eslint/parser", + "parserOptions": { + "sourceType": "module", + "ecmaVersion": 2019 + }, + "rules": { + } +} diff --git a/__tests__/get-os.test.js b/__tests__/get-os.test.ts similarity index 91% rename from __tests__/get-os.test.js rename to __tests__/get-os.test.ts index c278d84..dff6d0c 100644 --- a/__tests__/get-os.test.js +++ b/__tests__/get-os.test.ts @@ -1,4 +1,4 @@ -const getOS = require("../lib/get-os"); +import getOS from "../src/get-os"; describe("getOS", () => { test("test", () => { diff --git a/__tests__/get-url.test.js b/__tests__/get-url.test.ts similarity index 95% rename from __tests__/get-url.test.js rename to __tests__/get-url.test.ts index fa2c1d1..e07ccb2 100644 --- a/__tests__/get-url.test.js +++ b/__tests__/get-url.test.ts @@ -1,4 +1,4 @@ -const getURL = require("../lib/get-url"); +import getURL from "../src/get-url"; describe("getURL()", () => { test("test", () => { diff --git a/jest.config.js b/jest.config.js new file mode 100644 index 0000000..563d4cc --- /dev/null +++ b/jest.config.js @@ -0,0 +1,11 @@ +module.exports = { + clearMocks: true, + moduleFileExtensions: ['js', 'ts'], + testEnvironment: 'node', + testMatch: ['**/*.test.ts'], + testRunner: 'jest-circus/runner', + transform: { + '^.+\\.ts$': 'ts-jest' + }, + verbose: true +} \ No newline at end of file diff --git a/lib/get-latest-version.js b/lib/get-latest-version.js index e3bdcd3..9d2f85d 100644 --- a/lib/get-latest-version.js +++ b/lib/get-latest-version.js @@ -1,21 +1,22 @@ +"use strict"; +Object.defineProperty(exports, "__esModule", { value: true }); const XMLHttpRequest = require("xmlhttprequest").XMLHttpRequest; - function getLatestVersion() { - return new Promise((resolve, reject) => { - const xhr = new XMLHttpRequest(); - const url = "https://formulae.brew.sh/api/formula/hugo.json"; - xhr.open("GET", url); - xhr.send(); - xhr.onreadystatechange = function() { - if (xhr.readyState === 4 && xhr.status === 200) { - const result = JSON.parse(xhr.responseText); - const latestVersion = result.versions.stable; - resolve(latestVersion); - } else if (xhr.readyState === 4 && xhr.status !== 200) { - reject(`ERROR: got status ${xhr.status} of ${url}`); - } - }; - }); + return new Promise((resolve, reject) => { + const xhr = new XMLHttpRequest(); + const url = "https://formulae.brew.sh/api/formula/hugo.json"; + xhr.open("GET", url); + xhr.send(); + xhr.onreadystatechange = function () { + if (xhr.readyState === 4 && xhr.status === 200) { + const result = JSON.parse(xhr.responseText); + const latestVersion = result.versions.stable; + resolve(latestVersion); + } + else if (xhr.readyState === 4 && xhr.status !== 200) { + reject(`ERROR: got status ${xhr.status} of ${url}`); + } + }; + }); } - -module.exports = getLatestVersion; +exports.default = getLatestVersion; diff --git a/lib/get-os.js b/lib/get-os.js index 3fa37a4..03e37ed 100644 --- a/lib/get-os.js +++ b/lib/get-os.js @@ -1,14 +1,18 @@ +"use strict"; +Object.defineProperty(exports, "__esModule", { value: true }); function getOS(platform) { - if (platform === "linux") { - return "Linux"; - } else if (platform === "darwin") { - return "macOS"; - } else if (platform === "win32") { - return "Windows"; - // throw new Error("Windows is not supported"); - } else { - throw new Error(`${platform} is not supported`); - } + if (platform === "linux") { + return "Linux"; + } + else if (platform === "darwin") { + return "macOS"; + } + else if (platform === "win32") { + return "Windows"; + // throw new Error("Windows is not supported"); + } + else { + throw new Error(`${platform} is not supported`); + } } - -module.exports = getOS; +exports.default = getOS; diff --git a/lib/get-url.js b/lib/get-url.js index 20a0c56..f033277 100644 --- a/lib/get-url.js +++ b/lib/get-url.js @@ -1,27 +1,27 @@ +"use strict"; +Object.defineProperty(exports, "__esModule", { value: true }); function getURL(os, extended, version) { - const extendedStr = extended => { - if (extended === "true") { - return "extended_"; - } else { - return ""; - // } else { - // throw new Error(`Invalid input (extended): ${extended}`); - } - }; - - const ext = os => { - if (os === "Windows") { - return "zip"; - } else { - return "tar.gz"; - } - }; - - const hugoName = `hugo_${extendedStr(extended)}${version}_${os}-64bit`; - const baseURL = "https://github.com/gohugoio/hugo/releases/download"; - const url = `${baseURL}/v${version}/${hugoName}.${ext(os)}`; - - return url; + const extendedStr = (extended) => { + if (extended === "true") { + return "extended_"; + } + else { + return ""; + // } else { + // throw new Error(`Invalid input (extended): ${extended}`); + } + }; + const ext = (os) => { + if (os === "Windows") { + return "zip"; + } + else { + return "tar.gz"; + } + }; + const hugoName = `hugo_${extendedStr(extended)}${version}_${os}-64bit`; + const baseURL = "https://github.com/gohugoio/hugo/releases/download"; + const url = `${baseURL}/v${version}/${hugoName}.${ext(os)}`; + return url; } - -module.exports = getURL; +exports.default = getURL; diff --git a/lib/index.js b/lib/index.js index 4aa7ea1..8174acd 100644 --- a/lib/index.js +++ b/lib/index.js @@ -1,33 +1,57 @@ -const core = require("@actions/core"); -const exec = require("@actions/exec"); -const getLatestVersion = require("./get-latest-version"); -const installer = require("./installer"); - +"use strict"; +var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) { + function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); } + return new (P || (P = Promise))(function (resolve, reject) { + function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } } + function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } } + function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); } + step((generator = generator.apply(thisArg, _arguments || [])).next()); + }); +}; +var __importStar = (this && this.__importStar) || function (mod) { + if (mod && mod.__esModule) return mod; + var result = {}; + if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) result[k] = mod[k]; + result["default"] = mod; + return result; +}; +var __importDefault = (this && this.__importDefault) || function (mod) { + return (mod && mod.__esModule) ? mod : { "default": mod }; +}; +Object.defineProperty(exports, "__esModule", { value: true }); +const core = __importStar(require("@actions/core")); +const exec = __importStar(require("@actions/exec")); +const get_latest_version_1 = __importDefault(require("./get-latest-version")); +const installer_1 = __importDefault(require("./installer")); // most @actions toolkit packages have async methods -async function run() { - try { - getLatestVersion().then( - async function(latestVersion) { - let hugoVersion = core.getInput("hugo-version"); - if (!hugoVersion || hugoVersion === "latest") { - hugoVersion = latestVersion; +function run() { + return __awaiter(this, void 0, void 0, function* () { + try { + get_latest_version_1.default().then(function (latestVersion) { + return __awaiter(this, void 0, void 0, function* () { + const hugoVersion = core.getInput("hugo-version"); + console.log(`Hugo version: ${hugoVersion}`); + const version = (v, latestVersion) => { + if (v === "" || v === "latest") { + return latestVersion; + } + else { + return v; + } + }; + yield installer_1.default(version(hugoVersion, latestVersion)); + // Show version + yield exec.exec("hugo version"); + yield exec.exec("go version"); + yield exec.exec("git --version"); + }); + }, function (error) { + core.setFailed(error); + }); } - console.log(`Hugo version: ${hugoVersion}`); - - await installer(hugoVersion); - - // Show version - await exec.exec("hugo version"); - await exec.exec("go version"); - await exec.exec("git --version"); - }, - function(error) { - core.setFailed(error); - } - ); - } catch (error) { - core.setFailed(error.message); - } + catch (error) { + core.setFailed(error.message); + } + }); } - run(); diff --git a/lib/installer.js b/lib/installer.js index bb22949..59a573a 100644 --- a/lib/installer.js +++ b/lib/installer.js @@ -1,38 +1,57 @@ -const core = require("@actions/core"); -const tc = require("@actions/tool-cache"); -const io = require("@actions/io"); -const getOS = require("./get-os"); -const getURL = require("./get-url"); - -async function installer(version) { - try { - const extended = core.getInput("extended"); - console.log(`Hugo extended: ${extended}`); - - const osName = getOS(process.platform); - console.log(`Operating System: ${osName}`); - - const hugoURL = getURL(osName, extended, version); - core.debug(`hugoURL: ${hugoURL}`); - - const hugoPath = `${process.env.HOME}/bin`; - await io.mkdirP(hugoPath); - core.addPath(hugoPath); - - // Download and extract Hugo binary - const hugoAssets = await tc.downloadTool(hugoURL); - let hugoBin = ""; - if (osName === "Windows") { - const hugoExtractedFolder = await tc.extractZip(hugoAssets, "/tmp"); - hugoBin = `${hugoExtractedFolder}/hugo.exe`; - } else { - const hugoExtractedFolder = await tc.extractTar(hugoAssets, "/tmp"); - hugoBin = `${hugoExtractedFolder}/hugo`; - } - await io.mv(hugoBin, hugoPath); - } catch (error) { - core.setFailed(error.message); - } +"use strict"; +var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) { + function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); } + return new (P || (P = Promise))(function (resolve, reject) { + function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } } + function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } } + function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); } + step((generator = generator.apply(thisArg, _arguments || [])).next()); + }); +}; +var __importStar = (this && this.__importStar) || function (mod) { + if (mod && mod.__esModule) return mod; + var result = {}; + if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) result[k] = mod[k]; + result["default"] = mod; + return result; +}; +var __importDefault = (this && this.__importDefault) || function (mod) { + return (mod && mod.__esModule) ? mod : { "default": mod }; +}; +Object.defineProperty(exports, "__esModule", { value: true }); +const core = __importStar(require("@actions/core")); +const tc = __importStar(require("@actions/tool-cache")); +const io = __importStar(require("@actions/io")); +const get_os_1 = __importDefault(require("./get-os")); +const get_url_1 = __importDefault(require("./get-url")); +function installer(version) { + return __awaiter(this, void 0, void 0, function* () { + try { + const extended = core.getInput("extended"); + console.log(`Hugo extended: ${extended}`); + const osName = get_os_1.default(process.platform); + console.log(`Operating System: ${osName}`); + const hugoURL = get_url_1.default(osName, extended, version); + core.debug(`hugoURL: ${hugoURL}`); + const hugoPath = `${process.env.HOME}/bin`; + yield io.mkdirP(hugoPath); + core.addPath(hugoPath); + // Download and extract Hugo binary + const hugoAssets = yield tc.downloadTool(hugoURL); + let hugoBin = ""; + if (osName === "Windows") { + const hugoExtractedFolder = yield tc.extractZip(hugoAssets, "/tmp"); + hugoBin = `${hugoExtractedFolder}/hugo.exe`; + } + else { + const hugoExtractedFolder = yield tc.extractTar(hugoAssets, "/tmp"); + hugoBin = `${hugoExtractedFolder}/hugo`; + } + yield io.mv(hugoBin, hugoPath); + } + catch (error) { + core.setFailed(error.message); + } + }); } - -module.exports = installer; +exports.default = installer; diff --git a/package-lock.json b/package-lock.json index 6ce03ef..7817dbd 100644 --- a/package-lock.json +++ b/package-lock.json @@ -461,6 +461,12 @@ "@babel/types": "^7.3.0" } }, + "@types/eslint-visitor-keys": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/@types/eslint-visitor-keys/-/eslint-visitor-keys-1.0.0.tgz", + "integrity": "sha512-OCutwjDZ4aFS6PB1UZ988C4YgwlBHJd6wCeQqaLdmadZ/7e+w79+hbMUFC1QXDNCmdyoRfAFdm0RypzwR+Qpag==", + "dev": true + }, "@types/istanbul-lib-coverage": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/@types/istanbul-lib-coverage/-/istanbul-lib-coverage-2.0.1.tgz", @@ -486,6 +492,33 @@ "@types/istanbul-lib-report": "*" } }, + "@types/jest": { + "version": "24.0.18", + "resolved": "https://registry.npmjs.org/@types/jest/-/jest-24.0.18.tgz", + "integrity": "sha512-jcDDXdjTcrQzdN06+TSVsPPqxvsZA/5QkYfIZlq1JMw7FdP5AZylbOc+6B/cuDurctRe+MziUMtQ3xQdrbjqyQ==", + "dev": true, + "requires": { + "@types/jest-diff": "*" + } + }, + "@types/jest-diff": { + "version": "20.0.1", + "resolved": "https://registry.npmjs.org/@types/jest-diff/-/jest-diff-20.0.1.tgz", + "integrity": "sha512-yALhelO3i0hqZwhjtcr6dYyaLoCHbAMshwtj6cGxTvHZAKXHsYGdff6E8EPw3xLKY0ELUTQ69Q1rQiJENnccMA==", + "dev": true + }, + "@types/json-schema": { + "version": "7.0.3", + "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.3.tgz", + "integrity": "sha512-Il2DtDVRGDcqjDtE+rF8iqg1CArehSK84HZJCT7AMITlyXRBpuPhqGLDQMowraqqu1coEaimg4ZOqggt6L6L+A==", + "dev": true + }, + "@types/node": { + "version": "12.7.5", + "resolved": "https://registry.npmjs.org/@types/node/-/node-12.7.5.tgz", + "integrity": "sha512-9fq4jZVhPNW8r+UYKnxF1e2HkDWOWKM5bC2/7c9wPV835I0aOrVbS/Hw/pWPk2uKrNXQqg9Z959Kz+IYDd5p3w==", + "dev": true + }, "@types/stack-utils": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/@types/stack-utils/-/stack-utils-1.0.1.tgz", @@ -507,6 +540,49 @@ "integrity": "sha512-gCubfBUZ6KxzoibJ+SCUc/57Ms1jz5NjHe4+dI2krNmU5zCPAphyLJYyTOg06ueIyfj+SaCUqmzun7ImlxDcKg==", "dev": true }, + "@typescript-eslint/experimental-utils": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/experimental-utils/-/experimental-utils-2.3.0.tgz", + "integrity": "sha512-ry+fgd0Hh33LyzS30bIhX/a1HJpvtnecjQjWxxsZTavrRa1ymdmX7tz+7lPrPAxB018jnNzwNtog6s3OhxPTAg==", + "dev": true, + "requires": { + "@types/json-schema": "^7.0.3", + "@typescript-eslint/typescript-estree": "2.3.0", + "eslint-scope": "^5.0.0" + } + }, + "@typescript-eslint/parser": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-2.3.0.tgz", + "integrity": "sha512-Dc+LAtHts0yDuusxG0NVjGvrpPy2kZauxqPbfFs0fmcMB4JhNs+WwIDMFGWeKjbGoPt/SIUC9XJ7E0ZD/f8InQ==", + "dev": true, + "requires": { + "@types/eslint-visitor-keys": "^1.0.0", + "@typescript-eslint/experimental-utils": "2.3.0", + "@typescript-eslint/typescript-estree": "2.3.0", + "eslint-visitor-keys": "^1.1.0" + } + }, + "@typescript-eslint/typescript-estree": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-2.3.0.tgz", + "integrity": "sha512-WBxfwsTeCOsmQ7cLjow7lgysviBKUW34npShu7dxJYUQCbSG5nfZWZTgmQPKEc+3flpbSM7tjXjQOgETYp+njQ==", + "dev": true, + "requires": { + "glob": "^7.1.4", + "is-glob": "^4.0.1", + "lodash.unescape": "4.0.1", + "semver": "^6.3.0" + }, + "dependencies": { + "semver": { + "version": "6.3.0", + "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", + "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", + "dev": true + } + } + }, "abab": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/abab/-/abab-2.0.1.tgz", @@ -866,6 +942,15 @@ } } }, + "bs-logger": { + "version": "0.2.6", + "resolved": "https://registry.npmjs.org/bs-logger/-/bs-logger-0.2.6.tgz", + "integrity": "sha512-pd8DCoxmbgc7hyPKOvxtqNcjYoOsABPQdcCUjGp3d42VR2CX1ORhk2A87oqqu5R1kk+76nsxZupkmyd+MVtCog==", + "dev": true, + "requires": { + "fast-json-stable-stringify": "2.x" + } + }, "bser": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/bser/-/bser-2.1.0.tgz", @@ -3031,6 +3116,30 @@ "throat": "^4.0.0" } }, + "jest-circus": { + "version": "24.9.0", + "resolved": "https://registry.npmjs.org/jest-circus/-/jest-circus-24.9.0.tgz", + "integrity": "sha512-dwkvwFtRc9Anmk1XTc+bonVL8rVMZ3CeGMoFWmv1oaQThdAgvfI9bwaFlZp+gLVphNVz6ZLfCWo3ERhS5CeVvA==", + "dev": true, + "requires": { + "@babel/traverse": "^7.1.0", + "@jest/environment": "^24.9.0", + "@jest/test-result": "^24.9.0", + "@jest/types": "^24.9.0", + "chalk": "^2.0.1", + "co": "^4.6.0", + "expect": "^24.9.0", + "is-generator-fn": "^2.0.0", + "jest-each": "^24.9.0", + "jest-matcher-utils": "^24.9.0", + "jest-message-util": "^24.9.0", + "jest-snapshot": "^24.9.0", + "jest-util": "^24.9.0", + "pretty-format": "^24.9.0", + "stack-utils": "^1.0.1", + "throat": "^4.0.0" + } + }, "jest-config": { "version": "24.9.0", "resolved": "https://registry.npmjs.org/jest-config/-/jest-config-24.9.0.tgz", @@ -3596,12 +3705,24 @@ "integrity": "sha512-8xOcRHvCjnocdS5cpwXQXVzmmh5e5+saE2QGoeQmbKmRS6J3VQppPOIt0MnmE+4xlZoumy0GPG0D0MVIQbNA1A==", "dev": true }, + "lodash.memoize": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/lodash.memoize/-/lodash.memoize-4.1.2.tgz", + "integrity": "sha1-vMbEmkKihA7Zl/Mj6tpezRguC/4=", + "dev": true + }, "lodash.sortby": { "version": "4.7.0", "resolved": "https://registry.npmjs.org/lodash.sortby/-/lodash.sortby-4.7.0.tgz", "integrity": "sha1-7dFMgk4sycHgsKG0K7UhBRakJDg=", "dev": true }, + "lodash.unescape": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/lodash.unescape/-/lodash.unescape-4.0.1.tgz", + "integrity": "sha1-vyJJiGzlFM2hEvrpIYzcBlIR/Jw=", + "dev": true + }, "loose-envify": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/loose-envify/-/loose-envify-1.4.0.tgz", @@ -3629,6 +3750,12 @@ } } }, + "make-error": { + "version": "1.3.5", + "resolved": "https://registry.npmjs.org/make-error/-/make-error-1.3.5.tgz", + "integrity": "sha512-c3sIjNUow0+8swNwVpqoH4YCShKNFkMaw6oH1mNS2haDZQqkeZFlHS3dhoeEbKKmJB4vXpJucU6oH75aDYeE9g==", + "dev": true + }, "makeerror": { "version": "1.0.11", "resolved": "https://registry.npmjs.org/makeerror/-/makeerror-1.0.11.tgz", @@ -5056,6 +5183,41 @@ "integrity": "sha1-yy4SAwZ+DI3h9hQJS5/kVwTqYAM=", "dev": true }, + "ts-jest": { + "version": "24.1.0", + "resolved": "https://registry.npmjs.org/ts-jest/-/ts-jest-24.1.0.tgz", + "integrity": "sha512-HEGfrIEAZKfu1pkaxB9au17b1d9b56YZSqz5eCVE8mX68+5reOvlM93xGOzzCREIov9mdH7JBG+s0UyNAqr0tQ==", + "dev": true, + "requires": { + "bs-logger": "0.x", + "buffer-from": "1.x", + "fast-json-stable-stringify": "2.x", + "json5": "2.x", + "lodash.memoize": "4.x", + "make-error": "1.x", + "mkdirp": "0.x", + "resolve": "1.x", + "semver": "^5.5", + "yargs-parser": "10.x" + }, + "dependencies": { + "camelcase": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-4.1.0.tgz", + "integrity": "sha1-1UVjW+HjPFQmScaRc+Xeas+uNN0=", + "dev": true + }, + "yargs-parser": { + "version": "10.1.0", + "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-10.1.0.tgz", + "integrity": "sha512-VCIyR1wJoEBZUqk5PA+oOBF6ypbwh5aNB3I50guxAL/quggdfs4TtNHQrSazFA3fYZ+tEqfs0zIGlv0c/rgjbQ==", + "dev": true, + "requires": { + "camelcase": "^4.1.0" + } + } + } + }, "tslib": { "version": "1.10.0", "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.10.0.tgz", @@ -5100,6 +5262,12 @@ "underscore": "1.8.3" } }, + "typescript": { + "version": "3.6.3", + "resolved": "https://registry.npmjs.org/typescript/-/typescript-3.6.3.tgz", + "integrity": "sha512-N7bceJL1CtRQ2RiG0AQME13ksR7DiuQh/QehubYcghzv20tnh+MQnQIuJddTmsbqYj+dztchykemz0zFzlvdQw==", + "dev": true + }, "uglify-js": { "version": "3.6.0", "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-3.6.0.tgz", diff --git a/package.json b/package.json index 14e603b..ee4bbb2 100644 --- a/package.json +++ b/package.json @@ -4,9 +4,13 @@ "description": "Hugo setup action", "main": "lib/index.js", "scripts": { - "lint": "eslint ./lib/**/*", + "lint": "eslint ./src/**/*.ts", + "lint:fix": "eslint --fix ./src/**/*.ts", "test": "jest --coverage --verbose", - "build": "npm prune --production" + "build": "npm prune --production", + "tsc": "tsc", + "format": "prettier --write **/*.ts", + "format:check": "prettier --check **/*.ts" }, "repository": { "type": "git", @@ -32,7 +36,13 @@ "xmlhttprequest": "^1.8.0" }, "devDependencies": { + "@types/jest": "^24.0.18", + "@types/node": "^12.7.5", + "@typescript-eslint/parser": "^2.3.0", "eslint": "^6.4.0", - "jest": "^24.9.0" + "jest": "^24.9.0", + "jest-circus": "^24.9.0", + "ts-jest": "^24.1.0", + "typescript": "^3.6.3" } } diff --git a/src/get-latest-version.ts b/src/get-latest-version.ts new file mode 100644 index 0000000..b82fd0e --- /dev/null +++ b/src/get-latest-version.ts @@ -0,0 +1,19 @@ +const XMLHttpRequest = require("xmlhttprequest").XMLHttpRequest; + +export default function getLatestVersion(): Promise { + return new Promise((resolve, reject) => { + const xhr = new XMLHttpRequest(); + const url: string = "https://formulae.brew.sh/api/formula/hugo.json"; + xhr.open("GET", url); + xhr.send(); + xhr.onreadystatechange = function() { + if (xhr.readyState === 4 && xhr.status === 200) { + const result = JSON.parse(xhr.responseText); + const latestVersion: string = result.versions.stable; + resolve(latestVersion); + } else if (xhr.readyState === 4 && xhr.status !== 200) { + reject(`ERROR: got status ${xhr.status} of ${url}`); + } + }; + }); +} diff --git a/src/get-os.ts b/src/get-os.ts new file mode 100644 index 0000000..08d77f1 --- /dev/null +++ b/src/get-os.ts @@ -0,0 +1,12 @@ +export default function getOS(platform: string) { + if (platform === "linux") { + return "Linux"; + } else if (platform === "darwin") { + return "macOS"; + } else if (platform === "win32") { + return "Windows"; + // throw new Error("Windows is not supported"); + } else { + throw new Error(`${platform} is not supported`); + } +} diff --git a/src/get-url.ts b/src/get-url.ts new file mode 100644 index 0000000..62a5ba1 --- /dev/null +++ b/src/get-url.ts @@ -0,0 +1,31 @@ +export default function getURL( + os: string, + extended: string, + version: string +): string { + const extendedStr = (extended: string) => { + if (extended === "true") { + return "extended_"; + } else { + return ""; + // } else { + // throw new Error(`Invalid input (extended): ${extended}`); + } + }; + + const ext = (os: string) => { + if (os === "Windows") { + return "zip"; + } else { + return "tar.gz"; + } + }; + + const hugoName: string = `hugo_${extendedStr( + extended + )}${version}_${os}-64bit`; + const baseURL: string = "https://github.com/gohugoio/hugo/releases/download"; + const url: string = `${baseURL}/v${version}/${hugoName}.${ext(os)}`; + + return url; +} diff --git a/src/index.ts b/src/index.ts new file mode 100644 index 0000000..267ef4b --- /dev/null +++ b/src/index.ts @@ -0,0 +1,37 @@ +import * as core from "@actions/core"; +import * as exec from "@actions/exec"; +import getLatestVersion from "./get-latest-version"; +import installer from "./installer"; + +// most @actions toolkit packages have async methods +async function run() { + try { + getLatestVersion().then( + async function(latestVersion): Promise { + const hugoVersion: string = core.getInput("hugo-version"); + console.log(`Hugo version: ${hugoVersion}`); + const version = (v: string, latestVersion: string): string => { + if (v === "" || v === "latest") { + return latestVersion; + } else { + return v; + } + }; + + await installer(version(hugoVersion, latestVersion)); + + // Show version + await exec.exec("hugo version"); + await exec.exec("go version"); + await exec.exec("git --version"); + }, + function(error) { + core.setFailed(error); + } + ); + } catch (error) { + core.setFailed(error.message); + } +} + +run(); diff --git a/src/installer.ts b/src/installer.ts new file mode 100644 index 0000000..e955db6 --- /dev/null +++ b/src/installer.ts @@ -0,0 +1,42 @@ +import * as core from "@actions/core"; +import * as tc from "@actions/tool-cache"; +import * as io from "@actions/io"; +import getOS from "./get-os"; +import getURL from "./get-url"; + +export default async function installer(version: string) { + try { + const extended: string = core.getInput("extended"); + console.log(`Hugo extended: ${extended}`); + + const osName: string = getOS(process.platform); + console.log(`Operating System: ${osName}`); + + const hugoURL: string = getURL(osName, extended, version); + core.debug(`hugoURL: ${hugoURL}`); + + const hugoPath: string = `${process.env.HOME}/bin`; + await io.mkdirP(hugoPath); + core.addPath(hugoPath); + + // Download and extract Hugo binary + const hugoAssets: string = await tc.downloadTool(hugoURL); + let hugoBin: string = ""; + if (osName === "Windows") { + const hugoExtractedFolder: string = await tc.extractZip( + hugoAssets, + "/tmp" + ); + hugoBin = `${hugoExtractedFolder}/hugo.exe`; + } else { + const hugoExtractedFolder: string = await tc.extractTar( + hugoAssets, + "/tmp" + ); + hugoBin = `${hugoExtractedFolder}/hugo`; + } + await io.mv(hugoBin, hugoPath); + } catch (error) { + core.setFailed(error.message); + } +} diff --git a/tsconfig.json b/tsconfig.json new file mode 100644 index 0000000..7e0f9c2 --- /dev/null +++ b/tsconfig.json @@ -0,0 +1,63 @@ +{ + "compilerOptions": { + /* Basic Options */ + // "incremental": true, /* Enable incremental compilation */ + "target": "es6", /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017', 'ES2018', 'ES2019' or 'ESNEXT'. */ + "module": "commonjs", /* Specify module code generation: 'none', 'commonjs', 'amd', 'system', 'umd', 'es2015', or 'ESNext'. */ + // "allowJs": true, /* Allow javascript files to be compiled. */ + // "checkJs": true, /* Report errors in .js files. */ + // "jsx": "preserve", /* Specify JSX code generation: 'preserve', 'react-native', or 'react'. */ + // "declaration": true, /* Generates corresponding '.d.ts' file. */ + // "declarationMap": true, /* Generates a sourcemap for each corresponding '.d.ts' file. */ + // "sourceMap": true, /* Generates corresponding '.map' file. */ + // "outFile": "./", /* Concatenate and emit output to single file. */ + "outDir": "./lib", /* Redirect output structure to the directory. */ + "rootDir": "./src", /* Specify the root directory of input files. Use to control the output directory structure with --outDir. */ + // "composite": true, /* Enable project compilation */ + // "tsBuildInfoFile": "./", /* Specify file to store incremental compilation information */ + // "removeComments": true, /* Do not emit comments to output. */ + // "noEmit": true, /* Do not emit outputs. */ + // "importHelpers": true, /* Import emit helpers from 'tslib'. */ + // "downlevelIteration": true, /* Provide full support for iterables in 'for-of', spread, and destructuring when targeting 'ES5' or 'ES3'. */ + // "isolatedModules": true, /* Transpile each file as a separate module (similar to 'ts.transpileModule'). */ + + /* Strict Type-Checking Options */ + "strict": true, /* Enable all strict type-checking options. */ + "noImplicitAny": true, /* Raise error on expressions and declarations with an implied 'any' type. */ + // "strictNullChecks": true, /* Enable strict null checks. */ + // "strictFunctionTypes": true, /* Enable strict checking of function types. */ + // "strictBindCallApply": true, /* Enable strict 'bind', 'call', and 'apply' methods on functions. */ + // "strictPropertyInitialization": true, /* Enable strict checking of property initialization in classes. */ + // "noImplicitThis": true, /* Raise error on 'this' expressions with an implied 'any' type. */ + // "alwaysStrict": true, /* Parse in strict mode and emit "use strict" for each source file. */ + + /* Additional Checks */ + // "noUnusedLocals": true, /* Report errors on unused locals. */ + // "noUnusedParameters": true, /* Report errors on unused parameters. */ + // "noImplicitReturns": true, /* Report error when not all code paths in function return a value. */ + // "noFallthroughCasesInSwitch": true, /* Report errors for fallthrough cases in switch statement. */ + + /* Module Resolution Options */ + // "moduleResolution": "node", /* Specify module resolution strategy: 'node' (Node.js) or 'classic' (TypeScript pre-1.6). */ + // "baseUrl": "./", /* Base directory to resolve non-absolute module names. */ + // "paths": {}, /* A series of entries which re-map imports to lookup locations relative to the 'baseUrl'. */ + // "rootDirs": [], /* List of root folders whose combined content represents the structure of the project at runtime. */ + // "typeRoots": [], /* List of folders to include type definitions from. */ + // "types": [], /* Type declaration files to be included in compilation. */ + // "allowSyntheticDefaultImports": true, /* Allow default imports from modules with no default export. This does not affect code emit, just typechecking. */ + "esModuleInterop": true /* Enables emit interoperability between CommonJS and ES Modules via creation of namespace objects for all imports. Implies 'allowSyntheticDefaultImports'. */ + // "preserveSymlinks": true, /* Do not resolve the real path of symlinks. */ + // "allowUmdGlobalAccess": true, /* Allow accessing UMD globals from modules. */ + + /* Source Map Options */ + // "sourceRoot": "", /* Specify the location where debugger should locate TypeScript files instead of source locations. */ + // "mapRoot": "", /* Specify the location where debugger should locate map files instead of generated locations. */ + // "inlineSourceMap": true, /* Emit a single file with source maps instead of having a separate file. */ + // "inlineSources": true, /* Emit the source alongside the sourcemaps within a single file; requires '--inlineSourceMap' or '--sourceMap' to be set. */ + + /* Experimental Options */ + // "experimentalDecorators": true, /* Enables experimental support for ES7 decorators. */ + // "emitDecoratorMetadata": true, /* Enables experimental support for emitting type metadata for decorators. */ + }, + "exclude": ["node_modules", "**/*.test.ts"] +}