@mohasinac/appkit 4.30.18 → 4.31.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.
Files changed (557) hide show
  1. package/dist/_internal/client/features/digital-code/CodeRevealPanel.js +5 -2
  2. package/dist/_internal/client/features/layout/DashboardLayoutClient.js +3 -3
  3. package/dist/_internal/client/features/layout/useSidebarSearch.d.ts +21 -5
  4. package/dist/_internal/client/features/layout/useSidebarSearch.js +27 -6
  5. package/dist/_internal/client/features/lottery/LotteryAdminEditView.d.ts +23 -3
  6. package/dist/_internal/client/features/lottery/LotteryAdminEditView.js +106 -86
  7. package/dist/_internal/client/features/lottery/LotteryPullForm.d.ts +16 -5
  8. package/dist/_internal/client/features/lottery/LotteryPullForm.js +65 -40
  9. package/dist/_internal/client/features/maintenance/views/AnalysisRunnerView.js +5 -2
  10. package/dist/_internal/client/features/maintenance/views/CloudLogsListView.js +11 -3
  11. package/dist/_internal/client/hand-mode/HandModeProvider.js +2 -0
  12. package/dist/_internal/server/features/auctions/actions.js +14 -3
  13. package/dist/_internal/server/features/auctions/service.js +1 -1
  14. package/dist/_internal/server/features/auth/permissions.d.ts +2 -0
  15. package/dist/_internal/server/features/auth/permissions.js +3 -2
  16. package/dist/_internal/server/features/blog/data.js +2 -2
  17. package/dist/_internal/server/features/blog/service.js +3 -3
  18. package/dist/_internal/server/features/brands/data.js +1 -1
  19. package/dist/_internal/server/features/brands/service.js +3 -3
  20. package/dist/_internal/server/features/bundles/actions.js +6 -1
  21. package/dist/_internal/server/features/bundles/data.js +21 -4
  22. package/dist/_internal/server/features/cart/data.js +3 -1
  23. package/dist/_internal/server/features/cart/service.js +13 -2
  24. package/dist/_internal/server/features/categories/data.js +26 -6
  25. package/dist/_internal/server/features/classified/index.d.ts +0 -1
  26. package/dist/_internal/server/features/classified/index.js +0 -1
  27. package/dist/_internal/server/features/digital-code/index.d.ts +0 -1
  28. package/dist/_internal/server/features/digital-code/index.js +0 -1
  29. package/dist/_internal/server/features/events/actions.js +17 -4
  30. package/dist/_internal/server/features/events/data.js +1 -1
  31. package/dist/_internal/server/features/events/service.js +1 -1
  32. package/dist/_internal/server/features/grouped/data.js +7 -2
  33. package/dist/_internal/server/features/item-requests/data.js +1 -1
  34. package/dist/_internal/server/features/live/index.d.ts +0 -1
  35. package/dist/_internal/server/features/live/index.js +0 -1
  36. package/dist/_internal/server/features/lottery/actions.js +2 -2
  37. package/dist/_internal/server/features/lottery/data.js +1 -1
  38. package/dist/_internal/server/features/orders/actions.js +7 -7
  39. package/dist/_internal/server/features/orders/data.d.ts +1 -1
  40. package/dist/_internal/server/features/orders/data.js +14 -2
  41. package/dist/_internal/server/features/orders/service.js +1 -1
  42. package/dist/_internal/server/features/pre-orders/service.js +1 -1
  43. package/dist/_internal/server/features/prize-draws/actions.js +1 -1
  44. package/dist/_internal/server/features/products/data.js +21 -6
  45. package/dist/_internal/server/features/products/list-public.d.ts +9 -0
  46. package/dist/_internal/server/features/products/list-public.js +95 -7
  47. package/dist/_internal/server/features/products/service.js +1 -1
  48. package/dist/_internal/server/features/promotions/actions.js +1 -1
  49. package/dist/_internal/server/features/promotions/data.js +1 -1
  50. package/dist/_internal/server/features/promotions/service.js +1 -1
  51. package/dist/_internal/server/features/reviews/data.d.ts +1 -1
  52. package/dist/_internal/server/features/reviews/data.js +6 -1
  53. package/dist/_internal/server/features/reviews/og-data.js +1 -1
  54. package/dist/_internal/server/features/shared/listing-data-factory.js +7 -2
  55. package/dist/_internal/server/features/site-settings/adapters.d.ts +2 -2
  56. package/dist/_internal/server/features/site-settings/adapters.js +8 -5
  57. package/dist/_internal/server/features/stores/data.js +1 -1
  58. package/dist/_internal/server/features/sublisting-categories/data.js +1 -1
  59. package/dist/_internal/server/features/tester/visibility.d.ts +2 -1
  60. package/dist/_internal/server/features/tester/visibility.js +2 -2
  61. package/dist/_internal/server/functions/scheduled.d.ts +3 -1
  62. package/dist/_internal/server/functions/scheduled.js +27 -1
  63. package/dist/_internal/server/jobs/core/auctionSettlement.js +6 -1
  64. package/dist/_internal/server/jobs/core/hardBanCascade.js +4 -0
  65. package/dist/_internal/server/jobs/core/index.d.ts +2 -0
  66. package/dist/_internal/server/jobs/core/index.js +2 -0
  67. package/dist/_internal/server/jobs/core/onOrderStatusChange.js +7 -15
  68. package/dist/_internal/server/jobs/core/pageViewPrune.d.ts +10 -0
  69. package/dist/_internal/server/jobs/core/pageViewPrune.js +44 -0
  70. package/dist/_internal/server/jobs/core/pageViewRollup.d.ts +2 -0
  71. package/dist/_internal/server/jobs/core/pageViewRollup.js +87 -0
  72. package/dist/_internal/server/jobs/core/revenueRollup.js +7 -1
  73. package/dist/_internal/server/jobs/handlers/index.d.ts +2 -0
  74. package/dist/_internal/server/jobs/handlers/index.js +2 -0
  75. package/dist/_internal/server/jobs/handlers/pageViewPrune.d.ts +2 -0
  76. package/dist/_internal/server/jobs/handlers/pageViewPrune.js +2 -0
  77. package/dist/_internal/server/jobs/handlers/pageViewRollup.d.ts +2 -0
  78. package/dist/_internal/server/jobs/handlers/pageViewRollup.js +2 -0
  79. package/dist/_internal/shared/actions/action-registry.d.ts +1 -1
  80. package/dist/_internal/shared/actions/action-registry.js +69 -22
  81. package/dist/_internal/shared/checkout/rules/classified.rule.d.ts +9 -4
  82. package/dist/_internal/shared/checkout/rules/classified.rule.js +7 -2
  83. package/dist/_internal/shared/features/layout/matchesNavQuery.d.ts +14 -0
  84. package/dist/_internal/shared/features/layout/matchesNavQuery.js +72 -0
  85. package/dist/_internal/shared/features/layout/types.d.ts +37 -1
  86. package/dist/_internal/shared/features/layout/types.js +19 -1
  87. package/dist/_internal/shared/features/notifications/action-url.d.ts +9 -1
  88. package/dist/_internal/shared/features/notifications/action-url.js +47 -0
  89. package/dist/_internal/shared/features/offers/config.d.ts +65 -0
  90. package/dist/_internal/shared/features/offers/config.js +73 -2
  91. package/dist/_internal/shared/features/orders/schema.d.ts +19 -1
  92. package/dist/_internal/shared/features/orders/schema.js +22 -2
  93. package/dist/_internal/shared/features/site-settings/types.d.ts +12 -3
  94. package/dist/_internal/shared/listing-types/capabilities.d.ts +8 -2
  95. package/dist/_internal/shared/listing-types/capabilities.js +6 -1
  96. package/dist/_internal/shared/listing-types/classified/ctas.js +6 -1
  97. package/dist/_internal/shared/listing-types/feature-flags.d.ts +10 -5
  98. package/dist/_internal/shared/listing-types/feature-flags.js +11 -6
  99. package/dist/client/api/useApiQuery.js +17 -6
  100. package/dist/client.d.ts +38 -20
  101. package/dist/client.js +39 -14
  102. package/dist/configs/next.js +10 -2
  103. package/dist/constants/api-endpoints.d.ts +18 -54
  104. package/dist/constants/api-endpoints.js +6 -26
  105. package/dist/constants/field-names.d.ts +6 -24
  106. package/dist/constants/field-names.js +10 -27
  107. package/dist/constants/geo/countries.d.ts +50 -0
  108. package/dist/constants/geo/countries.js +129 -0
  109. package/dist/constants/geo/subdivisions.d.ts +13 -0
  110. package/dist/constants/geo/subdivisions.js +104 -0
  111. package/dist/constants/index.d.ts +2 -2
  112. package/dist/constants/index.js +2 -2
  113. package/dist/constants/table-keys.d.ts +24 -0
  114. package/dist/constants/table-keys.js +28 -0
  115. package/dist/contracts/client-realtime.d.ts +6 -0
  116. package/dist/contracts/extend.d.ts +0 -9
  117. package/dist/contracts/index.d.ts +1 -1
  118. package/dist/contracts/realtime-session.d.ts +12 -12
  119. package/dist/contracts/realtime-session.js +79 -77
  120. package/dist/core/browser.d.ts +1 -1
  121. package/dist/core/browser.js +1 -1
  122. package/dist/core/index.d.ts +1 -1
  123. package/dist/core/index.js +1 -1
  124. package/dist/core/site-config.d.ts +0 -3
  125. package/dist/core/site-config.js +0 -3
  126. package/dist/errors/index.d.ts +1 -1
  127. package/dist/errors/index.js +1 -1
  128. package/dist/errors/messages.d.ts +0 -8
  129. package/dist/errors/messages.js +0 -9
  130. package/dist/features/about/components/DeveloperView.js +7 -2
  131. package/dist/features/about/components/PolicyPageView.js +9 -1
  132. package/dist/features/about/components/PublicProfileView.js +23 -5
  133. package/dist/features/about/schemas/index.d.ts +8 -8
  134. package/dist/features/account/components/AddressFilters.js +32 -11
  135. package/dist/features/account/components/AddressForm.d.ts +26 -25
  136. package/dist/features/account/components/AddressForm.js +81 -103
  137. package/dist/features/account/components/AddressesIndexListing.js +8 -4
  138. package/dist/features/account/components/NotificationBell.js +4 -3
  139. package/dist/features/account/components/NotificationPreferencesPanel.js +1 -1
  140. package/dist/features/account/components/UserOffersPanel.js +1 -1
  141. package/dist/features/account/components/UserSidebar.d.ts +3 -4
  142. package/dist/features/account/components/UserSupportView.js +89 -58
  143. package/dist/features/account/components/index.d.ts +1 -7
  144. package/dist/features/account/components/index.js +0 -3
  145. package/dist/features/account/hooks/useAddresses.d.ts +4 -3
  146. package/dist/features/account/hooks/useAddresses.js +4 -6
  147. package/dist/features/account/hooks/useCollapsedSections.d.ts +51 -10
  148. package/dist/features/account/hooks/useCollapsedSections.js +211 -38
  149. package/dist/features/account/hooks/useProfile.d.ts +8 -0
  150. package/dist/features/account/index.d.ts +0 -3
  151. package/dist/features/account/index.js +0 -3
  152. package/dist/features/account/schemas/index.d.ts +0 -92
  153. package/dist/features/account/schemas/index.js +42 -20
  154. package/dist/features/addresses/components/AddressLocationFields.d.ts +13 -0
  155. package/dist/features/addresses/components/AddressLocationFields.js +41 -0
  156. package/dist/features/addresses/hooks/usePostalLookup.d.ts +17 -0
  157. package/dist/features/addresses/hooks/usePostalLookup.js +133 -0
  158. package/dist/features/addresses/schemas/address-form.d.ts +423 -0
  159. package/dist/features/addresses/schemas/address-form.js +212 -0
  160. package/dist/features/addresses/schemas/index.d.ts +1 -0
  161. package/dist/features/addresses/schemas/index.js +8 -0
  162. package/dist/features/admin/actions/admin-read-actions.d.ts +1 -1
  163. package/dist/features/admin/actions/index.d.ts +0 -1
  164. package/dist/features/admin/actions/index.js +0 -1
  165. package/dist/features/admin/actions/notification-actions.js +1 -41
  166. package/dist/features/admin/components/AdminActionIndexView.d.ts +32 -0
  167. package/dist/features/admin/components/AdminActionIndexView.js +128 -0
  168. package/dist/features/admin/components/AdminAdEditorView.js +159 -163
  169. package/dist/features/admin/components/AdminAddressEditorView.js +97 -55
  170. package/dist/features/admin/components/AdminBrandEditorView.d.ts +15 -0
  171. package/dist/features/admin/components/AdminBrandEditorView.js +113 -77
  172. package/dist/features/admin/components/AdminBundleEditorView.d.ts +19 -9
  173. package/dist/features/admin/components/AdminBundleEditorView.js +136 -168
  174. package/dist/features/admin/components/AdminCategoryEditorView.js +120 -43
  175. package/dist/features/admin/components/AdminCouponEditorView.js +145 -109
  176. package/dist/features/admin/components/AdminEmployeeEditorView.js +125 -56
  177. package/dist/features/admin/components/AdminFaqEditorView.js +112 -58
  178. package/dist/features/admin/components/AdminFeatureEditorView.js +108 -68
  179. package/dist/features/admin/components/AdminFulfillmentView.js +5 -2
  180. package/dist/features/admin/components/AdminMediaView.js +3 -3
  181. package/dist/features/admin/components/AdminNavEditorView.js +69 -44
  182. package/dist/features/admin/components/AdminOrderEditorView.js +47 -10
  183. package/dist/features/admin/components/AdminPrizeDrawsView.js +16 -2
  184. package/dist/features/admin/components/AdminSidebar.d.ts +11 -7
  185. package/dist/features/admin/components/AdminSiteSettingsView.js +37 -37
  186. package/dist/features/admin/components/AdminStoreEditorView.js +75 -52
  187. package/dist/features/admin/components/AdminSublistingCategoryEditorView.js +71 -30
  188. package/dist/features/admin/components/AdminTesterChecklistItemEditorView.js +95 -65
  189. package/dist/features/admin/components/BrandQuickCreateForm.d.ts +10 -0
  190. package/dist/features/admin/components/BrandQuickCreateForm.js +49 -26
  191. package/dist/features/admin/components/CategoryQuickCreateForm.d.ts +11 -0
  192. package/dist/features/admin/components/CategoryQuickCreateForm.js +48 -26
  193. package/dist/features/admin/components/index.d.ts +2 -2
  194. package/dist/features/admin/components/index.js +1 -1
  195. package/dist/features/admin/constants/site-settings-tabs.d.ts +120 -0
  196. package/dist/features/admin/constants/site-settings-tabs.js +152 -0
  197. package/dist/features/admin/index.d.ts +0 -3
  198. package/dist/features/admin/index.js +0 -2
  199. package/dist/features/admin/repository/analytics-rollup.repository.d.ts +35 -0
  200. package/dist/features/admin/repository/analytics-rollup.repository.js +30 -0
  201. package/dist/features/admin/schemas/admin-editor-forms.d.ts +56 -57
  202. package/dist/features/admin/schemas/admin-editor-forms.js +97 -54
  203. package/dist/features/admin/schemas/admin-ops-forms.d.ts +57 -5
  204. package/dist/features/admin/schemas/admin-ops-forms.js +104 -20
  205. package/dist/features/admin/schemas/admin-user-form.js +7 -0
  206. package/dist/features/admin/schemas/firestore.d.ts +48 -95
  207. package/dist/features/admin/schemas/firestore.js +15 -151
  208. package/dist/features/admin/schemas/nav-item-form.js +9 -2
  209. package/dist/features/admin/server.d.ts +0 -4
  210. package/dist/features/admin/server.js +0 -2
  211. package/dist/features/admin/types/index.d.ts +0 -7
  212. package/dist/features/analytics/repository/page-views.repository.d.ts +14 -0
  213. package/dist/features/analytics/repository/page-views.repository.js +24 -0
  214. package/dist/features/analytics/types.d.ts +1 -1
  215. package/dist/features/analytics/types.js +13 -0
  216. package/dist/features/auctions/components/AuctionDetailPageView.js +6 -2
  217. package/dist/features/auctions/components/MarketplaceAuctionCard.js +3 -1
  218. package/dist/features/auth/actions/index.d.ts +0 -1
  219. package/dist/features/auth/actions/index.js +0 -1
  220. package/dist/features/auth/actions/profile-actions.js +4 -3
  221. package/dist/features/auth/actions/realtime-token-actions.js +1 -12
  222. package/dist/features/auth/auth-helpers.js +5 -7
  223. package/dist/features/auth/components/ForgotPasswordView.js +1 -1
  224. package/dist/features/auth/components/Guards.js +2 -1
  225. package/dist/features/auth/components/LoginForm.d.ts +0 -2
  226. package/dist/features/auth/components/LoginForm.js +2 -4
  227. package/dist/features/auth/components/RegisterForm.js +62 -19
  228. package/dist/features/auth/components/ResetPasswordView.js +1 -1
  229. package/dist/features/auth/hooks/useAuth.js +3 -0
  230. package/dist/features/auth/permissions/constants.d.ts +27 -1
  231. package/dist/features/auth/role-predicates.d.ts +75 -7
  232. package/dist/features/auth/role-predicates.js +28 -2
  233. package/dist/features/auth/schemas/firestore.d.ts +22 -0
  234. package/dist/features/auth/schemas/index.d.ts +1 -1
  235. package/dist/features/auth/schemas/index.js +44 -8
  236. package/dist/features/auth/types/index.d.ts +14 -1
  237. package/dist/features/blog/api/route.js +10 -2
  238. package/dist/features/blog/components/BlogIndexListing.js +1 -1
  239. package/dist/features/blog/hooks/useBlog.js +2 -2
  240. package/dist/features/blog/repository/blog.repository.js +3 -1
  241. package/dist/features/blog/schemas/index.d.ts +4 -0
  242. package/dist/features/blog/schemas/index.js +2 -0
  243. package/dist/features/blog/types/index.d.ts +1 -1
  244. package/dist/features/cart/actions/cart-actions.js +13 -4
  245. package/dist/features/cart/utils/pending-ops.js +1 -1
  246. package/dist/features/catalogue/components/CatalogueItemEditorView.d.ts +22 -0
  247. package/dist/features/catalogue/components/CatalogueItemEditorView.js +112 -52
  248. package/dist/features/catalogue/schemas/validation.d.ts +4 -4
  249. package/dist/features/catalogue/schemas/validation.js +47 -10
  250. package/dist/features/categories/components/BrandDetailPageView.js +28 -12
  251. package/dist/features/categories/components/CategoryDetailPageView.js +37 -20
  252. package/dist/features/categories/repository/categories.repository.js +3 -1
  253. package/dist/features/categories/schemas/bundle-form.d.ts +142 -0
  254. package/dist/features/categories/schemas/bundle-form.js +149 -0
  255. package/dist/features/checkout/actions/checkout-value-otp-actions.js +10 -1
  256. package/dist/features/classified/components/ClassifiedContactSellerPanel.js +1 -1
  257. package/dist/features/classified/components/ClassifiedDetailPageView.d.ts +5 -4
  258. package/dist/features/classified/components/ClassifiedDetailPageView.js +47 -18
  259. package/dist/features/consultation/components/ConsultationForm.js +1 -1
  260. package/dist/features/consultation/schemas/index.js +34 -10
  261. package/dist/features/corporate/schemas/index.js +36 -15
  262. package/dist/features/digital-codes/components/DigitalCodeDetailPageView.js +4 -1
  263. package/dist/features/events/components/EventBanner.js +5 -2
  264. package/dist/features/events/components/EventOfferCard.js +3 -1
  265. package/dist/features/events/components/EventPollWidget.js +1 -1
  266. package/dist/features/events/components/SpinWheelView.js +3 -2
  267. package/dist/features/filters/FilterPanel.js +3 -3
  268. package/dist/features/filters/RangeFilter.d.ts +10 -0
  269. package/dist/features/filters/RangeFilter.js +41 -4
  270. package/dist/features/grouped/components/GroupedListingEditorView.js +2 -1
  271. package/dist/features/history/hooks/useHistory.js +29 -27
  272. package/dist/features/homepage/components/AdSlot.js +3 -1
  273. package/dist/features/homepage/components/GoogleReviewsSection.js +8 -2
  274. package/dist/features/homepage/components/MarketplaceHomepageView.js +58 -15
  275. package/dist/features/homepage/components/SocialFeedSection.js +4 -1
  276. package/dist/features/homepage/hooks/useBlogArticles.js +1 -1
  277. package/dist/features/homepage/lib/live-stats.js +8 -1
  278. package/dist/features/homepage/repository/carousel.repository.js +2 -1
  279. package/dist/features/layout/BottomActions.js +84 -11
  280. package/dist/features/layout/BottomActionsContext.d.ts +1 -6
  281. package/dist/features/layout/BottomActionsContext.js +1 -1
  282. package/dist/features/layout/hooks/useBottomActions.js +2 -2
  283. package/dist/features/layout/hooks/useFormBottomActions.d.ts +12 -1
  284. package/dist/features/layout/hooks/useFormBottomActions.js +12 -6
  285. package/dist/features/live/components/LiveItemDetailPageView.js +4 -1
  286. package/dist/features/lottery/schemas/config-write.d.ts +9 -5
  287. package/dist/features/lottery/schemas/config-write.js +69 -9
  288. package/dist/features/media/finalize.js +3 -1
  289. package/dist/features/media/modals/ImageEditor.js +1 -1
  290. package/dist/features/media/modals/VideoThumbnailSelector.js +5 -2
  291. package/dist/features/media/modals/VideoTrimModal.js +5 -2
  292. package/dist/features/media/upload/MediaUploadField.js +2 -2
  293. package/dist/features/messages/hooks/useConversation.js +18 -4
  294. package/dist/features/messages/hooks/useConversations.js +25 -8
  295. package/dist/features/orders/components/RefundRequestView.js +5 -2
  296. package/dist/features/orders/schemas/buyer-forms.d.ts +6 -3
  297. package/dist/features/orders/schemas/buyer-forms.js +31 -3
  298. package/dist/features/orders/schemas/index.d.ts +2 -2
  299. package/dist/features/pre-orders/components/MarketplacePreorderCard.js +3 -1
  300. package/dist/features/pre-orders/components/PreOrderActionsClient.js +1 -1
  301. package/dist/features/pre-orders/components/PreOrderDetailPageView.js +4 -1
  302. package/dist/features/products/components/GroupSettingsPanel.js +3 -1
  303. package/dist/features/products/components/MakeOfferButton.d.ts +13 -2
  304. package/dist/features/products/components/MakeOfferButton.js +33 -11
  305. package/dist/features/products/components/PrizeDrawDetailPageView.js +4 -1
  306. package/dist/features/products/components/ProductDetailActions.js +0 -1
  307. package/dist/features/products/components/ProductDetailPageView.d.ts +7 -3
  308. package/dist/features/products/components/ProductDetailPageView.js +16 -7
  309. package/dist/features/products/components/ShareButton.js +3 -1
  310. package/dist/features/products/constants/action-defs.d.ts +1 -2
  311. package/dist/features/products/constants/action-defs.js +40 -43
  312. package/dist/features/products/repository/loadProductFeatures.js +10 -2
  313. package/dist/features/products/repository/products.repository.d.ts +5 -1
  314. package/dist/features/products/repository/products.repository.js +25 -2
  315. package/dist/features/products/schemas/firestore.d.ts +7 -3
  316. package/dist/features/products/schemas/product-features.validators.js +3 -0
  317. package/dist/features/promotions/components/CouponCard.js +11 -8
  318. package/dist/features/reviews/actions/review-actions.js +8 -1
  319. package/dist/features/reviews/components/ReviewDetailPageView.js +13 -3
  320. package/dist/features/reviews/components/ReviewDetailShell.js +3 -1
  321. package/dist/features/scams/actions/scam-actions.d.ts +9 -1
  322. package/dist/features/scams/actions/scam-actions.js +52 -12
  323. package/dist/features/scams/components/SellerTrustBadge.d.ts +1 -1
  324. package/dist/features/scams/components/SellerTrustBadge.js +13 -0
  325. package/dist/features/scams/repository/scammer.repository.js +2 -1
  326. package/dist/features/scams/schemas/firestore.d.ts +15 -1
  327. package/dist/features/scams/schemas/report-form.d.ts +5 -5
  328. package/dist/features/scams/schemas/report-form.js +18 -3
  329. package/dist/features/search/action-index/derive.d.ts +49 -0
  330. package/dist/features/search/action-index/derive.js +121 -0
  331. package/dist/features/search/action-index/repository.d.ts +42 -0
  332. package/dist/features/search/action-index/repository.js +100 -0
  333. package/dist/features/search/action-index/settings-entries.d.ts +41 -0
  334. package/dist/features/search/action-index/settings-entries.js +268 -0
  335. package/dist/features/search/action-index/types.d.ts +81 -0
  336. package/dist/features/search/action-index/types.js +102 -0
  337. package/dist/features/search/action-index/validate-entry.d.ts +34 -0
  338. package/dist/features/search/action-index/validate-entry.js +114 -0
  339. package/dist/features/search/hooks/useNavSuggestions.d.ts +5 -1
  340. package/dist/features/search/hooks/useNavSuggestions.js +23 -3
  341. package/dist/features/search/repository/search.repository.js +3 -1
  342. package/dist/features/seller/actions/offer-actions.js +43 -19
  343. package/dist/features/seller/actions/seller-actions.js +29 -5
  344. package/dist/features/seller/components/CategoryChipPicker.d.ts +9 -0
  345. package/dist/features/seller/components/CategoryChipPicker.js +12 -0
  346. package/dist/features/seller/components/FulfillmentView.js +5 -2
  347. package/dist/features/seller/components/PhysicalLocationModal.js +1 -1
  348. package/dist/features/seller/components/PrintCenterView.js +3 -1
  349. package/dist/features/seller/components/SellerAddressesView.js +5 -1
  350. package/dist/features/seller/components/SellerAnalyticsAlertsView.js +83 -43
  351. package/dist/features/seller/components/SellerArtView.d.ts +14 -7
  352. package/dist/features/seller/components/SellerArtView.js +4 -119
  353. package/dist/features/seller/components/SellerBidsView.js +1 -1
  354. package/dist/features/seller/components/SellerClassifiedView.d.ts +14 -7
  355. package/dist/features/seller/components/SellerClassifiedView.js +4 -124
  356. package/dist/features/seller/components/SellerCouponEditorView.d.ts +22 -1
  357. package/dist/features/seller/components/SellerCouponEditorView.js +91 -45
  358. package/dist/features/seller/components/SellerCouponsView.js +1 -1
  359. package/dist/features/seller/components/SellerDigitalCodesView.d.ts +14 -7
  360. package/dist/features/seller/components/SellerDigitalCodesView.js +4 -126
  361. package/dist/features/seller/components/SellerGoogleReviewsView.js +2 -2
  362. package/dist/features/seller/components/SellerListingTypeView.d.ts +66 -0
  363. package/dist/features/seller/components/SellerListingTypeView.js +277 -0
  364. package/dist/features/seller/components/SellerLiveView.d.ts +14 -7
  365. package/dist/features/seller/components/SellerLiveView.js +4 -126
  366. package/dist/features/seller/components/SellerOrdersView.js +3 -3
  367. package/dist/features/seller/components/SellerPayoutMethodsView.js +2 -2
  368. package/dist/features/seller/components/SellerProductShell.d.ts +5 -0
  369. package/dist/features/seller/components/SellerProductShell.js +15 -5
  370. package/dist/features/seller/components/SellerProductsView.js +24 -10
  371. package/dist/features/seller/components/SellerReviewsView.js +47 -16
  372. package/dist/features/seller/components/SellerShippingConfigsView.js +5 -4
  373. package/dist/features/seller/components/SellerSidebar.d.ts +3 -6
  374. package/dist/features/seller/components/SellerStickersView.d.ts +14 -7
  375. package/dist/features/seller/components/SellerStickersView.js +4 -119
  376. package/dist/features/seller/components/SellerStoreCategoriesView.js +3 -2
  377. package/dist/features/seller/components/SellerSupportView.d.ts +31 -0
  378. package/dist/features/seller/components/SellerSupportView.js +100 -0
  379. package/dist/features/seller/components/index.d.ts +4 -8
  380. package/dist/features/seller/components/index.js +2 -4
  381. package/dist/features/seller/index.d.ts +0 -1
  382. package/dist/features/seller/index.js +0 -1
  383. package/dist/features/seller/schemas/coupon-form.d.ts +214 -0
  384. package/dist/features/seller/schemas/coupon-form.js +155 -23
  385. package/dist/features/seller/schemas/offer-forms.d.ts +16 -7
  386. package/dist/features/seller/schemas/offer-forms.js +28 -12
  387. package/dist/features/shell/FormShell.js +2 -2
  388. package/dist/features/shell/QuickFormDrawer.js +2 -2
  389. package/dist/features/shell/SectionForm.d.ts +19 -1
  390. package/dist/features/shell/SectionForm.js +104 -17
  391. package/dist/features/shell/build-sections.d.ts +23 -0
  392. package/dist/features/shell/build-sections.js +106 -8
  393. package/dist/features/shell/field-ui-meta.d.ts +44 -0
  394. package/dist/features/shell/field-ui-meta.js +14 -7
  395. package/dist/features/shell/form-sections.d.ts +46 -0
  396. package/dist/features/shell/form-sections.js +114 -0
  397. package/dist/features/shipments/components/AdminShipmentEditorView.js +87 -64
  398. package/dist/features/shipments/schemas/validation.d.ts +2 -2
  399. package/dist/features/shipments/schemas/validation.js +44 -13
  400. package/dist/features/store-extensions/schemas/custom-role-form.js +6 -2
  401. package/dist/features/store-extensions/schemas/listing-template-form.d.ts +7 -7
  402. package/dist/features/store-extensions/schemas/payout-method-form.js +14 -0
  403. package/dist/features/stores/actions/store-query-actions.js +3 -2
  404. package/dist/features/stores/api/[storeSlug]/auctions/route.js +3 -1
  405. package/dist/features/stores/api/[storeSlug]/products/route.js +3 -1
  406. package/dist/features/stores/components/StoreDetailLayoutView.d.ts +1 -1
  407. package/dist/features/stores/components/StoreDetailLayoutView.js +12 -3
  408. package/dist/features/support/repository/support.repository.d.ts +21 -0
  409. package/dist/features/support/repository/support.repository.js +63 -0
  410. package/dist/features/support/schemas/firestore.d.ts +27 -2
  411. package/dist/features/support/schemas/firestore.js +2 -0
  412. package/dist/features/support/schemas/ticket-create-form.js +7 -0
  413. package/dist/features/tester/schemas/checklist-item-form.d.ts +43 -0
  414. package/dist/features/tester/schemas/checklist-item-form.js +109 -0
  415. package/dist/features/tester/seed-data/blog-tester-seed-data.js +2 -2
  416. package/dist/features/tester/seed-data/categories-tester-seed-data.js +2 -2
  417. package/dist/features/tester/seed-data/events-tester-seed-data.js +5 -5
  418. package/dist/features/tester/seed-data/orders-tester-seed-data.js +2 -2
  419. package/dist/features/tester/seed-data/products-tester-seed-data.js +48 -49
  420. package/dist/features/tester/seed-data/stores-tester-seed-data.js +3 -3
  421. package/dist/features/tester/seed-data/tester-checklist-seed-data.js +291 -30
  422. package/dist/features/whatsapp-bot/components/SellerWhatsAppSettingsView.js +51 -14
  423. package/dist/features/wishlist/hooks/useWishlistToggle.js +8 -1
  424. package/dist/http/api-handler.js +2 -1
  425. package/dist/index.d.ts +25 -104
  426. package/dist/index.js +38 -143
  427. package/dist/jobs.d.ts +1 -1
  428. package/dist/jobs.js +1 -1
  429. package/dist/monitoring/browser.d.ts +0 -2
  430. package/dist/monitoring/browser.js +12 -1
  431. package/dist/monitoring/index.d.ts +0 -2
  432. package/dist/monitoring/index.js +0 -1
  433. package/dist/next/api/routeHandler.js +9 -4
  434. package/dist/next/index.d.ts +1 -2
  435. package/dist/next/index.js +0 -1
  436. package/dist/next/middleware/index.d.ts +0 -2
  437. package/dist/next/middleware/index.js +0 -1
  438. package/dist/next/routing/route-map.d.ts +8 -7
  439. package/dist/next/routing/route-map.js +10 -3
  440. package/dist/providers/auth-firebase/session.js +3 -1
  441. package/dist/providers/db-firebase/admin-app-lite.js +8 -8
  442. package/dist/providers/db-firebase/admin.js +27 -13
  443. package/dist/providers/db-firebase/browser-stub.d.ts +1 -11
  444. package/dist/providers/db-firebase/browser-stub.js +6 -11
  445. package/dist/providers/db-firebase/index.d.ts +0 -1
  446. package/dist/providers/db-firebase/index.js +0 -1
  447. package/dist/providers/db-firebase/rtdb-paths.d.ts +15 -6
  448. package/dist/providers/db-firebase/rtdb-paths.js +15 -6
  449. package/dist/providers/db-firebase/rtdb-url.d.ts +27 -0
  450. package/dist/providers/db-firebase/rtdb-url.js +50 -0
  451. package/dist/providers/db-firebase/sieve.d.ts +22 -0
  452. package/dist/providers/firebase-client/realtime.d.ts +20 -0
  453. package/dist/providers/firebase-client/realtime.js +34 -1
  454. package/dist/providers.d.ts +1 -1
  455. package/dist/providers.js +1 -1
  456. package/dist/react/hooks/use-action-dispatch.js +8 -2
  457. package/dist/react/hooks/useFormStatePreservation.js +3 -1
  458. package/dist/react/hooks/useListingTypeFlags.d.ts +1 -1
  459. package/dist/react/hooks/useListingTypeFlags.js +1 -1
  460. package/dist/react/hooks/usePendingFilters.js +5 -3
  461. package/dist/react/hooks/usePendingTable.js +15 -3
  462. package/dist/react/hooks/useRealtimeEvent.js +20 -9
  463. package/dist/repositories/index.d.ts +0 -1
  464. package/dist/repositories/index.js +0 -1
  465. package/dist/schemas/registry.d.ts +197 -232
  466. package/dist/schemas/registry.js +5 -6
  467. package/dist/schemas/webhooks/razorpay.d.ts +50 -50
  468. package/dist/security/authorization.d.ts +9 -0
  469. package/dist/security/authorization.js +16 -2
  470. package/dist/security/browser.d.ts +1 -3
  471. package/dist/security/browser.js +5 -2
  472. package/dist/security/index.d.ts +1 -3
  473. package/dist/security/index.js +19 -2
  474. package/dist/security/pii-encrypt.js +16 -0
  475. package/dist/security/pii-schemas.d.ts +0 -14
  476. package/dist/security/pii-schemas.js +7 -15
  477. package/dist/seed/_helpers/category-forest.js +2 -2
  478. package/dist/seed/_helpers/media.d.ts +19 -0
  479. package/dist/seed/_helpers/media.js +75 -0
  480. package/dist/seed/blog-posts-seed-data.js +17 -17
  481. package/dist/seed/carousel-slides-seed-data.js +7 -7
  482. package/dist/seed/cart-seed-data.js +13 -13
  483. package/dist/seed/categories-seed-data.js +10 -10
  484. package/dist/seed/events-seed-data.js +24 -24
  485. package/dist/seed/factories/product.factory.js +4 -4
  486. package/dist/seed/factories/store.factory.js +3 -3
  487. package/dist/seed/factories/user.factory.js +2 -2
  488. package/dist/seed/grouped-listings-seed-data.js +11 -11
  489. package/dist/seed/homepage-sections-seed-data.js +2 -2
  490. package/dist/seed/index.d.ts +0 -1
  491. package/dist/seed/index.js +0 -1
  492. package/dist/seed/manifest.d.ts +1 -1
  493. package/dist/seed/manifest.js +0 -5
  494. package/dist/seed/notifications-seed-data.js +20 -1
  495. package/dist/seed/orders-seed-data.js +2 -2
  496. package/dist/seed/products-art-seed-data.js +16 -16
  497. package/dist/seed/products-auctions-seed-data.js +34 -34
  498. package/dist/seed/products-classifieds-seed-data.js +35 -37
  499. package/dist/seed/products-digital-codes-seed-data.js +20 -20
  500. package/dist/seed/products-live-items-seed-data.js +11 -11
  501. package/dist/seed/products-preorders-seed-data.js +13 -13
  502. package/dist/seed/products-prize-draws-seed-data.js +43 -43
  503. package/dist/seed/products-standard-seed-data.js +54 -54
  504. package/dist/seed/products-stickers-seed-data.js +15 -15
  505. package/dist/seed/reviews-seed-data.js +4 -4
  506. package/dist/seed/scammers-seed-data.js +3 -3
  507. package/dist/seed/site-settings-seed-data.js +11 -24
  508. package/dist/seed/store-extensions-seed-data.js +10 -10
  509. package/dist/seed/stores-seed-data.js +11 -11
  510. package/dist/seed/support-tickets-seed-data.d.ts +14 -0
  511. package/dist/seed/support-tickets-seed-data.js +20 -1
  512. package/dist/seed/users-seed-data.js +20 -20
  513. package/dist/server-entry.d.ts +0 -1
  514. package/dist/server-entry.js +0 -1
  515. package/dist/server.d.ts +9 -6
  516. package/dist/server.js +7 -13
  517. package/dist/styles.css +248 -68
  518. package/dist/tailwind-utilities.css +1 -1
  519. package/dist/tokens/themes/default-dark.js +2 -2
  520. package/dist/tokens/themes/default-light.js +2 -2
  521. package/dist/tokens/tokens.css +24 -4
  522. package/dist/ui/components/ActionRow.d.ts +50 -0
  523. package/dist/ui/components/ActionRow.js +53 -0
  524. package/dist/ui/components/ActionRow.style.css +145 -0
  525. package/dist/ui/components/Drawer.d.ts +10 -0
  526. package/dist/ui/components/Drawer.js +2 -1
  527. package/dist/ui/components/FilterDrawer.js +4 -1
  528. package/dist/ui/components/FilterDrawer.style.css +6 -12
  529. package/dist/ui/components/FormActionBar.js +14 -1
  530. package/dist/ui/components/FormActionBar.style.css +12 -11
  531. package/dist/ui/components/ListingLayout.js +8 -1
  532. package/dist/ui/components/ListingLayout.style.css +6 -13
  533. package/dist/ui/components/Modal.d.ts +15 -1
  534. package/dist/ui/components/Modal.js +17 -3
  535. package/dist/ui/components/QuickCreateModal.js +2 -2
  536. package/dist/ui/components/QuickCreateModal.style.css +78 -84
  537. package/dist/ui/components/RecordDetailModal.js +2 -2
  538. package/dist/ui/components/SideDrawer.d.ts +8 -0
  539. package/dist/ui/components/SideDrawer.js +2 -1
  540. package/dist/ui/components/SideDrawer.style.css +6 -3
  541. package/dist/ui/components/SideModal.d.ts +11 -1
  542. package/dist/ui/components/SideModal.js +3 -2
  543. package/dist/ui/components/SideModal.style.css +14 -0
  544. package/dist/ui/components/Typography.style.css +33 -24
  545. package/dist/ui/components/index.style.css +1 -0
  546. package/dist/ui/components/toolbar-collapse.js +1 -2
  547. package/dist/ui/forms/FormShell.style.css +260 -311
  548. package/dist/ui/index.d.ts +2 -0
  549. package/dist/ui/index.js +1 -0
  550. package/dist/utils/index.d.ts +0 -1
  551. package/dist/utils/index.js +0 -1
  552. package/dist/validation/index.d.ts +1 -1
  553. package/dist/validation/index.js +1 -1
  554. package/dist/validation/schemas.d.ts +0 -19
  555. package/dist/validation/schemas.js +8 -19
  556. package/package.json +1 -1
  557. package/scripts/seed-cli.mjs +3 -6
