Files
f0ckm/scripts/recreate_covers.mjs
2026-04-25 19:51:52 +02:00

54 lines
1.9 KiB
JavaScript

import db from "../src/inc/sql.mjs";
import cfg from "../src/inc/config.mjs";
import queue from "../src/inc/queue.mjs";
import fs from "fs";
import path from "path";
async function run() {
console.log("[BOOT] Starting coverart recreation script...");
const audioItems = await db`SELECT id, dest, mime FROM items WHERE mime LIKE 'audio/%' AND is_deleted = false`;
console.log(`[INFO] Found ${audioItems.length} audio items.`);
let count = 0;
for (const item of audioItems) {
process.stdout.write(`\r[${++count}/${audioItems.length}] Processing ${item.id}...`);
try {
const caPath = path.join(cfg.paths.ca, `${item.id}.webp`);
const tPath = path.join(cfg.paths.t, `${item.id}.webp`);
let needsProcessing = !fs.existsSync(caPath);
if (!needsProcessing) {
const stats = fs.statSync(caPath);
if (stats.size < 5000) needsProcessing = true; // Detect old gray placeholder
}
if (needsProcessing) {
try {
// Try extraction first
await queue.genThumbnail(item.dest, item.mime, item.id, '', false);
} catch (e) {
// If extraction fails, use the music.webp fallback
await fs.promises.copyFile('public/s/img/music.webp', caPath);
}
}
if (!fs.existsSync(tPath)) {
try {
await queue.spawn('magick', ['-size', '128x128', 'xc:#1a1a1a', tPath]);
} catch (err) { }
}
} catch (e) {
console.error(`\n[ERROR] ${item.id} processing failed:`, e.message);
}
}
console.log("\n[FINISH] All audio items processed.");
process.exit(0);
}
run().catch(err => {
console.error("[FATAL]", err);
process.exit(1);
});