mirror of
https://github.com/duckietm/Nitro-V3.git
synced 2026-06-20 15:36:18 +00:00
Migrate catalog giftConfiguration to useNitroQuery
The catalog's gift wrapping configuration was loaded by an effect in useCatalog that fired GetGiftWrappingConfigurationComposer every time the catalog opened, with the response stuffed into a catalogOptions slice via setState-in-effect. Migrating to a TanStack query gives us caching/dedup/loading-state for free on this one-shot session-stable loader. - New useGiftConfiguration() hook in src/hooks/catalog/ wraps the composer/parser pair with useNitroQuery and staleTime: Infinity (the wrapping config never changes within a session). - CatalogGiftView now reads from the query directly instead of via catalogOptions; the useCatalog() call in that component is also dropped (no other field was used). - useCatalog drops the GiftWrappingConfigurationEvent listener and the unconditional composer dispatch. - ICatalogOptions loses the giftConfiguration? field — no remaining consumer. First step toward the docs/ARCHITECTURE.md next-PR item 'Migrate useCatalog read-only fetches to useNitroQuery'. The clubGifts loader will follow once useNitroEventInvalidator lands (clubGifts can be push-updated by the server after SelectClubGiftComposer, so it needs cache invalidation, not just a one-shot fetch).
This commit is contained in:
@@ -1,6 +1,5 @@
|
|||||||
import { ClubGiftInfoParser, ClubOfferData, HabboGroupEntryData, MarketplaceConfigurationMessageParser } from '@nitrots/nitro-renderer';
|
import { ClubGiftInfoParser, ClubOfferData, HabboGroupEntryData, MarketplaceConfigurationMessageParser } from '@nitrots/nitro-renderer';
|
||||||
import { CatalogPetPalette } from './CatalogPetPalette';
|
import { CatalogPetPalette } from './CatalogPetPalette';
|
||||||
import { GiftWrappingConfiguration } from './GiftWrappingConfiguration';
|
|
||||||
|
|
||||||
export interface ICatalogOptions
|
export interface ICatalogOptions
|
||||||
{
|
{
|
||||||
@@ -9,6 +8,5 @@ export interface ICatalogOptions
|
|||||||
clubOffers?: ClubOfferData[];
|
clubOffers?: ClubOfferData[];
|
||||||
clubOffersByWindowId?: Record<number, ClubOfferData[]>;
|
clubOffersByWindowId?: Record<number, ClubOfferData[]>;
|
||||||
clubGifts?: ClubGiftInfoParser;
|
clubGifts?: ClubGiftInfoParser;
|
||||||
giftConfiguration?: GiftWrappingConfiguration;
|
|
||||||
marketplaceConfiguration?: MarketplaceConfigurationMessageParser;
|
marketplaceConfiguration?: MarketplaceConfigurationMessageParser;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -4,7 +4,7 @@ import { FaChevronLeft, FaChevronRight } from 'react-icons/fa';
|
|||||||
import { ColorUtils, LocalizeText, MessengerFriend, ProductTypeEnum, SendMessageComposer } from '../../../../api';
|
import { ColorUtils, LocalizeText, MessengerFriend, ProductTypeEnum, SendMessageComposer } from '../../../../api';
|
||||||
import { Button, Column, Flex, FormGroup, LayoutCurrencyIcon, LayoutFurniImageView, LayoutGiftTagView, NitroCardContentView, NitroCardHeaderView, NitroCardView, Text } from '../../../../common';
|
import { Button, Column, Flex, FormGroup, LayoutCurrencyIcon, LayoutFurniImageView, LayoutGiftTagView, NitroCardContentView, NitroCardHeaderView, NitroCardView, Text } from '../../../../common';
|
||||||
import { CatalogEvent, CatalogInitGiftEvent, CatalogPurchasedEvent } from '../../../../events';
|
import { CatalogEvent, CatalogInitGiftEvent, CatalogPurchasedEvent } from '../../../../events';
|
||||||
import { useCatalog, useFriends, useMessageEvent, useUiEvent } from '../../../../hooks';
|
import { useFriends, useGiftConfiguration, useMessageEvent, useUiEvent } from '../../../../hooks';
|
||||||
import { classNames } from '../../../../layout';
|
import { classNames } from '../../../../layout';
|
||||||
|
|
||||||
let isBuyingGift = false;
|
let isBuyingGift = false;
|
||||||
@@ -25,9 +25,8 @@ export const CatalogGiftView: FC<{}> = props =>
|
|||||||
const [ maxBoxIndex, setMaxBoxIndex ] = useState<number>(0);
|
const [ maxBoxIndex, setMaxBoxIndex ] = useState<number>(0);
|
||||||
const [ maxRibbonIndex, setMaxRibbonIndex ] = useState<number>(0);
|
const [ maxRibbonIndex, setMaxRibbonIndex ] = useState<number>(0);
|
||||||
const [ receiverNotFound, setReceiverNotFound ] = useState<boolean>(false);
|
const [ receiverNotFound, setReceiverNotFound ] = useState<boolean>(false);
|
||||||
const { catalogOptions = null } = useCatalog();
|
|
||||||
const { friends } = useFriends();
|
const { friends } = useFriends();
|
||||||
const { giftConfiguration = null } = catalogOptions;
|
const { data: giftConfiguration = null } = useGiftConfiguration();
|
||||||
const [ boxTypes, setBoxTypes ] = useState<number[]>([]);
|
const [ boxTypes, setBoxTypes ] = useState<number[]>([]);
|
||||||
const [ suggestions, setSuggestions ] = useState([]);
|
const [ suggestions, setSuggestions ] = useState([]);
|
||||||
const [ isAutocompleteVisible, setIsAutocompleteVisible ] = useState(true);
|
const [ isAutocompleteVisible, setIsAutocompleteVisible ] = useState(true);
|
||||||
|
|||||||
@@ -2,3 +2,4 @@ export * from './useCatalog';
|
|||||||
export * from './useCatalogFavorites';
|
export * from './useCatalogFavorites';
|
||||||
export * from './useCatalogPlaceMultipleItems';
|
export * from './useCatalogPlaceMultipleItems';
|
||||||
export * from './useCatalogSkipPurchaseConfirmation';
|
export * from './useCatalogSkipPurchaseConfirmation';
|
||||||
|
export * from './useGiftConfiguration';
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
import { BuildersClubFurniCountMessageEvent, BuildersClubPlaceRoomItemMessageComposer, BuildersClubPlaceWallItemMessageComposer, BuildersClubQueryFurniCountMessageComposer, BuildersClubSubscriptionStatusMessageEvent, CatalogPageMessageEvent, CatalogPagesListEvent, CatalogPublishedMessageEvent, ClubGiftInfoEvent, CreateLinkEvent, FrontPageItem, FurniturePlaceComposer, FurniturePlacePaintComposer, GetCatalogIndexComposer, GetCatalogPageComposer, GetClubGiftInfo, GetGiftWrappingConfigurationComposer, GetRoomEngine, GetSessionDataManager, GetTickerTime, GiftWrappingConfigurationEvent, GuildMembershipsMessageEvent, HabboClubOffersMessageEvent, LegacyDataType, LimitedEditionSoldOutEvent, MarketplaceMakeOfferResult, NodeData, ProductOfferEvent, PurchaseErrorMessageEvent, PurchaseFromCatalogComposer, PurchaseNotAllowedMessageEvent, PurchaseOKMessageEvent, RoomControllerLevel, RoomEngineObjectPlacedEvent, RoomObjectCategory, RoomObjectPlacementSource, RoomObjectType, RoomObjectVariable, RoomPreviewer, SellablePetPalettesMessageEvent, Vector3d } from '@nitrots/nitro-renderer';
|
import { BuildersClubFurniCountMessageEvent, BuildersClubPlaceRoomItemMessageComposer, BuildersClubPlaceWallItemMessageComposer, BuildersClubQueryFurniCountMessageComposer, BuildersClubSubscriptionStatusMessageEvent, CatalogPageMessageEvent, CatalogPagesListEvent, CatalogPublishedMessageEvent, ClubGiftInfoEvent, CreateLinkEvent, FrontPageItem, FurniturePlaceComposer, FurniturePlacePaintComposer, GetCatalogIndexComposer, GetCatalogPageComposer, GetClubGiftInfo, GetRoomEngine, GetSessionDataManager, GetTickerTime, GuildMembershipsMessageEvent, HabboClubOffersMessageEvent, LegacyDataType, LimitedEditionSoldOutEvent, MarketplaceMakeOfferResult, NodeData, ProductOfferEvent, PurchaseErrorMessageEvent, PurchaseFromCatalogComposer, PurchaseNotAllowedMessageEvent, PurchaseOKMessageEvent, RoomControllerLevel, RoomEngineObjectPlacedEvent, RoomObjectCategory, RoomObjectPlacementSource, RoomObjectType, RoomObjectVariable, RoomPreviewer, SellablePetPalettesMessageEvent, Vector3d } from '@nitrots/nitro-renderer';
|
||||||
import { useCallback, useEffect, useRef, useState } from 'react';
|
import { useCallback, useEffect, useRef, useState } from 'react';
|
||||||
import { useBetween } from 'use-between';
|
import { useBetween } from 'use-between';
|
||||||
import { BuilderFurniPlaceableStatus, CatalogNode, CatalogPage, CatalogPetPalette, CatalogType, DispatchUiEvent, FurniCategory, GetFurnitureData, GetProductDataForLocalization, GetRoomSession, GiftWrappingConfiguration, ICatalogNode, ICatalogOptions, ICatalogPage, IPageLocalization, IProduct, IPurchasableOffer, IPurchaseOptions, LocalizeText, NotificationAlertType, Offer, PageLocalization, PlacedObjectPurchaseData, PlaySound, Product, ProductTypeEnum, RequestedPage, SearchResult, SendMessageComposer, SoundNames } from '../../api';
|
import { BuilderFurniPlaceableStatus, CatalogNode, CatalogPage, CatalogPetPalette, CatalogType, DispatchUiEvent, FurniCategory, GetFurnitureData, GetProductDataForLocalization, GetRoomSession, ICatalogNode, ICatalogOptions, ICatalogPage, IPageLocalization, IProduct, IPurchasableOffer, IPurchaseOptions, LocalizeText, NotificationAlertType, Offer, PageLocalization, PlacedObjectPurchaseData, PlaySound, Product, ProductTypeEnum, RequestedPage, SearchResult, SendMessageComposer, SoundNames } from '../../api';
|
||||||
import { CatalogPurchaseFailureEvent, CatalogPurchaseNotAllowedEvent, CatalogPurchaseSoldOutEvent, CatalogPurchasedEvent, InventoryFurniAddedEvent } from '../../events';
|
import { CatalogPurchaseFailureEvent, CatalogPurchaseNotAllowedEvent, CatalogPurchaseSoldOutEvent, CatalogPurchasedEvent, InventoryFurniAddedEvent } from '../../events';
|
||||||
import { useMessageEvent, useNitroEvent, useUiEvent } from '../events';
|
import { useMessageEvent, useNitroEvent, useUiEvent } from '../events';
|
||||||
import { useNotification } from '../notification';
|
import { useNotification } from '../notification';
|
||||||
@@ -768,18 +768,6 @@ const useCatalogState = () =>
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
useMessageEvent<GiftWrappingConfigurationEvent>(GiftWrappingConfigurationEvent, event =>
|
|
||||||
{
|
|
||||||
const parser = event.getParser();
|
|
||||||
|
|
||||||
setCatalogOptions(prevValue =>
|
|
||||||
{
|
|
||||||
const giftConfiguration = new GiftWrappingConfiguration(parser);
|
|
||||||
|
|
||||||
return { ...prevValue, giftConfiguration };
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
useMessageEvent<MarketplaceMakeOfferResult>(MarketplaceMakeOfferResult, event =>
|
useMessageEvent<MarketplaceMakeOfferResult>(MarketplaceMakeOfferResult, event =>
|
||||||
{
|
{
|
||||||
const parser = event.getParser();
|
const parser = event.getParser();
|
||||||
@@ -1108,7 +1096,6 @@ const useCatalogState = () =>
|
|||||||
{
|
{
|
||||||
if(!isVisible || rootNode) return;
|
if(!isVisible || rootNode) return;
|
||||||
|
|
||||||
SendMessageComposer(new GetGiftWrappingConfigurationComposer());
|
|
||||||
SendMessageComposer(new GetClubGiftInfo());
|
SendMessageComposer(new GetClubGiftInfo());
|
||||||
SendMessageComposer(new GetCatalogIndexComposer(currentType));
|
SendMessageComposer(new GetCatalogIndexComposer(currentType));
|
||||||
SendMessageComposer(new BuildersClubQueryFurniCountMessageComposer());
|
SendMessageComposer(new BuildersClubQueryFurniCountMessageComposer());
|
||||||
|
|||||||
@@ -0,0 +1,29 @@
|
|||||||
|
import { GetGiftWrappingConfigurationComposer, GiftWrappingConfigurationEvent } from '@nitrots/nitro-renderer';
|
||||||
|
import { UseQueryResult } from '@tanstack/react-query';
|
||||||
|
import { GiftWrappingConfiguration } from '../../api';
|
||||||
|
import { useNitroQuery } from '../../api/nitro-query';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Wraps the GetGiftWrappingConfigurationComposer / GiftWrappingConfigurationEvent
|
||||||
|
* request-response pair as a TanStack query. The configuration is
|
||||||
|
* session-stable (box types, ribbon types, colour palette) so the data
|
||||||
|
* is cached with `staleTime: Infinity` — the server is asked at most
|
||||||
|
* once per session.
|
||||||
|
*
|
||||||
|
* Replaces the previous pattern in useCatalog where the composer was
|
||||||
|
* dispatched eagerly inside an `isVisible` effect and the result was
|
||||||
|
* stored in `catalogOptions.giftConfiguration`. Consumers now read the
|
||||||
|
* query directly and benefit from the standard TanStack loading/error
|
||||||
|
* states.
|
||||||
|
*/
|
||||||
|
export const useGiftConfiguration = (
|
||||||
|
options: { enabled?: boolean } = {}
|
||||||
|
): UseQueryResult<GiftWrappingConfiguration> =>
|
||||||
|
useNitroQuery<GiftWrappingConfigurationEvent, GiftWrappingConfiguration>({
|
||||||
|
key: [ 'nitro', 'catalog', 'giftConfiguration' ],
|
||||||
|
request: () => new GetGiftWrappingConfigurationComposer(),
|
||||||
|
parser: GiftWrappingConfigurationEvent,
|
||||||
|
select: event => new GiftWrappingConfiguration(event.getParser()),
|
||||||
|
enabled: options.enabled,
|
||||||
|
staleTime: Infinity
|
||||||
|
});
|
||||||
Reference in New Issue
Block a user