@adtrackify/at-service-common 4.0.31 → 4.0.32

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 (829) hide show
  1. package/dist/cjs/__tests__/clients/acuity-client.spec.d.ts +1 -1
  2. package/dist/cjs/__tests__/clients/acuity-client.spec.js +43 -43
  3. package/dist/cjs/__tests__/clients/cross-platform-compression.spec.d.ts +1 -1
  4. package/dist/cjs/__tests__/clients/cross-platform-compression.spec.js +354 -354
  5. package/dist/cjs/__tests__/clients/dynamodb-client.spec.d.ts +1 -1
  6. package/dist/cjs/__tests__/clients/dynamodb-client.spec.js +194 -194
  7. package/dist/cjs/__tests__/clients/event-collector-client.spec.d.ts +1 -1
  8. package/dist/cjs/__tests__/clients/event-collector-client.spec.js +227 -227
  9. package/dist/cjs/__tests__/clients/open-exchange-rates-client.spec.d.ts +1 -1
  10. package/dist/cjs/__tests__/clients/open-exchange-rates-client.spec.js +55 -55
  11. package/dist/cjs/__tests__/clients/sqs-bundled-client.spec.d.ts +1 -1
  12. package/dist/cjs/__tests__/clients/sqs-bundled-client.spec.js +931 -931
  13. package/dist/cjs/__tests__/clients/sqs-bundling-contracts.spec.d.ts +1 -1
  14. package/dist/cjs/__tests__/clients/sqs-bundling-contracts.spec.js +563 -563
  15. package/dist/cjs/__tests__/clients/sqs-client.spec.d.ts +1 -1
  16. package/dist/cjs/__tests__/clients/sqs-client.spec.js +191 -191
  17. package/dist/cjs/__tests__/clients/sqs-unbundle.spec.d.ts +1 -1
  18. package/dist/cjs/__tests__/clients/sqs-unbundle.spec.js +1357 -1357
  19. package/dist/cjs/__tests__/db/contact-enrichments-db-service.spec.d.ts +1 -1
  20. package/dist/cjs/__tests__/db/contact-enrichments-db-service.spec.js +68 -68
  21. package/dist/cjs/__tests__/db/destinations-db-service.spec.d.ts +1 -1
  22. package/dist/cjs/__tests__/db/destinations-db-service.spec.js +125 -125
  23. package/dist/cjs/__tests__/db/products-db-service.spec.d.ts +1 -1
  24. package/dist/cjs/__tests__/db/products-db-service.spec.js +89 -89
  25. package/dist/cjs/__tests__/db/shared-read-db-services.spec.d.ts +1 -1
  26. package/dist/cjs/__tests__/db/shared-read-db-services.spec.js +89 -89
  27. package/dist/cjs/__tests__/db/shopify-app-installs-db-service.spec.d.ts +1 -1
  28. package/dist/cjs/__tests__/db/shopify-app-installs-db-service.spec.js +104 -104
  29. package/dist/cjs/__tests__/db/subscriptions-db-service.spec.d.ts +1 -1
  30. package/dist/cjs/__tests__/db/subscriptions-db-service.spec.js +95 -95
  31. package/dist/cjs/__tests__/db/user-accounts-db-service.spec.d.ts +1 -1
  32. package/dist/cjs/__tests__/db/user-accounts-db-service.spec.js +76 -76
  33. package/dist/cjs/__tests__/helpers/account-users-helper.spec.d.ts +1 -1
  34. package/dist/cjs/__tests__/helpers/account-users-helper.spec.js +220 -220
  35. package/dist/cjs/__tests__/helpers/acuity-helper.spec.d.ts +1 -1
  36. package/dist/cjs/__tests__/helpers/acuity-helper.spec.js +69 -69
  37. package/dist/cjs/__tests__/helpers/api-key-auth-helper.spec.d.ts +1 -1
  38. package/dist/cjs/__tests__/helpers/api-key-auth-helper.spec.js +82 -82
  39. package/dist/cjs/__tests__/helpers/cognito-auth-helper.spec.d.ts +1 -1
  40. package/dist/cjs/__tests__/helpers/cognito-auth-helper.spec.js +46 -46
  41. package/dist/cjs/__tests__/helpers/public-api-response-helper.spec.d.ts +1 -1
  42. package/dist/cjs/__tests__/helpers/public-api-response-helper.spec.js +60 -60
  43. package/dist/cjs/__tests__/identity-cache/helpers.spec.d.ts +1 -1
  44. package/dist/cjs/__tests__/identity-cache/helpers.spec.js +592 -592
  45. package/dist/cjs/__tests__/identity-cache/identity-cache-db-service.spec.d.ts +1 -1
  46. package/dist/cjs/__tests__/identity-cache/identity-cache-db-service.spec.js +676 -676
  47. package/dist/cjs/__tests__/identity-cache/identity-cache-dynamodb-db-service.spec.d.ts +1 -1
  48. package/dist/cjs/__tests__/identity-cache/identity-cache-dynamodb-db-service.spec.js +555 -555
  49. package/dist/cjs/__tests__/identity-cache/identity-cache-tier-routing.spec.d.ts +1 -1
  50. package/dist/cjs/__tests__/identity-cache/identity-cache-tier-routing.spec.js +631 -631
  51. package/dist/cjs/__tests__/identity-cache/identity-client.spec.d.ts +1 -1
  52. package/dist/cjs/__tests__/identity-cache/identity-client.spec.js +359 -359
  53. package/dist/cjs/__tests__/identity-cache/identity-gateway-cache-hit.spec.d.ts +1 -1
  54. package/dist/cjs/__tests__/identity-cache/identity-gateway-cache-hit.spec.js +137 -137
  55. package/dist/cjs/__tests__/identity-cache/identity-gateway-cache-miss.spec.d.ts +1 -1
  56. package/dist/cjs/__tests__/identity-cache/identity-gateway-cache-miss.spec.js +152 -152
  57. package/dist/cjs/__tests__/identity-cache/identity-gateway-constructor.spec.d.ts +1 -1
  58. package/dist/cjs/__tests__/identity-cache/identity-gateway-constructor.spec.js +71 -71
  59. package/dist/cjs/__tests__/identity-cache/identity-gateway-edge-cases.spec.d.ts +1 -1
  60. package/dist/cjs/__tests__/identity-cache/identity-gateway-edge-cases.spec.js +88 -88
  61. package/dist/cjs/__tests__/identity-cache/identity-gateway-enqueue-async.spec.d.ts +1 -1
  62. package/dist/cjs/__tests__/identity-cache/identity-gateway-enqueue-async.spec.js +135 -135
  63. package/dist/cjs/__tests__/identity-cache/identity-gateway-stale-cache.spec.d.ts +1 -1
  64. package/dist/cjs/__tests__/identity-cache/identity-gateway-stale-cache.spec.js +223 -223
  65. package/dist/cjs/__tests__/identity-cache/identity-gateway-test-setup.d.ts +28 -28
  66. package/dist/cjs/__tests__/identity-cache/identity-gateway-test-setup.js +89 -89
  67. package/dist/cjs/__tests__/identity-cache/trait-merging-and-staleness.spec.d.ts +1 -1
  68. package/dist/cjs/__tests__/identity-cache/trait-merging-and-staleness.spec.js +1770 -1770
  69. package/dist/cjs/__tests__/identity-cache/volatile-traits-optimization.spec.d.ts +1 -1
  70. package/dist/cjs/__tests__/identity-cache/volatile-traits-optimization.spec.js +818 -818
  71. package/dist/cjs/__tests__/integration/sqs-bundling-roundtrip.spec.d.ts +1 -1
  72. package/dist/cjs/__tests__/integration/sqs-bundling-roundtrip.spec.js +584 -584
  73. package/dist/cjs/__tests__/libs/compress-decompress.spec.d.ts +1 -1
  74. package/dist/cjs/__tests__/libs/compress-decompress.spec.js +16 -16
  75. package/dist/cjs/__tests__/libs/contacts.spec.d.ts +1 -1
  76. package/dist/cjs/__tests__/libs/contacts.spec.js +294 -294
  77. package/dist/cjs/__tests__/libs/currency.spec.d.ts +1 -1
  78. package/dist/cjs/__tests__/libs/currency.spec.js +220 -220
  79. package/dist/cjs/__tests__/libs/dates.spec.d.ts +1 -1
  80. package/dist/cjs/__tests__/libs/dates.spec.js +130 -130
  81. package/dist/cjs/__tests__/libs/domain.spec.d.ts +1 -1
  82. package/dist/cjs/__tests__/libs/domain.spec.js +107 -107
  83. package/dist/cjs/__tests__/libs/numbers.spec.d.ts +1 -1
  84. package/dist/cjs/__tests__/libs/numbers.spec.js +261 -261
  85. package/dist/cjs/__tests__/s3-client/s3-client.spec.d.ts +1 -1
  86. package/dist/cjs/__tests__/s3-client/s3-client.spec.js +33 -33
  87. package/dist/cjs/__tests__/services/acuity-api-service.spec.d.ts +1 -1
  88. package/dist/cjs/__tests__/services/acuity-api-service.spec.js +71 -71
  89. package/dist/cjs/__tests__/services/cost/cost-calculation-types.spec.d.ts +1 -1
  90. package/dist/cjs/__tests__/services/cost/cost-calculation-types.spec.js +23 -23
  91. package/dist/cjs/__tests__/services/cost/cost-calculator-service.spec.d.ts +1 -1
  92. package/dist/cjs/__tests__/services/cost/cost-calculator-service.spec.js +3349 -3319
  93. package/dist/cjs/__tests__/services/cost/cost-calculator-service.spec.js.map +1 -1
  94. package/dist/cjs/__tests__/services/cost/cost-currency-service.spec.d.ts +1 -1
  95. package/dist/cjs/__tests__/services/cost/cost-currency-service.spec.js +114 -114
  96. package/dist/cjs/__tests__/services/cost/cost-filter-service.spec.d.ts +1 -1
  97. package/dist/cjs/__tests__/services/cost/cost-filter-service.spec.js +468 -468
  98. package/dist/cjs/__tests__/services/cost/order-cost/order-cost-resolution-service.spec.d.ts +1 -1
  99. package/dist/cjs/__tests__/services/cost/order-cost/order-cost-resolution-service.spec.js +360 -206
  100. package/dist/cjs/__tests__/services/cost/order-cost/order-cost-resolution-service.spec.js.map +1 -1
  101. package/dist/cjs/__tests__/services/currency-exchange-rate-lookup-service.spec.d.ts +1 -1
  102. package/dist/cjs/__tests__/services/currency-exchange-rate-lookup-service.spec.js +34 -34
  103. package/dist/cjs/__tests__/services/email-verification/contact-email-verification-service.spec.d.ts +1 -1
  104. package/dist/cjs/__tests__/services/email-verification/contact-email-verification-service.spec.js +93 -93
  105. package/dist/cjs/__tests__/services/email-verification/email-verification-service.spec.d.ts +1 -1
  106. package/dist/cjs/__tests__/services/email-verification/email-verification-service.spec.js +57 -57
  107. package/dist/cjs/__tests__/services/events/collect-queue-tracking-service.spec.d.ts +1 -1
  108. package/dist/cjs/__tests__/services/events/collect-queue-tracking-service.spec.js +229 -229
  109. package/dist/cjs/__tests__/services/events/tracking-event-sqs-service.spec.d.ts +1 -1
  110. package/dist/cjs/__tests__/services/events/tracking-event-sqs-service.spec.js +191 -191
  111. package/dist/cjs/__tests__/shopify/shopify-graphql-transformer.spec.d.ts +1 -1
  112. package/dist/cjs/__tests__/shopify/shopify-graphql-transformer.spec.js +35 -35
  113. package/dist/cjs/__tests__/unit/libs/api-router/public-api-router.spec.d.ts +1 -1
  114. package/dist/cjs/__tests__/unit/libs/api-router/public-api-router.spec.js +181 -181
  115. package/dist/cjs/__tests__/unit/libs/api-router/route-matcher.spec.d.ts +1 -1
  116. package/dist/cjs/__tests__/unit/libs/api-router/route-matcher.spec.js +69 -69
  117. package/dist/cjs/__tests__/utils/custom-measure-formula-utils.spec.d.ts +1 -1
  118. package/dist/cjs/__tests__/utils/custom-measure-formula-utils.spec.js +146 -146
  119. package/dist/cjs/clients/generic/cognito-client.d.ts +23 -23
  120. package/dist/cjs/clients/generic/cognito-client.js +209 -209
  121. package/dist/cjs/clients/generic/dynamodb-client.d.ts +20 -20
  122. package/dist/cjs/clients/generic/dynamodb-client.js +235 -235
  123. package/dist/cjs/clients/generic/eventbridge-client.d.ts +14 -14
  124. package/dist/cjs/clients/generic/eventbridge-client.js +51 -51
  125. package/dist/cjs/clients/generic/http-client.d.ts +14 -14
  126. package/dist/cjs/clients/generic/http-client.js +61 -61
  127. package/dist/cjs/clients/generic/index.d.ts +13 -13
  128. package/dist/cjs/clients/generic/index.js +29 -29
  129. package/dist/cjs/clients/generic/lambda-invoke-client.d.ts +10 -10
  130. package/dist/cjs/clients/generic/lambda-invoke-client.js +39 -39
  131. package/dist/cjs/clients/generic/location-client.d.ts +8 -8
  132. package/dist/cjs/clients/generic/location-client.js +31 -31
  133. package/dist/cjs/clients/generic/redis-client.d.ts +33 -33
  134. package/dist/cjs/clients/generic/redis-client.js +191 -191
  135. package/dist/cjs/clients/generic/s3-client.d.ts +23 -23
  136. package/dist/cjs/clients/generic/s3-client.js +216 -216
  137. package/dist/cjs/clients/generic/singlestore-db-client.d.ts +14 -14
  138. package/dist/cjs/clients/generic/singlestore-db-client.js +67 -67
  139. package/dist/cjs/clients/generic/sqs-bundled-client.d.ts +15 -15
  140. package/dist/cjs/clients/generic/sqs-bundled-client.js +311 -311
  141. package/dist/cjs/clients/generic/sqs-bundled-client.types.d.ts +53 -53
  142. package/dist/cjs/clients/generic/sqs-bundled-client.types.js +17 -17
  143. package/dist/cjs/clients/generic/sqs-client.d.ts +53 -53
  144. package/dist/cjs/clients/generic/sqs-client.js +285 -285
  145. package/dist/cjs/clients/generic/sqs-unbundle.d.ts +32 -32
  146. package/dist/cjs/clients/generic/sqs-unbundle.js +144 -144
  147. package/dist/cjs/clients/index.d.ts +3 -3
  148. package/dist/cjs/clients/index.js +19 -19
  149. package/dist/cjs/clients/internal-api/accounts-client.d.ts +91 -91
  150. package/dist/cjs/clients/internal-api/accounts-client.js +129 -129
  151. package/dist/cjs/clients/internal-api/cache-lambda-client.d.ts +26 -26
  152. package/dist/cjs/clients/internal-api/cache-lambda-client.js +89 -89
  153. package/dist/cjs/clients/internal-api/db-management-client.d.ts +18 -18
  154. package/dist/cjs/clients/internal-api/db-management-client.js +36 -36
  155. package/dist/cjs/clients/internal-api/destinations-client.d.ts +34 -34
  156. package/dist/cjs/clients/internal-api/destinations-client.js +79 -79
  157. package/dist/cjs/clients/internal-api/event-collector-client.d.ts +122 -122
  158. package/dist/cjs/clients/internal-api/event-collector-client.js +78 -78
  159. package/dist/cjs/clients/internal-api/identity-client.d.ts +41 -41
  160. package/dist/cjs/clients/internal-api/identity-client.js +137 -137
  161. package/dist/cjs/clients/internal-api/index.d.ts +9 -9
  162. package/dist/cjs/clients/internal-api/index.js +25 -25
  163. package/dist/cjs/clients/internal-api/shopify-app-install-client.d.ts +37 -37
  164. package/dist/cjs/clients/internal-api/shopify-app-install-client.js +81 -81
  165. package/dist/cjs/clients/internal-api/subscriptions-client.d.ts +26 -26
  166. package/dist/cjs/clients/internal-api/subscriptions-client.js +77 -77
  167. package/dist/cjs/clients/internal-api/users-auth-client.d.ts +35 -35
  168. package/dist/cjs/clients/internal-api/users-auth-client.js +110 -110
  169. package/dist/cjs/clients/third-party/acuity-client.d.ts +10 -10
  170. package/dist/cjs/clients/third-party/acuity-client.js +40 -40
  171. package/dist/cjs/clients/third-party/emailable-client.d.ts +7 -7
  172. package/dist/cjs/clients/third-party/emailable-client.js +25 -25
  173. package/dist/cjs/clients/third-party/exchange-rate-api-client.d.ts +17 -17
  174. package/dist/cjs/clients/third-party/exchange-rate-api-client.js +19 -19
  175. package/dist/cjs/clients/third-party/index.d.ts +6 -6
  176. package/dist/cjs/clients/third-party/index.js +22 -22
  177. package/dist/cjs/clients/third-party/loops-client.d.ts +10 -10
  178. package/dist/cjs/clients/third-party/loops-client.js +30 -30
  179. package/dist/cjs/clients/third-party/open-exchange-rates-client.d.ts +8 -8
  180. package/dist/cjs/clients/third-party/open-exchange-rates-client.js +27 -27
  181. package/dist/cjs/clients/third-party/shopify/graphql-analytics-queries.d.ts +18 -18
  182. package/dist/cjs/clients/third-party/shopify/graphql-analytics-queries.js +22 -22
  183. package/dist/cjs/clients/third-party/shopify/graphql-order-queries.d.ts +25 -25
  184. package/dist/cjs/clients/third-party/shopify/graphql-order-queries.js +4 -4
  185. package/dist/cjs/clients/third-party/shopify/graphql-product-queries.d.ts +2 -2
  186. package/dist/cjs/clients/third-party/shopify/graphql-product-queries.js +5 -5
  187. package/dist/cjs/clients/third-party/shopify/shopify-graphql-client.d.ts +42 -42
  188. package/dist/cjs/clients/third-party/shopify/shopify-graphql-client.js +352 -352
  189. package/dist/cjs/clients/third-party/shopify-client.d.ts +29 -29
  190. package/dist/cjs/clients/third-party/shopify-client.js +146 -146
  191. package/dist/cjs/constants/index.d.ts +1 -1
  192. package/dist/cjs/constants/index.js +17 -17
  193. package/dist/cjs/constants/sqs.d.ts +20 -20
  194. package/dist/cjs/constants/sqs.js +26 -26
  195. package/dist/cjs/helpers/account-users-helper.d.ts +2 -2
  196. package/dist/cjs/helpers/account-users-helper.js +22 -22
  197. package/dist/cjs/helpers/acuity-helper.d.ts +4 -4
  198. package/dist/cjs/helpers/acuity-helper.js +56 -56
  199. package/dist/cjs/helpers/api-key-auth-helper.d.ts +9 -9
  200. package/dist/cjs/helpers/api-key-auth-helper.js +40 -40
  201. package/dist/cjs/helpers/api-key-authorizer-helper.d.ts +36 -36
  202. package/dist/cjs/helpers/api-key-authorizer-helper.js +87 -87
  203. package/dist/cjs/helpers/cognito-auth-helper.d.ts +5 -5
  204. package/dist/cjs/helpers/cognito-auth-helper.js +14 -14
  205. package/dist/cjs/helpers/index.d.ts +11 -11
  206. package/dist/cjs/helpers/index.js +27 -27
  207. package/dist/cjs/helpers/input-validation-helper.d.ts +3 -3
  208. package/dist/cjs/helpers/input-validation-helper.js +22 -22
  209. package/dist/cjs/helpers/logging-helper.d.ts +16 -16
  210. package/dist/cjs/helpers/logging-helper.js +84 -84
  211. package/dist/cjs/helpers/public-api-response-helper.d.ts +21 -21
  212. package/dist/cjs/helpers/public-api-response-helper.js +45 -45
  213. package/dist/cjs/helpers/response-helper.d.ts +18 -18
  214. package/dist/cjs/helpers/response-helper.js +43 -43
  215. package/dist/cjs/helpers/shopify-helper.d.ts +9 -9
  216. package/dist/cjs/helpers/shopify-helper.js +26 -26
  217. package/dist/cjs/helpers/sqs-utils.d.ts +6 -6
  218. package/dist/cjs/helpers/sqs-utils.js +14 -14
  219. package/dist/cjs/index.d.ts +7 -7
  220. package/dist/cjs/index.js +23 -23
  221. package/dist/cjs/libs/api-router/index.d.ts +2 -2
  222. package/dist/cjs/libs/api-router/index.js +18 -18
  223. package/dist/cjs/libs/api-router/public-api-router.d.ts +3 -3
  224. package/dist/cjs/libs/api-router/public-api-router.js +36 -36
  225. package/dist/cjs/libs/api-router/route-matcher.d.ts +21 -21
  226. package/dist/cjs/libs/api-router/route-matcher.js +36 -36
  227. package/dist/cjs/libs/click-id-parser.d.ts +23 -23
  228. package/dist/cjs/libs/click-id-parser.js +49 -49
  229. package/dist/cjs/libs/compression.d.ts +2 -2
  230. package/dist/cjs/libs/compression.js +33 -33
  231. package/dist/cjs/libs/contacts.d.ts +7 -7
  232. package/dist/cjs/libs/contacts.js +152 -152
  233. package/dist/cjs/libs/cookie.d.ts +17 -17
  234. package/dist/cjs/libs/cookie.js +76 -76
  235. package/dist/cjs/libs/crypto.d.ts +4 -4
  236. package/dist/cjs/libs/crypto.js +25 -25
  237. package/dist/cjs/libs/csv.d.ts +2 -2
  238. package/dist/cjs/libs/csv.js +35 -35
  239. package/dist/cjs/libs/currency.d.ts +1 -1
  240. package/dist/cjs/libs/currency.js +29 -29
  241. package/dist/cjs/libs/dates.d.ts +12 -12
  242. package/dist/cjs/libs/dates.js +96 -96
  243. package/dist/cjs/libs/domain.d.ts +2 -2
  244. package/dist/cjs/libs/domain.js +38 -38
  245. package/dist/cjs/libs/emails.d.ts +8 -8
  246. package/dist/cjs/libs/emails.js +154 -154
  247. package/dist/cjs/libs/http-error.d.ts +21 -21
  248. package/dist/cjs/libs/http-error.js +63 -63
  249. package/dist/cjs/libs/http-status-codes.d.ts +58 -58
  250. package/dist/cjs/libs/http-status-codes.js +62 -62
  251. package/dist/cjs/libs/index.d.ts +19 -19
  252. package/dist/cjs/libs/index.js +35 -35
  253. package/dist/cjs/libs/numbers.d.ts +1 -1
  254. package/dist/cjs/libs/numbers.js +15 -15
  255. package/dist/cjs/libs/referrer-parser/index.d.ts +2 -2
  256. package/dist/cjs/libs/referrer-parser/index.js +18 -18
  257. package/dist/cjs/libs/referrer-parser/referrer-data.d.ts +9 -9
  258. package/dist/cjs/libs/referrer-parser/referrer-data.js +3307 -3307
  259. package/dist/cjs/libs/referrer-parser/referrer-parser-util.d.ts +20 -20
  260. package/dist/cjs/libs/referrer-parser/referrer-parser-util.js +131 -131
  261. package/dist/cjs/libs/strings.d.ts +3 -3
  262. package/dist/cjs/libs/strings.js +46 -46
  263. package/dist/cjs/libs/traits.d.ts +6 -6
  264. package/dist/cjs/libs/traits.js +65 -65
  265. package/dist/cjs/libs/url.d.ts +1 -1
  266. package/dist/cjs/libs/url.js +13 -13
  267. package/dist/cjs/services/acuity-api-service.d.ts +9 -9
  268. package/dist/cjs/services/acuity-api-service.js +73 -73
  269. package/dist/cjs/services/cache/generic-cached-object.d.ts +5 -5
  270. package/dist/cjs/services/cache/generic-cached-object.js +2 -2
  271. package/dist/cjs/services/cache/index.d.ts +1 -1
  272. package/dist/cjs/services/cache/index.js +17 -17
  273. package/dist/cjs/services/cache/product-cache-service.d.ts +21 -21
  274. package/dist/cjs/services/cache/product-cache-service.js +76 -76
  275. package/dist/cjs/services/cost/cost-calculation-types.d.ts +69 -69
  276. package/dist/cjs/services/cost/cost-calculation-types.js +19 -19
  277. package/dist/cjs/services/cost/cost-calculator-service.d.ts +24 -24
  278. package/dist/cjs/services/cost/cost-calculator-service.js +461 -456
  279. package/dist/cjs/services/cost/cost-calculator-service.js.map +1 -1
  280. package/dist/cjs/services/cost/cost-currency-service.d.ts +6 -6
  281. package/dist/cjs/services/cost/cost-currency-service.js +87 -87
  282. package/dist/cjs/services/cost/cost-filter-service.d.ts +10 -10
  283. package/dist/cjs/services/cost/cost-filter-service.js +121 -121
  284. package/dist/cjs/services/cost/index.d.ts +5 -5
  285. package/dist/cjs/services/cost/index.js +21 -21
  286. package/dist/cjs/services/cost/order-cost/index.d.ts +2 -2
  287. package/dist/cjs/services/cost/order-cost/index.js +18 -18
  288. package/dist/cjs/services/cost/order-cost/order-cost-resolution-service.d.ts +26 -23
  289. package/dist/cjs/services/cost/order-cost/order-cost-resolution-service.js +403 -361
  290. package/dist/cjs/services/cost/order-cost/order-cost-resolution-service.js.map +1 -1
  291. package/dist/cjs/services/cost/order-cost/order-cost-resolution-types.d.ts +37 -37
  292. package/dist/cjs/services/cost/order-cost/order-cost-resolution-types.js +2 -2
  293. package/dist/cjs/services/currency-exchange-rate-lookup-service.d.ts +12 -12
  294. package/dist/cjs/services/currency-exchange-rate-lookup-service.js +94 -94
  295. package/dist/cjs/services/db/accounts-db-service.d.ts +9 -9
  296. package/dist/cjs/services/db/accounts-db-service.js +33 -33
  297. package/dist/cjs/services/db/api-keys-db-service.d.ts +10 -10
  298. package/dist/cjs/services/db/api-keys-db-service.js +36 -36
  299. package/dist/cjs/services/db/contact-enrichments-db-service.d.ts +15 -15
  300. package/dist/cjs/services/db/contact-enrichments-db-service.js +94 -94
  301. package/dist/cjs/services/db/currency-exchange-rates-db-service.d.ts +21 -21
  302. package/dist/cjs/services/db/currency-exchange-rates-db-service.js +39 -39
  303. package/dist/cjs/services/db/custom-measures-db-service.d.ts +14 -14
  304. package/dist/cjs/services/db/custom-measures-db-service.js +48 -48
  305. package/dist/cjs/services/db/destinations-db-service.d.ts +13 -13
  306. package/dist/cjs/services/db/destinations-db-service.js +74 -74
  307. package/dist/cjs/services/db/identity-cache-db-service.d.ts +28 -28
  308. package/dist/cjs/services/db/identity-cache-db-service.js +320 -320
  309. package/dist/cjs/services/db/identity-cache-dynamodb-service/constants.d.ts +3 -3
  310. package/dist/cjs/services/db/identity-cache-dynamodb-service/constants.js +6 -6
  311. package/dist/cjs/services/db/identity-cache-dynamodb-service/identity-cache-dynamodb-db-service.d.ts +20 -20
  312. package/dist/cjs/services/db/identity-cache-dynamodb-service/identity-cache-dynamodb-db-service.js +362 -362
  313. package/dist/cjs/services/db/identity-cache-dynamodb-service/identity-gateway-service.d.ts +23 -23
  314. package/dist/cjs/services/db/identity-cache-dynamodb-service/identity-gateway-service.js +222 -222
  315. package/dist/cjs/services/db/identity-cache-dynamodb-service/index.d.ts +4 -4
  316. package/dist/cjs/services/db/identity-cache-dynamodb-service/index.js +20 -20
  317. package/dist/cjs/services/db/identity-cache-dynamodb-service/key-builders.d.ts +12 -12
  318. package/dist/cjs/services/db/identity-cache-dynamodb-service/key-builders.js +31 -31
  319. package/dist/cjs/services/db/identity-cache-dynamodb-service/types.d.ts +71 -71
  320. package/dist/cjs/services/db/identity-cache-dynamodb-service/types.js +28 -28
  321. package/dist/cjs/services/db/index.d.ts +22 -22
  322. package/dist/cjs/services/db/index.js +38 -38
  323. package/dist/cjs/services/db/log-events-db-service.d.ts +11 -11
  324. package/dist/cjs/services/db/log-events-db-service.js +181 -181
  325. package/dist/cjs/services/db/pixels-db-service.d.ts +8 -8
  326. package/dist/cjs/services/db/pixels-db-service.js +35 -35
  327. package/dist/cjs/services/db/products-db-service-types.d.ts +10 -10
  328. package/dist/cjs/services/db/products-db-service-types.js +2 -2
  329. package/dist/cjs/services/db/products-db-service.d.ts +19 -19
  330. package/dist/cjs/services/db/products-db-service.js +281 -281
  331. package/dist/cjs/services/db/purchasable-contacts-db-service.d.ts +9 -9
  332. package/dist/cjs/services/db/purchasable-contacts-db-service.js +43 -43
  333. package/dist/cjs/services/db/purchased-contacts/index.d.ts +2 -2
  334. package/dist/cjs/services/db/purchased-contacts/index.js +18 -18
  335. package/dist/cjs/services/db/purchased-contacts/purchased-contacts-db-service.d.ts +18 -18
  336. package/dist/cjs/services/db/purchased-contacts/purchased-contacts-db-service.js +152 -152
  337. package/dist/cjs/services/db/purchased-contacts/types.d.ts +11 -11
  338. package/dist/cjs/services/db/purchased-contacts/types.js +2 -2
  339. package/dist/cjs/services/db/shopify-app-installs-db-service.d.ts +10 -10
  340. package/dist/cjs/services/db/shopify-app-installs-db-service.js +52 -52
  341. package/dist/cjs/services/db/shopify-products-cache-db-service.d.ts +16 -16
  342. package/dist/cjs/services/db/shopify-products-cache-db-service.js +73 -73
  343. package/dist/cjs/services/db/subscriptions-db-service.d.ts +11 -11
  344. package/dist/cjs/services/db/subscriptions-db-service.js +38 -38
  345. package/dist/cjs/services/db/tracking-events-db-service.d.ts +21 -21
  346. package/dist/cjs/services/db/tracking-events-db-service.js +188 -188
  347. package/dist/cjs/services/db/user-accounts-db-service.d.ts +7 -7
  348. package/dist/cjs/services/db/user-accounts-db-service.js +17 -17
  349. package/dist/cjs/services/email-verification/contact-email-verification-service.d.ts +7 -7
  350. package/dist/cjs/services/email-verification/contact-email-verification-service.js +101 -101
  351. package/dist/cjs/services/email-verification/email-verification-service.d.ts +19 -19
  352. package/dist/cjs/services/email-verification/email-verification-service.js +131 -131
  353. package/dist/cjs/services/email-verification/index.d.ts +2 -2
  354. package/dist/cjs/services/email-verification/index.js +18 -18
  355. package/dist/cjs/services/eventbridge-integration-service.d.ts +9 -9
  356. package/dist/cjs/services/eventbridge-integration-service.js +28 -28
  357. package/dist/cjs/services/events/build-collect-queue-tracking-event.d.ts +11 -11
  358. package/dist/cjs/services/events/build-collect-queue-tracking-event.js +23 -23
  359. package/dist/cjs/services/events/collect-queue-tracking-service.d.ts +12 -12
  360. package/dist/cjs/services/events/collect-queue-tracking-service.js +22 -22
  361. package/dist/cjs/services/events/index.d.ts +5 -5
  362. package/dist/cjs/services/events/index.js +21 -21
  363. package/dist/cjs/services/events/log-event-service.d.ts +19 -19
  364. package/dist/cjs/services/events/log-event-service.js +77 -77
  365. package/dist/cjs/services/events/metric-event-service.d.ts +9 -9
  366. package/dist/cjs/services/events/metric-event-service.js +49 -49
  367. package/dist/cjs/services/events/tracking-event-sqs-service.d.ts +8 -8
  368. package/dist/cjs/services/events/tracking-event-sqs-service.js +36 -36
  369. package/dist/cjs/services/generic-cache-service.d.ts +7 -7
  370. package/dist/cjs/services/generic-cache-service.js +33 -33
  371. package/dist/cjs/services/index.d.ts +11 -11
  372. package/dist/cjs/services/index.js +27 -27
  373. package/dist/cjs/services/ipdata-lookup-service.d.ts +20 -20
  374. package/dist/cjs/services/ipdata-lookup-service.js +112 -112
  375. package/dist/cjs/services/shopify/index.d.ts +2 -2
  376. package/dist/cjs/services/shopify/index.js +18 -18
  377. package/dist/cjs/services/shopify/products/index.d.ts +1 -1
  378. package/dist/cjs/services/shopify/products/index.js +17 -17
  379. package/dist/cjs/services/shopify/products/shopify-products-serviceV2.d.ts +17 -17
  380. package/dist/cjs/services/shopify/products/shopify-products-serviceV2.js +112 -112
  381. package/dist/cjs/services/shopify/shopify-graphql-transformer.d.ts +8 -8
  382. package/dist/cjs/services/shopify/shopify-graphql-transformer.js +141 -141
  383. package/dist/cjs/types/acuity-types.d.ts +74 -74
  384. package/dist/cjs/types/acuity-types.js +2 -2
  385. package/dist/cjs/types/api-response.d.ts +6 -6
  386. package/dist/cjs/types/api-response.js +2 -2
  387. package/dist/cjs/types/index.d.ts +6 -6
  388. package/dist/cjs/types/index.js +35 -35
  389. package/dist/cjs/types/internal-events/event-detail-types.d.ts +20 -20
  390. package/dist/cjs/types/internal-events/event-detail-types.js +27 -27
  391. package/dist/cjs/types/internal-events/index.d.ts +1 -1
  392. package/dist/cjs/types/internal-events/index.js +17 -17
  393. package/dist/cjs/types/open-exchange-rates-types.d.ts +10 -10
  394. package/dist/cjs/types/open-exchange-rates-types.js +2 -2
  395. package/dist/cjs/types/public-api-types.d.ts +24 -24
  396. package/dist/cjs/types/public-api-types.js +13 -13
  397. package/dist/cjs/types/shopify-graphql-types/admin.generated.d.ts +123 -123
  398. package/dist/cjs/types/shopify-graphql-types/admin.generated.js +2 -2
  399. package/dist/cjs/types/shopify-graphql-types/admin.types.d.ts +26289 -26289
  400. package/dist/cjs/types/shopify-graphql-types/admin.types.js +5311 -5311
  401. package/dist/cjs/types/shopify-graphql-types/index.d.ts +2 -2
  402. package/dist/cjs/types/shopify-graphql-types/index.js +18 -18
  403. package/dist/cjs/types/shopify-rest-types.d.ts +767 -767
  404. package/dist/cjs/types/shopify-rest-types.js +2 -2
  405. package/dist/cjs/utils/compression.d.ts +36 -36
  406. package/dist/cjs/utils/compression.js +198 -198
  407. package/dist/cjs/utils/custom-measure-formula-utils.d.ts +6 -6
  408. package/dist/cjs/utils/custom-measure-formula-utils.js +209 -209
  409. package/dist/cjs/utils/index.d.ts +4 -4
  410. package/dist/cjs/utils/index.js +20 -20
  411. package/dist/cjs/utils/retry-envelope.d.ts +12 -12
  412. package/dist/cjs/utils/retry-envelope.js +28 -28
  413. package/dist/cjs/utils/size.d.ts +2 -2
  414. package/dist/cjs/utils/size.js +49 -49
  415. package/dist/esm/__tests__/clients/acuity-client.spec.d.ts +1 -1
  416. package/dist/esm/__tests__/clients/acuity-client.spec.js +41 -41
  417. package/dist/esm/__tests__/clients/cross-platform-compression.spec.d.ts +1 -1
  418. package/dist/esm/__tests__/clients/cross-platform-compression.spec.js +329 -329
  419. package/dist/esm/__tests__/clients/dynamodb-client.spec.d.ts +1 -1
  420. package/dist/esm/__tests__/clients/dynamodb-client.spec.js +192 -192
  421. package/dist/esm/__tests__/clients/event-collector-client.spec.d.ts +1 -1
  422. package/dist/esm/__tests__/clients/event-collector-client.spec.js +225 -225
  423. package/dist/esm/__tests__/clients/open-exchange-rates-client.spec.d.ts +1 -1
  424. package/dist/esm/__tests__/clients/open-exchange-rates-client.spec.js +53 -53
  425. package/dist/esm/__tests__/clients/sqs-bundled-client.spec.d.ts +1 -1
  426. package/dist/esm/__tests__/clients/sqs-bundled-client.spec.js +906 -906
  427. package/dist/esm/__tests__/clients/sqs-bundling-contracts.spec.d.ts +1 -1
  428. package/dist/esm/__tests__/clients/sqs-bundling-contracts.spec.js +538 -538
  429. package/dist/esm/__tests__/clients/sqs-client.spec.d.ts +1 -1
  430. package/dist/esm/__tests__/clients/sqs-client.spec.js +189 -189
  431. package/dist/esm/__tests__/clients/sqs-unbundle.spec.d.ts +1 -1
  432. package/dist/esm/__tests__/clients/sqs-unbundle.spec.js +1355 -1355
  433. package/dist/esm/__tests__/db/contact-enrichments-db-service.spec.d.ts +1 -1
  434. package/dist/esm/__tests__/db/contact-enrichments-db-service.spec.js +66 -66
  435. package/dist/esm/__tests__/db/destinations-db-service.spec.d.ts +1 -1
  436. package/dist/esm/__tests__/db/destinations-db-service.spec.js +123 -123
  437. package/dist/esm/__tests__/db/products-db-service.spec.d.ts +1 -1
  438. package/dist/esm/__tests__/db/products-db-service.spec.js +87 -87
  439. package/dist/esm/__tests__/db/shared-read-db-services.spec.d.ts +1 -1
  440. package/dist/esm/__tests__/db/shared-read-db-services.spec.js +87 -87
  441. package/dist/esm/__tests__/db/shopify-app-installs-db-service.spec.d.ts +1 -1
  442. package/dist/esm/__tests__/db/shopify-app-installs-db-service.spec.js +102 -102
  443. package/dist/esm/__tests__/db/subscriptions-db-service.spec.d.ts +1 -1
  444. package/dist/esm/__tests__/db/subscriptions-db-service.spec.js +93 -93
  445. package/dist/esm/__tests__/db/user-accounts-db-service.spec.d.ts +1 -1
  446. package/dist/esm/__tests__/db/user-accounts-db-service.spec.js +74 -74
  447. package/dist/esm/__tests__/helpers/account-users-helper.spec.d.ts +1 -1
  448. package/dist/esm/__tests__/helpers/account-users-helper.spec.js +218 -218
  449. package/dist/esm/__tests__/helpers/acuity-helper.spec.d.ts +1 -1
  450. package/dist/esm/__tests__/helpers/acuity-helper.spec.js +67 -67
  451. package/dist/esm/__tests__/helpers/api-key-auth-helper.spec.d.ts +1 -1
  452. package/dist/esm/__tests__/helpers/api-key-auth-helper.spec.js +80 -80
  453. package/dist/esm/__tests__/helpers/cognito-auth-helper.spec.d.ts +1 -1
  454. package/dist/esm/__tests__/helpers/cognito-auth-helper.spec.js +44 -44
  455. package/dist/esm/__tests__/helpers/public-api-response-helper.spec.d.ts +1 -1
  456. package/dist/esm/__tests__/helpers/public-api-response-helper.spec.js +55 -55
  457. package/dist/esm/__tests__/identity-cache/helpers.spec.d.ts +1 -1
  458. package/dist/esm/__tests__/identity-cache/helpers.spec.js +590 -590
  459. package/dist/esm/__tests__/identity-cache/identity-cache-db-service.spec.d.ts +1 -1
  460. package/dist/esm/__tests__/identity-cache/identity-cache-db-service.spec.js +674 -674
  461. package/dist/esm/__tests__/identity-cache/identity-cache-dynamodb-db-service.spec.d.ts +1 -1
  462. package/dist/esm/__tests__/identity-cache/identity-cache-dynamodb-db-service.spec.js +553 -553
  463. package/dist/esm/__tests__/identity-cache/identity-cache-tier-routing.spec.d.ts +1 -1
  464. package/dist/esm/__tests__/identity-cache/identity-cache-tier-routing.spec.js +629 -629
  465. package/dist/esm/__tests__/identity-cache/identity-client.spec.d.ts +1 -1
  466. package/dist/esm/__tests__/identity-cache/identity-client.spec.js +357 -357
  467. package/dist/esm/__tests__/identity-cache/identity-gateway-cache-hit.spec.d.ts +1 -1
  468. package/dist/esm/__tests__/identity-cache/identity-gateway-cache-hit.spec.js +135 -135
  469. package/dist/esm/__tests__/identity-cache/identity-gateway-cache-miss.spec.d.ts +1 -1
  470. package/dist/esm/__tests__/identity-cache/identity-gateway-cache-miss.spec.js +150 -150
  471. package/dist/esm/__tests__/identity-cache/identity-gateway-constructor.spec.d.ts +1 -1
  472. package/dist/esm/__tests__/identity-cache/identity-gateway-constructor.spec.js +69 -69
  473. package/dist/esm/__tests__/identity-cache/identity-gateway-edge-cases.spec.d.ts +1 -1
  474. package/dist/esm/__tests__/identity-cache/identity-gateway-edge-cases.spec.js +86 -86
  475. package/dist/esm/__tests__/identity-cache/identity-gateway-enqueue-async.spec.d.ts +1 -1
  476. package/dist/esm/__tests__/identity-cache/identity-gateway-enqueue-async.spec.js +133 -133
  477. package/dist/esm/__tests__/identity-cache/identity-gateway-stale-cache.spec.d.ts +1 -1
  478. package/dist/esm/__tests__/identity-cache/identity-gateway-stale-cache.spec.js +221 -221
  479. package/dist/esm/__tests__/identity-cache/identity-gateway-test-setup.d.ts +28 -28
  480. package/dist/esm/__tests__/identity-cache/identity-gateway-test-setup.js +82 -82
  481. package/dist/esm/__tests__/identity-cache/trait-merging-and-staleness.spec.d.ts +1 -1
  482. package/dist/esm/__tests__/identity-cache/trait-merging-and-staleness.spec.js +1768 -1768
  483. package/dist/esm/__tests__/identity-cache/volatile-traits-optimization.spec.d.ts +1 -1
  484. package/dist/esm/__tests__/identity-cache/volatile-traits-optimization.spec.js +816 -816
  485. package/dist/esm/__tests__/integration/sqs-bundling-roundtrip.spec.d.ts +1 -1
  486. package/dist/esm/__tests__/integration/sqs-bundling-roundtrip.spec.js +582 -582
  487. package/dist/esm/__tests__/libs/compress-decompress.spec.d.ts +1 -1
  488. package/dist/esm/__tests__/libs/compress-decompress.spec.js +14 -14
  489. package/dist/esm/__tests__/libs/contacts.spec.d.ts +1 -1
  490. package/dist/esm/__tests__/libs/contacts.spec.js +292 -292
  491. package/dist/esm/__tests__/libs/currency.spec.d.ts +1 -1
  492. package/dist/esm/__tests__/libs/currency.spec.js +218 -218
  493. package/dist/esm/__tests__/libs/dates.spec.d.ts +1 -1
  494. package/dist/esm/__tests__/libs/dates.spec.js +128 -128
  495. package/dist/esm/__tests__/libs/domain.spec.d.ts +1 -1
  496. package/dist/esm/__tests__/libs/domain.spec.js +105 -105
  497. package/dist/esm/__tests__/libs/numbers.spec.d.ts +1 -1
  498. package/dist/esm/__tests__/libs/numbers.spec.js +259 -259
  499. package/dist/esm/__tests__/s3-client/s3-client.spec.d.ts +1 -1
  500. package/dist/esm/__tests__/s3-client/s3-client.spec.js +31 -31
  501. package/dist/esm/__tests__/services/acuity-api-service.spec.d.ts +1 -1
  502. package/dist/esm/__tests__/services/acuity-api-service.spec.js +69 -69
  503. package/dist/esm/__tests__/services/cost/cost-calculation-types.spec.d.ts +1 -1
  504. package/dist/esm/__tests__/services/cost/cost-calculation-types.spec.js +21 -21
  505. package/dist/esm/__tests__/services/cost/cost-calculator-service.spec.d.ts +1 -1
  506. package/dist/esm/__tests__/services/cost/cost-calculator-service.spec.js +3347 -3317
  507. package/dist/esm/__tests__/services/cost/cost-calculator-service.spec.js.map +1 -1
  508. package/dist/esm/__tests__/services/cost/cost-currency-service.spec.d.ts +1 -1
  509. package/dist/esm/__tests__/services/cost/cost-currency-service.spec.js +112 -112
  510. package/dist/esm/__tests__/services/cost/cost-filter-service.spec.d.ts +1 -1
  511. package/dist/esm/__tests__/services/cost/cost-filter-service.spec.js +466 -466
  512. package/dist/esm/__tests__/services/cost/order-cost/order-cost-resolution-service.spec.d.ts +1 -1
  513. package/dist/esm/__tests__/services/cost/order-cost/order-cost-resolution-service.spec.js +358 -204
  514. package/dist/esm/__tests__/services/cost/order-cost/order-cost-resolution-service.spec.js.map +1 -1
  515. package/dist/esm/__tests__/services/currency-exchange-rate-lookup-service.spec.d.ts +1 -1
  516. package/dist/esm/__tests__/services/currency-exchange-rate-lookup-service.spec.js +32 -32
  517. package/dist/esm/__tests__/services/email-verification/contact-email-verification-service.spec.d.ts +1 -1
  518. package/dist/esm/__tests__/services/email-verification/contact-email-verification-service.spec.js +91 -91
  519. package/dist/esm/__tests__/services/email-verification/email-verification-service.spec.d.ts +1 -1
  520. package/dist/esm/__tests__/services/email-verification/email-verification-service.spec.js +55 -55
  521. package/dist/esm/__tests__/services/events/collect-queue-tracking-service.spec.d.ts +1 -1
  522. package/dist/esm/__tests__/services/events/collect-queue-tracking-service.spec.js +227 -227
  523. package/dist/esm/__tests__/services/events/tracking-event-sqs-service.spec.d.ts +1 -1
  524. package/dist/esm/__tests__/services/events/tracking-event-sqs-service.spec.js +189 -189
  525. package/dist/esm/__tests__/shopify/shopify-graphql-transformer.spec.d.ts +1 -1
  526. package/dist/esm/__tests__/shopify/shopify-graphql-transformer.spec.js +33 -33
  527. package/dist/esm/__tests__/unit/libs/api-router/public-api-router.spec.d.ts +1 -1
  528. package/dist/esm/__tests__/unit/libs/api-router/public-api-router.spec.js +156 -156
  529. package/dist/esm/__tests__/unit/libs/api-router/route-matcher.spec.d.ts +1 -1
  530. package/dist/esm/__tests__/unit/libs/api-router/route-matcher.spec.js +67 -67
  531. package/dist/esm/__tests__/utils/custom-measure-formula-utils.spec.d.ts +1 -1
  532. package/dist/esm/__tests__/utils/custom-measure-formula-utils.spec.js +144 -144
  533. package/dist/esm/clients/generic/cognito-client.d.ts +23 -23
  534. package/dist/esm/clients/generic/cognito-client.js +204 -204
  535. package/dist/esm/clients/generic/dynamodb-client.d.ts +20 -20
  536. package/dist/esm/clients/generic/dynamodb-client.js +231 -231
  537. package/dist/esm/clients/generic/eventbridge-client.d.ts +14 -14
  538. package/dist/esm/clients/generic/eventbridge-client.js +47 -47
  539. package/dist/esm/clients/generic/http-client.d.ts +14 -14
  540. package/dist/esm/clients/generic/http-client.js +53 -53
  541. package/dist/esm/clients/generic/index.d.ts +13 -13
  542. package/dist/esm/clients/generic/index.js +13 -13
  543. package/dist/esm/clients/generic/lambda-invoke-client.d.ts +10 -10
  544. package/dist/esm/clients/generic/lambda-invoke-client.js +35 -35
  545. package/dist/esm/clients/generic/location-client.d.ts +8 -8
  546. package/dist/esm/clients/generic/location-client.js +27 -27
  547. package/dist/esm/clients/generic/redis-client.d.ts +33 -33
  548. package/dist/esm/clients/generic/redis-client.js +184 -184
  549. package/dist/esm/clients/generic/s3-client.d.ts +23 -23
  550. package/dist/esm/clients/generic/s3-client.js +209 -209
  551. package/dist/esm/clients/generic/singlestore-db-client.d.ts +14 -14
  552. package/dist/esm/clients/generic/singlestore-db-client.js +40 -40
  553. package/dist/esm/clients/generic/sqs-bundled-client.d.ts +15 -15
  554. package/dist/esm/clients/generic/sqs-bundled-client.js +307 -307
  555. package/dist/esm/clients/generic/sqs-bundled-client.types.d.ts +53 -53
  556. package/dist/esm/clients/generic/sqs-bundled-client.types.js +14 -14
  557. package/dist/esm/clients/generic/sqs-client.d.ts +53 -53
  558. package/dist/esm/clients/generic/sqs-client.js +281 -281
  559. package/dist/esm/clients/generic/sqs-unbundle.d.ts +32 -32
  560. package/dist/esm/clients/generic/sqs-unbundle.js +137 -137
  561. package/dist/esm/clients/index.d.ts +3 -3
  562. package/dist/esm/clients/index.js +3 -3
  563. package/dist/esm/clients/internal-api/accounts-client.d.ts +91 -91
  564. package/dist/esm/clients/internal-api/accounts-client.js +125 -125
  565. package/dist/esm/clients/internal-api/cache-lambda-client.d.ts +26 -26
  566. package/dist/esm/clients/internal-api/cache-lambda-client.js +85 -85
  567. package/dist/esm/clients/internal-api/db-management-client.d.ts +18 -18
  568. package/dist/esm/clients/internal-api/db-management-client.js +32 -32
  569. package/dist/esm/clients/internal-api/destinations-client.d.ts +34 -34
  570. package/dist/esm/clients/internal-api/destinations-client.js +75 -75
  571. package/dist/esm/clients/internal-api/event-collector-client.d.ts +122 -122
  572. package/dist/esm/clients/internal-api/event-collector-client.js +74 -74
  573. package/dist/esm/clients/internal-api/identity-client.d.ts +41 -41
  574. package/dist/esm/clients/internal-api/identity-client.js +133 -133
  575. package/dist/esm/clients/internal-api/index.d.ts +9 -9
  576. package/dist/esm/clients/internal-api/index.js +9 -9
  577. package/dist/esm/clients/internal-api/shopify-app-install-client.d.ts +37 -37
  578. package/dist/esm/clients/internal-api/shopify-app-install-client.js +77 -77
  579. package/dist/esm/clients/internal-api/subscriptions-client.d.ts +26 -26
  580. package/dist/esm/clients/internal-api/subscriptions-client.js +73 -73
  581. package/dist/esm/clients/internal-api/users-auth-client.d.ts +35 -35
  582. package/dist/esm/clients/internal-api/users-auth-client.js +106 -106
  583. package/dist/esm/clients/third-party/acuity-client.d.ts +10 -10
  584. package/dist/esm/clients/third-party/acuity-client.js +36 -36
  585. package/dist/esm/clients/third-party/emailable-client.d.ts +7 -7
  586. package/dist/esm/clients/third-party/emailable-client.js +21 -21
  587. package/dist/esm/clients/third-party/exchange-rate-api-client.d.ts +17 -17
  588. package/dist/esm/clients/third-party/exchange-rate-api-client.js +15 -15
  589. package/dist/esm/clients/third-party/index.d.ts +6 -6
  590. package/dist/esm/clients/third-party/index.js +6 -6
  591. package/dist/esm/clients/third-party/loops-client.d.ts +10 -10
  592. package/dist/esm/clients/third-party/loops-client.js +26 -26
  593. package/dist/esm/clients/third-party/open-exchange-rates-client.d.ts +8 -8
  594. package/dist/esm/clients/third-party/open-exchange-rates-client.js +23 -23
  595. package/dist/esm/clients/third-party/shopify/graphql-analytics-queries.d.ts +18 -18
  596. package/dist/esm/clients/third-party/shopify/graphql-analytics-queries.js +19 -19
  597. package/dist/esm/clients/third-party/shopify/graphql-order-queries.d.ts +25 -25
  598. package/dist/esm/clients/third-party/shopify/graphql-order-queries.js +1 -1
  599. package/dist/esm/clients/third-party/shopify/graphql-product-queries.d.ts +2 -2
  600. package/dist/esm/clients/third-party/shopify/graphql-product-queries.js +2 -2
  601. package/dist/esm/clients/third-party/shopify/shopify-graphql-client.d.ts +42 -42
  602. package/dist/esm/clients/third-party/shopify/shopify-graphql-client.js +348 -348
  603. package/dist/esm/clients/third-party/shopify-client.d.ts +29 -29
  604. package/dist/esm/clients/third-party/shopify-client.js +142 -142
  605. package/dist/esm/constants/index.d.ts +1 -1
  606. package/dist/esm/constants/index.js +1 -1
  607. package/dist/esm/constants/sqs.d.ts +20 -20
  608. package/dist/esm/constants/sqs.js +22 -22
  609. package/dist/esm/helpers/account-users-helper.d.ts +2 -2
  610. package/dist/esm/helpers/account-users-helper.js +18 -18
  611. package/dist/esm/helpers/acuity-helper.d.ts +4 -4
  612. package/dist/esm/helpers/acuity-helper.js +51 -51
  613. package/dist/esm/helpers/api-key-auth-helper.d.ts +9 -9
  614. package/dist/esm/helpers/api-key-auth-helper.js +35 -35
  615. package/dist/esm/helpers/api-key-authorizer-helper.d.ts +36 -36
  616. package/dist/esm/helpers/api-key-authorizer-helper.js +83 -83
  617. package/dist/esm/helpers/cognito-auth-helper.d.ts +5 -5
  618. package/dist/esm/helpers/cognito-auth-helper.js +10 -10
  619. package/dist/esm/helpers/index.d.ts +11 -11
  620. package/dist/esm/helpers/index.js +11 -11
  621. package/dist/esm/helpers/input-validation-helper.d.ts +3 -3
  622. package/dist/esm/helpers/input-validation-helper.js +18 -18
  623. package/dist/esm/helpers/logging-helper.d.ts +16 -16
  624. package/dist/esm/helpers/logging-helper.js +56 -56
  625. package/dist/esm/helpers/public-api-response-helper.d.ts +21 -21
  626. package/dist/esm/helpers/public-api-response-helper.js +38 -38
  627. package/dist/esm/helpers/response-helper.d.ts +18 -18
  628. package/dist/esm/helpers/response-helper.js +37 -37
  629. package/dist/esm/helpers/shopify-helper.d.ts +9 -9
  630. package/dist/esm/helpers/shopify-helper.js +21 -21
  631. package/dist/esm/helpers/sqs-utils.d.ts +6 -6
  632. package/dist/esm/helpers/sqs-utils.js +9 -9
  633. package/dist/esm/index.d.ts +7 -7
  634. package/dist/esm/index.js +7 -7
  635. package/dist/esm/libs/api-router/index.d.ts +2 -2
  636. package/dist/esm/libs/api-router/index.js +2 -2
  637. package/dist/esm/libs/api-router/public-api-router.d.ts +3 -3
  638. package/dist/esm/libs/api-router/public-api-router.js +32 -32
  639. package/dist/esm/libs/api-router/route-matcher.d.ts +21 -21
  640. package/dist/esm/libs/api-router/route-matcher.js +30 -30
  641. package/dist/esm/libs/click-id-parser.d.ts +23 -23
  642. package/dist/esm/libs/click-id-parser.js +45 -45
  643. package/dist/esm/libs/compression.d.ts +2 -2
  644. package/dist/esm/libs/compression.js +25 -25
  645. package/dist/esm/libs/contacts.d.ts +7 -7
  646. package/dist/esm/libs/contacts.js +143 -143
  647. package/dist/esm/libs/cookie.d.ts +17 -17
  648. package/dist/esm/libs/cookie.js +70 -70
  649. package/dist/esm/libs/crypto.d.ts +4 -4
  650. package/dist/esm/libs/crypto.js +15 -15
  651. package/dist/esm/libs/csv.d.ts +2 -2
  652. package/dist/esm/libs/csv.js +30 -30
  653. package/dist/esm/libs/currency.d.ts +1 -1
  654. package/dist/esm/libs/currency.js +22 -22
  655. package/dist/esm/libs/dates.d.ts +12 -12
  656. package/dist/esm/libs/dates.js +83 -83
  657. package/dist/esm/libs/domain.d.ts +2 -2
  658. package/dist/esm/libs/domain.js +33 -33
  659. package/dist/esm/libs/emails.d.ts +8 -8
  660. package/dist/esm/libs/emails.js +146 -146
  661. package/dist/esm/libs/http-error.d.ts +21 -21
  662. package/dist/esm/libs/http-error.js +59 -59
  663. package/dist/esm/libs/http-status-codes.d.ts +58 -58
  664. package/dist/esm/libs/http-status-codes.js +59 -59
  665. package/dist/esm/libs/index.d.ts +19 -19
  666. package/dist/esm/libs/index.js +19 -19
  667. package/dist/esm/libs/numbers.d.ts +1 -1
  668. package/dist/esm/libs/numbers.js +11 -11
  669. package/dist/esm/libs/referrer-parser/index.d.ts +2 -2
  670. package/dist/esm/libs/referrer-parser/index.js +2 -2
  671. package/dist/esm/libs/referrer-parser/referrer-data.d.ts +9 -9
  672. package/dist/esm/libs/referrer-parser/referrer-data.js +3304 -3304
  673. package/dist/esm/libs/referrer-parser/referrer-parser-util.d.ts +20 -20
  674. package/dist/esm/libs/referrer-parser/referrer-parser-util.js +124 -124
  675. package/dist/esm/libs/strings.d.ts +3 -3
  676. package/dist/esm/libs/strings.js +40 -40
  677. package/dist/esm/libs/traits.d.ts +6 -6
  678. package/dist/esm/libs/traits.js +54 -54
  679. package/dist/esm/libs/url.d.ts +1 -1
  680. package/dist/esm/libs/url.js +9 -9
  681. package/dist/esm/services/acuity-api-service.d.ts +9 -9
  682. package/dist/esm/services/acuity-api-service.js +69 -69
  683. package/dist/esm/services/cache/generic-cached-object.d.ts +5 -5
  684. package/dist/esm/services/cache/generic-cached-object.js +1 -1
  685. package/dist/esm/services/cache/index.d.ts +1 -1
  686. package/dist/esm/services/cache/index.js +1 -1
  687. package/dist/esm/services/cache/product-cache-service.d.ts +21 -21
  688. package/dist/esm/services/cache/product-cache-service.js +68 -68
  689. package/dist/esm/services/cost/cost-calculation-types.d.ts +69 -69
  690. package/dist/esm/services/cost/cost-calculation-types.js +15 -15
  691. package/dist/esm/services/cost/cost-calculator-service.d.ts +24 -24
  692. package/dist/esm/services/cost/cost-calculator-service.js +455 -450
  693. package/dist/esm/services/cost/cost-calculator-service.js.map +1 -1
  694. package/dist/esm/services/cost/cost-currency-service.d.ts +6 -6
  695. package/dist/esm/services/cost/cost-currency-service.js +84 -84
  696. package/dist/esm/services/cost/cost-filter-service.d.ts +10 -10
  697. package/dist/esm/services/cost/cost-filter-service.js +118 -118
  698. package/dist/esm/services/cost/index.d.ts +5 -5
  699. package/dist/esm/services/cost/index.js +5 -5
  700. package/dist/esm/services/cost/order-cost/index.d.ts +2 -2
  701. package/dist/esm/services/cost/order-cost/index.js +2 -2
  702. package/dist/esm/services/cost/order-cost/order-cost-resolution-service.d.ts +26 -23
  703. package/dist/esm/services/cost/order-cost/order-cost-resolution-service.js +397 -355
  704. package/dist/esm/services/cost/order-cost/order-cost-resolution-service.js.map +1 -1
  705. package/dist/esm/services/cost/order-cost/order-cost-resolution-types.d.ts +37 -37
  706. package/dist/esm/services/cost/order-cost/order-cost-resolution-types.js +1 -1
  707. package/dist/esm/services/currency-exchange-rate-lookup-service.d.ts +12 -12
  708. package/dist/esm/services/currency-exchange-rate-lookup-service.js +90 -90
  709. package/dist/esm/services/db/accounts-db-service.d.ts +9 -9
  710. package/dist/esm/services/db/accounts-db-service.js +29 -29
  711. package/dist/esm/services/db/api-keys-db-service.d.ts +10 -10
  712. package/dist/esm/services/db/api-keys-db-service.js +32 -32
  713. package/dist/esm/services/db/contact-enrichments-db-service.d.ts +15 -15
  714. package/dist/esm/services/db/contact-enrichments-db-service.js +90 -90
  715. package/dist/esm/services/db/currency-exchange-rates-db-service.d.ts +21 -21
  716. package/dist/esm/services/db/currency-exchange-rates-db-service.js +35 -35
  717. package/dist/esm/services/db/custom-measures-db-service.d.ts +14 -14
  718. package/dist/esm/services/db/custom-measures-db-service.js +44 -44
  719. package/dist/esm/services/db/destinations-db-service.d.ts +13 -13
  720. package/dist/esm/services/db/destinations-db-service.js +70 -70
  721. package/dist/esm/services/db/identity-cache-db-service.d.ts +28 -28
  722. package/dist/esm/services/db/identity-cache-db-service.js +313 -313
  723. package/dist/esm/services/db/identity-cache-dynamodb-service/constants.d.ts +3 -3
  724. package/dist/esm/services/db/identity-cache-dynamodb-service/constants.js +3 -3
  725. package/dist/esm/services/db/identity-cache-dynamodb-service/identity-cache-dynamodb-db-service.d.ts +20 -20
  726. package/dist/esm/services/db/identity-cache-dynamodb-service/identity-cache-dynamodb-db-service.js +358 -358
  727. package/dist/esm/services/db/identity-cache-dynamodb-service/identity-gateway-service.d.ts +23 -23
  728. package/dist/esm/services/db/identity-cache-dynamodb-service/identity-gateway-service.js +218 -218
  729. package/dist/esm/services/db/identity-cache-dynamodb-service/index.d.ts +4 -4
  730. package/dist/esm/services/db/identity-cache-dynamodb-service/index.js +4 -4
  731. package/dist/esm/services/db/identity-cache-dynamodb-service/key-builders.d.ts +12 -12
  732. package/dist/esm/services/db/identity-cache-dynamodb-service/key-builders.js +23 -23
  733. package/dist/esm/services/db/identity-cache-dynamodb-service/types.d.ts +71 -71
  734. package/dist/esm/services/db/identity-cache-dynamodb-service/types.js +25 -25
  735. package/dist/esm/services/db/index.d.ts +22 -22
  736. package/dist/esm/services/db/index.js +22 -22
  737. package/dist/esm/services/db/log-events-db-service.d.ts +11 -11
  738. package/dist/esm/services/db/log-events-db-service.js +177 -177
  739. package/dist/esm/services/db/pixels-db-service.d.ts +8 -8
  740. package/dist/esm/services/db/pixels-db-service.js +31 -31
  741. package/dist/esm/services/db/products-db-service-types.d.ts +10 -10
  742. package/dist/esm/services/db/products-db-service-types.js +1 -1
  743. package/dist/esm/services/db/products-db-service.d.ts +19 -19
  744. package/dist/esm/services/db/products-db-service.js +277 -277
  745. package/dist/esm/services/db/purchasable-contacts-db-service.d.ts +9 -9
  746. package/dist/esm/services/db/purchasable-contacts-db-service.js +39 -39
  747. package/dist/esm/services/db/purchased-contacts/index.d.ts +2 -2
  748. package/dist/esm/services/db/purchased-contacts/index.js +2 -2
  749. package/dist/esm/services/db/purchased-contacts/purchased-contacts-db-service.d.ts +18 -18
  750. package/dist/esm/services/db/purchased-contacts/purchased-contacts-db-service.js +148 -148
  751. package/dist/esm/services/db/purchased-contacts/types.d.ts +11 -11
  752. package/dist/esm/services/db/purchased-contacts/types.js +1 -1
  753. package/dist/esm/services/db/shopify-app-installs-db-service.d.ts +10 -10
  754. package/dist/esm/services/db/shopify-app-installs-db-service.js +48 -48
  755. package/dist/esm/services/db/shopify-products-cache-db-service.d.ts +16 -16
  756. package/dist/esm/services/db/shopify-products-cache-db-service.js +66 -66
  757. package/dist/esm/services/db/subscriptions-db-service.d.ts +11 -11
  758. package/dist/esm/services/db/subscriptions-db-service.js +34 -34
  759. package/dist/esm/services/db/tracking-events-db-service.d.ts +21 -21
  760. package/dist/esm/services/db/tracking-events-db-service.js +184 -184
  761. package/dist/esm/services/db/user-accounts-db-service.d.ts +7 -7
  762. package/dist/esm/services/db/user-accounts-db-service.js +13 -13
  763. package/dist/esm/services/email-verification/contact-email-verification-service.d.ts +7 -7
  764. package/dist/esm/services/email-verification/contact-email-verification-service.js +97 -97
  765. package/dist/esm/services/email-verification/email-verification-service.d.ts +19 -19
  766. package/dist/esm/services/email-verification/email-verification-service.js +127 -127
  767. package/dist/esm/services/email-verification/index.d.ts +2 -2
  768. package/dist/esm/services/email-verification/index.js +2 -2
  769. package/dist/esm/services/eventbridge-integration-service.d.ts +9 -9
  770. package/dist/esm/services/eventbridge-integration-service.js +24 -24
  771. package/dist/esm/services/events/build-collect-queue-tracking-event.d.ts +11 -11
  772. package/dist/esm/services/events/build-collect-queue-tracking-event.js +19 -19
  773. package/dist/esm/services/events/collect-queue-tracking-service.d.ts +12 -12
  774. package/dist/esm/services/events/collect-queue-tracking-service.js +18 -18
  775. package/dist/esm/services/events/index.d.ts +5 -5
  776. package/dist/esm/services/events/index.js +5 -5
  777. package/dist/esm/services/events/log-event-service.d.ts +19 -19
  778. package/dist/esm/services/events/log-event-service.js +73 -73
  779. package/dist/esm/services/events/metric-event-service.d.ts +9 -9
  780. package/dist/esm/services/events/metric-event-service.js +45 -45
  781. package/dist/esm/services/events/tracking-event-sqs-service.d.ts +8 -8
  782. package/dist/esm/services/events/tracking-event-sqs-service.js +32 -32
  783. package/dist/esm/services/generic-cache-service.d.ts +7 -7
  784. package/dist/esm/services/generic-cache-service.js +29 -29
  785. package/dist/esm/services/index.d.ts +11 -11
  786. package/dist/esm/services/index.js +11 -11
  787. package/dist/esm/services/ipdata-lookup-service.d.ts +20 -20
  788. package/dist/esm/services/ipdata-lookup-service.js +108 -108
  789. package/dist/esm/services/shopify/index.d.ts +2 -2
  790. package/dist/esm/services/shopify/index.js +2 -2
  791. package/dist/esm/services/shopify/products/index.d.ts +1 -1
  792. package/dist/esm/services/shopify/products/index.js +1 -1
  793. package/dist/esm/services/shopify/products/shopify-products-serviceV2.d.ts +17 -17
  794. package/dist/esm/services/shopify/products/shopify-products-serviceV2.js +108 -108
  795. package/dist/esm/services/shopify/shopify-graphql-transformer.d.ts +8 -8
  796. package/dist/esm/services/shopify/shopify-graphql-transformer.js +138 -138
  797. package/dist/esm/types/acuity-types.d.ts +74 -74
  798. package/dist/esm/types/acuity-types.js +1 -1
  799. package/dist/esm/types/api-response.d.ts +6 -6
  800. package/dist/esm/types/api-response.js +1 -1
  801. package/dist/esm/types/index.d.ts +6 -6
  802. package/dist/esm/types/index.js +6 -6
  803. package/dist/esm/types/internal-events/event-detail-types.d.ts +20 -20
  804. package/dist/esm/types/internal-events/event-detail-types.js +24 -24
  805. package/dist/esm/types/internal-events/index.d.ts +1 -1
  806. package/dist/esm/types/internal-events/index.js +1 -1
  807. package/dist/esm/types/open-exchange-rates-types.d.ts +10 -10
  808. package/dist/esm/types/open-exchange-rates-types.js +1 -1
  809. package/dist/esm/types/public-api-types.d.ts +24 -24
  810. package/dist/esm/types/public-api-types.js +10 -10
  811. package/dist/esm/types/shopify-graphql-types/admin.generated.d.ts +123 -123
  812. package/dist/esm/types/shopify-graphql-types/admin.generated.js +1 -1
  813. package/dist/esm/types/shopify-graphql-types/admin.types.d.ts +26289 -26289
  814. package/dist/esm/types/shopify-graphql-types/admin.types.js +5299 -5299
  815. package/dist/esm/types/shopify-graphql-types/index.d.ts +2 -2
  816. package/dist/esm/types/shopify-graphql-types/index.js +2 -2
  817. package/dist/esm/types/shopify-rest-types.d.ts +767 -767
  818. package/dist/esm/types/shopify-rest-types.js +1 -1
  819. package/dist/esm/utils/compression.d.ts +36 -36
  820. package/dist/esm/utils/compression.js +187 -187
  821. package/dist/esm/utils/custom-measure-formula-utils.d.ts +6 -6
  822. package/dist/esm/utils/custom-measure-formula-utils.js +201 -201
  823. package/dist/esm/utils/index.d.ts +4 -4
  824. package/dist/esm/utils/index.js +4 -4
  825. package/dist/esm/utils/retry-envelope.d.ts +12 -12
  826. package/dist/esm/utils/retry-envelope.js +22 -22
  827. package/dist/esm/utils/size.d.ts +2 -2
  828. package/dist/esm/utils/size.js +44 -44
  829. package/package.json +136 -136
