near-sandbox
Version:
CLI tool for testing NEAR smart contracts
141 lines (140 loc) • 4.9 kB
JavaScript
Object.defineProperty(exports, "__esModule", { value: true });
exports.Binary = void 0;
const fs = require("fs/promises");
const url_1 = require("url");
const path_1 = require("path");
const tar = require("tar");
const got_1 = require("got");
const utils_1 = require("./utils");
const child_process_1 = require("child_process");
const stream = require("stream");
const util_1 = require("util");
const pipeline = (0, util_1.promisify)(stream.pipeline);
class Binary {
constructor(name, url, installDir = Binary.DEFAULT_INSTALL_DIR) {
Object.defineProperty(this, "name", {
enumerable: true,
configurable: true,
writable: true,
value: name
});
Object.defineProperty(this, "installDir", {
enumerable: true,
configurable: true,
writable: true,
value: installDir
});
Object.defineProperty(this, "urls", {
enumerable: true,
configurable: true,
writable: true,
value: void 0
});
let errors = [];
let urls = [];
if (typeof url === "string" || url instanceof url_1.URL) {
urls.push(url);
}
else {
if (url.length == 0) {
throw new Error("No URL provided got empty array");
}
urls = url;
}
if (!name || typeof name !== "string") {
errors.push("You must specify the name of your binary as a string");
}
try {
this.urls = urls.map((path) => typeof path === "string" ? new url_1.URL(path) : path);
}
catch (e) {
errors.push(e);
}
if (errors.length > 0) {
errors.push('\nCorrect usage: new Binary("my-binary", "https://example.com/binary/download.tar.gz"');
errors.unshift("One or more of the parameters you passed to the Binary constructor are invalid:\n");
throw new Error(errors.join("\n"));
}
}
/**
*
* @param name binary name, e.g. 'git'
* @param path URL of where to find binary
* @param destination Directory to put the binary
* @returns
*/
static async create(name, path, destination) {
const bin = new Binary(name, path, destination !== null && destination !== void 0 ? destination : (await (0, utils_1.searchPath)(name)));
if (destination === bin.installDir) {
await fs.mkdir(bin.installDir, { recursive: true });
}
return bin;
}
get binPath() {
return (0, path_1.join)(this.installDir, this.name);
}
async download(url) {
// Ensure the install directory exists
if (!await (0, utils_1.fileExists)(this.installDir)) {
await fs.mkdir(this.installDir, { recursive: true });
}
return pipeline(got_1.default.stream(url), new stream.PassThrough(), tar.x({ strip: 1, C: this.installDir }));
}
async install() {
for (let url of this.urls) {
try {
await this.download(url);
return true;
}
catch (error) { }
}
throw new Error(`Failed to download from: \n${this.urls.join("\n")}`);
}
async exists() {
return await (0, utils_1.fileExists)(this.binPath);
}
async run(cliArgs, options = { stdio: [null, utils_1.inherit, utils_1.inherit] }) {
if (!(await this.exists())) {
try {
await this.install();
}
catch (err) {
console.error(err);
return 1;
}
}
const args = cliArgs !== null && cliArgs !== void 0 ? cliArgs : process.argv.slice(2);
const result = (0, child_process_1.spawn)(this.binPath, args, options);
result.on("error", (error) => {
console.log(error);
});
return new Promise((resolve, reject) => {
result.on("close", (code) => {
if (!code) {
resolve(code !== null && code !== void 0 ? code : 0);
}
reject(code);
});
});
}
async runAndExit(cliArgs, options = { stdio: [null, utils_1.inherit, utils_1.inherit] }) {
process.exit(await this.run(cliArgs, options));
}
async uninstall() {
if (this.installDir === Binary.DEFAULT_INSTALL_DIR &&
(await this.exists())) {
await (0, utils_1.rm)(this.binPath);
if (await this.exists()) {
throw new Error(`Failed to remove binary located ${this.binPath}`);
}
}
}
}
exports.Binary = Binary;
Object.defineProperty(Binary, "DEFAULT_INSTALL_DIR", {
enumerable: true,
configurable: true,
writable: true,
value: (0, path_1.join)(__dirname, "..", "bin")
});
;