73 lines
2.6 KiB
TypeScript
73 lines
2.6 KiB
TypeScript
import { PrismaClient } from '@prisma/client';
|
|
import { parseFile } from 'music-metadata';
|
|
import path from 'path';
|
|
import fs from 'fs/promises';
|
|
|
|
const prisma = new PrismaClient();
|
|
const UPLOADS_DIR = path.join(process.cwd(), 'public/uploads');
|
|
|
|
async function restoreSongs() {
|
|
console.log('Starting song restoration...');
|
|
|
|
try {
|
|
const files = await fs.readdir(UPLOADS_DIR);
|
|
const mp3Files = files.filter(f => f.endsWith('.mp3'));
|
|
|
|
console.log(`Found ${mp3Files.length} MP3 files.`);
|
|
|
|
for (const filename of mp3Files) {
|
|
// Check if song already exists
|
|
const existing = await prisma.song.findFirst({
|
|
where: { filename }
|
|
});
|
|
|
|
if (existing) {
|
|
console.log(`Skipping ${filename} (already exists)`);
|
|
continue;
|
|
}
|
|
|
|
const filePath = path.join(UPLOADS_DIR, filename);
|
|
|
|
try {
|
|
const metadata = await parseFile(filePath);
|
|
|
|
const title = metadata.common.title || 'Unknown Title';
|
|
const artist = metadata.common.artist || 'Unknown Artist';
|
|
|
|
// Try to find matching cover
|
|
// This is a best-effort guess based on timestamp or just null if we can't link it easily
|
|
// Since we don't store the link between file and cover in filename, we might lose cover association
|
|
// unless we re-extract it. But we already have cover files.
|
|
// For now, let's just restore the song entry. Re-extracting cover would duplicate files.
|
|
// If the user wants covers back perfectly, we might need to re-parse or just leave null.
|
|
// Let's leave null for now to avoid clutter, or maybe try to find a cover with similar timestamp if possible?
|
|
// Actually, the cover filename is not easily deducible from song filename.
|
|
// Let's just restore the song data.
|
|
|
|
await prisma.song.create({
|
|
data: {
|
|
title,
|
|
artist,
|
|
filename,
|
|
// coverImage: null // We lose the cover link unfortunately, unless we re-extract
|
|
}
|
|
});
|
|
|
|
console.log(`Restored: ${title} - ${artist}`);
|
|
|
|
} catch (e) {
|
|
console.error(`Failed to process ${filename}:`, e);
|
|
}
|
|
}
|
|
|
|
console.log('Restoration complete.');
|
|
|
|
} catch (e) {
|
|
console.error('Error reading uploads directory:', e);
|
|
} finally {
|
|
await prisma.$disconnect();
|
|
}
|
|
}
|
|
|
|
restoreSongs();
|