From a98763c83348bc33355851db3e45409bf0e921ba Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Pawe=C5=82=20Chy=C5=82a?= Date: Mon, 11 Mar 2024 09:57:07 +0100 Subject: [PATCH] Prevent warehouses fetch when no channels in variant details (#4712) * Prevent warehouses fetch when no channels * Add changeset * useAllwarehouses hook with tests --- .changeset/tender-windows-invent.md | 5 ++ .../views/ProductVariant/ProductVariant.tsx | 14 +--- .../ProductVariant/useAllWarehouses.test.ts | 72 +++++++++++++++++++ .../views/ProductVariant/useAllWarehouses.ts | 20 ++++++ 4 files changed, 100 insertions(+), 11 deletions(-) create mode 100644 .changeset/tender-windows-invent.md create mode 100644 src/products/views/ProductVariant/useAllWarehouses.test.ts create mode 100644 src/products/views/ProductVariant/useAllWarehouses.ts diff --git a/.changeset/tender-windows-invent.md b/.changeset/tender-windows-invent.md new file mode 100644 index 00000000000..da92cd5f282 --- /dev/null +++ b/.changeset/tender-windows-invent.md @@ -0,0 +1,5 @@ +--- +"saleor-dashboard": patch +--- + +Prevent unnecessary warehouses fetch in product variant details when variant has not channel assigned diff --git a/src/products/views/ProductVariant/ProductVariant.tsx b/src/products/views/ProductVariant/ProductVariant.tsx index 731cd6f4aa9..ce5e7c16ab1 100644 --- a/src/products/views/ProductVariant/ProductVariant.tsx +++ b/src/products/views/ProductVariant/ProductVariant.tsx @@ -29,7 +29,6 @@ import { useVariantMediaUnassignMutation, useVariantUpdateMutation, } from "@dashboard/graphql"; -import { useFetchAllWarehouses } from "@dashboard/hooks/useFetchAllWarehouse"; import useNavigator from "@dashboard/hooks/useNavigator"; import useNotifier from "@dashboard/hooks/useNotifier"; import useOnSetDefaultVariant from "@dashboard/hooks/useOnSetDefaultVariant"; @@ -59,6 +58,7 @@ import { } from "../../urls"; import { mapFormsetStockToStockInput } from "../../utils/data"; import { createVariantReorderHandler } from "./../ProductUpdate/handlers"; +import { useAllWarehouses } from "./useAllWarehouses"; import { useSubmitChannels } from "./useSubmitChannels"; interface ProductUpdateProps { @@ -141,15 +141,7 @@ export const ProductVariant: React.FC = ({ const variant = data?.productVariant; const channels = createVariantChannels(variant); - const warehouses = useFetchAllWarehouses({ - displayLoader: true, - variables: { - first: 100, - filter: { - channels: channels.map(channel => channel.id), - }, - }, - }); + const warehouses = useAllWarehouses(channels); const [deactivatePreorder, deactivatePreoderOpts] = useProductVariantPreorderDeactivateMutation({}); @@ -325,7 +317,7 @@ export const ProductVariant: React.FC = ({ placeholderImage={placeholderImg} variant={variant} header={variant?.name || variant?.sku} - warehouses={mapEdgesToItems(warehouses?.data?.warehouses) || []} + warehouses={warehouses} onDelete={() => openModal("remove")} onSubmit={handleSubmit} onWarehouseConfigure={() => navigate(warehouseAddPath)} diff --git a/src/products/views/ProductVariant/useAllWarehouses.test.ts b/src/products/views/ProductVariant/useAllWarehouses.test.ts new file mode 100644 index 00000000000..5b26c927b23 --- /dev/null +++ b/src/products/views/ProductVariant/useAllWarehouses.test.ts @@ -0,0 +1,72 @@ +import { ChannelPriceData } from "@dashboard/channels/utils"; +import { useFetchAllWarehouses } from "@dashboard/hooks/useFetchAllWarehouse"; + +import { useAllWarehouses } from "./useAllWarehouses"; + +jest.mock("@dashboard/hooks/useFetchAllWarehouse"); + +describe("useAllWarehouses", () => { + it("should skip query when no channels and return empty array", () => { + // Arrange + const mockedUseFetchAllWarehouses = jest.fn(); + (useFetchAllWarehouses as jest.Mock).mockImplementation( + mockedUseFetchAllWarehouses, + ); + + // Act + const result = useAllWarehouses([]); + + // Assert + expect(result).toEqual([]); + expect(mockedUseFetchAllWarehouses).toHaveBeenCalledWith({ + displayLoader: true, + skip: true, + variables: { + filter: { + channels: [], + }, + first: 100, + }, + }); + }); + + it("should run query when channels provided", () => { + // Arrange + const mockedUseFetchAllWarehouses = jest.fn(() => ({ + data: { + warehouses: { + edges: [ + { + node: { + id: "1", + }, + }, + ], + }, + }, + })); + (useFetchAllWarehouses as jest.Mock).mockImplementation( + mockedUseFetchAllWarehouses, + ); + + // Act + const result = useAllWarehouses([ + { + id: "1", + }, + ] as ChannelPriceData[]); + + // Assert + expect(result).toEqual([{ id: "1" }]); + expect(mockedUseFetchAllWarehouses).toHaveBeenCalledWith({ + displayLoader: true, + skip: false, + variables: { + filter: { + channels: ["1"], + }, + first: 100, + }, + }); + }); +}); diff --git a/src/products/views/ProductVariant/useAllWarehouses.ts b/src/products/views/ProductVariant/useAllWarehouses.ts new file mode 100644 index 00000000000..fce39234d94 --- /dev/null +++ b/src/products/views/ProductVariant/useAllWarehouses.ts @@ -0,0 +1,20 @@ +import { ChannelPriceData } from "@dashboard/channels/utils"; +import { useFetchAllWarehouses } from "@dashboard/hooks/useFetchAllWarehouse"; +import { mapEdgesToItems } from "@dashboard/utils/maps"; + +export const useAllWarehouses = (channels: ChannelPriceData[]) => { + const channelsIds = channels.map(channel => channel.id); + + const warehouses = useFetchAllWarehouses({ + displayLoader: true, + skip: !channelsIds.length, + variables: { + first: 100, + filter: { + channels: channelsIds, + }, + }, + }); + + return mapEdgesToItems(warehouses?.data?.warehouses) || []; +};