@aglyn/plugins-commerce 1.0.0-beta.143

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 (417) hide show
  1. package/LICENSE +201 -0
  2. package/README.md +10 -0
  3. package/package.json +57 -0
  4. package/src/index.d.ts +38 -0
  5. package/src/index.js +38 -0
  6. package/src/index.js.map +1 -0
  7. package/src/lib/components/account.d.ts +31 -0
  8. package/src/lib/components/account.js +645 -0
  9. package/src/lib/components/account.js.map +1 -0
  10. package/src/lib/components/cart.d.ts +38 -0
  11. package/src/lib/components/cart.js +851 -0
  12. package/src/lib/components/cart.js.map +1 -0
  13. package/src/lib/components/commerce-console-page.d.ts +32 -0
  14. package/src/lib/components/commerce-console-page.js +296 -0
  15. package/src/lib/components/commerce-console-page.js.map +1 -0
  16. package/src/lib/components/commerce-console-sections.d.ts +34 -0
  17. package/src/lib/components/commerce-console-sections.js +62 -0
  18. package/src/lib/components/commerce-console-sections.js.map +1 -0
  19. package/src/lib/components/console/catalog-organization-card.component.d.ts +14 -0
  20. package/src/lib/components/console/catalog-organization-card.component.js +1087 -0
  21. package/src/lib/components/console/catalog-organization-card.component.js.map +1 -0
  22. package/src/lib/components/console/commerce-analytics-card.component.d.ts +27 -0
  23. package/src/lib/components/console/commerce-analytics-card.component.js +310 -0
  24. package/src/lib/components/console/commerce-analytics-card.component.js.map +1 -0
  25. package/src/lib/components/console/commerce-glance-card.component.d.ts +20 -0
  26. package/src/lib/components/console/commerce-glance-card.component.js +340 -0
  27. package/src/lib/components/console/commerce-glance-card.component.js.map +1 -0
  28. package/src/lib/components/console/commerce-stat-tile.component.d.ts +37 -0
  29. package/src/lib/components/console/commerce-stat-tile.component.js +72 -0
  30. package/src/lib/components/console/commerce-stat-tile.component.js.map +1 -0
  31. package/src/lib/components/console/discounts-card.component.d.ts +14 -0
  32. package/src/lib/components/console/discounts-card.component.js +443 -0
  33. package/src/lib/components/console/discounts-card.component.js.map +1 -0
  34. package/src/lib/components/console/entitlement-gate.component.d.ts +76 -0
  35. package/src/lib/components/console/entitlement-gate.component.js +115 -0
  36. package/src/lib/components/console/entitlement-gate.component.js.map +1 -0
  37. package/src/lib/components/console/gift-cards-card.component.d.ts +29 -0
  38. package/src/lib/components/console/gift-cards-card.component.js +379 -0
  39. package/src/lib/components/console/gift-cards-card.component.js.map +1 -0
  40. package/src/lib/components/console/host-coupons-card.component.d.ts +14 -0
  41. package/src/lib/components/console/host-coupons-card.component.js +252 -0
  42. package/src/lib/components/console/host-coupons-card.component.js.map +1 -0
  43. package/src/lib/components/console/host-orders-card.component.d.ts +13 -0
  44. package/src/lib/components/console/host-orders-card.component.js +861 -0
  45. package/src/lib/components/console/host-orders-card.component.js.map +1 -0
  46. package/src/lib/components/console/locations-card.component.d.ts +14 -0
  47. package/src/lib/components/console/locations-card.component.js +256 -0
  48. package/src/lib/components/console/locations-card.component.js.map +1 -0
  49. package/src/lib/components/console/member-posts-card.component.d.ts +8 -0
  50. package/src/lib/components/console/member-posts-card.component.js +283 -0
  51. package/src/lib/components/console/member-posts-card.component.js.map +1 -0
  52. package/src/lib/components/console/newest-site-users-card.component.d.ts +36 -0
  53. package/src/lib/components/console/newest-site-users-card.component.js +126 -0
  54. package/src/lib/components/console/newest-site-users-card.component.js.map +1 -0
  55. package/src/lib/components/console/order-detail-dialog.component.d.ts +28 -0
  56. package/src/lib/components/console/order-detail-dialog.component.js +976 -0
  57. package/src/lib/components/console/order-detail-dialog.component.js.map +1 -0
  58. package/src/lib/components/console/paid-media.d.ts +127 -0
  59. package/src/lib/components/console/paid-media.js +397 -0
  60. package/src/lib/components/console/paid-media.js.map +1 -0
  61. package/src/lib/components/console/payments-settings-card.component.d.ts +13 -0
  62. package/src/lib/components/console/payments-settings-card.component.js +295 -0
  63. package/src/lib/components/console/payments-settings-card.component.js.map +1 -0
  64. package/src/lib/components/console/pos-page.component.d.ts +13 -0
  65. package/src/lib/components/console/pos-page.component.js +916 -0
  66. package/src/lib/components/console/pos-page.component.js.map +1 -0
  67. package/src/lib/components/console/product-editor-dialog.component.d.ts +32 -0
  68. package/src/lib/components/console/product-editor-dialog.component.js +1374 -0
  69. package/src/lib/components/console/product-editor-dialog.component.js.map +1 -0
  70. package/src/lib/components/console/products-hub-card.component.d.ts +16 -0
  71. package/src/lib/components/console/products-hub-card.component.js +1280 -0
  72. package/src/lib/components/console/products-hub-card.component.js.map +1 -0
  73. package/src/lib/components/console/products-hub-zone.component.d.ts +50 -0
  74. package/src/lib/components/console/products-hub-zone.component.js +200 -0
  75. package/src/lib/components/console/products-hub-zone.component.js.map +1 -0
  76. package/src/lib/components/console/recovery-queue-card.component.d.ts +39 -0
  77. package/src/lib/components/console/recovery-queue-card.component.js +262 -0
  78. package/src/lib/components/console/recovery-queue-card.component.js.map +1 -0
  79. package/src/lib/components/console/registers-card.component.d.ts +21 -0
  80. package/src/lib/components/console/registers-card.component.js +296 -0
  81. package/src/lib/components/console/registers-card.component.js.map +1 -0
  82. package/src/lib/components/console/reservations-card.component.d.ts +14 -0
  83. package/src/lib/components/console/reservations-card.component.js +650 -0
  84. package/src/lib/components/console/reservations-card.component.js.map +1 -0
  85. package/src/lib/components/console/reviews-moderation-card.component.d.ts +8 -0
  86. package/src/lib/components/console/reviews-moderation-card.component.js +235 -0
  87. package/src/lib/components/console/reviews-moderation-card.component.js.map +1 -0
  88. package/src/lib/components/console/shipping-settings-card.component.d.ts +38 -0
  89. package/src/lib/components/console/shipping-settings-card.component.js +560 -0
  90. package/src/lib/components/console/shipping-settings-card.component.js.map +1 -0
  91. package/src/lib/components/console/stock-movements-card.component.d.ts +31 -0
  92. package/src/lib/components/console/stock-movements-card.component.js +333 -0
  93. package/src/lib/components/console/stock-movements-card.component.js.map +1 -0
  94. package/src/lib/components/console/store-settings-card.component.d.ts +14 -0
  95. package/src/lib/components/console/store-settings-card.component.js +300 -0
  96. package/src/lib/components/console/store-settings-card.component.js.map +1 -0
  97. package/src/lib/components/console/storefront-tax-summary-card.component.d.ts +73 -0
  98. package/src/lib/components/console/storefront-tax-summary-card.component.js +408 -0
  99. package/src/lib/components/console/storefront-tax-summary-card.component.js.map +1 -0
  100. package/src/lib/components/console/suppliers-card.component.d.ts +8 -0
  101. package/src/lib/components/console/suppliers-card.component.js +328 -0
  102. package/src/lib/components/console/suppliers-card.component.js.map +1 -0
  103. package/src/lib/components/console/tax-settings-card.component.d.ts +14 -0
  104. package/src/lib/components/console/tax-settings-card.component.js +473 -0
  105. package/src/lib/components/console/tax-settings-card.component.js.map +1 -0
  106. package/src/lib/components/gate.d.ts +39 -0
  107. package/src/lib/components/gate.js +202 -0
  108. package/src/lib/components/gate.js.map +1 -0
  109. package/src/lib/components/gated-video.d.ts +40 -0
  110. package/src/lib/components/gated-video.js +366 -0
  111. package/src/lib/components/gated-video.js.map +1 -0
  112. package/src/lib/components/member-feed.d.ts +32 -0
  113. package/src/lib/components/member-feed.js +198 -0
  114. package/src/lib/components/member-feed.js.map +1 -0
  115. package/src/lib/components/member-recovery.d.ts +35 -0
  116. package/src/lib/components/member-recovery.js +313 -0
  117. package/src/lib/components/member-recovery.js.map +1 -0
  118. package/src/lib/components/member-signin.d.ts +35 -0
  119. package/src/lib/components/member-signin.js +257 -0
  120. package/src/lib/components/member-signin.js.map +1 -0
  121. package/src/lib/components/member-signup.d.ts +34 -0
  122. package/src/lib/components/member-signup.js +287 -0
  123. package/src/lib/components/member-signup.js.map +1 -0
  124. package/src/lib/components/newsletter-signup.d.ts +39 -0
  125. package/src/lib/components/newsletter-signup.js +229 -0
  126. package/src/lib/components/newsletter-signup.js.map +1 -0
  127. package/src/lib/components/product-detail.d.ts +38 -0
  128. package/src/lib/components/product-detail.js +1022 -0
  129. package/src/lib/components/product-detail.js.map +1 -0
  130. package/src/lib/components/product-grid.d.ts +67 -0
  131. package/src/lib/components/product-grid.js +909 -0
  132. package/src/lib/components/product-grid.js.map +1 -0
  133. package/src/lib/components/product-reviews.d.ts +32 -0
  134. package/src/lib/components/product-reviews.js +349 -0
  135. package/src/lib/components/product-reviews.js.map +1 -0
  136. package/src/lib/components/related-products.d.ts +33 -0
  137. package/src/lib/components/related-products.js +232 -0
  138. package/src/lib/components/related-products.js.map +1 -0
  139. package/src/lib/components/reservation-widget.d.ts +33 -0
  140. package/src/lib/components/reservation-widget.js +418 -0
  141. package/src/lib/components/reservation-widget.js.map +1 -0
  142. package/src/lib/components/storefront-payment-element-fallback.d.ts +18 -0
  143. package/src/lib/components/storefront-payment-element-fallback.js +51 -0
  144. package/src/lib/components/storefront-payment-element-fallback.js.map +1 -0
  145. package/src/lib/components/storefront-payment-element.d.ts +78 -0
  146. package/src/lib/components/storefront-payment-element.js +156 -0
  147. package/src/lib/components/storefront-payment-element.js.map +1 -0
  148. package/src/lib/components/wishlist.d.ts +46 -0
  149. package/src/lib/components/wishlist.js +304 -0
  150. package/src/lib/components/wishlist.js.map +1 -0
  151. package/src/lib/constants/bundle-common.d.ts +18 -0
  152. package/src/lib/constants/bundle-common.js +18 -0
  153. package/src/lib/constants/bundle-common.js.map +1 -0
  154. package/src/lib/constants/product-filters.d.ts +35 -0
  155. package/src/lib/constants/product-filters.js +109 -0
  156. package/src/lib/constants/product-filters.js.map +1 -0
  157. package/src/lib/model/commerce-cart.d.ts +52 -0
  158. package/src/lib/model/commerce-cart.js +102 -0
  159. package/src/lib/model/commerce-cart.js.map +1 -0
  160. package/src/lib/model/commerce-connect-transfer.d.ts +243 -0
  161. package/src/lib/model/commerce-connect-transfer.js +231 -0
  162. package/src/lib/model/commerce-connect-transfer.js.map +1 -0
  163. package/src/lib/model/commerce-discounts.d.ts +164 -0
  164. package/src/lib/model/commerce-discounts.js +231 -0
  165. package/src/lib/model/commerce-discounts.js.map +1 -0
  166. package/src/lib/model/commerce-dispute.d.ts +124 -0
  167. package/src/lib/model/commerce-dispute.js +225 -0
  168. package/src/lib/model/commerce-dispute.js.map +1 -0
  169. package/src/lib/model/commerce-gift-cards.d.ts +107 -0
  170. package/src/lib/model/commerce-gift-cards.js +121 -0
  171. package/src/lib/model/commerce-gift-cards.js.map +1 -0
  172. package/src/lib/model/commerce-io.d.ts +36 -0
  173. package/src/lib/model/commerce-io.js +245 -0
  174. package/src/lib/model/commerce-io.js.map +1 -0
  175. package/src/lib/model/commerce-orders.d.ts +1040 -0
  176. package/src/lib/model/commerce-orders.js +1022 -0
  177. package/src/lib/model/commerce-orders.js.map +1 -0
  178. package/src/lib/model/commerce-promotions.d.ts +188 -0
  179. package/src/lib/model/commerce-promotions.js +199 -0
  180. package/src/lib/model/commerce-promotions.js.map +1 -0
  181. package/src/lib/model/commerce-reservations.d.ts +175 -0
  182. package/src/lib/model/commerce-reservations.js +157 -0
  183. package/src/lib/model/commerce-reservations.js.map +1 -0
  184. package/src/lib/model/commerce-shipping.d.ts +316 -0
  185. package/src/lib/model/commerce-shipping.js +484 -0
  186. package/src/lib/model/commerce-shipping.js.map +1 -0
  187. package/src/lib/model/commerce-stock-holds.d.ts +199 -0
  188. package/src/lib/model/commerce-stock-holds.js +190 -0
  189. package/src/lib/model/commerce-stock-holds.js.map +1 -0
  190. package/src/lib/model/commerce-subscription-status.d.ts +67 -0
  191. package/src/lib/model/commerce-subscription-status.js +76 -0
  192. package/src/lib/model/commerce-subscription-status.js.map +1 -0
  193. package/src/lib/model/commerce-tax-decision.d.ts +222 -0
  194. package/src/lib/model/commerce-tax-decision.js +165 -0
  195. package/src/lib/model/commerce-tax-decision.js.map +1 -0
  196. package/src/lib/model/commerce-tax.d.ts +176 -0
  197. package/src/lib/model/commerce-tax.js +92 -0
  198. package/src/lib/model/commerce-tax.js.map +1 -0
  199. package/src/lib/model/commerce.d.ts +551 -0
  200. package/src/lib/model/commerce.js +739 -0
  201. package/src/lib/model/commerce.js.map +1 -0
  202. package/src/lib/model/index.d.ts +40 -0
  203. package/src/lib/model/index.js +40 -0
  204. package/src/lib/model/index.js.map +1 -0
  205. package/src/lib/model/order-figures.d.ts +48 -0
  206. package/src/lib/model/order-figures.js +74 -0
  207. package/src/lib/model/order-figures.js.map +1 -0
  208. package/src/lib/model/plugin-permissions.d.ts +23 -0
  209. package/src/lib/model/plugin-permissions.js +34 -0
  210. package/src/lib/model/plugin-permissions.js.map +1 -0
  211. package/src/lib/model/purchase-analytics.d.ts +186 -0
  212. package/src/lib/model/purchase-analytics.js +216 -0
  213. package/src/lib/model/purchase-analytics.js.map +1 -0
  214. package/src/lib/plugin-config.d.ts +62 -0
  215. package/src/lib/plugin-config.js +78 -0
  216. package/src/lib/plugin-config.js.map +1 -0
  217. package/src/lib/plugin.d.ts +28 -0
  218. package/src/lib/plugin.js +147 -0
  219. package/src/lib/plugin.js.map +1 -0
  220. package/src/lib/server/billing-webhook.d.ts +26 -0
  221. package/src/lib/server/billing-webhook.js +4011 -0
  222. package/src/lib/server/billing-webhook.js.map +1 -0
  223. package/src/lib/server/cancel-order.d.ts +87 -0
  224. package/src/lib/server/cancel-order.js +368 -0
  225. package/src/lib/server/cancel-order.js.map +1 -0
  226. package/src/lib/server/cart-checkout.d.ts +25 -0
  227. package/src/lib/server/cart-checkout.js +976 -0
  228. package/src/lib/server/cart-checkout.js.map +1 -0
  229. package/src/lib/server/cart-cookie.d.ts +32 -0
  230. package/src/lib/server/cart-cookie.js +77 -0
  231. package/src/lib/server/cart-cookie.js.map +1 -0
  232. package/src/lib/server/cart.d.ts +34 -0
  233. package/src/lib/server/cart.js +181 -0
  234. package/src/lib/server/cart.js.map +1 -0
  235. package/src/lib/server/catalog.d.ts +127 -0
  236. package/src/lib/server/catalog.js +277 -0
  237. package/src/lib/server/catalog.js.map +1 -0
  238. package/src/lib/server/checkout.d.ts +36 -0
  239. package/src/lib/server/checkout.js +915 -0
  240. package/src/lib/server/checkout.js.map +1 -0
  241. package/src/lib/server/connect.d.ts +26 -0
  242. package/src/lib/server/connect.js +238 -0
  243. package/src/lib/server/connect.js.map +1 -0
  244. package/src/lib/server/contact-refund.d.ts +117 -0
  245. package/src/lib/server/contact-refund.js +196 -0
  246. package/src/lib/server/contact-refund.js.map +1 -0
  247. package/src/lib/server/download.d.ts +39 -0
  248. package/src/lib/server/download.js +206 -0
  249. package/src/lib/server/download.js.map +1 -0
  250. package/src/lib/server/draft-order.d.ts +26 -0
  251. package/src/lib/server/draft-order.js +706 -0
  252. package/src/lib/server/draft-order.js.map +1 -0
  253. package/src/lib/server/feed.d.ts +24 -0
  254. package/src/lib/server/feed.js +59 -0
  255. package/src/lib/server/feed.js.map +1 -0
  256. package/src/lib/server/fulfill-order.d.ts +97 -0
  257. package/src/lib/server/fulfill-order.js +235 -0
  258. package/src/lib/server/fulfill-order.js.map +1 -0
  259. package/src/lib/server/gate.d.ts +36 -0
  260. package/src/lib/server/gate.js +112 -0
  261. package/src/lib/server/gate.js.map +1 -0
  262. package/src/lib/server/gift-cards.d.ts +42 -0
  263. package/src/lib/server/gift-cards.js +219 -0
  264. package/src/lib/server/gift-cards.js.map +1 -0
  265. package/src/lib/server/low-stock.d.ts +49 -0
  266. package/src/lib/server/low-stock.js +60 -0
  267. package/src/lib/server/low-stock.js.map +1 -0
  268. package/src/lib/server/manual-tax-rate.d.ts +82 -0
  269. package/src/lib/server/manual-tax-rate.js +113 -0
  270. package/src/lib/server/manual-tax-rate.js.map +1 -0
  271. package/src/lib/server/member-feed.d.ts +24 -0
  272. package/src/lib/server/member-feed.js +72 -0
  273. package/src/lib/server/member-feed.js.map +1 -0
  274. package/src/lib/server/member-name-search.d.ts +37 -0
  275. package/src/lib/server/member-name-search.js +42 -0
  276. package/src/lib/server/member-name-search.js.map +1 -0
  277. package/src/lib/server/member-post.d.ts +23 -0
  278. package/src/lib/server/member-post.js +166 -0
  279. package/src/lib/server/member-post.js.map +1 -0
  280. package/src/lib/server/membership-account.d.ts +37 -0
  281. package/src/lib/server/membership-account.js +148 -0
  282. package/src/lib/server/membership-account.js.map +1 -0
  283. package/src/lib/server/membership-admin-password.d.ts +33 -0
  284. package/src/lib/server/membership-admin-password.js +202 -0
  285. package/src/lib/server/membership-admin-password.js.map +1 -0
  286. package/src/lib/server/membership-content.d.ts +23 -0
  287. package/src/lib/server/membership-content.js +105 -0
  288. package/src/lib/server/membership-content.js.map +1 -0
  289. package/src/lib/server/membership-login.d.ts +19 -0
  290. package/src/lib/server/membership-login.js +137 -0
  291. package/src/lib/server/membership-login.js.map +1 -0
  292. package/src/lib/server/membership-logout.d.ts +19 -0
  293. package/src/lib/server/membership-logout.js +35 -0
  294. package/src/lib/server/membership-logout.js.map +1 -0
  295. package/src/lib/server/membership-recover.d.ts +60 -0
  296. package/src/lib/server/membership-recover.js +244 -0
  297. package/src/lib/server/membership-recover.js.map +1 -0
  298. package/src/lib/server/membership-register.d.ts +22 -0
  299. package/src/lib/server/membership-register.js +241 -0
  300. package/src/lib/server/membership-register.js.map +1 -0
  301. package/src/lib/server/membership-reset.d.ts +26 -0
  302. package/src/lib/server/membership-reset.js +88 -0
  303. package/src/lib/server/membership-reset.js.map +1 -0
  304. package/src/lib/server/membership-wishlist.d.ts +23 -0
  305. package/src/lib/server/membership-wishlist.js +89 -0
  306. package/src/lib/server/membership-wishlist.js.map +1 -0
  307. package/src/lib/server/membership.d.ts +96 -0
  308. package/src/lib/server/membership.js +222 -0
  309. package/src/lib/server/membership.js.map +1 -0
  310. package/src/lib/server/native-checkout.d.ts +170 -0
  311. package/src/lib/server/native-checkout.js +193 -0
  312. package/src/lib/server/native-checkout.js.map +1 -0
  313. package/src/lib/server/newsletter.d.ts +23 -0
  314. package/src/lib/server/newsletter.js +323 -0
  315. package/src/lib/server/newsletter.js.map +1 -0
  316. package/src/lib/server/notify-restock.d.ts +22 -0
  317. package/src/lib/server/notify-restock.js +84 -0
  318. package/src/lib/server/notify-restock.js.map +1 -0
  319. package/src/lib/server/order-analytics.d.ts +134 -0
  320. package/src/lib/server/order-analytics.js +263 -0
  321. package/src/lib/server/order-analytics.js.map +1 -0
  322. package/src/lib/server/order-figures.d.ts +33 -0
  323. package/src/lib/server/order-figures.js +220 -0
  324. package/src/lib/server/order-figures.js.map +1 -0
  325. package/src/lib/server/paid-media-delivery.d.ts +173 -0
  326. package/src/lib/server/paid-media-delivery.js +212 -0
  327. package/src/lib/server/paid-media-delivery.js.map +1 -0
  328. package/src/lib/server/pos-order.d.ts +54 -0
  329. package/src/lib/server/pos-order.js +1137 -0
  330. package/src/lib/server/pos-order.js.map +1 -0
  331. package/src/lib/server/process-abandoned.d.ts +54 -0
  332. package/src/lib/server/process-abandoned.js +222 -0
  333. package/src/lib/server/process-abandoned.js.map +1 -0
  334. package/src/lib/server/process-restock.d.ts +42 -0
  335. package/src/lib/server/process-restock.js +219 -0
  336. package/src/lib/server/process-restock.js.map +1 -0
  337. package/src/lib/server/product-card.d.ts +29 -0
  338. package/src/lib/server/product-card.js +54 -0
  339. package/src/lib/server/product-card.js.map +1 -0
  340. package/src/lib/server/product.d.ts +70 -0
  341. package/src/lib/server/product.js +105 -0
  342. package/src/lib/server/product.js.map +1 -0
  343. package/src/lib/server/promotion-hold.d.ts +144 -0
  344. package/src/lib/server/promotion-hold.js +174 -0
  345. package/src/lib/server/promotion-hold.js.map +1 -0
  346. package/src/lib/server/reconcile-stock.d.ts +106 -0
  347. package/src/lib/server/reconcile-stock.js +349 -0
  348. package/src/lib/server/reconcile-stock.js.map +1 -0
  349. package/src/lib/server/refund.d.ts +45 -0
  350. package/src/lib/server/refund.js +607 -0
  351. package/src/lib/server/refund.js.map +1 -0
  352. package/src/lib/server/related.d.ts +24 -0
  353. package/src/lib/server/related.js +104 -0
  354. package/src/lib/server/related.js.map +1 -0
  355. package/src/lib/server/reservation-availability.d.ts +23 -0
  356. package/src/lib/server/reservation-availability.js +111 -0
  357. package/src/lib/server/reservation-availability.js.map +1 -0
  358. package/src/lib/server/reserve-stock.d.ts +156 -0
  359. package/src/lib/server/reserve-stock.js +146 -0
  360. package/src/lib/server/reserve-stock.js.map +1 -0
  361. package/src/lib/server/reserve.d.ts +25 -0
  362. package/src/lib/server/reserve.js +426 -0
  363. package/src/lib/server/reserve.js.map +1 -0
  364. package/src/lib/server/restock-flag.d.ts +202 -0
  365. package/src/lib/server/restock-flag.js +449 -0
  366. package/src/lib/server/restock-flag.js.map +1 -0
  367. package/src/lib/server/reviews.d.ts +51 -0
  368. package/src/lib/server/reviews.js +132 -0
  369. package/src/lib/server/reviews.js.map +1 -0
  370. package/src/lib/server/site-page-enricher.d.ts +42 -0
  371. package/src/lib/server/site-page-enricher.js +149 -0
  372. package/src/lib/server/site-page-enricher.js.map +1 -0
  373. package/src/lib/server/site-page-resolver.d.ts +26 -0
  374. package/src/lib/server/site-page-resolver.js +223 -0
  375. package/src/lib/server/site-page-resolver.js.map +1 -0
  376. package/src/lib/server/stock-hold.d.ts +127 -0
  377. package/src/lib/server/stock-hold.js +258 -0
  378. package/src/lib/server/stock-hold.js.map +1 -0
  379. package/src/lib/server/storefront-tax-record.d.ts +22 -0
  380. package/src/lib/server/storefront-tax-record.js +218 -0
  381. package/src/lib/server/storefront-tax-record.js.map +1 -0
  382. package/src/lib/server/storefront-tax.d.ts +197 -0
  383. package/src/lib/server/storefront-tax.js +245 -0
  384. package/src/lib/server/storefront-tax.js.map +1 -0
  385. package/src/lib/server/stream.d.ts +25 -0
  386. package/src/lib/server/stream.js +191 -0
  387. package/src/lib/server/stream.js.map +1 -0
  388. package/src/lib/server/subscription-portal.d.ts +24 -0
  389. package/src/lib/server/subscription-portal.js +91 -0
  390. package/src/lib/server/subscription-portal.js.map +1 -0
  391. package/src/lib/server/supplier-outbox.d.ts +190 -0
  392. package/src/lib/server/supplier-outbox.js +342 -0
  393. package/src/lib/server/supplier-outbox.js.map +1 -0
  394. package/src/lib/server/supplier-update.d.ts +23 -0
  395. package/src/lib/server/supplier-update.js +289 -0
  396. package/src/lib/server/supplier-update.js.map +1 -0
  397. package/src/lib/server/tax-profile.d.ts +29 -0
  398. package/src/lib/server/tax-profile.js +40 -0
  399. package/src/lib/server/tax-profile.js.map +1 -0
  400. package/src/lib/server.d.ts +32 -0
  401. package/src/lib/server.js +311 -0
  402. package/src/lib/server.js.map +1 -0
  403. package/src/lib/site.d.ts +27 -0
  404. package/src/lib/site.js +134 -0
  405. package/src/lib/site.js.map +1 -0
  406. package/src/lib/utils/escape-html.d.ts +41 -0
  407. package/src/lib/utils/escape-html.js +41 -0
  408. package/src/lib/utils/escape-html.js.map +1 -0
  409. package/src/lib/utils/generate-preset-id.d.ts +19 -0
  410. package/src/lib/utils/generate-preset-id.js +25 -0
  411. package/src/lib/utils/generate-preset-id.js.map +1 -0
  412. package/src/lib/utils/member-continue.d.ts +45 -0
  413. package/src/lib/utils/member-continue.js +49 -0
  414. package/src/lib/utils/member-continue.js.map +1 -0
  415. package/src/lib/utils/use-storefront-purchase-event.d.ts +60 -0
  416. package/src/lib/utils/use-storefront-purchase-event.js +142 -0
  417. package/src/lib/utils/use-storefront-purchase-event.js.map +1 -0
