@shware/workflow 0.0.0-stage → 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (442) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +154 -2
  3. package/dist/_virtual/_rolldown/runtime.cjs +23 -0
  4. package/dist/apns-relay.cjs +105 -0
  5. package/dist/apns-relay.cjs.map +1 -0
  6. package/dist/apns-relay.d.cts +28 -0
  7. package/dist/apns-relay.d.cts.map +1 -0
  8. package/dist/apns-relay.d.mts +28 -0
  9. package/dist/apns-relay.d.mts.map +1 -0
  10. package/dist/apns-relay.mjs +104 -0
  11. package/dist/apns-relay.mjs.map +1 -0
  12. package/dist/apns.cjs +121 -0
  13. package/dist/apns.cjs.map +1 -0
  14. package/dist/apns.d.cts +63 -0
  15. package/dist/apns.d.cts.map +1 -0
  16. package/dist/apns.d.mts +63 -0
  17. package/dist/apns.d.mts.map +1 -0
  18. package/dist/apns.mjs +116 -0
  19. package/dist/apns.mjs.map +1 -0
  20. package/dist/client.cjs +125 -0
  21. package/dist/client.cjs.map +1 -0
  22. package/dist/client.d.cts +108 -0
  23. package/dist/client.d.cts.map +1 -0
  24. package/dist/client.d.mts +108 -0
  25. package/dist/client.d.mts.map +1 -0
  26. package/dist/client.mjs +122 -0
  27. package/dist/client.mjs.map +1 -0
  28. package/dist/cloudflare/bindings.cjs +28 -0
  29. package/dist/cloudflare/bindings.cjs.map +1 -0
  30. package/dist/cloudflare/bindings.d.cts +144 -0
  31. package/dist/cloudflare/bindings.d.cts.map +1 -0
  32. package/dist/cloudflare/bindings.d.mts +144 -0
  33. package/dist/cloudflare/bindings.d.mts.map +1 -0
  34. package/dist/cloudflare/bindings.mjs +25 -0
  35. package/dist/cloudflare/bindings.mjs.map +1 -0
  36. package/dist/cloudflare/channels.cjs +164 -0
  37. package/dist/cloudflare/channels.cjs.map +1 -0
  38. package/dist/cloudflare/channels.d.cts +29 -0
  39. package/dist/cloudflare/channels.d.cts.map +1 -0
  40. package/dist/cloudflare/channels.d.mts +29 -0
  41. package/dist/cloudflare/channels.d.mts.map +1 -0
  42. package/dist/cloudflare/channels.mjs +161 -0
  43. package/dist/cloudflare/channels.mjs.map +1 -0
  44. package/dist/cloudflare/d1-env.cjs +17 -0
  45. package/dist/cloudflare/d1-env.cjs.map +1 -0
  46. package/dist/cloudflare/d1-env.d.cts +12 -0
  47. package/dist/cloudflare/d1-env.d.cts.map +1 -0
  48. package/dist/cloudflare/d1-env.d.mts +12 -0
  49. package/dist/cloudflare/d1-env.d.mts.map +1 -0
  50. package/dist/cloudflare/d1-env.mjs +16 -0
  51. package/dist/cloudflare/d1-env.mjs.map +1 -0
  52. package/dist/cloudflare/index.cjs +54 -0
  53. package/dist/cloudflare/index.d.cts +19 -0
  54. package/dist/cloudflare/index.d.mts +19 -0
  55. package/dist/cloudflare/index.mjs +16 -0
  56. package/dist/cloudflare/router.cjs +516 -0
  57. package/dist/cloudflare/router.cjs.map +1 -0
  58. package/dist/cloudflare/router.d.cts +157 -0
  59. package/dist/cloudflare/router.d.cts.map +1 -0
  60. package/dist/cloudflare/router.d.mts +157 -0
  61. package/dist/cloudflare/router.d.mts.map +1 -0
  62. package/dist/cloudflare/router.mjs +503 -0
  63. package/dist/cloudflare/router.mjs.map +1 -0
  64. package/dist/cloudflare/runner.cjs +225 -0
  65. package/dist/cloudflare/runner.cjs.map +1 -0
  66. package/dist/cloudflare/runner.d.cts +73 -0
  67. package/dist/cloudflare/runner.d.cts.map +1 -0
  68. package/dist/cloudflare/runner.d.mts +73 -0
  69. package/dist/cloudflare/runner.d.mts.map +1 -0
  70. package/dist/cloudflare/runner.mjs +224 -0
  71. package/dist/cloudflare/runner.mjs.map +1 -0
  72. package/dist/cloudflare/schema.sql +127 -0
  73. package/dist/cloudflare/senders.cjs +114 -0
  74. package/dist/cloudflare/senders.cjs.map +1 -0
  75. package/dist/cloudflare/senders.d.cts +68 -0
  76. package/dist/cloudflare/senders.d.cts.map +1 -0
  77. package/dist/cloudflare/senders.d.mts +68 -0
  78. package/dist/cloudflare/senders.d.mts.map +1 -0
  79. package/dist/cloudflare/senders.mjs +108 -0
  80. package/dist/cloudflare/senders.mjs.map +1 -0
  81. package/dist/cloudflare/worker.cjs +228 -0
  82. package/dist/cloudflare/worker.cjs.map +1 -0
  83. package/dist/cloudflare/worker.d.cts +92 -0
  84. package/dist/cloudflare/worker.d.cts.map +1 -0
  85. package/dist/cloudflare/worker.d.mts +92 -0
  86. package/dist/cloudflare/worker.d.mts.map +1 -0
  87. package/dist/cloudflare/worker.mjs +224 -0
  88. package/dist/cloudflare/worker.mjs.map +1 -0
  89. package/dist/cloudflare/workers.d.cjs +0 -0
  90. package/dist/cloudflare/workers.d.cts +44 -0
  91. package/dist/cloudflare/workers.d.cts.map +1 -0
  92. package/dist/cloudflare/workers.d.mts +44 -0
  93. package/dist/cloudflare/workers.d.mts.map +1 -0
  94. package/dist/config.cjs +151 -0
  95. package/dist/config.cjs.map +1 -0
  96. package/dist/config.d.cts +149 -0
  97. package/dist/config.d.cts.map +1 -0
  98. package/dist/config.d.mts +149 -0
  99. package/dist/config.d.mts.map +1 -0
  100. package/dist/config.mjs +143 -0
  101. package/dist/config.mjs.map +1 -0
  102. package/dist/contract.cjs +212 -0
  103. package/dist/contract.cjs.map +1 -0
  104. package/dist/contract.d.cts +90 -0
  105. package/dist/contract.d.cts.map +1 -0
  106. package/dist/contract.d.mts +90 -0
  107. package/dist/contract.d.mts.map +1 -0
  108. package/dist/contract.mjs +206 -0
  109. package/dist/contract.mjs.map +1 -0
  110. package/dist/dsl/action.cjs +29 -0
  111. package/dist/dsl/action.cjs.map +1 -0
  112. package/dist/dsl/action.d.cts +64 -0
  113. package/dist/dsl/action.d.cts.map +1 -0
  114. package/dist/dsl/action.d.mts +64 -0
  115. package/dist/dsl/action.d.mts.map +1 -0
  116. package/dist/dsl/action.mjs +28 -0
  117. package/dist/dsl/action.mjs.map +1 -0
  118. package/dist/dsl/base.cjs +34 -0
  119. package/dist/dsl/base.cjs.map +1 -0
  120. package/dist/dsl/base.d.cts +45 -0
  121. package/dist/dsl/base.d.cts.map +1 -0
  122. package/dist/dsl/base.d.mts +45 -0
  123. package/dist/dsl/base.d.mts.map +1 -0
  124. package/dist/dsl/base.mjs +30 -0
  125. package/dist/dsl/base.mjs.map +1 -0
  126. package/dist/dsl/bundle.cjs +207 -0
  127. package/dist/dsl/bundle.cjs.map +1 -0
  128. package/dist/dsl/bundle.d.cts +19 -0
  129. package/dist/dsl/bundle.d.cts.map +1 -0
  130. package/dist/dsl/bundle.d.mts +19 -0
  131. package/dist/dsl/bundle.d.mts.map +1 -0
  132. package/dist/dsl/bundle.mjs +206 -0
  133. package/dist/dsl/bundle.mjs.map +1 -0
  134. package/dist/dsl/condition.cjs +177 -0
  135. package/dist/dsl/condition.cjs.map +1 -0
  136. package/dist/dsl/condition.d.cts +140 -0
  137. package/dist/dsl/condition.d.cts.map +1 -0
  138. package/dist/dsl/condition.d.mts +140 -0
  139. package/dist/dsl/condition.d.mts.map +1 -0
  140. package/dist/dsl/condition.mjs +156 -0
  141. package/dist/dsl/condition.mjs.map +1 -0
  142. package/dist/dsl/flow.cjs +228 -0
  143. package/dist/dsl/flow.cjs.map +1 -0
  144. package/dist/dsl/flow.d.cts +223 -0
  145. package/dist/dsl/flow.d.cts.map +1 -0
  146. package/dist/dsl/flow.d.mts +223 -0
  147. package/dist/dsl/flow.d.mts.map +1 -0
  148. package/dist/dsl/flow.mjs +226 -0
  149. package/dist/dsl/flow.mjs.map +1 -0
  150. package/dist/dsl/index.cjs +38 -0
  151. package/dist/dsl/index.d.cts +10 -0
  152. package/dist/dsl/index.d.mts +10 -0
  153. package/dist/dsl/index.mjs +9 -0
  154. package/dist/dsl/refs.cjs +59 -0
  155. package/dist/dsl/refs.cjs.map +1 -0
  156. package/dist/dsl/refs.d.cts +88 -0
  157. package/dist/dsl/refs.d.cts.map +1 -0
  158. package/dist/dsl/refs.d.mts +88 -0
  159. package/dist/dsl/refs.d.mts.map +1 -0
  160. package/dist/dsl/refs.mjs +55 -0
  161. package/dist/dsl/refs.mjs.map +1 -0
  162. package/dist/dsl/template.cjs +65 -0
  163. package/dist/dsl/template.cjs.map +1 -0
  164. package/dist/dsl/template.d.cts +75 -0
  165. package/dist/dsl/template.d.cts.map +1 -0
  166. package/dist/dsl/template.d.mts +75 -0
  167. package/dist/dsl/template.d.mts.map +1 -0
  168. package/dist/dsl/template.mjs +63 -0
  169. package/dist/dsl/template.mjs.map +1 -0
  170. package/dist/dsl/trigger.cjs +40 -0
  171. package/dist/dsl/trigger.cjs.map +1 -0
  172. package/dist/dsl/trigger.d.cts +65 -0
  173. package/dist/dsl/trigger.d.cts.map +1 -0
  174. package/dist/dsl/trigger.d.mts +65 -0
  175. package/dist/dsl/trigger.d.mts.map +1 -0
  176. package/dist/dsl/trigger.mjs +39 -0
  177. package/dist/dsl/trigger.mjs.map +1 -0
  178. package/dist/dsl/workflow.cjs +121 -0
  179. package/dist/dsl/workflow.cjs.map +1 -0
  180. package/dist/dsl/workflow.d.cts +59 -0
  181. package/dist/dsl/workflow.d.cts.map +1 -0
  182. package/dist/dsl/workflow.d.mts +59 -0
  183. package/dist/dsl/workflow.d.mts.map +1 -0
  184. package/dist/dsl/workflow.mjs +120 -0
  185. package/dist/dsl/workflow.mjs.map +1 -0
  186. package/dist/engine/actions.cjs +27 -0
  187. package/dist/engine/actions.cjs.map +1 -0
  188. package/dist/engine/actions.d.cts +40 -0
  189. package/dist/engine/actions.d.cts.map +1 -0
  190. package/dist/engine/actions.d.mts +40 -0
  191. package/dist/engine/actions.d.mts.map +1 -0
  192. package/dist/engine/actions.mjs +26 -0
  193. package/dist/engine/actions.mjs.map +1 -0
  194. package/dist/engine/bucket.cjs +72 -0
  195. package/dist/engine/bucket.cjs.map +1 -0
  196. package/dist/engine/bucket.d.cts +32 -0
  197. package/dist/engine/bucket.d.cts.map +1 -0
  198. package/dist/engine/bucket.d.mts +32 -0
  199. package/dist/engine/bucket.d.mts.map +1 -0
  200. package/dist/engine/bucket.mjs +69 -0
  201. package/dist/engine/bucket.mjs.map +1 -0
  202. package/dist/engine/condition.cjs +166 -0
  203. package/dist/engine/condition.cjs.map +1 -0
  204. package/dist/engine/condition.d.cts +52 -0
  205. package/dist/engine/condition.d.cts.map +1 -0
  206. package/dist/engine/condition.d.mts +52 -0
  207. package/dist/engine/condition.d.mts.map +1 -0
  208. package/dist/engine/condition.mjs +161 -0
  209. package/dist/engine/condition.mjs.map +1 -0
  210. package/dist/engine/index.cjs +20 -0
  211. package/dist/engine/index.d.cts +8 -0
  212. package/dist/engine/index.d.mts +8 -0
  213. package/dist/engine/index.mjs +7 -0
  214. package/dist/engine/interpreter.cjs +428 -0
  215. package/dist/engine/interpreter.cjs.map +1 -0
  216. package/dist/engine/interpreter.d.cts +6 -0
  217. package/dist/engine/interpreter.d.cts.map +1 -0
  218. package/dist/engine/interpreter.d.mts +6 -0
  219. package/dist/engine/interpreter.d.mts.map +1 -0
  220. package/dist/engine/interpreter.mjs +427 -0
  221. package/dist/engine/interpreter.mjs.map +1 -0
  222. package/dist/engine/ports.cjs +0 -0
  223. package/dist/engine/ports.d.cts +252 -0
  224. package/dist/engine/ports.d.cts.map +1 -0
  225. package/dist/engine/ports.d.mts +252 -0
  226. package/dist/engine/ports.d.mts.map +1 -0
  227. package/dist/engine/ports.mjs +1 -0
  228. package/dist/engine/recipient.cjs +23 -0
  229. package/dist/engine/recipient.cjs.map +1 -0
  230. package/dist/engine/recipient.d.cts +13 -0
  231. package/dist/engine/recipient.d.cts.map +1 -0
  232. package/dist/engine/recipient.d.mts +13 -0
  233. package/dist/engine/recipient.d.mts.map +1 -0
  234. package/dist/engine/recipient.mjs +22 -0
  235. package/dist/engine/recipient.mjs.map +1 -0
  236. package/dist/engine/time-scale.cjs +54 -0
  237. package/dist/engine/time-scale.cjs.map +1 -0
  238. package/dist/engine/time-scale.d.cts +31 -0
  239. package/dist/engine/time-scale.d.cts.map +1 -0
  240. package/dist/engine/time-scale.d.mts +31 -0
  241. package/dist/engine/time-scale.d.mts.map +1 -0
  242. package/dist/engine/time-scale.mjs +52 -0
  243. package/dist/engine/time-scale.mjs.map +1 -0
  244. package/dist/engine/time-window.cjs +149 -0
  245. package/dist/engine/time-window.cjs.map +1 -0
  246. package/dist/engine/time-window.d.cts +22 -0
  247. package/dist/engine/time-window.d.cts.map +1 -0
  248. package/dist/engine/time-window.d.mts +22 -0
  249. package/dist/engine/time-window.d.mts.map +1 -0
  250. package/dist/engine/time-window.mjs +147 -0
  251. package/dist/engine/time-window.mjs.map +1 -0
  252. package/dist/fcm.cjs +125 -0
  253. package/dist/fcm.cjs.map +1 -0
  254. package/dist/fcm.d.cts +48 -0
  255. package/dist/fcm.d.cts.map +1 -0
  256. package/dist/fcm.d.mts +48 -0
  257. package/dist/fcm.d.mts.map +1 -0
  258. package/dist/fcm.mjs +121 -0
  259. package/dist/fcm.mjs.map +1 -0
  260. package/dist/hash.cjs +245 -0
  261. package/dist/hash.cjs.map +1 -0
  262. package/dist/hash.d.cts +30 -0
  263. package/dist/hash.d.cts.map +1 -0
  264. package/dist/hash.d.mts +30 -0
  265. package/dist/hash.d.mts.map +1 -0
  266. package/dist/hash.mjs +239 -0
  267. package/dist/hash.mjs.map +1 -0
  268. package/dist/index.cjs +100 -0
  269. package/dist/index.d.cts +18 -0
  270. package/dist/index.d.mts +18 -0
  271. package/dist/index.mjs +17 -0
  272. package/dist/ir.cjs +366 -0
  273. package/dist/ir.cjs.map +1 -0
  274. package/dist/ir.d.cts +486 -0
  275. package/dist/ir.d.cts.map +1 -0
  276. package/dist/ir.d.mts +486 -0
  277. package/dist/ir.d.mts.map +1 -0
  278. package/dist/ir.mjs +344 -0
  279. package/dist/ir.mjs.map +1 -0
  280. package/dist/jwt.cjs +22 -0
  281. package/dist/jwt.cjs.map +1 -0
  282. package/dist/jwt.d.cts +9 -0
  283. package/dist/jwt.d.cts.map +1 -0
  284. package/dist/jwt.d.mts +9 -0
  285. package/dist/jwt.d.mts.map +1 -0
  286. package/dist/jwt.mjs +20 -0
  287. package/dist/jwt.mjs.map +1 -0
  288. package/dist/plan.cjs +223 -0
  289. package/dist/plan.cjs.map +1 -0
  290. package/dist/plan.d.cts +68 -0
  291. package/dist/plan.d.cts.map +1 -0
  292. package/dist/plan.d.mts +68 -0
  293. package/dist/plan.d.mts.map +1 -0
  294. package/dist/plan.mjs +221 -0
  295. package/dist/plan.mjs.map +1 -0
  296. package/dist/postgres-js.cjs +42 -0
  297. package/dist/postgres-js.cjs.map +1 -0
  298. package/dist/postgres-js.d.cts +28 -0
  299. package/dist/postgres-js.d.cts.map +1 -0
  300. package/dist/postgres-js.d.mts +28 -0
  301. package/dist/postgres-js.d.mts.map +1 -0
  302. package/dist/postgres-js.mjs +38 -0
  303. package/dist/postgres-js.mjs.map +1 -0
  304. package/dist/provenance.cjs +67 -0
  305. package/dist/provenance.cjs.map +1 -0
  306. package/dist/provenance.d.cts +41 -0
  307. package/dist/provenance.d.cts.map +1 -0
  308. package/dist/provenance.d.mts +41 -0
  309. package/dist/provenance.d.mts.map +1 -0
  310. package/dist/provenance.mjs +65 -0
  311. package/dist/provenance.mjs.map +1 -0
  312. package/dist/push.cjs +14 -0
  313. package/dist/push.cjs.map +1 -0
  314. package/dist/push.d.cts +16 -0
  315. package/dist/push.d.cts.map +1 -0
  316. package/dist/push.d.mts +16 -0
  317. package/dist/push.d.mts.map +1 -0
  318. package/dist/push.mjs +13 -0
  319. package/dist/push.mjs.map +1 -0
  320. package/dist/react-email.cjs +48 -0
  321. package/dist/react-email.cjs.map +1 -0
  322. package/dist/react-email.d.cts +7 -0
  323. package/dist/react-email.d.cts.map +1 -0
  324. package/dist/react-email.d.mts +7 -0
  325. package/dist/react-email.d.mts.map +1 -0
  326. package/dist/react-email.mjs +47 -0
  327. package/dist/react-email.mjs.map +1 -0
  328. package/dist/reporting/classify.cjs +42 -0
  329. package/dist/reporting/classify.cjs.map +1 -0
  330. package/dist/reporting/classify.d.cts +60 -0
  331. package/dist/reporting/classify.d.cts.map +1 -0
  332. package/dist/reporting/classify.d.mts +60 -0
  333. package/dist/reporting/classify.d.mts.map +1 -0
  334. package/dist/reporting/classify.mjs +38 -0
  335. package/dist/reporting/classify.mjs.map +1 -0
  336. package/dist/reporting/observer.cjs +63 -0
  337. package/dist/reporting/observer.cjs.map +1 -0
  338. package/dist/reporting/observer.d.cts +18 -0
  339. package/dist/reporting/observer.d.cts.map +1 -0
  340. package/dist/reporting/observer.d.mts +18 -0
  341. package/dist/reporting/observer.d.mts.map +1 -0
  342. package/dist/reporting/observer.mjs +62 -0
  343. package/dist/reporting/observer.mjs.map +1 -0
  344. package/dist/reporting/tracking.cjs +153 -0
  345. package/dist/reporting/tracking.cjs.map +1 -0
  346. package/dist/reporting/tracking.d.cts +43 -0
  347. package/dist/reporting/tracking.d.cts.map +1 -0
  348. package/dist/reporting/tracking.d.mts +43 -0
  349. package/dist/reporting/tracking.d.mts.map +1 -0
  350. package/dist/reporting/tracking.mjs +151 -0
  351. package/dist/reporting/tracking.mjs.map +1 -0
  352. package/dist/runtime.cjs +19 -0
  353. package/dist/runtime.cjs.map +1 -0
  354. package/dist/runtime.d.cts +30 -0
  355. package/dist/runtime.d.cts.map +1 -0
  356. package/dist/runtime.d.mts +30 -0
  357. package/dist/runtime.d.mts.map +1 -0
  358. package/dist/runtime.mjs +18 -0
  359. package/dist/runtime.mjs.map +1 -0
  360. package/dist/store/d1.cjs +185 -0
  361. package/dist/store/d1.cjs.map +1 -0
  362. package/dist/store/d1.d.cts +55 -0
  363. package/dist/store/d1.d.cts.map +1 -0
  364. package/dist/store/d1.d.mts +55 -0
  365. package/dist/store/d1.d.mts.map +1 -0
  366. package/dist/store/d1.mjs +184 -0
  367. package/dist/store/d1.mjs.map +1 -0
  368. package/dist/store/facts.cjs +60 -0
  369. package/dist/store/facts.cjs.map +1 -0
  370. package/dist/store/facts.d.cts +38 -0
  371. package/dist/store/facts.d.cts.map +1 -0
  372. package/dist/store/facts.d.mts +38 -0
  373. package/dist/store/facts.d.mts.map +1 -0
  374. package/dist/store/facts.mjs +58 -0
  375. package/dist/store/facts.mjs.map +1 -0
  376. package/dist/store/index.cjs +31 -0
  377. package/dist/store/index.cjs.map +1 -0
  378. package/dist/store/index.d.cts +291 -0
  379. package/dist/store/index.d.cts.map +1 -0
  380. package/dist/store/index.d.mts +291 -0
  381. package/dist/store/index.d.mts.map +1 -0
  382. package/dist/store/index.mjs +22 -0
  383. package/dist/store/index.mjs.map +1 -0
  384. package/dist/store/postgres-reporting.cjs +213 -0
  385. package/dist/store/postgres-reporting.cjs.map +1 -0
  386. package/dist/store/postgres-reporting.d.cts +63 -0
  387. package/dist/store/postgres-reporting.d.cts.map +1 -0
  388. package/dist/store/postgres-reporting.d.mts +63 -0
  389. package/dist/store/postgres-reporting.d.mts.map +1 -0
  390. package/dist/store/postgres-reporting.mjs +212 -0
  391. package/dist/store/postgres-reporting.mjs.map +1 -0
  392. package/dist/store/postgres.cjs +309 -0
  393. package/dist/store/postgres.cjs.map +1 -0
  394. package/dist/store/postgres.d.cts +77 -0
  395. package/dist/store/postgres.d.cts.map +1 -0
  396. package/dist/store/postgres.d.mts +77 -0
  397. package/dist/store/postgres.d.mts.map +1 -0
  398. package/dist/store/postgres.mjs +306 -0
  399. package/dist/store/postgres.mjs.map +1 -0
  400. package/dist/store/sql.cjs +24 -0
  401. package/dist/store/sql.cjs.map +1 -0
  402. package/dist/store/sql.d.cts +25 -0
  403. package/dist/store/sql.d.cts.map +1 -0
  404. package/dist/store/sql.d.mts +25 -0
  405. package/dist/store/sql.d.mts.map +1 -0
  406. package/dist/store/sql.mjs +23 -0
  407. package/dist/store/sql.mjs.map +1 -0
  408. package/dist/store/tables.cjs +404 -0
  409. package/dist/store/tables.cjs.map +1 -0
  410. package/dist/store/tables.d.cts +81 -0
  411. package/dist/store/tables.d.cts.map +1 -0
  412. package/dist/store/tables.d.mts +81 -0
  413. package/dist/store/tables.d.mts.map +1 -0
  414. package/dist/store/tables.mjs +399 -0
  415. package/dist/store/tables.mjs.map +1 -0
  416. package/dist/templates.cjs +247 -0
  417. package/dist/templates.cjs.map +1 -0
  418. package/dist/templates.d.cts +187 -0
  419. package/dist/templates.d.cts.map +1 -0
  420. package/dist/templates.d.mts +187 -0
  421. package/dist/templates.d.mts.map +1 -0
  422. package/dist/templates.mjs +230 -0
  423. package/dist/templates.mjs.map +1 -0
  424. package/dist/webhooks.cjs +96 -0
  425. package/dist/webhooks.cjs.map +1 -0
  426. package/dist/webhooks.d.cts +25 -0
  427. package/dist/webhooks.d.cts.map +1 -0
  428. package/dist/webhooks.d.mts +25 -0
  429. package/dist/webhooks.d.mts.map +1 -0
  430. package/dist/webhooks.mjs +94 -0
  431. package/dist/webhooks.mjs.map +1 -0
  432. package/dist/webpush.cjs +180 -0
  433. package/dist/webpush.cjs.map +1 -0
  434. package/dist/webpush.d.cts +53 -0
  435. package/dist/webpush.d.cts.map +1 -0
  436. package/dist/webpush.d.mts +53 -0
  437. package/dist/webpush.d.mts.map +1 -0
  438. package/dist/webpush.mjs +175 -0
  439. package/dist/webpush.mjs.map +1 -0
  440. package/package.json +189 -3
  441. package/src/cloudflare/schema.sql +127 -0
  442. package/src/cloudflare/workers.d.ts +44 -0