@@ -0,0 +1,44 @@
1
+ /*
2
+ * WHY: `pageViews` writes one document per entity per day and had NO prune.
3
+ * Twenty-seven scheduled functions existed — `cartPrune`,
4
+ * `notificationPrune`, `draftPrune`, `dailyDataCleanup` — and not one of
5
+ * them touched this collection, so it was the only unbounded writer in the
6
+ * system. Its size was capped by nothing except how many distinct pages
7
+ * the catalogue had, multiplied by how long the site had been running.
8
+ *
9
+ * WHAT: Delete day-buckets older than the retention window. Shaped after
10
+ * `notificationPrune`, which is the smallest correct prune in the repo.
11
+ *
12
+ * The daily rows are the raw material; `pageViewRollup` keeps the long-run
13
+ * totals, so deleting the buckets loses granularity past the window and not the
14
+ * history itself.
15
+ *
16
+ * EXPORTS: PAGE_VIEW_TTL_DAYS, runPageViewPrune
17
+ *
18
+ * @tag domain:analytics
19
+ * @tag layer:job
20
+ * @tag pattern:none
21
+ * @tag access:server-only
22
+ * @tag consumers:pageViewPrune scheduled function
23
+ * @tag sideEffects:deletes pageViews documents
24
+ */
25
+ import { pageViewsRepository } from "../../../../features/analytics/repository/page-views.repository";
26
+ import { batchDelete } from "../handlers/_helpers";
27
+ /**
28
+ * 90 days.
29
+ *
30
+ * Long enough for a quarter-over-quarter comparison in the admin report, which
31
+ * is the longest range that screen offers, and short enough that the collection
32
+ * reaches a steady state instead of growing forever.
33
+ */
34
+ export const PAGE_VIEW_TTL_DAYS = 90;
35
+ export async function runPageViewPrune(ctx) {
36
+ ctx.logger.info(`Pruning page-view buckets older than ${PAGE_VIEW_TTL_DAYS} days`);
37
+ const refs = await pageViewsRepository.getOlderThanRefs(PAGE_VIEW_TTL_DAYS);
38
+ if (refs.length === 0) {
39
+ ctx.logger.info("No stale page-view buckets found");
40
+ return;
41
+ }
42
+ const deleted = await batchDelete(ctx, refs);
43
+ ctx.logger.info("Page-view prune complete", { deleted });
44
+ }
@@ -0,0 +1,2 @@
1
+ import type { JobContext } from "../runtime/types";
2
+ export declare function runPageViewRollup(ctx: JobContext): Promise<void>;
@@ -0,0 +1,87 @@
1
+ /*
2
+ * WHY: `pageViewPrune` deletes day-buckets past the retention window. Without a
3
+ * rollup that would also delete the only record that those views ever
4
+ * happened — the admin's lifetime total would silently walk backwards as
5
+ * the prune caught up with it.
6
+ *
7
+ * WHAT: Fold each new day-bucket into a singleton total before the prune can
8
+ * reach it. Modelled on `revenueRollup`: scan → one small doc → the API
9
+ * route reads a single document instead of the collection.
10
+ *
11
+ * EXPORTS: runPageViewRollup
12
+ *
13
+ * @tag domain:analytics
14
+ * @tag layer:job
15
+ * @tag pattern:none
16
+ * @tag access:server-only
17
+ * @tag consumers:pageViewRollup scheduled function
18
+ * @tag sideEffects:writes analytics/pageViewRollup
19
+ */
20
+ import { pageViewsRepository } from "../../../../features/analytics/repository/page-views.repository";
21
+ import { pageViewRollupRepository } from "../../../../features/admin/repository/analytics-rollup.repository";
22
+ /** The earliest date this rollup will fold in on a cold start. */
23
+ const EPOCH_DATE = "2020-01-01";
24
+ function dayKey(offsetDays) {
25
+ const d = new Date();
26
+ d.setUTCDate(d.getUTCDate() + offsetDays);
27
+ return d.toISOString().slice(0, 10);
28
+ }
29
+ export async function runPageViewRollup(ctx) {
30
+ const existing = await pageViewRollupRepository.get();
31
+ /*
32
+ * 🛑 `throughDate` is what makes this job re-runnable.
33
+ *
34
+ * The rollup ACCUMULATES rather than recomputing — the day-buckets it has
35
+ * already folded in get deleted by `pageViewPrune`, so a recompute-from-
36
+ * scratch would produce a total that shrinks every time the prune runs. So it
37
+ * must only ever read buckets it has not seen, and `throughDate` is the
38
+ * boundary. Running this twice in one day is a no-op; running it after a
39
+ * missed day still catches up.
40
+ */
41
+ const from = existing?.throughDate
42
+ ? dayKey(0) === existing.throughDate
43
+ ? null // already folded in today — nothing new to read
44
+ : nextDay(existing.throughDate)
45
+ : EPOCH_DATE;
46
+ if (from === null) {
47
+ ctx.logger.info("pageViewRollup: already current", {
48
+ throughDate: existing?.throughDate ?? "",
49
+ });
50
+ return;
51
+ }
52
+ // Yesterday, not today: today's buckets are still being written to, and
53
+ // folding a partial day in would make it uncountable tomorrow.
54
+ const through = dayKey(-1);
55
+ if (from > through) {
56
+ ctx.logger.info("pageViewRollup: nothing to fold", { from, through });
57
+ return;
58
+ }
59
+ /*
60
+ * No `.catch(() => [])`. An empty range is a legitimate zero, so a swallowed
61
+ * query failure would write a confident "no views" the dashboard cannot tell
62
+ * from the real thing — and unlike `revenueRollup`, this one ACCUMULATES, so
63
+ * a bad read would also advance `throughDate` past days it never counted and
64
+ * lose them permanently. Let it throw; the runner records the failure and the
65
+ * stale-but-correct singleton stays.
66
+ */
67
+ const buckets = await pageViewsRepository.listInRange(from, through);
68
+ const byEntityType = { ...(existing?.byEntityType ?? {}) };
69
+ let totalViews = existing?.totalViews ?? 0;
70
+ for (const b of buckets) {
71
+ const n = Number(b.count) || 0;
72
+ totalViews += n;
73
+ byEntityType[b.entityType] = (byEntityType[b.entityType] ?? 0) + n;
74
+ }
75
+ await pageViewRollupRepository.set({ totalViews, byEntityType, throughDate: through });
76
+ ctx.logger.info("pageViewRollup: complete", {
77
+ from,
78
+ through,
79
+ bucketsFolded: buckets.length,
80
+ totalViews,
81
+ });
82
+ }
83
+ function nextDay(dateKey) {
84
+ const d = new Date(`${dateKey}T00:00:00.000Z`);
85
+ d.setUTCDate(d.getUTCDate() + 1);
86
+ return d.toISOString().slice(0, 10);
87
+ }
@@ -12,7 +12,13 @@
12
12
  import { orderRepository } from "../../../../repositories";
