From c5a5c4b8af2a63ded171c332873d34c0bad2e374 Mon Sep 17 00:00:00 2001 From: schroda <50052685+schroda@users.noreply.github.com> Date: Sat, 2 Mar 2024 15:26:15 +0100 Subject: [PATCH] Fix/add manga to library without dialog not adding default categories (#632) * Add default categories when adding manga to library without dialog * Add manga to library and update categories in one mutation --- src/components/manga/MangaDetails.tsx | 15 +++++++++------ src/components/navbar/action/CategorySelect.tsx | 11 ++++++++--- src/lib/data/Mangas.ts | 6 ++++-- src/lib/graphql/generated/graphql.ts | 4 +++- src/lib/graphql/mutations/MangaMutation.ts | 11 ++++++++++- src/lib/requests/RequestManager.ts | 8 ++++++-- 6 files changed, 40 insertions(+), 15 deletions(-) diff --git a/src/components/manga/MangaDetails.tsx b/src/components/manga/MangaDetails.tsx index e37ca40a..11f89575 100644 --- a/src/components/manga/MangaDetails.tsx +++ b/src/components/manga/MangaDetails.tsx @@ -193,9 +193,12 @@ export const MangaDetails: React.FC = ({ manga }) => { } }, [manga.source]); - const addToLibrary = () => { + const addToLibrary = (addToCategories: number[] = [], removeFromCategories: number[] = []) => { requestManager - .updateManga(manga.id, { inLibrary: true }) + .updateManga(manga.id, { + updateManga: { inLibrary: true }, + updateMangaCategories: { addToCategories, removeFromCategories }, + }) .response.then(() => makeToast(t('library.info.label.added_to_library'), 'success')) .catch(() => { makeToast(t('library.error.label.add_to_library'), 'error'); @@ -218,7 +221,7 @@ export const MangaDetails: React.FC = ({ manga }) => { const showCategorySelectDialog = showAddToLibraryCategorySelectDialog && !!userCreatedCategories.length; if (!showCategorySelectDialog) { - addToLibrary(); + addToLibrary(Categories.getIds(Categories.getDefaults(userCreatedCategories!))); return; } @@ -226,7 +229,7 @@ export const MangaDetails: React.FC = ({ manga }) => { }; const removeFromLibrary = () => { - Promise.all([requestManager.updateManga(manga.id, { inLibrary: false }).response]) + Promise.all([requestManager.updateManga(manga.id, { updateManga: { inLibrary: false } }).response]) .then(() => makeToast(t('library.info.label.removed_from_library'), 'success')) .catch(() => { makeToast(t('library.error.label.remove_from_library'), 'error'); @@ -284,11 +287,11 @@ export const MangaDetails: React.FC = ({ manga }) => { {isCategorySelectOpen && ( { + onClose={(didUpdateCategories, addToCategories, removeFromCategories) => { setIsCategorySelectOpen(false); if (didUpdateCategories) { - addToLibrary(); + addToLibrary(addToCategories, removeFromCategories); } }} mangaId={manga.id} diff --git a/src/components/navbar/action/CategorySelect.tsx b/src/components/navbar/action/CategorySelect.tsx index edd75973..8cbbc643 100644 --- a/src/components/navbar/action/CategorySelect.tsx +++ b/src/components/navbar/action/CategorySelect.tsx @@ -28,7 +28,7 @@ import { makeToast } from '@/components/util/Toast.tsx'; type BaseProps = { open: boolean; - onClose: (didUpdateCategories: boolean) => void; + onClose: (didUpdateCategories: boolean, addToCategories?: number[], removeFromCategories?: number[]) => void; }; type SingleMangaModeProps = { @@ -125,8 +125,6 @@ export function CategorySelect(props: Props) { }; const handleOk = () => { - onClose(true); - const addToCategories = isSingleSelectionMode ? categoriesToAdd.filter((categoryId) => !mangaCategoryIds.includes(categoryId)) : categoriesToAdd; @@ -134,6 +132,8 @@ export function CategorySelect(props: Props) { ? mangaCategoryIds.filter((categoryId) => !categoriesToAdd.includes(categoryId)) : categoriesToRemove; + onClose(true, addToCategories, removeFromCategories); + if (doNotShowAddToLibraryDialogAgain) { requestUpdateServerMetadata(convertToGqlMeta(serverMetadata)! ?? {}, [ ['showAddToLibraryCategorySelectDialog', false], @@ -145,6 +145,11 @@ export function CategorySelect(props: Props) { return; } + if (addToLibrary) { + // categories get updated in MangaDetails + return; + } + Mangas.performAction('change_categories', mangaIds, { changeCategoriesPatch: { addToCategories, diff --git a/src/lib/data/Mangas.ts b/src/lib/data/Mangas.ts index d386c813..9433f6a1 100644 --- a/src/lib/data/Mangas.ts +++ b/src/lib/data/Mangas.ts @@ -299,9 +299,11 @@ export class Mangas { ? Mangas.migrateCategories(mangaToMigrateData.manga, mangaToMigrateToData.fetchManga.manga) : undefined, !mangaToMigrateToData.fetchManga.manga.inLibrary - ? requestManager.updateManga(mangaIdToMigrateTo, { inLibrary: true }).response + ? requestManager.updateManga(mangaIdToMigrateTo, { updateManga: { inLibrary: true } }).response + : undefined, + mode === 'migrate' + ? requestManager.updateManga(mangaId, { updateManga: { inLibrary: false } }).response : undefined, - mode === 'migrate' ? requestManager.updateManga(mangaId, { inLibrary: false }).response : undefined, ]); }); } diff --git a/src/lib/graphql/generated/graphql.ts b/src/lib/graphql/generated/graphql.ts index efcfb65c..2872422c 100644 --- a/src/lib/graphql/generated/graphql.ts +++ b/src/lib/graphql/generated/graphql.ts @@ -2833,10 +2833,12 @@ export type SetMangaMetadataMutation = { __typename?: 'Mutation', setMangaMeta: export type UpdateMangaMutationVariables = Exact<{ input: UpdateMangaInput; + updateCategoryInput: UpdateMangaCategoriesInput; + updateCategories: Scalars['Boolean']['input']; }>; -export type UpdateMangaMutation = { __typename?: 'Mutation', updateManga: { __typename?: 'UpdateMangaPayload', clientMutationId?: string | null, manga: { __typename?: 'MangaType', id: number, inLibrary: boolean, inLibraryAt: any, categories: { __typename?: 'CategoryNodeList', totalCount: number, nodes: Array<{ __typename?: 'CategoryType', id: number, mangas: { __typename?: 'MangaNodeList', totalCount: number } }> } } } }; +export type UpdateMangaMutation = { __typename?: 'Mutation', updateManga: { __typename?: 'UpdateMangaPayload', clientMutationId?: string | null, manga: { __typename?: 'MangaType', id: number, inLibrary: boolean, inLibraryAt: any } }, updateMangaCategories?: { __typename?: 'UpdateMangaCategoriesPayload', manga: { __typename?: 'MangaType', id: number, categories: { __typename?: 'CategoryNodeList', totalCount: number, nodes: Array<{ __typename?: 'CategoryType', id: number, mangas: { __typename?: 'MangaNodeList', totalCount: number } }> } } } }; export type UpdateMangasMutationVariables = Exact<{ input: UpdateMangasInput; diff --git a/src/lib/graphql/mutations/MangaMutation.ts b/src/lib/graphql/mutations/MangaMutation.ts index 2e6d368a..0fb6daeb 100644 --- a/src/lib/graphql/mutations/MangaMutation.ts +++ b/src/lib/graphql/mutations/MangaMutation.ts @@ -99,13 +99,22 @@ export const SET_MANGA_METADATA = gql` `; export const UPDATE_MANGA = gql` - mutation UPDATE_MANGA($input: UpdateMangaInput!) { + mutation UPDATE_MANGA( + $input: UpdateMangaInput! + $updateCategoryInput: UpdateMangaCategoriesInput! + $updateCategories: Boolean! + ) { updateManga(input: $input) { clientMutationId manga { id inLibrary inLibraryAt + } + } + updateMangaCategories(input: $updateCategoryInput) @include(if: $updateCategories) { + manga { + id categories { nodes { id diff --git a/src/lib/requests/RequestManager.ts b/src/lib/requests/RequestManager.ts index f852e81a..f1f7588f 100644 --- a/src/lib/requests/RequestManager.ts +++ b/src/lib/requests/RequestManager.ts @@ -1560,13 +1560,17 @@ export class RequestManager { public updateManga( id: number, - patch: UpdateMangaPatchInput, + patch: { updateManga: UpdateMangaPatchInput; updateMangaCategories?: UpdateMangaCategoriesPatchInput }, options?: MutationOptions, ): AbortableApolloMutationResponse { const result = this.doRequest( GQLMethod.MUTATION, UPDATE_MANGA, - { input: { id, patch } }, + { + input: { id, patch: patch.updateManga }, + updateCategoryInput: { id, patch: patch.updateMangaCategories ?? {} }, + updateCategories: !!patch.updateMangaCategories, + }, options, );