@pattern-stack/codegen 0.15.1 → 0.15.3

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 (527) hide show
  1. package/CHANGELOG.md +85 -0
  2. package/dist/chunk-27ETSJ2X.js +84 -0
  3. package/dist/chunk-27ETSJ2X.js.map +1 -0
  4. package/dist/chunk-2E224ZSN.js +20 -0
  5. package/dist/chunk-2E224ZSN.js.map +1 -0
  6. package/dist/chunk-2FTZLDBP.js +179 -0
  7. package/dist/chunk-2FTZLDBP.js.map +1 -0
  8. package/dist/chunk-2N4UG4VD.js +20 -0
  9. package/dist/chunk-2N4UG4VD.js.map +1 -0
  10. package/dist/chunk-2TVVBC53.js +92 -0
  11. package/dist/chunk-2TVVBC53.js.map +1 -0
  12. package/dist/chunk-2VHZ7EKC.js +37 -0
  13. package/dist/chunk-2VHZ7EKC.js.map +1 -0
  14. package/dist/chunk-32BMMV4H.js +109 -0
  15. package/dist/chunk-32BMMV4H.js.map +1 -0
  16. package/dist/chunk-32DOFN3T.js +4042 -0
  17. package/dist/chunk-32DOFN3T.js.map +1 -0
  18. package/dist/chunk-36U5UGIO.js +107 -0
  19. package/dist/chunk-36U5UGIO.js.map +1 -0
  20. package/dist/chunk-3CJFPU6Q.js +14 -0
  21. package/dist/chunk-3CJFPU6Q.js.map +1 -0
  22. package/dist/chunk-3NMCDN7L.js +90 -0
  23. package/dist/chunk-3NMCDN7L.js.map +1 -0
  24. package/dist/chunk-3SZFUTXE.js +62 -0
  25. package/dist/chunk-3SZFUTXE.js.map +1 -0
  26. package/dist/chunk-4DOJBQTP.js +117 -0
  27. package/dist/chunk-4DOJBQTP.js.map +1 -0
  28. package/dist/chunk-4H3PETLM.js +290 -0
  29. package/dist/chunk-4H3PETLM.js.map +1 -0
  30. package/dist/chunk-4JLJYWJC.js +308 -0
  31. package/dist/chunk-4JLJYWJC.js.map +1 -0
  32. package/dist/chunk-4KNXX6TI.js +29 -0
  33. package/dist/chunk-4KNXX6TI.js.map +1 -0
  34. package/dist/chunk-4LH67P4U.js +17 -0
  35. package/dist/chunk-4LH67P4U.js.map +1 -0
  36. package/dist/chunk-4MF3HKJA.js +94 -0
  37. package/dist/chunk-4MF3HKJA.js.map +1 -0
  38. package/dist/chunk-4MVGAMUA.js +40 -0
  39. package/dist/chunk-4MVGAMUA.js.map +1 -0
  40. package/dist/chunk-4RFHUZXU.js +635 -0
  41. package/dist/chunk-4RFHUZXU.js.map +1 -0
  42. package/dist/chunk-5A432NZJ.js +7 -0
  43. package/dist/chunk-5A432NZJ.js.map +1 -0
  44. package/dist/chunk-5Y7W3XR6.js +356 -0
  45. package/dist/chunk-5Y7W3XR6.js.map +1 -0
  46. package/dist/chunk-6DWFJNIK.js +15 -0
  47. package/dist/chunk-6DWFJNIK.js.map +1 -0
  48. package/dist/chunk-6I7ULIN6.js +15 -0
  49. package/dist/chunk-6I7ULIN6.js.map +1 -0
  50. package/dist/chunk-6XY6ZMMD.js +25 -0
  51. package/dist/chunk-6XY6ZMMD.js.map +1 -0
  52. package/dist/chunk-7B3RYX45.js +63 -0
  53. package/dist/chunk-7B3RYX45.js.map +1 -0
  54. package/dist/chunk-7C3FOSDI.js +1 -0
  55. package/dist/chunk-7C3FOSDI.js.map +1 -0
  56. package/dist/chunk-7KOW6PU6.js +59 -0
  57. package/dist/chunk-7KOW6PU6.js.map +1 -0
  58. package/dist/chunk-7RELQJIN.js +22 -0
  59. package/dist/chunk-7RELQJIN.js.map +1 -0
  60. package/dist/chunk-7YGORYZD.js +112 -0
  61. package/dist/chunk-7YGORYZD.js.map +1 -0
  62. package/dist/chunk-AHV4GDYM.js +63 -0
  63. package/dist/chunk-AHV4GDYM.js.map +1 -0
  64. package/dist/chunk-AQFQ4BYM.js +81 -0
  65. package/dist/chunk-AQFQ4BYM.js.map +1 -0
  66. package/dist/chunk-AS3NAZB6.js +14 -0
  67. package/dist/chunk-AS3NAZB6.js.map +1 -0
  68. package/dist/chunk-BGULBWKJ.js +88 -0
  69. package/dist/chunk-BGULBWKJ.js.map +1 -0
  70. package/dist/chunk-BIO6F7YI.js +17 -0
  71. package/dist/chunk-BIO6F7YI.js.map +1 -0
  72. package/dist/chunk-BOPZWRJK.js +36 -0
  73. package/dist/chunk-BOPZWRJK.js.map +1 -0
  74. package/dist/chunk-BPARRK6F.js +14 -0
  75. package/dist/chunk-BPARRK6F.js.map +1 -0
  76. package/dist/chunk-CO6LUM72.js +59 -0
  77. package/dist/chunk-CO6LUM72.js.map +1 -0
  78. package/dist/chunk-DCCZB4UC.js +100 -0
  79. package/dist/chunk-DCCZB4UC.js.map +1 -0
  80. package/dist/chunk-DV4RV2DC.js +59 -0
  81. package/dist/chunk-DV4RV2DC.js.map +1 -0
  82. package/dist/chunk-EDKJU5BO.js +11 -0
  83. package/dist/chunk-EDKJU5BO.js.map +1 -0
  84. package/dist/chunk-EO2QPOKH.js +116 -0
  85. package/dist/chunk-EO2QPOKH.js.map +1 -0
  86. package/dist/chunk-EOLLMEAH.js +155 -0
  87. package/dist/chunk-EOLLMEAH.js.map +1 -0
  88. package/dist/chunk-EWYCWP4H.js +14 -0
  89. package/dist/chunk-EWYCWP4H.js.map +1 -0
  90. package/dist/chunk-EXVDJMIY.js +33 -0
  91. package/dist/chunk-EXVDJMIY.js.map +1 -0
  92. package/dist/chunk-FASRXRX5.js +19 -0
  93. package/dist/chunk-FASRXRX5.js.map +1 -0
  94. package/dist/chunk-FBGHYQIZ.js +201 -0
  95. package/dist/chunk-FBGHYQIZ.js.map +1 -0
  96. package/dist/chunk-FI34KYZ5.js +1 -0
  97. package/dist/chunk-FI34KYZ5.js.map +1 -0
  98. package/dist/chunk-FN2PYDPP.js +1 -0
  99. package/dist/chunk-FN2PYDPP.js.map +1 -0
  100. package/dist/chunk-GCYKMF22.js +81 -0
  101. package/dist/chunk-GCYKMF22.js.map +1 -0
  102. package/dist/chunk-GM3RMJIJ.js +92 -0
  103. package/dist/chunk-GM3RMJIJ.js.map +1 -0
  104. package/dist/chunk-GYGNEQSC.js +9 -0
  105. package/dist/chunk-GYGNEQSC.js.map +1 -0
  106. package/dist/chunk-H5NH7KPE.js +21 -0
  107. package/dist/chunk-H5NH7KPE.js.map +1 -0
  108. package/dist/chunk-HNWZFNKP.js +168 -0
  109. package/dist/chunk-HNWZFNKP.js.map +1 -0
  110. package/dist/chunk-HUH73XGI.js +1 -0
  111. package/dist/chunk-HUH73XGI.js.map +1 -0
  112. package/dist/chunk-I6MVCB5A.js +39 -0
  113. package/dist/chunk-I6MVCB5A.js.map +1 -0
  114. package/dist/chunk-IBGER4YK.js +12 -0
  115. package/dist/chunk-IBGER4YK.js.map +1 -0
  116. package/dist/chunk-IF5I3DAA.js +92 -0
  117. package/dist/chunk-IF5I3DAA.js.map +1 -0
  118. package/dist/chunk-IP4OO26U.js +54 -0
  119. package/dist/chunk-IP4OO26U.js.map +1 -0
  120. package/dist/chunk-IWAOY6KC.js +1 -0
  121. package/dist/chunk-IWAOY6KC.js.map +1 -0
  122. package/dist/chunk-IYNSRIGR.js +122 -0
  123. package/dist/chunk-IYNSRIGR.js.map +1 -0
  124. package/dist/chunk-J37YWU7Y.js +19 -0
  125. package/dist/chunk-J37YWU7Y.js.map +1 -0
  126. package/dist/chunk-J6KZS54B.js +269 -0
  127. package/dist/chunk-J6KZS54B.js.map +1 -0
  128. package/dist/chunk-J6MN42LG.js +19 -0
  129. package/dist/chunk-J6MN42LG.js.map +1 -0
  130. package/dist/chunk-J7JMVS2B.js +53 -0
  131. package/dist/chunk-J7JMVS2B.js.map +1 -0
  132. package/dist/chunk-JRQO2IOF.js +65 -0
  133. package/dist/chunk-JRQO2IOF.js.map +1 -0
  134. package/dist/chunk-JWNHNUYL.js +96 -0
  135. package/dist/chunk-JWNHNUYL.js.map +1 -0
  136. package/dist/chunk-K2I6XIK5.js +122 -0
  137. package/dist/chunk-K2I6XIK5.js.map +1 -0
  138. package/dist/chunk-KVOWSC5S.js +1 -0
  139. package/dist/chunk-KVOWSC5S.js.map +1 -0
  140. package/dist/chunk-KYR3B3OW.js +79 -0
  141. package/dist/chunk-KYR3B3OW.js.map +1 -0
  142. package/dist/chunk-L3LZWWSX.js +61 -0
  143. package/dist/chunk-L3LZWWSX.js.map +1 -0
  144. package/dist/chunk-L4SDDEEU.js +1 -0
  145. package/dist/chunk-L4SDDEEU.js.map +1 -0
  146. package/dist/chunk-L6FTY45T.js +13 -0
  147. package/dist/chunk-L6FTY45T.js.map +1 -0
  148. package/dist/chunk-L7BNNRGI.js +134 -0
  149. package/dist/chunk-L7BNNRGI.js.map +1 -0
  150. package/dist/chunk-LG57S2SC.js +150 -0
  151. package/dist/chunk-LG57S2SC.js.map +1 -0
  152. package/dist/chunk-M6QLSLPO.js +97 -0
  153. package/dist/chunk-M6QLSLPO.js.map +1 -0
  154. package/dist/chunk-MZ6GV4YF.js +21 -0
  155. package/dist/chunk-MZ6GV4YF.js.map +1 -0
  156. package/dist/chunk-N5OTOWTP.js +55 -0
  157. package/dist/chunk-N5OTOWTP.js.map +1 -0
  158. package/dist/chunk-NN7XZEGF.js +14 -0
  159. package/dist/chunk-NN7XZEGF.js.map +1 -0
  160. package/dist/chunk-NPFPZ2HO.js +13 -0
  161. package/dist/chunk-NPFPZ2HO.js.map +1 -0
  162. package/dist/chunk-NXXDZ6ZF.js +42 -0
  163. package/dist/chunk-NXXDZ6ZF.js.map +1 -0
  164. package/dist/chunk-NYBCQZC7.js +11 -0
  165. package/dist/chunk-NYBCQZC7.js.map +1 -0
  166. package/dist/chunk-O37C3YE6.js +111 -0
  167. package/dist/chunk-O37C3YE6.js.map +1 -0
  168. package/dist/chunk-OFRRBC7M.js +78 -0
  169. package/dist/chunk-OFRRBC7M.js.map +1 -0
  170. package/dist/chunk-OGIZXGPY.js +222 -0
  171. package/dist/chunk-OGIZXGPY.js.map +1 -0
  172. package/dist/chunk-OKXZ63IA.js +168 -0
  173. package/dist/chunk-OKXZ63IA.js.map +1 -0
  174. package/dist/chunk-OSQRXVG2.js +58 -0
  175. package/dist/chunk-OSQRXVG2.js.map +1 -0
  176. package/dist/chunk-OTDN3OUQ.js +215 -0
  177. package/dist/chunk-OTDN3OUQ.js.map +1 -0
  178. package/dist/chunk-PNZSGAB2.js +114 -0
  179. package/dist/chunk-PNZSGAB2.js.map +1 -0
  180. package/dist/chunk-PRWIX6UW.js +21 -0
  181. package/dist/chunk-PRWIX6UW.js.map +1 -0
  182. package/dist/chunk-PSXUNOVU.js +7 -0
  183. package/dist/chunk-PSXUNOVU.js.map +1 -0
  184. package/dist/chunk-QLTJSCE6.js +44 -0
  185. package/dist/chunk-QLTJSCE6.js.map +1 -0
  186. package/dist/chunk-RC23QROE.js +447 -0
  187. package/dist/chunk-RC23QROE.js.map +1 -0
  188. package/dist/chunk-RDVTWIYY.js +212 -0
  189. package/dist/chunk-RDVTWIYY.js.map +1 -0
  190. package/dist/chunk-RFH7N6EP.js +36 -0
  191. package/dist/chunk-RFH7N6EP.js.map +1 -0
  192. package/dist/chunk-RHVN6NA7.js +134 -0
  193. package/dist/chunk-RHVN6NA7.js.map +1 -0
  194. package/dist/chunk-S7C6TIIF.js +21 -0
  195. package/dist/chunk-S7C6TIIF.js.map +1 -0
  196. package/dist/chunk-SNQ3TOWP.js +20 -0
  197. package/dist/chunk-SNQ3TOWP.js.map +1 -0
  198. package/dist/chunk-SOVM2VEK.js +14 -0
  199. package/dist/chunk-SOVM2VEK.js.map +1 -0
  200. package/dist/chunk-SQDOBLBP.js +13 -0
  201. package/dist/chunk-SQDOBLBP.js.map +1 -0
  202. package/dist/chunk-SR7F3TJY.js +130 -0
  203. package/dist/chunk-SR7F3TJY.js.map +1 -0
  204. package/dist/chunk-SZVPIHWE.js +129 -0
  205. package/dist/chunk-SZVPIHWE.js.map +1 -0
  206. package/dist/chunk-T4BIIU5E.js +89 -0
  207. package/dist/chunk-T4BIIU5E.js.map +1 -0
  208. package/dist/chunk-T6SCOJF4.js +92 -0
  209. package/dist/chunk-T6SCOJF4.js.map +1 -0
  210. package/dist/chunk-TNXH7BJS.js +48 -0
  211. package/dist/chunk-TNXH7BJS.js.map +1 -0
  212. package/dist/chunk-U64T4YZE.js +9 -0
  213. package/dist/chunk-U64T4YZE.js.map +1 -0
  214. package/dist/chunk-UQ5EHOH2.js +39 -0
  215. package/dist/chunk-UQ5EHOH2.js.map +1 -0
  216. package/dist/chunk-UTN4GBPQ.js +1 -0
  217. package/dist/chunk-UTN4GBPQ.js.map +1 -0
  218. package/dist/chunk-V4AF6DI4.js +16 -0
  219. package/dist/chunk-V4AF6DI4.js.map +1 -0
  220. package/dist/chunk-W72PRNJY.js +126 -0
  221. package/dist/chunk-W72PRNJY.js.map +1 -0
  222. package/dist/chunk-WL67FZGF.js +21 -0
  223. package/dist/chunk-WL67FZGF.js.map +1 -0
  224. package/dist/chunk-WWGYCIJX.js +29 -0
  225. package/dist/chunk-WWGYCIJX.js.map +1 -0
  226. package/dist/chunk-X2GMTYPA.js +50 -0
  227. package/dist/chunk-X2GMTYPA.js.map +1 -0
  228. package/dist/chunk-XCEI7NUH.js +41 -0
  229. package/dist/chunk-XCEI7NUH.js.map +1 -0
  230. package/dist/chunk-Y7GDG744.js +88 -0
  231. package/dist/chunk-Y7GDG744.js.map +1 -0
  232. package/dist/chunk-Y7RRSEOC.js +9 -0
  233. package/dist/chunk-Y7RRSEOC.js.map +1 -0
  234. package/dist/chunk-YLPAPPLW.js +75 -0
  235. package/dist/chunk-YLPAPPLW.js.map +1 -0
  236. package/dist/chunk-YPWODKD5.js +184 -0
  237. package/dist/chunk-YPWODKD5.js.map +1 -0
  238. package/dist/chunk-YSLTTQLC.js +25 -0
  239. package/dist/chunk-YSLTTQLC.js.map +1 -0
  240. package/dist/chunk-YTN6BKWA.js +121 -0
  241. package/dist/chunk-YTN6BKWA.js.map +1 -0
  242. package/dist/chunk-Z7PQCAVK.js +200 -0
  243. package/dist/chunk-Z7PQCAVK.js.map +1 -0
  244. package/dist/chunk-ZUKFQL6E.js +47 -0
  245. package/dist/chunk-ZUKFQL6E.js.map +1 -0
  246. package/dist/chunk-ZUMULSEQ.js +1 -0
  247. package/dist/chunk-ZUMULSEQ.js.map +1 -0
  248. package/dist/runtime/analytics/index.js +8 -41
  249. package/dist/runtime/analytics/index.js.map +1 -1
  250. package/dist/runtime/analytics/types.js +8 -41
  251. package/dist/runtime/analytics/types.js.map +1 -1
  252. package/dist/runtime/base-classes/activity-entity-repository.js +6 -312
  253. package/dist/runtime/base-classes/activity-entity-repository.js.map +1 -1
  254. package/dist/runtime/base-classes/activity-entity-service.js +6 -212
  255. package/dist/runtime/base-classes/activity-entity-service.js.map +1 -1
  256. package/dist/runtime/base-classes/base-read-use-cases.js +5 -27
  257. package/dist/runtime/base-classes/base-read-use-cases.js.map +1 -1
  258. package/dist/runtime/base-classes/base-repository.js +5 -277
  259. package/dist/runtime/base-classes/base-repository.js.map +1 -1
  260. package/dist/runtime/base-classes/base-service.js +5 -184
  261. package/dist/runtime/base-classes/base-service.js.map +1 -1
  262. package/dist/runtime/base-classes/index.js +59 -1076
  263. package/dist/runtime/base-classes/index.js.map +1 -1
  264. package/dist/runtime/base-classes/integrated-entity-repository.js +6 -486
  265. package/dist/runtime/base-classes/integrated-entity-repository.js.map +1 -1
  266. package/dist/runtime/base-classes/integrated-entity-service.js +6 -213
  267. package/dist/runtime/base-classes/integrated-entity-service.js.map +1 -1
  268. package/dist/runtime/base-classes/junction-integration-repository.js +8 -448
  269. package/dist/runtime/base-classes/junction-integration-repository.js.map +1 -1
  270. package/dist/runtime/base-classes/knowledge-entity-repository.js +6 -283
  271. package/dist/runtime/base-classes/knowledge-entity-repository.js.map +1 -1
  272. package/dist/runtime/base-classes/knowledge-entity-service.js +6 -190
  273. package/dist/runtime/base-classes/knowledge-entity-service.js.map +1 -1
  274. package/dist/runtime/base-classes/lifecycle-events.js +8 -70
  275. package/dist/runtime/base-classes/lifecycle-events.js.map +1 -1
  276. package/dist/runtime/base-classes/metadata-entity-repository.js +6 -330
  277. package/dist/runtime/base-classes/metadata-entity-repository.js.map +1 -1
  278. package/dist/runtime/base-classes/metadata-entity-service.js +6 -212
  279. package/dist/runtime/base-classes/metadata-entity-service.js.map +1 -1
  280. package/dist/runtime/base-classes/tenant-context.js +10 -36
  281. package/dist/runtime/base-classes/tenant-context.js.map +1 -1
  282. package/dist/runtime/base-classes/with-analytics.js +4 -7
  283. package/dist/runtime/base-classes/with-analytics.js.map +1 -1
  284. package/dist/runtime/constants/tokens.js +5 -3
  285. package/dist/runtime/constants/tokens.js.map +1 -1
  286. package/dist/runtime/eav-helpers.js +2 -0
  287. package/dist/runtime/eav-helpers.js.map +1 -1
  288. package/dist/runtime/pipes/zod-validation.pipe.js +3 -10
  289. package/dist/runtime/pipes/zod-validation.pipe.js.map +1 -1
  290. package/dist/runtime/shared/openapi/error-response.dto.js +5 -8
  291. package/dist/runtime/shared/openapi/error-response.dto.js.map +1 -1
  292. package/dist/runtime/shared/openapi/errors.js +5 -19
  293. package/dist/runtime/shared/openapi/errors.js.map +1 -1
  294. package/dist/runtime/shared/openapi/index.js +15 -106
  295. package/dist/runtime/shared/openapi/index.js.map +1 -1
  296. package/dist/runtime/shared/openapi/registry.js +6 -103
  297. package/dist/runtime/shared/openapi/registry.js.map +1 -1
  298. package/dist/runtime/shared/openapi/registry.tokens.js +4 -2
  299. package/dist/runtime/shared/openapi/registry.tokens.js.map +1 -1
  300. package/dist/runtime/subsystems/analytics/analytics.module.js +8 -117
  301. package/dist/runtime/subsystems/analytics/analytics.module.js.map +1 -1
  302. package/dist/runtime/subsystems/analytics/analytics.tokens.js +7 -8
  303. package/dist/runtime/subsystems/analytics/analytics.tokens.js.map +1 -1
  304. package/dist/runtime/subsystems/analytics/cube-backend.js +6 -71
  305. package/dist/runtime/subsystems/analytics/cube-backend.js.map +1 -1
  306. package/dist/runtime/subsystems/analytics/index.js +16 -117
  307. package/dist/runtime/subsystems/analytics/index.js.map +1 -1
  308. package/dist/runtime/subsystems/analytics/noop-backend.js +4 -21
  309. package/dist/runtime/subsystems/analytics/noop-backend.js.map +1 -1
  310. package/dist/runtime/subsystems/auth/auth-oauth-state.schema.js +4 -8
  311. package/dist/runtime/subsystems/auth/auth-oauth-state.schema.js.map +1 -1
  312. package/dist/runtime/subsystems/auth/auth.module.js +12 -359
  313. package/dist/runtime/subsystems/auth/auth.module.js.map +1 -1
  314. package/dist/runtime/subsystems/auth/auth.tokens.js +12 -13
  315. package/dist/runtime/subsystems/auth/auth.tokens.js.map +1 -1
  316. package/dist/runtime/subsystems/auth/backends/encryption-key/env.js +4 -49
  317. package/dist/runtime/subsystems/auth/backends/encryption-key/env.js.map +1 -1
  318. package/dist/runtime/subsystems/auth/backends/state-store.drizzle-backend.js +6 -64
  319. package/dist/runtime/subsystems/auth/backends/state-store.drizzle-backend.js.map +1 -1
  320. package/dist/runtime/subsystems/auth/backends/state-store.memory-backend.js +5 -47
  321. package/dist/runtime/subsystems/auth/backends/state-store.memory-backend.js.map +1 -1
  322. package/dist/runtime/subsystems/auth/controllers/auth.controller.js +5 -139
  323. package/dist/runtime/subsystems/auth/controllers/auth.controller.js.map +1 -1
  324. package/dist/runtime/subsystems/auth/index.js +53 -542
  325. package/dist/runtime/subsystems/auth/index.js.map +1 -1
  326. package/dist/runtime/subsystems/auth/middleware/requester-context.js +9 -65
  327. package/dist/runtime/subsystems/auth/middleware/requester-context.js.map +1 -1
  328. package/dist/runtime/subsystems/auth/protocols/oauth-state-store.js +4 -9
  329. package/dist/runtime/subsystems/auth/protocols/oauth-state-store.js.map +1 -1
  330. package/dist/runtime/subsystems/auth/runtime/connection-broken.error.js +4 -15
  331. package/dist/runtime/subsystems/auth/runtime/connection-broken.error.js.map +1 -1
  332. package/dist/runtime/subsystems/auth/runtime/oauth2-refresh.strategy.js +5 -104
  333. package/dist/runtime/subsystems/auth/runtime/oauth2-refresh.strategy.js.map +1 -1
  334. package/dist/runtime/subsystems/auth/runtime/session-expired.error.js +5 -16
  335. package/dist/runtime/subsystems/auth/runtime/session-expired.error.js.map +1 -1
  336. package/dist/runtime/subsystems/auth/runtime/with-auth-retry.js +5 -29
  337. package/dist/runtime/subsystems/auth/runtime/with-auth-retry.js.map +1 -1
  338. package/dist/runtime/subsystems/bridge/assert-tenant-id.js +5 -18
  339. package/dist/runtime/subsystems/bridge/assert-tenant-id.js.map +1 -1
  340. package/dist/runtime/subsystems/bridge/bridge-delivery-handler.js +12 -184
  341. package/dist/runtime/subsystems/bridge/bridge-delivery-handler.js.map +1 -1
  342. package/dist/runtime/subsystems/bridge/bridge-delivery.drizzle-backend.js +10 -448
  343. package/dist/runtime/subsystems/bridge/bridge-delivery.drizzle-backend.js.map +1 -1
  344. package/dist/runtime/subsystems/bridge/bridge-delivery.memory-backend.js +5 -126
  345. package/dist/runtime/subsystems/bridge/bridge-delivery.memory-backend.js.map +1 -1
  346. package/dist/runtime/subsystems/bridge/bridge-delivery.schema.js +6 -308
  347. package/dist/runtime/subsystems/bridge/bridge-delivery.schema.js.map +1 -1
  348. package/dist/runtime/subsystems/bridge/bridge-errors.js +6 -35
  349. package/dist/runtime/subsystems/bridge/bridge-errors.js.map +1 -1
  350. package/dist/runtime/subsystems/bridge/bridge-outbox-drain-hook.js +14 -606
  351. package/dist/runtime/subsystems/bridge/bridge-outbox-drain-hook.js.map +1 -1
  352. package/dist/runtime/subsystems/bridge/bridge.module.js +35 -3476
  353. package/dist/runtime/subsystems/bridge/bridge.module.js.map +1 -1
  354. package/dist/runtime/subsystems/bridge/bridge.tokens.js +9 -7
  355. package/dist/runtime/subsystems/bridge/bridge.tokens.js.map +1 -1
  356. package/dist/runtime/subsystems/bridge/event-flow.service.js +11 -137
  357. package/dist/runtime/subsystems/bridge/event-flow.service.js.map +1 -1
  358. package/dist/runtime/subsystems/bridge/generated/registry.js +4 -2
  359. package/dist/runtime/subsystems/bridge/generated/registry.js.map +1 -1
  360. package/dist/runtime/subsystems/bridge/index.js +60 -3470
  361. package/dist/runtime/subsystems/bridge/index.js.map +1 -1
  362. package/dist/runtime/subsystems/bridge/reserved-pools.js +4 -6
  363. package/dist/runtime/subsystems/bridge/reserved-pools.js.map +1 -1
  364. package/dist/runtime/subsystems/cache/cache.drizzle-backend.js +10 -133
  365. package/dist/runtime/subsystems/cache/cache.drizzle-backend.js.map +1 -1
  366. package/dist/runtime/subsystems/cache/cache.memory-backend.js +6 -101
  367. package/dist/runtime/subsystems/cache/cache.memory-backend.js.map +1 -1
  368. package/dist/runtime/subsystems/cache/cache.module.js +10 -278
  369. package/dist/runtime/subsystems/cache/cache.module.js.map +1 -1
  370. package/dist/runtime/subsystems/cache/cache.schema.js +4 -14
  371. package/dist/runtime/subsystems/cache/cache.schema.js.map +1 -1
  372. package/dist/runtime/subsystems/cache/cache.tokens.js +6 -7
  373. package/dist/runtime/subsystems/cache/cache.tokens.js.map +1 -1
  374. package/dist/runtime/subsystems/cache/index.js +20 -278
  375. package/dist/runtime/subsystems/cache/index.js.map +1 -1
  376. package/dist/runtime/subsystems/events/domain-events.schema.js +3 -72
  377. package/dist/runtime/subsystems/events/domain-events.schema.js.map +1 -1
  378. package/dist/runtime/subsystems/events/event-bus.drizzle-backend.js +9 -413
  379. package/dist/runtime/subsystems/events/event-bus.drizzle-backend.js.map +1 -1
  380. package/dist/runtime/subsystems/events/event-bus.memory-backend.js +7 -235
  381. package/dist/runtime/subsystems/events/event-bus.memory-backend.js.map +1 -1
  382. package/dist/runtime/subsystems/events/event-bus.redis-backend.js +8 -20
  383. package/dist/runtime/subsystems/events/event-bus.redis-backend.js.map +1 -1
  384. package/dist/runtime/subsystems/events/event-keyset-cursor.js +8 -30
  385. package/dist/runtime/subsystems/events/event-keyset-cursor.js.map +1 -1
  386. package/dist/runtime/subsystems/events/event-read.protocol.js +2 -0
  387. package/dist/runtime/subsystems/events/event-read.protocol.js.map +1 -1
  388. package/dist/runtime/subsystems/events/events-errors.js +4 -11
  389. package/dist/runtime/subsystems/events/events-errors.js.map +1 -1
  390. package/dist/runtime/subsystems/events/events.module.js +15 -949
  391. package/dist/runtime/subsystems/events/events.module.js.map +1 -1
  392. package/dist/runtime/subsystems/events/events.tokens.js +10 -11
  393. package/dist/runtime/subsystems/events/events.tokens.js.map +1 -1
  394. package/dist/runtime/subsystems/events/generated/bus.js +9 -240
  395. package/dist/runtime/subsystems/events/generated/bus.js.map +1 -1
  396. package/dist/runtime/subsystems/events/generated/index.js +23 -240
  397. package/dist/runtime/subsystems/events/generated/index.js.map +1 -1
  398. package/dist/runtime/subsystems/events/generated/registry.js +5 -82
  399. package/dist/runtime/subsystems/events/generated/registry.js.map +1 -1
  400. package/dist/runtime/subsystems/events/generated/schemas.js +12 -52
  401. package/dist/runtime/subsystems/events/generated/schemas.js.map +1 -1
  402. package/dist/runtime/subsystems/events/generated/types.js +1 -0
  403. package/dist/runtime/subsystems/events/index.js +32 -949
  404. package/dist/runtime/subsystems/events/index.js.map +1 -1
  405. package/dist/runtime/subsystems/index.d.ts +5 -1
  406. package/dist/runtime/subsystems/index.js +182 -5912
  407. package/dist/runtime/subsystems/index.js.map +1 -1
  408. package/dist/runtime/subsystems/integration/build-change-source.js +6 -178
  409. package/dist/runtime/subsystems/integration/build-change-source.js.map +1 -1
  410. package/dist/runtime/subsystems/integration/deep-equal.differ.js +4 -109
  411. package/dist/runtime/subsystems/integration/deep-equal.differ.js.map +1 -1
  412. package/dist/runtime/subsystems/integration/detection-config.schema.js +11 -78
  413. package/dist/runtime/subsystems/integration/detection-config.schema.js.map +1 -1
  414. package/dist/runtime/subsystems/integration/entity-change-source-registry.memory.js +5 -30
  415. package/dist/runtime/subsystems/integration/entity-change-source-registry.memory.js.map +1 -1
  416. package/dist/runtime/subsystems/integration/entity-change-source-registry.protocol.js +4 -9
  417. package/dist/runtime/subsystems/integration/entity-change-source-registry.protocol.js.map +1 -1
  418. package/dist/runtime/subsystems/integration/execute-integration.use-case.js +6 -239
  419. package/dist/runtime/subsystems/integration/execute-integration.use-case.js.map +1 -1
  420. package/dist/runtime/subsystems/integration/incremental-read.js +5 -144
  421. package/dist/runtime/subsystems/integration/incremental-read.js.map +1 -1
  422. package/dist/runtime/subsystems/integration/index.js +83 -1352
  423. package/dist/runtime/subsystems/integration/index.js.map +1 -1
  424. package/dist/runtime/subsystems/integration/integration-audit.schema.js +10 -155
  425. package/dist/runtime/subsystems/integration/integration-audit.schema.js.map +1 -1
  426. package/dist/runtime/subsystems/integration/integration-cursor-store.drizzle-backend.js +7 -270
  427. package/dist/runtime/subsystems/integration/integration-cursor-store.drizzle-backend.js.map +1 -1
  428. package/dist/runtime/subsystems/integration/integration-cursor-store.memory-backend.js +4 -65
  429. package/dist/runtime/subsystems/integration/integration-cursor-store.memory-backend.js.map +1 -1
  430. package/dist/runtime/subsystems/integration/integration-errors.js +5 -15
  431. package/dist/runtime/subsystems/integration/integration-errors.js.map +1 -1
  432. package/dist/runtime/subsystems/integration/integration-field-diff.protocol.js +5 -7
  433. package/dist/runtime/subsystems/integration/integration-field-diff.protocol.js.map +1 -1
  434. package/dist/runtime/subsystems/integration/integration-run-recorder.drizzle-backend.js +8 -303
  435. package/dist/runtime/subsystems/integration/integration-run-recorder.drizzle-backend.js.map +1 -1
  436. package/dist/runtime/subsystems/integration/integration-run-recorder.memory-backend.js +5 -125
  437. package/dist/runtime/subsystems/integration/integration-run-recorder.memory-backend.js.map +1 -1
  438. package/dist/runtime/subsystems/integration/integration.module.js +13 -700
  439. package/dist/runtime/subsystems/integration/integration.module.js.map +1 -1
  440. package/dist/runtime/subsystems/integration/integration.tokens.js +11 -9
  441. package/dist/runtime/subsystems/integration/integration.tokens.js.map +1 -1
  442. package/dist/runtime/subsystems/integration/loopback.middleware.js +4 -16
  443. package/dist/runtime/subsystems/integration/loopback.middleware.js.map +1 -1
  444. package/dist/runtime/subsystems/integration/poll-change-source.d.ts +1 -1
  445. package/dist/runtime/subsystems/integration/poll-change-source.js +4 -89
  446. package/dist/runtime/subsystems/integration/poll-change-source.js.map +1 -1
  447. package/dist/runtime/subsystems/integration/webhook-change-source.d.ts +4 -3
  448. package/dist/runtime/subsystems/integration/webhook-change-source.js +4 -70
  449. package/dist/runtime/subsystems/integration/webhook-change-source.js.map +1 -1
  450. package/dist/runtime/subsystems/jobs/bullmq.config.js +9 -140
  451. package/dist/runtime/subsystems/jobs/bullmq.config.js.map +1 -1
  452. package/dist/runtime/subsystems/jobs/index.js +88 -2691
  453. package/dist/runtime/subsystems/jobs/index.js.map +1 -1
  454. package/dist/runtime/subsystems/jobs/job-handler.base.js +10 -49
  455. package/dist/runtime/subsystems/jobs/job-handler.base.js.map +1 -1
  456. package/dist/runtime/subsystems/jobs/job-orchestration.schema.js +13 -152
  457. package/dist/runtime/subsystems/jobs/job-orchestration.schema.js.map +1 -1
  458. package/dist/runtime/subsystems/jobs/job-orchestrator.bullmq-backend.js +36 -699
  459. package/dist/runtime/subsystems/jobs/job-orchestrator.bullmq-backend.js.map +1 -1
  460. package/dist/runtime/subsystems/jobs/job-orchestrator.drizzle-backend.js +10 -564
  461. package/dist/runtime/subsystems/jobs/job-orchestrator.drizzle-backend.js.map +1 -1
  462. package/dist/runtime/subsystems/jobs/job-orchestrator.memory-backend.js +10 -824
  463. package/dist/runtime/subsystems/jobs/job-orchestrator.memory-backend.js.map +1 -1
  464. package/dist/runtime/subsystems/jobs/job-run-keyset-cursor.js +9 -51
  465. package/dist/runtime/subsystems/jobs/job-run-keyset-cursor.js.map +1 -1
  466. package/dist/runtime/subsystems/jobs/job-run-service.drizzle-backend.js +9 -416
  467. package/dist/runtime/subsystems/jobs/job-run-service.drizzle-backend.js.map +1 -1
  468. package/dist/runtime/subsystems/jobs/job-run-service.memory-backend.js +9 -290
  469. package/dist/runtime/subsystems/jobs/job-run-service.memory-backend.js.map +1 -1
  470. package/dist/runtime/subsystems/jobs/job-step-service.drizzle-backend.js +5 -213
  471. package/dist/runtime/subsystems/jobs/job-step-service.drizzle-backend.js.map +1 -1
  472. package/dist/runtime/subsystems/jobs/job-step-service.memory-backend.js +5 -131
  473. package/dist/runtime/subsystems/jobs/job-step-service.memory-backend.js.map +1 -1
  474. package/dist/runtime/subsystems/jobs/job-worker.bullmq-backend.js +9 -175
  475. package/dist/runtime/subsystems/jobs/job-worker.bullmq-backend.js.map +1 -1
  476. package/dist/runtime/subsystems/jobs/job-worker.js +14 -613
  477. package/dist/runtime/subsystems/jobs/job-worker.js.map +1 -1
  478. package/dist/runtime/subsystems/jobs/job-worker.module.js +23 -2647
  479. package/dist/runtime/subsystems/jobs/job-worker.module.js.map +1 -1
  480. package/dist/runtime/subsystems/jobs/jobs-domain.module.js +19 -1897
  481. package/dist/runtime/subsystems/jobs/jobs-domain.module.js.map +1 -1
  482. package/dist/runtime/subsystems/jobs/jobs-domain.tokens.js +8 -9
  483. package/dist/runtime/subsystems/jobs/jobs-domain.tokens.js.map +1 -1
  484. package/dist/runtime/subsystems/jobs/jobs-errors.js +10 -78
  485. package/dist/runtime/subsystems/jobs/jobs-errors.js.map +1 -1
  486. package/dist/runtime/subsystems/jobs/memory-job-store.js +4 -15
  487. package/dist/runtime/subsystems/jobs/memory-job-store.js.map +1 -1
  488. package/dist/runtime/subsystems/jobs/pool-config.loader.js +9 -124
  489. package/dist/runtime/subsystems/jobs/pool-config.loader.js.map +1 -1
  490. package/dist/runtime/subsystems/observability/index.js +21 -310
  491. package/dist/runtime/subsystems/observability/index.js.map +1 -1
  492. package/dist/runtime/subsystems/observability/observability-errors.js +4 -9
  493. package/dist/runtime/subsystems/observability/observability-errors.js.map +1 -1
  494. package/dist/runtime/subsystems/observability/observability.module.js +11 -300
  495. package/dist/runtime/subsystems/observability/observability.module.js.map +1 -1
  496. package/dist/runtime/subsystems/observability/observability.service.js +9 -197
  497. package/dist/runtime/subsystems/observability/observability.service.js.map +1 -1
  498. package/dist/runtime/subsystems/observability/observability.tokens.js +5 -3
  499. package/dist/runtime/subsystems/observability/observability.tokens.js.map +1 -1
  500. package/dist/runtime/subsystems/observability/reporters/bridge-metrics.reporter.js +4 -84
  501. package/dist/runtime/subsystems/observability/reporters/bridge-metrics.reporter.js.map +1 -1
  502. package/dist/runtime/subsystems/observability/reporters/index.js +5 -84
  503. package/dist/runtime/subsystems/observability/reporters/index.js.map +1 -1
  504. package/dist/runtime/subsystems/storage/index.js +15 -200
  505. package/dist/runtime/subsystems/storage/index.js.map +1 -1
  506. package/dist/runtime/subsystems/storage/storage.local-backend.js +4 -103
  507. package/dist/runtime/subsystems/storage/storage.local-backend.js.map +1 -1
  508. package/dist/runtime/subsystems/storage/storage.memory-backend.js +5 -68
  509. package/dist/runtime/subsystems/storage/storage.memory-backend.js.map +1 -1
  510. package/dist/runtime/subsystems/storage/storage.module.js +8 -200
  511. package/dist/runtime/subsystems/storage/storage.module.js.map +1 -1
  512. package/dist/runtime/subsystems/storage/storage.tokens.js +5 -6
  513. package/dist/runtime/subsystems/storage/storage.tokens.js.map +1 -1
  514. package/dist/runtime/subsystems/storage/storage.utils.js +4 -14
  515. package/dist/runtime/subsystems/storage/storage.utils.js.map +1 -1
  516. package/dist/runtime/subsystems/token-key.js +5 -3
  517. package/dist/runtime/subsystems/token-key.js.map +1 -1
  518. package/dist/src/cli/index.js +637 -5454
  519. package/dist/src/cli/index.js.map +1 -1
  520. package/dist/src/index.js +68 -4170
  521. package/dist/src/index.js.map +1 -1
  522. package/package.json +1 -1
  523. package/runtime/subsystems/bridge/bridge-outbox-drain-hook.ts +44 -21
  524. package/runtime/subsystems/index.ts +27 -0
  525. package/runtime/subsystems/integration/poll-change-source.ts +10 -7
  526. package/runtime/subsystems/integration/webhook-change-source.ts +12 -8
  527. package/runtime/subsystems/jobs/job-worker.ts +17 -11
