@replohq/sdk 0.1.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 (280) hide show
  1. package/LICENSE +11 -0
  2. package/_vendor/replo-utils/lib/crypto.d.ts +30 -0
  3. package/_vendor/replo-utils/lib/errors.d.ts +83 -0
  4. package/_vendor/replo-utils/lib/json.d.ts +6 -0
  5. package/_vendor/replo-utils/lib/json.mjs +43 -0
  6. package/_vendor/replo-utils/lib/misc.d.ts +145 -0
  7. package/_vendor/replo-utils/lib/object.d.ts +31 -0
  8. package/_vendor/schemas/errors.d.ts +459 -0
  9. package/_vendor/schemas/generated/consent.d.ts +55 -0
  10. package/_vendor/schemas/generated/errors.d.ts +61 -0
  11. package/_vendor/schemas/loaderKeys.d.ts +1 -0
  12. package/_vendor/schemas/loaderKeys.mjs +27 -0
  13. package/_vendor/schemas/money.d.ts +60 -0
  14. package/_vendor/schemas/money.mjs +2051 -0
  15. package/analytics/analytics-provider.d.ts +16 -0
  16. package/analytics/analytics-provider.js +113 -0
  17. package/analytics/analytics-provider.js.map +7 -0
  18. package/analytics/analytics-sink.d.ts +26 -0
  19. package/analytics/analytics-sink.js +1 -0
  20. package/analytics/analytics-sink.js.map +7 -0
  21. package/analytics/get-analytics-sinks.d.ts +27 -0
  22. package/analytics/get-analytics-sinks.js +52 -0
  23. package/analytics/get-analytics-sinks.js.map +7 -0
  24. package/analytics/hooks/use-product-viewed-analytics.d.ts +23 -0
  25. package/analytics/hooks/use-product-viewed-analytics.js +34 -0
  26. package/analytics/hooks/use-product-viewed-analytics.js.map +7 -0
  27. package/analytics/replo-first-party-pixel.d.ts +12 -0
  28. package/analytics/replo-first-party-pixel.js +31 -0
  29. package/analytics/replo-first-party-pixel.js.map +7 -0
  30. package/analytics/replo-pixel-script.d.ts +13 -0
  31. package/analytics/replo-pixel-script.js +30 -0
  32. package/analytics/replo-pixel-script.js.map +7 -0
  33. package/analytics/sinks/ga4-sink.d.ts +15 -0
  34. package/analytics/sinks/ga4-sink.js +60 -0
  35. package/analytics/sinks/ga4-sink.js.map +7 -0
  36. package/analytics/sinks/meta-sink.d.ts +14 -0
  37. package/analytics/sinks/meta-sink.js +56 -0
  38. package/analytics/sinks/meta-sink.js.map +7 -0
  39. package/analytics/sinks/pinterest-sink.d.ts +14 -0
  40. package/analytics/sinks/pinterest-sink.js +76 -0
  41. package/analytics/sinks/pinterest-sink.js.map +7 -0
  42. package/analytics/sinks/reddit-sink.d.ts +14 -0
  43. package/analytics/sinks/reddit-sink.js +80 -0
  44. package/analytics/sinks/reddit-sink.js.map +7 -0
  45. package/analytics/sinks/replo-sink.d.ts +14 -0
  46. package/analytics/sinks/replo-sink.js +57 -0
  47. package/analytics/sinks/replo-sink.js.map +7 -0
  48. package/analytics/sinks/snapchat-sink.d.ts +14 -0
  49. package/analytics/sinks/snapchat-sink.js +67 -0
  50. package/analytics/sinks/snapchat-sink.js.map +7 -0
  51. package/analytics/sinks/tiktok-sink.d.ts +14 -0
  52. package/analytics/sinks/tiktok-sink.js +79 -0
  53. package/analytics/sinks/tiktok-sink.js.map +7 -0
  54. package/analytics/sinks/window-sink.d.ts +18 -0
  55. package/analytics/sinks/window-sink.js +46 -0
  56. package/analytics/sinks/window-sink.js.map +7 -0
  57. package/analytics/utils/analytics-utils.d.ts +7 -0
  58. package/analytics/utils/analytics-utils.js +130 -0
  59. package/analytics/utils/analytics-utils.js.map +7 -0
  60. package/analytics/utils/navigation-tracker.d.ts +16 -0
  61. package/analytics/utils/navigation-tracker.js +44 -0
  62. package/analytics/utils/navigation-tracker.js.map +7 -0
  63. package/analytics/utils/shopify-funnel-gate.d.ts +8 -0
  64. package/analytics/utils/shopify-funnel-gate.js +22 -0
  65. package/analytics/utils/shopify-funnel-gate.js.map +7 -0
  66. package/cart/buy-now-action.d.ts +21 -0
  67. package/cart/buy-now-action.js +104 -0
  68. package/cart/buy-now-action.js.map +7 -0
  69. package/cart/cart-actions.d.ts +63 -0
  70. package/cart/cart-actions.js +90 -0
  71. package/cart/cart-actions.js.map +7 -0
  72. package/cart/cart-loader.d.ts +9 -0
  73. package/cart/cart-loader.js +11 -0
  74. package/cart/cart-loader.js.map +7 -0
  75. package/cart/cart-provider.d.ts +85 -0
  76. package/cart/cart-provider.js +372 -0
  77. package/cart/cart-provider.js.map +7 -0
  78. package/cart/cart-schema.d.ts +74 -0
  79. package/cart/cart-schema.js +69 -0
  80. package/cart/cart-schema.js.map +7 -0
  81. package/cart/cart-types.d.ts +132 -0
  82. package/cart/cart-types.js +8 -0
  83. package/cart/cart-types.js.map +7 -0
  84. package/cart/gateways/cart-constants.d.ts +1 -0
  85. package/cart/gateways/cart-constants.js +5 -0
  86. package/cart/gateways/cart-constants.js.map +7 -0
  87. package/cart/gateways/cart-gateway.d.ts +10 -0
  88. package/cart/gateways/cart-gateway.js +19 -0
  89. package/cart/gateways/cart-gateway.js.map +7 -0
  90. package/cart/gateways/cookie-cart-gateway.d.ts +28 -0
  91. package/cart/gateways/cookie-cart-gateway.js +109 -0
  92. package/cart/gateways/cookie-cart-gateway.js.map +7 -0
  93. package/cart/gateways/default-cart-gateway.d.ts +19 -0
  94. package/cart/gateways/default-cart-gateway.js +30 -0
  95. package/cart/gateways/default-cart-gateway.js.map +7 -0
  96. package/cart/gateways/resolver-cart-gateway.d.ts +2 -0
  97. package/cart/gateways/resolver-cart-gateway.js +109 -0
  98. package/cart/gateways/resolver-cart-gateway.js.map +7 -0
  99. package/cart/gateways/stripe-cart-gateway.d.ts +19 -0
  100. package/cart/gateways/stripe-cart-gateway.js +28 -0
  101. package/cart/gateways/stripe-cart-gateway.js.map +7 -0
  102. package/cart/hooks/use-add-to-cart.d.ts +63 -0
  103. package/cart/hooks/use-add-to-cart.js +124 -0
  104. package/cart/hooks/use-add-to-cart.js.map +7 -0
  105. package/cart/hooks/use-buy-now.d.ts +49 -0
  106. package/cart/hooks/use-buy-now.js +62 -0
  107. package/cart/hooks/use-buy-now.js.map +7 -0
  108. package/cart/utils/cart-utils.d.ts +43 -0
  109. package/cart/utils/cart-utils.js +46 -0
  110. package/cart/utils/cart-utils.js.map +7 -0
  111. package/cart/utils/cookie-cart-persistence.d.ts +55 -0
  112. package/cart/utils/cookie-cart-persistence.js +166 -0
  113. package/cart/utils/cookie-cart-persistence.js.map +7 -0
  114. package/cart/utils/variant-to-cart-line.d.ts +74 -0
  115. package/cart/utils/variant-to-cart-line.js +162 -0
  116. package/cart/utils/variant-to-cart-line.js.map +7 -0
  117. package/chunk-UJCSKKID.mjs +27 -0
  118. package/consent/consent-action.d.ts +9 -0
  119. package/consent/consent-action.js +25 -0
  120. package/consent/consent-action.js.map +7 -0
  121. package/consent/consent-actions.d.ts +28 -0
  122. package/consent/consent-actions.js +36 -0
  123. package/consent/consent-actions.js.map +7 -0
  124. package/consent/consent-store.d.ts +69 -0
  125. package/consent/consent-store.js +194 -0
  126. package/consent/consent-store.js.map +7 -0
  127. package/consent/cookie.d.ts +36 -0
  128. package/consent/cookie.js +82 -0
  129. package/consent/cookie.js.map +7 -0
  130. package/consent/replo-scripts.d.ts +23 -0
  131. package/consent/replo-scripts.js +102 -0
  132. package/consent/replo-scripts.js.map +7 -0
  133. package/consent/script-registration-store.d.ts +25 -0
  134. package/consent/script-registration-store.js +61 -0
  135. package/consent/script-registration-store.js.map +7 -0
  136. package/consent/script-snippets.d.ts +24 -0
  137. package/consent/script-snippets.js +122 -0
  138. package/consent/script-snippets.js.map +7 -0
  139. package/consent/types.d.ts +34 -0
  140. package/consent/types.js +1 -0
  141. package/consent/types.js.map +7 -0
  142. package/consent/window-api.d.ts +41 -0
  143. package/consent/window-api.js +73 -0
  144. package/consent/window-api.js.map +7 -0
  145. package/env.d.ts +9 -0
  146. package/env.js +42 -0
  147. package/env.js.map +7 -0
  148. package/gateways/canopy-api.d.ts +83 -0
  149. package/gateways/canopy-api.js +197 -0
  150. package/gateways/canopy-api.js.map +7 -0
  151. package/hooks/use-client-value.d.ts +10 -0
  152. package/hooks/use-client-value.js +12 -0
  153. package/hooks/use-client-value.js.map +7 -0
  154. package/hooks/use-formatted-price.d.ts +15 -0
  155. package/hooks/use-formatted-price.js +20 -0
  156. package/hooks/use-formatted-price.js.map +7 -0
  157. package/lib/canopy-error.d.ts +25 -0
  158. package/lib/canopy-error.js +24 -0
  159. package/lib/canopy-error.js.map +7 -0
  160. package/lib/get-query-client.d.ts +2 -0
  161. package/lib/get-query-client.js +34 -0
  162. package/lib/get-query-client.js.map +7 -0
  163. package/lib/integration-utils.d.ts +2 -0
  164. package/lib/integration-utils.js +9 -0
  165. package/lib/integration-utils.js.map +7 -0
  166. package/lib/shopify-utils.d.ts +10 -0
  167. package/lib/shopify-utils.js +7 -0
  168. package/lib/shopify-utils.js.map +7 -0
  169. package/lib/url-utils.d.ts +4 -0
  170. package/lib/url-utils.js +8 -0
  171. package/lib/url-utils.js.map +7 -0
  172. package/loaders/collection-loader.d.ts +11 -0
  173. package/loaders/collection-loader.js +55 -0
  174. package/loaders/collection-loader.js.map +7 -0
  175. package/loaders/collection-products-loader.d.ts +12 -0
  176. package/loaders/collection-products-loader.js +58 -0
  177. package/loaders/collection-products-loader.js.map +7 -0
  178. package/loaders/contentful-entries-loader.d.ts +17 -0
  179. package/loaders/contentful-entries-loader.js +78 -0
  180. package/loaders/contentful-entries-loader.js.map +7 -0
  181. package/loaders/contentful-entry-loader.d.ts +14 -0
  182. package/loaders/contentful-entry-loader.js +60 -0
  183. package/loaders/contentful-entry-loader.js.map +7 -0
  184. package/loaders/invoke-loader-action.d.ts +11 -0
  185. package/loaders/invoke-loader-action.js +14 -0
  186. package/loaders/invoke-loader-action.js.map +7 -0
  187. package/loaders/invoke-loader-server.d.ts +18 -0
  188. package/loaders/invoke-loader-server.js +40 -0
  189. package/loaders/invoke-loader-server.js.map +7 -0
  190. package/loaders/invoke-loader.d.ts +16 -0
  191. package/loaders/invoke-loader.js +37 -0
  192. package/loaders/invoke-loader.js.map +7 -0
  193. package/loaders/levanta-product-loader.d.ts +11 -0
  194. package/loaders/levanta-product-loader.js +53 -0
  195. package/loaders/levanta-product-loader.js.map +7 -0
  196. package/loaders/loader-error-boundary.d.ts +25 -0
  197. package/loaders/loader-error-boundary.js +24 -0
  198. package/loaders/loader-error-boundary.js.map +7 -0
  199. package/loaders/loader-keys.d.ts +34 -0
  200. package/loaders/loader-keys.js +26 -0
  201. package/loaders/loader-keys.js.map +7 -0
  202. package/loaders/loader-schemas.d.ts +946 -0
  203. package/loaders/loader-schemas.js +353 -0
  204. package/loaders/loader-schemas.js.map +7 -0
  205. package/loaders/metaobject-loader.d.ts +12 -0
  206. package/loaders/metaobject-loader.js +54 -0
  207. package/loaders/metaobject-loader.js.map +7 -0
  208. package/loaders/metaobjects-loader.d.ts +14 -0
  209. package/loaders/metaobjects-loader.js +60 -0
  210. package/loaders/metaobjects-loader.js.map +7 -0
  211. package/loaders/okendo-review-aggregate-loader.d.ts +17 -0
  212. package/loaders/okendo-review-aggregate-loader.js +56 -0
  213. package/loaders/okendo-review-aggregate-loader.js.map +7 -0
  214. package/loaders/okendo-reviews-loader.d.ts +23 -0
  215. package/loaders/okendo-reviews-loader.js +54 -0
  216. package/loaders/okendo-reviews-loader.js.map +7 -0
  217. package/loaders/prefetch-loaders.d.ts +33 -0
  218. package/loaders/prefetch-loaders.js +46 -0
  219. package/loaders/prefetch-loaders.js.map +7 -0
  220. package/loaders/preview-placeholder.d.ts +25 -0
  221. package/loaders/preview-placeholder.js +222 -0
  222. package/loaders/preview-placeholder.js.map +7 -0
  223. package/loaders/product-loader-args.d.ts +21 -0
  224. package/loaders/product-loader-args.js +17 -0
  225. package/loaders/product-loader-args.js.map +7 -0
  226. package/loaders/product-loader.d.ts +10 -0
  227. package/loaders/product-loader.js +52 -0
  228. package/loaders/product-loader.js.map +7 -0
  229. package/loaders/rebuy-recommendations-loader.d.ts +165 -0
  230. package/loaders/rebuy-recommendations-loader.js +57 -0
  231. package/loaders/rebuy-recommendations-loader.js.map +7 -0
  232. package/loaders/reviews-io-review-aggregate-loader.d.ts +12 -0
  233. package/loaders/reviews-io-review-aggregate-loader.js +43 -0
  234. package/loaders/reviews-io-review-aggregate-loader.js.map +7 -0
  235. package/loaders/reviews-io-reviews-loader.d.ts +14 -0
  236. package/loaders/reviews-io-reviews-loader.js +65 -0
  237. package/loaders/reviews-io-reviews-loader.js.map +7 -0
  238. package/loaders/smile-earning-rules-loader.d.ts +19 -0
  239. package/loaders/smile-earning-rules-loader.js +44 -0
  240. package/loaders/smile-earning-rules-loader.js.map +7 -0
  241. package/loaders/smile-rewards-loader.d.ts +19 -0
  242. package/loaders/smile-rewards-loader.js +44 -0
  243. package/loaders/smile-rewards-loader.js.map +7 -0
  244. package/loaders/smile-vip-tiers-loader.d.ts +18 -0
  245. package/loaders/smile-vip-tiers-loader.js +43 -0
  246. package/loaders/smile-vip-tiers-loader.js.map +7 -0
  247. package/loaders/statsig-experiment-loader.d.ts +20 -0
  248. package/loaders/statsig-experiment-loader.js +81 -0
  249. package/loaders/statsig-experiment-loader.js.map +7 -0
  250. package/loaders/yotpo-review-aggregate-loader.d.ts +12 -0
  251. package/loaders/yotpo-review-aggregate-loader.js +50 -0
  252. package/loaders/yotpo-review-aggregate-loader.js.map +7 -0
  253. package/loaders/yotpo-reviews-loader.d.ts +14 -0
  254. package/loaders/yotpo-reviews-loader.js +65 -0
  255. package/loaders/yotpo-reviews-loader.js.map +7 -0
  256. package/money.d.ts +9 -0
  257. package/money.js +13 -0
  258. package/money.js.map +7 -0
  259. package/next/config.d.ts +4 -0
  260. package/next/config.js +91 -0
  261. package/next/config.js.map +7 -0
  262. package/next/image-loader.d.ts +2 -0
  263. package/next/image-loader.js +52 -0
  264. package/next/image-loader.js.map +7 -0
  265. package/next/open-next.d.ts +2 -0
  266. package/next/open-next.js +24 -0
  267. package/next/open-next.js.map +7 -0
  268. package/orders/order-status-schema.d.ts +161 -0
  269. package/orders/order-status-schema.js +83 -0
  270. package/orders/order-status-schema.js.map +7 -0
  271. package/orders/order-status.d.ts +11 -0
  272. package/orders/order-status.js +41 -0
  273. package/orders/order-status.js.map +7 -0
  274. package/package.json +216 -0
  275. package/providers/query-provider.d.ts +1 -0
  276. package/providers/query-provider.js +12 -0
  277. package/providers/query-provider.js.map +7 -0
  278. package/providers/replo-provider.d.ts +1 -0
  279. package/providers/replo-provider.js +22 -0
  280. package/providers/replo-provider.js.map +7 -0