@@ -0,0 +1,40 @@
1
+ Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
2
+ const require_dsl_refs = require("./refs.cjs");
3
+ const require_dsl_condition = require("./condition.cjs");
4
+ //#region src/dsl/trigger.ts
5
+ const makeTrigger = (ir) => {
6
+ return {
7
+ type: ir.type,
8
+ ir
9
+ };
10
+ };
11
+ /**
12
+ * Trigger definition: a plain object — event names come from e.xxx references.
13
+ *
14
+ * const login = trigger.event(e.login, { filter: newUsers7d });
15
+ */
16
+ const trigger = {
17
+ event: (ev, whereOrOpts, maybeOpts) => {
18
+ const where = typeof whereOrOpts === "function" ? whereOrOpts : void 0;
19
+ const opts = typeof whereOrOpts === "function" ? maybeOpts : whereOrOpts;
20
+ return makeTrigger({
21
+ type: "event",
22
+ event: ev.name,
23
+ ...where !== void 0 ? { where: require_dsl_condition.condIR(where(require_dsl_refs.payloadRefs())) } : {},
24
+ ...opts?.filter !== void 0 ? { filter: require_dsl_condition.condIR(opts.filter) } : {}
25
+ });
26
+ },
27
+ segment: (seg) => makeTrigger({
28
+ type: "segment",
29
+ segment: seg.id
30
+ }),
31
+ date: (at) => makeTrigger({
32
+ type: "date",
33
+ at
34
+ }),
35
+ webhook: () => makeTrigger({ type: "webhook" })
36
+ };
37
+ //#endregion
38
+ exports.trigger = trigger;
39
+
40
+ //# sourceMappingURL=trigger.cjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"trigger.cjs","names":["condIR","payloadRefs"],"sources":["../../src/dsl/trigger.ts"],"sourcesContent":["import type { TriggerIR } from '../ir';\nimport { type Condition, type PayloadWhere, type SegmentRef, condIR } from './condition';\nimport { type EventRef, payloadRefs } from './refs';\n\n/**\n * Triggers — the four ways into a workflow, mirroring customer.io's campaign\n * trigger types. A trigger is a plain reusable object; the event name and\n * payload types flow in from an e.xxx reference, so the factory itself needs\n * no generics.\n */\n\n/** 'YYYY-MM-DD HH:mm:ss'. TODO: validate at runtime — template literals cannot express leading zeros. */\nexport type DateTime = string;\n\n/** Trigger reference: what trigger.xxx() returns, reusable across workflows. */\nexport interface TriggerRef {\n readonly type: 'event' | 'segment' | 'date' | 'webhook';\n}\n\n/** @internal the compiled shape behind a TriggerRef — workflow.toIR reads .ir off it */\nexport interface TriggerInternal extends TriggerRef {\n readonly ir: TriggerIR;\n}\n\nconst makeTrigger = (ir: TriggerIR): TriggerRef => {\n const impl: TriggerInternal = { type: ir.type, ir };\n return impl;\n};\n\nexport interface EventTriggerOptions {\n filter?: Condition;\n}\n\n/** Trigger factory: four ways in, mirroring customer.io's campaign trigger types. */\nexport interface TriggerFactory {\n /**\n * Event trigger: the event name comes from an e.xxx reference (types flow in\n * from it, so the factory itself needs no generics). Two independent gates:\n * - the optional second argument is a payload where clause (typed refs, the\n * ordinary predicates — compiles to IR data the UI renders):\n * trigger.event(e.login, (p) => eq(p.platform, 'web'))\n * - `filter` tests the user's profile (customer.io's trigger Filters).\n * The user enters only if the event fired *and* both gates hold.\n */\n event<P>(event: EventRef<P>, opts?: EventTriggerOptions): TriggerRef;\n event<P>(event: EventRef<P>, where: PayloadWhere<P>, opts?: EventTriggerOptions): TriggerRef;\n\n /**\n * Segment-entry trigger: the user enters the moment they go from not\n * matching to matching. Only a named segment is accepted — entry semantics\n * need a membership table, which an anonymous expression cannot provide.\n * Runtime note: membership is maintained lazily (re-evaluated on the user's\n * ingest/identify activity), so purely time-driven drift — e.g. an\n * inactivity segment becoming true by clock alone — is only observed on the\n * user's next activity. TODO: a cron sweep for time-driven segments.\n */\n segment(segment: SegmentRef): TriggerRef;\n\n /**\n * Scheduled trigger (one-shot, e.g. '2026-12-25 09:00:00', interpreted as\n * UTC). TODO: not routed by the runtime yet — deployBundle reports it in\n * `unrouted`; the implementation goes through cron + Queues (instance\n * creation is rate-limited, a date trigger fans out to the whole audience at\n * once). TODO: cron/recurring form.\n */\n date(at: DateTime): TriggerRef;\n\n /** Webhook trigger: third-party or external code fires it via a URL; the runtime allocates the endpoint. */\n webhook(): TriggerRef;\n}\n\n/**\n * Trigger definition: a plain object — event names come from e.xxx references.\n *\n * const login = trigger.event(e.login, { filter: newUsers7d });\n */\nexport const trigger: TriggerFactory = {\n event: <P>(\n ev: EventRef<P>,\n whereOrOpts?: PayloadWhere<P> | EventTriggerOptions,\n maybeOpts?: EventTriggerOptions\n ) => {\n const where = typeof whereOrOpts === 'function' ? whereOrOpts : undefined;\n const opts = typeof whereOrOpts === 'function' ? maybeOpts : whereOrOpts;\n return makeTrigger({\n type: 'event',\n event: ev.name,\n ...(where !== undefined ? { where: condIR(where(payloadRefs<P>())) } : {}),\n ...(opts?.filter !== undefined ? { filter: condIR(opts.filter) } : {}),\n });\n },\n segment: (seg) => makeTrigger({ type: 'segment', segment: seg.id }),\n date: (at) => makeTrigger({ type: 'date', at }),\n webhook: () => makeTrigger({ type: 'webhook' }),\n};\n"],"mappings":";;;;AAwBA,MAAM,eAAe,OAA8B;CAEjD,OAAO;EADyB,MAAM,GAAG;EAAM;CACrC;AACZ;;;;;;AAiDA,MAAa,UAA0B;CACrC,QACE,IACA,aACA,cACG;EACH,MAAM,QAAQ,OAAO,gBAAgB,aAAa,cAAc,KAAA;EAChE,MAAM,OAAO,OAAO,gBAAgB,aAAa,YAAY;EAC7D,OAAO,YAAY;GACjB,MAAM;GACN,OAAO,GAAG;GACV,GAAI,UAAU,KAAA,IAAY,EAAE,OAAOA,sBAAAA,OAAO,MAAMC,iBAAAA,YAAe,CAAC,CAAC,EAAE,IAAI,CAAC;GACxE,GAAI,MAAM,WAAW,KAAA,IAAY,EAAE,QAAQD,sBAAAA,OAAO,KAAK,MAAM,EAAE,IAAI,CAAC;EACtE,CAAC;CACH;CACA,UAAU,QAAQ,YAAY;EAAE,MAAM;EAAW,SAAS,IAAI;CAAG,CAAC;CAClE,OAAO,OAAO,YAAY;EAAE,MAAM;EAAQ;CAAG,CAAC;CAC9C,eAAe,YAAY,EAAE,MAAM,UAAU,CAAC;AAChD"}
@@ -0,0 +1,65 @@
1
+ import { TriggerIR } from "../ir.cjs";
2
+ import { EventRef } from "./refs.cjs";
3
+ import { Condition, PayloadWhere, SegmentRef } from "./condition.cjs";
4
+ //#region src/dsl/trigger.d.ts
5
+ /**
6
+ * Triggers — the four ways into a workflow, mirroring customer.io's campaign
7
+ * trigger types. A trigger is a plain reusable object; the event name and
8
+ * payload types flow in from an e.xxx reference, so the factory itself needs
9
+ * no generics.
10
+ */
11
+ /** 'YYYY-MM-DD HH:mm:ss'. TODO: validate at runtime — template literals cannot express leading zeros. */
12
+ export type DateTime = string;
13
+ /** Trigger reference: what trigger.xxx() returns, reusable across workflows. */
14
+ export interface TriggerRef {
15
+ readonly type: 'event' | 'segment' | 'date' | 'webhook';
16
+ }
17
+ /** @internal the compiled shape behind a TriggerRef — workflow.toIR reads .ir off it */
18
+ export interface TriggerInternal extends TriggerRef {
19
+ readonly ir: TriggerIR;
20
+ }
21
+ export interface EventTriggerOptions {
22
+ filter?: Condition;
23
+ }
24
+ /** Trigger factory: four ways in, mirroring customer.io's campaign trigger types. */
25
+ export interface TriggerFactory {
26
+ /**
27
+ * Event trigger: the event name comes from an e.xxx reference (types flow in
28
+ * from it, so the factory itself needs no generics). Two independent gates:
29
+ * - the optional second argument is a payload where clause (typed refs, the
30
+ * ordinary predicates — compiles to IR data the UI renders):
31
+ * trigger.event(e.login, (p) => eq(p.platform, 'web'))
32
+ * - `filter` tests the user's profile (customer.io's trigger Filters).
33
+ * The user enters only if the event fired *and* both gates hold.
34
+ */
35
+ event<P>(event: EventRef<P>, opts?: EventTriggerOptions): TriggerRef;
36
+ event<P>(event: EventRef<P>, where: PayloadWhere<P>, opts?: EventTriggerOptions): TriggerRef;
37
+ /**
38
+ * Segment-entry trigger: the user enters the moment they go from not
39
+ * matching to matching. Only a named segment is accepted — entry semantics
40
+ * need a membership table, which an anonymous expression cannot provide.
41
+ * Runtime note: membership is maintained lazily (re-evaluated on the user's
42
+ * ingest/identify activity), so purely time-driven drift — e.g. an
43
+ * inactivity segment becoming true by clock alone — is only observed on the
44
+ * user's next activity. TODO: a cron sweep for time-driven segments.
45
+ */
46
+ segment(segment: SegmentRef): TriggerRef;
47
+ /**
48
+ * Scheduled trigger (one-shot, e.g. '2026-12-25 09:00:00', interpreted as
49
+ * UTC). TODO: not routed by the runtime yet — deployBundle reports it in
50
+ * `unrouted`; the implementation goes through cron + Queues (instance
51
+ * creation is rate-limited, a date trigger fans out to the whole audience at
52
+ * once). TODO: cron/recurring form.
53
+ */
54
+ date(at: DateTime): TriggerRef;
55
+ /** Webhook trigger: third-party or external code fires it via a URL; the runtime allocates the endpoint. */
56
+ webhook(): TriggerRef;
57
+ }
58
+ /**
59
+ * Trigger definition: a plain object — event names come from e.xxx references.
60
+ *
61
+ * const login = trigger.event(e.login, { filter: newUsers7d });
62
+ */
63
+ export declare const trigger: TriggerFactory;
64
+ //#endregion
65
+ //# sourceMappingURL=trigger.d.cts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"trigger.d.cts","names":[],"sources":["../../src/dsl/trigger.ts"],"mappings":";;;;;;;;;;;YAYY;;iBAGK;WACN;;;iBAIM,wBAAwB;WAC9B,IAAI;;iBAQE;EACf,SAAS;;;iBAIM;;;;;;;;;;EAUf,MAAM,GAAG,OAAO,SAAS,IAAI,OAAO,sBAAsB;EAC1D,MAAM,GAAG,OAAO,SAAS,IAAI,OAAO,aAAa,IAAI,OAAO,sBAAsB;;;;;;;;;;EAWlF,QAAQ,SAAS,aAAa;;;;;;;;EAS9B,KAAK,IAAI,WAAW;;EAGpB,WAAW;;;;;;;qBAQA,SAAS"}
@@ -0,0 +1,65 @@
1
+ import { TriggerIR } from "../ir.mjs";
2
+ import { EventRef } from "./refs.mjs";
3
+ import { Condition, PayloadWhere, SegmentRef } from "./condition.mjs";
4
+ //#region src/dsl/trigger.d.ts
5
+ /**
6
+ * Triggers — the four ways into a workflow, mirroring customer.io's campaign
7
+ * trigger types. A trigger is a plain reusable object; the event name and
8
+ * payload types flow in from an e.xxx reference, so the factory itself needs
9
+ * no generics.
10
+ */
11
+ /** 'YYYY-MM-DD HH:mm:ss'. TODO: validate at runtime — template literals cannot express leading zeros. */
12
+ export type DateTime = string;
13
+ /** Trigger reference: what trigger.xxx() returns, reusable across workflows. */
14
+ export interface TriggerRef {
15
+ readonly type: 'event' | 'segment' | 'date' | 'webhook';
16
+ }
17
+ /** @internal the compiled shape behind a TriggerRef — workflow.toIR reads .ir off it */
18
+ export interface TriggerInternal extends TriggerRef {
19
+ readonly ir: TriggerIR;
20
+ }
21
+ export interface EventTriggerOptions {
22
+ filter?: Condition;
23
+ }
24
+ /** Trigger factory: four ways in, mirroring customer.io's campaign trigger types. */
25
+ export interface TriggerFactory {
26
+ /**
27
+ * Event trigger: the event name comes from an e.xxx reference (types flow in
28
+ * from it, so the factory itself needs no generics). Two independent gates:
29
+ * - the optional second argument is a payload where clause (typed refs, the
30
+ * ordinary predicates — compiles to IR data the UI renders):
31
+ * trigger.event(e.login, (p) => eq(p.platform, 'web'))
32
+ * - `filter` tests the user's profile (customer.io's trigger Filters).
33
+ * The user enters only if the event fired *and* both gates hold.
34
+ */
35
+ event<P>(event: EventRef<P>, opts?: EventTriggerOptions): TriggerRef;
36
+ event<P>(event: EventRef<P>, where: PayloadWhere<P>, opts?: EventTriggerOptions): TriggerRef;
37
+ /**
38
+ * Segment-entry trigger: the user enters the moment they go from not
39
+ * matching to matching. Only a named segment is accepted — entry semantics
40
+ * need a membership table, which an anonymous expression cannot provide.
41
+ * Runtime note: membership is maintained lazily (re-evaluated on the user's
42
+ * ingest/identify activity), so purely time-driven drift — e.g. an
43
+ * inactivity segment becoming true by clock alone — is only observed on the
44
+ * user's next activity. TODO: a cron sweep for time-driven segments.
45
+ */
46
+ segment(segment: SegmentRef): TriggerRef;
47
+ /**
48
+ * Scheduled trigger (one-shot, e.g. '2026-12-25 09:00:00', interpreted as
49
+ * UTC). TODO: not routed by the runtime yet — deployBundle reports it in
50
+ * `unrouted`; the implementation goes through cron + Queues (instance
51
+ * creation is rate-limited, a date trigger fans out to the whole audience at
52
+ * once). TODO: cron/recurring form.
53
+ */
54
+ date(at: DateTime): TriggerRef;
55
+ /** Webhook trigger: third-party or external code fires it via a URL; the runtime allocates the endpoint. */
56
+ webhook(): TriggerRef;
57
+ }
58
+ /**
59
+ * Trigger definition: a plain object — event names come from e.xxx references.
60
+ *
61
+ * const login = trigger.event(e.login, { filter: newUsers7d });
62
+ */
63
+ export declare const trigger: TriggerFactory;
64
+ //#endregion
65
+ //# sourceMappingURL=trigger.d.mts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"trigger.d.mts","names":[],"sources":["../../src/dsl/trigger.ts"],"mappings":";;;;;;;;;;;YAYY;;iBAGK;WACN;;;iBAIM,wBAAwB;WAC9B,IAAI;;iBAQE;EACf,SAAS;;;iBAIM;;;;;;;;;;EAUf,MAAM,GAAG,OAAO,SAAS,IAAI,OAAO,sBAAsB;EAC1D,MAAM,GAAG,OAAO,SAAS,IAAI,OAAO,aAAa,IAAI,OAAO,sBAAsB;;;;;;;;;;EAWlF,QAAQ,SAAS,aAAa;;;;;;;;EAS9B,KAAK,IAAI,WAAW;;EAGpB,WAAW;;;;;;;qBAQA,SAAS"}
@@ -0,0 +1,39 @@
1
+ import { payloadRefs } from "./refs.mjs";
2
+ import { condIR } from "./condition.mjs";
3
+ //#region src/dsl/trigger.ts
4
+ const makeTrigger = (ir) => {
5
+ return {
6
+ type: ir.type,
7
+ ir
8
+ };
9
+ };
10
+ /**
11
+ * Trigger definition: a plain object — event names come from e.xxx references.
12
+ *
13
+ * const login = trigger.event(e.login, { filter: newUsers7d });
14
+ */
15
+ const trigger = {
16
+ event: (ev, whereOrOpts, maybeOpts) => {
17
+ const where = typeof whereOrOpts === "function" ? whereOrOpts : void 0;
18
+ const opts = typeof whereOrOpts === "function" ? maybeOpts : whereOrOpts;
19
+ return makeTrigger({
20
+ type: "event",
21
+ event: ev.name,
22
+ ...where !== void 0 ? { where: condIR(where(payloadRefs())) } : {},
23
+ ...opts?.filter !== void 0 ? { filter: condIR(opts.filter) } : {}
24
+ });
25
+ },
26
+ segment: (seg) => makeTrigger({
27
+ type: "segment",
28
+ segment: seg.id
29
+ }),
30
+ date: (at) => makeTrigger({
31
+ type: "date",
32
+ at
33
+ }),
34
+ webhook: () => makeTrigger({ type: "webhook" })
35
+ };
36
+ //#endregion
37
+ export { trigger };
38
+
39
+ //# sourceMappingURL=trigger.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"trigger.mjs","names":[],"sources":["../../src/dsl/trigger.ts"],"sourcesContent":["import type { TriggerIR } from '../ir';\nimport { type Condition, type PayloadWhere, type SegmentRef, condIR } from './condition';\nimport { type EventRef, payloadRefs } from './refs';\n\n/**\n * Triggers — the four ways into a workflow, mirroring customer.io's campaign\n * trigger types. A trigger is a plain reusable object; the event name and\n * payload types flow in from an e.xxx reference, so the factory itself needs\n * no generics.\n */\n\n/** 'YYYY-MM-DD HH:mm:ss'. TODO: validate at runtime — template literals cannot express leading zeros. */\nexport type DateTime = string;\n\n/** Trigger reference: what trigger.xxx() returns, reusable across workflows. */\nexport interface TriggerRef {\n readonly type: 'event' | 'segment' | 'date' | 'webhook';\n}\n\n/** @internal the compiled shape behind a TriggerRef — workflow.toIR reads .ir off it */\nexport interface TriggerInternal extends TriggerRef {\n readonly ir: TriggerIR;\n}\n\nconst makeTrigger = (ir: TriggerIR): TriggerRef => {\n const impl: TriggerInternal = { type: ir.type, ir };\n return impl;\n};\n\nexport interface EventTriggerOptions {\n filter?: Condition;\n}\n\n/** Trigger factory: four ways in, mirroring customer.io's campaign trigger types. */\nexport interface TriggerFactory {\n /**\n * Event trigger: the event name comes from an e.xxx reference (types flow in\n * from it, so the factory itself needs no generics). Two independent gates:\n * - the optional second argument is a payload where clause (typed refs, the\n * ordinary predicates — compiles to IR data the UI renders):\n * trigger.event(e.login, (p) => eq(p.platform, 'web'))\n * - `filter` tests the user's profile (customer.io's trigger Filters).\n * The user enters only if the event fired *and* both gates hold.\n */\n event<P>(event: EventRef<P>, opts?: EventTriggerOptions): TriggerRef;\n event<P>(event: EventRef<P>, where: PayloadWhere<P>, opts?: EventTriggerOptions): TriggerRef;\n\n /**\n * Segment-entry trigger: the user enters the moment they go from not\n * matching to matching. Only a named segment is accepted — entry semantics\n * need a membership table, which an anonymous expression cannot provide.\n * Runtime note: membership is maintained lazily (re-evaluated on the user's\n * ingest/identify activity), so purely time-driven drift — e.g. an\n * inactivity segment becoming true by clock alone — is only observed on the\n * user's next activity. TODO: a cron sweep for time-driven segments.\n */\n segment(segment: SegmentRef): TriggerRef;\n\n /**\n * Scheduled trigger (one-shot, e.g. '2026-12-25 09:00:00', interpreted as\n * UTC). TODO: not routed by the runtime yet — deployBundle reports it in\n * `unrouted`; the implementation goes through cron + Queues (instance\n * creation is rate-limited, a date trigger fans out to the whole audience at\n * once). TODO: cron/recurring form.\n */\n date(at: DateTime): TriggerRef;\n\n /** Webhook trigger: third-party or external code fires it via a URL; the runtime allocates the endpoint. */\n webhook(): TriggerRef;\n}\n\n/**\n * Trigger definition: a plain object — event names come from e.xxx references.\n *\n * const login = trigger.event(e.login, { filter: newUsers7d });\n */\nexport const trigger: TriggerFactory = {\n event: <P>(\n ev: EventRef<P>,\n whereOrOpts?: PayloadWhere<P> | EventTriggerOptions,\n maybeOpts?: EventTriggerOptions\n ) => {\n const where = typeof whereOrOpts === 'function' ? whereOrOpts : undefined;\n const opts = typeof whereOrOpts === 'function' ? maybeOpts : whereOrOpts;\n return makeTrigger({\n type: 'event',\n event: ev.name,\n ...(where !== undefined ? { where: condIR(where(payloadRefs<P>())) } : {}),\n ...(opts?.filter !== undefined ? { filter: condIR(opts.filter) } : {}),\n });\n },\n segment: (seg) => makeTrigger({ type: 'segment', segment: seg.id }),\n date: (at) => makeTrigger({ type: 'date', at }),\n webhook: () => makeTrigger({ type: 'webhook' }),\n};\n"],"mappings":";;;AAwBA,MAAM,eAAe,OAA8B;CAEjD,OAAO;EADyB,MAAM,GAAG;EAAM;CACrC;AACZ;;;;;;AAiDA,MAAa,UAA0B;CACrC,QACE,IACA,aACA,cACG;EACH,MAAM,QAAQ,OAAO,gBAAgB,aAAa,cAAc,KAAA;EAChE,MAAM,OAAO,OAAO,gBAAgB,aAAa,YAAY;EAC7D,OAAO,YAAY;GACjB,MAAM;GACN,OAAO,GAAG;GACV,GAAI,UAAU,KAAA,IAAY,EAAE,OAAO,OAAO,MAAM,YAAe,CAAC,CAAC,EAAE,IAAI,CAAC;GACxE,GAAI,MAAM,WAAW,KAAA,IAAY,EAAE,QAAQ,OAAO,KAAK,MAAM,EAAE,IAAI,CAAC;EACtE,CAAC;CACH;CACA,UAAU,QAAQ,YAAY;EAAE,MAAM;EAAW,SAAS,IAAI;CAAG,CAAC;CAClE,OAAO,OAAO,YAAY;EAAE,MAAM;EAAQ;CAAG,CAAC;CAC9C,eAAe,YAAY,EAAE,MAAM,UAAU,CAAC;AAChD"}
@@ -0,0 +1,121 @@
1
+ Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
2
+ const require_hash = require("../hash.cjs");
3
+ const require_provenance = require("../provenance.cjs");
4
+ const require_dsl_base = require("./base.cjs");
5
+ const require_dsl_condition = require("./condition.cjs");
6
+ const require_dsl_flow = require("./flow.cjs");
7
+ const require_ir = require("../ir.cjs");
8
+ //#region src/dsl/workflow.ts
9
+ /**
10
+ * Assign node ids from the structural path (rules in ir.ts's header). Written
11
+ * in place into the tree toIR deep-cloned, never into the builder's own nodes.
12
+ */
13
+ function assignIds(nodes, prefix) {
14
+ nodes.forEach((node, i) => {
15
+ const id = prefix === "" ? String(i) : `${prefix}.${i}`;
16
+ node.id = id;
17
+ switch (node.type) {
18
+ case "branch":
19
+ node.cases.forEach((c, ci) => assignIds(c.flow, `${id}.c${ci}`));
20
+ if (node.otherwise) assignIds(node.otherwise, `${id}.o`);
21
+ break;
22
+ case "cohort":
23
+ node.arms.forEach((arm) => assignIds(arm.flow, `${id}.${arm.name}`));
24
+ break;
25
+ case "wait_until": if (Array.isArray(node.onTimeout)) assignIds(node.onTimeout, `${id}.t`);
26
+ }
27
+ });
28
+ }
29
+ /**
30
+ * Ids are derived, never authored, so a duplicate is always a compiler bug —
31
+ * and a silent one: assignIds writes in place, so the second write simply wins
32
+ * and two nodes ship as one. What that costs is concrete, because an id is the
33
+ * durable step name (`step.do('{id}:send')`), the message idempotency key
34
+ * (`{instanceId}:{id}`) and the cohort bucket seed: the twins share a
35
+ * checkpoint, and the second send is suppressed as a duplicate of the first.
36
+ * Cheap to check once at the end of the compile, so it is checked.
37
+ */
38
+ function assertUniqueIds(nodes, seen = /* @__PURE__ */ new Set()) {
39
+ for (const node of nodes) {
40
+ if (seen.has(node.id)) throw new Error(`toIR(): node id '${node.id}' is used twice — ids are durable step names and message idempotency keys, so they must be unique`);
41
+ seen.add(node.id);
42
+ switch (node.type) {
43
+ case "branch":
44
+ for (const branchCase of node.cases) assertUniqueIds(branchCase.flow, seen);
45
+ if (node.otherwise) assertUniqueIds(node.otherwise, seen);
46
+ break;
47
+ case "cohort":
48
+ for (const arm of node.arms) assertUniqueIds(arm.flow, seen);
49
+ break;
50
+ case "wait_until": if (Array.isArray(node.onTimeout)) assertUniqueIds(node.onTimeout, seen);
51
+ }
52
+ }
53
+ }
54
+ var WorkflowBuilderImpl = class extends require_dsl_flow.FlowBuilderImpl {
55
+ options;
56
+ loc;
57
+ constructor(options, loc) {
58
+ super();
59
+ this.options = options;
60
+ this.loc = loc;
61
+ }
62
+ goalIR() {
63
+ const goal = this.options.goal;
64
+ if (goal === void 0) return void 0;
65
+ if ("__condition" in goal) return {
66
+ condition: require_dsl_condition.condIR(goal),
67
+ exitOnMatch: true
68
+ };
69
+ return {
70
+ condition: require_dsl_condition.condIR(goal.condition),
71
+ ...goal.within !== void 0 ? { within: require_dsl_base.durationIR(goal.within) } : {},
72
+ exitOnMatch: goal.exitOnMatch ?? true
73
+ };
74
+ }
75
+ metaIR() {
76
+ const { name, description } = this.options;
77
+ if (name === void 0 && description === void 0 && this.loc === void 0) return;
78
+ return {
79
+ ...name !== void 0 ? { name } : {},
80
+ ...description !== void 0 ? { description } : {},
81
+ ...this.loc !== void 0 ? { loc: this.loc } : {}
82
+ };
83
+ }
84
+ toIR() {
85
+ const flowNodes = structuredClone(this.nodes);
86
+ assignIds(flowNodes, "");
87
+ assertUniqueIds(flowNodes);
88
+ const goal = this.goalIR();
89
+ const meta = this.metaIR();
90
+ const body = {
91
+ irVersion: 2,
92
+ id: this.options.id,
93
+ ...meta !== void 0 ? { meta } : {},
94
+ trigger: this.options.trigger.ir,
95
+ ...goal !== void 0 ? { goal } : {},
96
+ ...this.options.exitWhen !== void 0 ? { exitWhen: require_dsl_condition.condIR(this.options.exitWhen) } : {},
97
+ flow: flowNodes
98
+ };
99
+ return require_ir.WorkflowIR.parse({
100
+ ...body,
101
+ contentHash: require_hash.semanticHash(body)
102
+ });
103
+ }
104
+ };
105
+ /**
106
+ * Workflow definition: an id, configuration (trigger / goal / exitWhen),
107
+ * optional labels, and chained steps.
108
+ *
109
+ * export const onboarding = workflow({
110
+ * id: 'onboarding',
111
+ * name: 'Onboarding',
112
+ * trigger: trigger.event(e.sign_up),
113
+ * }).email(t.email.welcome);
114
+ */
115
+ function workflow(definition) {
116
+ return new WorkflowBuilderImpl(definition, require_provenance.captureLoc(workflow));
117
+ }
118
+ //#endregion
119
+ exports.workflow = workflow;
120
+
121
+ //# sourceMappingURL=workflow.cjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"workflow.cjs","names":["FlowBuilderImpl","condIR","durationIR","WorkflowIRSchema","semanticHash","captureLoc"],"sources":["../../src/dsl/workflow.ts"],"sourcesContent":["import { semanticHash } from '../hash';\nimport {\n type GoalIR,\n IR_VERSION,\n type MetaIR,\n type NodeIR,\n type SourceLocIR,\n type WorkflowIR,\n WorkflowIR as WorkflowIRSchema,\n} from '../ir';\nimport { captureLoc } from '../provenance';\nimport { type Duration, durationIR } from './base';\nimport { type Condition, condIR } from './condition';\nimport { type FlowBuilder, FlowBuilderImpl } from './flow';\nimport type { TriggerInternal, TriggerRef } from './trigger';\n\n/**\n * The workflow — a named flow chain plus its configuration (options =\n * configuration, the chain = steps), and the compiler back half: `toIR()`\n * deep-clones the collected nodes, assigns structural-path ids, computes the\n * contentHash (metadata stripped, see hash.ts) and self-checks the result\n * against the authoritative IR schema.\n */\n\n/** Full conversion-goal configuration (customer.io's Goal & Exit semantics). */\nexport interface GoalOptions {\n condition: Condition;\n /** Attribution window: how long after entry a match still counts as a conversion. Unbounded by default. */\n within?: Duration;\n /** Exit on conversion. Defaults to true — this is what absorbs all those True→Exit arms in a UI canvas. */\n exitOnMatch?: boolean;\n}\n\nexport interface WorkflowDefinition {\n /**\n * Wire identity — engine instances, the entry ledger and stats keys are all\n * built on it (`WorkflowIR.id`), so it is not something to rename for\n * readability; `name` is.\n */\n id: string;\n\n /** Trigger: a trigger.xxx() asset. TODO: multiple triggers, entry frequency / re-entry policy. */\n trigger: TriggerRef;\n\n /**\n * Conversion goal: feeds reporting (conversion rate / attribution) and by\n * default exits on match. Checked before each node runs. Pass a condition\n * for the shorthand, or GoalOptions for the full form.\n */\n goal?: Condition | GoalOptions;\n\n /** Plain exit condition: leaving without counting as a conversion (unsubscribed, no longer eligible). Coexists with goal. */\n exitWhen?: Condition;\n\n /*\n * Everything below is human-facing metadata: it lands in IR's `meta` field\n * and is **excluded from contentHash**. Editing it neither invalidates the\n * version in-flight users are pinned to nor shows up as a change in plan.\n */\n\n /** Human label: what the studio shows instead of the id. */\n name?: string;\n\n /** One line on what this flow does (UI lists, plan output). */\n description?: string;\n}\n\nexport interface WorkflowBuilder extends FlowBuilder {\n toIR(): WorkflowIR;\n}\n\n/**\n * Assign node ids from the structural path (rules in ir.ts's header). Written\n * in place into the tree toIR deep-cloned, never into the builder's own nodes.\n */\nfunction assignIds(nodes: NodeIR[], prefix: string): void {\n nodes.forEach((node, i) => {\n const id = prefix === '' ? String(i) : `${prefix}.${i}`;\n node.id = id;\n switch (node.type) {\n case 'branch':\n node.cases.forEach((c, ci) => assignIds(c.flow, `${id}.c${ci}`));\n if (node.otherwise) assignIds(node.otherwise, `${id}.o`);\n break;\n case 'cohort':\n node.arms.forEach((arm) => assignIds(arm.flow, `${id}.${arm.name}`));\n break;\n case 'wait_until':\n if (Array.isArray(node.onTimeout)) assignIds(node.onTimeout, `${id}.t`);\n break;\n default:\n break;\n }\n });\n}\n\n/**\n * Ids are derived, never authored, so a duplicate is always a compiler bug —\n * and a silent one: assignIds writes in place, so the second write simply wins\n * and two nodes ship as one. What that costs is concrete, because an id is the\n * durable step name (`step.do('{id}:send')`), the message idempotency key\n * (`{instanceId}:{id}`) and the cohort bucket seed: the twins share a\n * checkpoint, and the second send is suppressed as a duplicate of the first.\n * Cheap to check once at the end of the compile, so it is checked.\n */\nfunction assertUniqueIds(nodes: readonly NodeIR[], seen = new Set<string>()): void {\n for (const node of nodes) {\n if (seen.has(node.id)) {\n throw new Error(\n `toIR(): node id '${node.id}' is used twice — ids are durable step names and message idempotency keys, so they must be unique`\n );\n }\n seen.add(node.id);\n switch (node.type) {\n case 'branch':\n for (const branchCase of node.cases) assertUniqueIds(branchCase.flow, seen);\n if (node.otherwise) assertUniqueIds(node.otherwise, seen);\n break;\n case 'cohort':\n for (const arm of node.arms) assertUniqueIds(arm.flow, seen);\n break;\n case 'wait_until':\n if (Array.isArray(node.onTimeout)) assertUniqueIds(node.onTimeout, seen);\n break;\n default:\n break;\n }\n }\n}\n\nclass WorkflowBuilderImpl extends FlowBuilderImpl implements WorkflowBuilder {\n constructor(\n private readonly options: WorkflowDefinition,\n /** Callsite of the workflow() call (provenance; lands in meta.loc). */\n private readonly loc: SourceLocIR | undefined\n ) {\n super();\n }\n\n private goalIR(): GoalIR | undefined {\n const goal = this.options.goal;\n if (goal === undefined) return undefined;\n if ('__condition' in goal) {\n return { condition: condIR(goal), exitOnMatch: true };\n }\n return {\n condition: condIR(goal.condition),\n ...(goal.within !== undefined ? { within: durationIR(goal.within) } : {}),\n exitOnMatch: goal.exitOnMatch ?? true,\n };\n }\n\n private metaIR(): MetaIR | undefined {\n const { name, description } = this.options;\n if (name === undefined && description === undefined && this.loc === undefined) {\n return undefined;\n }\n return {\n ...(name !== undefined ? { name } : {}),\n ...(description !== undefined ? { description } : {}),\n ...(this.loc !== undefined ? { loc: this.loc } : {}),\n };\n }\n\n toIR(): WorkflowIR {\n const flowNodes = structuredClone(this.nodes);\n assignIds(flowNodes, '');\n assertUniqueIds(flowNodes);\n const goal = this.goalIR();\n const meta = this.metaIR();\n const body = {\n irVersion: IR_VERSION,\n id: this.options.id,\n ...(meta !== undefined ? { meta } : {}),\n trigger: (this.options.trigger as TriggerInternal).ir,\n ...(goal !== undefined ? { goal } : {}),\n ...(this.options.exitWhen !== undefined ? { exitWhen: condIR(this.options.exitWhen) } : {}),\n flow: flowNodes,\n };\n // semanticHash strips meta / label / reason, so metadata edits leave contentHash alone\n // Self-check: the compiler's output must pass IR's authoritative schema\n return WorkflowIRSchema.parse({ ...body, contentHash: semanticHash(body) });\n }\n}\n\n/**\n * Workflow definition: an id, configuration (trigger / goal / exitWhen),\n * optional labels, and chained steps.\n *\n * export const onboarding = workflow({\n * id: 'onboarding',\n * name: 'Onboarding',\n * trigger: trigger.event(e.sign_up),\n * }).email(t.email.welcome);\n */\nexport function workflow(definition: WorkflowDefinition): WorkflowBuilder {\n return new WorkflowBuilderImpl(definition, captureLoc(workflow));\n}\n"],"mappings":";;;;;;;;;;;;AA2EA,SAAS,UAAU,OAAiB,QAAsB;CACxD,MAAM,SAAS,MAAM,MAAM;EACzB,MAAM,KAAK,WAAW,KAAK,OAAO,CAAC,IAAI,GAAG,OAAO,GAAG;EACpD,KAAK,KAAK;EACV,QAAQ,KAAK,MAAb;GACE,KAAK;IACH,KAAK,MAAM,SAAS,GAAG,OAAO,UAAU,EAAE,MAAM,GAAG,GAAG,IAAI,IAAI,CAAC;IAC/D,IAAI,KAAK,WAAW,UAAU,KAAK,WAAW,GAAG,GAAG,GAAG;IACvD;GACF,KAAK;IACH,KAAK,KAAK,SAAS,QAAQ,UAAU,IAAI,MAAM,GAAG,GAAG,GAAG,IAAI,MAAM,CAAC;IACnE;GACF,KAAK,cACH,IAAI,MAAM,QAAQ,KAAK,SAAS,GAAG,UAAU,KAAK,WAAW,GAAG,GAAG,GAAG;EAI1E;CACF,CAAC;AACH;;;;;;;;;;AAWA,SAAS,gBAAgB,OAA0B,uBAAO,IAAI,IAAY,GAAS;CACjF,KAAK,MAAM,QAAQ,OAAO;EACxB,IAAI,KAAK,IAAI,KAAK,EAAE,GAClB,MAAM,IAAI,MACR,oBAAoB,KAAK,GAAG,kGAC9B;EAEF,KAAK,IAAI,KAAK,EAAE;EAChB,QAAQ,KAAK,MAAb;GACE,KAAK;IACH,KAAK,MAAM,cAAc,KAAK,OAAO,gBAAgB,WAAW,MAAM,IAAI;IAC1E,IAAI,KAAK,WAAW,gBAAgB,KAAK,WAAW,IAAI;IACxD;GACF,KAAK;IACH,KAAK,MAAM,OAAO,KAAK,MAAM,gBAAgB,IAAI,MAAM,IAAI;IAC3D;GACF,KAAK,cACH,IAAI,MAAM,QAAQ,KAAK,SAAS,GAAG,gBAAgB,KAAK,WAAW,IAAI;EAI3E;CACF;AACF;AAEA,IAAM,sBAAN,cAAkCA,iBAAAA,gBAA2C;CAExD;CAEA;CAHnB,YACE,SAEA,KACA;EACA,MAAM;EAJW,KAAA,UAAA;EAEA,KAAA,MAAA;CAGnB;CAEA,SAAqC;EACnC,MAAM,OAAO,KAAK,QAAQ;EAC1B,IAAI,SAAS,KAAA,GAAW,OAAO,KAAA;EAC/B,IAAI,iBAAiB,MACnB,OAAO;GAAE,WAAWC,sBAAAA,OAAO,IAAI;GAAG,aAAa;EAAK;EAEtD,OAAO;GACL,WAAWA,sBAAAA,OAAO,KAAK,SAAS;GAChC,GAAI,KAAK,WAAW,KAAA,IAAY,EAAE,QAAQC,iBAAAA,WAAW,KAAK,MAAM,EAAE,IAAI,CAAC;GACvE,aAAa,KAAK,eAAe;EACnC;CACF;CAEA,SAAqC;EACnC,MAAM,EAAE,MAAM,gBAAgB,KAAK;EACnC,IAAI,SAAS,KAAA,KAAa,gBAAgB,KAAA,KAAa,KAAK,QAAQ,KAAA,GAClE;EAEF,OAAO;GACL,GAAI,SAAS,KAAA,IAAY,EAAE,KAAK,IAAI,CAAC;GACrC,GAAI,gBAAgB,KAAA,IAAY,EAAE,YAAY,IAAI,CAAC;GACnD,GAAI,KAAK,QAAQ,KAAA,IAAY,EAAE,KAAK,KAAK,IAAI,IAAI,CAAC;EACpD;CACF;CAEA,OAAmB;EACjB,MAAM,YAAY,gBAAgB,KAAK,KAAK;EAC5C,UAAU,WAAW,EAAE;EACvB,gBAAgB,SAAS;EACzB,MAAM,OAAO,KAAK,OAAO;EACzB,MAAM,OAAO,KAAK,OAAO;EACzB,MAAM,OAAO;GACX,WAAA;GACA,IAAI,KAAK,QAAQ;GACjB,GAAI,SAAS,KAAA,IAAY,EAAE,KAAK,IAAI,CAAC;GACrC,SAAU,KAAK,QAAQ,QAA4B;GACnD,GAAI,SAAS,KAAA,IAAY,EAAE,KAAK,IAAI,CAAC;GACrC,GAAI,KAAK,QAAQ,aAAa,KAAA,IAAY,EAAE,UAAUD,sBAAAA,OAAO,KAAK,QAAQ,QAAQ,EAAE,IAAI,CAAC;GACzF,MAAM;EACR;EAGA,OAAOE,WAAAA,WAAiB,MAAM;GAAE,GAAG;GAAM,aAAaC,aAAAA,aAAa,IAAI;EAAE,CAAC;CAC5E;AACF;;;;;;;;;;;AAYA,SAAgB,SAAS,YAAiD;CACxE,OAAO,IAAI,oBAAoB,YAAYC,mBAAAA,WAAW,QAAQ,CAAC;AACjE"}
@@ -0,0 +1,59 @@
1
+ import { WorkflowIR } from "../ir.cjs";
2
+ import { Duration } from "./base.cjs";
3
+ import { Condition } from "./condition.cjs";
4
+ import { FlowBuilder } from "./flow.cjs";
5
+ import { TriggerRef } from "./trigger.cjs";
6
+ //#region src/dsl/workflow.d.ts
7
+ /**
8
+ * The workflow — a named flow chain plus its configuration (options =
9
+ * configuration, the chain = steps), and the compiler back half: `toIR()`
10
+ * deep-clones the collected nodes, assigns structural-path ids, computes the
11
+ * contentHash (metadata stripped, see hash.ts) and self-checks the result
12
+ * against the authoritative IR schema.
13
+ */
14
+ /** Full conversion-goal configuration (customer.io's Goal & Exit semantics). */
15
+ export interface GoalOptions {
16
+ condition: Condition;
17
+ /** Attribution window: how long after entry a match still counts as a conversion. Unbounded by default. */
18
+ within?: Duration;
19
+ /** Exit on conversion. Defaults to true — this is what absorbs all those True→Exit arms in a UI canvas. */
20
+ exitOnMatch?: boolean;
21
+ }
22
+ export interface WorkflowDefinition {
23
+ /**
24
+ * Wire identity — engine instances, the entry ledger and stats keys are all
25
+ * built on it (`WorkflowIR.id`), so it is not something to rename for
26
+ * readability; `name` is.
27
+ */
28
+ id: string;
29
+ /** Trigger: a trigger.xxx() asset. TODO: multiple triggers, entry frequency / re-entry policy. */
30
+ trigger: TriggerRef;
31
+ /**
32
+ * Conversion goal: feeds reporting (conversion rate / attribution) and by
33
+ * default exits on match. Checked before each node runs. Pass a condition
34
+ * for the shorthand, or GoalOptions for the full form.
35
+ */
36
+ goal?: Condition | GoalOptions;
37
+ /** Plain exit condition: leaving without counting as a conversion (unsubscribed, no longer eligible). Coexists with goal. */
38
+ exitWhen?: Condition;
39
+ /** Human label: what the studio shows instead of the id. */
40
+ name?: string;
41
+ /** One line on what this flow does (UI lists, plan output). */
42
+ description?: string;
43
+ }
44
+ export interface WorkflowBuilder extends FlowBuilder {
45
+ toIR(): WorkflowIR;
46
+ }
47
+ /**
48
+ * Workflow definition: an id, configuration (trigger / goal / exitWhen),
49
+ * optional labels, and chained steps.
50
+ *
51
+ * export const onboarding = workflow({
52
+ * id: 'onboarding',
53
+ * name: 'Onboarding',
54
+ * trigger: trigger.event(e.sign_up),
55
+ * }).email(t.email.welcome);
56
+ */
57
+ export declare function workflow(definition: WorkflowDefinition): WorkflowBuilder;
58
+ //#endregion
59
+ //# sourceMappingURL=workflow.d.cts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"workflow.d.cts","names":[],"sources":["../../src/dsl/workflow.ts"],"mappings":";;;;;;;;;;;;;;iBAyBiB;EACf,WAAW;;EAEX,SAAS;;EAET;;iBAGe;;;;;;EAMf;;EAGA,SAAS;;;;;;EAOT,OAAO,YAAY;;EAGnB,WAAW;;EASX;;EAGA;;iBAGe,wBAAwB;EACvC,QAAQ;;;;;;;;;;;;wBA+HM,SAAS,YAAY,qBAAqB"}
@@ -0,0 +1,59 @@
1
+ import { WorkflowIR } from "../ir.mjs";
2
+ import { Duration } from "./base.mjs";
3
+ import { Condition } from "./condition.mjs";
4
+ import { FlowBuilder } from "./flow.mjs";
5
+ import { TriggerRef } from "./trigger.mjs";
6
+ //#region src/dsl/workflow.d.ts
7
+ /**
8
+ * The workflow — a named flow chain plus its configuration (options =
9
+ * configuration, the chain = steps), and the compiler back half: `toIR()`
10
+ * deep-clones the collected nodes, assigns structural-path ids, computes the
11
+ * contentHash (metadata stripped, see hash.ts) and self-checks the result
12
+ * against the authoritative IR schema.
13
+ */
14
+ /** Full conversion-goal configuration (customer.io's Goal & Exit semantics). */
15
+ export interface GoalOptions {
16
+ condition: Condition;
17
+ /** Attribution window: how long after entry a match still counts as a conversion. Unbounded by default. */
18
+ within?: Duration;
19
+ /** Exit on conversion. Defaults to true — this is what absorbs all those True→Exit arms in a UI canvas. */
20
+ exitOnMatch?: boolean;
21
+ }
22
+ export interface WorkflowDefinition {
23
+ /**
24
+ * Wire identity — engine instances, the entry ledger and stats keys are all
25
+ * built on it (`WorkflowIR.id`), so it is not something to rename for
26
+ * readability; `name` is.
27
+ */
28
+ id: string;
29
+ /** Trigger: a trigger.xxx() asset. TODO: multiple triggers, entry frequency / re-entry policy. */
30
+ trigger: TriggerRef;
31
+ /**
32
+ * Conversion goal: feeds reporting (conversion rate / attribution) and by
33
+ * default exits on match. Checked before each node runs. Pass a condition
34
+ * for the shorthand, or GoalOptions for the full form.
35
+ */
36
+ goal?: Condition | GoalOptions;
37
+ /** Plain exit condition: leaving without counting as a conversion (unsubscribed, no longer eligible). Coexists with goal. */
38
+ exitWhen?: Condition;
39
+ /** Human label: what the studio shows instead of the id. */
40
+ name?: string;
41
+ /** One line on what this flow does (UI lists, plan output). */
42
+ description?: string;
43
+ }
44
+ export interface WorkflowBuilder extends FlowBuilder {
45
+ toIR(): WorkflowIR;
46
+ }
47
+ /**
48
+ * Workflow definition: an id, configuration (trigger / goal / exitWhen),
49
+ * optional labels, and chained steps.
50
+ *
51
+ * export const onboarding = workflow({
52
+ * id: 'onboarding',
53
+ * name: 'Onboarding',
54
+ * trigger: trigger.event(e.sign_up),
55
+ * }).email(t.email.welcome);
56
+ */
57
+ export declare function workflow(definition: WorkflowDefinition): WorkflowBuilder;
58
+ //#endregion
59
+ //# sourceMappingURL=workflow.d.mts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"workflow.d.mts","names":[],"sources":["../../src/dsl/workflow.ts"],"mappings":";;;;;;;;;;;;;;iBAyBiB;EACf,WAAW;;EAEX,SAAS;;EAET;;iBAGe;;;;;;EAMf;;EAGA,SAAS;;;;;;EAOT,OAAO,YAAY;;EAGnB,WAAW;;EASX;;EAGA;;iBAGe,wBAAwB;EACvC,QAAQ;;;;;;;;;;;;wBA+HM,SAAS,YAAY,qBAAqB"}
@@ -0,0 +1,120 @@
1
+ import { semanticHash } from "../hash.mjs";
2
+ import { captureLoc } from "../provenance.mjs";
3
+ import { durationIR } from "./base.mjs";
4
+ import { condIR } from "./condition.mjs";
5
+ import { FlowBuilderImpl } from "./flow.mjs";
6
+ import { WorkflowIR } from "../ir.mjs";
7
+ //#region src/dsl/workflow.ts
8
+ /**
9
+ * Assign node ids from the structural path (rules in ir.ts's header). Written
10
+ * in place into the tree toIR deep-cloned, never into the builder's own nodes.
11
+ */
12
+ function assignIds(nodes, prefix) {
13
+ nodes.forEach((node, i) => {
14
+ const id = prefix === "" ? String(i) : `${prefix}.${i}`;
15
+ node.id = id;
16
+ switch (node.type) {
17
+ case "branch":
18
+ node.cases.forEach((c, ci) => assignIds(c.flow, `${id}.c${ci}`));
19
+ if (node.otherwise) assignIds(node.otherwise, `${id}.o`);
20
+ break;
21
+ case "cohort":
22
+ node.arms.forEach((arm) => assignIds(arm.flow, `${id}.${arm.name}`));
23
+ break;
24
+ case "wait_until": if (Array.isArray(node.onTimeout)) assignIds(node.onTimeout, `${id}.t`);
25
+ }
26
+ });
27
+ }
28
+ /**
29
+ * Ids are derived, never authored, so a duplicate is always a compiler bug —
30
+ * and a silent one: assignIds writes in place, so the second write simply wins
31
+ * and two nodes ship as one. What that costs is concrete, because an id is the
32
+ * durable step name (`step.do('{id}:send')`), the message idempotency key
33
+ * (`{instanceId}:{id}`) and the cohort bucket seed: the twins share a
34
+ * checkpoint, and the second send is suppressed as a duplicate of the first.
35
+ * Cheap to check once at the end of the compile, so it is checked.
36
+ */
37
+ function assertUniqueIds(nodes, seen = /* @__PURE__ */ new Set()) {
38
+ for (const node of nodes) {
39
+ if (seen.has(node.id)) throw new Error(`toIR(): node id '${node.id}' is used twice — ids are durable step names and message idempotency keys, so they must be unique`);
40
+ seen.add(node.id);
41
+ switch (node.type) {
42
+ case "branch":
43
+ for (const branchCase of node.cases) assertUniqueIds(branchCase.flow, seen);
44
+ if (node.otherwise) assertUniqueIds(node.otherwise, seen);
45
+ break;
46
+ case "cohort":
47
+ for (const arm of node.arms) assertUniqueIds(arm.flow, seen);
48
+ break;
49
+ case "wait_until": if (Array.isArray(node.onTimeout)) assertUniqueIds(node.onTimeout, seen);
50
+ }
51
+ }
52
+ }
53
+ var WorkflowBuilderImpl = class extends FlowBuilderImpl {
54
+ options;
55
+ loc;
56
+ constructor(options, loc) {
57
+ super();
58
+ this.options = options;
59
+ this.loc = loc;
60
+ }
61
+ goalIR() {
62
+ const goal = this.options.goal;
63
+ if (goal === void 0) return void 0;
64
+ if ("__condition" in goal) return {
65
+ condition: condIR(goal),
66
+ exitOnMatch: true
67
+ };
68
+ return {
69
+ condition: condIR(goal.condition),
70
+ ...goal.within !== void 0 ? { within: durationIR(goal.within) } : {},
71
+ exitOnMatch: goal.exitOnMatch ?? true
72
+ };
73
+ }
74
+ metaIR() {
75
+ const { name, description } = this.options;
76
+ if (name === void 0 && description === void 0 && this.loc === void 0) return;
77
+ return {
78
+ ...name !== void 0 ? { name } : {},
79
+ ...description !== void 0 ? { description } : {},
80
+ ...this.loc !== void 0 ? { loc: this.loc } : {}
81
+ };
82
+ }
83
+ toIR() {
84
+ const flowNodes = structuredClone(this.nodes);
85
+ assignIds(flowNodes, "");
86
+ assertUniqueIds(flowNodes);
87
+ const goal = this.goalIR();
88
+ const meta = this.metaIR();
89
+ const body = {
90
+ irVersion: 2,
91
+ id: this.options.id,
92
+ ...meta !== void 0 ? { meta } : {},
93
+ trigger: this.options.trigger.ir,
94
+ ...goal !== void 0 ? { goal } : {},
95
+ ...this.options.exitWhen !== void 0 ? { exitWhen: condIR(this.options.exitWhen) } : {},
96
+ flow: flowNodes
97
+ };
98
+ return WorkflowIR.parse({
99
+ ...body,
100
+ contentHash: semanticHash(body)
101
+ });
102
+ }
103
+ };
104
+ /**
105
+ * Workflow definition: an id, configuration (trigger / goal / exitWhen),
106
+ * optional labels, and chained steps.
107
+ *
108
+ * export const onboarding = workflow({
109
+ * id: 'onboarding',
110
+ * name: 'Onboarding',
111
+ * trigger: trigger.event(e.sign_up),
112
+ * }).email(t.email.welcome);
113
+ */
114
+ function workflow(definition) {
115
+ return new WorkflowBuilderImpl(definition, captureLoc(workflow));
116
+ }
117
+ //#endregion
118
+ export { workflow };
119
+
120
+ //# sourceMappingURL=workflow.mjs.map