@mohasinac/appkit 4.11.2 → 4.12.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/_internal/server/features/checkout/actions.d.ts +40 -3
- package/dist/_internal/server/features/checkout/actions.js +232 -47
- package/dist/_internal/server/features/checkout/data.d.ts +10 -0
- package/dist/_internal/server/features/orders/adapters.js +20 -0
- package/dist/_internal/server/features/products/data.d.ts +12 -3
- package/dist/_internal/server/features/products/data.js +55 -4
- package/dist/_internal/server/features/products/index.d.ts +1 -1
- package/dist/_internal/server/features/products/index.js +1 -1
- package/dist/_internal/server/features/products/list-public.d.ts +47 -0
- package/dist/_internal/server/features/products/list-public.js +131 -6
- package/dist/_internal/server/features/reviews/data.d.ts +1 -1
- package/dist/_internal/server/features/reviews/data.js +3 -2
- package/dist/_internal/server/features/tester/visibility.js +3 -3
- package/dist/_internal/server/jobs/core/auctionSettlement.js +5 -2
- package/dist/_internal/server/jobs/core/testerSandboxCleanup.d.ts +1 -1
- package/dist/_internal/server/jobs/core/testerSandboxCleanup.js +4 -1
- package/dist/_internal/server/jobs/core/testerSandboxRefresh.js +2 -0
- package/dist/_internal/server/jobs/handlers/_helpers.js +4 -1
- package/dist/_internal/shared/checkout/lanes.d.ts +20 -0
- package/dist/_internal/shared/checkout/lanes.js +28 -0
- package/dist/_internal/shared/features/checkout/config.d.ts +4 -0
- package/dist/_internal/shared/features/checkout/config.js +8 -0
- package/dist/_internal/shared/features/promotions/schema.d.ts +0 -16
- package/dist/_internal/shared/features/promotions/schema.js +0 -2
- package/dist/_internal/shared/features/reviews/config.d.ts +8 -1
- package/dist/_internal/shared/features/reviews/config.js +8 -1
- package/dist/_internal/shared/fees/calculator.d.ts +34 -2
- package/dist/_internal/shared/fees/calculator.js +45 -1
- package/dist/_internal/shared/listing-types/_registry.d.ts +88 -1
- package/dist/_internal/shared/listing-types/_registry.js +63 -1
- package/dist/_internal/shared/listing-types/art/config.d.ts +59 -0
- package/dist/_internal/shared/listing-types/art/config.js +12 -0
- package/dist/_internal/shared/listing-types/auction/config.d.ts +53 -0
- package/dist/_internal/shared/listing-types/auction/config.js +17 -0
- package/dist/_internal/shared/listing-types/classified/config.d.ts +59 -0
- package/dist/_internal/shared/listing-types/classified/config.js +14 -0
- package/dist/_internal/shared/listing-types/digital-code/config.d.ts +59 -0
- package/dist/_internal/shared/listing-types/digital-code/config.js +12 -0
- package/dist/_internal/shared/listing-types/live/config.d.ts +59 -0
- package/dist/_internal/shared/listing-types/live/config.js +14 -0
- package/dist/_internal/shared/listing-types/pre-order/config.d.ts +110 -0
- package/dist/_internal/shared/listing-types/pre-order/config.js +14 -0
- package/dist/_internal/shared/listing-types/prize-draw/config.d.ts +44 -0
- package/dist/_internal/shared/listing-types/prize-draw/config.js +10 -0
- package/dist/_internal/shared/listing-types/standard/config.d.ts +59 -0
- package/dist/_internal/shared/listing-types/standard/config.js +9 -0
- package/dist/_internal/shared/listing-types/stickers/config.d.ts +59 -0
- package/dist/_internal/shared/listing-types/stickers/config.js +12 -0
- package/dist/client.d.ts +12 -2
- package/dist/client.js +8 -2
- package/dist/constants/api-endpoints.d.ts +6 -0
- package/dist/constants/api-endpoints.js +2 -0
- package/dist/constants/field-names.d.ts +12 -0
- package/dist/constants/field-names.js +12 -0
- package/dist/constants/table-keys.d.ts +2 -0
- package/dist/constants/table-keys.js +2 -0
- package/dist/features/account/components/UserOrdersView.js +27 -5
- package/dist/features/admin/components/AdminAddressesView.js +21 -11
- package/dist/features/admin/components/AdminArtView.d.ts +9 -0
- package/dist/features/admin/components/AdminArtView.js +11 -35
- package/dist/features/admin/components/AdminClassifiedView.d.ts +9 -0
- package/dist/features/admin/components/AdminClassifiedView.js +11 -35
- package/dist/features/admin/components/AdminCouponEditorView.js +1 -4
- package/dist/features/admin/components/AdminDigitalCodesView.d.ts +9 -0
- package/dist/features/admin/components/AdminDigitalCodesView.js +11 -42
- package/dist/features/admin/components/AdminLiveView.d.ts +9 -0
- package/dist/features/admin/components/AdminLiveView.js +11 -41
- package/dist/features/admin/components/AdminOrderEditorView.d.ts +8 -1
- package/dist/features/admin/components/AdminOrderEditorView.js +4 -3
- package/dist/features/admin/components/AdminOrdersView.js +14 -1
- package/dist/features/admin/components/AdminPaymentMethodsView.js +18 -11
- package/dist/features/admin/components/AdminProductsView.js +34 -18
- package/dist/features/admin/components/AdminSiteConfigGuideView.js +1 -1
- package/dist/features/admin/components/AdminSiteSettingsView.js +4 -2
- package/dist/features/admin/components/AdminStickersView.d.ts +9 -0
- package/dist/features/admin/components/AdminStickersView.js +11 -35
- package/dist/features/admin/constants/filter-tabs.d.ts +26 -9
- package/dist/features/admin/constants/filter-tabs.js +22 -9
- package/dist/features/admin/hooks/useAdminListing.js +7 -2
- package/dist/features/admin/schemas/firestore.d.ts +5 -0
- package/dist/features/admin/schemas/firestore.js +1 -0
- package/dist/features/auctions/actions/bid-actions.js +2 -2
- package/dist/features/auctions/components/AuctionBidsTable.js +1 -1
- package/dist/features/auctions/components/AuctionBottomActions.js +1 -0
- package/dist/features/auctions/components/AuctionDetailPageView.js +13 -11
- package/dist/features/cart/components/CartDrawer.d.ts +9 -1
- package/dist/features/cart/components/CartDrawer.js +4 -3
- package/dist/features/cart/components/CartPriceBreakdown.d.ts +61 -0
- package/dist/features/cart/components/CartPriceBreakdown.js +25 -0
- package/dist/features/cart/components/StoreAddonsPicker.d.ts +47 -0
- package/dist/features/cart/components/StoreAddonsPicker.js +21 -0
- package/dist/features/cart/components/index.d.ts +4 -0
- package/dist/features/cart/components/index.js +2 -0
- package/dist/features/cart/repository/cart.repository.d.ts +20 -2
- package/dist/features/cart/repository/cart.repository.js +49 -0
- package/dist/features/cart/schemas/firestore.d.ts +26 -2
- package/dist/features/categories/components/BrandDetailTabs.js +31 -11
- package/dist/features/categories/components/CategoryDetailTabs.js +27 -7
- package/dist/features/categories/components/CategoryProductsListing.d.ts +9 -1
- package/dist/features/categories/components/CategoryProductsListing.js +5 -2
- package/dist/features/classified/components/ClassifiedDetailPageView.js +2 -1
- package/dist/features/contact/email.js +5 -1
- package/dist/features/digital-codes/components/DigitalCodeDetailPageView.js +17 -16
- package/dist/features/homepage/components/FeaturedResultsSection.js +1 -1
- package/dist/features/homepage/components/SectionCarousel.js +1 -1
- package/dist/features/homepage/components/ShopByCategorySection.js +1 -1
- package/dist/features/layout/AppLayoutShell.js +9 -2
- package/dist/features/layout/BottomActions.js +62 -6
- package/dist/features/layout/BottomActionsContext.d.ts +26 -0
- package/dist/features/layout/BottomActionsContext.js +18 -1
- package/dist/features/layout/hooks/useBottomActions.d.ts +12 -1
- package/dist/features/layout/hooks/useBottomActions.js +14 -1
- package/dist/features/layout/index.d.ts +1 -1
- package/dist/features/live/components/LiveItemDetailPageView.js +7 -6
- package/dist/features/orders/components/OrderAddonBadges.d.ts +36 -0
- package/dist/features/orders/components/OrderAddonBadges.js +28 -0
- package/dist/features/orders/components/index.d.ts +1 -0
- package/dist/features/orders/components/index.js +1 -0
- package/dist/features/orders/repository/orders.repository.d.ts +36 -0
- package/dist/features/orders/repository/orders.repository.js +18 -0
- package/dist/features/orders/types/index.d.ts +38 -0
- package/dist/features/pre-orders/components/PreOrderBottomActions.d.ts +1 -1
- package/dist/features/pre-orders/components/PreOrderBottomActions.js +3 -19
- package/dist/features/products/components/ArtStickersListView.js +5 -4
- package/dist/features/products/components/AuctionsIndexListing.js +1 -2
- package/dist/features/products/components/ListingBottomActions.d.ts +28 -0
- package/dist/features/products/components/ListingBottomActions.js +25 -0
- package/dist/features/products/components/PrizeDrawBottomActions.d.ts +1 -1
- package/dist/features/products/components/PrizeDrawBottomActions.js +3 -21
- package/dist/features/products/components/PrizeDrawsListingView.js +18 -33
- package/dist/features/products/components/ProductDetailActions.js +4 -0
- package/dist/features/products/components/ProductDetailPageView.js +7 -7
- package/dist/features/products/components/ProductsIndexListing.js +87 -11
- package/dist/features/products/components/ProductsIndexPageView.js +14 -2
- package/dist/features/products/config/listing-type-listing-config.d.ts +31 -0
- package/dist/features/products/config/listing-type-listing-config.js +74 -0
- package/dist/features/products/constants/listing-tabs.d.ts +43 -198
- package/dist/features/products/constants/listing-tabs.js +71 -58
- package/dist/features/products/constants/sieve.d.ts +104 -1
- package/dist/features/products/constants/sieve.js +27 -7
- package/dist/features/products/hooks/useProducts.js +14 -0
- package/dist/features/products/repository/products.repository.d.ts +45 -1
- package/dist/features/products/repository/products.repository.js +26 -3
- package/dist/features/products/types/index.d.ts +15 -0
- package/dist/features/products/utils/listing-badge-variant.d.ts +20 -1
- package/dist/features/products/utils/listing-badge-variant.js +26 -1
- package/dist/features/products/utils/listing-type.d.ts +24 -0
- package/dist/features/products/utils/listing-type.js +48 -0
- package/dist/features/promotions/actions/coupon-actions.d.ts +7 -0
- package/dist/features/promotions/actions/coupon-actions.js +12 -1
- package/dist/features/promotions/actions/coupon-stacking.d.ts +24 -0
- package/dist/features/promotions/actions/coupon-stacking.js +21 -0
- package/dist/features/promotions/actions/index.d.ts +1 -0
- package/dist/features/promotions/actions/index.js +1 -0
- package/dist/features/promotions/actions/seller-coupon-actions.d.ts +0 -1
- package/dist/features/promotions/actions/seller-coupon-actions.js +0 -1
- package/dist/features/promotions/components/CouponHelpDetails.d.ts +20 -0
- package/dist/features/promotions/components/CouponHelpDetails.js +17 -0
- package/dist/features/promotions/components/CouponsIndexListing.js +2 -1
- package/dist/features/promotions/components/index.d.ts +2 -0
- package/dist/features/promotions/components/index.js +1 -0
- package/dist/features/promotions/constants/coupon-help.d.ts +27 -0
- package/dist/features/promotions/constants/coupon-help.js +42 -0
- package/dist/features/promotions/repository/coupons.repository.d.ts +10 -1
- package/dist/features/promotions/repository/coupons.repository.js +22 -8
- package/dist/features/promotions/schemas/firestore.d.ts +0 -1
- package/dist/features/promotions/schemas/firestore.js +1 -1
- package/dist/features/promotions/schemas/index.d.ts +0 -20
- package/dist/features/promotions/schemas/index.js +0 -1
- package/dist/features/reviews/actions/review-actions.js +5 -1
- package/dist/features/reviews/components/ReviewDetailPageView.js +2 -1
- package/dist/features/reviews/components/ReviewFilters.d.ts +7 -1
- package/dist/features/reviews/components/ReviewFilters.js +4 -3
- package/dist/features/reviews/components/ReviewsIndexListing.d.ts +6 -0
- package/dist/features/reviews/components/ReviewsIndexListing.js +9 -109
- package/dist/features/reviews/components/ReviewsListingPanel.d.ts +41 -0
- package/dist/features/reviews/components/ReviewsListingPanel.js +226 -0
- package/dist/features/reviews/components/index.d.ts +2 -0
- package/dist/features/reviews/components/index.js +1 -0
- package/dist/features/reviews/hooks/useReviews.d.ts +8 -0
- package/dist/features/reviews/hooks/useReviews.js +14 -6
- package/dist/features/reviews/repository/reviews.repository.d.ts +29 -1
- package/dist/features/reviews/repository/reviews.repository.js +77 -41
- package/dist/features/reviews/types/index.d.ts +8 -1
- package/dist/features/seller/components/SellerOrdersView.js +2 -1
- package/dist/features/seller/components/SellerProductsCards.js +2 -2
- package/dist/features/seller/components/SellerProductsView.js +21 -18
- package/dist/features/stores/actions/store-query-actions.js +1 -1
- package/dist/features/stores/components/StoreArtStickersPageView.d.ts +21 -0
- package/dist/features/stores/components/StoreArtStickersPageView.js +30 -0
- package/dist/features/stores/components/StoreAuctionsListing.js +5 -11
- package/dist/features/stores/components/StoreAuctionsPageView.d.ts +4 -1
- package/dist/features/stores/components/StoreAuctionsPageView.js +17 -17
- package/dist/features/stores/components/StoreClassifiedsListing.js +7 -0
- package/dist/features/stores/components/StoreClassifiedsPageView.d.ts +4 -1
- package/dist/features/stores/components/StoreClassifiedsPageView.js +16 -12
- package/dist/features/stores/components/StoreDetailLayoutView.js +4 -3
- package/dist/features/stores/components/StoreDigitalCodesListing.js +5 -0
- package/dist/features/stores/components/StoreDigitalCodesPageView.d.ts +4 -1
- package/dist/features/stores/components/StoreDigitalCodesPageView.js +16 -12
- package/dist/features/stores/components/StoreLiveItemsListing.js +7 -0
- package/dist/features/stores/components/StoreLiveItemsPageView.d.ts +4 -1
- package/dist/features/stores/components/StoreLiveItemsPageView.js +16 -12
- package/dist/features/stores/components/StorePreOrdersListing.js +6 -11
- package/dist/features/stores/components/StorePreOrdersPageView.d.ts +4 -1
- package/dist/features/stores/components/StorePreOrdersPageView.js +17 -17
- package/dist/features/stores/components/StorePrizeDrawsPageView.d.ts +4 -8
- package/dist/features/stores/components/StorePrizeDrawsPageView.js +17 -22
- package/dist/features/stores/components/StoreProductsListing.d.ts +7 -1
- package/dist/features/stores/components/StoreProductsListing.js +3 -2
- package/dist/features/stores/components/StoreProductsPageView.d.ts +1 -1
- package/dist/features/stores/components/StoreProductsPageView.js +16 -21
- package/dist/features/stores/components/StoreReviewsListing.d.ts +4 -0
- package/dist/features/stores/components/StoreReviewsListing.js +7 -108
- package/dist/features/stores/schemas/index.d.ts +2 -2
- package/dist/features/tester/seed-data/coupons-tester-seed-data.js +3 -3
- package/dist/features/tester/seed-data/index.d.ts +1 -0
- package/dist/features/tester/seed-data/index.js +1 -0
- package/dist/features/tester/seed-data/offers-tester-seed-data.d.ts +2 -0
- package/dist/features/tester/seed-data/offers-tester-seed-data.js +61 -0
- package/dist/features/tester/seed-data/tester-checklist-seed-data.js +939 -1
- package/dist/index.d.ts +9 -3
- package/dist/index.js +11 -2
- package/dist/next/routing/route-map.d.ts +2 -0
- package/dist/next/routing/route-map.js +5 -0
- package/dist/react/hooks/useListingTypeFlags.d.ts +12 -19
- package/dist/react/hooks/useListingTypeFlags.js +4 -9
- package/dist/schemas/registry.d.ts +0 -12
- package/dist/seed/claimed-coupons-seed-data.js +3 -3
- package/dist/seed/coupons-seed-data.js +29 -10
- package/dist/seed/faq-seed-data.js +2 -2
- package/dist/seed/manifest.js +2 -2
- package/dist/seed/reviews-seed-data.js +52 -0
- package/dist/server-entry.d.ts +1 -0
- package/dist/server-entry.js +1 -0
- package/dist/styles.css +55 -39
- package/dist/tailwind-utilities.css +1 -1
- package/dist/ui/components/Checkbox.d.ts +10 -1
- package/dist/ui/components/Checkbox.js +14 -2
- package/dist/ui/components/Checkbox.style.css +11 -0
- package/dist/ui/components/FilterChipGroup.d.ts +21 -3
- package/dist/ui/components/FilterChipGroup.js +33 -4
- package/dist/ui/components/HorizontalScroller.d.ts +1 -2
- package/dist/ui/components/HorizontalScroller.js +9 -5
- package/dist/ui/components/HorizontalScroller.style.css +43 -38
- package/package.json +1 -1
|
@@ -4,19 +4,31 @@ import { Container, Div, Heading, Main, Section, Text, TextLink } from "../../..
|
|
|
4
4
|
import { AdSlot } from "../../homepage/components/AdSlot";
|
|
5
5
|
import { ProductsIndexListing } from "./ProductsIndexListing";
|
|
6
6
|
import { PRODUCT_FIELDS } from "../../../constants/field-names";
|
|
7
|
+
import { TABLE_KEYS } from "../../../constants/table-keys";
|
|
7
8
|
import { sortBy } from "../../../constants/sort";
|
|
8
9
|
import { GENERIC_PRODUCT_LISTING_TYPES } from "../constants/listing-tabs";
|
|
9
|
-
import { listPublicProducts, parsePublicProductParams, } from "../../../_internal/server/features/products/list-public";
|
|
10
|
+
import { listPublicProducts, parsePublicProductParams, defaultTogglesForListingTypes, } from "../../../_internal/server/features/products/list-public";
|
|
11
|
+
import { parseSelectedListingTypes } from "../utils/listing-type";
|
|
10
12
|
const DEFAULT_PAGE_SIZE = 24;
|
|
11
13
|
const DEFAULT_SORT = sortBy(PRODUCT_FIELDS.CREATED_AT);
|
|
12
14
|
export async function ProductsIndexPageView({ searchParams = {} }) {
|
|
15
|
+
// The "Show sold" / "Show ended" defaults depend on WHICH types are in play,
|
|
16
|
+
// and this page now spans all nine. Both sides derive them from the same
|
|
17
|
+
// helper — a hardcoded `hideSoldByDefault: true` here would disagree with
|
|
18
|
+
// the client the moment the user ticks Auctions, and `staleTime: Infinity`
|
|
19
|
+
// would freeze that disagreement (Root Cause #30).
|
|
20
|
+
const raw = searchParams[TABLE_KEYS.LISTING_TYPE];
|
|
21
|
+
const selectedTypes = parseSelectedListingTypes(Array.isArray(raw) ? raw[0] : raw);
|
|
22
|
+
const effectiveTypes = selectedTypes.length > 0 ? selectedTypes : GENERIC_PRODUCT_LISTING_TYPES;
|
|
23
|
+
const { hideSoldByDefault, hideEndedByDefault } = defaultTogglesForListingTypes(effectiveTypes);
|
|
13
24
|
// See ArtStickersListView — one shared filter implementation with
|
|
14
25
|
// /api/products, so SSR and the client refetch agree by construction.
|
|
15
26
|
const products = await listPublicProducts(parsePublicProductParams(searchParams, {
|
|
16
27
|
listingTypes: GENERIC_PRODUCT_LISTING_TYPES,
|
|
17
28
|
pageSize: DEFAULT_PAGE_SIZE,
|
|
18
29
|
sorts: DEFAULT_SORT,
|
|
19
|
-
hideSoldByDefault
|
|
30
|
+
hideSoldByDefault,
|
|
31
|
+
hideEndedByDefault,
|
|
20
32
|
}));
|
|
21
33
|
return (_jsxs(Main, { children: [_jsx(Section, { border: "bottom-subtle", paddingY: "b-md", padding: "t-xl", children: _jsxs(Container, { size: "xl", children: [_jsx(Heading, { level: 1, size: "3xl", weight: "bold", color: "primary", children: "Products" }), _jsx(Text, { className: "mt-1", color: "muted", size: "sm", children: "Discover amazing products and deals" }), _jsx(Div, { className: "mt-3", children: _jsx(TextLink, { variant: "bare", href: String(ROUTES.PUBLIC.AUCTIONS), rounded: "full", paddingX: "sm", paddingY: "2xs", size: "xs", weight: "medium", layout: "inline-flex", align: "center", gap: "sm", className: "border border-primary/30 bg-primary/10 text-primary-700 dark:text-primary-400 hover:bg-primary/15 transition-colors", children: "\uD83C\uDFF7\uFE0F Looking for unique deals? Browse Auctions \u2192" }) })] }) }), _jsxs(Container, { size: "xl", padding: "x-md", children: [_jsx(AdSlot, { id: "listing-sidebar-top", className: "mb-4 mt-4" }), _jsx(ProductsIndexListing, { initialData: products }), _jsx(AdSlot, { id: "listing-sidebar-bottom", className: "mt-8" })] })] }));
|
|
22
34
|
}
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
import type { JsonArray } from "../../../schemas/types";
|
|
2
|
+
import type { ListingType } from "../types";
|
|
3
|
+
import type { ListingViewConfig } from "../../admin/components/DataListingView";
|
|
4
|
+
export interface ListingTypeListingRow {
|
|
5
|
+
id: string;
|
|
6
|
+
primary: string;
|
|
7
|
+
secondary: string;
|
|
8
|
+
status: string;
|
|
9
|
+
updatedAt: string;
|
|
10
|
+
image?: string;
|
|
11
|
+
}
|
|
12
|
+
interface ListingTypeListingResponse {
|
|
13
|
+
items?: JsonArray;
|
|
14
|
+
total?: number;
|
|
15
|
+
}
|
|
16
|
+
export interface BuildListingTypeListingOptions {
|
|
17
|
+
/** Override the page heading; defaults to the type's registered plural label. */
|
|
18
|
+
title?: string;
|
|
19
|
+
searchPlaceholder?: string;
|
|
20
|
+
emptyLabel?: string;
|
|
21
|
+
}
|
|
22
|
+
/**
|
|
23
|
+
* Admin browse config for one listing type.
|
|
24
|
+
*
|
|
25
|
+
* `status` is a real filter here (unlike the five hand-written copies, which
|
|
26
|
+
* offered none) because an admin's main reason to open a per-type list is to
|
|
27
|
+
* find the drafts and in-review items — exactly the rows a status filter
|
|
28
|
+
* surfaces.
|
|
29
|
+
*/
|
|
30
|
+
export declare function buildListingTypeListingConfig(type: ListingType, opts?: BuildListingTypeListingOptions): ListingViewConfig<ListingTypeListingResponse, ListingTypeListingRow>;
|
|
31
|
+
export {};
|
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
/*
|
|
2
|
+
* WHY: Five admin views (Art, Stickers, Classified, Digital Codes, Live Items)
|
|
3
|
+
* were five copies of ONE config that differed only by listing type,
|
|
4
|
+
* title and placeholder text. Five copies is well past the Duplication
|
|
5
|
+
* Framework's Rule of Three, and it showed: every one carried
|
|
6
|
+
* `filterKeys: []` (no filter drawer at all despite filterable data) and
|
|
7
|
+
* its own hand-written three-option sort array, so a fix to any of it had
|
|
8
|
+
* to be applied five times and never was.
|
|
9
|
+
*
|
|
10
|
+
* WHAT: `buildListingTypeListingConfig(type, opts)` — one config, driven by
|
|
11
|
+
* the listing-type plugin registry. Title, sort set and per-type facet
|
|
12
|
+
* keys all come from `pluginFor(type)`, so a new listing type gets a
|
|
13
|
+
* working admin browse page with no new file.
|
|
14
|
+
*
|
|
15
|
+
* EXPORTS: ListingTypeListingRow, BuildListingTypeListingOptions,
|
|
16
|
+
* buildListingTypeListingConfig
|
|
17
|
+
*
|
|
18
|
+
* @tag domain:products
|
|
19
|
+
* @tag layer:config
|
|
20
|
+
* @tag pattern:factory
|
|
21
|
+
* @tag access:client
|
|
22
|
+
* @tag consumers:AdminArtView,AdminStickersView,AdminClassifiedView,AdminDigitalCodesView,AdminLiveView
|
|
23
|
+
* @tag sideEffects:none
|
|
24
|
+
*/
|
|
25
|
+
import { SIEVE_OP, sieveAnd, sieveFilter } from "../../../utils/sieve-builder";
|
|
26
|
+
import { sortBy } from "../../../constants/sort";
|
|
27
|
+
import { PRODUCT_FIELDS } from "../../../constants/field-names";
|
|
28
|
+
import { ADMIN_ENDPOINTS } from "../../../constants/api-endpoints";
|
|
29
|
+
import { ROUTES } from "../../../next/routing/route-map";
|
|
30
|
+
import { pluginFor } from "../../../_internal/shared/listing-types/_registry";
|
|
31
|
+
import { toRecordArray, toRelativeDate, toCurrency, toStringValue, } from "../../admin/hooks/useAdminListingData";
|
|
32
|
+
/**
|
|
33
|
+
* Admin browse config for one listing type.
|
|
34
|
+
*
|
|
35
|
+
* `status` is a real filter here (unlike the five hand-written copies, which
|
|
36
|
+
* offered none) because an admin's main reason to open a per-type list is to
|
|
37
|
+
* find the drafts and in-review items — exactly the rows a status filter
|
|
38
|
+
* surfaces.
|
|
39
|
+
*/
|
|
40
|
+
export function buildListingTypeListingConfig(type, opts = {}) {
|
|
41
|
+
const plugin = pluginFor(type);
|
|
42
|
+
const label = opts.title ?? plugin.pluralLabel;
|
|
43
|
+
return {
|
|
44
|
+
portal: "admin",
|
|
45
|
+
title: label,
|
|
46
|
+
searchPlaceholder: opts.searchPlaceholder ?? `Search ${label.toLowerCase()} by name or seller`,
|
|
47
|
+
emptyLabel: opts.emptyLabel ?? `No ${label.toLowerCase()} listings`,
|
|
48
|
+
filterKeys: ["status"],
|
|
49
|
+
defaultSort: sortBy(PRODUCT_FIELDS.CREATED_AT),
|
|
50
|
+
// Keyed on the canonical type so two types can never share a cache entry.
|
|
51
|
+
queryKey: ["admin", "listing-type", type],
|
|
52
|
+
endpoint: ADMIN_ENDPOINTS.PRODUCTS,
|
|
53
|
+
// The type's own sort set, not a copy-pasted three-option array.
|
|
54
|
+
sortOptions: [...plugin.sortOptions],
|
|
55
|
+
mapRows: (response) => toRecordArray(response.items).map((item, index) => ({
|
|
56
|
+
id: toStringValue(item.id, `${type}-${index}`),
|
|
57
|
+
primary: toStringValue(item.title ?? item.productTitle, "Untitled listing"),
|
|
58
|
+
secondary: [
|
|
59
|
+
toStringValue(item.sellerName, "Unknown seller"),
|
|
60
|
+
toCurrency(item.price),
|
|
61
|
+
].join(" · "),
|
|
62
|
+
status: toStringValue(item.status, "draft"),
|
|
63
|
+
updatedAt: toRelativeDate(item.updatedAt ?? item.createdAt),
|
|
64
|
+
image: toStringValue(item.mainImage, "") || undefined,
|
|
65
|
+
})),
|
|
66
|
+
getTotal: (response, mappedRows) => typeof response.total === "number" ? response.total : mappedRows.length,
|
|
67
|
+
buildFilters: (state) => sieveAnd(sieveFilter(PRODUCT_FIELDS.LISTING_TYPE, SIEVE_OP.EQ, type), state.status && state.status !== "All"
|
|
68
|
+
? sieveFilter(PRODUCT_FIELDS.STATUS, SIEVE_OP.EQ, state.status)
|
|
69
|
+
: "") || undefined,
|
|
70
|
+
// These are products filtered by listingType — reuse the real admin
|
|
71
|
+
// product editor rather than leaving rows non-navigable.
|
|
72
|
+
rowHrefTemplate: String(ROUTES.ADMIN.PRODUCTS_EDIT("{id}")),
|
|
73
|
+
};
|
|
74
|
+
}
|
|
@@ -6,16 +6,20 @@
|
|
|
6
6
|
* filter on the `products` collection or to a separate collection
|
|
7
7
|
* (currently only `bundles`).
|
|
8
8
|
*
|
|
9
|
-
*
|
|
9
|
+
* DERIVED, NOT HAND-WRITTEN (2026-08-21). Every array below is built from
|
|
10
|
+
* `ALL_LISTING_TYPES` + the listing-type plugin registry, so a new listing
|
|
11
|
+
* type appears on every tab bar automatically. They used to be nine separate
|
|
12
|
+
* hand-maintained literals and had drifted badly: `/products` offered only 4
|
|
13
|
+
* of 9 types (missing auctions, pre-orders, prize draws, art, stickers — the
|
|
14
|
+
* bug that started this sweep), the admin type chips used display LABELS as
|
|
15
|
+
* Sieve filter ids, and several arrays still listed `bundle`, which stopped
|
|
16
|
+
* being a listingType in SB-UNI-D. `scripts/audit-listing-type-tab-coverage.mjs`
|
|
17
|
+
* blocks any regression.
|
|
18
|
+
*
|
|
19
|
+
* To add a tab that ISN'T a listing type (bundles, stores), append it to the
|
|
20
|
+
* relevant array explicitly — those are genuinely different collections.
|
|
10
21
|
*/
|
|
11
22
|
import type { ListingType } from "../types";
|
|
12
|
-
/**
|
|
13
|
-
* The consolidated generic `/products` browse tab covers these 4 listing
|
|
14
|
-
* types (auctions/pre-orders/bundles/prize-draws/art+stickers each have
|
|
15
|
-
* their own dedicated public page). Shared between the server-rendered
|
|
16
|
-
* page view and the client listing component so they can't drift apart.
|
|
17
|
-
*/
|
|
18
|
-
export declare const GENERIC_PRODUCT_LISTING_TYPES: readonly ["standard", "classified", "digital-code", "live"];
|
|
19
23
|
export interface ListingTab {
|
|
20
24
|
id: string;
|
|
21
25
|
label: string;
|
|
@@ -28,197 +32,38 @@ export interface ListingTab {
|
|
|
28
32
|
/** Set when the tab queries a non-product entity (e.g. `stores`). */
|
|
29
33
|
entity?: "stores";
|
|
30
34
|
}
|
|
35
|
+
/**
|
|
36
|
+
* The generic `/products` browse page spans EVERY listing type (2026-08-21).
|
|
37
|
+
*
|
|
38
|
+
* It used to span only `standard|classified|digital-code|live` on the theory
|
|
39
|
+
* that auctions/pre-orders/prize-draws/art each had a dedicated page — but
|
|
40
|
+
* that made five of nine types unreachable from the main catalogue, broke
|
|
41
|
+
* seven legacy `/search/.../tab/<type>` permanent redirects that all point at
|
|
42
|
+
* `/products`, and made the cross-type Compare + bulk-cart features (which
|
|
43
|
+
* only exist on this page) unusable for those types. The dedicated pages
|
|
44
|
+
* remain, and `/products` links to them when a single time-boxed type is
|
|
45
|
+
* selected.
|
|
46
|
+
*/
|
|
47
|
+
export declare const GENERIC_PRODUCT_LISTING_TYPES: readonly ListingType[];
|
|
48
|
+
/** The listing types the combined `/art` page spans. */
|
|
49
|
+
export declare const ART_STICKERS_LISTING_TYPES: readonly ListingType[];
|
|
31
50
|
/** Tabs shown on `/categories/[slug]` and `/brands/[slug]` detail pages. */
|
|
32
|
-
export declare const CATEGORY_PAGE_TABS: readonly [
|
|
33
|
-
|
|
34
|
-
readonly label: "Products";
|
|
35
|
-
readonly listingType: "standard";
|
|
36
|
-
}, {
|
|
37
|
-
readonly id: "auctions";
|
|
38
|
-
readonly label: "Auctions";
|
|
39
|
-
readonly listingType: "auction";
|
|
40
|
-
}, {
|
|
41
|
-
readonly id: "pre-orders";
|
|
42
|
-
readonly label: "Pre-Orders";
|
|
43
|
-
readonly listingType: "pre-order";
|
|
44
|
-
}, {
|
|
45
|
-
readonly id: "prize-draws";
|
|
46
|
-
readonly label: "Prize Draws";
|
|
47
|
-
readonly listingType: "prize-draw";
|
|
48
|
-
}, {
|
|
49
|
-
readonly id: "bundles";
|
|
50
|
-
readonly label: "Bundles";
|
|
51
|
-
readonly collection: "bundles";
|
|
52
|
-
}, {
|
|
53
|
-
readonly id: "classifieds";
|
|
54
|
-
readonly label: "Classifieds";
|
|
55
|
-
readonly listingType: "classified";
|
|
56
|
-
}, {
|
|
57
|
-
readonly id: "digital-codes";
|
|
58
|
-
readonly label: "Digital Codes";
|
|
59
|
-
readonly listingType: "digital-code";
|
|
60
|
-
}, {
|
|
61
|
-
readonly id: "live";
|
|
62
|
-
readonly label: "Live Items";
|
|
63
|
-
readonly listingType: "live";
|
|
64
|
-
}, {
|
|
65
|
-
readonly id: "art";
|
|
66
|
-
readonly label: "Art & Stickers";
|
|
67
|
-
readonly listingType: "art|stickers";
|
|
68
|
-
}, {
|
|
69
|
-
readonly id: "stores";
|
|
70
|
-
readonly label: "Stores";
|
|
71
|
-
readonly entity: "stores";
|
|
72
|
-
}];
|
|
73
|
-
export type CategoryTabId = (typeof CATEGORY_PAGE_TABS)[number]["id"];
|
|
51
|
+
export declare const CATEGORY_PAGE_TABS: readonly ListingTab[];
|
|
52
|
+
export type CategoryTabId = string;
|
|
74
53
|
/** Tabs shown on the public `/stores/[slug]` nav bar. */
|
|
75
|
-
export declare const STORE_PAGE_TABS: readonly [
|
|
76
|
-
|
|
77
|
-
readonly label: "Products";
|
|
78
|
-
readonly listingType: "standard";
|
|
79
|
-
}, {
|
|
80
|
-
readonly id: "auctions";
|
|
81
|
-
readonly label: "Auctions";
|
|
82
|
-
readonly listingType: "auction";
|
|
83
|
-
}, {
|
|
84
|
-
readonly id: "pre-orders";
|
|
85
|
-
readonly label: "Pre-Orders";
|
|
86
|
-
readonly listingType: "pre-order";
|
|
87
|
-
}, {
|
|
88
|
-
readonly id: "prize-draws";
|
|
89
|
-
readonly label: "Prize Draws";
|
|
90
|
-
readonly listingType: "prize-draw";
|
|
91
|
-
}, {
|
|
92
|
-
readonly id: "bundles";
|
|
93
|
-
readonly label: "Bundles";
|
|
94
|
-
readonly collection: "bundles";
|
|
95
|
-
}, {
|
|
96
|
-
readonly id: "classifieds";
|
|
97
|
-
readonly label: "Classifieds";
|
|
98
|
-
readonly listingType: "classified";
|
|
99
|
-
}, {
|
|
100
|
-
readonly id: "digital-codes";
|
|
101
|
-
readonly label: "Digital Codes";
|
|
102
|
-
readonly listingType: "digital-code";
|
|
103
|
-
}, {
|
|
104
|
-
readonly id: "live";
|
|
105
|
-
readonly label: "Live Items";
|
|
106
|
-
readonly listingType: "live";
|
|
107
|
-
}, {
|
|
108
|
-
readonly id: "art";
|
|
109
|
-
readonly label: "Art & Stickers";
|
|
110
|
-
readonly listingType: "art|stickers";
|
|
111
|
-
}];
|
|
112
|
-
export type StoreTabId = (typeof STORE_PAGE_TABS)[number]["id"];
|
|
54
|
+
export declare const STORE_PAGE_TABS: readonly ListingTab[];
|
|
55
|
+
export type StoreTabId = string;
|
|
113
56
|
/** Tabs shown on the seller-dashboard listings view + admin products list. */
|
|
114
|
-
export declare const SELLER_LISTING_TABS: readonly [
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
}, {
|
|
126
|
-
readonly id: "pre-orders";
|
|
127
|
-
readonly label: "Pre-Orders";
|
|
128
|
-
readonly listingType: "pre-order";
|
|
129
|
-
}, {
|
|
130
|
-
readonly id: "prize-draws";
|
|
131
|
-
readonly label: "Prize Draws";
|
|
132
|
-
readonly listingType: "prize-draw";
|
|
133
|
-
}, {
|
|
134
|
-
readonly id: "classifieds";
|
|
135
|
-
readonly label: "Classifieds";
|
|
136
|
-
readonly listingType: "classified";
|
|
137
|
-
}, {
|
|
138
|
-
readonly id: "digital-codes";
|
|
139
|
-
readonly label: "Digital Codes";
|
|
140
|
-
readonly listingType: "digital-code";
|
|
141
|
-
}, {
|
|
142
|
-
readonly id: "live";
|
|
143
|
-
readonly label: "Live Items";
|
|
144
|
-
readonly listingType: "live";
|
|
145
|
-
}, {
|
|
146
|
-
readonly id: "art";
|
|
147
|
-
readonly label: "Art";
|
|
148
|
-
readonly listingType: "art";
|
|
149
|
-
}, {
|
|
150
|
-
readonly id: "stickers";
|
|
151
|
-
readonly label: "Stickers";
|
|
152
|
-
readonly listingType: "stickers";
|
|
153
|
-
}];
|
|
154
|
-
export type SellerListingTabId = (typeof SELLER_LISTING_TABS)[number]["id"];
|
|
155
|
-
/** Tabs shown on `/search` results. */
|
|
156
|
-
export declare const SEARCH_RESULT_TABS: readonly [{
|
|
157
|
-
readonly id: "all";
|
|
158
|
-
readonly label: "All";
|
|
159
|
-
}, {
|
|
160
|
-
readonly id: "products";
|
|
161
|
-
readonly label: "Products";
|
|
162
|
-
readonly listingType: "standard";
|
|
163
|
-
}, {
|
|
164
|
-
readonly id: "auctions";
|
|
165
|
-
readonly label: "Auctions";
|
|
166
|
-
readonly listingType: "auction";
|
|
167
|
-
}, {
|
|
168
|
-
readonly id: "pre-orders";
|
|
169
|
-
readonly label: "Pre-Orders";
|
|
170
|
-
readonly listingType: "pre-order";
|
|
171
|
-
}, {
|
|
172
|
-
readonly id: "prize-draws";
|
|
173
|
-
readonly label: "Prize Draws";
|
|
174
|
-
readonly listingType: "prize-draw";
|
|
175
|
-
}, {
|
|
176
|
-
readonly id: "bundles";
|
|
177
|
-
readonly label: "Bundles";
|
|
178
|
-
readonly collection: "bundles";
|
|
179
|
-
}, {
|
|
180
|
-
readonly id: "classifieds";
|
|
181
|
-
readonly label: "Classifieds";
|
|
182
|
-
readonly listingType: "classified";
|
|
183
|
-
}, {
|
|
184
|
-
readonly id: "digital-codes";
|
|
185
|
-
readonly label: "Digital Codes";
|
|
186
|
-
readonly listingType: "digital-code";
|
|
187
|
-
}, {
|
|
188
|
-
readonly id: "live";
|
|
189
|
-
readonly label: "Live Items";
|
|
190
|
-
readonly listingType: "live";
|
|
191
|
-
}, {
|
|
192
|
-
readonly id: "art";
|
|
193
|
-
readonly label: "Art & Stickers";
|
|
194
|
-
readonly listingType: "art|stickers";
|
|
195
|
-
}];
|
|
196
|
-
export type SearchTabId = (typeof SEARCH_RESULT_TABS)[number]["id"];
|
|
197
|
-
/** In-page type-filter chips on the generic `/products` browse page. */
|
|
198
|
-
export declare const PRODUCT_TYPE_FILTER_TABS: readonly [{
|
|
199
|
-
readonly id: "All";
|
|
200
|
-
readonly label: "All";
|
|
201
|
-
}, {
|
|
202
|
-
readonly id: "standard";
|
|
203
|
-
readonly label: "Standard";
|
|
204
|
-
}, {
|
|
205
|
-
readonly id: "classified";
|
|
206
|
-
readonly label: "Classified";
|
|
207
|
-
}, {
|
|
208
|
-
readonly id: "digital-code";
|
|
209
|
-
readonly label: "Digital Codes";
|
|
210
|
-
}, {
|
|
211
|
-
readonly id: "live";
|
|
212
|
-
readonly label: "Live Items";
|
|
213
|
-
}];
|
|
57
|
+
export declare const SELLER_LISTING_TABS: readonly ListingTab[];
|
|
58
|
+
export type SellerListingTabId = string;
|
|
59
|
+
/**
|
|
60
|
+
* In-page type-filter chips on the generic `/products` browse page.
|
|
61
|
+
*
|
|
62
|
+
* Multi-select (checkbox semantics) — no "All" sentinel chip, because "none
|
|
63
|
+
* checked" already means "every type". A sentinel would be a second way to
|
|
64
|
+
* express the same state and would have to be cleared whenever a real chip
|
|
65
|
+
* was ticked.
|
|
66
|
+
*/
|
|
67
|
+
export declare const PRODUCT_TYPE_FILTER_TABS: readonly ListingTab[];
|
|
214
68
|
/** In-page type-filter chips on the combined `/art` (Art & Stickers) page. */
|
|
215
|
-
export declare const ART_STICKERS_TYPE_FILTER_TABS: readonly [
|
|
216
|
-
readonly id: "All";
|
|
217
|
-
readonly label: "All";
|
|
218
|
-
}, {
|
|
219
|
-
readonly id: "art";
|
|
220
|
-
readonly label: "Art";
|
|
221
|
-
}, {
|
|
222
|
-
readonly id: "stickers";
|
|
223
|
-
readonly label: "Stickers";
|
|
224
|
-
}];
|
|
69
|
+
export declare const ART_STICKERS_TYPE_FILTER_TABS: readonly ListingTab[];
|
|
@@ -6,78 +6,91 @@
|
|
|
6
6
|
* filter on the `products` collection or to a separate collection
|
|
7
7
|
* (currently only `bundles`).
|
|
8
8
|
*
|
|
9
|
-
*
|
|
9
|
+
* DERIVED, NOT HAND-WRITTEN (2026-08-21). Every array below is built from
|
|
10
|
+
* `ALL_LISTING_TYPES` + the listing-type plugin registry, so a new listing
|
|
11
|
+
* type appears on every tab bar automatically. They used to be nine separate
|
|
12
|
+
* hand-maintained literals and had drifted badly: `/products` offered only 4
|
|
13
|
+
* of 9 types (missing auctions, pre-orders, prize draws, art, stickers — the
|
|
14
|
+
* bug that started this sweep), the admin type chips used display LABELS as
|
|
15
|
+
* Sieve filter ids, and several arrays still listed `bundle`, which stopped
|
|
16
|
+
* being a listingType in SB-UNI-D. `scripts/audit-listing-type-tab-coverage.mjs`
|
|
17
|
+
* blocks any regression.
|
|
18
|
+
*
|
|
19
|
+
* To add a tab that ISN'T a listing type (bundles, stores), append it to the
|
|
20
|
+
* relevant array explicitly — those are genuinely different collections.
|
|
21
|
+
*/
|
|
22
|
+
import { ALL_LISTING_TYPES } from "../../../_internal/shared/listing-types/feature-flags";
|
|
23
|
+
import { pluginFor } from "../../../_internal/shared/listing-types/_registry";
|
|
24
|
+
/**
|
|
25
|
+
* The generic `/products` browse page spans EVERY listing type (2026-08-21).
|
|
26
|
+
*
|
|
27
|
+
* It used to span only `standard|classified|digital-code|live` on the theory
|
|
28
|
+
* that auctions/pre-orders/prize-draws/art each had a dedicated page — but
|
|
29
|
+
* that made five of nine types unreachable from the main catalogue, broke
|
|
30
|
+
* seven legacy `/search/.../tab/<type>` permanent redirects that all point at
|
|
31
|
+
* `/products`, and made the cross-type Compare + bulk-cart features (which
|
|
32
|
+
* only exist on this page) unusable for those types. The dedicated pages
|
|
33
|
+
* remain, and `/products` links to them when a single time-boxed type is
|
|
34
|
+
* selected.
|
|
35
|
+
*/
|
|
36
|
+
export const GENERIC_PRODUCT_LISTING_TYPES = ALL_LISTING_TYPES;
|
|
37
|
+
/** The listing types the combined `/art` page spans. */
|
|
38
|
+
export const ART_STICKERS_LISTING_TYPES = ["art", "stickers"];
|
|
39
|
+
/**
|
|
40
|
+
* A FILTER chip — `id` is the canonical `listingType`, because it is passed
|
|
41
|
+
* straight into `sieveFilter("listingType", EQ, id)`. Never a display label.
|
|
42
|
+
*/
|
|
43
|
+
function chipTab(type) {
|
|
44
|
+
return { id: type, label: pluginFor(type).chipLabel, listingType: type };
|
|
45
|
+
}
|
|
46
|
+
/**
|
|
47
|
+
* A ROUTE-BACKED tab — `id` is the plugin's `tabSlug`, because it doubles as
|
|
48
|
+
* the URL segment (`/stores/{slug}/pre-orders`) and is live in bookmarks.
|
|
49
|
+
* The canonical type still rides along in `listingType` for the query.
|
|
10
50
|
*/
|
|
51
|
+
function pluralTab(type) {
|
|
52
|
+
const plugin = pluginFor(type);
|
|
53
|
+
return { id: plugin.tabSlug, label: plugin.pluralLabel, listingType: type };
|
|
54
|
+
}
|
|
11
55
|
/**
|
|
12
|
-
*
|
|
13
|
-
*
|
|
14
|
-
*
|
|
15
|
-
*
|
|
56
|
+
* Art and stickers share the combined `/art` browse page, so category/brand/
|
|
57
|
+
* store tab bars show them as ONE tab backed by a two-value OR-group. Derived
|
|
58
|
+
* from both plugins rather than a hardcoded `"art|stickers"` string so the
|
|
59
|
+
* pipe-group can't drift from the registry.
|
|
16
60
|
*/
|
|
17
|
-
|
|
61
|
+
const ART_STICKERS_COMBINED_TAB = {
|
|
62
|
+
id: pluginFor("art").tabSlug,
|
|
63
|
+
label: `${pluginFor("art").pluralLabel} & ${pluginFor("stickers").pluralLabel}`,
|
|
64
|
+
listingType: ART_STICKERS_LISTING_TYPES.join("|"),
|
|
65
|
+
};
|
|
66
|
+
/** Listing types that get their own tab on a combined surface (art+stickers merge into one). */
|
|
67
|
+
const SEPARATELY_TABBED_TYPES = ALL_LISTING_TYPES.filter((t) => t !== "art" && t !== "stickers");
|
|
18
68
|
/** Tabs shown on `/categories/[slug]` and `/brands/[slug]` detail pages. */
|
|
19
69
|
export const CATEGORY_PAGE_TABS = [
|
|
20
|
-
|
|
21
|
-
{ id: "auctions", label: "Auctions", listingType: "auction" },
|
|
22
|
-
{ id: "pre-orders", label: "Pre-Orders", listingType: "pre-order" },
|
|
23
|
-
{ id: "prize-draws", label: "Prize Draws", listingType: "prize-draw" },
|
|
70
|
+
...SEPARATELY_TABBED_TYPES.map(pluralTab),
|
|
24
71
|
{ id: "bundles", label: "Bundles", collection: "bundles" },
|
|
25
|
-
|
|
26
|
-
{ id: "digital-codes", label: "Digital Codes", listingType: "digital-code" },
|
|
27
|
-
{ id: "live", label: "Live Items", listingType: "live" },
|
|
28
|
-
// Combined — one public browse page (`/art`) spans both listing types.
|
|
29
|
-
{ id: "art", label: "Art & Stickers", listingType: "art|stickers" },
|
|
72
|
+
ART_STICKERS_COMBINED_TAB,
|
|
30
73
|
{ id: "stores", label: "Stores", entity: "stores" },
|
|
31
74
|
];
|
|
32
75
|
/** Tabs shown on the public `/stores/[slug]` nav bar. */
|
|
33
76
|
export const STORE_PAGE_TABS = [
|
|
34
|
-
|
|
35
|
-
{ id: "auctions", label: "Auctions", listingType: "auction" },
|
|
36
|
-
{ id: "pre-orders", label: "Pre-Orders", listingType: "pre-order" },
|
|
37
|
-
{ id: "prize-draws", label: "Prize Draws", listingType: "prize-draw" },
|
|
77
|
+
...SEPARATELY_TABBED_TYPES.map(pluralTab),
|
|
38
78
|
{ id: "bundles", label: "Bundles", collection: "bundles" },
|
|
39
|
-
|
|
40
|
-
{ id: "digital-codes", label: "Digital Codes", listingType: "digital-code" },
|
|
41
|
-
{ id: "live", label: "Live Items", listingType: "live" },
|
|
42
|
-
{ id: "art", label: "Art & Stickers", listingType: "art|stickers" },
|
|
79
|
+
ART_STICKERS_COMBINED_TAB,
|
|
43
80
|
];
|
|
44
81
|
/** Tabs shown on the seller-dashboard listings view + admin products list. */
|
|
45
82
|
export const SELLER_LISTING_TABS = [
|
|
46
83
|
{ id: "all", label: "All" },
|
|
47
|
-
|
|
48
|
-
{ id: "auctions", label: "Auctions", listingType: "auction" },
|
|
49
|
-
{ id: "pre-orders", label: "Pre-Orders", listingType: "pre-order" },
|
|
50
|
-
{ id: "prize-draws", label: "Prize Draws", listingType: "prize-draw" },
|
|
51
|
-
{ id: "classifieds", label: "Classifieds", listingType: "classified" },
|
|
52
|
-
{ id: "digital-codes", label: "Digital Codes", listingType: "digital-code" },
|
|
53
|
-
{ id: "live", label: "Live Items", listingType: "live" },
|
|
54
|
-
{ id: "art", label: "Art", listingType: "art" },
|
|
55
|
-
{ id: "stickers", label: "Stickers", listingType: "stickers" },
|
|
56
|
-
];
|
|
57
|
-
/** Tabs shown on `/search` results. */
|
|
58
|
-
export const SEARCH_RESULT_TABS = [
|
|
59
|
-
{ id: "all", label: "All" },
|
|
60
|
-
{ id: "products", label: "Products", listingType: "standard" },
|
|
61
|
-
{ id: "auctions", label: "Auctions", listingType: "auction" },
|
|
62
|
-
{ id: "pre-orders", label: "Pre-Orders", listingType: "pre-order" },
|
|
63
|
-
{ id: "prize-draws", label: "Prize Draws", listingType: "prize-draw" },
|
|
64
|
-
{ id: "bundles", label: "Bundles", collection: "bundles" },
|
|
65
|
-
{ id: "classifieds", label: "Classifieds", listingType: "classified" },
|
|
66
|
-
{ id: "digital-codes", label: "Digital Codes", listingType: "digital-code" },
|
|
67
|
-
{ id: "live", label: "Live Items", listingType: "live" },
|
|
68
|
-
{ id: "art", label: "Art & Stickers", listingType: "art|stickers" },
|
|
69
|
-
];
|
|
70
|
-
/** In-page type-filter chips on the generic `/products` browse page. */
|
|
71
|
-
export const PRODUCT_TYPE_FILTER_TABS = [
|
|
72
|
-
{ id: "All", label: "All" },
|
|
73
|
-
{ id: "standard", label: "Standard" },
|
|
74
|
-
{ id: "classified", label: "Classified" },
|
|
75
|
-
{ id: "digital-code", label: "Digital Codes" },
|
|
76
|
-
{ id: "live", label: "Live Items" },
|
|
84
|
+
...ALL_LISTING_TYPES.map(pluralTab),
|
|
77
85
|
];
|
|
86
|
+
/**
|
|
87
|
+
* In-page type-filter chips on the generic `/products` browse page.
|
|
88
|
+
*
|
|
89
|
+
* Multi-select (checkbox semantics) — no "All" sentinel chip, because "none
|
|
90
|
+
* checked" already means "every type". A sentinel would be a second way to
|
|
91
|
+
* express the same state and would have to be cleared whenever a real chip
|
|
92
|
+
* was ticked.
|
|
93
|
+
*/
|
|
94
|
+
export const PRODUCT_TYPE_FILTER_TABS = ALL_LISTING_TYPES.map(chipTab);
|
|
78
95
|
/** In-page type-filter chips on the combined `/art` (Art & Stickers) page. */
|
|
79
|
-
export const ART_STICKERS_TYPE_FILTER_TABS =
|
|
80
|
-
{ id: "All", label: "All" },
|
|
81
|
-
{ id: "art", label: "Art" },
|
|
82
|
-
{ id: "stickers", label: "Stickers" },
|
|
83
|
-
];
|
|
96
|
+
export const ART_STICKERS_TYPE_FILTER_TABS = ART_STICKERS_LISTING_TYPES.map(chipTab);
|
|
@@ -141,6 +141,90 @@ export declare const PREORDER_SORT_OPTIONS: readonly [{
|
|
|
141
141
|
readonly value: string;
|
|
142
142
|
readonly label: "Lowest Deposit First";
|
|
143
143
|
}];
|
|
144
|
+
/**
|
|
145
|
+
* Public pre-order browse subset. Drops "Lowest Deposit First" — deposit
|
|
146
|
+
* amount is a seller-side pricing lever buyers don't shop by — but keeps
|
|
147
|
+
* both delivery-date directions, which are the primary browse intent.
|
|
148
|
+
*/
|
|
149
|
+
export declare const PREORDER_PUBLIC_SORT_OPTIONS: readonly [{
|
|
150
|
+
readonly value: string;
|
|
151
|
+
readonly label: "Earliest Delivery";
|
|
152
|
+
}, {
|
|
153
|
+
readonly value: string;
|
|
154
|
+
readonly label: "Latest Delivery";
|
|
155
|
+
}, {
|
|
156
|
+
readonly value: string;
|
|
157
|
+
readonly label: "Newest First";
|
|
158
|
+
} | {
|
|
159
|
+
readonly value: string;
|
|
160
|
+
readonly label: "Oldest First";
|
|
161
|
+
} | {
|
|
162
|
+
readonly value: string;
|
|
163
|
+
readonly label: "Price: Low to High";
|
|
164
|
+
} | {
|
|
165
|
+
readonly value: string;
|
|
166
|
+
readonly label: "Price: High to Low";
|
|
167
|
+
} | {
|
|
168
|
+
readonly value: string;
|
|
169
|
+
readonly label: "Fewest Slots Left";
|
|
170
|
+
} | {
|
|
171
|
+
readonly value: string;
|
|
172
|
+
readonly label: "Lowest Deposit First";
|
|
173
|
+
}, {
|
|
174
|
+
readonly value: string;
|
|
175
|
+
readonly label: "Newest First";
|
|
176
|
+
} | {
|
|
177
|
+
readonly value: string;
|
|
178
|
+
readonly label: "Oldest First";
|
|
179
|
+
} | {
|
|
180
|
+
readonly value: string;
|
|
181
|
+
readonly label: "Price: Low to High";
|
|
182
|
+
} | {
|
|
183
|
+
readonly value: string;
|
|
184
|
+
readonly label: "Price: High to Low";
|
|
185
|
+
} | {
|
|
186
|
+
readonly value: string;
|
|
187
|
+
readonly label: "Fewest Slots Left";
|
|
188
|
+
} | {
|
|
189
|
+
readonly value: string;
|
|
190
|
+
readonly label: "Lowest Deposit First";
|
|
191
|
+
}, {
|
|
192
|
+
readonly value: string;
|
|
193
|
+
readonly label: "Newest First";
|
|
194
|
+
} | {
|
|
195
|
+
readonly value: string;
|
|
196
|
+
readonly label: "Oldest First";
|
|
197
|
+
} | {
|
|
198
|
+
readonly value: string;
|
|
199
|
+
readonly label: "Price: Low to High";
|
|
200
|
+
} | {
|
|
201
|
+
readonly value: string;
|
|
202
|
+
readonly label: "Price: High to Low";
|
|
203
|
+
} | {
|
|
204
|
+
readonly value: string;
|
|
205
|
+
readonly label: "Fewest Slots Left";
|
|
206
|
+
} | {
|
|
207
|
+
readonly value: string;
|
|
208
|
+
readonly label: "Lowest Deposit First";
|
|
209
|
+
}, {
|
|
210
|
+
readonly value: string;
|
|
211
|
+
readonly label: "Newest First";
|
|
212
|
+
} | {
|
|
213
|
+
readonly value: string;
|
|
214
|
+
readonly label: "Oldest First";
|
|
215
|
+
} | {
|
|
216
|
+
readonly value: string;
|
|
217
|
+
readonly label: "Price: Low to High";
|
|
218
|
+
} | {
|
|
219
|
+
readonly value: string;
|
|
220
|
+
readonly label: "Price: High to Low";
|
|
221
|
+
} | {
|
|
222
|
+
readonly value: string;
|
|
223
|
+
readonly label: "Fewest Slots Left";
|
|
224
|
+
} | {
|
|
225
|
+
readonly value: string;
|
|
226
|
+
readonly label: "Lowest Deposit First";
|
|
227
|
+
}];
|
|
144
228
|
export declare const BUNDLE_SORT_OPTIONS: readonly [...({
|
|
145
229
|
readonly value: string;
|
|
146
230
|
readonly label: "Newest First";
|
|
@@ -173,4 +257,23 @@ export declare const PRIZE_DRAW_SORT_OPTIONS: readonly [{
|
|
|
173
257
|
readonly value: string;
|
|
174
258
|
readonly label: "Entry: High to Low";
|
|
175
259
|
}];
|
|
176
|
-
|
|
260
|
+
/** Public prize-draw browse subset — every option is buyer-meaningful. */
|
|
261
|
+
export declare const PRIZE_DRAW_PUBLIC_SORT_OPTIONS: readonly [{
|
|
262
|
+
readonly value: string;
|
|
263
|
+
readonly label: "Newest First";
|
|
264
|
+
}, {
|
|
265
|
+
readonly value: string;
|
|
266
|
+
readonly label: "Oldest First";
|
|
267
|
+
}, {
|
|
268
|
+
readonly value: string;
|
|
269
|
+
readonly label: "Reveal: Soonest";
|
|
270
|
+
}, {
|
|
271
|
+
readonly value: string;
|
|
272
|
+
readonly label: "Reveal: Furthest";
|
|
273
|
+
}, {
|
|
274
|
+
readonly value: string;
|
|
275
|
+
readonly label: "Entry: Low to High";
|
|
276
|
+
}, {
|
|
277
|
+
readonly value: string;
|
|
278
|
+
readonly label: "Entry: High to Low";
|
|
279
|
+
}];
|