Files
smartrestic/ts_install/install.ts
T

103 lines
3.3 KiB
TypeScript
Raw Permalink Normal View History

import { createWriteStream, promises as fs } from 'fs';
import { Readable, pipeline } from 'stream';
import { promisify } from 'util';
import { fileURLToPath } from 'url';
import { dirname, join } from 'path';
import * as smartarchive from '@push.rocks/smartarchive';
const streamPipeline = promisify(pipeline);
interface IRelease {
id: number;
tag_name: string;
assets: IAsset[];
}
interface IAsset {
url: string;
name: string;
}
class ResticReleaseDownloader {
private baseUrl: string;
constructor() {
this.baseUrl = 'https://api.github.com/repos/restic/restic/releases';
}
public async getPackageVersion(): Promise<string> {
// Get the directory of the current module
const currentDir = dirname(fileURLToPath(import.meta.url));
// Construct the path to the package.json file
const packageJsonPath = join(currentDir, '../package.json');
// Read the package.json file
const packageJsonData = await fs.readFile(packageJsonPath, 'utf8');
// Parse the package.json file
const packageJson = JSON.parse(packageJsonData);
// Return the version
return packageJson.version;
};
public async downloadAllReleases(targetFolder: string): Promise<void> {
const releases = await this.fetchReleases();
for (const release of releases) {
if (release.tag_name === `v${await this.getPackageVersion()}`) {
console.log(`Downloading restic v${await this.getPackageVersion()}`);
await this.downloadAssets(release, targetFolder);
} else {
continue;
}
}
}
private async fetchReleases(): Promise<IRelease[]> {
const response = await fetch(this.baseUrl);
if (!response.ok) {
throw new Error(`Failed to fetch releases: ${response.statusText}`);
}
return response.json();
}
private async downloadAssets(release: IRelease, targetFolder: string): Promise<void> {
for (const asset of release.assets) {
console.error(`Downloading: ${asset.name}`);
const response = await fetch(asset.url, {
headers: { 'Accept': 'application/octet-stream' }
});
if (!response.ok) {
console.error(`Failed to download asset: ${asset.name}`);
continue;
} else {
console.log(`Downloaded asset: ${asset.name} successfully!!!`);
}
const asyncIterable = {
async *[Symbol.asyncIterator]() {
const reader = response.body.getReader();
while (true) {
const { done, value } = await reader.read();
if (done) break;
yield value;
}
}
};
const readableStream = Readable.from(asyncIterable);
const unpackStream = smartarchive.SmartArchive.fromArchiveStream(readableStream)
unpackStream
}
}
}
// lets do the actual work
const downloader = new ResticReleaseDownloader();
const targetFolder = join(dirname(fileURLToPath(import.meta.url)), '../.nogit/resticbins/');
await fs.mkdir(targetFolder, { recursive: true });
await downloader.downloadAllReleases(targetFolder);