@@ -0,0 +1,739 @@
1
+ import { _ as _extends } from "@swc/helpers/_/_extends";
2
+ /**
3
+ * @license
4
+ * Copyright 2026 Aglyn LLC
5
+ *
6
+ * Licensed under the Apache License, Version 2.0 (the "License");
7
+ * you may not use this file except in compliance with the License.
8
+ * You may obtain a copy of the License at
9
+ *
10
+ * http://www.apache.org/licenses/LICENSE-2.0
11
+ *
12
+ * Unless required by applicable law or agreed to in writing, software
13
+ * distributed under the License is distributed on an "AS IS" BASIS,
14
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15
+ * See the License for the specific language governing permissions and
16
+ * limitations under the License.
17
+ */ import { nameSearchFields } from "@aglyn/aglyn/app-utils/name-search";
18
+ /**
19
+ * Commerce catalog v1 (AGL-276): products with options/variants,
20
+ * hierarchical categories, tags, and manual/smart collections. Pure
21
+ * model + helpers — no I/O; the products hub and storefront APIs operate
22
+ * over these shapes. Documents live under `hosts/{hostId}/products`,
23
+ * `.../productCategories`, and `.../collections`; the legacy Commerce
24
+ * Starter product doc (AGL-90: name/priceUsd/inventory) lifts into this
25
+ * shape via `liftLegacyProduct`, so existing docs keep working.
26
+ */ /*
27
+ * THERE IS NO STOREFRONT FEE CONSTANT, and that absence is load-bearing
28
+ * (AGL-2295).
29
+ *
30
+ * `COMMERCE_PLATFORM_FEE_PERCENT = 2` lived here with ZERO call sites. It
31
+ * asserted a flat 2% that agrees with the plan table for exactly one cell
32
+ * (Starter, physical) and disagrees with the other fifteen — Starter digital
33
+ * is 5%, Pro digital 3%, Business 2%, Scale 1%, and every physical rate above
34
+ * Starter is 0%. Nothing was wrong while nothing read it; the cost was that
35
+ * the next reader wiring it up would silently re-price every plan, and a
36
+ * constant sitting in the model beside the types reads like the answer.
37
+ *
38
+ * The single source is `resolveTransactionFeePct(org, productType)` in
39
+ * `plan-entitlements.ts`, resolved PER REQUEST from the org — because it
40
+ * depends on the plan, on per-org staff overrides, and on whether the
41
+ * subscription is still alive. A constant cannot express any of that.
42
+ * `commerce-fee-single-source.spec.ts` fails the build if one comes back.
43
+ */ /** Product price ceiling (whole USD). */ export const COMMERCE_MAX_PRICE_USD = 10000;
44
+ /**
45
+ * The register ids within the plan's `posRegisters` cap (AGL-482), ranked
46
+ * by creation order — the same ordering `pos-order.ts` enforces at sale
47
+ * time. Registers beyond the cap (e.g. after a Business→Pro downgrade) are
48
+ * excluded so the console/POS can dim or hide them instead of surfacing a
49
+ * checkout 403. `cap` of `Infinity` returns all.
50
+ */ export function registersWithinCap(registers, cap) {
51
+ const createdMs = (r)=>{
52
+ var _ref, _ref1;
53
+ var _r_createdAt_toMillis, _r_createdAt, _r_createdAt1;
54
+ return (_ref = (_ref1 = (_r_createdAt = r.createdAt) == null ? void 0 : (_r_createdAt_toMillis = _r_createdAt.toMillis) == null ? void 0 : _r_createdAt_toMillis.call(_r_createdAt)) != null ? _ref1 : (_r_createdAt1 = r.createdAt) == null ? void 0 : _r_createdAt1.seconds) != null ? _ref : 0;
55
+ };
56
+ const ranked = [
57
+ ...registers
58
+ ].sort((a, b)=>createdMs(a) - createdMs(b) || a.$id.localeCompare(b.$id));
59
+ return new Set(ranked.slice(0, Math.max(0, cap)).map((r)=>r.$id));
60
+ }
61
+ /** Variant ceiling per product (Shopify parity). */ export const COMMERCE_MAX_VARIANTS = 100;
62
+ export const COMMERCE_MAX_OPTIONS = 3;
63
+ export const COMMERCE_MAX_OPTION_VALUES = 25;
64
+ export const COMMERCE_SLUG_MAX_LENGTH = 80;
65
+ /** Lowercase-kebab slug from a product/category/collection name. */ export function commerceSlug(name) {
66
+ return String(name != null ? name : '').normalize('NFKD').replace(/[̀-ͯ]/g, '').toLowerCase().replace(/[^a-z0-9]+/g, '-').replace(/^-+|-+$/g, '').slice(0, COMMERCE_SLUG_MAX_LENGTH);
67
+ }
68
+ /**
69
+ * The search keys a product write carries, so the catalog can be searched by
70
+ * the QUERY rather than by the rows a listener happened to fetch (AGL-2501).
71
+ *
72
+ * The hub lists `limit(500)`, and the search compared what that returned — so
73
+ * a product past the window answered "no products match", which reads as the
74
+ * product not existing rather than as the search not reaching it. Filtering
75
+ * server-side needs fields Firestore can index, and neither of the two things
76
+ * a merchant searches by is one:
77
+ *
78
+ * - A NAME needs case-insensitive contains, which Firestore has no operator
79
+ * for. `nameSearchFields` denormalizes it into the three shapes that are
80
+ * indexable — an exact key, word-prefix tokens for `array-contains`, and
81
+ * the key reversed so "ends with" becomes a prefix range.
82
+ * - A SKU lives inside `variants`, an array of OBJECTS, and Firestore cannot
83
+ * query a field inside one. Flattened here into a top-level array so a SKU
84
+ * is one `array-contains`.
85
+ *
86
+ * ⛔ A SKU therefore matches WHOLE, not as a substring: "abc-123" finds it and
87
+ * "123" does not. That is the right way round for a SKU, which is a value
88
+ * somebody copies rather than half-remembers — unlike a name, where the tokens
89
+ * above buy word-prefix matching precisely because names are half-remembered.
90
+ *
91
+ * `barcodes` is the same flattening for the same reason, and it is the one the
92
+ * register depends on: a keyboard-wedge scanner types the code and presses
93
+ * Enter, so the lookup has to be exact and has to reach the whole catalog. A
94
+ * scan is never a half-remembered value.
95
+ *
96
+ * Lower-cased because the translator lower-cases the typed query before it
97
+ * builds the `array-contains`; stored and typed have to be normalized the same
98
+ * way or the two silently disagree.
99
+ *
100
+ * ⚠️ Each array is OMITTED when a product has none, rather than written as
101
+ * `[]`. `isNotEmpty` is served as `!= null`, and an empty array is not null —
102
+ * so a product with no SKUs at all would answer "has a SKU" for every row.
103
+ *
104
+ * ⚠️ Spread this at EVERY write that sets a product's name or variants. A
105
+ * write that sets the name without it leaves the keys describing the previous
106
+ * name, and the product becomes findable only by what it used to be called.
107
+ */ export function productSearchFields(product) {
108
+ const flatten = (read)=>{
109
+ var _product_variants;
110
+ return [
111
+ ...new Set(((_product_variants = product.variants) != null ? _product_variants : []).map((variant)=>{
112
+ var _read;
113
+ return ((_read = read(variant)) != null ? _read : '').trim().toLowerCase();
114
+ }).filter(Boolean))
115
+ ];
116
+ };
117
+ const skus = flatten((variant)=>variant.sku);
118
+ const barcodes = flatten((variant)=>variant.barcode);
119
+ return _extends({}, nameSearchFields(product.name), skus.length ? {
120
+ skus
121
+ } : {}, barcodes.length ? {
122
+ barcodes
123
+ } : {});
124
+ }
125
+ /**
126
+ * Cartesian product of option values → the variant option combinations
127
+ * the products hub materializes into a variants matrix. Empty/absent
128
+ * options yield a single default combination ({}).
129
+ */ export function expandVariantMatrix(options) {
130
+ const usable = (options != null ? options : []).filter((option)=>{
131
+ var _ref;
132
+ var _option_values;
133
+ return option.name && ((_ref = (_option_values = option.values) == null ? void 0 : _option_values.length) != null ? _ref : 0) > 0;
134
+ });
135
+ if (usable.length === 0) return [
136
+ {}
137
+ ];
138
+ let combos = [
139
+ {}
140
+ ];
141
+ for (const option of usable){
142
+ const next = [];
143
+ for (const combo of combos){
144
+ for (const value of option.values){
145
+ next.push(_extends({}, combo, {
146
+ [option.name]: value
147
+ }));
148
+ }
149
+ }
150
+ combos = next;
151
+ if (combos.length > COMMERCE_MAX_VARIANTS) {
152
+ return combos.slice(0, COMMERCE_MAX_VARIANTS);
153
+ }
154
+ }
155
+ return combos;
156
+ }
157
+ /**
158
+ * The option axes renamed, with every variant's selection carried to the new
159
+ * name in place (AGL-3066).
160
+ *
161
+ * A variant keeps its selections keyed by option NAME, so a rename has to move
162
+ * each key rather than rebuild the matrix: a rebuild matches variants by name
163
+ * and value, finds none under the new name, and replaces every variant with a
164
+ * new id holding the first variant's price and stock and no SKU, barcode,
165
+ * compare-at price or weight. Moving the key keeps the id every order line
166
+ * and stock movement refers to, and every field a person set.
167
+ *
168
+ * `names` holds one entry per option, in order; an entry that is not a string
169
+ * keeps that option's name. Each selection keeps its position among a
170
+ * variant's selections, because a variant is labeled by them in order.
171
+ *
172
+ * Two options may share a name for a moment while a person types. A variant
173
+ * cannot hold two selections under one name, so while the new names are not
174
+ * all different nothing is moved, and `validateProduct` refuses the product.
175
+ * The selection left under the old name is found again by its value once the
176
+ * names differ, so typing through a duplicate loses nothing.
177
+ */ export function renameProductOptions(product, names) {
178
+ var _product_options, _product_variants;
179
+ const current = (_product_options = product.options) != null ? _product_options : [];
180
+ const options = current.map((option, index)=>{
181
+ const name = names[index];
182
+ return typeof name === 'string' ? _extends({}, option, {
183
+ name
184
+ }) : option;
185
+ });
186
+ const next = options.map((option)=>option.name);
187
+ if (new Set(next).size !== next.length) return {
188
+ options,
189
+ variants: product.variants
190
+ };
191
+ const variants = ((_product_variants = product.variants) != null ? _product_variants : []).map((variant)=>{
192
+ const selections = variant.options;
193
+ if (!selections) return variant;
194
+ const axisOf = optionAxesOf(current, selections);
195
+ const moved = {};
196
+ let changed = false;
197
+ for (const [key, value] of Object.entries(selections)){
198
+ const axis = axisOf.get(key);
199
+ const name = axis === undefined ? key : next[axis];
200
+ if (name !== key) changed = true;
201
+ moved[name] = value;
202
+ }
203
+ return changed ? _extends({}, variant, {
204
+ options: moved
205
+ }) : variant;
206
+ });
207
+ return {
208
+ options,
209
+ variants
210
+ };
211
+ }
212
+ /**
213
+ * Which option each of a variant's selections belongs to: the option of the
214
+ * same name first, and then, for a selection under a name no option has any
215
+ * longer, the one remaining option whose values hold its value. A selection
216
+ * that fits neither belongs to no option and is left as it is.
217
+ */ function optionAxesOf(options, selections) {
218
+ const axisOf = new Map();
219
+ const taken = new Set();
220
+ options.forEach((option, index)=>{
221
+ if (Object.prototype.hasOwnProperty.call(selections, option.name) && !axisOf.has(option.name)) {
222
+ axisOf.set(option.name, index);
223
+ taken.add(index);
224
+ }
225
+ });
226
+ for (const [key, value] of Object.entries(selections)){
227
+ if (axisOf.has(key)) continue;
228
+ const axis = options.findIndex((option, index)=>{
229
+ var _option_values;
230
+ return !taken.has(index) && ((_option_values = option.values) != null ? _option_values : []).includes(value);
231
+ });
232
+ if (axis === -1) continue;
233
+ axisOf.set(key, axis);
234
+ taken.add(axis);
235
+ }
236
+ return axisOf;
237
+ }
238
+ /**
239
+ * Whether a variant has a price a sale can charge (AGL-2916).
240
+ *
241
+ * A product proposed by AI is created with every price left empty for the
242
+ * merchant to set, so a stored variant can lack one. `Number(undefined)` is
243
+ * no price, and neither is `null`, which `Number` reads as zero: a sale door
244
+ * that priced either would charge nothing, or fail at the processor.
245
+ */ export function variantHasPrice(variant) {
246
+ const price = variant == null ? void 0 : variant.priceUsd;
247
+ return typeof price === 'number' && Number.isFinite(price) && price >= 0;
248
+ }
249
+ /** Whether any variant of a product still needs its price set (AGL-2916). */ export function productPriceMissing(product) {
250
+ var _product_variants;
251
+ return ((_product_variants = product.variants) != null ? _product_variants : []).some((variant)=>!variantHasPrice(variant));
252
+ }
253
+ /**
254
+ * The fields proposed copy changes on a product (AGL-2916), in the shape the
255
+ * editor stores them: only the fields `values` names. Tags and categories are
256
+ * each kept once; the search listing keeps its share image; and option names
257
+ * rename the product's options through `renameProductOptions`, keeping every
258
+ * variant, only when they name each option once with a name of its own.
259
+ */ export function productCopyPatch(product, values) {
260
+ var _product_options;
261
+ var _values_optionNames;
262
+ const patch = {};
263
+ if (typeof values.description === 'string') patch.description = values.description;
264
+ if (Array.isArray(values.tags)) {
265
+ patch.tags = [
266
+ ...new Set(values.tags.map((tag)=>tag.trim()).filter(Boolean))
267
+ ];
268
+ }
269
+ if (Array.isArray(values.categoryIds)) {
270
+ patch.categoryIds = [
271
+ ...new Set(values.categoryIds.filter(Boolean))
272
+ ];
273
+ }
274
+ if (typeof values.seoTitle === 'string' || typeof values.seoDescription === 'string') {
275
+ patch.seo = _extends({}, product.seo, typeof values.seoTitle === 'string' ? {
276
+ title: values.seoTitle
277
+ } : {}, typeof values.seoDescription === 'string' ? {
278
+ description: values.seoDescription
279
+ } : {});
280
+ }
281
+ const options = (_product_options = product.options) != null ? _product_options : [];
282
+ const names = (_values_optionNames = values.optionNames) == null ? void 0 : _values_optionNames.map((name)=>name.trim());
283
+ if (names && options.length > 0 && names.length === options.length && names.every(Boolean) && new Set(names).size === names.length && names.some((name, index)=>name !== options[index].name)) {
284
+ Object.assign(patch, renameProductOptions(product, names));
285
+ }
286
+ return patch;
287
+ }
288
+ /**
289
+ * The document a proposed product is created as (AGL-2916): a `draft`, under
290
+ * a slug no product in `takenSlugs` has, with one variant for each
291
+ * combination of its options and NO price on any of them. Prices are the
292
+ * merchant's to set: the editor refuses to save the product until every
293
+ * variant has one, and no sale door sells a variant without one
294
+ * (`variantHasPrice`). The search keys travel with the name, as on every
295
+ * create path.
296
+ */ export function unpricedProductDraft(proposal, takenSlugs, nowMs) {
297
+ const name = proposal.name.trim().slice(0, 120);
298
+ const base = commerceSlug(name) || 'product';
299
+ let slug = base;
300
+ for(let suffix = 2; takenSlugs.has(slug); suffix += 1)slug = `${base}-${suffix}`;
301
+ const seen = new Set();
302
+ const options = proposal.options.map((option)=>({
303
+ name: option.name.trim(),
304
+ values: [
305
+ ...new Set(option.values.map((value)=>value.trim()).filter(Boolean))
306
+ ].slice(0, COMMERCE_MAX_OPTION_VALUES)
307
+ })).filter((option)=>{
308
+ if (!option.name || !option.values.length || seen.has(option.name)) return false;
309
+ seen.add(option.name);
310
+ return true;
311
+ }).slice(0, COMMERCE_MAX_OPTIONS);
312
+ const variants = options.length ? expandVariantMatrix(options).map((combo, index)=>({
313
+ id: `v${nowMs.toString(36)}${index}`,
314
+ options: combo
315
+ })) : [
316
+ {
317
+ id: 'default'
318
+ }
319
+ ];
320
+ const seoTitle = proposal.seoTitle.trim();
321
+ const seoDescription = proposal.seoDescription.trim();
322
+ return _extends({}, productSearchFields({
323
+ name
324
+ }), {
325
+ slug,
326
+ type: proposal.type,
327
+ status: 'draft',
328
+ description: proposal.description,
329
+ tags: [
330
+ ...new Set(proposal.tags.map((tag)=>tag.trim()).filter(Boolean))
331
+ ]
332
+ }, options.length ? {
333
+ options
334
+ } : {}, {
335
+ variants
336
+ }, seoTitle || seoDescription ? {
337
+ seo: _extends({}, seoTitle ? {
338
+ title: seoTitle
339
+ } : {}, seoDescription ? {
340
+ description: seoDescription
341
+ } : {})
342
+ } : {}, {
343
+ createdAtMs: nowMs,
344
+ updatedAtMs: nowMs
345
+ });
346
+ }
347
+ /** Variant whose option selections match exactly; undefined if none. */ export function findVariant(product, selections) {
348
+ var _product_variants;
349
+ return (_product_variants = product.variants) == null ? void 0 : _product_variants.find((variant)=>{
350
+ var _variant_options;
351
+ const options = (_variant_options = variant.options) != null ? _variant_options : {};
352
+ const keys = new Set([
353
+ ...Object.keys(options),
354
+ ...Object.keys(selections)
355
+ ]);
356
+ for (const key of keys){
357
+ if (options[key] !== selections[key]) return false;
358
+ }
359
+ return true;
360
+ });
361
+ }
362
+ /** [min, max] price across variants; [0, 0] when there are none. */ export function productPriceRange(product) {
363
+ var _product_variants;
364
+ const prices = ((_product_variants = product.variants) != null ? _product_variants : []).map((variant)=>Number(variant.priceUsd)).filter((price)=>Number.isFinite(price) && price >= 0);
365
+ if (prices.length === 0) return [
366
+ 0,
367
+ 0
368
+ ];
369
+ return [
370
+ Math.min(...prices),
371
+ Math.max(...prices)
372
+ ];
373
+ }
374
+ /** Sum of tracked inventory; null when every variant is untracked. */ export function productInventory(product) {
375
+ var _product_variants;
376
+ let total = null;
377
+ for (const variant of (_product_variants = product.variants) != null ? _product_variants : []){
378
+ if (variant.inventory == null) continue;
379
+ total = (total != null ? total : 0) + Number(variant.inventory);
380
+ }
381
+ return total;
382
+ }
383
+ /**
384
+ * Whether `quantity` of a variant is purchasable (AGL-281): untracked
385
+ * stock always is; tracked stock honors the product's oversell policy.
386
+ */ export function canPurchase(product, variantId, quantity = 1) {
387
+ var _product_variants, _product_variants1;
388
+ const variant = variantId ? (_product_variants = product.variants) == null ? void 0 : _product_variants.find((item)=>item.id === variantId) : (_product_variants1 = product.variants) == null ? void 0 : _product_variants1[0];
389
+ if (!variant) return false;
390
+ if (variant.inventory == null) return true;
391
+ if (product.oversellPolicy === 'backorder') return true;
392
+ return Number(variant.inventory) >= quantity;
393
+ }
394
+ export function stockShortfall(product, variantId, quantity = 1) {
395
+ var _product_variants, _product_variants1;
396
+ if (canPurchase(product, variantId, quantity)) return null;
397
+ const variant = variantId ? (_product_variants = product.variants) == null ? void 0 : _product_variants.find((item)=>item.id === variantId) : (_product_variants1 = product.variants) == null ? void 0 : _product_variants1[0];
398
+ // `canPurchase` answers false for a variant that does not exist at all. That
399
+ // is not a stock shortfall and must not be reported as "0 in stock" — the
400
+ // register's own line builder falls back to `variants[0]`, so the case is
401
+ // unreachable from the counter, and inventing a count for it would be the
402
+ // one failure mode this feature must not have.
403
+ if (!variant || variant.inventory == null) return null;
404
+ return {
405
+ available: Math.max(0, Math.round(Number(variant.inventory) || 0))
406
+ };
407
+ }
408
+ /**
409
+ * Whether stock tracking MEANS anything on a product (AGL-1744).
410
+ *
411
+ * `canPurchase` above gates every checkout on stock, subscription sessions
412
+ * included, but nothing ever decrements for a subscription — not on the
413
+ * initial charge (the `commerce-subscription` webhook branch deliberately
414
+ * writes no order and touches no inventory, AGL-1732) and not on renewal
415
+ * (`invoice.payment_succeeded` is unhandled repo-wide, AGL-1743). So on a
416
+ * subscription-only product that gate is permanently satisfied: one unit of
417
+ * stock sells an unlimited number of subscriptions, and the count never
418
+ * moves however many boxes ship. The merchant set a number, the system
419
+ * checks it on every sale, and the number is never true.
420
+ *
421
+ * AGL-1750 resolved the half AGL-1744 had to leave open: every paid invoice
422
+ * of a PHYSICAL subscription now mints an order and decrements its variant's
423
+ * stock (the `invoice.paid` branch of the commerce webhook), opening cycle
424
+ * included. So the honest split is now three-way:
425
+ *
426
+ * - `subscriptionOptional` ("Both") products have a real one-time path —
427
+ * the cart only ever builds `mode: 'payment'` sessions, and buy-now with
428
+ * `billing: 'once'` records a plain order — and that path decrements
429
+ * honestly. Withdrawing stock tracking there would delete a working
430
+ * control and re-open the AGL-1711 oversell on the half that works.
431
+ * - a PHYSICAL subscription box consumes a unit every cycle, and since
432
+ * AGL-1750 the cycle's own order decrements it — the count moves as the
433
+ * boxes ship, so the number the merchant sets is kept true again.
434
+ * - a DIGITAL or SERVICE subscription-only product still has no
435
+ * decrementing path anywhere, so the field stays withdrawn there: one
436
+ * unit would still sell unlimited subscriptions.
437
+ *
438
+ * This says nothing about what `canPurchase` returns — that is the gate for
439
+ * every other purchase path and is deliberately untouched. This is a console
440
+ * predicate: it stops the editor inviting a merchant to set a number the
441
+ * system will never keep true.
442
+ */ export function stockTrackingApplies(product) {
443
+ return !product.subscription || product.subscriptionOptional === true || product.type === 'physical';
444
+ }
445
+ /**
446
+ * Resolves the Stripe Checkout mode for a product + the buyer's
447
+ * requested billing choice (AGL-545). The product doc is authoritative:
448
+ * - no `subscription` → always one-time (the request field is ignored)
449
+ * - `subscription` without `subscriptionOptional` → always subscription
450
+ * (a forged `billing: 'once'` cannot buy a subscription product once)
451
+ * - `subscriptionOptional` → the buyer chooses; absent/invalid choices
452
+ * default to one-time, matching the PDP default.
453
+ */ export function resolveCheckoutBillingMode(product, requested) {
454
+ if (!product.subscription) return 'payment';
455
+ if (!product.subscriptionOptional) return 'subscription';
456
+ return requested === 'subscribe' ? 'subscription' : 'payment';
457
+ }
458
+ /**
459
+ * Applies a stock delta to one variant, flooring at zero (race-window
460
+ * sales can't drive the display negative), and returns the new variants
461
+ * array — callers persist it plus the `productInventory` denormalization.
462
+ * With `locationId`, the delta lands in that location's bucket and the
463
+ * flat `inventory` re-sums across locations (AGL-286).
464
+ */ export function adjustVariantInventory(product, variantId, delta, locationId) {
465
+ var _product_variants;
466
+ return ((_product_variants = product.variants) != null ? _product_variants : []).map((variant)=>{
467
+ if (variant.id !== variantId || variant.inventory == null) return variant;
468
+ if (locationId && variant.inventoryByLocation) {
469
+ var _variant_inventoryByLocation_locationId;
470
+ const buckets = _extends({}, variant.inventoryByLocation, {
471
+ [locationId]: Math.max(0, Number((_variant_inventoryByLocation_locationId = variant.inventoryByLocation[locationId]) != null ? _variant_inventoryByLocation_locationId : 0) + delta)
472
+ });
473
+ return _extends({}, variant, {
474
+ inventoryByLocation: buckets,
475
+ inventory: Object.values(buckets).reduce((sum, count)=>sum + Number(count), 0)
476
+ });
477
+ }
478
+ return _extends({}, variant, {
479
+ inventory: Math.max(0, Number(variant.inventory) + delta)
480
+ });
481
+ });
482
+ }
483
+ /**
484
+ * What `adjustVariantInventory` will ACTUALLY move the count by (AGL-2149).
485
+ *
486
+ * The floor in that helper is not a rounding detail, it is a silent absorber. A
487
+ * backorder product (`oversellPolicy: 'backorder'`, which `canPurchase` admits
488
+ * at any stock level) sitting at 0 sells 3: `Math.max(0, 0 + -3)` is 0, so the
489
+ * count does not move — correctly, since inventory is a shelf count and shelves
490
+ * do not go negative — but the ledger row said `-3` and every reversal read it
491
+ * as three units to put back. Cancelling that order handed the merchant 3 units
492
+ * that never existed and a stock badge that offers them for sale.
493
+ *
494
+ * Removing the floor is not the alternative: every reader of `inventory` — the
495
+ * badges, `canPurchase`, `productInventory`, `isLowStock` — assumes it cannot
496
+ * go negative, and a negative count would be a far wider change than the bug.
497
+ * So the clamp stays and the amount it absorbed is recorded instead.
498
+ *
499
+ * Deliberately mirrors `adjustVariantInventory`'s own arithmetic, including
500
+ * which field the clamp applies to in the location-tracked case, so the two
501
+ * cannot disagree about what happened.
502
+ */ export function appliedVariantInventoryDelta(product, variantId, delta, locationId) {
503
+ var _product_variants;
504
+ const variant = ((_product_variants = product.variants) != null ? _product_variants : []).find((item)=>item.id === variantId);
505
+ if (!variant || variant.inventory == null) return 0;
506
+ if (locationId && variant.inventoryByLocation) {
507
+ var _variant_inventoryByLocation_locationId;
508
+ const before = Number((_variant_inventoryByLocation_locationId = variant.inventoryByLocation[locationId]) != null ? _variant_inventoryByLocation_locationId : 0);
509
+ return Math.max(0, before + delta) - before;
510
+ }
511
+ const before = Number(variant.inventory);
512
+ return Math.max(0, before + delta) - before;
513
+ }
514
+ /**
515
+ * Moves stock between two locations of a tracked variant (AGL-286).
516
+ * Quantity clamps to what the source location holds; the flat total is
517
+ * unchanged by construction.
518
+ */ export function transferVariantInventory(product, variantId, fromLocationId, toLocationId, quantity) {
519
+ var _product_variants;
520
+ return ((_product_variants = product.variants) != null ? _product_variants : []).map((variant)=>{
521
+ var _variant_inventoryByLocation, _buckets_fromLocationId, _buckets_toLocationId;
522
+ if (variant.id !== variantId || variant.inventory == null) return variant;
523
+ const buckets = _extends({}, (_variant_inventoryByLocation = variant.inventoryByLocation) != null ? _variant_inventoryByLocation : {});
524
+ const available = Math.max(0, Number((_buckets_fromLocationId = buckets[fromLocationId]) != null ? _buckets_fromLocationId : 0));
525
+ const moved = Math.min(available, Math.max(0, Math.round(quantity)));
526
+ if (moved === 0) return variant;
527
+ buckets[fromLocationId] = available - moved;
528
+ buckets[toLocationId] = Math.max(0, Number((_buckets_toLocationId = buckets[toLocationId]) != null ? _buckets_toLocationId : 0)) + moved;
529
+ return _extends({}, variant, {
530
+ inventoryByLocation: buckets
531
+ });
532
+ });
533
+ }
534
+ /** True when tracked stock is at/below the product's alert threshold. */ export function isLowStock(product) {
535
+ const threshold = product.lowStockThreshold;
536
+ if (threshold == null || !(threshold >= 0)) return false;
537
+ const total = productInventory(product);
538
+ return total != null && total <= threshold;
539
+ }
540
+ function ruleMatches(product, rule) {
541
+ const value = rule.value;
542
+ switch(rule.field){
543
+ case 'tag':
544
+ {
545
+ var _product_tags;
546
+ const tags = (_product_tags = product.tags) != null ? _product_tags : [];
547
+ const has = tags.includes(String(value));
548
+ return rule.op === 'neq' ? !has : has;
549
+ }
550
+ case 'categoryId':
551
+ {
552
+ var _product_categoryIds;
553
+ const ids = (_product_categoryIds = product.categoryIds) != null ? _product_categoryIds : [];
554
+ const has = ids.includes(String(value));
555
+ return rule.op === 'neq' ? !has : has;
556
+ }
557
+ case 'priceUsd':
558
+ {
559
+ const [min, max] = productPriceRange(product);
560
+ const numeric = Number(value);
561
+ if (!Number.isFinite(numeric)) return false;
562
+ if (rule.op === 'lt') return min < numeric;
563
+ if (rule.op === 'gt') return max > numeric;
564
+ if (rule.op === 'neq') return min !== numeric || max !== numeric;
565
+ return min <= numeric && numeric <= max;
566
+ }
567
+ case 'name':
568
+ {
569
+ var _product_name;
570
+ const name = ((_product_name = product.name) != null ? _product_name : '').toLowerCase();
571
+ const needle = String(value).toLowerCase();
572
+ if (rule.op === 'contains') return name.includes(needle);
573
+ if (rule.op === 'neq') return name !== needle;
574
+ return name === needle;
575
+ }
576
+ case 'type':
577
+ {
578
+ const matches = product.type === value;
579
+ return rule.op === 'neq' ? !matches : matches;
580
+ }
581
+ default:
582
+ return false;
583
+ }
584
+ }
585
+ /**
586
+ * Smart-collection membership: draft/archived/deleted products never
587
+ * match; manual collections answer from productIds.
588
+ */ export function matchesCollection(product, collection, productId) {
589
+ var _collection_rules;
590
+ if (product.deletedAt || product.status !== 'active') return false;
591
+ if (collection.mode === 'manual') {
592
+ var _collection_productIds;
593
+ return productId != null && ((_collection_productIds = collection.productIds) != null ? _collection_productIds : []).includes(productId);
594
+ }
595
+ const rules = (_collection_rules = collection.rules) != null ? _collection_rules : [];
596
+ if (rules.length === 0) return false;
597
+ const matcher = (rule)=>ruleMatches(product, rule);
598
+ return collection.matchAll === false ? rules.some(matcher) : rules.every(matcher);
599
+ }
600
+ /**
601
+ * Lifts a legacy Commerce Starter doc (AGL-90: flat name/priceUsd/
602
+ * inventory/imageUrl) into the catalog shape with a single default
603
+ * variant. Already-lifted docs pass through unchanged.
604
+ */ export function liftLegacyProduct(raw) {
605
+ var _raw_priceUsd, _raw_name, _raw_name1, _raw_type, _raw_status, _raw_inventory;
606
+ if (Array.isArray(raw.variants) && raw.variants.length > 0) {
607
+ return raw;
608
+ }
609
+ const priceUsd = Number((_raw_priceUsd = raw.priceUsd) != null ? _raw_priceUsd : 0);
610
+ return _extends({}, raw, {
611
+ name: (_raw_name = raw.name) != null ? _raw_name : 'Product',
612
+ slug: raw.slug || commerceSlug((_raw_name1 = raw.name) != null ? _raw_name1 : 'product'),
613
+ type: (_raw_type = raw.type) != null ? _raw_type : 'physical',
614
+ status: (_raw_status = raw.status) != null ? _raw_status : 'active',
615
+ variants: [
616
+ {
617
+ id: 'default',
618
+ priceUsd: Number.isFinite(priceUsd) ? priceUsd : 0,
619
+ inventory: (_raw_inventory = raw.inventory) != null ? _raw_inventory : null
620
+ }
621
+ ]
622
+ });
623
+ }
624
+ /** Actionable error, or null when the product is storable. */ export function validateProduct(product) {
625
+ var _product_options, _product_variants;
626
+ var _product_name;
627
+ if (!((_product_name = product.name) == null ? void 0 : _product_name.trim())) return 'Product name is required';
628
+ if (!product.slug || product.slug !== commerceSlug(product.slug)) {
629
+ return 'Slug must be lowercase letters, numbers, and dashes';
630
+ }
631
+ if (![
632
+ 'physical',
633
+ 'digital',
634
+ 'service'
635
+ ].includes(product.type)) {
636
+ return 'Unknown product type';
637
+ }
638
+ if (![
639
+ 'draft',
640
+ 'active',
641
+ 'archived'
642
+ ].includes(product.status)) {
643
+ return 'Unknown product status';
644
+ }
645
+ const options = (_product_options = product.options) != null ? _product_options : [];
646
+ if (options.length > COMMERCE_MAX_OPTIONS) {
647
+ return `At most ${COMMERCE_MAX_OPTIONS} options per product`;
648
+ }
649
+ for (const option of options){
650
+ var _ref;
651
+ var _option_name, _option_values;
652
+ if (!((_option_name = option.name) == null ? void 0 : _option_name.trim())) return 'Option names are required';
653
+ if (((_ref = (_option_values = option.values) == null ? void 0 : _option_values.length) != null ? _ref : 0) === 0) {
654
+ return `Option "${option.name}" needs at least one value`;
655
+ }
656
+ if (option.values.length > COMMERCE_MAX_OPTION_VALUES) {
657
+ return `Option "${option.name}" has too many values`;
658
+ }
659
+ if (new Set(option.values).size !== option.values.length) {
660
+ return `Option "${option.name}" has duplicate values`;
661
+ }
662
+ }
663
+ // A variant keys its selections by option name, so two options with one
664
+ // name cannot both be selected (AGL-3066).
665
+ if (new Set(options.map((option)=>option.name.trim())).size !== options.length) {
666
+ return 'Each option needs its own name';
667
+ }
668
+ const variants = (_product_variants = product.variants) != null ? _product_variants : [];
669
+ if (variants.length === 0) return 'Products need at least one variant';
670
+ if (variants.length > COMMERCE_MAX_VARIANTS) {
671
+ return `At most ${COMMERCE_MAX_VARIANTS} variants per product`;
672
+ }
673
+ const ids = new Set();
674
+ const skus = new Set();
675
+ for (const variant of variants){
676
+ if (!variant.id) return 'Variants need stable ids';
677
+ if (ids.has(variant.id)) return 'Variant ids must be unique';
678
+ ids.add(variant.id);
679
+ if (variant.priceUsd === undefined || variant.priceUsd === null) {
680
+ return 'Set a price for every variant';
681
+ }
682
+ const price = Number(variant.priceUsd);
683
+ if (!Number.isFinite(price) || price < 0) {
684
+ return 'Variant prices must be zero or more';
685
+ }
686
+ if (price > COMMERCE_MAX_PRICE_USD) {
687
+ return `Prices are capped at $${COMMERCE_MAX_PRICE_USD}`;
688
+ }
689
+ if (variant.sku) {
690
+ if (skus.has(variant.sku)) return 'Variant SKUs must be unique';
691
+ skus.add(variant.sku);
692
+ }
693
+ if (variant.compareAtPriceUsd != null && Number(variant.compareAtPriceUsd) <= price) {
694
+ return 'Compare-at price must exceed the price';
695
+ }
696
+ }
697
+ return null;
698
+ }
699
+ /** Actionable error, or null when the collection is storable. */ export function validateCollection(collection) {
700
+ var _collection_name;
701
+ if (!((_collection_name = collection.name) == null ? void 0 : _collection_name.trim())) return 'Collection name is required';
702
+ if (!collection.slug || collection.slug !== commerceSlug(collection.slug)) {
703
+ return 'Slug must be lowercase letters, numbers, and dashes';
704
+ }
705
+ if (collection.mode !== 'manual' && collection.mode !== 'smart') {
706
+ return 'Unknown collection mode';
707
+ }
708
+ if (collection.mode === 'smart') {
709
+ var _collection_rules;
710
+ const rules = (_collection_rules = collection.rules) != null ? _collection_rules : [];
711
+ if (rules.length === 0) return 'Smart collections need at least one rule';
712
+ for (const rule of rules){
713
+ if (![
714
+ 'tag',
715
+ 'categoryId',
716
+ 'priceUsd',
717
+ 'name',
718
+ 'type'
719
+ ].includes(rule.field)) {
720
+ return 'Unknown rule field';
721
+ }
722
+ if (![
723
+ 'eq',
724
+ 'neq',
725
+ 'lt',
726
+ 'gt',
727
+ 'contains'
728
+ ].includes(rule.op)) {
729
+ return 'Unknown rule operator';
730
+ }
731
+ if (rule.value === '' || rule.value == null) {
732
+ return 'Rule values are required';
733
+ }
734
+ }
735
+ }
736
+ return null;
737
+ }
738
+
739
+ //# sourceMappingURL=commerce.js.map