List of manga entries to process.
Size of each batch (default: 50).
Parsing configuration.
Result containing processed entries, validation errors, and statistics.
export function processKenmeiMangaBatches(
mangaList: KenmeiManga[],
batchSize = 50,
options: Partial<KenmeiParseOptions> = {},
): ProcessingResult {
return withGroup(
`[KenmeiParser] Process Batches (${mangaList.length} entries, batch size ${batchSize})`,
() => {
const parseOptions = { ...DEFAULT_PARSE_OPTIONS, ...options };
const validationErrors: ValidationError[] = [];
const processedEntries: KenmeiManga[] = [];
const now = () =>
typeof globalThis.performance?.now === "function"
? globalThis.performance.now()
: Date.now();
const startTime = now();
console.info(
`[KenmeiParser] Batch processing started — totalEntries=${mangaList.length}, batchSize=${batchSize}`,
);
try {
if (mangaList.length === 0) {
console.info(`[KenmeiParser] No manga entries to process`);
return {
processedEntries,
validationErrors,
totalEntries: 0,
successfulEntries: 0,
};
}
processBatchIteration(
mangaList,
batchSize,
parseOptions,
validationErrors,
processedEntries,
);
const durationMs = Math.round(now() - startTime);
console.info(
`[KenmeiParser] Batch processing completed — processed=${processedEntries.length}, errors=${validationErrors.length}, duration=${durationMs}ms`,
);
logValidationErrors(validationErrors);
return {
processedEntries,
validationErrors,
totalEntries: mangaList.length,
successfulEntries: processedEntries.length,
};
} catch (err) {
const elapsed = Math.round(now() - startTime);
if (err instanceof Error) {
console.error(
`[KenmeiParser] Fatal error during batch processing after ${elapsed}ms: ${err.message}`,
);
} else {
console.error(
`[KenmeiParser] Unknown fatal error during batch processing after ${elapsed}ms`,
);
}
throw err;
}
},
);
}
Process Kenmei manga list in batches with validation and normalization.