@@ -1,583 +1,583 @@
1
- import { BundledSQSClient } from '../../clients/generic/sqs-bundled-client';
2
- import { CompressionAlgorithm } from '../../clients/generic/sqs-bundled-client.types';
3
- import { unbundleRecords } from '../../clients/generic/sqs-unbundle';
4
- import { compress } from '../../utils/compression';
5
- import { createSqsLimits, SQS_1MB } from '../../constants/sqs';
6
- jest.mock('../../helpers/logging-helper', () => ({
7
- Logger: {
8
- debug: jest.fn(),
9
- info: jest.fn(),
10
- warn: jest.fn(),
11
- error: jest.fn(),
12
- },
13
- }));
14
- function makeTestEvent(id, name = 'test', value, metadata) {
15
- return { id, name, value, metadata };
16
- }
17
- function makeRealisticTrackingEvent(index) {
18
- return {
19
- anonymousId: `anon-${index}-${Math.random().toString(36).substring(7)}`,
20
- accountId: `acc-${index % 10}`,
21
- pixelId: `pixel-${index % 5}`,
22
- eventType: ['track', 'identify', 'page'][index % 3] ?? 'track',
23
- eventName: ['purchase', 'add_to_cart', 'page_view', 'begin_checkout'][index % 4] ?? 'track',
24
- timestamp: new Date(Date.now() - index * 1000).toISOString(),
25
- context: {
26
- page: {
27
- url: `https://example.com/product/${index}`,
28
- path: `/product/${index}`,
29
- title: `Product ${index} - Example Store`,
30
- referrer: index % 3 === 0 ? 'https://google.com' : '',
31
- },
32
- userAgent: 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 Safari/537.36',
33
- ip: `192.168.${index % 256}.${(index * 7) % 256}`,
34
- locale: ['en-US', 'en-GB', 'de-DE', 'fr-FR'][index % 4] ?? 'en-US',
35
- timezone: 'America/New_York',
36
- },
37
- properties: {
38
- productId: `prod-${index}`,
39
- productName: `Amazing Product ${index}`,
40
- price: 29.99 + (index % 100),
41
- currency: 'USD',
42
- quantity: (index % 5) + 1,
43
- category: ['Electronics', 'Clothing', 'Home', 'Sports'][index % 4],
44
- customFields: {
45
- brand: `Brand${index % 20}`,
46
- sku: `SKU-${index}-${Date.now()}`,
47
- inStock: index % 2 === 0,
48
- },
49
- },
50
- shopifyData: index % 3 === 0
51
- ? {
52
- checkoutToken: `checkout-${index}`,
53
- orderId: index % 5 === 0 ? `order-${index}` : undefined,
54
- customerEmail: `customer${index}@example.com`,
55
- lineItems: Array.from({ length: (index % 3) + 1 }, (_, j) => ({
56
- variantId: `variant-${index}-${j}`,
57
- title: `Line Item ${j}`,
58
- price: 19.99 + j * 10,
59
- quantity: j + 1,
60
- })),
61
- }
62
- : undefined,
63
- };
64
- }
65
- function simulateSqsDelivery(envelopes) {
66
- return envelopes.map((env, i) => ({
67
- messageId: `msg-${i}-${Date.now()}`,
68
- body: JSON.stringify({ messageBody: env }),
69
- }));
70
- }
71
- describe('Full Round-Trip: Producer → Consumer', () => {
72
- let mockSqsClient;
73
- let capturedEnvelopes;
74
- beforeEach(() => {
75
- capturedEnvelopes = [];
76
- mockSqsClient = {
77
- buildAndSendMessagesV2: jest.fn(async (_type, envelopes) => {
78
- capturedEnvelopes.push(...envelopes);
79
- return {
80
- successCount: envelopes.length,
81
- failedCount: 0,
82
- batchCount: 1,
83
- failedMessages: [],
84
- };
85
- }),
86
- queueUrl: 'https://sqs.us-east-1.amazonaws.com/123456789/test-queue',
87
- limits: createSqsLimits(SQS_1MB),
88
- };
89
- });
90
- describe('1. Basic round-trip test (100 items)', () => {
91
- it('100 items survive complete round-trip with deep equality', async () => {
92
- const bundledClient = new BundledSQSClient(mockSqsClient, {
93
- compression: CompressionAlgorithm.ZSTD,
94
- compressionLevel: 3,
95
- });
96
- const originalItems = Array.from({ length: 100 }, (_, i) => ({
97
- id: `event-${i}`,
98
- name: 'purchase',
99
- value: i * 99.99,
100
- metadata: { source: 'test', index: i },
101
- }));
102
- await bundledClient.sendBundled('test', originalItems);
103
- expect(capturedEnvelopes.length).toBeGreaterThanOrEqual(1);
104
- const sqsRecords = simulateSqsDelivery(capturedEnvelopes);
105
- const { items: recoveredItems, stats } = await unbundleRecords(sqsRecords);
106
- expect(recoveredItems).toHaveLength(100);
107
- expect(recoveredItems).toEqual(originalItems);
108
- expect(stats.bundledSqsRecords).toBe(capturedEnvelopes.length);
109
- expect(stats.failedRecords).toBe(0);
110
- });
111
- it('preserves all primitive types correctly', async () => {
112
- const bundledClient = new BundledSQSClient(mockSqsClient, {
113
- compression: CompressionAlgorithm.ZSTD,
114
- });
115
- const originalItems = [
116
- { id: 'str', name: 'string-test', value: undefined },
117
- { id: 'num', name: 'number-test', value: 123.456 },
118
- { id: 'zero', name: 'zero-test', value: 0 },
119
- { id: 'neg', name: 'negative-test', value: -999.99 },
120
- { id: 'big', name: 'big-number', value: Number.MAX_SAFE_INTEGER },
121
- ];
122
- await bundledClient.sendBundled('test', originalItems);
123
- const sqsRecords = simulateSqsDelivery(capturedEnvelopes);
124
- const { items: recoveredItems } = await unbundleRecords(sqsRecords);
125
- expect(recoveredItems).toEqual(originalItems);
126
- });
127
- });
128
- describe('2. Large scale round-trip (1000 items)', () => {
129
- it('1000 items survive round-trip with no data loss', async () => {
130
- const bundledClient = new BundledSQSClient(mockSqsClient, {
131
- compression: CompressionAlgorithm.ZSTD,
132
- compressionLevel: 3,
133
- });
134
- const originalItems = Array.from({ length: 1000 }, (_, i) => ({
135
- id: `event-${i.toString().padStart(4, '0')}`,
136
- name: `type-${i % 10}`,
137
- value: i * 1.5,
138
- metadata: {
139
- batch: Math.floor(i / 100),
140
- position: i % 100,
141
- timestamp: Date.now() + i,
142
- },
143
- }));
144
- await bundledClient.sendBundled('test', originalItems);
145
- const sqsRecords = simulateSqsDelivery(capturedEnvelopes);
146
- const { items: recoveredItems, stats } = await unbundleRecords(sqsRecords);
147
- expect(recoveredItems).toHaveLength(1000);
148
- expect(stats.totalItems).toBe(1000);
149
- expect(stats.failedRecords).toBe(0);
150
- const recoveredIds = recoveredItems.map((item) => item.id);
151
- const originalIds = originalItems.map((item) => item.id);
152
- expect(new Set(recoveredIds)).toEqual(new Set(originalIds));
153
- expect(recoveredItems).toEqual(originalItems);
154
- });
155
- it('preserves order within each bundle', async () => {
156
- const bundledClient = new BundledSQSClient(mockSqsClient, {
157
- compression: CompressionAlgorithm.ZSTD,
158
- maxItemsPerBundle: 100,
159
- });
160
- const originalItems = Array.from({ length: 500 }, (_, i) => makeTestEvent(`seq-${i}`, 'ordered', i));
161
- await bundledClient.sendBundled('test', originalItems);
162
- const sqsRecords = simulateSqsDelivery(capturedEnvelopes);
163
- const { items: recoveredItems } = await unbundleRecords(sqsRecords);
164
- let currentBundleStart = 0;
165
- for (const envelope of capturedEnvelopes) {
166
- const bundleSize = envelope.n;
167
- const bundleItems = recoveredItems.slice(currentBundleStart, currentBundleStart + bundleSize);
168
- for (let j = 1; j < bundleItems.length; j++) {
169
- const prevValue = bundleItems[j - 1]?.value ?? 0;
170
- const currValue = bundleItems[j]?.value ?? 0;
171
- expect(currValue).toBeGreaterThan(prevValue);
172
- }
173
- currentBundleStart += bundleSize;
174
- }
175
- });
176
- });
177
- describe('3. Compression round-trip verification', () => {
178
- it('ZSTD compressed data decompresses to byte-exact JSON', async () => {
179
- const bundledClient = new BundledSQSClient(mockSqsClient, {
180
- compression: CompressionAlgorithm.ZSTD,
181
- compressionLevel: 5,
182
- });
183
- const originalItems = Array.from({ length: 50 }, (_, i) => ({
184
- id: `compress-test-${i}`,
185
- name: 'compression-verification',
186
- value: i * 123.456789,
187
- metadata: {
188
- unicode: '日本語テスト',
189
- emoji: '🚀✨🎉',
190
- special: 'line\nbreak\ttab\r\nwindows',
191
- quotes: '"double" and \'single\'',
192
- },
193
- }));
194
- const originalJson = JSON.stringify(originalItems);
195
- await bundledClient.sendBundled('test', originalItems);
196
- const sqsRecords = simulateSqsDelivery(capturedEnvelopes);
197
- const { items: recoveredItems } = await unbundleRecords(sqsRecords);
198
- const recoveredJson = JSON.stringify(recoveredItems);
199
- expect(recoveredJson).toBe(originalJson);
200
- expect(recoveredItems).toEqual(originalItems);
201
- });
202
- it('verifies actual compression occurred', async () => {
203
- const bundledClient = new BundledSQSClient(mockSqsClient, {
204
- compression: CompressionAlgorithm.ZSTD,
205
- compressionLevel: 3,
206
- });
207
- const originalItems = Array.from({ length: 200 }, (_, i) => ({
208
- id: `item-${i}`,
209
- name: 'repetitive-data-for-compression',
210
- value: i,
211
- metadata: {
212
- commonField1: 'this is repeated many times',
213
- commonField2: 'another repeated value',
214
- },
215
- }));
216
- const originalSizeBytes = Buffer.byteLength(JSON.stringify(originalItems), 'utf8');
217
- await bundledClient.sendBundled('test', originalItems);
218
- for (const envelope of capturedEnvelopes) {
219
- expect(envelope.c).toBe(CompressionAlgorithm.ZSTD);
220
- expect(typeof envelope.p).toBe('string');
221
- const compressedSizeBytes = Buffer.byteLength(envelope.p, 'utf8');
222
- expect(compressedSizeBytes).toBeLessThan(originalSizeBytes);
223
- }
224
- });
225
- });
226
- describe('4. Mixed message types round-trip', () => {
227
- it('handles mix of NONE and ZSTD compression in same batch', async () => {
228
- const zstdClient = new BundledSQSClient(mockSqsClient, {
229
- compression: CompressionAlgorithm.ZSTD,
230
- });
231
- const noneClient = new BundledSQSClient(mockSqsClient, {
232
- compression: CompressionAlgorithm.NONE,
233
- });
234
- const zstdItems = [
235
- makeTestEvent('zstd-1', 'compressed', 100),
236
- makeTestEvent('zstd-2', 'compressed', 200),
237
- ];
238
- const noneItems = [
239
- makeTestEvent('none-1', 'uncompressed', 300),
240
- makeTestEvent('none-2', 'uncompressed', 400),
241
- ];
242
- await zstdClient.sendBundled('test', zstdItems);
243
- const zstdEnvelopes = [...capturedEnvelopes];
244
- capturedEnvelopes = [];
245
- await noneClient.sendBundled('test', noneItems);
246
- const noneEnvelopes = [...capturedEnvelopes];
247
- const allEnvelopes = [...zstdEnvelopes, ...noneEnvelopes];
248
- const sqsRecords = simulateSqsDelivery(allEnvelopes);
249
- const { items: recoveredItems, stats } = await unbundleRecords(sqsRecords);
250
- expect(recoveredItems).toHaveLength(4);
251
- expect(stats.bundledSqsRecords).toBe(2);
252
- expect(stats.failedRecords).toBe(0);
253
- const zstdRecovered = recoveredItems.filter((item) => item.name === 'compressed');
254
- const noneRecovered = recoveredItems.filter((item) => item.name === 'uncompressed');
255
- expect(zstdRecovered).toHaveLength(2);
256
- expect(noneRecovered).toHaveLength(2);
257
- expect(zstdRecovered).toEqual(zstdItems);
258
- expect(noneRecovered).toEqual(noneItems);
259
- });
260
- it('handles mixed bundled and legacy messages', async () => {
261
- const bundledClient = new BundledSQSClient(mockSqsClient, {
262
- compression: CompressionAlgorithm.ZSTD,
263
- });
264
- const bundledItems = [
265
- makeTestEvent('bundled-1', 'bundled', 100),
266
- makeTestEvent('bundled-2', 'bundled', 200),
267
- ];
268
- await bundledClient.sendBundled('test', bundledItems);
269
- const legacyRecord = {
270
- messageId: 'legacy-msg-1',
271
- body: JSON.stringify(makeTestEvent('legacy-1', 'legacy', 999)),
272
- };
273
- const wrappedLegacyRecord = {
274
- messageId: 'legacy-msg-2',
275
- body: JSON.stringify({ messageBody: makeTestEvent('legacy-2', 'wrapped-legacy', 888) }),
276
- };
277
- const bundledRecords = simulateSqsDelivery(capturedEnvelopes);
278
- const allRecords = [...bundledRecords, legacyRecord, wrappedLegacyRecord];
279
- const { items: recoveredItems, stats } = await unbundleRecords(allRecords);
280
- expect(recoveredItems).toHaveLength(4);
281
- expect(stats.bundledSqsRecords).toBe(1);
282
- expect(stats.legacySqsRecords).toBe(2);
283
- expect(stats.failedRecords).toBe(0);
284
- });
285
- });
286
- describe('5. Error injection round-trip', () => {
287
- it('recovers valid bundles while reporting corrupted bundle in failedMessageIds', async () => {
288
- const bundledClient = new BundledSQSClient(mockSqsClient, {
289
- compression: CompressionAlgorithm.ZSTD,
290
- });
291
- const validItems1 = [makeTestEvent('valid-1', 'first-batch', 100)];
292
- const validItems2 = [makeTestEvent('valid-2', 'second-batch', 200)];
293
- await bundledClient.sendBundled('test', validItems1);
294
- const envelope1 = { ...capturedEnvelopes[0] };
295
- capturedEnvelopes = [];
296
- await bundledClient.sendBundled('test', validItems2);
297
- const envelope2 = { ...capturedEnvelopes[0] };
298
- const corruptedEnvelope = {
299
- v: 1,
300
- c: CompressionAlgorithm.ZSTD,
301
- n: 10,
302
- s: 1000,
303
- p: 'dGhpcyBpcyBub3QgdmFsaWQgenN0ZA==',
304
- };
305
- const records = [
306
- { messageId: 'valid-1', body: JSON.stringify({ messageBody: envelope1 }) },
307
- { messageId: 'corrupted', body: JSON.stringify({ messageBody: corruptedEnvelope }) },
308
- { messageId: 'valid-2', body: JSON.stringify({ messageBody: envelope2 }) },
309
- ];
310
- const { items: recoveredItems, failedMessageIds, stats } = await unbundleRecords(records);
311
- expect(recoveredItems).toHaveLength(2);
312
- expect(recoveredItems[0]?.id).toBe('valid-1');
313
- expect(recoveredItems[1]?.id).toBe('valid-2');
314
- expect(failedMessageIds).toContain('corrupted');
315
- expect(failedMessageIds).toHaveLength(1);
316
- expect(stats.bundledSqsRecords).toBe(2);
317
- expect(stats.failedRecords).toBe(1);
318
- expect(stats.totalItems).toBe(2);
319
- });
320
- it('handles invalid JSON gracefully', async () => {
321
- const bundledClient = new BundledSQSClient(mockSqsClient, {
322
- compression: CompressionAlgorithm.ZSTD,
323
- });
324
- const validItems = [makeTestEvent('valid', 'test', 100)];
325
- await bundledClient.sendBundled('test', validItems);
326
- const records = [
327
- ...simulateSqsDelivery(capturedEnvelopes),
328
- { messageId: 'invalid-json-1', body: 'not-valid-json{{{' },
329
- { messageId: 'invalid-json-2', body: '{"incomplete":' },
330
- { messageId: 'empty', body: '' },
331
- ];
332
- const { items: recoveredItems, failedMessageIds, stats } = await unbundleRecords(records);
333
- expect(recoveredItems).toHaveLength(1);
334
- expect(recoveredItems[0]?.id).toBe('valid');
335
- expect(failedMessageIds).toContain('invalid-json-1');
336
- expect(failedMessageIds).toContain('invalid-json-2');
337
- expect(failedMessageIds).toContain('empty');
338
- expect(failedMessageIds).toHaveLength(3);
339
- expect(stats.failedRecords).toBe(3);
340
- });
341
- it('handles decompression bomb protection', async () => {
342
- const largeItems = Array.from({ length: 1000 }, (_, i) => ({
343
- id: `item-${i}`,
344
- data: 'x'.repeat(1000),
345
- }));
346
- const json = JSON.stringify(largeItems);
347
- const compressed = await compress(Buffer.from(json, 'utf8'), CompressionAlgorithm.ZSTD, 3);
348
- const base64 = compressed.toString('base64');
349
- const bigEnvelope = {
350
- v: 1,
351
- c: CompressionAlgorithm.ZSTD,
352
- n: 1000,
353
- s: json.length,
354
- p: base64,
355
- };
356
- const records = [{ messageId: 'too-large', body: JSON.stringify({ messageBody: bigEnvelope }) }];
357
- const { failedMessageIds, stats } = await unbundleRecords(records, {
358
- maxDecompressedSizeBytes: 100 * 1024,
359
- });
360
- expect(failedMessageIds).toContain('too-large');
361
- expect(stats.failedRecords).toBe(1);
362
- });
363
- });
364
- describe('6. Realistic event types round-trip', () => {
365
- it('TrackingEvent-like structures survive round-trip exactly', async () => {
366
- const realisticMockSqs = {
367
- buildAndSendMessagesV2: jest.fn(async (_type, envelopes) => {
368
- capturedEnvelopes = [];
369
- capturedEnvelopes.push(...envelopes);
370
- return {
371
- successCount: envelopes.length,
372
- failedCount: 0,
373
- batchCount: 1,
374
- failedMessages: [],
375
- };
376
- }),
377
- queueUrl: 'https://sqs.us-east-1.amazonaws.com/123456789/test-queue',
378
- limits: createSqsLimits(SQS_1MB),
379
- };
380
- const bundledClient = new BundledSQSClient(realisticMockSqs, {
381
- compression: CompressionAlgorithm.ZSTD,
382
- compressionLevel: 3,
383
- });
384
- const originalEvents = Array.from({ length: 100 }, (_, i) => makeRealisticTrackingEvent(i));
385
- await bundledClient.sendBundled('tracking-events', originalEvents);
386
- const sqsRecords = simulateSqsDelivery(capturedEnvelopes);
387
- const { items: recoveredEvents, stats } = await unbundleRecords(sqsRecords);
388
- expect(recoveredEvents).toHaveLength(100);
389
- expect(stats.failedRecords).toBe(0);
390
- expect(recoveredEvents).toEqual(originalEvents);
391
- for (let i = 0; i < originalEvents.length; i++) {
392
- const original = originalEvents[i];
393
- const recovered = recoveredEvents[i];
394
- expect(recovered?.anonymousId).toBe(original?.anonymousId);
395
- expect(recovered?.context.page.url).toBe(original?.context.page.url);
396
- expect(recovered?.properties.price).toBe(original?.properties.price);
397
- if (original?.shopifyData) {
398
- expect(recovered?.shopifyData).toEqual(original.shopifyData);
399
- }
400
- }
401
- });
402
- it('preserves nested object structures exactly', async () => {
403
- const bundledClient = new BundledSQSClient(mockSqsClient, {
404
- compression: CompressionAlgorithm.ZSTD,
405
- });
406
- const deeplyNestedItems = [
407
- {
408
- id: 'nested-1',
409
- name: 'deep-nesting',
410
- nested: {
411
- level1: {
412
- level2: {
413
- deep: 'very deep value',
414
- },
415
- },
416
- },
417
- },
418
- {
419
- id: 'nested-2',
420
- name: 'with-arrays',
421
- tags: ['tag1', 'tag2', 'tag3'],
422
- metadata: {
423
- array: [1, 2, 3],
424
- object: { a: 1, b: 2 },
425
- mixed: [{ key: 'value' }, [1, 2, 3]],
426
- },
427
- },
428
- ];
429
- await bundledClient.sendBundled('test', deeplyNestedItems);
430
- const sqsRecords = simulateSqsDelivery(capturedEnvelopes);
431
- const { items: recoveredItems } = await unbundleRecords(sqsRecords);
432
- expect(recoveredItems).toEqual(deeplyNestedItems);
433
- expect(recoveredItems[0]?.nested?.level1.level2.deep).toBe('very deep value');
434
- expect(recoveredItems[1]?.tags).toEqual(['tag1', 'tag2', 'tag3']);
435
- });
436
- });
437
- describe('7. High compression ratio round-trip', () => {
438
- it('highly repetitive data compresses and decompresses correctly', async () => {
439
- const bundledClient = new BundledSQSClient(mockSqsClient, {
440
- compression: CompressionAlgorithm.ZSTD,
441
- compressionLevel: 3,
442
- });
443
- const repetitiveString = 'AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA';
444
- const originalItems = Array.from({ length: 200 }, (_, i) => ({
445
- id: `repetitive-${i}`,
446
- name: repetitiveString,
447
- value: 42,
448
- metadata: {
449
- field1: repetitiveString,
450
- field2: repetitiveString,
451
- field3: repetitiveString,
452
- field4: repetitiveString,
453
- field5: repetitiveString,
454
- },
455
- }));
456
- const originalSizeBytes = Buffer.byteLength(JSON.stringify(originalItems), 'utf8');
457
- await bundledClient.sendBundled('test', originalItems);
458
- let totalCompressedSize = 0;
459
- for (const envelope of capturedEnvelopes) {
460
- expect(typeof envelope.p).toBe('string');
461
- totalCompressedSize += Buffer.byteLength(envelope.p, 'utf8');
462
- }
463
- const compressionRatio = originalSizeBytes / totalCompressedSize;
464
- expect(compressionRatio).toBeGreaterThan(5);
465
- const sqsRecords = simulateSqsDelivery(capturedEnvelopes);
466
- const { items: recoveredItems, stats } = await unbundleRecords(sqsRecords);
467
- expect(recoveredItems).toHaveLength(200);
468
- expect(recoveredItems).toEqual(originalItems);
469
- expect(stats.failedRecords).toBe(0);
470
- for (const item of recoveredItems) {
471
- expect(item.name).toBe(repetitiveString);
472
- expect(item.value).toBe(42);
473
- expect(item.metadata?.field1).toBe(repetitiveString);
474
- }
475
- });
476
- it('varying compression levels all round-trip correctly', async () => {
477
- const items = Array.from({ length: 50 }, (_, i) => makeTestEvent(`level-test-${i}`, 'compression-level', i));
478
- for (const level of [1, 3, 9, 15]) {
479
- capturedEnvelopes = [];
480
- const bundledClient = new BundledSQSClient(mockSqsClient, {
481
- compression: CompressionAlgorithm.ZSTD,
482
- compressionLevel: level,
483
- });
484
- await bundledClient.sendBundled('test', items);
485
- const sqsRecords = simulateSqsDelivery(capturedEnvelopes);
486
- const { items: recoveredItems, stats } = await unbundleRecords(sqsRecords);
487
- expect(recoveredItems).toEqual(items);
488
- expect(stats.failedRecords).toBe(0);
489
- }
490
- });
491
- });
492
- describe('8. Edge cases', () => {
493
- it('empty arrays survive round-trip', async () => {
494
- const bundledClient = new BundledSQSClient(mockSqsClient, {
495
- compression: CompressionAlgorithm.ZSTD,
496
- });
497
- const result = await bundledClient.sendBundled('test', []);
498
- expect(result.totalItems).toBe(0);
499
- expect(capturedEnvelopes).toHaveLength(0);
500
- });
501
- it('single item survives round-trip', async () => {
502
- const bundledClient = new BundledSQSClient(mockSqsClient, {
503
- compression: CompressionAlgorithm.ZSTD,
504
- });
505
- const singleItem = [makeTestEvent('single', 'lone-wolf', 999)];
506
- await bundledClient.sendBundled('test', singleItem);
507
- const sqsRecords = simulateSqsDelivery(capturedEnvelopes);
508
- const { items: recoveredItems } = await unbundleRecords(sqsRecords);
509
- expect(recoveredItems).toHaveLength(1);
510
- expect(recoveredItems).toEqual(singleItem);
511
- });
512
- it('special characters survive round-trip', async () => {
513
- const bundledClient = new BundledSQSClient(mockSqsClient, {
514
- compression: CompressionAlgorithm.ZSTD,
515
- });
516
- const specialCharsItems = [
517
- {
518
- id: 'unicode-日本語',
519
- name: '中文测试',
520
- metadata: {
521
- emoji: '🎉🚀✨💯',
522
- rtl: 'مرحبا بالعالم',
523
- escape: '\\n\\t\\r',
524
- quotes: '"double" \'single\' `backtick`',
525
- angle: '<script>alert("xss")</script>',
526
- null_char: 'before\x00after',
527
- },
528
- },
529
- ];
530
- await bundledClient.sendBundled('test', specialCharsItems);
531
- const sqsRecords = simulateSqsDelivery(capturedEnvelopes);
532
- const { items: recoveredItems } = await unbundleRecords(sqsRecords);
533
- expect(recoveredItems).toEqual(specialCharsItems);
534
- });
535
- it('null and undefined values are handled correctly', async () => {
536
- const bundledClient = new BundledSQSClient(mockSqsClient, {
537
- compression: CompressionAlgorithm.ZSTD,
538
- });
539
- const itemsWithNulls = [
540
- { id: 'null-test', name: 'test', value: undefined },
541
- {
542
- id: 'explicit-null',
543
- name: 'test',
544
- metadata: { key: null },
545
- },
546
- ];
547
- await bundledClient.sendBundled('test', itemsWithNulls);
548
- const sqsRecords = simulateSqsDelivery(capturedEnvelopes);
549
- const { items: recoveredItems } = await unbundleRecords(sqsRecords);
550
- expect(recoveredItems[0]?.value).toBeUndefined();
551
- expect(recoveredItems[1]?.metadata?.key).toBeNull();
552
- });
553
- it('recordMap correctly tracks items back to SQS messages', async () => {
554
- const bundledClient = new BundledSQSClient(mockSqsClient, {
555
- compression: CompressionAlgorithm.ZSTD,
556
- maxItemsPerBundle: 3,
557
- });
558
- const items = Array.from({ length: 10 }, (_, i) => makeTestEvent(`item-${i}`, 'tracking', i));
559
- await bundledClient.sendBundled('test', items);
560
- const sqsRecords = capturedEnvelopes.map((env, i) => ({
561
- messageId: `bundle-${i}`,
562
- body: JSON.stringify({ messageBody: env }),
563
- }));
564
- const { items: recoveredItems, recordMap, stats } = await unbundleRecords(sqsRecords);
565
- expect(recoveredItems).toHaveLength(10);
566
- const messageIdCounts = new Map();
567
- for (const item of recoveredItems) {
568
- const messageId = recordMap.get(item);
569
- expect(messageId).toBeDefined();
570
- if (messageId) {
571
- messageIdCounts.set(messageId, (messageIdCounts.get(messageId) ?? 0) + 1);
572
- }
573
- }
574
- expect(messageIdCounts.size).toBe(capturedEnvelopes.length);
575
- for (const [messageId, count] of messageIdCounts) {
576
- expect(count).toBeLessThanOrEqual(3);
577
- expect(messageId).toMatch(/^bundle-\d+$/);
578
- }
579
- expect(stats.bundledSqsRecords).toBe(capturedEnvelopes.length);
580
- });
581
- });
582
- });
1
+ import { BundledSQSClient } from '../../clients/generic/sqs-bundled-client';
2
+ import { CompressionAlgorithm } from '../../clients/generic/sqs-bundled-client.types';
3
+ import { unbundleRecords } from '../../clients/generic/sqs-unbundle';
4
+ import { compress } from '../../utils/compression';
5
+ import { createSqsLimits, SQS_1MB } from '../../constants/sqs';
6
+ jest.mock('../../helpers/logging-helper', () => ({
7
+ Logger: {
8
+ debug: jest.fn(),
9
+ info: jest.fn(),
10
+ warn: jest.fn(),
11
+ error: jest.fn(),
12
+ },
13
+ }));
14
+ function makeTestEvent(id, name = 'test', value, metadata) {
15
+ return { id, name, value, metadata };
16
+ }
17
+ function makeRealisticTrackingEvent(index) {
18
+ return {
19
+ anonymousId: `anon-${index}-${Math.random().toString(36).substring(7)}`,
20
+ accountId: `acc-${index % 10}`,
21
+ pixelId: `pixel-${index % 5}`,
22
+ eventType: ['track', 'identify', 'page'][index % 3] ?? 'track',
23
+ eventName: ['purchase', 'add_to_cart', 'page_view', 'begin_checkout'][index % 4] ?? 'track',
24
+ timestamp: new Date(Date.now() - index * 1000).toISOString(),
25
+ context: {
26
+ page: {
27
+ url: `https://example.com/product/${index}`,
28
+ path: `/product/${index}`,
29
+ title: `Product ${index} - Example Store`,
30
+ referrer: index % 3 === 0 ? 'https://google.com' : '',
31
+ },
32
+ userAgent: 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 Safari/537.36',
33
+ ip: `192.168.${index % 256}.${(index * 7) % 256}`,
34
+ locale: ['en-US', 'en-GB', 'de-DE', 'fr-FR'][index % 4] ?? 'en-US',
35
+ timezone: 'America/New_York',
36
+ },
37
+ properties: {
38
+ productId: `prod-${index}`,
39
+ productName: `Amazing Product ${index}`,
40
+ price: 29.99 + (index % 100),
41
+ currency: 'USD',
42
+ quantity: (index % 5) + 1,
43
+ category: ['Electronics', 'Clothing', 'Home', 'Sports'][index % 4],
44
+ customFields: {
45
+ brand: `Brand${index % 20}`,
46
+ sku: `SKU-${index}-${Date.now()}`,
47
+ inStock: index % 2 === 0,
48
+ },
49
+ },
50
+ shopifyData: index % 3 === 0
51
+ ? {
52
+ checkoutToken: `checkout-${index}`,
53
+ orderId: index % 5 === 0 ? `order-${index}` : undefined,
54
+ customerEmail: `customer${index}@example.com`,
55
+ lineItems: Array.from({ length: (index % 3) + 1 }, (_, j) => ({
56
+ variantId: `variant-${index}-${j}`,
57
+ title: `Line Item ${j}`,
58
+ price: 19.99 + j * 10,
59
+ quantity: j + 1,
60
+ })),
61
+ }
62
+ : undefined,
63
+ };
64
+ }
65
+ function simulateSqsDelivery(envelopes) {
66
+ return envelopes.map((env, i) => ({
67
+ messageId: `msg-${i}-${Date.now()}`,
68
+ body: JSON.stringify({ messageBody: env }),
69
+ }));
70
+ }
71
+ describe('Full Round-Trip: Producer → Consumer', () => {
72
+ let mockSqsClient;
73
+ let capturedEnvelopes;
74
+ beforeEach(() => {
75
+ capturedEnvelopes = [];
76
+ mockSqsClient = {
77
+ buildAndSendMessagesV2: jest.fn(async (_type, envelopes) => {
78
+ capturedEnvelopes.push(...envelopes);
79
+ return {
80
+ successCount: envelopes.length,
81
+ failedCount: 0,
82
+ batchCount: 1,
83
+ failedMessages: [],
84
+ };
85
+ }),
86
+ queueUrl: 'https://sqs.us-east-1.amazonaws.com/123456789/test-queue',
87
+ limits: createSqsLimits(SQS_1MB),
88
+ };
89
+ });
90
+ describe('1. Basic round-trip test (100 items)', () => {
91
+ it('100 items survive complete round-trip with deep equality', async () => {
92
+ const bundledClient = new BundledSQSClient(mockSqsClient, {
93
+ compression: CompressionAlgorithm.ZSTD,
94
+ compressionLevel: 3,
95
+ });
96
+ const originalItems = Array.from({ length: 100 }, (_, i) => ({
97
+ id: `event-${i}`,
98
+ name: 'purchase',
99
+ value: i * 99.99,
100
+ metadata: { source: 'test', index: i },
101
+ }));
102
+ await bundledClient.sendBundled('test', originalItems);
103
+ expect(capturedEnvelopes.length).toBeGreaterThanOrEqual(1);
104
+ const sqsRecords = simulateSqsDelivery(capturedEnvelopes);
105
+ const { items: recoveredItems, stats } = await unbundleRecords(sqsRecords);
106
+ expect(recoveredItems).toHaveLength(100);
107
+ expect(recoveredItems).toEqual(originalItems);
108
+ expect(stats.bundledSqsRecords).toBe(capturedEnvelopes.length);
109
+ expect(stats.failedRecords).toBe(0);
110
+ });
111
+ it('preserves all primitive types correctly', async () => {
112
+ const bundledClient = new BundledSQSClient(mockSqsClient, {
113
+ compression: CompressionAlgorithm.ZSTD,
114
+ });
115
+ const originalItems = [
116
+ { id: 'str', name: 'string-test', value: undefined },
117
+ { id: 'num', name: 'number-test', value: 123.456 },
118
+ { id: 'zero', name: 'zero-test', value: 0 },
119
+ { id: 'neg', name: 'negative-test', value: -999.99 },
120
+ { id: 'big', name: 'big-number', value: Number.MAX_SAFE_INTEGER },
121
+ ];
122
+ await bundledClient.sendBundled('test', originalItems);
123
+ const sqsRecords = simulateSqsDelivery(capturedEnvelopes);
124
+ const { items: recoveredItems } = await unbundleRecords(sqsRecords);
125
+ expect(recoveredItems).toEqual(originalItems);
126
+ });
127
+ });
128
+ describe('2. Large scale round-trip (1000 items)', () => {
129
+ it('1000 items survive round-trip with no data loss', async () => {
130
+ const bundledClient = new BundledSQSClient(mockSqsClient, {
131
+ compression: CompressionAlgorithm.ZSTD,
132
+ compressionLevel: 3,
133
+ });
134
+ const originalItems = Array.from({ length: 1000 }, (_, i) => ({
135
+ id: `event-${i.toString().padStart(4, '0')}`,
136
+ name: `type-${i % 10}`,
137
+ value: i * 1.5,
138
+ metadata: {
139
+ batch: Math.floor(i / 100),
140
+ position: i % 100,
141
+ timestamp: Date.now() + i,
142
+ },
143
+ }));
144
+ await bundledClient.sendBundled('test', originalItems);
145
+ const sqsRecords = simulateSqsDelivery(capturedEnvelopes);
146
+ const { items: recoveredItems, stats } = await unbundleRecords(sqsRecords);
147
+ expect(recoveredItems).toHaveLength(1000);
148
+ expect(stats.totalItems).toBe(1000);
149
+ expect(stats.failedRecords).toBe(0);
150
+ const recoveredIds = recoveredItems.map((item) => item.id);
151
+ const originalIds = originalItems.map((item) => item.id);
152
+ expect(new Set(recoveredIds)).toEqual(new Set(originalIds));
153
+ expect(recoveredItems).toEqual(originalItems);
154
+ });
155
+ it('preserves order within each bundle', async () => {
156
+ const bundledClient = new BundledSQSClient(mockSqsClient, {
157
+ compression: CompressionAlgorithm.ZSTD,
158
+ maxItemsPerBundle: 100,
159
+ });
160
+ const originalItems = Array.from({ length: 500 }, (_, i) => makeTestEvent(`seq-${i}`, 'ordered', i));
161
+ await bundledClient.sendBundled('test', originalItems);
162
+ const sqsRecords = simulateSqsDelivery(capturedEnvelopes);
163
+ const { items: recoveredItems } = await unbundleRecords(sqsRecords);
164
+ let currentBundleStart = 0;
165
+ for (const envelope of capturedEnvelopes) {
166
+ const bundleSize = envelope.n;
167
+ const bundleItems = recoveredItems.slice(currentBundleStart, currentBundleStart + bundleSize);
168
+ for (let j = 1; j < bundleItems.length; j++) {
169
+ const prevValue = bundleItems[j - 1]?.value ?? 0;
170
+ const currValue = bundleItems[j]?.value ?? 0;
171
+ expect(currValue).toBeGreaterThan(prevValue);
172
+ }
173
+ currentBundleStart += bundleSize;
174
+ }
175
+ });
176
+ });
177
+ describe('3. Compression round-trip verification', () => {
178
+ it('ZSTD compressed data decompresses to byte-exact JSON', async () => {
179
+ const bundledClient = new BundledSQSClient(mockSqsClient, {
180
+ compression: CompressionAlgorithm.ZSTD,
181
+ compressionLevel: 5,
182
+ });
183
+ const originalItems = Array.from({ length: 50 }, (_, i) => ({
184
+ id: `compress-test-${i}`,
185
+ name: 'compression-verification',
186
+ value: i * 123.456789,
187
+ metadata: {
188
+ unicode: '日本語テスト',
189
+ emoji: '🚀✨🎉',
190
+ special: 'line\nbreak\ttab\r\nwindows',
191
+ quotes: '"double" and \'single\'',
192
+ },
193
+ }));
194
+ const originalJson = JSON.stringify(originalItems);
195
+ await bundledClient.sendBundled('test', originalItems);
196
+ const sqsRecords = simulateSqsDelivery(capturedEnvelopes);
197
+ const { items: recoveredItems } = await unbundleRecords(sqsRecords);
198
+ const recoveredJson = JSON.stringify(recoveredItems);
199
+ expect(recoveredJson).toBe(originalJson);
200
+ expect(recoveredItems).toEqual(originalItems);
201
+ });
202
+ it('verifies actual compression occurred', async () => {
203
+ const bundledClient = new BundledSQSClient(mockSqsClient, {
204
+ compression: CompressionAlgorithm.ZSTD,
205
+ compressionLevel: 3,
206
+ });
207
+ const originalItems = Array.from({ length: 200 }, (_, i) => ({
208
+ id: `item-${i}`,
209
+ name: 'repetitive-data-for-compression',
210
+ value: i,
211
+ metadata: {
212
+ commonField1: 'this is repeated many times',
213
+ commonField2: 'another repeated value',
214
+ },
215
+ }));
216
+ const originalSizeBytes = Buffer.byteLength(JSON.stringify(originalItems), 'utf8');
217
+ await bundledClient.sendBundled('test', originalItems);
218
+ for (const envelope of capturedEnvelopes) {
219
+ expect(envelope.c).toBe(CompressionAlgorithm.ZSTD);
220
+ expect(typeof envelope.p).toBe('string');
221
+ const compressedSizeBytes = Buffer.byteLength(envelope.p, 'utf8');
222
+ expect(compressedSizeBytes).toBeLessThan(originalSizeBytes);
223
+ }
224
+ });
225
+ });
226
+ describe('4. Mixed message types round-trip', () => {
227
+ it('handles mix of NONE and ZSTD compression in same batch', async () => {
228
+ const zstdClient = new BundledSQSClient(mockSqsClient, {
229
+ compression: CompressionAlgorithm.ZSTD,
230
+ });
231
+ const noneClient = new BundledSQSClient(mockSqsClient, {
232
+ compression: CompressionAlgorithm.NONE,
233
+ });
234
+ const zstdItems = [
235
+ makeTestEvent('zstd-1', 'compressed', 100),
236
+ makeTestEvent('zstd-2', 'compressed', 200),
237
+ ];
238
+ const noneItems = [
239
+ makeTestEvent('none-1', 'uncompressed', 300),
240
+ makeTestEvent('none-2', 'uncompressed', 400),
241
+ ];
242
+ await zstdClient.sendBundled('test', zstdItems);
243
+ const zstdEnvelopes = [...capturedEnvelopes];
244
+ capturedEnvelopes = [];
245
+ await noneClient.sendBundled('test', noneItems);
246
+ const noneEnvelopes = [...capturedEnvelopes];
247
+ const allEnvelopes = [...zstdEnvelopes, ...noneEnvelopes];
248
+ const sqsRecords = simulateSqsDelivery(allEnvelopes);
249
+ const { items: recoveredItems, stats } = await unbundleRecords(sqsRecords);
250
+ expect(recoveredItems).toHaveLength(4);
251
+ expect(stats.bundledSqsRecords).toBe(2);
252
+ expect(stats.failedRecords).toBe(0);
253
+ const zstdRecovered = recoveredItems.filter((item) => item.name === 'compressed');
254
+ const noneRecovered = recoveredItems.filter((item) => item.name === 'uncompressed');
255
+ expect(zstdRecovered).toHaveLength(2);
256
+ expect(noneRecovered).toHaveLength(2);
257
+ expect(zstdRecovered).toEqual(zstdItems);
258
+ expect(noneRecovered).toEqual(noneItems);
259
+ });
260
+ it('handles mixed bundled and legacy messages', async () => {
261
+ const bundledClient = new BundledSQSClient(mockSqsClient, {
262
+ compression: CompressionAlgorithm.ZSTD,
263
+ });
264
+ const bundledItems = [
265
+ makeTestEvent('bundled-1', 'bundled', 100),
266
+ makeTestEvent('bundled-2', 'bundled', 200),
267
+ ];
268
+ await bundledClient.sendBundled('test', bundledItems);
269
+ const legacyRecord = {
270
+ messageId: 'legacy-msg-1',
271
+ body: JSON.stringify(makeTestEvent('legacy-1', 'legacy', 999)),
272
+ };
273
+ const wrappedLegacyRecord = {
274
+ messageId: 'legacy-msg-2',
275
+ body: JSON.stringify({ messageBody: makeTestEvent('legacy-2', 'wrapped-legacy', 888) }),
276
+ };
277
+ const bundledRecords = simulateSqsDelivery(capturedEnvelopes);
278
+ const allRecords = [...bundledRecords, legacyRecord, wrappedLegacyRecord];
279
+ const { items: recoveredItems, stats } = await unbundleRecords(allRecords);
280
+ expect(recoveredItems).toHaveLength(4);
281
+ expect(stats.bundledSqsRecords).toBe(1);
282
+ expect(stats.legacySqsRecords).toBe(2);
283
+ expect(stats.failedRecords).toBe(0);
284
+ });
285
+ });
286
+ describe('5. Error injection round-trip', () => {
287
+ it('recovers valid bundles while reporting corrupted bundle in failedMessageIds', async () => {
288
+ const bundledClient = new BundledSQSClient(mockSqsClient, {
289
+ compression: CompressionAlgorithm.ZSTD,
290
+ });
291
+ const validItems1 = [makeTestEvent('valid-1', 'first-batch', 100)];
292
+ const validItems2 = [makeTestEvent('valid-2', 'second-batch', 200)];
293
+ await bundledClient.sendBundled('test', validItems1);
294
+ const envelope1 = { ...capturedEnvelopes[0] };
295
+ capturedEnvelopes = [];
296
+ await bundledClient.sendBundled('test', validItems2);
297
+ const envelope2 = { ...capturedEnvelopes[0] };
298
+ const corruptedEnvelope = {
299
+ v: 1,
300
+ c: CompressionAlgorithm.ZSTD,
301
+ n: 10,
302
+ s: 1000,
303
+ p: 'dGhpcyBpcyBub3QgdmFsaWQgenN0ZA==',
304
+ };
305
+ const records = [
306
+ { messageId: 'valid-1', body: JSON.stringify({ messageBody: envelope1 }) },
307
+ { messageId: 'corrupted', body: JSON.stringify({ messageBody: corruptedEnvelope }) },
308
+ { messageId: 'valid-2', body: JSON.stringify({ messageBody: envelope2 }) },
309
+ ];
310
+ const { items: recoveredItems, failedMessageIds, stats } = await unbundleRecords(records);
311
+ expect(recoveredItems).toHaveLength(2);
312
+ expect(recoveredItems[0]?.id).toBe('valid-1');
313
+ expect(recoveredItems[1]?.id).toBe('valid-2');
314
+ expect(failedMessageIds).toContain('corrupted');
315
+ expect(failedMessageIds).toHaveLength(1);
316
+ expect(stats.bundledSqsRecords).toBe(2);
317
+ expect(stats.failedRecords).toBe(1);
318
+ expect(stats.totalItems).toBe(2);
319
+ });
320
+ it('handles invalid JSON gracefully', async () => {
321
+ const bundledClient = new BundledSQSClient(mockSqsClient, {
322
+ compression: CompressionAlgorithm.ZSTD,
323
+ });
324
+ const validItems = [makeTestEvent('valid', 'test', 100)];
325
+ await bundledClient.sendBundled('test', validItems);
326
+ const records = [
327
+ ...simulateSqsDelivery(capturedEnvelopes),
328
+ { messageId: 'invalid-json-1', body: 'not-valid-json{{{' },
329
+ { messageId: 'invalid-json-2', body: '{"incomplete":' },
330
+ { messageId: 'empty', body: '' },
331
+ ];
332
+ const { items: recoveredItems, failedMessageIds, stats } = await unbundleRecords(records);
333
+ expect(recoveredItems).toHaveLength(1);
334
+ expect(recoveredItems[0]?.id).toBe('valid');
335
+ expect(failedMessageIds).toContain('invalid-json-1');
336
+ expect(failedMessageIds).toContain('invalid-json-2');
337
+ expect(failedMessageIds).toContain('empty');
338
+ expect(failedMessageIds).toHaveLength(3);
339
+ expect(stats.failedRecords).toBe(3);
340
+ });
341
+ it('handles decompression bomb protection', async () => {
342
+ const largeItems = Array.from({ length: 1000 }, (_, i) => ({
343
+ id: `item-${i}`,
344
+ data: 'x'.repeat(1000),
345
+ }));
346
+ const json = JSON.stringify(largeItems);
347
+ const compressed = await compress(Buffer.from(json, 'utf8'), CompressionAlgorithm.ZSTD, 3);
348
+ const base64 = compressed.toString('base64');
349
+ const bigEnvelope = {
350
+ v: 1,
351
+ c: CompressionAlgorithm.ZSTD,
352
+ n: 1000,
353
+ s: json.length,
354
+ p: base64,
355
+ };
356
+ const records = [{ messageId: 'too-large', body: JSON.stringify({ messageBody: bigEnvelope }) }];
357
+ const { failedMessageIds, stats } = await unbundleRecords(records, {
358
+ maxDecompressedSizeBytes: 100 * 1024,
359
+ });
360
+ expect(failedMessageIds).toContain('too-large');
361
+ expect(stats.failedRecords).toBe(1);
362
+ });
363
+ });
364
+ describe('6. Realistic event types round-trip', () => {
365
+ it('TrackingEvent-like structures survive round-trip exactly', async () => {
366
+ const realisticMockSqs = {
367
+ buildAndSendMessagesV2: jest.fn(async (_type, envelopes) => {
368
+ capturedEnvelopes = [];
369
+ capturedEnvelopes.push(...envelopes);
370
+ return {
371
+ successCount: envelopes.length,
372
+ failedCount: 0,
373
+ batchCount: 1,
374
+ failedMessages: [],
375
+ };
376
+ }),
377
+ queueUrl: 'https://sqs.us-east-1.amazonaws.com/123456789/test-queue',
378
+ limits: createSqsLimits(SQS_1MB),
379
+ };
380
+ const bundledClient = new BundledSQSClient(realisticMockSqs, {
381
+ compression: CompressionAlgorithm.ZSTD,
382
+ compressionLevel: 3,
383
+ });
384
+ const originalEvents = Array.from({ length: 100 }, (_, i) => makeRealisticTrackingEvent(i));
385
+ await bundledClient.sendBundled('tracking-events', originalEvents);
386
+ const sqsRecords = simulateSqsDelivery(capturedEnvelopes);
387
+ const { items: recoveredEvents, stats } = await unbundleRecords(sqsRecords);
388
+ expect(recoveredEvents).toHaveLength(100);
389
+ expect(stats.failedRecords).toBe(0);
390
+ expect(recoveredEvents).toEqual(originalEvents);
391
+ for (let i = 0; i < originalEvents.length; i++) {
392
+ const original = originalEvents[i];
393
+ const recovered = recoveredEvents[i];
394
+ expect(recovered?.anonymousId).toBe(original?.anonymousId);
395
+ expect(recovered?.context.page.url).toBe(original?.context.page.url);
396
+ expect(recovered?.properties.price).toBe(original?.properties.price);
397
+ if (original?.shopifyData) {
398
+ expect(recovered?.shopifyData).toEqual(original.shopifyData);
399
+ }
400
+ }
401
+ });
402
+ it('preserves nested object structures exactly', async () => {
403
+ const bundledClient = new BundledSQSClient(mockSqsClient, {
404
+ compression: CompressionAlgorithm.ZSTD,
405
+ });
406
+ const deeplyNestedItems = [
407
+ {
408
+ id: 'nested-1',
409
+ name: 'deep-nesting',
410
+ nested: {
411
+ level1: {
412
+ level2: {
413
+ deep: 'very deep value',
414
+ },
415
+ },
416
+ },
417
+ },
418
+ {
419
+ id: 'nested-2',
420
+ name: 'with-arrays',
421
+ tags: ['tag1', 'tag2', 'tag3'],
422
+ metadata: {
423
+ array: [1, 2, 3],
424
+ object: { a: 1, b: 2 },
425
+ mixed: [{ key: 'value' }, [1, 2, 3]],
426
+ },
427
+ },
428
+ ];
429
+ await bundledClient.sendBundled('test', deeplyNestedItems);
430
+ const sqsRecords = simulateSqsDelivery(capturedEnvelopes);
431
+ const { items: recoveredItems } = await unbundleRecords(sqsRecords);
432
+ expect(recoveredItems).toEqual(deeplyNestedItems);
433
+ expect(recoveredItems[0]?.nested?.level1.level2.deep).toBe('very deep value');
434
+ expect(recoveredItems[1]?.tags).toEqual(['tag1', 'tag2', 'tag3']);
435
+ });
436
+ });
437
+ describe('7. High compression ratio round-trip', () => {
438
+ it('highly repetitive data compresses and decompresses correctly', async () => {
439
+ const bundledClient = new BundledSQSClient(mockSqsClient, {
440
+ compression: CompressionAlgorithm.ZSTD,
441
+ compressionLevel: 3,
442
+ });
443
+ const repetitiveString = 'AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA';
444
+ const originalItems = Array.from({ length: 200 }, (_, i) => ({
445
+ id: `repetitive-${i}`,
446
+ name: repetitiveString,
447
+ value: 42,
448
+ metadata: {
449
+ field1: repetitiveString,
450
+ field2: repetitiveString,
451
+ field3: repetitiveString,
452
+ field4: repetitiveString,
453
+ field5: repetitiveString,
454
+ },
455
+ }));
456
+ const originalSizeBytes = Buffer.byteLength(JSON.stringify(originalItems), 'utf8');
457
+ await bundledClient.sendBundled('test', originalItems);
458
+ let totalCompressedSize = 0;
459
+ for (const envelope of capturedEnvelopes) {
460
+ expect(typeof envelope.p).toBe('string');
461
+ totalCompressedSize += Buffer.byteLength(envelope.p, 'utf8');
462
+ }
463
+ const compressionRatio = originalSizeBytes / totalCompressedSize;
464
+ expect(compressionRatio).toBeGreaterThan(5);
465
+ const sqsRecords = simulateSqsDelivery(capturedEnvelopes);
466
+ const { items: recoveredItems, stats } = await unbundleRecords(sqsRecords);
467
+ expect(recoveredItems).toHaveLength(200);
468
+ expect(recoveredItems).toEqual(originalItems);
469
+ expect(stats.failedRecords).toBe(0);
470
+ for (const item of recoveredItems) {
471
+ expect(item.name).toBe(repetitiveString);
472
+ expect(item.value).toBe(42);
473
+ expect(item.metadata?.field1).toBe(repetitiveString);
474
+ }
475
+ });
476
+ it('varying compression levels all round-trip correctly', async () => {
477
+ const items = Array.from({ length: 50 }, (_, i) => makeTestEvent(`level-test-${i}`, 'compression-level', i));
478
+ for (const level of [1, 3, 9, 15]) {
479
+ capturedEnvelopes = [];
480
+ const bundledClient = new BundledSQSClient(mockSqsClient, {
481
+ compression: CompressionAlgorithm.ZSTD,
482
+ compressionLevel: level,
483
+ });
484
+ await bundledClient.sendBundled('test', items);
485
+ const sqsRecords = simulateSqsDelivery(capturedEnvelopes);
486
+ const { items: recoveredItems, stats } = await unbundleRecords(sqsRecords);
487
+ expect(recoveredItems).toEqual(items);
488
+ expect(stats.failedRecords).toBe(0);
489
+ }
490
+ });
491
+ });
492
+ describe('8. Edge cases', () => {
493
+ it('empty arrays survive round-trip', async () => {
494
+ const bundledClient = new BundledSQSClient(mockSqsClient, {
495
+ compression: CompressionAlgorithm.ZSTD,
496
+ });
497
+ const result = await bundledClient.sendBundled('test', []);
498
+ expect(result.totalItems).toBe(0);
499
+ expect(capturedEnvelopes).toHaveLength(0);
500
+ });
501
+ it('single item survives round-trip', async () => {
502
+ const bundledClient = new BundledSQSClient(mockSqsClient, {
503
+ compression: CompressionAlgorithm.ZSTD,
504
+ });
505
+ const singleItem = [makeTestEvent('single', 'lone-wolf', 999)];
506
+ await bundledClient.sendBundled('test', singleItem);
507
+ const sqsRecords = simulateSqsDelivery(capturedEnvelopes);
508
+ const { items: recoveredItems } = await unbundleRecords(sqsRecords);
509
+ expect(recoveredItems).toHaveLength(1);
510
+ expect(recoveredItems).toEqual(singleItem);
511
+ });
512
+ it('special characters survive round-trip', async () => {
513
+ const bundledClient = new BundledSQSClient(mockSqsClient, {
514
+ compression: CompressionAlgorithm.ZSTD,
515
+ });
516
+ const specialCharsItems = [
517
+ {
518
+ id: 'unicode-日本語',
519
+ name: '中文测试',
520
+ metadata: {
521
+ emoji: '🎉🚀✨💯',
522
+ rtl: 'مرحبا بالعالم',
523
+ escape: '\\n\\t\\r',
524
+ quotes: '"double" \'single\' `backtick`',
525
+ angle: '<script>alert("xss")</script>',
526
+ null_char: 'before\x00after',
527
+ },
528
+ },
529
+ ];
530
+ await bundledClient.sendBundled('test', specialCharsItems);
531
+ const sqsRecords = simulateSqsDelivery(capturedEnvelopes);
532
+ const { items: recoveredItems } = await unbundleRecords(sqsRecords);
533
+ expect(recoveredItems).toEqual(specialCharsItems);
534
+ });
535
+ it('null and undefined values are handled correctly', async () => {
536
+ const bundledClient = new BundledSQSClient(mockSqsClient, {
537
+ compression: CompressionAlgorithm.ZSTD,
538
+ });
539
+ const itemsWithNulls = [
540
+ { id: 'null-test', name: 'test', value: undefined },
541
+ {
542
+ id: 'explicit-null',
543
+ name: 'test',
544
+ metadata: { key: null },
545
+ },
546
+ ];
547
+ await bundledClient.sendBundled('test', itemsWithNulls);
548
+ const sqsRecords = simulateSqsDelivery(capturedEnvelopes);
549
+ const { items: recoveredItems } = await unbundleRecords(sqsRecords);
550
+ expect(recoveredItems[0]?.value).toBeUndefined();
551
+ expect(recoveredItems[1]?.metadata?.key).toBeNull();
552
+ });
553
+ it('recordMap correctly tracks items back to SQS messages', async () => {
554
+ const bundledClient = new BundledSQSClient(mockSqsClient, {
555
+ compression: CompressionAlgorithm.ZSTD,
556
+ maxItemsPerBundle: 3,
557
+ });
558
+ const items = Array.from({ length: 10 }, (_, i) => makeTestEvent(`item-${i}`, 'tracking', i));
559
+ await bundledClient.sendBundled('test', items);
560
+ const sqsRecords = capturedEnvelopes.map((env, i) => ({
561
+ messageId: `bundle-${i}`,
562
+ body: JSON.stringify({ messageBody: env }),
563
+ }));
564
+ const { items: recoveredItems, recordMap, stats } = await unbundleRecords(sqsRecords);
565
+ expect(recoveredItems).toHaveLength(10);
566
+ const messageIdCounts = new Map();
567
+ for (const item of recoveredItems) {
568
+ const messageId = recordMap.get(item);
569
+ expect(messageId).toBeDefined();
570
+ if (messageId) {
571
+ messageIdCounts.set(messageId, (messageIdCounts.get(messageId) ?? 0) + 1);
572
+ }
573
+ }
574
+ expect(messageIdCounts.size).toBe(capturedEnvelopes.length);
575
+ for (const [messageId, count] of messageIdCounts) {
576
+ expect(count).toBeLessThanOrEqual(3);
577
+ expect(messageId).toMatch(/^bundle-\d+$/);
578
+ }
579
+ expect(stats.bundledSqsRecords).toBe(capturedEnvelopes.length);
580
+ });
581
+ });
582
+ });
583
583
  //# sourceMappingURL=sqs-bundling-roundtrip.spec.js.map