13
13
  import { analyticsRollupRepository } from "../../../../repositories";
14
14
  export async function runRevenueRollup(ctx) {
15
- const deliveredOrders = await orderRepository.findByStatus("delivered").catch(() => []);
15
+ // No `.catch(() => [])` here on purpose: an empty list is a legitimate
16
+ // outcome that writes `totalRevenue: 0`, so swallowing a query failure would
17
+ // overwrite yesterday's correct rollup with a confident zero that the
18
+ // dashboard has no way to distinguish from "no delivered orders". Let it
19
+ // throw — the job runner records the failure and the stale-but-correct
20
+ // singleton stays put.
21
+ const deliveredOrders = await orderRepository.findByStatus("delivered");
16
22
  const totalRevenue = deliveredOrders.reduce((sum, order) => sum + (Number(order.totalPrice ?? 0) || 0), 0);
17
23
  await analyticsRollupRepository.setDashboardRollup({
18
24
  totalRevenue,
@@ -28,6 +28,8 @@ export { hardBanReinstatementHandler } from "./hardBanReinstatement";
28
28
  export { paymentReviewAutoApproveHandler } from "./paymentReviewAutoApprove";
29
29
  export { productStatsSyncHandler } from "./productStatsSync";
30
30
  export { revenueRollupHandler } from "./revenueRollup";
31
+ export { pageViewRollupHandler } from "./pageViewRollup";
32
+ export { pageViewPruneHandler } from "./pageViewPrune";
31
33
  export { dailyStatusDigestHandler } from "./dailyStatusDigest";
32
34
  export { positionsReconcileHandler } from "./positionsReconcile";
33
35
  export { payoutBatchHandler } from "./payoutBatch";
@@ -28,6 +28,8 @@ export { hardBanReinstatementHandler } from "./hardBanReinstatement";
28
28
  export { paymentReviewAutoApproveHandler } from "./paymentReviewAutoApprove";
29
29
  export { productStatsSyncHandler } from "./productStatsSync";
30
30
  export { revenueRollupHandler } from "./revenueRollup";
31
+ export { pageViewRollupHandler } from "./pageViewRollup";
32
+ export { pageViewPruneHandler } from "./pageViewPrune";
31
33
  export { dailyStatusDigestHandler } from "./dailyStatusDigest";
32
34
  export { positionsReconcileHandler } from "./positionsReconcile";
33
35
  export { payoutBatchHandler } from "./payoutBatch";
@@ -0,0 +1,2 @@
1
+ import type { ScheduleHandler } from "../runtime/types";
2
+ export declare const pageViewPruneHandler: ScheduleHandler;
@@ -0,0 +1,2 @@
1
+ import { runPageViewPrune } from "../core/pageViewPrune";
2
+ export const pageViewPruneHandler = runPageViewPrune;
@@ -0,0 +1,2 @@
1
+ import type { ScheduleHandler } from "../runtime/types";
2
+ export declare const pageViewRollupHandler: ScheduleHandler;
@@ -0,0 +1,2 @@
1
+ import { runPageViewRollup } from "../core/pageViewRollup";
2
+ export const pageViewRollupHandler = runPageViewRollup;
@@ -29,7 +29,7 @@ import type { IconKey } from "../../../ui/icons/icon-registry";
29
29
  /** What KIND of action — drives default UI affordance (link vs button vs danger). */
30
30
  export type ActionKind = "primary" | "secondary" | "danger" | "ghost" | "link" | "chip";
31
31
  /** Resource bucket — keyed top-level in the ACTIONS tree. */
32
- export type ActionResource = "PRODUCT" | "AUCTION" | "PRE_ORDER" | "PRIZE_DRAW" | "CLASSIFIED" | "DIGITAL_CODE" | "LIVE" | "BUNDLE" | "GROUP" | "CATEGORY" | "BRAND" | "SUBLISTING" | "STORE" | "BLOG" | "EVENT" | "SHIPMENT" | "CATALOGUE" | "USER" | "SELLER" | "ADMIN" | "CART" | "CHECKOUT" | "NAV" | "MEDIA" | "SUPPORT" | "LOTTERY" | "TESTER";
32
+ export type ActionResource = "PRODUCT" | "AUCTION" | "PRE_ORDER" | "PRIZE_DRAW" | "DIGITAL_CODE" | "BUNDLE" | "GROUP" | "CATEGORY" | "BRAND" | "SUBLISTING" | "STORE" | "BLOG" | "EVENT" | "SHIPMENT" | "CATALOGUE" | "USER" | "SELLER" | "ADMIN" | "CART" | "CHECKOUT" | "NAV" | "MEDIA" | "SUPPORT" | "LOTTERY" | "TESTER";
33
33
  /** Confirmation modal config — when set, <Button action={...}> opens
34
34
  * a confirm dialog before firing the actual handler. */
35
35
  export interface ActionConfirmation {
@@ -172,9 +172,17 @@ export const ACTIONS = {
172
172
  iconKey: "message",
173
173
  id: "product.make-offer",
174
174
  label: "Make an offer",
175
- description: "Propose a price to the seller for a classified listing.",
175
+ /*
176
+ * Scope corrected 2026-08-31: this was `["classified"]`, but the button it
177
+ * labels (`MakeOfferButton`) mounts on every type whose capability says
178
+ * `canMakeOffer` — which is standard, art and stickers as well. On
179
+ * classified specifically it is the ONLY purchase path, and a seller who
180
+ * has not opted into haggling receives a request to buy at the asking
181
+ * price rather than a lower offer.
182
+ */
183
+ description: "Propose a price to the seller, or request to buy at the asking price.",
176
184
  kind: "secondary",
177
- listingTypeScope: ["classified"],
185
+ listingTypeScope: ["standard", "classified", "art", "stickers"],
178
186
  },
179
187
  },
180
188
  AUCTION: {
@@ -271,16 +279,15 @@ export const ACTIONS = {
271
279
  listingTypeScope: ["prize-draw"],
272
280
  },
273
281
  },
274
- CLASSIFIED: {
275
- "contact-seller": {
276
- iconKey: "message",
277
- id: "classified.contact-seller",
278
- label: "Contact seller",
279
- description: "Open a conversations thread with the seller — classified flow (SB-UNI-M).",
280
- kind: "primary",
281
- listingTypeScope: ["classified"],
282
- },
283
- },
282
+ /*
283
+ * `CLASSIFIED` held one entry, "contact-seller", whose description read
284
+ * "Open a conversations thread with the seller". It had ZERO consumers — the
285
+ * button on the classified PDP was hand-written — and the feature it named was
286
+ * deleted 2026-08-31. `PRODUCT["make-offer"]` below is the action that is
287
+ * actually wired (`MakeOfferButton`), and on a classified it is now the only
288
+ * purchase path, so a second bucket duplicating it would be exactly the drift
289
+ * Rule #7 exists to prevent.
290
+ */
284
291
  DIGITAL_CODE: {
285
292
  "claim-code": {
286
293
  iconKey: "confirm",
@@ -291,16 +298,12 @@ export const ACTIONS = {
291
298
  listingTypeScope: ["digital-code"],
292
299
  },
293
300
  },
294
- LIVE: {
295
- "inquire": {
296
- iconKey: "message",
297
- id: "live.inquire",
298
- label: "Inquire",
299
- description: "Open a conversation with the seller about a live-item listing.",
300
- kind: "primary",
301
- listingTypeScope: ["live"],
302
- },
303
- },
301
+ /*
302
+ * `LIVE.inquire` ("Open a conversation with the seller about a live-item
303
+ * listing") went the same way and for the same two reasons: no consumer, and
304
+ * the conversations feature is gone. It was never needed either — a live item
305
+ * has `canAddToCart: true`, so unlike classified it has a real checkout.
306
+ */
304
307
  BUNDLE: {
305
308
  "buy-now": {
306
309
  iconKey: "cart",
@@ -879,6 +882,26 @@ export const ACTIONS = {
879
882
  confirmKind: "danger",
880
883
  },
881
884
  },
885
+ /*
886
+ * The alerts list rendered a bare `<Button variant="ghost">Delete</Button>`
887
+ * with a raw onClick — no ActionDef, so no confirmation, so one misplaced
888
+ * click silently removed an alert with nothing to undo it (Rule #7).
889
+ */
890
+ "delete-analytics-alert": {
891
+ iconKey: "delete",
892
+ id: "store.delete-analytics-alert",
893
+ label: "Delete",
894
+ ariaLabel: "Delete this analytics alert",
895
+ description: "Permanently removes this alert rule. Past notifications are unaffected.",
896
+ kind: "danger",
897
+ permissions: ["seller", "admin"],
898
+ confirmation: {
899
+ title: "Delete this alert?",
900
+ body: "You will stop being notified when this rule matches. Alerts already sent are unaffected. This cannot be undone.",
901
+ confirmLabel: "Delete alert",
902
+ confirmKind: "danger",
903
+ },
904
+ },
882
905
  "cancel-form": {
883
906
  iconKey: "cancel",
884
907
  id: "store.cancel-form",
@@ -1197,6 +1220,30 @@ export const ACTIONS = {
1197
1220
  confirmKind: "danger",
1198
1221
  },
1199
1222
  },
1223
+ /*
1224
+ * A LOT, not the whole shipment.
1225
+ *
1226
+ * The lot row's delete button used `shipment.delete`, so the dialog asked
1227
+ * "Delete this shipment?" and warned about removing every lot — while the
1228
+ * handler deleted one lot. A confirmation that names the wrong object is
1229
+ * worse than none: it is either ignored, or it stops someone doing
1230
+ * something harmless.
1231
+ */
1232
+ "delete-lot": {
1233
+ iconKey: "delete",
1234
+ id: "shipment.delete-lot",
1235
+ label: "Delete",
1236
+ ariaLabel: "Delete this lot and its items",
1237
+ description: "Permanently deletes this lot and every item in it.",
1238
+ kind: "danger",
1239
+ permissions: ["admin"],
1240
+ confirmation: {
1241
+ title: "Delete this lot?",
1242
+ body: "This permanently removes the lot and every item in it. The rest of the shipment is untouched. Items still linked to a product must be unlinked first.",
1243
+ confirmLabel: "Delete lot",
1244
+ confirmKind: "danger",
1245
+ },
1246
+ },
1200
1247
  },
1201
1248
  CATALOGUE: {
1202
1249
  "list-item": {
@@ -1,9 +1,14 @@
1
1
  /**
2
- * Classified listing rule — chat-only, no checkout.
2
+ * Classified listing rule — no cart, no checkout; the offer IS the purchase path.
3
3
  *
4
- * Classified listings (OLX / Facebook Marketplace pattern) surface a
5
- * "Contact Seller" CTA that opens a conversations thread. No cart, no
6
- * payment, no order. SB-UNI-M will wire the full flow.
4
+ * Classified listings (OLX / Facebook Marketplace pattern) never reach cart or
5
+ * order creation. The buyer transacts through Make-an-Offer: the seller accepts,
6
+ * which produces a locked cart line in the offer lane, and checkout proceeds
7
+ * from there like any other accepted offer.
8
+ *
9
+ * A seller who has not set `allowOffers` still receives requests to buy at their
10
+ * asking price — see `resolveOfferBounds` in the offers config. Without that,
11
+ * unchecking one flag would make the listing untransactable.
7
12
  */
8
13
  import type { ListingCheckoutRule } from "./types";
9
14
  export declare const classifiedRule: ListingCheckoutRule;
@@ -1,9 +1,14 @@
1
1
  import { DEFAULT_LISTING_RULE } from "./_defaults";
2
2
  export const classifiedRule = {
3
3
  ...DEFAULT_LISTING_RULE,
4
- orderType: "standard", // placeholder — classified never reaches order creation
4
+ orderType: "standard", // placeholder — a classified reaches order creation only via an accepted offer
5
5
  purchaseable: false,
6
6
  cartEligible: false,
7
- cartIneligibleHint: 'Use "Contact Seller" to arrange a meetup.',
7
+ /*
8
+ * Names the control the page actually has. It read 'Use "Contact Seller" to
9
+ * arrange a meetup' until 2026-08-31, and that button opened a conversations
10
+ * thread which no longer exists.
11
+ */
12
+ cartIneligibleHint: "Make an offer to buy this — classified listings are arranged with the seller.",
8
13
  requiresShippingAddress: false,
9
14
  };
@@ -0,0 +1,14 @@
1
+ /** The fields the matcher reads. Everything is optional but `label`. */
2
+ export interface NavSearchable {
3
+ label: string;
4
+ description?: string;
5
+ keywords?: string[];
6
+ }
7
+ /**
8
+ * How well `item` answers `query`. `0` when it does not.
9
+ *
10
+ * The query is matched whole rather than tokenised: "prize draws" should find
11
+ * Prize Draws, and splitting on spaces would also match anything containing
12
+ * "draws" on its own, which for a two-word query is nearly everything.
13
+ */
14
+ export declare function matchesNavQuery(item: NavSearchable, query: string): number;
@@ -0,0 +1,72 @@
1
+ /*
2
+ * WHY: The sidebar search was `item.label.toLowerCase().includes(q)` — so it
3
+ * could only ever find a screen by the name it already shows you. Typing
4
+ * "refund" found nothing, because the screen is called "Payouts"; typing
5
+ * "postcode" found nothing, because the field is called PIN code; typing
6
+ * "maintenance" found nothing, because the toggle lives inside "Site
7
+ * Settings". A search that only matches what is already on screen is a
8
+ * filter, not a search.
9
+ * WHAT: One matcher over label + description + keywords, shared by the sidebar
10
+ * search and (in W7) the action index.
11
+ *
12
+ * ## Ranking, not just filtering
13
+ *
14
+ * A label hit and a keyword hit are not equally good answers. "orders" should
15
+ * put **Orders** first and "Orders & Finance" (a guide that mentions orders)
16
+ * second — so the matcher returns a SCORE and the caller sorts by it. Without
17
+ * that, alphabetical order decides, and the exact match can land ninth.
18
+ *
19
+ * EXPORTS: matchesNavQuery, type NavSearchable
20
+ *
21
+ * @tag domain:layout
22
+ * @tag layer:shared
23
+ * @tag pattern:none
24
+ * @tag access:isomorphic
25
+ * @tag consumers:useSidebarSearch,action index
26
+ * @tag sideEffects:none
27
+ */
28
+ /** Higher is a better answer. `0` means no match at all. */
29
+ const SCORE = {
30
+ labelExact: 100,
31
+ labelPrefix: 80,
32
+ labelSubstring: 60,
33
+ keywordExact: 50,
34
+ keywordSubstring: 30,
35
+ description: 10,
36
+ };
37
+ /**
38
+ * How well `item` answers `query`. `0` when it does not.
39
+ *
40
+ * The query is matched whole rather than tokenised: "prize draws" should find
41
+ * Prize Draws, and splitting on spaces would also match anything containing
42
+ * "draws" on its own, which for a two-word query is nearly everything.
43
+ */
44
+ export function matchesNavQuery(item, query) {
45
+ const q = query.trim().toLowerCase();
46
+ if (!q)
47
+ return 0;
48
+ const label = item.label.toLowerCase();
49
+ if (label === q)
50
+ return SCORE.labelExact;
51
+ if (label.startsWith(q))
52
+ return SCORE.labelPrefix;
53
+ if (label.includes(q))
54
+ return SCORE.labelSubstring;
55
+ for (const keyword of item.keywords ?? []) {
56
+ const k = keyword.toLowerCase();
57
+ if (k === q)
58
+ return SCORE.keywordExact;
59
+ if (k.includes(q) || q.includes(k))
60
+ return SCORE.keywordSubstring;
61
+ }
62
+ /*
63
+ * The description is matched LAST and scores lowest on purpose: it is a
64
+ * sentence, so it contains common words, and letting it outrank a keyword
65
+ * would mean "shipping" surfaced every screen whose description happens to
66
+ * mention shipping ahead of the one actually called Shipping.
67
+ */
68
+ if (item.description && item.description.toLowerCase().includes(q)) {
69
+ return SCORE.description;
70
+ }
71
+ return 0;
72
+ }
@@ -25,12 +25,48 @@ export interface SidebarNavItem {
25
25
  badge?: number;
26
26
  /**
27
27
  * Stable nav-* slug used as the key in siteSettings.navConfig.
28
- * If absent, item is always visible (no admin toggle, no permission check).
28
+ *
29
+ * 🛑 **Derived from the href, never hand-written** — `navItemId(portal, href)`.
30
+ * A hand-written id drifts from the route it names, and because it is also
31
+ * the `navConfig` key, a drifted id silently un-toggles the item: the admin
32
+ * hides "Payouts", the toggle writes a key nothing reads, and the entry
33
+ * stays.
34
+ *
35
+ * If absent, the item is always visible — no admin toggle and **no
36
+ * permission check**, which is why every admin item having no id meant
37
+ * `requiredPermission` had never once been enforced.
29
38
  */
30
39
  id?: string;
31
40
  /** RBAC permission key — item only shows to users with this permission. */
32
41
  requiredPermission?: string;
42
+ /**
43
+ * One sentence on what this screen is FOR, in the user's words rather than
44
+ * the entity's. "Refund a buyer, or check why a payout is late" finds its
45
+ * screen; "Payouts" only finds itself.
46
+ *
47
+ * Consumed by the sidebar search and, in W7, by the action index.
48
+ */
49
+ description?: string;
50
+ /**
51
+ * Words someone might search for that are not in the label — synonyms
52
+ * ("postcode" for PIN), the old name of a renamed screen, the noun the rest
53
+ * of the industry uses.
54
+ */
55
+ keywords?: string[];
56
+ /** Which dashboard this belongs to. Set by the helper alongside `id`. */
57
+ portal?: NavPortal;
33
58
  }
59
+ /** The three dashboards a sidebar item can belong to. */
60
+ export type NavPortal = "admin" | "store" | "user";
61
+ /**
62
+ * The `navConfig` key for a nav item: `nav-{portal}-{slug-of-href}`.
63
+ *
64
+ * Derived rather than authored so an id cannot disagree with the route it
65
+ * points at. Locale prefixes and dynamic segments are stripped, so
66
+ * `/en/admin/orders` and `/admin/orders` produce the same key — otherwise a
67
+ * localised build would write a second set of toggles nobody can find.
68
+ */
69
+ export declare function navItemId(portal: NavPortal, href: string): string;
34
70
  /** Sidebar group with title + items + default-open state. */
35
71
  export interface SidebarNavGroup {
36
72
  title: string;
@@ -10,4 +10,22 @@
10
10
  * 2. render-prop slots on each section (defined on the section component itself).
11
11
  * 3. Section replacement via AppShell named slots.
12
12
  */
13
- export {};
13
+ /**
14
+ * The `navConfig` key for a nav item: `nav-{portal}-{slug-of-href}`.
15
+ *
16
+ * Derived rather than authored so an id cannot disagree with the route it
17
+ * points at. Locale prefixes and dynamic segments are stripped, so
18
+ * `/en/admin/orders` and `/admin/orders` produce the same key — otherwise a
19
+ * localised build would write a second set of toggles nobody can find.
20
+ */
21
+ export function navItemId(portal, href) {
22
+ const path = href
23
+ .replace(/^https?:\/\/[^/]+/, "")
24
+ .replace(/^\/[a-z]{2}(-[A-Z]{2})?(?=\/)/, "")
25
+ .replace(/[?#].*$/, "")
26
+ .replace(/^\/+|\/+$/g, "")
27
+ .replace(/[^a-zA-Z0-9/-]+/g, "-")
28
+ .replace(/\//g, "-")
29
+ .toLowerCase();
30
+ return `nav-${portal}-${path || "root"}`;
31
+ }
@@ -25,7 +25,7 @@
25
25
  * When those pages are built, change the entry here and all 40 call sites
26
26
  * follow. That is the whole point of the indirection.
27
27
  */
28
- import type { NotificationRelatedType } from "../../../../features/admin/schemas/firestore";
28
+ import type { NotificationRelatedType, NotificationType } from "../../../../features/admin/schemas/firestore";
29
29
  /**
30
30
  * Which portal the recipient reads this in.
31
31
  *
@@ -45,3 +45,11 @@ export type NotificationAudience = "buyer" | "seller" | "admin";
45
45
  * looking at.
46
46
  */
47
47
  export declare function resolveNotificationActionUrl(relatedType: NotificationRelatedType | undefined, relatedId: string | undefined, audience: NotificationAudience): string | undefined;
48
+ /**
49
+ * Which portal each notification type belongs to.
50
+ *
51
+ * `Record<NotificationType, …>`, so a new type cannot compile without an
52
+ * answer — the same discipline `typeToPrefsKey` needed after it silently
53
+ * omitted three types and ignored those users' opt-outs.
54
+ */
55
+ export declare const TYPE_AUDIENCE: Record<NotificationType, NotificationAudience>;
@@ -109,3 +109,50 @@ export function resolveNotificationActionUrl(relatedType, relatedId, audience) {
109
109
  }
110
110
  }
111
111
  }
112
+ /*
113
+ * Moved here from `features/admin/actions/notification-actions.ts` 2026-08-31.
114
+ * It belongs beside the resolver it feeds, and being module-private in a
115
+ * `"use server"` file meant the SEED could not use it — so seeded notifications
116
+ * carried no `actionUrl` and rendered unclickable, the exact defect the central
117
+ * resolver was built to end.
118
+ */
119
+ /**
120
+ * Which portal each notification type belongs to.
121
+ *
122
+ * `Record<NotificationType, …>`, so a new type cannot compile without an
123
+ * answer — the same discipline `typeToPrefsKey` needed after it silently
124
+ * omitted three types and ignored those users' opt-outs.
125
+ */
126
+ export const TYPE_AUDIENCE = {
127
+ // Buyer-facing: the order lifecycle they are waiting on.
128
+ order_placed: "buyer",
129
+ order_confirmed: "buyer",
130
+ order_shipped: "buyer",
131
+ order_delivered: "buyer",
132
+ order_cancelled: "buyer",
133
+ refund_initiated: "buyer",
134
+ payment_review: "buyer",
135
+ emi_installment_due_soon: "buyer",
136
+ emi_installment_overdue: "buyer",
137
+ prize_won: "buyer",
138
+ prize_reveal_expired: "buyer",
139
+ product_available: "buyer",
140
+ bid_placed: "buyer",
141
+ bid_outbid: "buyer",
142
+ bid_won: "buyer",
143
+ bid_lost: "buyer",
144
+ offer_responded: "buyer",
145
+ offer_counter_accepted: "buyer",
146
+ offer_expired: "buyer",
147
+ review_replied: "buyer",
148
+ catalogue_images_stale: "buyer",
149
+ // Seller-facing.
150
+ auction_ended: "seller", // "your auction closed with no winner"
151
+ offer_received: "seller",
152
+ review_approved: "seller",
153
+ // Account-level, which lives in the user portal for everyone.
154
+ welcome: "buyer",
155
+ account_action: "buyer",
156
+ system: "buyer",
157
+ promotion: "buyer",
158
+ };