@@ -1,242 +1,9 @@
1
- var __defProp = Object.defineProperty;
2
- var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
3
- var __decorateClass = (decorators, target, key, kind) => {
4
- var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc(target, key) : target;
5
- for (var i = decorators.length - 1, decorator; i >= 0; i--)
6
- if (decorator = decorators[i])
7
- result = (kind ? decorator(target, key, result) : decorator(result)) || result;
8
- if (kind && result) __defProp(target, key, result);
9
- return result;
10
- };
11
- var __decorateParam = (index, decorator) => (target, key) => decorator(target, key, index);
12
-
13
- // runtime/subsystems/integration/execute-integration.use-case.ts
14
- import { Inject, Injectable, Logger, Optional } from "@nestjs/common";
15
-
16
- // runtime/subsystems/integration/integration-errors.ts
17
- var MissingTenantIdError = class extends Error {
18
- name = "MissingTenantIdError";
19
- constructor(operation) {
20
- super(
21
- `Missing tenantId for integration operation '${operation}'. IntegrationModule is configured with multiTenant: true \u2014 every call must include a non-null tenantId. Either pass the tenantId or disable multi-tenancy on the module.`
22
- );
23
- }
24
- };
25
- function assertTenantId(tenantId, options) {
26
- if (!options.multiTenant) return;
27
- if (tenantId === void 0 || tenantId === null) {
28
- throw new MissingTenantIdError(options.operation);
29
- }
30
- }
31
-
32
- // runtime/subsystems/integration/integration.tokens.ts
33
- var INTEGRATION_CHANGE_SOURCE = "INTEGRATION_CHANGE_SOURCE";
34
- var INTEGRATION_CURSOR_STORE = "INTEGRATION_CURSOR_STORE";
35
- var INTEGRATION_FIELD_DIFFER = "INTEGRATION_FIELD_DIFFER";
36
- var INTEGRATION_SINK = "INTEGRATION_SINK";
37
- var INTEGRATION_RUN_RECORDER = "INTEGRATION_RUN_RECORDER";
38
- var INTEGRATION_MULTI_TENANT = "INTEGRATION_MULTI_TENANT";
39
-
40
- // runtime/subsystems/integration/execute-integration.use-case.ts
41
- var ExecuteIntegrationUseCase = class {
42
- constructor(source, cursors, differ, sink, recorder, multiTenant = false) {
43
- this.source = source;
44
- this.cursors = cursors;
45
- this.differ = differ;
46
- this.sink = sink;
47
- this.recorder = recorder;
48
- this.multiTenant = multiTenant;
49
- }
50
- source;
51
- cursors;
52
- differ;
53
- sink;
54
- recorder;
55
- multiTenant;
56
- logger = new Logger(ExecuteIntegrationUseCase.name);
57
- async execute(input) {
58
- assertTenantId(input.tenantId, {
59
- multiTenant: this.multiTenant,
60
- operation: "execute"
61
- });
62
- const source = input.sourceOverride ?? this.source;
63
- const startedAt = Date.now();
64
- const cursorBefore = await this.cursors.get(input.subscription.id, input.tenantId);
65
- const { id: runId } = await this.recorder.startRun({
66
- subscriptionId: input.subscription.id,
67
- direction: input.direction,
68
- action: input.action,
69
- cursorBefore,
70
- tenantId: input.tenantId
71
- });
72
- let recordsFound = 0;
73
- let recordsProcessed = 0;
74
- let recordsFailed = 0;
75
- let latestCursor = cursorBefore;
76
- let cursorAdvanced = false;
77
- let runError = null;
78
- let status = "no_changes";
79
- try {
80
- for await (const change of source.listChanges(input.subscription, cursorBefore)) {
81
- recordsFound++;
82
- latestCursor = change.cursor;
83
- cursorAdvanced = true;
84
- try {
85
- await this.processChange(runId, input, change);
86
- recordsProcessed++;
87
- } catch (err) {
88
- recordsFailed++;
89
- const message = err instanceof Error ? err.message : String(err);
90
- this.logger.warn(
91
- `integration item failed: subscription=${input.subscription.id} externalId=${change.externalId}: ${message}`
92
- );
93
- await this.recorder.recordItem({
94
- integrationRunId: runId,
95
- entityType: input.subscription.domain,
96
- externalId: change.externalId,
97
- operation: change.operation === "deleted" ? "deleted" : "updated",
98
- status: "failed",
99
- changedFields: {},
100
- error: message,
101
- tenantId: input.tenantId
102
- });
103
- }
104
- }
105
- if (recordsFailed > 0 && recordsProcessed === 0 && recordsFound > 0) {
106
- status = "failed";
107
- runError = `all ${recordsFailed} records failed`;
108
- } else if (recordsFound === 0) {
109
- status = "no_changes";
110
- } else {
111
- status = "success";
112
- }
113
- } catch (err) {
114
- status = "failed";
115
- runError = err instanceof Error ? err.message : String(err);
116
- this.logger.error(
117
- `integration source failed: subscription=${input.subscription.id}: ${runError}`
118
- );
119
- }
120
- if (cursorAdvanced && latestCursor !== null && latestCursor !== void 0) {
121
- try {
122
- await this.cursors.put(input.subscription.id, latestCursor, input.tenantId);
123
- } catch (err) {
124
- const message = err instanceof Error ? err.message : String(err);
125
- this.logger.error(
126
- `cursor put failed: subscription=${input.subscription.id}: ${message}`
127
- );
128
- if (status !== "failed") {
129
- status = "failed";
130
- runError = `cursor put failed: ${message}`;
131
- }
132
- }
133
- }
134
- const durationMs = Date.now() - startedAt;
135
- await this.recorder.completeRun(runId, {
136
- status,
137
- recordsFound,
138
- recordsProcessed,
139
- cursorAfter: cursorAdvanced ? latestCursor : cursorBefore,
140
- durationMs,
141
- error: runError
142
- });
143
- return {
144
- runId,
145
- status,
146
- recordsFound,
147
- recordsProcessed,
148
- recordsFailed,
149
- cursorBefore,
150
- cursorAfter: cursorAdvanced ? latestCursor : cursorBefore,
151
- durationMs,
152
- error: runError
153
- };
154
- }
155
- async processChange(runId, input, change) {
156
- if (change.operation === "deleted") {
157
- const result = await this.sink.softDeleteByExternalId(
158
- input.userId,
159
- change.externalId
160
- );
161
- await this.recorder.recordItem({
162
- integrationRunId: runId,
163
- entityType: input.subscription.domain,
164
- externalId: change.externalId,
165
- localId: result?.id ?? null,
166
- operation: result ? "deleted" : "noop",
167
- status: "success",
168
- changedFields: {},
169
- tenantId: input.tenantId
170
- });
171
- return;
172
- }
173
- const existing = await this.sink.findByExternalId(
174
- input.userId,
175
- change.externalId
176
- );
177
- const diff = this.differ.diff(
178
- existing,
179
- change.record,
180
- change.providerChangedFields
181
- );
182
- if (diff === "noop") {
183
- if (!this.sink.reprojectsOnNoop) {
184
- await this.recorder.recordItem({
185
- integrationRunId: runId,
186
- entityType: input.subscription.domain,
187
- externalId: change.externalId,
188
- localId: null,
189
- operation: "noop",
190
- status: "success",
191
- changedFields: {},
192
- tenantId: input.tenantId
193
- });
194
- return;
195
- }
196
- const { id: noopLocalId } = await this.sink.upsertByExternalId(
197
- input.userId,
198
- change.record,
199
- input.provider
200
- );
201
- await this.recorder.recordItem({
202
- integrationRunId: runId,
203
- entityType: input.subscription.domain,
204
- externalId: change.externalId,
205
- localId: noopLocalId,
206
- operation: "noop",
207
- status: "success",
208
- changedFields: {},
209
- tenantId: input.tenantId
210
- });
211
- return;
212
- }
213
- const { id: localId } = await this.sink.upsertByExternalId(
214
- input.userId,
215
- change.record,
216
- input.provider
217
- );
218
- await this.recorder.recordItem({
219
- integrationRunId: runId,
220
- entityType: input.subscription.domain,
221
- externalId: change.externalId,
222
- localId,
223
- operation: existing === null ? "created" : "updated",
224
- status: "success",
225
- changedFields: diff,
226
- tenantId: input.tenantId
227
- });
228
- }
229
- };
230
- ExecuteIntegrationUseCase = __decorateClass([
231
- Injectable(),
232
- __decorateParam(0, Inject(INTEGRATION_CHANGE_SOURCE)),
233
- __decorateParam(1, Inject(INTEGRATION_CURSOR_STORE)),
234
- __decorateParam(2, Inject(INTEGRATION_FIELD_DIFFER)),
235
- __decorateParam(3, Inject(INTEGRATION_SINK)),
236
- __decorateParam(4, Inject(INTEGRATION_RUN_RECORDER)),
237
- __decorateParam(5, Optional()),
238
- __decorateParam(5, Inject(INTEGRATION_MULTI_TENANT))
239
- ], ExecuteIntegrationUseCase);
1
+ import {
2
+ ExecuteIntegrationUseCase
3
+ } from "../../../chunk-OGIZXGPY.js";
4
+ import "../../../chunk-MZ6GV4YF.js";
5
+ import "../../../chunk-S7C6TIIF.js";
6
+ import "../../../chunk-2E224ZSN.js";
240
7
  export {
241
8
  ExecuteIntegrationUseCase
242
9
  };
