Enrich audiobook metadata from Audnexus

Query Audnexus (Audible) to backfill missing metadata during manual imports and file organization. Adds getAudibleService imports and calls to fetch audiobook details by ASIN, then backfills series, seriesPart, seriesAsin, year (from releaseDate) and narrator when missing and updates the DB. Failures are non-fatal and logged; logs were added to surface enrichment steps. Also uses the resolved series/seriesPart when building organization metadata.
This commit is contained in:
kikootwo
2026-03-04 12:19:37 -05:00
parent cbf02d3e24
commit d0ce485bdc
2 changed files with 152 additions and 3 deletions
+43
View File
@@ -12,6 +12,7 @@ import { prisma } from '@/lib/db';
import { getJobQueueService } from '@/lib/services/job-queue.service';
import { RMABLogger } from '@/lib/utils/logger';
import { AUDIO_EXTENSIONS } from '@/lib/constants/audio-formats';
import { getAudibleService } from '@/lib/integrations/audible.service';
const logger = RMABLogger.create('API.Admin.ManualImport');
@@ -174,6 +175,48 @@ export async function POST(request: NextRequest) {
);
}
// Enrich missing series/year data from Audnexus (mirrors request-creator.service.ts)
if (audiobook.audibleAsin && (!audiobook.series || !audiobook.year)) {
try {
const audibleService = getAudibleService();
const audnexusData = await audibleService.getAudiobookDetails(audiobook.audibleAsin);
if (audnexusData) {
const updates: Record<string, any> = {};
if (!audiobook.series && audnexusData.series) {
updates.series = audnexusData.series;
}
if (!audiobook.seriesPart && audnexusData.seriesPart) {
updates.seriesPart = audnexusData.seriesPart;
}
if (!audiobook.seriesAsin && audnexusData.seriesAsin) {
updates.seriesAsin = audnexusData.seriesAsin;
}
if (!audiobook.year && audnexusData.releaseDate) {
const releaseYear = new Date(audnexusData.releaseDate).getFullYear();
if (!isNaN(releaseYear)) {
updates.year = releaseYear;
}
}
if (!audiobook.narrator && audnexusData.narrator) {
updates.narrator = audnexusData.narrator;
}
if (Object.keys(updates).length > 0) {
await prisma.audiobook.update({
where: { id: audiobook.id },
data: updates,
});
logger.info(`Enriched audiobook metadata from Audnexus for ASIN ${audiobook.audibleAsin}`, updates);
}
}
} catch (error) {
// Non-fatal: series enrichment failure should never block the import
logger.warn(`Failed to enrich metadata from Audnexus for ASIN ${audiobook.audibleAsin}: ${error instanceof Error ? error.message : String(error)}`);
}
}
// Check for existing requests
const existingRequest = await prisma.request.findFirst({
where: {