-
Notifications
You must be signed in to change notification settings - Fork 33
/
install.js
154 lines (133 loc) · 5.09 KB
/
install.js
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
146
147
148
149
150
151
152
153
154
'use strict';
const path = require('path');
const fs = require('fs');
const extractZip = require('extract-zip');
const got = require('got');
const tmp = require('tmp');
const debug = require('debug')('node-chromium');
const rimraf = require('rimraf');
const ProgressBar = require('progress');
const config = require('./config');
const utils = require('./utils');
const cache = require('./cache');
let progressBar = null;
/* eslint unicorn/prevent-abbreviations: ["off"] */
function createTempFile() {
return new Promise((resolve, reject) => {
tmp.file((error, path) => {
if (error) {
console.log('An error occured while trying to create temporary file', error);
reject(error);
} else {
resolve(path);
}
});
});
}
/**
* Downloads the Chromium archive from the default CDN or mirror if configured.
* If the required archive is retrieved from the cache directory then the download will be skipped.
* @param {string} revision The Chromium revision to download.
*/
async function downloadChromiumRevision(revision) {
const cacheEntry = cache.get(revision);
if (cacheEntry) {
debug('Found Chromium archive in cache, skipping download');
return Promise.resolve(cacheEntry);
}
debug('Downloading Chromium archive from Google CDN');
const url = utils.getDownloadUrl(revision);
const tmpPath = await createTempFile();
return _downloadFile(url, tmpPath).then(tmpPath => {
cache.put(revision, tmpPath);
return tmpPath;
});
}
function _downloadFile(url, destPath) {
return new Promise((resolve, reject) => {
got.stream(url, utils.getRequestOptions(url))
.on('downloadProgress', onProgress)
.on('error', error => {
console.error('An error occurred while trying to download file', error.message);
reject(error);
})
.pipe(fs.createWriteStream(destPath))
.on('error', error => {
console.error('An error occurred while trying to save file to disk', error);
reject(error);
})
.on('finish', () => {
resolve(destPath);
});
});
}
/**
* Handles download progress events.
* @param progress Information about progress so far.
*/
function onProgress(progress) {
const fakeProgressBar = {tick: () => {}};
try {
if (!progressBar) {
const formatBytes = bytes => {
const mb = bytes / 1024 / 1024;
return `${Math.round(mb * 10) / 10} MB`;
};
if (progress.total) {
progressBar = new ProgressBar(`Downloading Chromium - ${formatBytes(progress.total)} [:bar] :percent :etas `, {
width: 20,
total: progress.total
});
} else {
progressBar = fakeProgressBar;
console.info('\tPlease wait, this may take a while...');
}
}
progressBar.tick(progress.transferred - progressBar.curr);
} catch (error) {
// Don't die on progress bar failure, log it and stop progress
console.error('Error displaying progress bar. Continuing anyway...', error);
progressBar = fakeProgressBar;
}
}
function unzipArchive(archivePath, outputFolder) {
debug('Started extracting archive', archivePath);
return new Promise((resolve, reject) => {
const osOutputFolder = path.join(outputFolder, utils.getOsChromiumFolderName());
rimraf(osOutputFolder, () => {
extractZip(archivePath, {dir: outputFolder}, error => {
if (error) {
console.error('An error occurred while trying to extract archive', error);
reject(error);
} else {
debug('Archive was successfully extracted');
resolve(true);
}
});
});
});
}
async function install() {
const chromiumRevision = config.getEnvVar('NODE_CHROMIUM_REVISION');
try {
console.info('Step 1. Retrieving Chromium revision number');
const revision = chromiumRevision || await utils.getLatestRevisionNumber();
console.info(`Step 2. Downloading Chromium revision ${revision}`);
const archivePath = await downloadChromiumRevision(revision);
console.info('Step 3. Setting up Chromium binaries');
await unzipArchive(archivePath, config.BIN_OUT_PATH);
console.info('Process is successfully finished');
} catch (error) {
console.error('An error occurred while trying to setup Chromium. Resolve all issues and restart the process', error);
}
}
if (require.main === module) {
// Module called directly, not via "require", so execute install...
if (config.getEnvVar('NODE_CHROMIUM_SKIP_INSTALL').toLowerCase() === 'true') {
console.info('Skipping chromium install');
} else {
install();
}
}
tmp.setGracefulCleanup(); // Ensure temporary files are cleaned up when process exits
module.exports = install;