@mohasinac/appkit 2.7.58 → 2.8.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/client/features/filters/filter-load-options.d.ts +4 -5
- package/dist/_internal/server/features/auctions/og.js +8 -32
- package/dist/_internal/server/features/blog/og.js +10 -49
- package/dist/_internal/server/features/checkout/actions.js +6 -0
- package/dist/_internal/server/features/classified/og.js +9 -51
- package/dist/_internal/server/features/digital-code/actions.d.ts +11 -0
- package/dist/_internal/server/features/digital-code/actions.js +30 -0
- package/dist/_internal/server/features/digital-code/index.d.ts +1 -0
- package/dist/_internal/server/features/digital-code/index.js +1 -0
- package/dist/_internal/server/features/digital-code/og.js +9 -51
- package/dist/_internal/server/features/events/og.js +10 -49
- package/dist/_internal/server/features/item-requests/data.d.ts +17 -0
- package/dist/_internal/server/features/item-requests/data.js +20 -0
- package/dist/_internal/server/features/item-requests/index.d.ts +2 -0
- package/dist/_internal/server/features/item-requests/index.js +2 -0
- package/dist/_internal/server/features/item-requests/og.d.ts +40 -0
- package/dist/_internal/server/features/item-requests/og.js +136 -0
- package/dist/_internal/server/features/live/actions.d.ts +5 -0
- package/dist/_internal/server/features/live/actions.js +24 -0
- package/dist/_internal/server/features/live/index.d.ts +1 -0
- package/dist/_internal/server/features/live/index.js +1 -0
- package/dist/_internal/server/features/live/og.js +9 -51
- package/dist/_internal/server/features/media/contextGuards.js +19 -8
- package/dist/_internal/server/features/pre-orders/og.js +8 -32
- package/dist/_internal/server/features/prize-draws/data.d.ts +17 -0
- package/dist/_internal/server/features/prize-draws/data.js +20 -0
- package/dist/_internal/server/features/prize-draws/index.d.ts +2 -0
- package/dist/_internal/server/features/prize-draws/index.js +2 -0
- package/dist/_internal/server/features/prize-draws/og.d.ts +30 -0
- package/dist/_internal/server/features/prize-draws/og.js +50 -0
- package/dist/_internal/server/features/products/og.js +8 -33
- package/dist/_internal/server/features/scams/og.js +1 -1
- package/dist/_internal/server/features/seo/og-layout.d.ts +42 -0
- package/dist/_internal/server/features/seo/og-layout.js +69 -0
- package/dist/_internal/server/features/stores/og.js +8 -41
- package/dist/_internal/server/features/sublisting-categories/og.js +11 -42
- package/dist/_internal/shared/actions/bulk-helpers.d.ts +3 -0
- package/dist/_internal/shared/actions/bulk-helpers.js +19 -0
- package/dist/_internal/shared/config/schema.d.ts +4 -4
- package/dist/client.d.ts +13 -6
- package/dist/client.js +9 -3
- package/dist/configs/next.js +11 -0
- package/dist/constants/index.d.ts +4 -0
- package/dist/constants/index.js +2 -0
- package/dist/constants/notification-types.d.ts +20 -0
- package/dist/constants/notification-types.js +37 -0
- package/dist/constants/pagination-presets.d.ts +39 -0
- package/dist/constants/pagination-presets.js +38 -0
- package/dist/errors/messages.d.ts +0 -4
- package/dist/errors/messages.js +0 -4
- package/dist/features/account/components/AddressesIndexListing.js +3 -4
- package/dist/features/account/components/UserOffersPanel.js +1 -1
- package/dist/features/account/components/UserSidebar.js +14 -10
- package/dist/features/account/components/UserSupportView.d.ts +1 -2
- package/dist/features/account/components/UserSupportView.js +9 -1
- package/dist/features/admin/actions/admin-actions.js +16 -1
- package/dist/features/admin/components/AdminAllEventEntriesView.d.ts +2 -3
- package/dist/features/admin/components/AdminAllEventEntriesView.js +50 -89
- package/dist/features/admin/components/AdminBidsView.d.ts +2 -3
- package/dist/features/admin/components/AdminBidsView.js +64 -104
- package/dist/features/admin/components/AdminBlogView.d.ts +3 -7
- package/dist/features/admin/components/AdminBlogView.js +53 -88
- package/dist/features/admin/components/AdminBrandEditorView.js +14 -17
- package/dist/features/admin/components/AdminBrandsView.d.ts +2 -3
- package/dist/features/admin/components/AdminBrandsView.js +85 -89
- package/dist/features/admin/components/AdminBundlesView.js +68 -130
- package/dist/features/admin/components/AdminCarouselView.d.ts +2 -2
- package/dist/features/admin/components/AdminCarouselView.js +22 -70
- package/dist/features/admin/components/AdminCartsView.d.ts +2 -3
- package/dist/features/admin/components/AdminCartsView.js +39 -89
- package/dist/features/admin/components/AdminCategoriesView.d.ts +3 -3
- package/dist/features/admin/components/AdminCategoriesView.js +97 -96
- package/dist/features/admin/components/AdminCategoryEditorView.js +2 -6
- package/dist/features/admin/components/AdminClassifiedView.d.ts +3 -0
- package/dist/features/admin/components/AdminClassifiedView.js +44 -0
- package/dist/features/admin/components/AdminContactView.d.ts +2 -2
- package/dist/features/admin/components/AdminContactView.js +105 -130
- package/dist/features/admin/components/AdminCouponEditorView.js +14 -17
- package/dist/features/admin/components/AdminCouponsView.d.ts +3 -6
- package/dist/features/admin/components/AdminCouponsView.js +69 -97
- package/dist/features/admin/components/AdminDigitalCodesView.d.ts +3 -0
- package/dist/features/admin/components/AdminDigitalCodesView.js +51 -0
- package/dist/features/admin/components/AdminFaqEditorView.js +14 -17
- package/dist/features/admin/components/AdminFaqsView.d.ts +4 -4
- package/dist/features/admin/components/AdminFaqsView.js +79 -86
- package/dist/features/admin/components/AdminFeatureEditorView.js +7 -9
- package/dist/features/admin/components/AdminFeaturesView.d.ts +2 -3
- package/dist/features/admin/components/AdminFeaturesView.js +57 -70
- package/dist/features/admin/components/AdminGroupedListingsView.d.ts +3 -0
- package/dist/features/admin/components/AdminGroupedListingsView.js +43 -0
- package/dist/features/admin/components/AdminHistoryView.d.ts +2 -3
- package/dist/features/admin/components/AdminHistoryView.js +35 -52
- package/dist/features/admin/components/AdminListingScaffold.d.ts +2 -2
- package/dist/features/admin/components/AdminListingScaffold.js +3 -3
- package/dist/features/admin/components/AdminLiveView.d.ts +3 -0
- package/dist/features/admin/components/AdminLiveView.js +50 -0
- package/dist/features/admin/components/AdminNewsletterView.d.ts +2 -2
- package/dist/features/admin/components/AdminNewsletterView.js +68 -108
- package/dist/features/admin/components/AdminNotificationsView.d.ts +2 -3
- package/dist/features/admin/components/AdminNotificationsView.js +67 -99
- package/dist/features/admin/components/AdminOrderEditorView.js +10 -10
- package/dist/features/admin/components/AdminOrdersView.d.ts +2 -3
- package/dist/features/admin/components/AdminOrdersView.js +93 -113
- package/dist/features/admin/components/AdminPayoutsView.d.ts +2 -3
- package/dist/features/admin/components/AdminPayoutsView.js +51 -97
- package/dist/features/admin/components/AdminPrizeDrawsView.d.ts +2 -3
- package/dist/features/admin/components/AdminPrizeDrawsView.js +41 -83
- package/dist/features/admin/components/AdminProductEditorView.js +3 -7
- package/dist/features/admin/components/AdminProductsView.d.ts +4 -4
- package/dist/features/admin/components/AdminProductsView.js +166 -167
- package/dist/features/admin/components/AdminReturnRequestsView.d.ts +1 -1
- package/dist/features/admin/components/AdminReturnRequestsView.js +64 -66
- package/dist/features/admin/components/AdminReviewsView.d.ts +3 -7
- package/dist/features/admin/components/AdminReviewsView.js +94 -116
- package/dist/features/admin/components/AdminScammersView.d.ts +2 -3
- package/dist/features/admin/components/AdminScammersView.js +53 -103
- package/dist/features/admin/components/AdminSectionsView.js +1 -1
- package/dist/features/admin/components/AdminSessionsView.d.ts +2 -3
- package/dist/features/admin/components/AdminSessionsView.js +62 -95
- package/dist/features/admin/components/AdminStoreAddressesView.d.ts +1 -1
- package/dist/features/admin/components/AdminStoreAddressesView.js +39 -53
- package/dist/features/admin/components/AdminStoreEditorView.js +21 -8
- package/dist/features/admin/components/AdminStoresView.d.ts +2 -3
- package/dist/features/admin/components/AdminStoresView.js +67 -105
- package/dist/features/admin/components/AdminSublistingCategoriesView.d.ts +1 -1
- package/dist/features/admin/components/AdminSublistingCategoriesView.js +29 -49
- package/dist/features/admin/components/AdminSublistingCategoryEditorView.js +17 -20
- package/dist/features/admin/components/AdminSupportTicketDetailView.d.ts +10 -1
- package/dist/features/admin/components/AdminSupportTicketDetailView.js +191 -5
- package/dist/features/admin/components/AdminSupportTicketsView.d.ts +2 -3
- package/dist/features/admin/components/AdminSupportTicketsView.js +65 -102
- package/dist/features/admin/components/AdminTeamView.d.ts +2 -2
- package/dist/features/admin/components/AdminTeamView.js +42 -85
- package/dist/features/admin/components/AdminUserEditorView.d.ts +11 -1
- package/dist/features/admin/components/AdminUserEditorView.js +80 -6
- package/dist/features/admin/components/AdminUsersView.d.ts +2 -3
- package/dist/features/admin/components/AdminUsersView.js +108 -106
- package/dist/features/admin/components/AdminViewCards.d.ts +1 -1
- package/dist/features/admin/components/AdminWishlistsView.d.ts +2 -3
- package/dist/features/admin/components/AdminWishlistsView.js +36 -62
- package/dist/features/admin/components/DataListingView.d.ts +122 -0
- package/dist/features/admin/components/DataListingView.js +66 -0
- package/dist/features/admin/components/index.d.ts +10 -4
- package/dist/features/admin/components/index.js +6 -2
- package/dist/features/admin/constants/filter-tabs.d.ts +23 -17
- package/dist/features/admin/constants/filter-tabs.js +21 -17
- package/dist/features/admin/hooks/useAdminListing.d.ts +59 -0
- package/dist/features/admin/hooks/useAdminListing.js +71 -0
- package/dist/features/admin/schemas/firestore.js +6 -7
- package/dist/features/auctions/server.d.ts +0 -1
- package/dist/features/auctions/server.js +0 -1
- package/dist/features/auth/actions/realtime-token-actions.js +1 -1
- package/dist/features/auth/repository/user.repository.js +1 -1
- package/dist/features/auth/schemas/firestore.d.ts +1 -0
- package/dist/features/blog/components/BlogIndexListing.js +3 -6
- package/dist/features/cart/repository/cart.repository.d.ts +4 -1
- package/dist/features/cart/repository/cart.repository.js +12 -0
- package/dist/features/categories/components/CategoriesIndexListing.js +3 -6
- package/dist/features/checkout/hooks/useCheckoutApi.d.ts +0 -2
- package/dist/features/checkout/index.d.ts +1 -1
- package/dist/features/events/components/AdminEventsView.d.ts +3 -3
- package/dist/features/events/components/AdminEventsView.js +50 -86
- package/dist/features/events/components/EventOfferCard.d.ts +19 -0
- package/dist/features/events/components/EventOfferCard.js +29 -0
- package/dist/features/events/components/EventRaffleEntryForm.d.ts +25 -0
- package/dist/features/events/components/EventRaffleEntryForm.js +37 -0
- package/dist/features/events/components/EventRafflesSection.d.ts +1 -4
- package/dist/features/events/components/EventRafflesSection.js +17 -6
- package/dist/features/events/components/EventSaleBanner.d.ts +21 -0
- package/dist/features/events/components/EventSaleBanner.js +18 -0
- package/dist/features/events/components/EventsIndexListing.js +3 -4
- package/dist/features/events/components/index.d.ts +6 -0
- package/dist/features/events/components/index.js +4 -0
- package/dist/features/events/repository/event-entry.repository.d.ts +5 -0
- package/dist/features/events/repository/event-entry.repository.js +7 -0
- package/dist/features/filters/AsyncFacetSection.d.ts +1 -1
- package/dist/features/homepage/components/AnnouncementBar.d.ts +4 -1
- package/dist/features/homepage/components/AnnouncementBar.js +51 -4
- package/dist/features/homepage/components/FAQSection.d.ts +0 -5
- package/dist/features/homepage/components/MarketplaceHomepageView.d.ts +3 -1
- package/dist/features/homepage/components/MarketplaceHomepageView.js +2 -2
- package/dist/features/homepage/components/index.d.ts +1 -1
- package/dist/features/homepage/components/index.js +1 -1
- package/dist/features/homepage/lib/live-stats.js +1 -1
- package/dist/features/homepage/lib/section-renderer.d.ts +2 -2
- package/dist/features/homepage/lib/section-renderer.js +2 -2
- package/dist/features/homepage/schemas/firestore.d.ts +0 -2
- package/dist/features/layout/index.d.ts +0 -2
- package/dist/features/layout/index.js +0 -1
- package/dist/features/orders/repository/orders.repository.d.ts +0 -1
- package/dist/features/orders/repository/orders.repository.js +0 -1
- package/dist/features/orders/server.d.ts +1 -1
- package/dist/features/orders/server.js +1 -1
- package/dist/features/pre-orders/server.d.ts +0 -1
- package/dist/features/pre-orders/server.js +0 -1
- package/dist/features/products/components/GroupSettingsPanel.js +65 -49
- package/dist/features/products/components/PrizeDrawItemsEditor.js +2 -2
- package/dist/features/products/components/PrizeDrawsSection.d.ts +1 -4
- package/dist/features/products/components/PrizeDrawsSection.js +17 -6
- package/dist/features/products/components/PrizeRevealModal.js +1 -1
- package/dist/features/products/components/ProductCardMetadataSection.d.ts +11 -0
- package/dist/features/products/components/ProductCardMetadataSection.js +25 -0
- package/dist/features/products/components/ProductDetailPageView.js +3 -1
- package/dist/features/products/components/ProductFeaturesSelector.js +1 -1
- package/dist/features/products/components/ProductGradingTab.d.ts +13 -0
- package/dist/features/products/components/ProductGradingTab.js +25 -0
- package/dist/features/products/components/ProductGrid.js +14 -2
- package/dist/features/products/components/ProductTabsShell.d.ts +5 -1
- package/dist/features/products/components/ProductTabsShell.js +6 -1
- package/dist/features/products/components/index.d.ts +4 -0
- package/dist/features/products/components/index.js +3 -0
- package/dist/features/products/constants/action-defs.d.ts +5 -0
- package/dist/features/products/constants/action-defs.js +52 -32
- package/dist/features/products/constants/sieve.d.ts +24 -4
- package/dist/features/products/constants/sieve.js +20 -11
- package/dist/features/products/repository/products.repository.d.ts +0 -2
- package/dist/features/products/repository/products.repository.js +0 -2
- package/dist/features/products/schemas/firestore.d.ts +17 -0
- package/dist/features/products/schemas/product-features.validators.d.ts +2 -2
- package/dist/features/products/schemas/product-templates.d.ts +2 -4
- package/dist/features/products/server.d.ts +1 -1
- package/dist/features/products/server.js +1 -1
- package/dist/features/products/types/index.d.ts +4 -0
- package/dist/features/promotions/components/CouponCard.js +5 -5
- package/dist/features/promotions/components/CouponsIndexListing.js +3 -2
- package/dist/features/promotions/server.d.ts +0 -1
- package/dist/features/promotions/server.js +0 -1
- package/dist/features/reviews/components/ReviewsIndexListing.js +3 -4
- package/dist/features/reviews/repository/reviews.repository.d.ts +0 -1
- package/dist/features/reviews/repository/reviews.repository.js +0 -1
- package/dist/features/reviews/server.d.ts +1 -1
- package/dist/features/reviews/server.js +1 -1
- package/dist/features/search/api/route.js +44 -1
- package/dist/features/search/components/Search.js +2 -0
- package/dist/features/search/hooks/useNavSuggestions.d.ts +5 -1
- package/dist/features/search/hooks/useNavSuggestions.js +31 -4
- package/dist/features/seller/components/BrandInlineSelect.js +2 -2
- package/dist/features/seller/components/CategoryInlineSelect.js +2 -2
- package/dist/features/seller/components/SellerAddressesView.js +10 -20
- package/dist/features/seller/components/SellerAuctionsView.d.ts +3 -3
- package/dist/features/seller/components/SellerAuctionsView.js +67 -106
- package/dist/features/seller/components/SellerBidsView.js +6 -6
- package/dist/features/seller/components/SellerBundlesView.js +72 -105
- package/dist/features/seller/components/SellerClassifiedView.js +74 -105
- package/dist/features/seller/components/SellerCouponEditorView.js +1 -1
- package/dist/features/seller/components/SellerCouponsView.d.ts +2 -2
- package/dist/features/seller/components/SellerCouponsView.js +51 -96
- package/dist/features/seller/components/SellerDigitalCodesView.js +70 -103
- package/dist/features/seller/components/SellerGroupedListingsView.js +34 -54
- package/dist/features/seller/components/SellerLiveView.js +70 -99
- package/dist/features/seller/components/SellerOffersPanel.js +1 -1
- package/dist/features/seller/components/SellerOffersView.d.ts +2 -2
- package/dist/features/seller/components/SellerOffersView.js +37 -70
- package/dist/features/seller/components/SellerOrdersView.d.ts +2 -2
- package/dist/features/seller/components/SellerOrdersView.js +10 -24
- package/dist/features/seller/components/SellerPayoutMethodsView.js +12 -24
- package/dist/features/seller/components/SellerPayoutsView.d.ts +2 -2
- package/dist/features/seller/components/SellerPayoutsView.js +34 -69
- package/dist/features/seller/components/SellerPreOrdersView.d.ts +2 -2
- package/dist/features/seller/components/SellerPreOrdersView.js +55 -97
- package/dist/features/seller/components/SellerPrizeDrawsView.d.ts +2 -2
- package/dist/features/seller/components/SellerPrizeDrawsView.js +55 -97
- package/dist/features/seller/components/SellerProductShell.d.ts +1 -1
- package/dist/features/seller/components/SellerProductsFilterDrawer.d.ts +1 -1
- package/dist/features/seller/components/SellerProductsFilterDrawer.js +3 -6
- package/dist/features/seller/components/SellerProductsView.d.ts +2 -2
- package/dist/features/seller/components/SellerProductsView.js +24 -32
- package/dist/features/seller/components/SellerShippingConfigsView.js +12 -24
- package/dist/features/seller/components/SellerSidebar.d.ts +0 -4
- package/dist/features/seller/components/SellerSidebar.js +0 -2
- package/dist/features/seller/components/SellerStoreCategoriesView.js +15 -34
- package/dist/features/seller/components/SellerTemplatesView.js +27 -43
- package/dist/features/seller/components/SellersListView.d.ts +1 -2
- package/dist/features/seller/components/analytics/SellerAnalyticsStats.d.ts +5 -0
- package/dist/features/seller/components/analytics/SellerAnalyticsStats.js +2 -8
- package/dist/features/seller/components/index.d.ts +0 -3
- package/dist/features/seller/components/index.js +0 -2
- package/dist/features/seller/server.d.ts +0 -1
- package/dist/features/seller/server.js +0 -1
- package/dist/features/shell/FormShell.d.ts +1 -1
- package/dist/features/shell/FormShell.js +4 -1
- package/dist/features/shell/field-groups/ImageFieldGroup.d.ts +18 -0
- package/dist/features/shell/field-groups/ImageFieldGroup.js +15 -0
- package/dist/features/shell/field-groups/SeoFieldGroup.d.ts +22 -0
- package/dist/features/shell/field-groups/SeoFieldGroup.js +16 -0
- package/dist/features/shell/field-groups/StatusFieldGroup.d.ts +35 -0
- package/dist/features/shell/field-groups/StatusFieldGroup.js +16 -0
- package/dist/features/shell/field-groups/TitleDescriptionGroup.d.ts +40 -0
- package/dist/features/shell/field-groups/TitleDescriptionGroup.js +16 -0
- package/dist/features/shell/field-groups/index.d.ts +13 -0
- package/dist/features/shell/field-groups/index.js +9 -0
- package/dist/features/shell/index.d.ts +2 -0
- package/dist/features/shell/index.js +1 -0
- package/dist/features/stores/components/StoreCapabilitiesGuideView.d.ts +1 -2
- package/dist/features/stores/components/StoreFinanceGuideView.d.ts +1 -2
- package/dist/features/stores/components/StoreHeader.js +2 -1
- package/dist/features/stores/components/StoreListingsGuideView.d.ts +1 -2
- package/dist/features/stores/components/StoreOrdersGuideView.d.ts +1 -2
- package/dist/features/stores/components/StoreReviewsListing.js +3 -4
- package/dist/features/stores/components/StoreScopedSearch.d.ts +16 -0
- package/dist/features/stores/components/StoreScopedSearch.js +27 -0
- package/dist/features/stores/components/StoreSettingsGuideView.d.ts +1 -2
- package/dist/features/stores/components/StoresIndexListing.js +3 -4
- package/dist/features/stores/server.d.ts +0 -1
- package/dist/features/stores/server.js +0 -1
- package/dist/features/support/schemas/firestore.d.ts +22 -1
- package/dist/features/support/schemas/firestore.js +10 -0
- package/dist/features/wishlist/server.d.ts +0 -1
- package/dist/features/wishlist/server.js +0 -1
- package/dist/index.d.ts +11 -33
- package/dist/index.js +17 -62
- package/dist/next/routing/route-map.d.ts +8 -0
- package/dist/next/routing/route-map.js +4 -0
- package/dist/react/contexts/SessionContext.d.ts +2 -0
- package/dist/react/contexts/SessionContext.js +2 -0
- package/dist/react/hooks/useEntityDelete.d.ts +15 -0
- package/dist/react/hooks/useEntityDelete.js +39 -0
- package/dist/react/hooks/useListingTypeFlags.d.ts +32 -0
- package/dist/react/hooks/useListingTypeFlags.js +19 -0
- package/dist/react/index.d.ts +2 -0
- package/dist/react/index.js +2 -0
- package/dist/repositories/index.d.ts +3 -3
- package/dist/repositories/index.js +3 -3
- package/dist/security/index.d.ts +1 -1
- package/dist/security/index.js +1 -1
- package/dist/security/pii-redact.d.ts +8 -0
- package/dist/security/pii-redact.js +10 -1
- package/dist/seed/grouped-listings-seed-data.d.ts +4 -0
- package/dist/seed/products-preorders-seed-data.d.ts +4 -0
- package/dist/seed/products-prize-draws-seed-data.js +3 -0
- package/dist/seed/site-settings-seed-data.js +5 -5
- package/dist/seed/sub-listings-seed-data.d.ts +4 -0
- package/dist/server.d.ts +2 -0
- package/dist/server.js +4 -0
- package/dist/styles.css +54 -395
- package/dist/tailwind-utilities.css +1 -1
- package/dist/ui/components/BaseListingCard.d.ts +10 -0
- package/dist/ui/components/BaseListingCard.js +17 -1
- package/dist/ui/components/DetailPageGallery.d.ts +32 -0
- package/dist/ui/components/DetailPageGallery.js +47 -0
- package/dist/ui/components/DetailPageHero.d.ts +30 -0
- package/dist/ui/components/DetailPageHero.js +22 -0
- package/dist/ui/components/DetailPageTabs.d.ts +34 -0
- package/dist/ui/components/DetailPageTabs.js +38 -0
- package/dist/ui/components/HorizontalScroller.style.css +15 -2
- package/dist/ui/components/ListingFilterDrawer.d.ts +10 -0
- package/dist/ui/components/ListingFilterDrawer.js +8 -0
- package/dist/ui/components/ListingLayout.d.ts +11 -2
- package/dist/ui/components/ListingLayout.js +12 -6
- package/dist/ui/components/PaginatedSelect.d.ts +66 -0
- package/dist/ui/components/PaginatedSelect.js +201 -0
- package/dist/ui/components/PaginatedSelect.style.css +254 -0
- package/dist/ui/components/Semantic.d.ts +0 -4
- package/dist/ui/components/Semantic.js +0 -2
- package/dist/ui/components/SettingsSection.d.ts +47 -0
- package/dist/ui/components/SettingsSection.js +38 -0
- package/dist/ui/components/index.style.css +1 -4
- package/dist/ui/index.d.ts +14 -14
- package/dist/ui/index.js +7 -7
- package/dist/utils/id-generators.d.ts +1 -18
- package/dist/utils/id-generators.js +51 -18
- package/dist/validation/schemas.d.ts +25 -0
- package/dist/validation/schemas.js +28 -0
- package/package.json +1 -1
|
@@ -0,0 +1,136 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import { resolveOgImageUrl } from "../seo/og";
|
|
3
|
+
function formatPriceInr(paise) {
|
|
4
|
+
const rupees = Math.round(paise / 100);
|
|
5
|
+
return `≤ ₹${rupees.toLocaleString("en-IN")}`;
|
|
6
|
+
}
|
|
7
|
+
function normalizeStatus(s) {
|
|
8
|
+
if (s === "open" || s === "closed" || s === "removed" || s === "approved")
|
|
9
|
+
return s;
|
|
10
|
+
return null;
|
|
11
|
+
}
|
|
12
|
+
export function renderItemRequestOg(doc, opts) {
|
|
13
|
+
const budgetLabel = typeof doc?.maxBudgetInPaise === "number" && doc.maxBudgetInPaise > 0
|
|
14
|
+
? formatPriceInr(doc.maxBudgetInPaise)
|
|
15
|
+
: null;
|
|
16
|
+
return renderItemRequestOgImage({
|
|
17
|
+
title: doc?.title ?? "Item Request",
|
|
18
|
+
opDisplayName: doc?.opDisplayName ?? null,
|
|
19
|
+
budgetLabel,
|
|
20
|
+
imageUrl: resolveOgImageUrl(doc?.imageUrls?.[0] ?? null, opts.baseUrl),
|
|
21
|
+
status: normalizeStatus(doc?.status),
|
|
22
|
+
replyCount: doc?.replyCount ?? null,
|
|
23
|
+
category: doc?.category ?? null,
|
|
24
|
+
}, opts.siteName);
|
|
25
|
+
}
|
|
26
|
+
const STATUS_BADGE = {
|
|
27
|
+
open: {
|
|
28
|
+
text: "Open",
|
|
29
|
+
bg: "rgba(74, 222, 128, 0.18)",
|
|
30
|
+
border: "rgba(74, 222, 128, 0.4)",
|
|
31
|
+
color: "#bbf7d0",
|
|
32
|
+
},
|
|
33
|
+
approved: {
|
|
34
|
+
text: "Approved",
|
|
35
|
+
bg: "rgba(56, 189, 248, 0.18)",
|
|
36
|
+
border: "rgba(56, 189, 248, 0.4)",
|
|
37
|
+
color: "#e0f2fe",
|
|
38
|
+
},
|
|
39
|
+
closed: {
|
|
40
|
+
text: "Closed",
|
|
41
|
+
bg: "rgba(148, 163, 184, 0.2)",
|
|
42
|
+
border: "rgba(148, 163, 184, 0.45)",
|
|
43
|
+
color: "#e2e8f0",
|
|
44
|
+
},
|
|
45
|
+
removed: {
|
|
46
|
+
text: "Removed",
|
|
47
|
+
bg: "rgba(239, 68, 68, 0.18)",
|
|
48
|
+
border: "rgba(239, 68, 68, 0.45)",
|
|
49
|
+
color: "#fee2e2",
|
|
50
|
+
},
|
|
51
|
+
};
|
|
52
|
+
export function renderItemRequestOgImage(data, siteName) {
|
|
53
|
+
const { title, opDisplayName, budgetLabel, imageUrl, status, replyCount, category } = data;
|
|
54
|
+
const statusBadge = status ? STATUS_BADGE[status] : null;
|
|
55
|
+
const replyLabel = typeof replyCount === "number" && replyCount >= 0
|
|
56
|
+
? `${replyCount} repl${replyCount === 1 ? "y" : "ies"}`
|
|
57
|
+
: null;
|
|
58
|
+
return (_jsxs("div", { style: {
|
|
59
|
+
display: "flex",
|
|
60
|
+
width: "100%",
|
|
61
|
+
height: "100%",
|
|
62
|
+
background: "#0f172a",
|
|
63
|
+
fontFamily: "sans-serif",
|
|
64
|
+
position: "relative",
|
|
65
|
+
overflow: "hidden",
|
|
66
|
+
}, children: [imageUrl && (_jsx("img", { src: imageUrl, alt: "", style: {
|
|
67
|
+
position: "absolute",
|
|
68
|
+
inset: 0,
|
|
69
|
+
width: "100%",
|
|
70
|
+
height: "100%",
|
|
71
|
+
objectFit: "cover",
|
|
72
|
+
opacity: 0.14,
|
|
73
|
+
} })), _jsx("div", { style: {
|
|
74
|
+
position: "absolute",
|
|
75
|
+
inset: 0,
|
|
76
|
+
background: "linear-gradient(135deg, rgba(15,23,42,0.95) 0%, rgba(15,23,42,0.8) 100%)",
|
|
77
|
+
} }), _jsxs("div", { style: {
|
|
78
|
+
position: "relative",
|
|
79
|
+
display: "flex",
|
|
80
|
+
flexDirection: "column",
|
|
81
|
+
gap: 22,
|
|
82
|
+
padding: "72px",
|
|
83
|
+
width: "100%",
|
|
84
|
+
height: "100%",
|
|
85
|
+
justifyContent: "flex-end",
|
|
86
|
+
}, children: [_jsxs("div", { style: {
|
|
87
|
+
fontSize: 18,
|
|
88
|
+
color: "#22d3ee",
|
|
89
|
+
fontWeight: 600,
|
|
90
|
+
letterSpacing: 2,
|
|
91
|
+
textTransform: "uppercase",
|
|
92
|
+
}, children: [siteName, " \u00B7 Wanted"] }), _jsx("div", { style: {
|
|
93
|
+
fontSize: 64,
|
|
94
|
+
fontWeight: 800,
|
|
95
|
+
color: "#f1f5f9",
|
|
96
|
+
lineHeight: 1.1,
|
|
97
|
+
display: "-webkit-box",
|
|
98
|
+
WebkitLineClamp: 3,
|
|
99
|
+
WebkitBoxOrient: "vertical",
|
|
100
|
+
overflow: "hidden",
|
|
101
|
+
letterSpacing: -1,
|
|
102
|
+
}, children: title }), (opDisplayName || category) && (_jsxs("div", { style: { fontSize: 22, color: "#94a3b8" }, children: [opDisplayName ? `by ${opDisplayName}` : "", opDisplayName && category ? " · " : "", category ?? ""] })), _jsxs("div", { style: {
|
|
103
|
+
display: "flex",
|
|
104
|
+
flexDirection: "row",
|
|
105
|
+
gap: 12,
|
|
106
|
+
marginTop: 4,
|
|
107
|
+
flexWrap: "wrap",
|
|
108
|
+
}, children: [statusBadge && (_jsx("div", { style: {
|
|
109
|
+
display: "inline-flex",
|
|
110
|
+
padding: "10px 22px",
|
|
111
|
+
borderRadius: 999,
|
|
112
|
+
background: statusBadge.bg,
|
|
113
|
+
color: statusBadge.color,
|
|
114
|
+
fontSize: 22,
|
|
115
|
+
fontWeight: 700,
|
|
116
|
+
border: `1px solid ${statusBadge.border}`,
|
|
117
|
+
}, children: statusBadge.text })), budgetLabel && (_jsx("div", { style: {
|
|
118
|
+
display: "inline-flex",
|
|
119
|
+
padding: "10px 22px",
|
|
120
|
+
borderRadius: 999,
|
|
121
|
+
background: "rgba(34, 211, 238, 0.18)",
|
|
122
|
+
color: "#cffafe",
|
|
123
|
+
fontSize: 22,
|
|
124
|
+
fontWeight: 700,
|
|
125
|
+
border: "1px solid rgba(34, 211, 238, 0.4)",
|
|
126
|
+
}, children: budgetLabel })), replyLabel && (_jsx("div", { style: {
|
|
127
|
+
display: "inline-flex",
|
|
128
|
+
padding: "10px 22px",
|
|
129
|
+
borderRadius: 999,
|
|
130
|
+
background: "rgba(148, 163, 184, 0.18)",
|
|
131
|
+
color: "#e2e8f0",
|
|
132
|
+
fontSize: 22,
|
|
133
|
+
fontWeight: 600,
|
|
134
|
+
border: "1px solid rgba(148, 163, 184, 0.35)",
|
|
135
|
+
}, children: replyLabel }))] })] })] }));
|
|
136
|
+
}
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
import type { ConversationDocument } from "../../../../features/messages/schemas/firestore";
|
|
2
|
+
export interface StartLiveConversationInput {
|
|
3
|
+
productId: string;
|
|
4
|
+
}
|
|
5
|
+
export declare function startLiveConversationAction(input: StartLiveConversationInput): Promise<ConversationDocument>;
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
"use server";
|
|
2
|
+
import { conversationsRepository } from "../../../../features/messages/repository/conversations.repository";
|
|
3
|
+
import { requireRoleUser } from "../../../../providers/auth-firebase/helpers";
|
|
4
|
+
import { storeRepository, productRepository } from "../../../../repositories";
|
|
5
|
+
export async function startLiveConversationAction(input) {
|
|
6
|
+
const user = await requireRoleUser(["user", "buyer", "seller", "admin"]);
|
|
7
|
+
const product = await productRepository.findByIdOrSlug(input.productId);
|
|
8
|
+
if (!product || product.listingType !== "live") {
|
|
9
|
+
throw new Error("Product not found or not a live-item listing");
|
|
10
|
+
}
|
|
11
|
+
const store = await storeRepository.findById(product.storeId);
|
|
12
|
+
if (!store) {
|
|
13
|
+
throw new Error("Store not found");
|
|
14
|
+
}
|
|
15
|
+
return conversationsRepository.findOrCreateByContext({
|
|
16
|
+
buyerId: user.uid,
|
|
17
|
+
buyerDisplayName: user.name ?? user.email ?? user.uid,
|
|
18
|
+
storeId: product.storeId,
|
|
19
|
+
storeName: store.storeName,
|
|
20
|
+
sellerDisplayName: store.storeName,
|
|
21
|
+
productId: product.id,
|
|
22
|
+
productTitle: product.title,
|
|
23
|
+
});
|
|
24
|
+
}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { renderOgLayout } from "../seo/og-layout";
|
|
2
2
|
import { resolveOgImageUrl } from "../seo/og";
|
|
3
3
|
export function renderLiveItemOg(doc, opts) {
|
|
4
4
|
const priceLabel = doc?.price != null
|
|
@@ -16,56 +16,14 @@ export function renderLiveItemOg(doc, opts) {
|
|
|
16
16
|
}, opts.siteName);
|
|
17
17
|
}
|
|
18
18
|
export function renderLiveItemOgImage(data, siteName) {
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
overflow: "hidden",
|
|
28
|
-
}, children: [imageUrl && (_jsx("img", { src: imageUrl, alt: "", style: {
|
|
29
|
-
position: "absolute",
|
|
30
|
-
inset: 0,
|
|
31
|
-
width: "100%",
|
|
32
|
-
height: "100%",
|
|
33
|
-
objectFit: "cover",
|
|
34
|
-
opacity: 0.15,
|
|
35
|
-
} })), _jsx("div", { style: {
|
|
36
|
-
position: "absolute",
|
|
37
|
-
inset: 0,
|
|
38
|
-
background: "linear-gradient(135deg, rgba(5,46,22,0.96) 0%, rgba(5,46,22,0.82) 100%)",
|
|
39
|
-
} }), _jsxs("div", { style: {
|
|
40
|
-
position: "relative",
|
|
41
|
-
display: "flex",
|
|
42
|
-
width: "100%",
|
|
43
|
-
height: "100%",
|
|
44
|
-
padding: "60px",
|
|
45
|
-
gap: "48px",
|
|
46
|
-
alignItems: "center",
|
|
47
|
-
}, children: [imageUrl && (_jsx("img", { src: imageUrl, alt: title, style: {
|
|
48
|
-
width: 400,
|
|
49
|
-
height: 400,
|
|
50
|
-
objectFit: "contain",
|
|
51
|
-
borderRadius: 16,
|
|
52
|
-
flexShrink: 0,
|
|
53
|
-
} })), _jsxs("div", { style: { display: "flex", flexDirection: "column", gap: 20, flex: 1 }, children: [_jsxs("div", { style: {
|
|
54
|
-
fontSize: 18,
|
|
55
|
-
color: "#86efac",
|
|
56
|
-
fontWeight: 600,
|
|
57
|
-
letterSpacing: 2,
|
|
58
|
-
textTransform: "uppercase",
|
|
59
|
-
}, children: [siteName, " \u00B7 Live Listing"] }), _jsx("div", { style: {
|
|
60
|
-
fontSize: imageUrl ? 44 : 56,
|
|
61
|
-
fontWeight: 700,
|
|
62
|
-
color: "#f1f5f9",
|
|
63
|
-
lineHeight: 1.2,
|
|
64
|
-
display: "-webkit-box",
|
|
65
|
-
WebkitLineClamp: 3,
|
|
66
|
-
WebkitBoxOrient: "vertical",
|
|
67
|
-
overflow: "hidden",
|
|
68
|
-
}, children: title }), species && (_jsx("div", { style: { fontSize: 24, color: "#86efac", fontStyle: "italic" }, children: species })), priceLabel && (_jsx("div", { style: { fontSize: 32, fontWeight: 700, color: "#4ade80" }, children: priceLabel }))] })] })] }));
|
|
19
|
+
return renderOgLayout({
|
|
20
|
+
title: data.title,
|
|
21
|
+
subtitle: data.species ?? undefined,
|
|
22
|
+
imageUrl: data.imageUrl,
|
|
23
|
+
siteName: `${siteName} · Live Listing`,
|
|
24
|
+
accentSlot: data.priceLabel,
|
|
25
|
+
theme: { background: "#052e16", accentColor: "#86efac" },
|
|
26
|
+
});
|
|
69
27
|
}
|
|
70
28
|
/** Type-safe overload that accepts the full ProductDocument. */
|
|
71
29
|
export function renderLiveItemOgFromDoc(doc, opts) {
|
|
@@ -10,7 +10,22 @@
|
|
|
10
10
|
* import from any server route.
|
|
11
11
|
*/
|
|
12
12
|
import { classifyMime, MIME_TO_EXT, } from "../../../shared/media/limits";
|
|
13
|
-
import { generateMediaFilename, } from "../../../../utils/id-generators";
|
|
13
|
+
import { generateMediaFilename, validateMediaFilename, } from "../../../../utils/id-generators";
|
|
14
|
+
/**
|
|
15
|
+
* W1-51 — validate the generated filename before returning ok:true so a
|
|
16
|
+
* malformed name can never enter signed-URL storage. Generators producing
|
|
17
|
+
* unexpected output fail-closed with a 500.
|
|
18
|
+
*/
|
|
19
|
+
function okWithFilename(ctx, filename, ext) {
|
|
20
|
+
if (validateMediaFilename(filename))
|
|
21
|
+
return { ok: true, filename, ext };
|
|
22
|
+
return {
|
|
23
|
+
ok: false,
|
|
24
|
+
status: 500,
|
|
25
|
+
error: "Generated media filename failed validation",
|
|
26
|
+
details: { context: ctx.type, filename },
|
|
27
|
+
};
|
|
28
|
+
}
|
|
14
29
|
// Per-context limits — mirrored from the previous inline constants in
|
|
15
30
|
// /api/media/upload. Adjust here, not at the call site.
|
|
16
31
|
export const CONTEXT_LIMITS = {
|
|
@@ -183,7 +198,7 @@ export function applyMediaContextGuards({ detectedMime, context: ctx, }) {
|
|
|
183
198
|
details: { context: ctx.type, detected: detectedMime },
|
|
184
199
|
};
|
|
185
200
|
}
|
|
186
|
-
return
|
|
201
|
+
return okWithFilename(ctx, generateMediaFilename(ctx), ext);
|
|
187
202
|
}
|
|
188
203
|
if (isImageOrPdfContext(ctx)) {
|
|
189
204
|
// shipping-proof and refund-proof accept images or PDFs, not video.
|
|
@@ -194,7 +209,7 @@ export function applyMediaContextGuards({ detectedMime, context: ctx, }) {
|
|
|
194
209
|
error: `${ctx.type} must be an image or PDF, not a video`,
|
|
195
210
|
};
|
|
196
211
|
}
|
|
197
|
-
return
|
|
212
|
+
return okWithFilename(ctx, generateMediaFilename(ctx), ext);
|
|
198
213
|
}
|
|
199
214
|
if (isPdf) {
|
|
200
215
|
return {
|
|
@@ -204,9 +219,5 @@ export function applyMediaContextGuards({ detectedMime, context: ctx, }) {
|
|
|
204
219
|
details: { context: ctx.type, detected: detectedMime },
|
|
205
220
|
};
|
|
206
221
|
}
|
|
207
|
-
return {
|
|
208
|
-
ok: true,
|
|
209
|
-
filename: generateMediaFilename({ ...ctx, ext }),
|
|
210
|
-
ext,
|
|
211
|
-
};
|
|
222
|
+
return okWithFilename(ctx, generateMediaFilename({ ...ctx, ext }), ext);
|
|
212
223
|
}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { renderOgLayout } from "../seo/og-layout";
|
|
2
2
|
import { resolveOgImageUrl } from "../seo/og";
|
|
3
3
|
/** High-level OG renderer — accepts the raw pre-order document from `getPreOrderForDetail`. */
|
|
4
4
|
export function renderPreOrderOg(doc, opts) {
|
|
@@ -16,35 +16,11 @@ export function renderPreOrderOg(doc, opts) {
|
|
|
16
16
|
}, opts.siteName);
|
|
17
17
|
}
|
|
18
18
|
export function renderPreOrderOgImage(data, siteName) {
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
position: "relative",
|
|
27
|
-
overflow: "hidden",
|
|
28
|
-
}, children: [imageUrl && (_jsx("img", { src: imageUrl, alt: "", style: { position: "absolute", inset: 0, width: "100%", height: "100%", objectFit: "cover", opacity: 0.15 } })), _jsx("div", { style: {
|
|
29
|
-
position: "absolute",
|
|
30
|
-
inset: 0,
|
|
31
|
-
background: "linear-gradient(135deg, rgba(15,23,42,0.95) 0%, rgba(15,23,42,0.8) 100%)",
|
|
32
|
-
} }), _jsxs("div", { style: {
|
|
33
|
-
position: "relative",
|
|
34
|
-
display: "flex",
|
|
35
|
-
width: "100%",
|
|
36
|
-
height: "100%",
|
|
37
|
-
padding: "60px",
|
|
38
|
-
gap: "48px",
|
|
39
|
-
alignItems: "center",
|
|
40
|
-
}, children: [imageUrl && (_jsx("img", { src: imageUrl, alt: title, style: { width: 420, height: 420, objectFit: "contain", borderRadius: 16, flexShrink: 0 } })), _jsxs("div", { style: { display: "flex", flexDirection: "column", gap: 24, flex: 1 }, children: [_jsxs("div", { style: { fontSize: 20, color: "#818cf8", fontWeight: 600, letterSpacing: 2, textTransform: "uppercase" }, children: [siteName, " \u00B7 Pre-Order"] }), _jsx("div", { style: {
|
|
41
|
-
fontSize: imageUrl ? 44 : 56,
|
|
42
|
-
fontWeight: 700,
|
|
43
|
-
color: "#f1f5f9",
|
|
44
|
-
lineHeight: 1.2,
|
|
45
|
-
display: "-webkit-box",
|
|
46
|
-
WebkitLineClamp: 3,
|
|
47
|
-
WebkitBoxOrient: "vertical",
|
|
48
|
-
overflow: "hidden",
|
|
49
|
-
}, children: title }), releaseDateLabel && (_jsx("div", { style: { fontSize: 28, fontWeight: 600, color: "#818cf8" }, children: releaseDateLabel }))] })] })] }));
|
|
19
|
+
return renderOgLayout({
|
|
20
|
+
title: data.title,
|
|
21
|
+
imageUrl: data.imageUrl,
|
|
22
|
+
siteName: `${siteName} · Pre-Order`,
|
|
23
|
+
accentSlot: data.releaseDateLabel,
|
|
24
|
+
theme: { accentColor: "#818cf8" },
|
|
25
|
+
});
|
|
50
26
|
}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Prize Draw data layer — OG-coverage-followup 2026-05-23.
|
|
3
|
+
*
|
|
4
|
+
* Prize draws live as products with `listingType:"prize-draw"`. This file
|
|
5
|
+
* wraps the repo call in `React.cache` so the OG renderer and any future
|
|
6
|
+
* page/generateMetadata pair share one Firestore read per request.
|
|
7
|
+
*/
|
|
8
|
+
import type { ProductDocument } from "../../../../features/products/schemas/firestore";
|
|
9
|
+
export interface PrizeDrawDataOptions {
|
|
10
|
+
_reserved?: never;
|
|
11
|
+
}
|
|
12
|
+
/**
|
|
13
|
+
* Fetch a single prize-draw product by slug or id. Returns null when the
|
|
14
|
+
* slug is empty or no matching product exists. The caller is responsible
|
|
15
|
+
* for asserting `listingType === "prize-draw"` if a strict gate is required.
|
|
16
|
+
*/
|
|
17
|
+
export declare const getPrizeDrawForDetail: (slugOrId: string, _opts?: PrizeDrawDataOptions) => Promise<ProductDocument | null>;
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Prize Draw data layer — OG-coverage-followup 2026-05-23.
|
|
3
|
+
*
|
|
4
|
+
* Prize draws live as products with `listingType:"prize-draw"`. This file
|
|
5
|
+
* wraps the repo call in `React.cache` so the OG renderer and any future
|
|
6
|
+
* page/generateMetadata pair share one Firestore read per request.
|
|
7
|
+
*/
|
|
8
|
+
import { cache } from "react";
|
|
9
|
+
import { productRepository } from "../../../../repositories";
|
|
10
|
+
/**
|
|
11
|
+
* Fetch a single prize-draw product by slug or id. Returns null when the
|
|
12
|
+
* slug is empty or no matching product exists. The caller is responsible
|
|
13
|
+
* for asserting `listingType === "prize-draw"` if a strict gate is required.
|
|
14
|
+
*/
|
|
15
|
+
export const getPrizeDrawForDetail = cache(async (slugOrId, _opts) => {
|
|
16
|
+
void _opts;
|
|
17
|
+
if (!slugOrId)
|
|
18
|
+
return null;
|
|
19
|
+
return (await productRepository.findByIdOrSlug(slugOrId).catch(() => null)) ?? null;
|
|
20
|
+
});
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Prize Draw OG image renderer — OG-coverage-followup 2026-05-23.
|
|
3
|
+
* Migrated to renderOgLayout factory 2026-05-24 (Session 5 W1-1).
|
|
4
|
+
*/
|
|
5
|
+
import type { ReactElement } from "react";
|
|
6
|
+
export interface PrizeDrawOgData {
|
|
7
|
+
title: string;
|
|
8
|
+
pricePerEntryLabel?: string | null;
|
|
9
|
+
imageUrl?: string | null;
|
|
10
|
+
revealStatus?: "pending" | "open" | "closed" | null;
|
|
11
|
+
entriesLabel?: string | null;
|
|
12
|
+
}
|
|
13
|
+
interface PrizeDrawDocLike {
|
|
14
|
+
title?: string | null;
|
|
15
|
+
name?: string | null;
|
|
16
|
+
pricePerEntry?: number | null;
|
|
17
|
+
price?: number | null;
|
|
18
|
+
currency?: string | null;
|
|
19
|
+
mainImage?: string | null;
|
|
20
|
+
images?: (string | null | undefined)[] | null;
|
|
21
|
+
prizeRevealStatus?: "pending" | "open" | "closed" | null;
|
|
22
|
+
prizeMaxEntries?: number | null;
|
|
23
|
+
prizeCurrentEntries?: number | null;
|
|
24
|
+
}
|
|
25
|
+
export declare function renderPrizeDrawOg(doc: PrizeDrawDocLike | null | undefined, opts: {
|
|
26
|
+
siteName: string;
|
|
27
|
+
baseUrl?: string;
|
|
28
|
+
}): ReactElement;
|
|
29
|
+
export declare function renderPrizeDrawOgImage(data: PrizeDrawOgData, siteName: string): ReactElement;
|
|
30
|
+
export {};
|
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Prize Draw OG image renderer — OG-coverage-followup 2026-05-23.
|
|
3
|
+
* Migrated to renderOgLayout factory 2026-05-24 (Session 5 W1-1).
|
|
4
|
+
*/
|
|
5
|
+
import { renderOgLayout } from "../seo/og-layout";
|
|
6
|
+
import { resolveOgImageUrl } from "../seo/og";
|
|
7
|
+
function formatPriceInr(paise, currency) {
|
|
8
|
+
return new Intl.NumberFormat("en-IN", {
|
|
9
|
+
style: "currency",
|
|
10
|
+
currency,
|
|
11
|
+
maximumFractionDigits: 0,
|
|
12
|
+
}).format(paise / 100);
|
|
13
|
+
}
|
|
14
|
+
export function renderPrizeDrawOg(doc, opts) {
|
|
15
|
+
const entryPaise = doc?.pricePerEntry ?? doc?.price ?? null;
|
|
16
|
+
const pricePerEntryLabel = typeof entryPaise === "number" && entryPaise > 0
|
|
17
|
+
? `${formatPriceInr(entryPaise, doc?.currency ?? "INR")} / entry`
|
|
18
|
+
: "Free entry";
|
|
19
|
+
const max = doc?.prizeMaxEntries ?? null;
|
|
20
|
+
const current = doc?.prizeCurrentEntries ?? 0;
|
|
21
|
+
const entriesLabel = typeof max === "number" && max > 0
|
|
22
|
+
? `${Math.max(0, max - current).toLocaleString("en-IN")} of ${max.toLocaleString("en-IN")} entries left`
|
|
23
|
+
: null;
|
|
24
|
+
return renderPrizeDrawOgImage({
|
|
25
|
+
title: doc?.title ?? doc?.name ?? "Prize Draw",
|
|
26
|
+
pricePerEntryLabel,
|
|
27
|
+
imageUrl: resolveOgImageUrl(doc?.mainImage || doc?.images?.[0] || null, opts.baseUrl),
|
|
28
|
+
revealStatus: doc?.prizeRevealStatus ?? null,
|
|
29
|
+
entriesLabel,
|
|
30
|
+
}, opts.siteName);
|
|
31
|
+
}
|
|
32
|
+
const REVEAL_BADGE_TEXT = {
|
|
33
|
+
pending: "Reveal pending",
|
|
34
|
+
open: "Reveal open",
|
|
35
|
+
closed: "Reveal closed",
|
|
36
|
+
};
|
|
37
|
+
export function renderPrizeDrawOgImage(data, siteName) {
|
|
38
|
+
const badges = [
|
|
39
|
+
data.pricePerEntryLabel,
|
|
40
|
+
data.revealStatus ? REVEAL_BADGE_TEXT[data.revealStatus] : null,
|
|
41
|
+
].filter((s) => Boolean(s));
|
|
42
|
+
return renderOgLayout({
|
|
43
|
+
title: data.title,
|
|
44
|
+
subtitle: data.entriesLabel ?? undefined,
|
|
45
|
+
imageUrl: data.imageUrl,
|
|
46
|
+
siteName: `${siteName} · Prize Draw`,
|
|
47
|
+
badges: badges.length > 0 ? badges : undefined,
|
|
48
|
+
theme: { accentColor: "#fbbf24" },
|
|
49
|
+
});
|
|
50
|
+
}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { renderOgLayout } from "../seo/og-layout";
|
|
2
2
|
import { resolveOgImageUrl } from "../seo/og";
|
|
3
3
|
/** High-level OG renderer — accepts the raw product document from `getProductForDetail`. */
|
|
4
4
|
export function renderProductOg(doc, opts) {
|
|
@@ -9,36 +9,11 @@ export function renderProductOg(doc, opts) {
|
|
|
9
9
|
}, opts.siteName);
|
|
10
10
|
}
|
|
11
11
|
export function renderProductOgImage(data, siteName) {
|
|
12
|
-
const
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
fontFamily: "sans-serif",
|
|
20
|
-
position: "relative",
|
|
21
|
-
overflow: "hidden",
|
|
22
|
-
}, children: [imageUrl && (_jsx("img", { src: imageUrl, alt: "", style: { position: "absolute", inset: 0, width: "100%", height: "100%", objectFit: "cover", opacity: 0.15 } })), _jsx("div", { style: {
|
|
23
|
-
position: "absolute",
|
|
24
|
-
inset: 0,
|
|
25
|
-
background: "linear-gradient(135deg, rgba(15,23,42,0.95) 0%, rgba(15,23,42,0.8) 100%)",
|
|
26
|
-
} }), _jsxs("div", { style: {
|
|
27
|
-
position: "relative",
|
|
28
|
-
display: "flex",
|
|
29
|
-
width: "100%",
|
|
30
|
-
height: "100%",
|
|
31
|
-
padding: "60px",
|
|
32
|
-
gap: "48px",
|
|
33
|
-
alignItems: "center",
|
|
34
|
-
}, children: [imageUrl && (_jsx("img", { src: imageUrl, alt: title, style: { width: 420, height: 420, objectFit: "contain", borderRadius: 16, flexShrink: 0 } })), _jsxs("div", { style: { display: "flex", flexDirection: "column", gap: 24, flex: 1 }, children: [_jsx("div", { style: { fontSize: 20, color: "#84e122", fontWeight: 600, letterSpacing: 2, textTransform: "uppercase" }, children: siteName }), _jsx("div", { style: {
|
|
35
|
-
fontSize: imageUrl ? 44 : 56,
|
|
36
|
-
fontWeight: 700,
|
|
37
|
-
color: "#f1f5f9",
|
|
38
|
-
lineHeight: 1.2,
|
|
39
|
-
display: "-webkit-box",
|
|
40
|
-
WebkitLineClamp: 3,
|
|
41
|
-
WebkitBoxOrient: "vertical",
|
|
42
|
-
overflow: "hidden",
|
|
43
|
-
}, children: title }), priceLabel && (_jsx("div", { style: { fontSize: 36, fontWeight: 800, color: "#84e122" }, children: priceLabel }))] })] })] }));
|
|
12
|
+
const priceLabel = data.price ? `₹${(data.price / 100).toLocaleString("en-IN")}` : null;
|
|
13
|
+
return renderOgLayout({
|
|
14
|
+
title: data.title,
|
|
15
|
+
imageUrl: data.imageUrl,
|
|
16
|
+
siteName,
|
|
17
|
+
accentSlot: priceLabel,
|
|
18
|
+
});
|
|
44
19
|
}
|
|
@@ -55,5 +55,5 @@ export function renderScamOgImage(data, siteName) {
|
|
|
55
55
|
fontSize: 22,
|
|
56
56
|
color: "#f87171",
|
|
57
57
|
fontWeight: 600,
|
|
58
|
-
}, children: scamTypeLabel }), reportCount > 0 && (_jsxs("div", { style: { fontSize: 22, color: "#64748b" }, children: [reportCount, " ", reportCount === 1 ? "report" : "reports"] }))] }),
|
|
58
|
+
}, children: scamTypeLabel }), reportCount > 0 && (_jsxs("div", { style: { fontSize: 22, color: "#64748b" }, children: [reportCount, " ", reportCount === 1 ? "report" : "reports"] }))] }), _jsxs("div", { style: { fontSize: 20, color: "#64748b", marginTop: 8 }, children: ["Do not transact with this individual. Verified by the ", siteName, " community."] })] })] }));
|
|
59
59
|
}
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
import type { ReactElement, ReactNode } from "react";
|
|
2
|
+
/**
|
|
3
|
+
* `renderOgLayout` — W1-1 — single shared OG card renderer that the 18 per-feature
|
|
4
|
+
* `og.tsx` files can delegate to. Layout: dark hero with optional background image
|
|
5
|
+
* (15% opacity wash), large feature image on the left, title + subtitle + badges +
|
|
6
|
+
* site brand stacked on the right. Each feature builds its own thin adapter that
|
|
7
|
+
* pulls the right fields off its document and passes them as slots here.
|
|
8
|
+
*
|
|
9
|
+
* The signature is intentionally narrow — domain-specific decorations (price
|
|
10
|
+
* pill, countdown, score chip) flow in via the `badges` array or the optional
|
|
11
|
+
* `accentSlot` (e.g. price label, urgency message). Anything more bespoke
|
|
12
|
+
* should compose this layout from outside, not extend it.
|
|
13
|
+
*/
|
|
14
|
+
export interface OgLayoutSlots {
|
|
15
|
+
/** Headline rendered at the largest type size. */
|
|
16
|
+
title: string;
|
|
17
|
+
/** Optional subtitle below the title. */
|
|
18
|
+
subtitle?: string;
|
|
19
|
+
/** Optional feature image rendered on the left (square contain-fit). */
|
|
20
|
+
imageUrl?: string | null;
|
|
21
|
+
/** Site brand label rendered as the eyebrow. */
|
|
22
|
+
siteName: string;
|
|
23
|
+
/** Optional badge chips rendered above the title. */
|
|
24
|
+
badges?: ReactNode[];
|
|
25
|
+
/** Optional accent line rendered below the title (price, countdown, etc.). */
|
|
26
|
+
accentSlot?: ReactNode;
|
|
27
|
+
/** Optional theme overrides — hex strings only (Satori doesn't accept CSS vars). */
|
|
28
|
+
theme?: Partial<OgLayoutTheme>;
|
|
29
|
+
}
|
|
30
|
+
export interface OgLayoutTheme {
|
|
31
|
+
/** Background base color. */
|
|
32
|
+
background: string;
|
|
33
|
+
/** Headline color. */
|
|
34
|
+
titleColor: string;
|
|
35
|
+
/** Subtitle / body text color. */
|
|
36
|
+
bodyColor: string;
|
|
37
|
+
/** Brand accent color used for the eyebrow + price. */
|
|
38
|
+
accentColor: string;
|
|
39
|
+
/** Gradient overlay (CSS gradient string). */
|
|
40
|
+
overlayGradient: string;
|
|
41
|
+
}
|
|
42
|
+
export declare function renderOgLayout(slots: OgLayoutSlots): ReactElement;
|