Extract migration entry search state update into function

This commit is contained in:
schroda
2026-06-21 15:36:12 +02:00
parent 0f12bf0607
commit 792c034599
2 changed files with 68 additions and 55 deletions

View File

@@ -7,9 +7,11 @@
*/ */
import type { import type {
ChapterListFieldsFragment,
GetMangaToMigrateQuery, GetMangaToMigrateQuery,
GetMangaToMigrateToFetchMutation, GetMangaToMigrateToFetchMutation,
GetMigratableSourcesQuery, GetMigratableSourcesQuery,
MangaMigrationFieldsFragment,
} from '@/lib/graphql/generated/graphql.ts'; } from '@/lib/graphql/generated/graphql.ts';
import type { import type {
SourceDisplayNameInfo, SourceDisplayNameInfo,
@@ -176,3 +178,8 @@ export type MigrationChapter = ChapterIdInfo &
export type MigrateAction = { copy: () => Promise<unknown>[]; cleanup: () => Promise<unknown>[] }; export type MigrateAction = { copy: () => Promise<unknown>[]; cleanup: () => Promise<unknown>[] };
export type MigrateActionCreator = () => MigrateAction; export type MigrateActionCreator = () => MigrateAction;
export type EntrySourceSearchResult = {
manga: MangaMigrationFieldsFragment;
chapters: ChapterListFieldsFragment[] | null;
};

View File

@@ -12,6 +12,7 @@ import { create } from 'zustand';
import { immer } from 'zustand/middleware/immer'; import { immer } from 'zustand/middleware/immer';
import { devtools, persist } from 'zustand/middleware'; import { devtools, persist } from 'zustand/middleware';
import { import {
type EntrySourceSearchResult,
type MigratableEntry, type MigratableEntry,
type MigrateOptions, type MigrateOptions,
type MigrationBulkSearchSettings, type MigrationBulkSearchSettings,
@@ -33,7 +34,6 @@ import {
import { requestManager } from '@/lib/requests/RequestManager.ts'; import { requestManager } from '@/lib/requests/RequestManager.ts';
import { GET_MIGRATION_SOURCE_MANGAS_FETCH } from '@/lib/graphql/source/SourceMutation.ts'; import { GET_MIGRATION_SOURCE_MANGAS_FETCH } from '@/lib/graphql/source/SourceMutation.ts';
import type { import type {
ChapterListFieldsFragment,
GetMigrationSourceMangasFetchMutation, GetMigrationSourceMangasFetchMutation,
GetMigrationSourceMangasFetchMutationVariables, GetMigrationSourceMangasFetchMutationVariables,
GetServerSettingsQuery, GetServerSettingsQuery,
@@ -796,7 +796,7 @@ export class MigrationManager {
sourceId: SourceIdInfo['id'], sourceId: SourceIdInfo['id'],
signal: AbortSignal, signal: AbortSignal,
{ selectHighestChapterNumberSource, performAdvancedSearch }: MigrationBulkSearchSettings, { selectHighestChapterNumberSource, performAdvancedSearch }: MigrationBulkSearchSettings,
): Promise<{ manga: MangaMigrationFieldsFragment; chapters: ChapterListFieldsFragment[] | null }[]> { ): Promise<EntrySourceSearchResult[]> {
if (signal.aborted) { if (signal.aborted) {
throw new Error(signal.reason); throw new Error(signal.reason);
} }
@@ -891,57 +891,17 @@ export class MigrationManager {
return updatedMatches; return updatedMatches;
} }
private static async searchForMangaInSource( private static updateEntrySearchState(
sourceId: SourceIdInfo['id'],
mangaId: MangaIdInfo['id'], mangaId: MangaIdInfo['id'],
mangaTitle: string, sourceId: SourceIdInfo['id'],
signal: AbortSignal, foundMatches: EntrySourceSearchResult[],
searchController: AbortController, {
options: MigrationBulkSearchSettings,
): Promise<void> {
const {
selectHighestChapterNumberSource, selectHighestChapterNumberSource,
ignoreOutdatedMatches, ignoreOutdatedMatches,
requireAdditionalChapters, requireAdditionalChapters,
ignoreWithMissingChapters, ignoreWithMissingChapters,
} = options; }: MigrationBulkSearchSettings,
): void {
signal.throwIfAborted();
if (!selectHighestChapterNumberSource && MigrationManager.hasHigherSourcePriorityMatch(mangaId, sourceId)) {
return;
}
const foundMatches = await (async () => {
try {
return await MigrationManager.findMatchesForMangaInSource(
mangaId,
mangaTitle,
sourceId,
signal,
options,
);
} catch (e) {
MigrationManager.updateState((draft) => {
const draftEntry = draft.entries[mangaId];
draftEntry.destSourceIdToSearchState[sourceId] = false;
});
throw e;
}
})();
if (!foundMatches.length) {
MigrationManager.updateState((draft) => {
const draftEntry = draft.entries[mangaId];
draftEntry.destSourceIdToSearchState[sourceId] = false;
});
return;
}
MigrationManager.updateState((draft) => { MigrationManager.updateState((draft) => {
const draftEntry = draft.entries[mangaId]; const draftEntry = draft.entries[mangaId];
const draftMatchEntry = draftEntry.selectedMatchMangaId const draftMatchEntry = draftEntry.selectedMatchMangaId
@@ -1009,14 +969,60 @@ export class MigrationManager {
draftEntry.selectedMatchMangaId = bestMatch.id; draftEntry.selectedMatchMangaId = bestMatch.id;
draftEntry.selectedMatchSourceId = sourceId; draftEntry.selectedMatchSourceId = sourceId;
} }
});
}
if ( private static async searchForMangaInSource(
!selectHighestChapterNumberSource && sourceId: SourceIdInfo['id'],
!MigrationManager.isHigherPrioritySourceUnsettled(mangaId, sourceId) mangaId: MangaIdInfo['id'],
) { mangaTitle: string,
signal: AbortSignal,
searchController: AbortController,
options: MigrationBulkSearchSettings,
): Promise<void> {
const { selectHighestChapterNumberSource } = options;
signal.throwIfAborted();
if (!selectHighestChapterNumberSource && MigrationManager.hasHigherSourcePriorityMatch(mangaId, sourceId)) {
return;
}
const foundMatches = await (async () => {
try {
return await MigrationManager.findMatchesForMangaInSource(
mangaId,
mangaTitle,
sourceId,
signal,
options,
);
} catch (e) {
MigrationManager.updateState((draft) => {
const draftEntry = draft.entries[mangaId];
draftEntry.destSourceIdToSearchState[sourceId] = false;
});
throw e;
}
})();
if (!foundMatches.length) {
MigrationManager.updateState((draft) => {
const draftEntry = draft.entries[mangaId];
draftEntry.destSourceIdToSearchState[sourceId] = false;
});
return;
}
MigrationManager.updateEntrySearchState(mangaId, sourceId, foundMatches, options);
if (!selectHighestChapterNumberSource && !MigrationManager.isHigherPrioritySourceUnsettled(mangaId, sourceId)) {
searchController.abort(`Found best match in source "${sourceId}"`); searchController.abort(`Found best match in source "${sourceId}"`);
} }
});
} }
private static async searchForManga( private static async searchForManga(