@@ -1 +1 @@
1
- {"version":3,"sources":["../../../../runtime/subsystems/integration/execute-integration.use-case.ts","../../../../runtime/subsystems/integration/integration-errors.ts","../../../../runtime/subsystems/integration/integration.tokens.ts"],"sourcesContent":["/**\n * ExecuteIntegrationUseCase — the generic integration orchestrator (SYNC-5).\n *\n * One class. Reused across every `(provider, detection-mode, canonical-entity)`\n * tuple. Parameterized over `T` so canonical records stay typed end-to-end.\n *\n * Flow per run:\n *\n * 1. `recorder.startRun(...)` — opens a `integration_runs` row in 'running'.\n * 2. for each change yielded by `source.listChanges(subscription, cursorBefore)`:\n * a. differ.diff(existing, incoming) → 'noop' short-circuits to\n * a noop audit row (no sink write).\n * b. sink.upsertByExternalId / softDeleteByExternalId → records\n * the local id on the audit row.\n * c. per-item try/catch — a failed item increments the failed\n * counter and records `status: 'failed'` with `error`, but\n * does NOT abort the run.\n * d. advance `latestCursor = change.cursor` as the iterator moves.\n * 3. `cursors.put(subscription.id, latestCursor)` when the loop completes\n * AND at least one cursor advance happened. On exceptions from the\n * source iterator (auth expiry, network error), we persist the\n * last-good cursor so the next run resumes from the last known\n * successful position.\n * 4. `finally { recorder.completeRun(...) }` — always terminates the run.\n *\n * Loopback suppression — when a consumer's writes echo back on the next\n * inbound poll/CDC/webhook — is composed into the source's middleware\n * chain via `createLoopbackMiddleware(store)` (#226-5 / ADR-033). The\n * orchestrator no longer special-cases echoes: middleware drops them\n * before they reach this loop. Consumers that don't have outbound\n * writeback paths simply omit the middleware.\n *\n * ## Generics\n *\n * - `T` = canonical record shape from the adapter side. Same `T` flows\n * through `IChangeSource<T>`, `IFieldDiffer<T>`, `IIntegrationSink<T>`.\n *\n * ## No CRM bleed\n *\n * Per the SYNC-5 issue's extraction notes (HS-9 finding), this orchestrator\n * is strictly provider-agnostic:\n * - `entityType` is `string` throughout; no `'opportunity' | 'account' | ...`\n * narrowing leaks into the use case\n * - the upstream consumer's `IntegrationRunRecorderService` class injection replaced with the\n * `IIntegrationRunRecorder` protocol (backend lands in SYNC-4)\n */\nimport { Inject, Injectable, Logger, Optional } from '@nestjs/common';\nimport type { IChangeSource, Change } from './integration-change-source.protocol';\nimport type { ICursorStore } from './integration-cursor-store.protocol';\nimport type { IFieldDiffer, FieldDiff } from './integration-field-diff.protocol';\nimport type { IIntegrationSink } from './integration-sink.protocol';\nimport type { IIntegrationRunRecorder } from './integration-run-recorder.protocol';\nimport { assertTenantId } from './integration-errors';\nimport {\n INTEGRATION_CHANGE_SOURCE,\n INTEGRATION_CURSOR_STORE,\n INTEGRATION_FIELD_DIFFER,\n INTEGRATION_MULTI_TENANT,\n INTEGRATION_RUN_RECORDER,\n INTEGRATION_SINK,\n} from './integration.tokens';\n\n// ============================================================================\n// Inputs + result\n// ============================================================================\n\nexport interface ExecuteIntegrationInput<T> {\n /** The subscription whose cursor/identity frames this run. */\n readonly subscription: {\n readonly id: string;\n readonly domain: string; // entityType — used on audit rows\n readonly externalRef?: string | null;\n };\n /** Per-run user context; threaded through sink writes. */\n readonly userId: string;\n /** Provider label persisted on saved rows, e.g. `'salesforce-crm'`. */\n readonly provider: string;\n /** Run direction — almost always `'inbound'`. Reserved for writeback. */\n readonly direction: 'inbound' | 'outbound';\n /** Detection mode — maps 1:1 to `integration_runs.action`. */\n readonly action: 'poll' | 'cdc' | 'webhook' | 'manual' | 'writeback';\n /** Multi-tenant deployments pass the tenant id through. */\n readonly tenantId?: string | null;\n /**\n * Optional override — inject a specific change source for this run when\n * the DI-bound source is not the one to use (e.g. manual backfill with\n * a custom cursor). Defaults to the DI-resolved `INTEGRATION_CHANGE_SOURCE`.\n */\n readonly sourceOverride?: IChangeSource<T>;\n}\n\nexport interface ExecuteIntegrationResult {\n readonly runId: string;\n readonly status: 'success' | 'no_changes' | 'failed';\n readonly recordsFound: number;\n readonly recordsProcessed: number;\n readonly recordsFailed: number;\n readonly cursorBefore: unknown | null;\n readonly cursorAfter: unknown | null;\n readonly durationMs: number;\n readonly error?: string | null;\n}\n\n// ============================================================================\n// ExecuteIntegrationUseCase\n// ============================================================================\n\n@Injectable()\nexport class ExecuteIntegrationUseCase<T extends Record<string, unknown>> {\n private readonly logger = new Logger(ExecuteIntegrationUseCase.name);\n\n constructor(\n @Inject(INTEGRATION_CHANGE_SOURCE) private readonly source: IChangeSource<T>,\n @Inject(INTEGRATION_CURSOR_STORE) private readonly cursors: ICursorStore,\n @Inject(INTEGRATION_FIELD_DIFFER) private readonly differ: IFieldDiffer<T>,\n @Inject(INTEGRATION_SINK) private readonly sink: IIntegrationSink<T>,\n @Inject(INTEGRATION_RUN_RECORDER) private readonly recorder: IIntegrationRunRecorder,\n @Optional()\n @Inject(INTEGRATION_MULTI_TENANT)\n private readonly multiTenant: boolean = false,\n ) {}\n\n async execute(input: ExecuteIntegrationInput<T>): Promise<ExecuteIntegrationResult> {\n // Defense-in-depth tenancy guard — fire BEFORE startRun so a rejected\n // input never leaves a dangling `status=running` row. Backends also\n // enforce (SYNC-4), but failing fast at the orchestrator boundary is\n // cheaper for observability, metrics, and manual cleanup.\n assertTenantId(input.tenantId, {\n multiTenant: this.multiTenant,\n operation: 'execute',\n });\n\n const source = input.sourceOverride ?? this.source;\n const startedAt = Date.now();\n const cursorBefore = await this.cursors.get(input.subscription.id, input.tenantId);\n\n const { id: runId } = await this.recorder.startRun({\n subscriptionId: input.subscription.id,\n direction: input.direction,\n action: input.action,\n cursorBefore,\n tenantId: input.tenantId,\n });\n\n let recordsFound = 0;\n let recordsProcessed = 0;\n let recordsFailed = 0;\n let latestCursor: unknown | null = cursorBefore;\n let cursorAdvanced = false;\n let runError: string | null = null;\n let status: 'success' | 'no_changes' | 'failed' = 'no_changes';\n\n try {\n for await (const change of source.listChanges(input.subscription, cursorBefore)) {\n recordsFound++;\n latestCursor = change.cursor;\n cursorAdvanced = true;\n\n try {\n await this.processChange(runId, input, change);\n recordsProcessed++;\n } catch (err) {\n recordsFailed++;\n const message = err instanceof Error ? err.message : String(err);\n this.logger.warn(\n `integration item failed: subscription=${input.subscription.id} externalId=${change.externalId}: ${message}`,\n );\n await this.recorder.recordItem({\n integrationRunId: runId,\n entityType: input.subscription.domain,\n externalId: change.externalId,\n operation: change.operation === 'deleted' ? 'deleted' : 'updated',\n status: 'failed',\n changedFields: {},\n error: message,\n tenantId: input.tenantId,\n });\n }\n }\n\n if (recordsFailed > 0 && recordsProcessed === 0 && recordsFound > 0) {\n // Every record we saw failed — call the run a failure, not a\n // success. Partial success (some processed, some failed) still\n // counts as 'success' so the cursor advances.\n status = 'failed';\n runError = `all ${recordsFailed} records failed`;\n } else if (recordsFound === 0) {\n status = 'no_changes';\n } else {\n status = 'success';\n }\n } catch (err) {\n // Source iterator itself threw — cursor DOES NOT advance past the\n // last-successful cursor. `latestCursor` still holds the last\n // `change.cursor` we observed, which is the furthest we know to\n // have delivered. Persist it (below) so next run resumes there.\n status = 'failed';\n runError = err instanceof Error ? err.message : String(err);\n this.logger.error(\n `integration source failed: subscription=${input.subscription.id}: ${runError}`,\n );\n }\n\n // Persist cursor advance only when something actually moved. Never\n // overwrite a valid cursor with `null` on a no-change run.\n if (cursorAdvanced && latestCursor !== null && latestCursor !== undefined) {\n try {\n await this.cursors.put(input.subscription.id, latestCursor, input.tenantId);\n } catch (err) {\n const message = err instanceof Error ? err.message : String(err);\n this.logger.error(\n `cursor put failed: subscription=${input.subscription.id}: ${message}`,\n );\n if (status !== 'failed') {\n status = 'failed';\n runError = `cursor put failed: ${message}`;\n }\n }\n }\n\n const durationMs = Date.now() - startedAt;\n\n await this.recorder.completeRun(runId, {\n status,\n recordsFound,\n recordsProcessed,\n cursorAfter: cursorAdvanced ? latestCursor : cursorBefore,\n durationMs,\n error: runError,\n });\n\n return {\n runId,\n status,\n recordsFound,\n recordsProcessed,\n recordsFailed,\n cursorBefore,\n cursorAfter: cursorAdvanced ? latestCursor : cursorBefore,\n durationMs,\n error: runError,\n };\n }\n\n private async processChange(\n runId: string,\n input: ExecuteIntegrationInput<T>,\n change: Change<T>,\n ): Promise<void> {\n // Deletion branch — no diff, no upsert; soft-delete via sink.\n if (change.operation === 'deleted') {\n const result = await this.sink.softDeleteByExternalId(\n input.userId,\n change.externalId,\n );\n await this.recorder.recordItem({\n integrationRunId: runId,\n entityType: input.subscription.domain,\n externalId: change.externalId,\n localId: result?.id ?? null,\n operation: result ? 'deleted' : 'noop',\n status: 'success',\n changedFields: {},\n tenantId: input.tenantId,\n });\n return;\n }\n\n // Create/update path — diff against local state, short-circuit on noop.\n const existing = await this.sink.findByExternalId(\n input.userId,\n change.externalId,\n );\n const diff = this.differ.diff(\n existing,\n change.record,\n change.providerChangedFields,\n );\n\n if (diff === 'noop') {\n // Sinks that declare `reprojectsOnNoop` reproject side data the differ\n // can't see (e.g. EAV field_values) — so fall through to the idempotent\n // upsert instead of short-circuiting. The canonical state is unchanged,\n // so the audit `operation` stays `'noop'`, but we capture the local id\n // returned by the upsert. Sinks without the flag keep today's behavior.\n if (!this.sink.reprojectsOnNoop) {\n await this.recorder.recordItem({\n integrationRunId: runId,\n entityType: input.subscription.domain,\n externalId: change.externalId,\n localId: null,\n operation: 'noop',\n status: 'success',\n changedFields: {},\n tenantId: input.tenantId,\n });\n return;\n }\n\n const { id: noopLocalId } = await this.sink.upsertByExternalId(\n input.userId,\n change.record,\n input.provider,\n );\n await this.recorder.recordItem({\n integrationRunId: runId,\n entityType: input.subscription.domain,\n externalId: change.externalId,\n localId: noopLocalId,\n operation: 'noop',\n status: 'success',\n changedFields: {},\n tenantId: input.tenantId,\n });\n return;\n }\n\n const { id: localId } = await this.sink.upsertByExternalId(\n input.userId,\n change.record,\n input.provider,\n );\n\n await this.recorder.recordItem({\n integrationRunId: runId,\n entityType: input.subscription.domain,\n externalId: change.externalId,\n localId,\n operation: existing === null ? 'created' : 'updated',\n status: 'success',\n changedFields: diff as FieldDiff,\n tenantId: input.tenantId,\n });\n }\n}\n","/**\n * Typed errors + shared boundary helpers for the integration subsystem.\n *\n * Classes (not bare Error) so consumers can `instanceof` them in catch\n * blocks and exception filters can map them to HTTP codes.\n *\n * Mirrors the shape of `events-errors.ts` and `jobs-errors.ts`.\n */\n\n/**\n * Thrown by the Drizzle cursor-store / run-recorder backends AND by the\n * orchestrator entry point when `INTEGRATION_MULTI_TENANT` is enabled but the\n * caller did not supply a non-null `tenantId`. Strict enforcement at the\n * boundary — explicit `null` still throws.\n *\n * Disable multi-tenancy on the module (`multiTenant: false`, the default)\n * to opt out of the requirement entirely.\n *\n * `operation` identifies the call site (e.g. `'cursor.put'`,\n * `'startRun'`, `'execute'`) so the stack-trace message points at the\n * specific boundary that rejected the input.\n */\nexport class MissingTenantIdError extends Error {\n override readonly name = 'MissingTenantIdError';\n constructor(operation: string) {\n super(\n `Missing tenantId for integration operation '${operation}'. IntegrationModule is ` +\n `configured with multiTenant: true — every call must include a ` +\n `non-null tenantId. Either pass the tenantId or disable multi-` +\n `tenancy on the module.`,\n );\n }\n}\n\n/**\n * Shared boundary guard — used at the orchestrator entry AND inside the\n * Drizzle backends. Keeping the check in one function guarantees every\n * `MissingTenantIdError` carries the same message shape regardless of the\n * site that raised it, which makes it easier for consumers to pattern-\n * match on the error in logs/metrics.\n *\n * When `multiTenant` is false, the function is a no-op — `tenantId` may\n * be anything (including `undefined`). When true, `undefined` or `null`\n * throws.\n */\nexport function assertTenantId(\n tenantId: string | null | undefined,\n options: { multiTenant: boolean; operation: string },\n): asserts tenantId is string {\n if (!options.multiTenant) return;\n if (tenantId === undefined || tenantId === null) {\n throw new MissingTenantIdError(options.operation);\n }\n}\n","/**\n * Integration subsystem — DI tokens\n *\n * String constants (not Symbols) so they match by value across import\n * boundaries — same convention as the events subsystem (`EVENT_BUS`). The\n * jobs subsystem uses Symbols for its analogous tokens; events and integration\n * stay internally consistent with strings.\n *\n * Usage in use cases:\n * ```ts\n * constructor(\n * @Inject(INTEGRATION_CHANGE_SOURCE) private readonly source: IChangeSource<CanonicalOpportunity>,\n * @Inject(INTEGRATION_CURSOR_STORE) private readonly cursors: ICursorStore,\n * @Inject(INTEGRATION_FIELD_DIFFER) private readonly differ: IFieldDiffer<CanonicalOpportunity>,\n * @Inject(INTEGRATION_SINK) private readonly sink: IIntegrationSink<CanonicalOpportunity>,\n * @Inject(INTEGRATION_RUN_RECORDER) private readonly recorder: IIntegrationRunRecorder,\n * ) {}\n * ```\n *\n * Concrete bindings are registered by `IntegrationModule.forRoot(...)` (SYNC-6).\n */\n\nexport const INTEGRATION_CHANGE_SOURCE = 'INTEGRATION_CHANGE_SOURCE' as const;\nexport const INTEGRATION_CURSOR_STORE = 'INTEGRATION_CURSOR_STORE' as const;\nexport const INTEGRATION_FIELD_DIFFER = 'INTEGRATION_FIELD_DIFFER' as const;\nexport const INTEGRATION_SINK = 'INTEGRATION_SINK' as const;\n\n/**\n * Run-recorder token (SYNC-5). Backed by `IIntegrationRunRecorder`. Drizzle impl\n * lands in SYNC-4; tests provide inline fakes.\n */\nexport const INTEGRATION_RUN_RECORDER = 'INTEGRATION_RUN_RECORDER' as const;\n\n/**\n * Injection token for the resolved `IntegrationModuleOptions` object (SYNC-6).\n *\n * Backends that need to observe module configuration (e.g. `multiTenant`\n * flag, pool filters) inject via this token. Provided automatically by\n * `IntegrationModule.forRoot(...)` / `IntegrationModule.forRootAsync(...)`.\n */\nexport const INTEGRATION_MODULE_OPTIONS = 'INTEGRATION_MODULE_OPTIONS' as const;\n\n/**\n * Injection token for the resolved multi-tenancy flag (SYNC-6).\n *\n * Provided by `IntegrationModule.forRoot(...)` as `options.multiTenant ?? false`.\n * Consumed by `ExecuteIntegrationUseCase` to enforce the tenantId-is-required rule.\n */\nexport const INTEGRATION_MULTI_TENANT = 'INTEGRATION_MULTI_TENANT' as const;\n\n/**\n * Injection token for the entity-keyed `IEntityChangeSourceRegistry` (C7,\n * #336). Bound to the codegen-emitted aggregator that folds per-provider\n * adapter contributions into one registry (RFC-0001 §3, emitted by Track D\n * D3/D4).\n *\n * A string constant, not `Symbol.for(...)`, to match this subsystem's token\n * convention (see file header). The originating issue's code block proposed a\n * `Symbol.for('@pattern-stack/codegen.entity-change-source-registry')` key,\n * predating the sync→integration consolidation onto string tokens; kept as a\n * string here for internal consistency with the other INTEGRATION_* tokens.\n */\nexport const ENTITY_CHANGE_SOURCE_REGISTRY = 'ENTITY_CHANGE_SOURCE_REGISTRY' as const;\n"],"mappings":"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","names":[]}
1
+ {"version":3,"sources":[],"sourcesContent":[],"mappings":"","names":[]}
@@ -1,147 +1,8 @@
1
- // runtime/subsystems/integration/incremental-read.ts
2
- async function mapConcurrent(ids, fn, limit) {
3
- const out = /* @__PURE__ */ new Map();
4
- if (ids.length === 0) return out;
5
- const width = Math.max(1, Math.min(limit, ids.length));
6
- let next = 0;
7
- const worker = async () => {
8
- while (next < ids.length) {
9
- const idx = next++;
10
- const id = ids[idx];
11
- out.set(id, await fn(id));
12
- }
13
- };
14
- await Promise.all(Array.from({ length: width }, worker));
15
- return out;
16
- }
17
- var IncrementalReadBase = class {
18
- /**
19
- * Whether the vendor takes the request predicate server-side. Declared, not
20
- * enforced here — surfaced into the emission manifest (R3) so the falsifier
21
- * suite (R4) can record which adapters filter post-hydrate. `false` is the
22
- * honest floor (e.g. Gmail without `q=`), handled via `matchesRecord`.
23
- */
24
- filterPushdown = false;
25
- /** Max concurrent in-flight calls for a `mapConcurrent`-built `hydrate`. */
26
- hydrateConcurrency = 10;
27
- /** `Change<T>.source` provenance stamped by `listChanges`. */
28
- changeSource = "poll";
29
- /**
30
- * Whether this source's cursor strategy is divisible (RFC-0003 §3). When
31
- * `true` (default — sortable watermarks like `systemModstamp`/`timestamp`/
32
- * `replayId`), `listChanges` emits each record's per-ref cursor, so the
33
- * orchestrator may checkpoint mid-walk and a crash resumes from the last
34
- * delivered ref.
35
- *
36
- * When `false` (atomic opaque tokens — Gmail `historyId`, Calendar
37
- * `syncToken`), `listChanges` WITHHOLDS per-ref cursors and emits the
38
- * end-of-walk token only on the final record, so the orchestrator's
39
- * persist-last-yielded lifecycle can never persist an unresumable mid-walk
40
- * token. The cost is blast-radius: an interrupted atomic run resumes
41
- * all-or-nothing from the prior persisted token. For atomic *backfills* that
42
- * radius is the whole enumerate walk — bound it with `ReadRequest.pageSize`
43
- * (smaller pages ⇒ shorter walks per run). Per-page atomic checkpointing is a
44
- * future refinement; R2 gates at end-of-walk.
45
- *
46
- * Codegen (R3) sets this from the strategy kind via `isDivisibleCursor`.
47
- */
48
- cursorDivisible = true;
49
- // ---- Optional filter hooks — exactly one is live per `filterPushdown` ----
50
- /** Pre-hydrate predicate over the cheap ref (preferred — avoids hydration). */
51
- matchesRef(_ref, _filter) {
52
- return true;
53
- }
54
- /** Post-hydrate predicate over the canonical record (the no-pushdown floor). */
55
- matchesRecord(_record, _filter) {
56
- return true;
57
- }
58
- /**
59
- * Resolve the filter for a subscription when adapting to `listChanges`
60
- * (which has no filter argument). Defaults to none; codegen wiring (R3)
61
- * overrides this to thread `DetectionConfig.filters`.
62
- */
63
- filterFor(_subscription) {
64
- return void 0;
65
- }
66
- // ---- PROVIDED by the base ----
67
- /**
68
- * Stream canonical records for a request. Filter is applied BEFORE hydrate
69
- * (structural: a kept ref is hydrated, a rejected one never is), so an
70
- * adapter cannot hydrate-then-discard. A hydrate miss (deleted mid-run) is
71
- * skipped, never fabricated.
72
- */
73
- async *read(req, ctx) {
74
- for await (const refPage of this.enumerate(req.mode, req.filter, req.pageSize, ctx)) {
75
- const kept = refPage.filter((ref) => this.matchesRef(ref, req.filter));
76
- if (kept.length === 0) continue;
77
- const raws = await this.hydrate(
78
- kept.map((ref) => ref.externalId),
79
- ctx
80
- );
81
- for (const ref of kept) {
82
- const raw = raws.get(ref.externalId);
83
- if (raw === void 0 || raw === null) continue;
84
- const record = this.toCanonical(raw);
85
- if (record !== null && this.matchesRecord(record, req.filter)) {
86
- yield { externalId: ref.externalId, record, raw, cursor: ref.cursor };
87
- }
88
- }
89
- }
90
- }
91
- /**
92
- * `RandomRead<T>` — single-record read, provided for free as
93
- * `toCanonical ∘ hydrate([id])`. Reuses the adapter's batched fetch + miss
94
- * tolerance; returns `null` for a missing or undecodable record.
95
- */
96
- async get(id, ctx) {
97
- const raws = await this.hydrate([id], ctx);
98
- const raw = raws.get(id);
99
- if (raw === void 0 || raw === null) return null;
100
- return this.toCanonical(raw);
101
- }
102
- /**
103
- * `IChangeSource<T>` adaptation. Maps the orchestrator's by-value cursor to a
104
- * `ReadMode` (`null` → `full` backfill, else `delta`), streams `read()`, and
105
- * stamps each `SourcedRecord` into a `Change<T>`. All records surface as
106
- * `'updated'`; the orchestrator's diff stage classifies create-vs-update and
107
- * deletes arrive as tombstone refs (`toCanonical` may flag them).
108
- *
109
- * Cursor emission honors `cursorDivisible` (RFC-0003 §3). Divisible: each
110
- * record carries its own per-ref cursor. Atomic: per-ref cursors are withheld
111
- * (`undefined`, which the orchestrator skips persisting) and the end-of-walk
112
- * token rides only on the final record — so a mid-walk crash never persists
113
- * an unresumable token. If an atomic run yields no surviving records, no
114
- * cursor is persisted and the next run re-reads the same (empty) delta — a
115
- * bounded inefficiency, never data loss.
116
- */
117
- async *listChanges(subscription, cursor) {
118
- const mode = cursor === null || cursor === void 0 ? { kind: "full" } : { kind: "delta", cursor };
119
- const filter = this.filterFor(subscription);
120
- const stream = this.read({ mode, filter }, { subscription });
121
- if (this.cursorDivisible) {
122
- for await (const sourced of stream) {
123
- yield this.toChange(sourced, sourced.cursor);
124
- }
125
- return;
126
- }
127
- let prev = null;
128
- for await (const sourced of stream) {
129
- if (prev !== null) yield this.toChange(prev, void 0);
130
- prev = sourced;
131
- }
132
- if (prev !== null) yield this.toChange(prev, prev.cursor);
133
- }
134
- /** Stamp a `SourcedRecord` into a `Change<T>` with an explicit emitted cursor. */
135
- toChange(sourced, cursor) {
136
- return {
137
- externalId: sourced.externalId,
138
- operation: "updated",
139
- record: sourced.record,
140
- cursor,
141
- source: this.changeSource
142
- };
143
- }
144
- };
1
+ import {
2
+ IncrementalReadBase,
3
+ mapConcurrent
4
+ } from "../../../chunk-LG57S2SC.js";
5
+ import "../../../chunk-2E224ZSN.js";
145
6
  export {
146
7
  IncrementalReadBase,
147
8
  mapConcurrent
@@ -1 +1 @@
1
- {"version":3,"sources":["../../../../runtime/subsystems/integration/incremental-read.ts"],"sourcesContent":["/**\n * Integration subsystem — `IncrementalRead<T, F>` + `RandomRead<T>` capability\n * and the providing `IncrementalReadBase<T, F, M>` (RFC-0003 R1).\n *\n * The universal read primitive. Where `IChangeSource.listChanges` is the\n * *transport* contract (stream `Change<T>`, orchestrator owns cursor lifecycle),\n * this base owns *how the body that produces those changes is written* — the\n * level the bare `changeSources = {}` author-seam left unstructured.\n *\n * The read decomposes into two composable verbs the adapter supplies:\n *\n * - `enumerate(mode, filter) → AsyncIterable<Ref<M>[]>` — the cheap delta /\n * backfill walk; streams pages of lightweight refs (id + per-ref cursor +\n * filterable metadata). LAZY: pull-driven so hydrate backpressures it.\n * - `hydrate(ids) → Map<id, raw>` — the expensive fetch-by-id, batched; where\n * bounded concurrency / a vendor `/batch` endpoint lives. Keyed and\n * miss-tolerant (a mid-run 404 cannot shift alignment).\n * - `toCanonical(raw) → T | null` — provider payload → canonical record.\n *\n * The base PROVIDES the orchestration: drain enumerate, **filter before\n * hydrate** (structural — an adapter physically cannot hydrate-then-discard),\n * keyed pairing, per-ref cursor emission, and the `IChangeSource.listChanges`\n * adaptation. It also provides `RandomRead.get()` for free as\n * `toCanonical ∘ hydrate([id])` — so every incremental adapter is a\n * single-record reader (the \"list cheaply, fill on click\" query-surface need)\n * without extra code.\n *\n * The shape generalizes dealbrain's proven HubSpot `listSince` (streams, pushes\n * the filter server-side, carries a per-record cursor) to vendors whose list\n * returns id-stubs (Gmail) or nested resources (Meet). Calendar-style\n * full-object lists override `hydrate` as a passthrough.\n *\n * See RFC-0003 (Track D round-3), ADR-033 (`detection:` config), and\n * `poll-change-source.ts` (the sibling primitive this composes beside).\n */\n\nimport type {\n Change,\n ChangeSource,\n IChangeSource,\n IntegrationSubscriptionView,\n} from './integration-change-source.protocol';\n\n// ============================================================================\n// Capability shapes\n// ============================================================================\n\n/**\n * How a read walks the upstream. Modes are values, not verbs (swe-brain\n * ADR-0003: mode ≠ capability) — one `read()` verb dispatches on these.\n *\n * - `delta` — incremental walk from a persisted cursor.\n * - `full` — cursorless backfill (optionally bounded by `since`).\n * - `reconcile` — gap-repair: re-fetch a known id set the cursor skipped\n * (the repair pass for the silent-tail-skip + #414-style\n * multi-provider divergence).\n */\nexport type ReadMode =\n | { readonly kind: 'delta'; readonly cursor: unknown }\n | { readonly kind: 'full'; readonly since?: Date }\n | { readonly kind: 'reconcile'; readonly knownIds: readonly string[] };\n\n/**\n * A cheap ref from the enumerate pass: identity + per-ref cursor + metadata to\n * filter or display on. `cursor` is the position AS OF this ref — see\n * `IncrementalReadBase.cursorDivisible` (R2) for when it may be checkpointed\n * mid-walk versus withheld until a safe boundary.\n */\nexport interface Ref<M = Record<string, unknown>> {\n readonly externalId: string;\n readonly cursor: unknown;\n readonly meta: M;\n}\n\n/** A read request: the mode, an optional adapter-typed filter, and page size. */\nexport interface ReadRequest<F = unknown> {\n readonly mode: ReadMode;\n readonly filter?: F;\n readonly pageSize?: number;\n}\n\n/**\n * Per-run context threaded from `listChanges` into the vendor read body (R5).\n *\n * Carries the `subscription` framing the run so `enumerate`/`hydrate` can resolve\n * **per-connection credentials** (and raw-landing keys) from\n * `subscription.externalRef` — the gap a multi-account consumer surfaced: a\n * singleton change source cannot hold connection-scoped auth, and before R5 the\n * base forwarded the subscription only into `filterFor`, never into the fetch.\n *\n * Optional throughout (the core contract): a direct `read()` / `get()` call — the\n * query surface's \"fill one record on click\" — may omit it. An adapter that needs\n * per-connection auth reads `ctx?.subscription?.externalRef` and asserts its\n * presence; a provider-level-auth adapter ignores it.\n */\nexport interface ReadContext {\n /** The subscription framing this run; `externalRef` is the upstream scope /\n * connection id the adapter resolves credentials + raw-landing keys from. */\n readonly subscription?: IntegrationSubscriptionView;\n}\n\n/**\n * The `read()`-side envelope: canonical record + the raw vendor payload it came\n * from + the originating external id + the per-ref cursor.\n *\n * Distinct from the runtime's transport envelope `Change<T>`\n * (operation/externalId/cursor/source). The relationship is one-directional:\n * `listChanges()` adapts `read()` → `Change<T>` (dropping `raw`, stamping\n * `operation`). `read()` keeps `raw` and `externalId` so a query surface can\n * re-project without a second fetch.\n */\nexport interface SourcedRecord<T> {\n readonly externalId: string;\n readonly record: T;\n readonly raw: unknown;\n readonly cursor: unknown;\n}\n\n/**\n * The universal read capability — one public verb that streams. Filtering,\n * hydration, and cursor emission are the providing base's concern.\n */\nexport interface IncrementalRead<T, F = unknown> {\n read(req: ReadRequest<F>, ctx?: ReadContext): AsyncIterable<SourcedRecord<T>>;\n}\n\n/**\n * Single-record read by external id — the \"fill on click\" atom. Provided for\n * free by `IncrementalReadBase` (composes `hydrate` + `toCanonical`); declared\n * as its own capability so consumers can depend on it without the streaming\n * surface.\n */\nexport interface RandomRead<T> {\n get(id: string, ctx?: ReadContext): Promise<T | null>;\n}\n\n// ============================================================================\n// Bounded-parallel map helper\n// ============================================================================\n\n/**\n * Map `ids` through `fn` with at most `limit` concurrent in-flight calls,\n * collecting results keyed by id. The workhorse for writing a batched\n * `hydrate` over a single-id fetch without serial N+1 latency.\n */\nexport async function mapConcurrent<R>(\n ids: readonly string[],\n fn: (id: string) => Promise<R>,\n limit: number,\n): Promise<Map<string, R>> {\n const out = new Map<string, R>();\n if (ids.length === 0) return out;\n const width = Math.max(1, Math.min(limit, ids.length));\n let next = 0;\n const worker = async (): Promise<void> => {\n while (next < ids.length) {\n const idx = next++;\n const id = ids[idx]!;\n out.set(id, await fn(id));\n }\n };\n await Promise.all(Array.from({ length: width }, worker));\n return out;\n}\n\n// ============================================================================\n// IncrementalReadBase\n// ============================================================================\n\n/**\n * Providing base for the read capability. A subclass fills exactly three vendor\n * methods — `enumerate`, `hydrate`, `toCanonical` — and gets a streaming,\n * filter-before-hydrate, miss-tolerant `IncrementalRead<T, F>` +\n * `IChangeSource<T>` + `RandomRead<T>`.\n *\n * Type params: `T` canonical record, `F` adapter-typed filter, `M` per-ref\n * metadata (defaults to an untyped bag — surface packages supply a domain `M`).\n */\nexport abstract class IncrementalReadBase<T, F = unknown, M = Record<string, unknown>>\n implements IncrementalRead<T, F>, IChangeSource<T>, RandomRead<T>\n{\n /** Human label for run logs — e.g. `'google-mail-email'`. */\n abstract readonly label: string;\n\n /**\n * Whether the vendor takes the request predicate server-side. Declared, not\n * enforced here — surfaced into the emission manifest (R3) so the falsifier\n * suite (R4) can record which adapters filter post-hydrate. `false` is the\n * honest floor (e.g. Gmail without `q=`), handled via `matchesRecord`.\n */\n protected readonly filterPushdown: boolean = false;\n\n /** Max concurrent in-flight calls for a `mapConcurrent`-built `hydrate`. */\n protected readonly hydrateConcurrency: number = 10;\n\n /** `Change<T>.source` provenance stamped by `listChanges`. */\n protected readonly changeSource: ChangeSource = 'poll';\n\n /**\n * Whether this source's cursor strategy is divisible (RFC-0003 §3). When\n * `true` (default — sortable watermarks like `systemModstamp`/`timestamp`/\n * `replayId`), `listChanges` emits each record's per-ref cursor, so the\n * orchestrator may checkpoint mid-walk and a crash resumes from the last\n * delivered ref.\n *\n * When `false` (atomic opaque tokens — Gmail `historyId`, Calendar\n * `syncToken`), `listChanges` WITHHOLDS per-ref cursors and emits the\n * end-of-walk token only on the final record, so the orchestrator's\n * persist-last-yielded lifecycle can never persist an unresumable mid-walk\n * token. The cost is blast-radius: an interrupted atomic run resumes\n * all-or-nothing from the prior persisted token. For atomic *backfills* that\n * radius is the whole enumerate walk — bound it with `ReadRequest.pageSize`\n * (smaller pages ⇒ shorter walks per run). Per-page atomic checkpointing is a\n * future refinement; R2 gates at end-of-walk.\n *\n * Codegen (R3) sets this from the strategy kind via `isDivisibleCursor`.\n */\n protected readonly cursorDivisible: boolean = true;\n\n // ---- SUPPLIED by the adapter (the irreducible vendor seam) ----\n\n /**\n * The cheap walk. Streams pages of refs; LAZY so `hydrate` backpressures it\n * (one page hydrated before the next is pulled). Mode-dispatch lives here:\n * `delta` resumes from `mode.cursor`, `full` walks from the top, `reconcile`\n * re-fetches `mode.knownIds`.\n *\n * `pageSize` (from `ReadRequest`) is the adapter's requested vendor page size\n * — also the atomic-cursor backfill blast-radius bound (§ `cursorDivisible`).\n * Honor it as a hint; vendors that cap page size clamp it.\n *\n * `ctx?.subscription` (R5) carries the run's subscription, so a per-connection\n * adapter resolves credentials / upstream scope from `externalRef` here; absent\n * on a direct `read()` with no run subscription.\n */\n protected abstract enumerate(\n mode: ReadMode,\n filter?: F,\n pageSize?: number,\n ctx?: ReadContext,\n ): AsyncIterable<Ref<M>[]>;\n\n /**\n * Fetch raw payloads for `ids`, keyed by id. MUST be miss-tolerant: omit (or\n * map to `null`) any id that 404s mid-run rather than throwing or shifting\n * alignment. Write it over `mapConcurrent(ids, (id) => this.fetchOne(id),\n * this.hydrateConcurrency)`; override with a real `/batch` call or a\n * passthrough (full-object list) where the vendor allows.\n *\n * `ctx?.subscription` (R5) carries the run's subscription for per-connection\n * credential resolution (the fetch is where the vendor call happens) and is the\n * natural place to land raw payloads keyed by `subscription.id`.\n */\n protected abstract hydrate(ids: string[], ctx?: ReadContext): Promise<Map<string, unknown>>;\n\n /** Provider payload → canonical record. Return `null` to drop a record. */\n protected abstract toCanonical(raw: unknown): T | null;\n\n // ---- Optional filter hooks — exactly one is live per `filterPushdown` ----\n\n /** Pre-hydrate predicate over the cheap ref (preferred — avoids hydration). */\n protected matchesRef(_ref: Ref<M>, _filter?: F): boolean {\n return true;\n }\n\n /** Post-hydrate predicate over the canonical record (the no-pushdown floor). */\n protected matchesRecord(_record: T, _filter?: F): boolean {\n return true;\n }\n\n /**\n * Resolve the filter for a subscription when adapting to `listChanges`\n * (which has no filter argument). Defaults to none; codegen wiring (R3)\n * overrides this to thread `DetectionConfig.filters`.\n */\n protected filterFor(_subscription: IntegrationSubscriptionView): F | undefined {\n return undefined;\n }\n\n // ---- PROVIDED by the base ----\n\n /**\n * Stream canonical records for a request. Filter is applied BEFORE hydrate\n * (structural: a kept ref is hydrated, a rejected one never is), so an\n * adapter cannot hydrate-then-discard. A hydrate miss (deleted mid-run) is\n * skipped, never fabricated.\n */\n async *read(req: ReadRequest<F>, ctx?: ReadContext): AsyncIterable<SourcedRecord<T>> {\n for await (const refPage of this.enumerate(req.mode, req.filter, req.pageSize, ctx)) {\n const kept = refPage.filter((ref) => this.matchesRef(ref, req.filter));\n if (kept.length === 0) continue;\n const raws = await this.hydrate(\n kept.map((ref) => ref.externalId),\n ctx,\n );\n for (const ref of kept) {\n const raw = raws.get(ref.externalId);\n if (raw === undefined || raw === null) continue; // deleted mid-run → skip\n const record = this.toCanonical(raw);\n if (record !== null && this.matchesRecord(record, req.filter)) {\n yield { externalId: ref.externalId, record, raw, cursor: ref.cursor };\n }\n }\n }\n }\n\n /**\n * `RandomRead<T>` — single-record read, provided for free as\n * `toCanonical ∘ hydrate([id])`. Reuses the adapter's batched fetch + miss\n * tolerance; returns `null` for a missing or undecodable record.\n */\n async get(id: string, ctx?: ReadContext): Promise<T | null> {\n const raws = await this.hydrate([id], ctx);\n const raw = raws.get(id);\n if (raw === undefined || raw === null) return null;\n return this.toCanonical(raw);\n }\n\n /**\n * `IChangeSource<T>` adaptation. Maps the orchestrator's by-value cursor to a\n * `ReadMode` (`null` → `full` backfill, else `delta`), streams `read()`, and\n * stamps each `SourcedRecord` into a `Change<T>`. All records surface as\n * `'updated'`; the orchestrator's diff stage classifies create-vs-update and\n * deletes arrive as tombstone refs (`toCanonical` may flag them).\n *\n * Cursor emission honors `cursorDivisible` (RFC-0003 §3). Divisible: each\n * record carries its own per-ref cursor. Atomic: per-ref cursors are withheld\n * (`undefined`, which the orchestrator skips persisting) and the end-of-walk\n * token rides only on the final record — so a mid-walk crash never persists\n * an unresumable token. If an atomic run yields no surviving records, no\n * cursor is persisted and the next run re-reads the same (empty) delta — a\n * bounded inefficiency, never data loss.\n */\n async *listChanges(\n subscription: IntegrationSubscriptionView,\n cursor: unknown | null,\n ): AsyncIterable<Change<T>> {\n const mode: ReadMode =\n cursor === null || cursor === undefined\n ? { kind: 'full' }\n : { kind: 'delta', cursor };\n const filter = this.filterFor(subscription);\n // R5: thread the run's subscription into the read body so `enumerate`/`hydrate`\n // can resolve per-connection credentials (and raw-landing keys) from it.\n const stream = this.read({ mode, filter }, { subscription });\n\n if (this.cursorDivisible) {\n for await (const sourced of stream) {\n yield this.toChange(sourced, sourced.cursor);\n }\n return;\n }\n\n // Atomic: one-record lookahead. Emit every record but the last with a\n // withheld (`undefined`) cursor; the last record carries the end-of-walk\n // token. Contract: an atomic adapter stamps the (single, shared) end-of-walk\n // token onto its refs' `cursor` — so whichever record survives last carries\n // it. The base emits a real cursor exactly once, on that final record, so the\n // orchestrator can never persist a mid-walk value. If zero records survive,\n // nothing is persisted (next run re-reads the delta — bounded, never lossy).\n let prev: SourcedRecord<T> | null = null;\n for await (const sourced of stream) {\n if (prev !== null) yield this.toChange(prev, undefined);\n prev = sourced;\n }\n if (prev !== null) yield this.toChange(prev, prev.cursor);\n }\n\n /** Stamp a `SourcedRecord` into a `Change<T>` with an explicit emitted cursor. */\n private toChange(sourced: SourcedRecord<T>, cursor: unknown): Change<T> {\n return {\n externalId: sourced.externalId,\n operation: 'updated',\n record: sourced.record,\n cursor,\n source: this.changeSource,\n };\n }\n}\n"],"mappings":"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","names":[]}
1
+ {"version":3,"sources":[],"sourcesContent":[],"mappings":"","names":[]}