@@ -0,0 +1,130 @@
1
+ function createEventQueue(checkPixelReady, sendEvent, pixelName) {
2
+ const queue = [];
3
+ let flushTimer = null;
4
+ let timeoutTimer = null;
5
+ let permanentlyDisabled = false;
6
+ const cleanup = () => {
7
+ if (flushTimer !== null) {
8
+ window.clearInterval(flushTimer);
9
+ flushTimer = null;
10
+ }
11
+ if (timeoutTimer !== null) {
12
+ window.clearTimeout(timeoutTimer);
13
+ timeoutTimer = null;
14
+ }
15
+ };
16
+ const flush = () => {
17
+ if (!checkPixelReady()) {
18
+ return;
19
+ }
20
+ console.debug(
21
+ `[analytics] flushing ${queue.length} queued events for ${pixelName}`
22
+ );
23
+ try {
24
+ queue.forEach(({ event, params }) => sendEvent(event, params));
25
+ } finally {
26
+ queue.length = 0;
27
+ cleanup();
28
+ }
29
+ };
30
+ const scheduleFlush = () => {
31
+ if (typeof window === "undefined" || flushTimer !== null) {
32
+ return;
33
+ }
34
+ flushTimer = window.setInterval(flush, 500);
35
+ timeoutTimer = window.setTimeout(() => {
36
+ queue.length = 0;
37
+ permanentlyDisabled = true;
38
+ console.debug(
39
+ `Analytics queue timed out after 30 seconds for ${pixelName}`
40
+ );
41
+ cleanup();
42
+ }, 3e4);
43
+ };
44
+ return (event, params = {}) => {
45
+ if (permanentlyDisabled) {
46
+ console.debug(
47
+ `[analytics] ${pixelName} queue is disabled, dropping event`,
48
+ event
49
+ );
50
+ return;
51
+ }
52
+ if (checkPixelReady()) {
53
+ sendEvent(event, params);
54
+ } else {
55
+ queue.push({ event, params });
56
+ scheduleFlush();
57
+ }
58
+ };
59
+ }
60
+ function createMethodQueue(checkInstanceReady, options) {
61
+ const queue = [];
62
+ let flushTimer = null;
63
+ let timeoutTimer = null;
64
+ let permanentlyDisabled = false;
65
+ const queueName = options?.queueName ?? "method queue";
66
+ const cleanup = () => {
67
+ if (flushTimer !== null) {
68
+ window.clearInterval(flushTimer);
69
+ flushTimer = null;
70
+ }
71
+ if (timeoutTimer !== null) {
72
+ window.clearTimeout(timeoutTimer);
73
+ timeoutTimer = null;
74
+ }
75
+ };
76
+ const flush = () => {
77
+ const instance = checkInstanceReady();
78
+ if (!instance) {
79
+ return;
80
+ }
81
+ try {
82
+ queue.forEach(({ method, args }) => {
83
+ const methodFunction = instance[method];
84
+ if (typeof methodFunction === "function") {
85
+ void methodFunction.apply(instance, args);
86
+ }
87
+ });
88
+ } finally {
89
+ queue.length = 0;
90
+ cleanup();
91
+ }
92
+ };
93
+ const scheduleFlush = () => {
94
+ if (typeof window === "undefined" || flushTimer !== null) {
95
+ return;
96
+ }
97
+ flushTimer = window.setInterval(flush, 500);
98
+ timeoutTimer = window.setTimeout(() => {
99
+ queue.length = 0;
100
+ permanentlyDisabled = true;
101
+ if (typeof window !== "undefined") {
102
+ console.debug(
103
+ `[analytics] ${queueName} timed out after 30 seconds and has been disabled`
104
+ );
105
+ }
106
+ options?.onTimeout?.();
107
+ cleanup();
108
+ }, 3e4);
109
+ };
110
+ return (method, ...args) => {
111
+ if (permanentlyDisabled) {
112
+ return;
113
+ }
114
+ const instance = checkInstanceReady();
115
+ if (instance) {
116
+ const methodFunction = instance[method];
117
+ if (typeof methodFunction === "function") {
118
+ void methodFunction.apply(instance, args);
119
+ }
120
+ } else {
121
+ queue.push({ method, args });
122
+ scheduleFlush();
123
+ }
124
+ };
125
+ }
126
+ export {
127
+ createEventQueue,
128
+ createMethodQueue
129
+ };
130
+ //# sourceMappingURL=analytics-utils.js.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../../analytics/utils/analytics-utils.ts"],
4
+ "sourcesContent": ["// oxlint-disable-next-line typescript/no-explicit-any -- legacy any, may or may not be needed\ntype QueuedEvent = { event: string; params: Record<string, any> };\n\nexport function createEventQueue(\n checkPixelReady: () => boolean,\n // oxlint-disable-next-line typescript/no-explicit-any -- legacy any, may or may not be needed\n sendEvent: (event: string, params: Record<string, any>) => void,\n pixelName: string,\n // oxlint-disable-next-line typescript/no-explicit-any -- legacy any, may or may not be needed\n): (event: string, params?: Record<string, any>) => void {\n const queue: QueuedEvent[] = [];\n let flushTimer: number | null = null;\n let timeoutTimer: number | null = null;\n let permanentlyDisabled = false;\n\n const cleanup = () => {\n if (flushTimer !== null) {\n window.clearInterval(flushTimer);\n flushTimer = null;\n }\n if (timeoutTimer !== null) {\n window.clearTimeout(timeoutTimer);\n timeoutTimer = null;\n }\n };\n\n const flush = () => {\n if (!checkPixelReady()) {\n return;\n }\n console.debug(\n `[analytics] flushing ${queue.length} queued events for ${pixelName}`,\n );\n try {\n queue.forEach(({ event, params }) => sendEvent(event, params));\n } finally {\n queue.length = 0;\n cleanup();\n }\n };\n\n const scheduleFlush = () => {\n if (typeof window === \"undefined\" || flushTimer !== null) {\n return;\n }\n\n flushTimer = window.setInterval(flush, 500);\n timeoutTimer = window.setTimeout(() => {\n queue.length = 0;\n permanentlyDisabled = true;\n console.debug(\n `Analytics queue timed out after 30 seconds for ${pixelName}`,\n );\n cleanup();\n }, 30_000);\n };\n\n // oxlint-disable-next-line typescript/no-explicit-any -- legacy any, may or may not be needed\n return (event: string, params: Record<string, any> = {}) => {\n if (permanentlyDisabled) {\n console.debug(\n `[analytics] ${pixelName} queue is disabled, dropping event`,\n event,\n );\n return;\n }\n\n if (checkPixelReady()) {\n sendEvent(event, params);\n } else {\n queue.push({ event, params });\n scheduleFlush();\n }\n };\n}\n\ntype MethodQueueOptions = {\n queueName?: string;\n onTimeout?: () => void;\n};\n\nexport function createMethodQueue<\n // oxlint-disable-next-line typescript/no-explicit-any -- legacy any, may or may not be needed\n InstanceType extends Record<string, (...args: any[]) => any>,\n>(\n checkInstanceReady: () => InstanceType | null,\n options?: MethodQueueOptions,\n // oxlint-disable-next-line typescript/no-explicit-any -- legacy any, may or may not be needed\n): (method: keyof InstanceType, ...args: any[]) => void {\n // oxlint-disable-next-line typescript/no-explicit-any -- legacy any, may or may not be needed\n const queue: { method: keyof InstanceType; args: any[] }[] = [];\n let flushTimer: number | null = null;\n let timeoutTimer: number | null = null;\n let permanentlyDisabled = false;\n const queueName = options?.queueName ?? \"method queue\";\n\n const cleanup = () => {\n if (flushTimer !== null) {\n window.clearInterval(flushTimer);\n flushTimer = null;\n }\n if (timeoutTimer !== null) {\n window.clearTimeout(timeoutTimer);\n timeoutTimer = null;\n }\n };\n\n const flush = () => {\n const instance = checkInstanceReady();\n if (!instance) {\n return;\n }\n try {\n queue.forEach(({ method, args }) => {\n const methodFunction = instance[method];\n if (typeof methodFunction === \"function\") {\n void methodFunction.apply(instance, args);\n }\n });\n } finally {\n queue.length = 0;\n cleanup();\n }\n };\n\n const scheduleFlush = () => {\n if (typeof window === \"undefined\" || flushTimer !== null) {\n return;\n }\n\n flushTimer = window.setInterval(flush, 500);\n timeoutTimer = window.setTimeout(() => {\n queue.length = 0;\n permanentlyDisabled = true;\n if (typeof window !== \"undefined\") {\n console.debug(\n `[analytics] ${queueName} timed out after 30 seconds and has been disabled`,\n );\n }\n options?.onTimeout?.();\n cleanup();\n }, 30_000);\n };\n\n // oxlint-disable-next-line typescript/no-explicit-any -- legacy any, may or may not be needed\n return (method: keyof InstanceType, ...args: any[]) => {\n if (permanentlyDisabled) {\n return;\n }\n\n const instance = checkInstanceReady();\n if (instance) {\n const methodFunction = instance[method];\n if (typeof methodFunction === \"function\") {\n void methodFunction.apply(instance, args);\n }\n } else {\n queue.push({ method, args });\n scheduleFlush();\n }\n };\n}\n"],
5
+ "mappings": "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",
6
+ "names": []
7
+ }
@@ -0,0 +1,16 @@
1
+ export type PageMetadata = {
2
+ url: string;
3
+ title: string;
4
+ referrer: string;
5
+ timestamp: number;
6
+ };
7
+ export declare class NavigationTracker {
8
+ private lastUrl;
9
+ private onNavigate;
10
+ private originalPushState;
11
+ constructor(onNavigate: (metadata: PageMetadata) => void);
12
+ init(): void;
13
+ private setupSPATracking;
14
+ private handleNavigation;
15
+ cleanup(): void;
16
+ }
@@ -0,0 +1,44 @@
1
+ class NavigationTracker {
2
+ lastUrl = null;
3
+ onNavigate;
4
+ originalPushState = null;
5
+ constructor(onNavigate) {
6
+ this.onNavigate = onNavigate;
7
+ }
8
+ init() {
9
+ this.handleNavigation();
10
+ window.addEventListener("popstate", this.handleNavigation);
11
+ this.setupSPATracking();
12
+ }
13
+ setupSPATracking() {
14
+ this.originalPushState = window.history.pushState;
15
+ window.history.pushState = (...args) => {
16
+ this.originalPushState.apply(window.history, args);
17
+ this.handleNavigation();
18
+ };
19
+ }
20
+ handleNavigation = () => {
21
+ const currentUrl = window.location.href;
22
+ if (this.lastUrl !== null && this.lastUrl === currentUrl) {
23
+ return;
24
+ }
25
+ this.lastUrl = currentUrl;
26
+ const metadata = {
27
+ url: currentUrl,
28
+ title: document.title,
29
+ referrer: document.referrer,
30
+ timestamp: Date.now()
31
+ };
32
+ this.onNavigate(metadata);
33
+ };
34
+ cleanup() {
35
+ window.removeEventListener("popstate", this.handleNavigation);
36
+ if (this.originalPushState) {
37
+ window.history.pushState = this.originalPushState;
38
+ }
39
+ }
40
+ }
41
+ export {
42
+ NavigationTracker
43
+ };
44
+ //# sourceMappingURL=navigation-tracker.js.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../../analytics/utils/navigation-tracker.ts"],
4
+ "sourcesContent": ["export type PageMetadata = {\n url: string;\n title: string;\n referrer: string;\n timestamp: number;\n};\n\nexport class NavigationTracker {\n private lastUrl: string | null = null;\n private onNavigate: (metadata: PageMetadata) => void;\n private originalPushState: typeof window.history.pushState | null = null;\n\n constructor(onNavigate: (metadata: PageMetadata) => void) {\n this.onNavigate = onNavigate;\n }\n\n init() {\n this.handleNavigation();\n\n window.addEventListener(\"popstate\", this.handleNavigation);\n\n this.setupSPATracking();\n }\n\n private setupSPATracking() {\n this.originalPushState = window.history.pushState;\n\n window.history.pushState = (...args) => {\n this.originalPushState!.apply(window.history, args);\n this.handleNavigation();\n };\n }\n\n private handleNavigation = () => {\n const currentUrl = window.location.href;\n\n if (this.lastUrl !== null && this.lastUrl === currentUrl) {\n return;\n }\n this.lastUrl = currentUrl;\n\n const metadata: PageMetadata = {\n url: currentUrl,\n title: document.title,\n referrer: document.referrer,\n timestamp: Date.now(),\n };\n\n this.onNavigate(metadata);\n };\n\n cleanup() {\n window.removeEventListener(\"popstate\", this.handleNavigation);\n\n if (this.originalPushState) {\n window.history.pushState = this.originalPushState;\n }\n }\n}\n"],
5
+ "mappings": "AAOO,MAAM,kBAAkB;AAAA,EACrB,UAAyB;AAAA,EACzB;AAAA,EACA,oBAA4D;AAAA,EAEpE,YAAY,YAA8C;AACxD,SAAK,aAAa;AAAA,EACpB;AAAA,EAEA,OAAO;AACL,SAAK,iBAAiB;AAEtB,WAAO,iBAAiB,YAAY,KAAK,gBAAgB;AAEzD,SAAK,iBAAiB;AAAA,EACxB;AAAA,EAEQ,mBAAmB;AACzB,SAAK,oBAAoB,OAAO,QAAQ;AAExC,WAAO,QAAQ,YAAY,IAAI,SAAS;AACtC,WAAK,kBAAmB,MAAM,OAAO,SAAS,IAAI;AAClD,WAAK,iBAAiB;AAAA,IACxB;AAAA,EACF;AAAA,EAEQ,mBAAmB,MAAM;AAC/B,UAAM,aAAa,OAAO,SAAS;AAEnC,QAAI,KAAK,YAAY,QAAQ,KAAK,YAAY,YAAY;AACxD;AAAA,IACF;AACA,SAAK,UAAU;AAEf,UAAM,WAAyB;AAAA,MAC7B,KAAK;AAAA,MACL,OAAO,SAAS;AAAA,MAChB,UAAU,SAAS;AAAA,MACnB,WAAW,KAAK,IAAI;AAAA,IACtB;AAEA,SAAK,WAAW,QAAQ;AAAA,EAC1B;AAAA,EAEA,UAAU;AACR,WAAO,oBAAoB,YAAY,KAAK,gBAAgB;AAE5D,QAAI,KAAK,mBAAmB;AAC1B,aAAO,QAAQ,YAAY,KAAK;AAAA,IAClC;AAAA,EACF;AACF;",
6
+ "names": []
7
+ }
@@ -0,0 +1,8 @@
1
+ import type { AnalyticsSink } from "../analytics-sink";
2
+ /**
3
+ * Wraps a third-party ad-pixel sink so checkout-funnel events Shopify owns
4
+ * become no-ops; every other event passes through untouched. Apply only to
5
+ * third-party pixel sinks — never to the first-party `ReploSink` (the
6
+ * storefront's own record) or the local `WindowSink` event bus.
7
+ */
8
+ export declare function gateShopifyOwnedFunnelEvents(sink: AnalyticsSink): AnalyticsSink;
@@ -0,0 +1,22 @@
1
+ const SHOPIFY_OWNED_FUNNEL_EVENTS = [
2
+ "startCheckout",
3
+ "purchase"
4
+ ];
5
+ const shopifyOwnedFunnelEvents = new Set(
6
+ SHOPIFY_OWNED_FUNNEL_EVENTS
7
+ );
8
+ function gateShopifyOwnedFunnelEvents(sink) {
9
+ return new Proxy(sink, {
10
+ get(target, property, receiver) {
11
+ if (typeof property === "string" && shopifyOwnedFunnelEvents.has(property)) {
12
+ return async () => {
13
+ };
14
+ }
15
+ return Reflect.get(target, property, receiver);
16
+ }
17
+ });
18
+ }
19
+ export {
20
+ gateShopifyOwnedFunnelEvents
21
+ };
22
+ //# sourceMappingURL=shopify-funnel-gate.js.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../../analytics/utils/shopify-funnel-gate.ts"],
4
+ "sourcesContent": ["import type { AnalyticsSink } from \"../analytics-sink\";\n\n/**\n * Checkout-funnel events that Shopify's hosted checkout already reports to ad\n * platforms server-side (via native sales channels / Customer Events / CAPI).\n * When checkout is Shopify-hosted, a third-party pixel firing these from the\n * storefront double-counts against Shopify's copy \u2014 the storefront and the\n * Shopify checkout are different origins, so there is no shared event_id to\n * deduplicate against. `startCheckout` is the one fired today; `purchase` is\n * listed so the gate covers it automatically if the storefront ever emits it.\n */\nconst SHOPIFY_OWNED_FUNNEL_EVENTS = [\n \"startCheckout\",\n \"purchase\",\n] as const satisfies readonly (keyof AnalyticsSink)[];\n\nconst shopifyOwnedFunnelEvents: ReadonlySet<string> = new Set(\n SHOPIFY_OWNED_FUNNEL_EVENTS,\n);\n\n/**\n * Wraps a third-party ad-pixel sink so checkout-funnel events Shopify owns\n * become no-ops; every other event passes through untouched. Apply only to\n * third-party pixel sinks \u2014 never to the first-party `ReploSink` (the\n * storefront's own record) or the local `WindowSink` event bus.\n */\nexport function gateShopifyOwnedFunnelEvents(\n sink: AnalyticsSink,\n): AnalyticsSink {\n return new Proxy(sink, {\n get(target, property, receiver) {\n if (\n typeof property === \"string\" &&\n shopifyOwnedFunnelEvents.has(property)\n ) {\n return async () => {};\n }\n return Reflect.get(target, property, receiver);\n },\n });\n}\n"],
5
+ "mappings": "AAWA,MAAM,8BAA8B;AAAA,EAClC;AAAA,EACA;AACF;AAEA,MAAM,2BAAgD,IAAI;AAAA,EACxD;AACF;AAQO,SAAS,6BACd,MACe;AACf,SAAO,IAAI,MAAM,MAAM;AAAA,IACrB,IAAI,QAAQ,UAAU,UAAU;AAC9B,UACE,OAAO,aAAa,YACpB,yBAAyB,IAAI,QAAQ,GACrC;AACA,eAAO,YAAY;AAAA,QAAC;AAAA,MACtB;AACA,aAAO,QAAQ,IAAI,QAAQ,UAAU,QAAQ;AAAA,IAC/C;AAAA,EACF,CAAC;AACH;",
6
+ "names": []
7
+ }
@@ -0,0 +1,21 @@
1
+ import type { CartLineAttribute } from "./cart-types";
2
+ /**
3
+ * Server action that handles the full buy-now flow:
4
+ * 1. For Shopify: creates a cart via the canopy-api-backed gateway, returns checkoutUrl.
5
+ * 2. For Stripe: creates a Stripe checkout session via canopy-api, returns session URL.
6
+ *
7
+ * Variant IDs are expected to already be Storefront GIDs (from data loader output).
8
+ * No internal→external ID mapping is needed.
9
+ */
10
+ export declare function buyNowAction(input: {
11
+ lineItems: {
12
+ variantId: string;
13
+ quantity: number;
14
+ sellingPlanId: string | null;
15
+ properties: CartLineAttribute[];
16
+ }[];
17
+ discountCodes: string[];
18
+ pageUrl: string;
19
+ }): Promise<{
20
+ redirectUrl: string;
21
+ }>;
@@ -0,0 +1,104 @@
1
+ "use server";
2
+ import { headers } from "next/headers";
3
+ import { v4 as uuidv4 } from "uuid";
4
+ import { z } from "zod";
5
+ import { getEnv } from "../env";
6
+ import { CanopyError } from "../lib/canopy-error";
7
+ import { getCheckoutProvider } from "../lib/integration-utils";
8
+ import { buildBaseUrl } from "../lib/url-utils";
9
+ import { createCartAction } from "./cart-actions";
10
+ import { REPLO_ATTRIBUTION_PROPERTY } from "./cart-types";
11
+ class BuyNowError extends CanopyError {
12
+ }
13
+ class BuyNowCartCreationError extends CanopyError {
14
+ }
15
+ async function buyNowAction(input) {
16
+ const { lineItems, discountCodes, pageUrl } = input;
17
+ const headersList = await headers();
18
+ const host = headersList.get("host");
19
+ if (!host) {
20
+ throw new BuyNowError({ message: "Missing host header" });
21
+ }
22
+ const forwardedProto = headersList.get("x-forwarded-proto");
23
+ const protocol = forwardedProto?.split(",")[0]?.trim() ?? "https";
24
+ const origin = `${protocol}://${host}`;
25
+ const checkoutProvider = await getCheckoutProvider();
26
+ const cartLines = lineItems.map((item) => {
27
+ const hasReploAttribution = item.properties.some(
28
+ (prop) => prop.key === REPLO_ATTRIBUTION_PROPERTY.key
29
+ );
30
+ const properties = hasReploAttribution ? item.properties : [REPLO_ATTRIBUTION_PROPERTY, ...item.properties];
31
+ return {
32
+ id: item.variantId,
33
+ quantity: item.quantity,
34
+ sellingPlanId: item.sellingPlanId,
35
+ properties
36
+ };
37
+ });
38
+ if (checkoutProvider === "stripe") {
39
+ const env = await getEnv();
40
+ const isSameOrigin = (() => {
41
+ try {
42
+ return Boolean(pageUrl) && new URL(pageUrl).origin === origin;
43
+ } catch {
44
+ return false;
45
+ }
46
+ })();
47
+ const safePageUrl = isSameOrigin ? pageUrl : origin;
48
+ const cancelUrl = safePageUrl;
49
+ const temporaryCartId = uuidv4();
50
+ const body = {
51
+ cartId: temporaryCartId,
52
+ lines: cartLines.map((line) => ({
53
+ variantId: line.id,
54
+ quantity: line.quantity,
55
+ properties: line.properties
56
+ })),
57
+ projectId: env.PROJECT_ID,
58
+ // canopy appends session_id={CHECKOUT_SESSION_ID} at session creation;
59
+ // the success route resolves it into the order status page.
60
+ successUrl: `${origin}/checkout/success`,
61
+ cancelUrl
62
+ };
63
+ const canopyApiUrl = `${buildBaseUrl(env.CANOPY_API_HOST)}/api/v1/stripe-checkout/create-session`;
64
+ const response = await fetch(canopyApiUrl, {
65
+ method: "POST",
66
+ headers: { "Content-Type": "application/json" },
67
+ body: JSON.stringify(body)
68
+ });
69
+ if (!response.ok) {
70
+ throw new BuyNowCartCreationError({
71
+ message: "Failed to create Stripe checkout session for buy now",
72
+ additionalData: {
73
+ status: response.status,
74
+ statusText: response.statusText
75
+ }
76
+ });
77
+ }
78
+ const data = z.object({ url: z.string() }).safeParse(await response.json());
79
+ if (!data.success) {
80
+ throw new BuyNowCartCreationError({
81
+ message: "Stripe checkout session response missing redirect URL",
82
+ cause: data.error
83
+ });
84
+ }
85
+ return { redirectUrl: data.data.url };
86
+ }
87
+ const cart = await createCartAction({
88
+ lines: cartLines,
89
+ skipStoringCart: true,
90
+ discountCodes: discountCodes.length > 0 ? discountCodes : void 0
91
+ });
92
+ if (!cart?.checkoutUrl) {
93
+ throw new BuyNowCartCreationError({
94
+ message: "Failed to create cart or get checkout URL",
95
+ additionalData: { lineItems, discountCodes }
96
+ });
97
+ }
98
+ const checkoutUrl = new URL(cart.checkoutUrl, origin);
99
+ return { redirectUrl: checkoutUrl.toString() };
100
+ }
101
+ export {
102
+ buyNowAction
103
+ };
104
+ //# sourceMappingURL=buy-now-action.js.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../cart/buy-now-action.ts"],
4
+ "sourcesContent": ["\"use server\";\n\nimport type { CartLineAttribute } from \"./cart-types\";\n\nimport { headers } from \"next/headers\";\n\nimport { v4 as uuidv4 } from \"uuid\";\nimport { z } from \"zod\";\n\nimport { getEnv } from \"../env\";\nimport { CanopyError } from \"../lib/canopy-error\";\nimport { getCheckoutProvider } from \"../lib/integration-utils\";\nimport { buildBaseUrl } from \"../lib/url-utils\";\nimport { createCartAction } from \"./cart-actions\";\nimport { REPLO_ATTRIBUTION_PROPERTY } from \"./cart-types\";\n\nclass BuyNowError extends CanopyError {}\nclass BuyNowCartCreationError extends CanopyError {}\n\n/**\n * Server action that handles the full buy-now flow:\n * 1. For Shopify: creates a cart via the canopy-api-backed gateway, returns checkoutUrl.\n * 2. For Stripe: creates a Stripe checkout session via canopy-api, returns session URL.\n *\n * Variant IDs are expected to already be Storefront GIDs (from data loader output).\n * No internal\u2192external ID mapping is needed.\n */\nexport async function buyNowAction(input: {\n lineItems: {\n variantId: string;\n quantity: number;\n sellingPlanId: string | null;\n properties: CartLineAttribute[];\n }[];\n discountCodes: string[];\n pageUrl: string;\n}): Promise<{ redirectUrl: string }> {\n const { lineItems, discountCodes, pageUrl } = input;\n\n const headersList = await headers();\n const host = headersList.get(\"host\");\n if (!host) {\n throw new BuyNowError({ message: \"Missing host header\" });\n }\n const forwardedProto = headersList.get(\"x-forwarded-proto\");\n const protocol = forwardedProto?.split(\",\")[0]?.trim() ?? \"https\";\n const origin = `${protocol}://${host}`;\n\n const checkoutProvider = await getCheckoutProvider();\n\n const cartLines = lineItems.map((item) => {\n const hasReploAttribution = item.properties.some(\n (prop) => prop.key === REPLO_ATTRIBUTION_PROPERTY.key,\n );\n const properties = hasReploAttribution\n ? item.properties\n : [REPLO_ATTRIBUTION_PROPERTY, ...item.properties];\n\n return {\n id: item.variantId,\n quantity: item.quantity,\n sellingPlanId: item.sellingPlanId,\n properties,\n };\n });\n\n if (checkoutProvider === \"stripe\") {\n const env = await getEnv();\n const isSameOrigin = (() => {\n try {\n return Boolean(pageUrl) && new URL(pageUrl).origin === origin;\n } catch {\n return false;\n }\n })();\n const safePageUrl = isSameOrigin ? pageUrl : origin;\n const cancelUrl = safePageUrl;\n const temporaryCartId = uuidv4();\n\n const body = {\n cartId: temporaryCartId,\n lines: cartLines.map((line) => ({\n variantId: line.id,\n quantity: line.quantity,\n properties: line.properties,\n })),\n projectId: env.PROJECT_ID,\n // canopy appends session_id={CHECKOUT_SESSION_ID} at session creation;\n // the success route resolves it into the order status page.\n successUrl: `${origin}/checkout/success`,\n cancelUrl,\n };\n\n const canopyApiUrl = `${buildBaseUrl(env.CANOPY_API_HOST)}/api/v1/stripe-checkout/create-session`;\n const response = await fetch(canopyApiUrl, {\n method: \"POST\",\n headers: { \"Content-Type\": \"application/json\" },\n body: JSON.stringify(body),\n });\n\n if (!response.ok) {\n throw new BuyNowCartCreationError({\n message: \"Failed to create Stripe checkout session for buy now\",\n additionalData: {\n status: response.status,\n statusText: response.statusText,\n },\n });\n }\n\n const data = z.object({ url: z.string() }).safeParse(await response.json());\n if (!data.success) {\n throw new BuyNowCartCreationError({\n message: \"Stripe checkout session response missing redirect URL\",\n cause: data.error,\n });\n }\n return { redirectUrl: data.data.url };\n }\n\n // Shopify and other integrations: create cart via canopy-api-backed gateway\n const cart = await createCartAction({\n lines: cartLines,\n skipStoringCart: true,\n discountCodes: discountCodes.length > 0 ? discountCodes : undefined,\n });\n\n if (!cart?.checkoutUrl) {\n throw new BuyNowCartCreationError({\n message: \"Failed to create cart or get checkout URL\",\n additionalData: { lineItems, discountCodes },\n });\n }\n\n const checkoutUrl = new URL(cart.checkoutUrl, origin);\n return { redirectUrl: checkoutUrl.toString() };\n}\n"],
5
+ "mappings": "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",
6
+ "names": []
7
+ }
@@ -0,0 +1,63 @@
1
+ import type { AddToCartPayload, Cart, CartLinePayload, RemoveFromCartPayload, UpdateCartLineItemPayload } from "./cart-types";
2
+ /**
3
+ * Gets the existing cart or creates a new one if none exists. This is necessary
4
+ * because we may not have cookies in the server context during initial load.
5
+ *
6
+ * See: https://nextjs.org/docs/app/api-reference/functions/cookies#understanding-cookie-behavior-in-server-components
7
+ *
8
+ * @returns The existing cart or a newly created cart
9
+ */
10
+ export declare function getOrCreateCartAction(): Promise<Cart | null>;
11
+ /**
12
+ * Retrieves the current cart from cookies. Returns null if no cart exists or
13
+ * if the cart has expired/been deleted.
14
+ *
15
+ * @returns The current cart or null if none exists
16
+ */
17
+ export declare function getCartAction(): Promise<Cart | null>;
18
+ /**
19
+ * Creates a new cart with optional initial line items. The cart ID is stored
20
+ * in a cookie for future retrieval.
21
+ *
22
+ * @param options.lines - Optional initial cart line items
23
+ * @param options.skipStoringCart - If true, skips storing the cart in cookies (used for buy-now flows)
24
+ * @param options.discountCodes - Optional discount codes to apply on cart creation
25
+ * @returns The newly created cart
26
+ */
27
+ export declare function createCartAction(options?: {
28
+ lines?: CartLinePayload[];
29
+ skipStoringCart?: boolean;
30
+ discountCodes?: string[];
31
+ }): Promise<Cart | null>;
32
+ /**
33
+ * Adds line items to an existing cart.
34
+ *
35
+ * @param lines - Array of cart line items to add
36
+ * @param cartId - The ID of the cart to add items to
37
+ * @returns The updated cart
38
+ */
39
+ export declare function addToCartAction(lines: AddToCartPayload["lines"], cartId: string): Promise<Cart | null>;
40
+ /**
41
+ * Updates a cart line item (typically quantity).
42
+ *
43
+ * @param line - The cart line item with updated values
44
+ * @param cartId - The ID of the cart containing the line item
45
+ * @returns The updated cart
46
+ */
47
+ export declare function updateCartLineItemAction(line: UpdateCartLineItemPayload["line"], cartId: string): Promise<Cart | null>;
48
+ /**
49
+ * Removes one or more line items from the cart.
50
+ *
51
+ * @param lineIds - Array of line item IDs to remove
52
+ * @param cartId - The ID of the cart to remove items from
53
+ * @returns The updated cart
54
+ */
55
+ export declare function removeCartLineItemsAction(lineIds: RemoveFromCartPayload["lineIds"], cartId: string): Promise<Cart | null>;
56
+ /**
57
+ * Updates discount codes for a cart.
58
+ *
59
+ * @param discountCodes - Array of discount code strings to apply
60
+ * @param cartId - The ID of the cart to update
61
+ * @returns The updated cart
62
+ */
63
+ export declare function updateCartDiscountCodesAction(discountCodes: string[], cartId: string): Promise<Cart | null>;
@@ -0,0 +1,90 @@
1
+ "use server";
2
+ import { cookies } from "next/headers";
3
+ import { getCheckoutProvider } from "../lib/integration-utils";
4
+ import { REPLO_CART_COOKIE_NAME } from "./gateways/cart-constants";
5
+ import { getCartGateway } from "./gateways/cart-gateway";
6
+ import {
7
+ loadCartFromCookie,
8
+ saveCartToCookie
9
+ } from "./utils/cookie-cart-persistence";
10
+ const SHOPIFY_CART_COOKIE_NAME = "replo_cart_id";
11
+ const CART_COOKIE_MAX_AGE = 60 * 60 * 24 * 30;
12
+ async function getOrCreateCartAction() {
13
+ const existingCart = await getCartAction();
14
+ if (existingCart) {
15
+ return existingCart;
16
+ }
17
+ return await createCartAction();
18
+ }
19
+ async function getCartAction() {
20
+ const checkoutProvider = await getCheckoutProvider();
21
+ if (checkoutProvider === "stripe") {
22
+ return await loadCartFromCookie(REPLO_CART_COOKIE_NAME);
23
+ }
24
+ const cookieStore = await cookies();
25
+ const existingCartId = cookieStore.get(SHOPIFY_CART_COOKIE_NAME)?.value;
26
+ if (!existingCartId) {
27
+ return null;
28
+ }
29
+ const cartGateway = await getCartGateway();
30
+ const cart = await cartGateway.getCart(existingCartId);
31
+ if (!cart) {
32
+ try {
33
+ cookieStore.delete(SHOPIFY_CART_COOKIE_NAME);
34
+ } catch (error) {
35
+ console.warn("Failed to delete cart cookie:", error);
36
+ }
37
+ }
38
+ return cart;
39
+ }
40
+ async function createCartAction(options) {
41
+ const { lines, skipStoringCart = false, discountCodes } = options ?? {};
42
+ const checkoutProvider = await getCheckoutProvider();
43
+ const cartGateway = await getCartGateway();
44
+ const cart = await cartGateway.createCart(lines, discountCodes);
45
+ if (cart && !skipStoringCart) {
46
+ try {
47
+ if (checkoutProvider === "stripe") {
48
+ await saveCartToCookie(cart, REPLO_CART_COOKIE_NAME);
49
+ } else {
50
+ const cookieStore = await cookies();
51
+ cookieStore.set(SHOPIFY_CART_COOKIE_NAME, cart.id, {
52
+ maxAge: CART_COOKIE_MAX_AGE,
53
+ httpOnly: true,
54
+ secure: process.env.NODE_ENV === "production",
55
+ sameSite: "lax",
56
+ path: "/"
57
+ });
58
+ }
59
+ } catch (cookieError) {
60
+ console.warn("Failed to set cart cookie:", cookieError);
61
+ }
62
+ }
63
+ return cart;
64
+ }
65
+ async function addToCartAction(lines, cartId) {
66
+ const cartGateway = await getCartGateway();
67
+ return await cartGateway.addToCart({ lines, cartId });
68
+ }
69
+ async function updateCartLineItemAction(line, cartId) {
70
+ const cartGateway = await getCartGateway();
71
+ return await cartGateway.updateCartLineItem({ line, cartId });
72
+ }
73
+ async function removeCartLineItemsAction(lineIds, cartId) {
74
+ const cartGateway = await getCartGateway();
75
+ return await cartGateway.removeCartLineItems({ lineIds, cartId });
76
+ }
77
+ async function updateCartDiscountCodesAction(discountCodes, cartId) {
78
+ const cartGateway = await getCartGateway();
79
+ return await cartGateway.updateCartDiscountCodes({ discountCodes, cartId });
80
+ }
81
+ export {
82
+ addToCartAction,
83
+ createCartAction,
84
+ getCartAction,
85
+ getOrCreateCartAction,
86
+ removeCartLineItemsAction,
87
+ updateCartDiscountCodesAction,
88
+ updateCartLineItemAction
89
+ };
90
+ //# sourceMappingURL=cart-actions.js.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../cart/cart-actions.ts"],
4
+ "sourcesContent": ["\"use server\";\n\nimport type {\n AddToCartPayload,\n Cart,\n CartLinePayload,\n RemoveFromCartPayload,\n UpdateCartLineItemPayload,\n} from \"./cart-types\";\n\nimport { cookies } from \"next/headers\";\n\nimport { getCheckoutProvider } from \"../lib/integration-utils\";\nimport { REPLO_CART_COOKIE_NAME } from \"./gateways/cart-constants\";\nimport { getCartGateway } from \"./gateways/cart-gateway\";\nimport {\n loadCartFromCookie,\n saveCartToCookie,\n} from \"./utils/cookie-cart-persistence\";\n\nconst SHOPIFY_CART_COOKIE_NAME = \"replo_cart_id\";\nconst CART_COOKIE_MAX_AGE = 60 * 60 * 24 * 30; // 30 days\n\n/**\n * Gets the existing cart or creates a new one if none exists. This is necessary\n * because we may not have cookies in the server context during initial load.\n *\n * See: https://nextjs.org/docs/app/api-reference/functions/cookies#understanding-cookie-behavior-in-server-components\n *\n * @returns The existing cart or a newly created cart\n */\nexport async function getOrCreateCartAction(): Promise<Cart | null> {\n const existingCart = await getCartAction();\n if (existingCart) {\n return existingCart;\n }\n return await createCartAction();\n}\n\n/**\n * Retrieves the current cart from cookies. Returns null if no cart exists or\n * if the cart has expired/been deleted.\n *\n * @returns The current cart or null if none exists\n */\nexport async function getCartAction(): Promise<Cart | null> {\n const checkoutProvider = await getCheckoutProvider();\n\n if (checkoutProvider === \"stripe\") {\n return await loadCartFromCookie(REPLO_CART_COOKIE_NAME);\n }\n\n const cookieStore = await cookies();\n const existingCartId = cookieStore.get(SHOPIFY_CART_COOKIE_NAME)?.value;\n\n if (!existingCartId) {\n return null;\n }\n\n const cartGateway = await getCartGateway();\n const cart = await cartGateway.getCart(existingCartId);\n\n // If we had a cart ID in the cookie but couldn't fetch the cart,\n // it means the cart is invalid/expired - clear the cookie\n if (!cart) {\n try {\n cookieStore.delete(SHOPIFY_CART_COOKIE_NAME);\n } catch (error) {\n console.warn(\"Failed to delete cart cookie:\", error);\n }\n }\n\n return cart;\n}\n\n/**\n * Creates a new cart with optional initial line items. The cart ID is stored\n * in a cookie for future retrieval.\n *\n * @param options.lines - Optional initial cart line items\n * @param options.skipStoringCart - If true, skips storing the cart in cookies (used for buy-now flows)\n * @param options.discountCodes - Optional discount codes to apply on cart creation\n * @returns The newly created cart\n */\nexport async function createCartAction(options?: {\n lines?: CartLinePayload[];\n skipStoringCart?: boolean;\n discountCodes?: string[];\n}): Promise<Cart | null> {\n const { lines, skipStoringCart = false, discountCodes } = options ?? {};\n const checkoutProvider = await getCheckoutProvider();\n const cartGateway = await getCartGateway();\n const cart = await cartGateway.createCart(lines, discountCodes);\n\n if (cart && !skipStoringCart) {\n // Set the cart ID in a cookie - this works in Server Action context\n try {\n if (checkoutProvider === \"stripe\") {\n await saveCartToCookie(cart, REPLO_CART_COOKIE_NAME);\n } else {\n const cookieStore = await cookies();\n cookieStore.set(SHOPIFY_CART_COOKIE_NAME, cart.id, {\n maxAge: CART_COOKIE_MAX_AGE,\n httpOnly: true,\n secure: process.env.NODE_ENV === \"production\",\n sameSite: \"lax\",\n path: \"/\",\n });\n }\n } catch (cookieError) {\n console.warn(\"Failed to set cart cookie:\", cookieError);\n }\n }\n\n return cart;\n}\n\n/**\n * Adds line items to an existing cart.\n *\n * @param lines - Array of cart line items to add\n * @param cartId - The ID of the cart to add items to\n * @returns The updated cart\n */\nexport async function addToCartAction(\n lines: AddToCartPayload[\"lines\"],\n cartId: string,\n): Promise<Cart | null> {\n const cartGateway = await getCartGateway();\n return await cartGateway.addToCart({ lines, cartId });\n}\n\n/**\n * Updates a cart line item (typically quantity).\n *\n * @param line - The cart line item with updated values\n * @param cartId - The ID of the cart containing the line item\n * @returns The updated cart\n */\nexport async function updateCartLineItemAction(\n line: UpdateCartLineItemPayload[\"line\"],\n cartId: string,\n): Promise<Cart | null> {\n const cartGateway = await getCartGateway();\n return await cartGateway.updateCartLineItem({ line, cartId });\n}\n\n/**\n * Removes one or more line items from the cart.\n *\n * @param lineIds - Array of line item IDs to remove\n * @param cartId - The ID of the cart to remove items from\n * @returns The updated cart\n */\nexport async function removeCartLineItemsAction(\n lineIds: RemoveFromCartPayload[\"lineIds\"],\n cartId: string,\n): Promise<Cart | null> {\n const cartGateway = await getCartGateway();\n return await cartGateway.removeCartLineItems({ lineIds, cartId });\n}\n\n/**\n * Updates discount codes for a cart.\n *\n * @param discountCodes - Array of discount code strings to apply\n * @param cartId - The ID of the cart to update\n * @returns The updated cart\n */\nexport async function updateCartDiscountCodesAction(\n discountCodes: string[],\n cartId: string,\n): Promise<Cart | null> {\n const cartGateway = await getCartGateway();\n return await cartGateway.updateCartDiscountCodes({ discountCodes, cartId });\n}\n"],
5
+ "mappings": ";AAUA,SAAS,eAAe;AAExB,SAAS,2BAA2B;AACpC,SAAS,8BAA8B;AACvC,SAAS,sBAAsB;AAC/B;AAAA,EACE;AAAA,EACA;AAAA,OACK;AAEP,MAAM,2BAA2B;AACjC,MAAM,sBAAsB,KAAK,KAAK,KAAK;AAU3C,eAAsB,wBAA8C;AAClE,QAAM,eAAe,MAAM,cAAc;AACzC,MAAI,cAAc;AAChB,WAAO;AAAA,EACT;AACA,SAAO,MAAM,iBAAiB;AAChC;AAQA,eAAsB,gBAAsC;AAC1D,QAAM,mBAAmB,MAAM,oBAAoB;AAEnD,MAAI,qBAAqB,UAAU;AACjC,WAAO,MAAM,mBAAmB,sBAAsB;AAAA,EACxD;AAEA,QAAM,cAAc,MAAM,QAAQ;AAClC,QAAM,iBAAiB,YAAY,IAAI,wBAAwB,GAAG;AAElE,MAAI,CAAC,gBAAgB;AACnB,WAAO;AAAA,EACT;AAEA,QAAM,cAAc,MAAM,eAAe;AACzC,QAAM,OAAO,MAAM,YAAY,QAAQ,cAAc;AAIrD,MAAI,CAAC,MAAM;AACT,QAAI;AACF,kBAAY,OAAO,wBAAwB;AAAA,IAC7C,SAAS,OAAO;AACd,cAAQ,KAAK,iCAAiC,KAAK;AAAA,IACrD;AAAA,EACF;AAEA,SAAO;AACT;AAWA,eAAsB,iBAAiB,SAId;AACvB,QAAM,EAAE,OAAO,kBAAkB,OAAO,cAAc,IAAI,WAAW,CAAC;AACtE,QAAM,mBAAmB,MAAM,oBAAoB;AACnD,QAAM,cAAc,MAAM,eAAe;AACzC,QAAM,OAAO,MAAM,YAAY,WAAW,OAAO,aAAa;AAE9D,MAAI,QAAQ,CAAC,iBAAiB;AAE5B,QAAI;AACF,UAAI,qBAAqB,UAAU;AACjC,cAAM,iBAAiB,MAAM,sBAAsB;AAAA,MACrD,OAAO;AACL,cAAM,cAAc,MAAM,QAAQ;AAClC,oBAAY,IAAI,0BAA0B,KAAK,IAAI;AAAA,UACjD,QAAQ;AAAA,UACR,UAAU;AAAA,UACV,QAAQ,QAAQ,IAAI,aAAa;AAAA,UACjC,UAAU;AAAA,UACV,MAAM;AAAA,QACR,CAAC;AAAA,MACH;AAAA,IACF,SAAS,aAAa;AACpB,cAAQ,KAAK,8BAA8B,WAAW;AAAA,IACxD;AAAA,EACF;AAEA,SAAO;AACT;AASA,eAAsB,gBACpB,OACA,QACsB;AACtB,QAAM,cAAc,MAAM,eAAe;AACzC,SAAO,MAAM,YAAY,UAAU,EAAE,OAAO,OAAO,CAAC;AACtD;AASA,eAAsB,yBACpB,MACA,QACsB;AACtB,QAAM,cAAc,MAAM,eAAe;AACzC,SAAO,MAAM,YAAY,mBAAmB,EAAE,MAAM,OAAO,CAAC;AAC9D;AASA,eAAsB,0BACpB,SACA,QACsB;AACtB,QAAM,cAAc,MAAM,eAAe;AACzC,SAAO,MAAM,YAAY,oBAAoB,EAAE,SAAS,OAAO,CAAC;AAClE;AASA,eAAsB,8BACpB,eACA,QACsB;AACtB,QAAM,cAAc,MAAM,eAAe;AACzC,SAAO,MAAM,YAAY,wBAAwB,EAAE,eAAe,OAAO,CAAC;AAC5E;",
6
+ "names": []
7
+ }
@@ -0,0 +1,9 @@
1
+ /**
2
+ * Server component that loads the cart and provides it to child components
3
+ * through the CartProvider context. In development mode, skips initial
4
+ * cart loading to avoid cookie issues during development.
5
+ *
6
+ * @param children - Child components that will have access to the cart
7
+ * @returns A CartProvider component wrapping the children with cart data
8
+ */
9
+ export declare function CartLoader({ children }: React.PropsWithChildren): Promise<import("react/jsx-runtime").JSX.Element>;
@@ -0,0 +1,11 @@
1
+ import { jsx } from "react/jsx-runtime";
2
+ import { getCartAction } from "./cart-actions";
3
+ import { CartProvider } from "./cart-provider";
4
+ async function CartLoader({ children }) {
5
+ const cart = process.env.NODE_ENV === "development" ? null : await getCartAction();
6
+ return /* @__PURE__ */ jsx(CartProvider, { cart, children });
7
+ }
8
+ export {
9
+ CartLoader
10
+ };
11
+ //# sourceMappingURL=cart-loader.js.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../cart/cart-loader.tsx"],
4
+ "sourcesContent": ["import { getCartAction } from \"./cart-actions\";\nimport { CartProvider } from \"./cart-provider\";\n\n/**\n * Server component that loads the cart and provides it to child components\n * through the CartProvider context. In development mode, skips initial\n * cart loading to avoid cookie issues during development.\n *\n * @param children - Child components that will have access to the cart\n * @returns A CartProvider component wrapping the children with cart data\n */\nexport async function CartLoader({ children }: React.PropsWithChildren) {\n const cart =\n process.env.NODE_ENV === \"development\" ? null : await getCartAction();\n\n return <CartProvider cart={cart}>{children}</CartProvider>;\n}\n"],
5
+ "mappings": "AAeS;AAfT,SAAS,qBAAqB;AAC9B,SAAS,oBAAoB;AAU7B,eAAsB,WAAW,EAAE,SAAS,GAA4B;AACtE,QAAM,OACJ,QAAQ,IAAI,aAAa,gBAAgB,OAAO,MAAM,cAAc;AAEtE,SAAO,oBAAC,gBAAa,MAAa,UAAS;AAC7C;",
6
+ "names": []
7
+ }