Fix handling of disabled manga migration steps

In case e.g., the "tracking" should not get migrated, the "migration action" was still created.
While creating the action, an error was thrown because the "tracking" information was missing, as expected, since it's not required.

To prevent this, the actions should only get created in case they are actually required for the migration.
This commit is contained in:
schroda
2025-08-03 15:41:30 +02:00
parent 5543e134fa
commit 1f55531436

View File

@@ -98,7 +98,8 @@ type PerformActionOptions<Action extends MangaAction> = Action extends 'mark_as_
? DownloadActionOption ? DownloadActionOption
: DefaultActionOption; : DefaultActionOption;
type MigrateFuncReturn = { copy: () => Promise<unknown>[]; cleanup: () => Promise<unknown>[] }; type MigrateAction = { copy: () => Promise<unknown>[]; cleanup: () => Promise<unknown>[] };
type MigrateActionCreator = () => MigrateAction;
const ARTIST_AUTHOR_SEPARATOR_REGEX = /\s*[,|、]\s*/; const ARTIST_AUTHOR_SEPARATOR_REGEX = /\s*[,|、]\s*/;
@@ -313,7 +314,7 @@ export class Mangas {
mangaToMigrate: GetMangaToMigrateQuery['manga'], mangaToMigrate: GetMangaToMigrateQuery['manga'],
mangaToMigrateToInfo: GetMangaToMigrateToFetchMutation, mangaToMigrateToInfo: GetMangaToMigrateToFetchMutation,
deleteChapters: boolean, deleteChapters: boolean,
): MigrateFuncReturn { ): MigrateAction {
if (!mangaToMigrate.chapters || !mangaToMigrateToInfo.fetchChapters?.chapters) { if (!mangaToMigrate.chapters || !mangaToMigrateToInfo.fetchChapters?.chapters) {
throw new Error('Chapters are missing'); throw new Error('Chapters are missing');
} }
@@ -362,7 +363,7 @@ export class Mangas {
mode: MigrateMode, mode: MigrateMode,
mangaToMigrate: MangaToMigrate, mangaToMigrate: MangaToMigrate,
mangaToMigrateTo: MangaToMigrateTo, mangaToMigrateTo: MangaToMigrateTo,
): MigrateFuncReturn { ): MigrateAction {
if (!mangaToMigrate.trackRecords) { if (!mangaToMigrate.trackRecords) {
throw new Error('TrackRecords of manga to migrate are missing'); throw new Error('TrackRecords of manga to migrate are missing');
} }
@@ -403,7 +404,7 @@ export class Mangas {
mangaToMigrateTo: MangaToMigrateTo, mangaToMigrateTo: MangaToMigrateTo,
migrateCategories: boolean, migrateCategories: boolean,
removeMangaFromCategories: boolean, removeMangaFromCategories: boolean,
): MigrateFuncReturn { ): MigrateAction {
if (!mangaToMigrateFrom?.categories) { if (!mangaToMigrateFrom?.categories) {
throw new Error('Categories are missing'); throw new Error('Categories are missing');
} }
@@ -477,18 +478,18 @@ export class Mangas {
} }
const performMigrationAction = async ( const performMigrationAction = async (
migrateAction: keyof MigrateFuncReturn, migrateAction: keyof MigrateAction,
...actions: [boolean | undefined, MigrateFuncReturn][] ...actions: MigrateAction[]
) => ) => Promise.all(actions.map((action) => action[migrateAction]()).flat());
Promise.all(
actions
.filter(([performAction]) => performAction)
.map(([, action]) => action[migrateAction]())
.flat(),
);
const performMigrationActions = async (...actions: [boolean | undefined, MigrateFuncReturn][]) => { const performMigrationActions = async (
const migrationActions: TupleUnion<keyof MigrateFuncReturn> = ['copy', 'cleanup']; ...actionCreators: [boolean | undefined, MigrateActionCreator][]
) => {
const migrationActions: TupleUnion<keyof MigrateAction> = ['copy', 'cleanup'];
const actions = actionCreators
.filter(([performAction]) => performAction)
.map(([, actionCreator]) => actionCreator());
for (const migrationAction of migrationActions) { for (const migrationAction of migrationActions) {
// the migration actions (copy, cleanup) are supposed to be run sequentially to ensure that the cleanup // the migration actions (copy, cleanup) are supposed to be run sequentially to ensure that the cleanup
@@ -501,21 +502,33 @@ export class Mangas {
await performMigrationActions( await performMigrationActions(
[ [
migrateChapters, migrateChapters,
Mangas.migrateChapters(mode, mangaToMigrateData.manga, mangaToMigrateToData, !!deleteChapters), () =>
Mangas.migrateChapters(
mode,
mangaToMigrateData.manga,
mangaToMigrateToData,
!!deleteChapters,
),
], ],
[ [
migrateTracking, migrateTracking,
Mangas.migrateTracking(mode, mangaToMigrateData.manga, mangaToMigrateToData.fetchManga.manga), () =>
Mangas.migrateTracking(
mode,
mangaToMigrateData.manga,
mangaToMigrateToData.fetchManga!.manga,
),
], ],
[ [
true, true,
Mangas.migrateManga( () =>
mode, Mangas.migrateManga(
mangaToMigrateData.manga, mode,
mangaToMigrateToData.fetchManga.manga, mangaToMigrateData.manga,
!!migrateCategories, mangaToMigrateToData.fetchManga!.manga,
removeMangaFromCategories, !!migrateCategories,
), removeMangaFromCategories,
),
], ],
); );
}, },