Rustelo/features/content-graph/scripts/download/download-cytoscape.js
Jesús Pérez c0281e759c
chore: update
2026-07-18 20:14:32 +01:00

76 lines
2.2 KiB
JavaScript

#!/usr/bin/env node
// Download Cytoscape.js + cose-bilkent layout plugin from CDN.
// Skips download if files exist and are < 30 days old.
//
// Usage:
// node scripts/download/download-cytoscape.js
import fs from 'fs';
import path from 'path';
import https from 'https';
import { fileURLToPath } from 'url';
const __dirname = path.dirname(fileURLToPath(import.meta.url));
const PUBLIC_JS = path.join(__dirname, '../../site/public/js');
const ASSETS = [
{
url: 'https://cdnjs.cloudflare.com/ajax/libs/cytoscape/3.29.2/cytoscape.min.js',
out: 'cytoscape.min.js',
name: 'Cytoscape.js 3.29.2',
},
{
url: 'https://cdn.jsdelivr.net/npm/cytoscape-cose-bilkent@4.1.0/cytoscape-cose-bilkent.js',
out: 'cytoscape-cose-bilkent.js',
name: 'cose-bilkent layout 4.1.0',
},
];
const MAX_AGE_MS = 30 * 24 * 60 * 60 * 1000;
function download(url, dest) {
return new Promise((resolve, reject) => {
https.get(url, (res) => {
if (res.statusCode === 301 || res.statusCode === 302) {
return download(res.headers.location, dest).then(resolve).catch(reject);
}
if (res.statusCode !== 200) {
return reject(new Error(`HTTP ${res.statusCode}: ${url}`));
}
const chunks = [];
res.on('data', (c) => chunks.push(c));
res.on('end', () => {
fs.mkdirSync(path.dirname(dest), { recursive: true });
fs.writeFileSync(dest, Buffer.concat(chunks));
resolve();
});
}).on('error', reject);
});
}
async function main() {
for (const asset of ASSETS) {
const dest = path.join(PUBLIC_JS, asset.out);
if (fs.existsSync(dest)) {
const age = Date.now() - fs.statSync(dest).mtimeMs;
if (age < MAX_AGE_MS) {
const kb = (fs.statSync(dest).size / 1024).toFixed(1);
console.log(`skip ${asset.name} (${kb} kB, cached)`);
continue;
}
}
process.stdout.write(`get ${asset.name} ... `);
try {
await download(asset.url, dest);
const kb = (fs.statSync(dest).size / 1024).toFixed(1);
console.log(`ok (${kb} kB)`);
} catch (err) {
console.error(`\nfail ${asset.name}: ${err.message}`);
process.exit(1);
}
}
}
main();