thevoidforge 21.0.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 (328) hide show
  1. package/dist/scripts/vault-read.d.ts +11 -0
  2. package/dist/scripts/vault-read.js +89 -0
  3. package/dist/scripts/voidforge.d.ts +20 -0
  4. package/dist/scripts/voidforge.js +404 -0
  5. package/dist/tsconfig.tsbuildinfo +1 -0
  6. package/dist/wizard/api/auth.d.ts +5 -0
  7. package/dist/wizard/api/auth.js +133 -0
  8. package/dist/wizard/api/blueprint.d.ts +45 -0
  9. package/dist/wizard/api/blueprint.js +184 -0
  10. package/dist/wizard/api/cloud-providers.d.ts +16 -0
  11. package/dist/wizard/api/cloud-providers.js +363 -0
  12. package/dist/wizard/api/credentials.d.ts +1 -0
  13. package/dist/wizard/api/credentials.js +258 -0
  14. package/dist/wizard/api/danger-room.d.ts +18 -0
  15. package/dist/wizard/api/danger-room.js +401 -0
  16. package/dist/wizard/api/deploy.d.ts +4 -0
  17. package/dist/wizard/api/deploy.js +164 -0
  18. package/dist/wizard/api/prd.d.ts +1 -0
  19. package/dist/wizard/api/prd.js +363 -0
  20. package/dist/wizard/api/project.d.ts +1 -0
  21. package/dist/wizard/api/project.js +239 -0
  22. package/dist/wizard/api/projects.d.ts +6 -0
  23. package/dist/wizard/api/projects.js +648 -0
  24. package/dist/wizard/api/provision.d.ts +4 -0
  25. package/dist/wizard/api/provision.js +535 -0
  26. package/dist/wizard/api/terminal.d.ts +25 -0
  27. package/dist/wizard/api/terminal.js +241 -0
  28. package/dist/wizard/api/users.d.ts +6 -0
  29. package/dist/wizard/api/users.js +244 -0
  30. package/dist/wizard/api/war-room.d.ts +14 -0
  31. package/dist/wizard/api/war-room.js +45 -0
  32. package/dist/wizard/lib/ad-platform-core.d.ts +6 -0
  33. package/dist/wizard/lib/ad-platform-core.js +1 -0
  34. package/dist/wizard/lib/adapters/index.d.ts +52 -0
  35. package/dist/wizard/lib/adapters/index.js +38 -0
  36. package/dist/wizard/lib/adapters/sandbox-bank.d.ts +17 -0
  37. package/dist/wizard/lib/adapters/sandbox-bank.js +77 -0
  38. package/dist/wizard/lib/adapters/sandbox.d.ts +39 -0
  39. package/dist/wizard/lib/adapters/sandbox.js +174 -0
  40. package/dist/wizard/lib/adapters/stripe.d.ts +19 -0
  41. package/dist/wizard/lib/adapters/stripe.js +143 -0
  42. package/dist/wizard/lib/adapters/types.d.ts +9 -0
  43. package/dist/wizard/lib/adapters/types.js +10 -0
  44. package/dist/wizard/lib/agent-memory.d.ts +36 -0
  45. package/dist/wizard/lib/agent-memory.js +114 -0
  46. package/dist/wizard/lib/anomaly-detection.d.ts +59 -0
  47. package/dist/wizard/lib/anomaly-detection.js +122 -0
  48. package/dist/wizard/lib/anthropic.d.ts +21 -0
  49. package/dist/wizard/lib/anthropic.js +105 -0
  50. package/dist/wizard/lib/asset-scanner.d.ts +23 -0
  51. package/dist/wizard/lib/asset-scanner.js +107 -0
  52. package/dist/wizard/lib/audit-log.d.ts +23 -0
  53. package/dist/wizard/lib/audit-log.js +70 -0
  54. package/dist/wizard/lib/autonomy-controller.d.ts +76 -0
  55. package/dist/wizard/lib/autonomy-controller.js +183 -0
  56. package/dist/wizard/lib/body-parser.d.ts +2 -0
  57. package/dist/wizard/lib/body-parser.js +36 -0
  58. package/dist/wizard/lib/build-analytics.d.ts +39 -0
  59. package/dist/wizard/lib/build-analytics.js +91 -0
  60. package/dist/wizard/lib/build-step.d.ts +21 -0
  61. package/dist/wizard/lib/build-step.js +104 -0
  62. package/dist/wizard/lib/campaign-proposer.d.ts +39 -0
  63. package/dist/wizard/lib/campaign-proposer.js +180 -0
  64. package/dist/wizard/lib/campaign-state-machine.d.ts +63 -0
  65. package/dist/wizard/lib/campaign-state-machine.js +114 -0
  66. package/dist/wizard/lib/ci-generator.d.ts +14 -0
  67. package/dist/wizard/lib/ci-generator.js +187 -0
  68. package/dist/wizard/lib/claude-merge.d.ts +38 -0
  69. package/dist/wizard/lib/claude-merge.js +115 -0
  70. package/dist/wizard/lib/codegen/erd-gen.d.ts +16 -0
  71. package/dist/wizard/lib/codegen/erd-gen.js +98 -0
  72. package/dist/wizard/lib/codegen/integrations.d.ts +18 -0
  73. package/dist/wizard/lib/codegen/integrations.js +189 -0
  74. package/dist/wizard/lib/codegen/openapi-gen.d.ts +15 -0
  75. package/dist/wizard/lib/codegen/openapi-gen.js +79 -0
  76. package/dist/wizard/lib/codegen/prisma-types.d.ts +15 -0
  77. package/dist/wizard/lib/codegen/prisma-types.js +44 -0
  78. package/dist/wizard/lib/codegen/seed-gen.d.ts +16 -0
  79. package/dist/wizard/lib/codegen/seed-gen.js +128 -0
  80. package/dist/wizard/lib/compliance.d.ts +51 -0
  81. package/dist/wizard/lib/compliance.js +112 -0
  82. package/dist/wizard/lib/correlation-engine.d.ts +59 -0
  83. package/dist/wizard/lib/correlation-engine.js +151 -0
  84. package/dist/wizard/lib/cost-estimator.d.ts +22 -0
  85. package/dist/wizard/lib/cost-estimator.js +72 -0
  86. package/dist/wizard/lib/cost-tracker.d.ts +27 -0
  87. package/dist/wizard/lib/cost-tracker.js +37 -0
  88. package/dist/wizard/lib/daemon-aggregator.d.ts +71 -0
  89. package/dist/wizard/lib/daemon-aggregator.js +204 -0
  90. package/dist/wizard/lib/daemon-core.d.ts +6 -0
  91. package/dist/wizard/lib/daemon-core.js +5 -0
  92. package/dist/wizard/lib/dashboard-data.d.ts +132 -0
  93. package/dist/wizard/lib/dashboard-data.js +336 -0
  94. package/dist/wizard/lib/dashboard-ws.d.ts +25 -0
  95. package/dist/wizard/lib/dashboard-ws.js +91 -0
  96. package/dist/wizard/lib/deep-current.d.ts +77 -0
  97. package/dist/wizard/lib/deep-current.js +234 -0
  98. package/dist/wizard/lib/deploy-coordinator.d.ts +40 -0
  99. package/dist/wizard/lib/deploy-coordinator.js +86 -0
  100. package/dist/wizard/lib/deploy-log.d.ts +28 -0
  101. package/dist/wizard/lib/deploy-log.js +52 -0
  102. package/dist/wizard/lib/desktop-notify.d.ts +27 -0
  103. package/dist/wizard/lib/desktop-notify.js +98 -0
  104. package/dist/wizard/lib/dns/cloudflare-dns.d.ts +35 -0
  105. package/dist/wizard/lib/dns/cloudflare-dns.js +216 -0
  106. package/dist/wizard/lib/dns/cloudflare-registrar.d.ts +31 -0
  107. package/dist/wizard/lib/dns/cloudflare-registrar.js +148 -0
  108. package/dist/wizard/lib/dns/types.d.ts +22 -0
  109. package/dist/wizard/lib/dns/types.js +4 -0
  110. package/dist/wizard/lib/document-discovery.d.ts +33 -0
  111. package/dist/wizard/lib/document-discovery.js +145 -0
  112. package/dist/wizard/lib/env-validator.d.ts +14 -0
  113. package/dist/wizard/lib/env-validator.js +205 -0
  114. package/dist/wizard/lib/env-writer.d.ts +13 -0
  115. package/dist/wizard/lib/env-writer.js +26 -0
  116. package/dist/wizard/lib/exec.d.ts +30 -0
  117. package/dist/wizard/lib/exec.js +52 -0
  118. package/dist/wizard/lib/experiment.d.ts +70 -0
  119. package/dist/wizard/lib/experiment.js +169 -0
  120. package/dist/wizard/lib/extensions.d.ts +20 -0
  121. package/dist/wizard/lib/extensions.js +183 -0
  122. package/dist/wizard/lib/financial/adapter-factory.d.ts +47 -0
  123. package/dist/wizard/lib/financial/adapter-factory.js +225 -0
  124. package/dist/wizard/lib/financial/billing/base.d.ts +6 -0
  125. package/dist/wizard/lib/financial/billing/base.js +1 -0
  126. package/dist/wizard/lib/financial/billing/google-billing.d.ts +56 -0
  127. package/dist/wizard/lib/financial/billing/google-billing.js +298 -0
  128. package/dist/wizard/lib/financial/billing/meta-billing.d.ts +54 -0
  129. package/dist/wizard/lib/financial/billing/meta-billing.js +243 -0
  130. package/dist/wizard/lib/financial/billing/tiktok-billing.d.ts +54 -0
  131. package/dist/wizard/lib/financial/billing/tiktok-billing.js +260 -0
  132. package/dist/wizard/lib/financial/campaign/base.d.ts +13 -0
  133. package/dist/wizard/lib/financial/campaign/base.js +1 -0
  134. package/dist/wizard/lib/financial/campaign/google-campaign.d.ts +42 -0
  135. package/dist/wizard/lib/financial/campaign/google-campaign.js +388 -0
  136. package/dist/wizard/lib/financial/campaign/meta-campaign.d.ts +41 -0
  137. package/dist/wizard/lib/financial/campaign/meta-campaign.js +311 -0
  138. package/dist/wizard/lib/financial/campaign/sandbox-campaign.d.ts +45 -0
  139. package/dist/wizard/lib/financial/campaign/sandbox-campaign.js +261 -0
  140. package/dist/wizard/lib/financial/campaign/tiktok-campaign.d.ts +40 -0
  141. package/dist/wizard/lib/financial/campaign/tiktok-campaign.js +350 -0
  142. package/dist/wizard/lib/financial/funding-auto.d.ts +44 -0
  143. package/dist/wizard/lib/financial/funding-auto.js +52 -0
  144. package/dist/wizard/lib/financial/funding-policy.d.ts +60 -0
  145. package/dist/wizard/lib/financial/funding-policy.js +179 -0
  146. package/dist/wizard/lib/financial/platform-planner.d.ts +47 -0
  147. package/dist/wizard/lib/financial/platform-planner.js +134 -0
  148. package/dist/wizard/lib/financial/reconciliation-engine.d.ts +78 -0
  149. package/dist/wizard/lib/financial/reconciliation-engine.js +193 -0
  150. package/dist/wizard/lib/financial/registry.d.ts +22 -0
  151. package/dist/wizard/lib/financial/registry.js +26 -0
  152. package/dist/wizard/lib/financial/reporting.d.ts +96 -0
  153. package/dist/wizard/lib/financial/reporting.js +198 -0
  154. package/dist/wizard/lib/financial/stablecoin/base.d.ts +6 -0
  155. package/dist/wizard/lib/financial/stablecoin/base.js +1 -0
  156. package/dist/wizard/lib/financial/stablecoin/circle.d.ts +54 -0
  157. package/dist/wizard/lib/financial/stablecoin/circle.js +367 -0
  158. package/dist/wizard/lib/financial/stablecoin/mercury.d.ts +24 -0
  159. package/dist/wizard/lib/financial/stablecoin/mercury.js +171 -0
  160. package/dist/wizard/lib/financial/stablecoin/sandbox-stablecoin.d.ts +47 -0
  161. package/dist/wizard/lib/financial/stablecoin/sandbox-stablecoin.js +202 -0
  162. package/dist/wizard/lib/financial/treasury-planner.d.ts +52 -0
  163. package/dist/wizard/lib/financial/treasury-planner.js +128 -0
  164. package/dist/wizard/lib/financial-core.d.ts +6 -0
  165. package/dist/wizard/lib/financial-core.js +5 -0
  166. package/dist/wizard/lib/financial-vault.d.ts +34 -0
  167. package/dist/wizard/lib/financial-vault.js +199 -0
  168. package/dist/wizard/lib/frontmatter.d.ts +30 -0
  169. package/dist/wizard/lib/frontmatter.js +96 -0
  170. package/dist/wizard/lib/gap-analysis.d.ts +37 -0
  171. package/dist/wizard/lib/gap-analysis.js +218 -0
  172. package/dist/wizard/lib/github.d.ts +22 -0
  173. package/dist/wizard/lib/github.js +261 -0
  174. package/dist/wizard/lib/headless-deploy.d.ts +14 -0
  175. package/dist/wizard/lib/headless-deploy.js +452 -0
  176. package/dist/wizard/lib/health-monitor.d.ts +15 -0
  177. package/dist/wizard/lib/health-monitor.js +91 -0
  178. package/dist/wizard/lib/health-poller.d.ts +9 -0
  179. package/dist/wizard/lib/health-poller.js +123 -0
  180. package/dist/wizard/lib/heartbeat.d.ts +15 -0
  181. package/dist/wizard/lib/heartbeat.js +827 -0
  182. package/dist/wizard/lib/http-helpers.d.ts +9 -0
  183. package/dist/wizard/lib/http-helpers.js +24 -0
  184. package/dist/wizard/lib/image-gen.d.ts +56 -0
  185. package/dist/wizard/lib/image-gen.js +159 -0
  186. package/dist/wizard/lib/instance-sizing.d.ts +26 -0
  187. package/dist/wizard/lib/instance-sizing.js +51 -0
  188. package/dist/wizard/lib/kongo/analytics.d.ts +29 -0
  189. package/dist/wizard/lib/kongo/analytics.js +179 -0
  190. package/dist/wizard/lib/kongo/campaigns.d.ts +52 -0
  191. package/dist/wizard/lib/kongo/campaigns.js +91 -0
  192. package/dist/wizard/lib/kongo/client.d.ts +58 -0
  193. package/dist/wizard/lib/kongo/client.js +221 -0
  194. package/dist/wizard/lib/kongo/jobs.d.ts +57 -0
  195. package/dist/wizard/lib/kongo/jobs.js +122 -0
  196. package/dist/wizard/lib/kongo/pages.d.ts +60 -0
  197. package/dist/wizard/lib/kongo/pages.js +150 -0
  198. package/dist/wizard/lib/kongo/provisioner.d.ts +64 -0
  199. package/dist/wizard/lib/kongo/provisioner.js +116 -0
  200. package/dist/wizard/lib/kongo/seed.d.ts +49 -0
  201. package/dist/wizard/lib/kongo/seed.js +237 -0
  202. package/dist/wizard/lib/kongo/types.d.ts +323 -0
  203. package/dist/wizard/lib/kongo/types.js +11 -0
  204. package/dist/wizard/lib/kongo/variants.d.ts +57 -0
  205. package/dist/wizard/lib/kongo/variants.js +88 -0
  206. package/dist/wizard/lib/kongo/webhooks.d.ts +41 -0
  207. package/dist/wizard/lib/kongo/webhooks.js +112 -0
  208. package/dist/wizard/lib/marker.d.ts +28 -0
  209. package/dist/wizard/lib/marker.js +79 -0
  210. package/dist/wizard/lib/migrator.d.ts +35 -0
  211. package/dist/wizard/lib/migrator.js +190 -0
  212. package/dist/wizard/lib/natural-language-deploy.d.ts +30 -0
  213. package/dist/wizard/lib/natural-language-deploy.js +186 -0
  214. package/dist/wizard/lib/network.d.ts +22 -0
  215. package/dist/wizard/lib/network.js +72 -0
  216. package/dist/wizard/lib/oauth-core.d.ts +6 -0
  217. package/dist/wizard/lib/oauth-core.js +5 -0
  218. package/dist/wizard/lib/open-browser.d.ts +1 -0
  219. package/dist/wizard/lib/open-browser.js +26 -0
  220. package/dist/wizard/lib/patterns/ad-billing-adapter.d.ts +209 -0
  221. package/dist/wizard/lib/patterns/ad-billing-adapter.js +269 -0
  222. package/dist/wizard/lib/patterns/ad-platform-adapter.d.ts +200 -0
  223. package/dist/wizard/lib/patterns/ad-platform-adapter.js +212 -0
  224. package/dist/wizard/lib/patterns/daemon-process.d.ts +88 -0
  225. package/dist/wizard/lib/patterns/daemon-process.js +271 -0
  226. package/dist/wizard/lib/patterns/financial-transaction.d.ts +161 -0
  227. package/dist/wizard/lib/patterns/financial-transaction.js +132 -0
  228. package/dist/wizard/lib/patterns/funding-plan.d.ts +136 -0
  229. package/dist/wizard/lib/patterns/funding-plan.js +200 -0
  230. package/dist/wizard/lib/patterns/oauth-token-lifecycle.d.ts +94 -0
  231. package/dist/wizard/lib/patterns/oauth-token-lifecycle.js +139 -0
  232. package/dist/wizard/lib/patterns/outbound-rate-limiter.d.ts +67 -0
  233. package/dist/wizard/lib/patterns/outbound-rate-limiter.js +216 -0
  234. package/dist/wizard/lib/patterns/revenue-source-adapter.d.ts +96 -0
  235. package/dist/wizard/lib/patterns/revenue-source-adapter.js +182 -0
  236. package/dist/wizard/lib/patterns/stablecoin-adapter.d.ts +218 -0
  237. package/dist/wizard/lib/patterns/stablecoin-adapter.js +264 -0
  238. package/dist/wizard/lib/prd-validator.d.ts +39 -0
  239. package/dist/wizard/lib/prd-validator.js +137 -0
  240. package/dist/wizard/lib/project-init.d.ts +24 -0
  241. package/dist/wizard/lib/project-init.js +193 -0
  242. package/dist/wizard/lib/project-registry.d.ts +86 -0
  243. package/dist/wizard/lib/project-registry.js +359 -0
  244. package/dist/wizard/lib/provision-manifest.d.ts +44 -0
  245. package/dist/wizard/lib/provision-manifest.js +164 -0
  246. package/dist/wizard/lib/provisioner-registry.d.ts +15 -0
  247. package/dist/wizard/lib/provisioner-registry.js +34 -0
  248. package/dist/wizard/lib/provisioners/aws-vps.d.ts +6 -0
  249. package/dist/wizard/lib/provisioners/aws-vps.js +643 -0
  250. package/dist/wizard/lib/provisioners/cloudflare.d.ts +6 -0
  251. package/dist/wizard/lib/provisioners/cloudflare.js +300 -0
  252. package/dist/wizard/lib/provisioners/docker.d.ts +6 -0
  253. package/dist/wizard/lib/provisioners/docker.js +75 -0
  254. package/dist/wizard/lib/provisioners/http-client.d.ts +20 -0
  255. package/dist/wizard/lib/provisioners/http-client.js +79 -0
  256. package/dist/wizard/lib/provisioners/railway.d.ts +6 -0
  257. package/dist/wizard/lib/provisioners/railway.js +413 -0
  258. package/dist/wizard/lib/provisioners/scripts/caddyfile.d.ts +10 -0
  259. package/dist/wizard/lib/provisioners/scripts/caddyfile.js +54 -0
  260. package/dist/wizard/lib/provisioners/scripts/deploy-vps.d.ts +10 -0
  261. package/dist/wizard/lib/provisioners/scripts/deploy-vps.js +112 -0
  262. package/dist/wizard/lib/provisioners/scripts/docker-compose.d.ts +11 -0
  263. package/dist/wizard/lib/provisioners/scripts/docker-compose.js +91 -0
  264. package/dist/wizard/lib/provisioners/scripts/dockerfile.d.ts +5 -0
  265. package/dist/wizard/lib/provisioners/scripts/dockerfile.js +185 -0
  266. package/dist/wizard/lib/provisioners/scripts/ecosystem-config.d.ts +10 -0
  267. package/dist/wizard/lib/provisioners/scripts/ecosystem-config.js +36 -0
  268. package/dist/wizard/lib/provisioners/scripts/provision-vps.d.ts +14 -0
  269. package/dist/wizard/lib/provisioners/scripts/provision-vps.js +202 -0
  270. package/dist/wizard/lib/provisioners/scripts/rollback-vps.d.ts +10 -0
  271. package/dist/wizard/lib/provisioners/scripts/rollback-vps.js +67 -0
  272. package/dist/wizard/lib/provisioners/self-deploy.d.ts +41 -0
  273. package/dist/wizard/lib/provisioners/self-deploy.js +185 -0
  274. package/dist/wizard/lib/provisioners/static-s3.d.ts +6 -0
  275. package/dist/wizard/lib/provisioners/static-s3.js +235 -0
  276. package/dist/wizard/lib/provisioners/types.d.ts +40 -0
  277. package/dist/wizard/lib/provisioners/types.js +4 -0
  278. package/dist/wizard/lib/provisioners/vercel.d.ts +6 -0
  279. package/dist/wizard/lib/provisioners/vercel.js +287 -0
  280. package/dist/wizard/lib/pty-manager.d.ts +42 -0
  281. package/dist/wizard/lib/pty-manager.js +231 -0
  282. package/dist/wizard/lib/rate-limiter-core.d.ts +5 -0
  283. package/dist/wizard/lib/rate-limiter-core.js +5 -0
  284. package/dist/wizard/lib/reconciliation.d.ts +43 -0
  285. package/dist/wizard/lib/reconciliation.js +173 -0
  286. package/dist/wizard/lib/revenue-types.d.ts +5 -0
  287. package/dist/wizard/lib/revenue-types.js +1 -0
  288. package/dist/wizard/lib/route-optimizer.d.ts +28 -0
  289. package/dist/wizard/lib/route-optimizer.js +93 -0
  290. package/dist/wizard/lib/s3-deploy.d.ts +19 -0
  291. package/dist/wizard/lib/s3-deploy.js +156 -0
  292. package/dist/wizard/lib/safety-tiers.d.ts +76 -0
  293. package/dist/wizard/lib/safety-tiers.js +134 -0
  294. package/dist/wizard/lib/sentry-generator.d.ts +15 -0
  295. package/dist/wizard/lib/sentry-generator.js +116 -0
  296. package/dist/wizard/lib/server-config.d.ts +13 -0
  297. package/dist/wizard/lib/server-config.js +23 -0
  298. package/dist/wizard/lib/service-install.d.ts +18 -0
  299. package/dist/wizard/lib/service-install.js +182 -0
  300. package/dist/wizard/lib/site-scanner.d.ts +80 -0
  301. package/dist/wizard/lib/site-scanner.js +262 -0
  302. package/dist/wizard/lib/ssh-deploy.d.ts +25 -0
  303. package/dist/wizard/lib/ssh-deploy.js +225 -0
  304. package/dist/wizard/lib/templates.d.ts +24 -0
  305. package/dist/wizard/lib/templates.js +219 -0
  306. package/dist/wizard/lib/totp.d.ts +35 -0
  307. package/dist/wizard/lib/totp.js +276 -0
  308. package/dist/wizard/lib/tower-auth.d.ts +43 -0
  309. package/dist/wizard/lib/tower-auth.js +352 -0
  310. package/dist/wizard/lib/tower-rate-limit.d.ts +14 -0
  311. package/dist/wizard/lib/tower-rate-limit.js +61 -0
  312. package/dist/wizard/lib/tower-session.d.ts +28 -0
  313. package/dist/wizard/lib/tower-session.js +119 -0
  314. package/dist/wizard/lib/treasury-backup.d.ts +23 -0
  315. package/dist/wizard/lib/treasury-backup.js +126 -0
  316. package/dist/wizard/lib/treasury-heartbeat.d.ts +82 -0
  317. package/dist/wizard/lib/treasury-heartbeat.js +1104 -0
  318. package/dist/wizard/lib/updater.d.ts +29 -0
  319. package/dist/wizard/lib/updater.js +190 -0
  320. package/dist/wizard/lib/user-manager.d.ts +39 -0
  321. package/dist/wizard/lib/user-manager.js +182 -0
  322. package/dist/wizard/lib/vault.d.ts +26 -0
  323. package/dist/wizard/lib/vault.js +161 -0
  324. package/dist/wizard/router.d.ts +5 -0
  325. package/dist/wizard/router.js +15 -0
  326. package/dist/wizard/server.d.ts +18 -0
  327. package/dist/wizard/server.js +436 -0
  328. package/package.json +59 -0
@@ -0,0 +1,182 @@
1
+ /**
2
+ * Pattern: Revenue Source Adapter (Read-Only)
3
+ *
4
+ * Key principles:
5
+ * - Read-only interface — VoidForge never processes payments directly
6
+ * - Separate from AdPlatformAdapter — revenue in, ad spend out
7
+ * - Polling with overlapping windows for gap-free coverage (ADR-5)
8
+ * - Dedup by externalId to prevent double-counting
9
+ * - Webhook signature verification mandatory when webhooks are implemented
10
+ * - USD-only enforcement (ADR-6) at connection time
11
+ *
12
+ * Agents: Dockson (treasury), Vin (analytics)
13
+ *
14
+ * PRD Reference: §9.4, §9.9, §9.17 (polling improvements), ADR-5/ADR-6
15
+ */
16
+ // ── Reference Implementation: Stripe ──────────────────
17
+ class StripeAdapter {
18
+ apiKey = '';
19
+ baseUrl = 'https://api.stripe.com/v1';
20
+ async connect(credentials) {
21
+ this.apiKey = credentials.apiKey || '';
22
+ try {
23
+ const account = await this.apiCall('GET', '/account');
24
+ return {
25
+ connected: true,
26
+ accountId: account.id,
27
+ accountName: account.business_profile?.name || account.email,
28
+ currency: account.default_currency?.toUpperCase(),
29
+ };
30
+ }
31
+ catch (err) {
32
+ return { connected: false, error: err.message };
33
+ }
34
+ }
35
+ async detectCurrency(credentials) {
36
+ const result = await this.connect(credentials);
37
+ return result.currency || 'USD';
38
+ }
39
+ async getTransactions(range, cursor) {
40
+ // Use Stripe Events API for sequential, immutable event log (§9.18)
41
+ const params = {
42
+ type: 'charge.succeeded',
43
+ 'created[gte]': String(Math.floor(new Date(range.start).getTime() / 1000)),
44
+ 'created[lte]': String(Math.floor(new Date(range.end).getTime() / 1000)),
45
+ limit: '100',
46
+ };
47
+ if (cursor)
48
+ params.starting_after = cursor;
49
+ const data = await this.apiCall('GET', '/events', params);
50
+ const transactions = data.data.map((event) => {
51
+ const charge = event.data?.object;
52
+ return {
53
+ externalId: event.id,
54
+ type: 'charge',
55
+ amount: (charge?.amount || 0), // Stripe amounts are already in cents
56
+ currency: 'USD',
57
+ description: charge?.description || '',
58
+ customerId: charge?.customer ? hashCustomerId(charge.customer) : undefined,
59
+ subscriptionId: charge?.subscription,
60
+ metadata: charge?.metadata || {},
61
+ createdAt: new Date(event.created * 1000).toISOString(),
62
+ };
63
+ });
64
+ return {
65
+ transactions,
66
+ hasMore: data.has_more,
67
+ cursor: data.data.length > 0 ? data.data[data.data.length - 1].id : undefined,
68
+ };
69
+ }
70
+ async getBalance() {
71
+ const data = await this.apiCall('GET', '/balance');
72
+ const usd = data.available.find((b) => b.currency === 'usd');
73
+ const pending = data.pending.find((b) => b.currency === 'usd');
74
+ return {
75
+ available: (usd?.amount || 0),
76
+ pending: (pending?.amount || 0),
77
+ currency: 'USD',
78
+ };
79
+ }
80
+ verifyWebhookSignature(payload, signature, secret) {
81
+ // Stripe uses HMAC-SHA256 for webhook signatures
82
+ const { createHmac } = require('node:crypto');
83
+ const parts = signature.split(',').reduce((acc, part) => {
84
+ const [key, value] = part.split('=');
85
+ acc[key] = value;
86
+ return acc;
87
+ }, {});
88
+ const timestamp = parts['t'];
89
+ const expected = parts['v1'];
90
+ if (!timestamp || !expected)
91
+ return false;
92
+ const signed = createHmac('sha256', secret)
93
+ .update(`${timestamp}.${payload.toString()}`)
94
+ .digest('hex');
95
+ // VG-006: Use timing-safe comparison to prevent timing attacks on signature
96
+ const { timingSafeEqual } = require('node:crypto');
97
+ if (signed.length !== expected.length)
98
+ return false;
99
+ return timingSafeEqual(Buffer.from(signed), Buffer.from(expected));
100
+ }
101
+ async apiCall(method, path, params) {
102
+ // Implementation: raw HTTPS (no Stripe SDK — zero dependency principle)
103
+ // Headers: Authorization: Bearer {apiKey}, Content-Type: application/x-www-form-urlencoded
104
+ // Sanitize response strings per §9.19.16 before returning
105
+ throw new Error('HTTP implementation — use node:https, no SDK dependencies');
106
+ }
107
+ }
108
+ // ── Paddle Adapter ────────────────────────────────────
109
+ class PaddleAdapter {
110
+ apiKey = '';
111
+ baseUrl = 'https://api.paddle.com';
112
+ async connect(credentials) {
113
+ this.apiKey = credentials.apiKey || '';
114
+ try {
115
+ const data = await this.apiCall('GET', '/businesses');
116
+ const biz = data.data?.[0];
117
+ return {
118
+ connected: true,
119
+ accountId: biz?.id,
120
+ accountName: biz?.name,
121
+ currency: biz?.currency_code,
122
+ };
123
+ }
124
+ catch (err) {
125
+ return { connected: false, error: err.message };
126
+ }
127
+ }
128
+ async detectCurrency(credentials) {
129
+ const result = await this.connect(credentials);
130
+ return result.currency || 'USD';
131
+ }
132
+ async getTransactions(range, cursor) {
133
+ const params = {
134
+ 'created_at[gte]': range.start,
135
+ 'created_at[lte]': range.end,
136
+ per_page: '100',
137
+ };
138
+ if (cursor)
139
+ params.after = cursor;
140
+ const data = await this.apiCall('GET', '/transactions', params);
141
+ const transactions = data.data.map((txn) => {
142
+ const details = txn.details;
143
+ const totals = details?.totals;
144
+ const items = txn.items;
145
+ const firstItemPrice = items?.[0]?.price;
146
+ return {
147
+ externalId: txn.id,
148
+ type: mapPaddleStatus(txn.status),
149
+ amount: Math.round(parseFloat(totals?.total || '0') * 100),
150
+ currency: 'USD',
151
+ description: firstItemPrice?.description || '',
152
+ customerId: txn.customer_id ? hashCustomerId(txn.customer_id) : undefined,
153
+ subscriptionId: txn.subscription_id,
154
+ metadata: txn.custom_data || {},
155
+ createdAt: txn.created_at,
156
+ };
157
+ });
158
+ return {
159
+ transactions,
160
+ hasMore: !!data.meta?.pagination?.next,
161
+ cursor: data.meta?.pagination?.next,
162
+ };
163
+ }
164
+ async apiCall(method, path, params) {
165
+ throw new Error('HTTP implementation — use node:https, no SDK dependencies');
166
+ }
167
+ }
168
+ // ── Helpers ───────────────────────────────────────────
169
+ function hashCustomerId(customerId) {
170
+ const { createHash } = require('node:crypto');
171
+ return createHash('sha256').update(customerId).digest('hex').substring(0, 16);
172
+ }
173
+ function mapPaddleStatus(status) {
174
+ if (status === 'completed' || status === 'paid')
175
+ return 'charge';
176
+ if (status === 'refunded' || status === 'partially_refunded')
177
+ return 'refund';
178
+ if (status === 'disputed')
179
+ return 'dispute';
180
+ return 'charge';
181
+ }
182
+ export { StripeAdapter, PaddleAdapter, hashCustomerId };
@@ -0,0 +1,218 @@
1
+ /**
2
+ * Pattern: Stablecoin Treasury Adapter (Split Interface)
3
+ *
4
+ * Key principles:
5
+ * - Split interface: StablecoinSetup (interactive CLI/Danger Room) + StablecoinAdapter (daemon runtime)
6
+ * - Single-writer constraint: only Heartbeat daemon calls the runtime adapter
7
+ * - Funding lifecycle: USDC held at provider → off-ramp instruction → fiat settlement at linked bank
8
+ * - All amounts in branded integer cents (Cents type from financial-transaction.ts)
9
+ * - Hash-chained TransferRecord for tamper-evident audit trail
10
+ * - Idempotency keys on all write operations (off-ramp, cancel)
11
+ * - Provider abstraction: Circle first-class, Bridge secondary, manual fallback
12
+ * - The adapter does NOT move money between bank and ad platform — that is ad-billing-adapter.ts
13
+ *
14
+ * Agents: Dockson (treasury), Heartbeat daemon
15
+ *
16
+ * PRD Reference: §11.1A, §12.1, §12.4, §12.5
17
+ *
18
+ * Circle API reference (v1):
19
+ * Auth: Bearer token via API key — header `Authorization: Bearer {apiKey}`
20
+ * Base URL: https://api.circle.com/v1
21
+ * GET /wallets → list wallets
22
+ * GET /wallets/{id}/balances → wallet balances (amount, currency, chain)
23
+ * GET /configuration → supported chains and assets
24
+ * GET /banks/wires → linked bank accounts
25
+ * POST /payouts → initiate wire payout (off-ramp)
26
+ * GET /payouts/{id} → transfer status
27
+ * GET /payouts?destination={bankId} → list completed payouts for reconciliation
28
+ *
29
+ * Response shape (balance):
30
+ * { data: { available: [{ amount: "1000.00", currency: "USD" }] } }
31
+ * Response shape (payout):
32
+ * { data: { id, status, amount: { amount, currency }, destination, createDate, updateDate } }
33
+ * Payout statuses: pending → processing → complete | failed
34
+ *
35
+ * Bridge API reference:
36
+ * Auth: API key header `Api-Key: {apiKey}`
37
+ * Base URL: https://api.bridge.xyz/v0
38
+ * POST /customers/{id}/liquidation_addresses → create liquidation address
39
+ * GET /customers/{id}/liquidation_addresses → list addresses
40
+ * GET /liquidation_addresses/{id} → transfer status
41
+ * Transfers settle via ACH to linked bank — status polling required
42
+ */
43
+ type Cents = number & {
44
+ readonly __brand: 'Cents';
45
+ };
46
+ declare function toCents(dollars: number): Cents;
47
+ declare function toDollars(cents: Cents): number;
48
+ type StablecoinProvider = 'circle' | 'bridge';
49
+ interface SupportedAsset {
50
+ asset: string;
51
+ network: string;
52
+ contractAddress: string;
53
+ minRedemption: Cents;
54
+ }
55
+ interface ProviderCredentials {
56
+ provider: StablecoinProvider;
57
+ apiKey: string;
58
+ environment: 'sandbox' | 'production';
59
+ }
60
+ interface StablecoinBalance {
61
+ provider: StablecoinProvider;
62
+ asset: string;
63
+ network: string;
64
+ balanceCents: Cents;
65
+ lastUpdated: string;
66
+ }
67
+ interface FiatBalance {
68
+ provider: 'mercury' | 'external';
69
+ accountId: string;
70
+ availableCents: Cents;
71
+ pendingCents: Cents;
72
+ currency: 'USD';
73
+ lastUpdated: string;
74
+ }
75
+ interface CombinedBalances {
76
+ stablecoin: StablecoinBalance[];
77
+ fiat: FiatBalance[];
78
+ totalStablecoinCents: Cents;
79
+ totalFiatAvailableCents: Cents;
80
+ }
81
+ interface OfframpQuote {
82
+ provider: StablecoinProvider;
83
+ sourceAsset: string;
84
+ sourceNetwork: string;
85
+ requestedCents: Cents;
86
+ estimatedFeeCents: Cents;
87
+ estimatedNetCents: Cents;
88
+ estimatedSettlementMinutes: number;
89
+ expiresAt: string;
90
+ quoteId?: string;
91
+ }
92
+ type TransferStatus = 'pending' | 'processing' | 'completed' | 'failed' | 'cancelled';
93
+ interface TransferRecord {
94
+ id: string;
95
+ fundingPlanId: string;
96
+ providerTransferId: string;
97
+ bankTransactionId?: string;
98
+ provider: StablecoinProvider;
99
+ direction: 'crypto_to_fiat';
100
+ sourceAsset: string;
101
+ sourceNetwork: string;
102
+ amountCents: Cents;
103
+ feesCents: Cents;
104
+ netAmountCents: Cents;
105
+ destinationBankId: string;
106
+ status: TransferStatus;
107
+ statusReason?: string;
108
+ initiatedAt: string;
109
+ completedAt?: string;
110
+ idempotencyKey: string;
111
+ previousHash: string;
112
+ hash: string;
113
+ }
114
+ interface TransferStatusDetail {
115
+ transferId: string;
116
+ providerTransferId: string;
117
+ status: TransferStatus;
118
+ amountCents: Cents;
119
+ feesCents: Cents;
120
+ initiatedAt: string;
121
+ completedAt?: string;
122
+ estimatedCompletionAt?: string;
123
+ providerRawStatus: string;
124
+ }
125
+ interface DateRange {
126
+ start: string;
127
+ end: string;
128
+ }
129
+ interface StablecoinSetup {
130
+ /** Verify provider API key is valid and has required permissions */
131
+ authenticate(credentials: ProviderCredentials): Promise<{
132
+ valid: boolean;
133
+ accountId?: string;
134
+ permissions?: string[];
135
+ error?: string;
136
+ }>;
137
+ /** List stablecoins and networks the provider supports for off-ramp */
138
+ verifySupportedAssets(credentials: ProviderCredentials): Promise<SupportedAsset[]>;
139
+ /** Confirm the provider has a linked bank destination for wire/ACH payouts */
140
+ verifyLinkedBank(credentials: ProviderCredentials): Promise<{
141
+ linked: boolean;
142
+ bankId?: string;
143
+ bankName?: string;
144
+ accountLast4?: string;
145
+ error?: string;
146
+ }>;
147
+ /** Fetch current stablecoin balances for initial state snapshot */
148
+ getInitialBalances(credentials: ProviderCredentials): Promise<StablecoinBalance[]>;
149
+ }
150
+ interface StablecoinAdapter {
151
+ /** Current stablecoin + fiat balances across all connected accounts */
152
+ getBalances(): Promise<CombinedBalances>;
153
+ /** Estimate fees, settlement time, and net proceeds for an off-ramp */
154
+ quoteRedemption(amountCents: Cents): Promise<OfframpQuote>;
155
+ /**
156
+ * Create an off-ramp instruction with the provider.
157
+ * Requires an idempotencyKey on the FundingPlan to prevent duplicate transfers.
158
+ * Returns the created TransferRecord (with hash chain linking).
159
+ */
160
+ initiateOfframp(plan: FundingPlanRef, previousHash: string): Promise<TransferRecord>;
161
+ /** Poll provider for transfer status updates */
162
+ getTransferStatus(transferId: string): Promise<TransferStatusDetail>;
163
+ /** Cancel a pending transfer if the provider supports cancellation */
164
+ cancelTransfer(transferId: string): Promise<{
165
+ cancelled: boolean;
166
+ reason?: string;
167
+ }>;
168
+ /** List completed transfers in a date range for reconciliation */
169
+ listCompletedTransfers(dateRange: DateRange): Promise<TransferRecord[]>;
170
+ }
171
+ interface FundingPlanRef {
172
+ id: string;
173
+ sourceFundingId: string;
174
+ destinationBankId: string;
175
+ requiredCents: Cents;
176
+ idempotencyKey: string;
177
+ }
178
+ declare function computeTransferHash(record: Omit<TransferRecord, 'hash'>, previousHash: string): string;
179
+ declare class CircleAdapter implements StablecoinSetup, StablecoinAdapter {
180
+ private config;
181
+ private readonly baseUrl;
182
+ private apiKey;
183
+ private bankId;
184
+ constructor(config: {
185
+ apiKey: string;
186
+ bankId: string;
187
+ environment: 'sandbox' | 'production';
188
+ });
189
+ authenticate(credentials: ProviderCredentials): Promise<{
190
+ valid: boolean;
191
+ accountId?: string;
192
+ permissions?: string[];
193
+ error?: string;
194
+ }>;
195
+ verifySupportedAssets(_credentials: ProviderCredentials): Promise<SupportedAsset[]>;
196
+ verifyLinkedBank(_credentials: ProviderCredentials): Promise<{
197
+ linked: boolean;
198
+ bankId?: string;
199
+ bankName?: string;
200
+ accountLast4?: string;
201
+ error?: string;
202
+ }>;
203
+ getInitialBalances(_credentials: ProviderCredentials): Promise<StablecoinBalance[]>;
204
+ getBalances(): Promise<CombinedBalances>;
205
+ quoteRedemption(amountCents: Cents): Promise<OfframpQuote>;
206
+ initiateOfframp(plan: FundingPlanRef, previousHash: string): Promise<TransferRecord>;
207
+ getTransferStatus(transferId: string): Promise<TransferStatusDetail>;
208
+ cancelTransfer(transferId: string): Promise<{
209
+ cancelled: boolean;
210
+ reason?: string;
211
+ }>;
212
+ listCompletedTransfers(dateRange: DateRange): Promise<TransferRecord[]>;
213
+ private fetchStablecoinBalances;
214
+ private apiCall;
215
+ }
216
+ declare function mapCircleStatus(circleStatus: string): TransferStatus;
217
+ export type { StablecoinSetup, StablecoinAdapter, StablecoinProvider, SupportedAsset, ProviderCredentials, StablecoinBalance, FiatBalance, CombinedBalances, OfframpQuote, TransferStatus, TransferRecord, TransferStatusDetail, FundingPlanRef, DateRange, };
218
+ export { toCents, toDollars, computeTransferHash, mapCircleStatus, CircleAdapter };
@@ -0,0 +1,264 @@
1
+ /**
2
+ * Pattern: Stablecoin Treasury Adapter (Split Interface)
3
+ *
4
+ * Key principles:
5
+ * - Split interface: StablecoinSetup (interactive CLI/Danger Room) + StablecoinAdapter (daemon runtime)
6
+ * - Single-writer constraint: only Heartbeat daemon calls the runtime adapter
7
+ * - Funding lifecycle: USDC held at provider → off-ramp instruction → fiat settlement at linked bank
8
+ * - All amounts in branded integer cents (Cents type from financial-transaction.ts)
9
+ * - Hash-chained TransferRecord for tamper-evident audit trail
10
+ * - Idempotency keys on all write operations (off-ramp, cancel)
11
+ * - Provider abstraction: Circle first-class, Bridge secondary, manual fallback
12
+ * - The adapter does NOT move money between bank and ad platform — that is ad-billing-adapter.ts
13
+ *
14
+ * Agents: Dockson (treasury), Heartbeat daemon
15
+ *
16
+ * PRD Reference: §11.1A, §12.1, §12.4, §12.5
17
+ *
18
+ * Circle API reference (v1):
19
+ * Auth: Bearer token via API key — header `Authorization: Bearer {apiKey}`
20
+ * Base URL: https://api.circle.com/v1
21
+ * GET /wallets → list wallets
22
+ * GET /wallets/{id}/balances → wallet balances (amount, currency, chain)
23
+ * GET /configuration → supported chains and assets
24
+ * GET /banks/wires → linked bank accounts
25
+ * POST /payouts → initiate wire payout (off-ramp)
26
+ * GET /payouts/{id} → transfer status
27
+ * GET /payouts?destination={bankId} → list completed payouts for reconciliation
28
+ *
29
+ * Response shape (balance):
30
+ * { data: { available: [{ amount: "1000.00", currency: "USD" }] } }
31
+ * Response shape (payout):
32
+ * { data: { id, status, amount: { amount, currency }, destination, createDate, updateDate } }
33
+ * Payout statuses: pending → processing → complete | failed
34
+ *
35
+ * Bridge API reference:
36
+ * Auth: API key header `Api-Key: {apiKey}`
37
+ * Base URL: https://api.bridge.xyz/v0
38
+ * POST /customers/{id}/liquidation_addresses → create liquidation address
39
+ * GET /customers/{id}/liquidation_addresses → list addresses
40
+ * GET /liquidation_addresses/{id} → transfer status
41
+ * Transfers settle via ACH to linked bank — status polling required
42
+ */
43
+ import { createHash } from 'node:crypto';
44
+ function toCents(dollars) {
45
+ return Math.round(dollars * 100);
46
+ }
47
+ function toDollars(cents) {
48
+ return cents / 100;
49
+ }
50
+ // ── Hash Chain Helper ───────────────────────────────
51
+ function computeTransferHash(record, previousHash) {
52
+ const payload = JSON.stringify({
53
+ id: record.id,
54
+ fundingPlanId: record.fundingPlanId,
55
+ providerTransferId: record.providerTransferId,
56
+ amountCents: record.amountCents,
57
+ feesCents: record.feesCents,
58
+ status: record.status,
59
+ initiatedAt: record.initiatedAt,
60
+ }) + previousHash;
61
+ return createHash('sha256').update(payload).digest('hex');
62
+ }
63
+ // ── Reference Implementation Sketch: Circle ─────────
64
+ // Production implementation would live in wizard/lib/financial/stablecoin/circle.ts
65
+ class CircleAdapter {
66
+ config;
67
+ baseUrl = 'https://api.circle.com/v1';
68
+ apiKey = '';
69
+ bankId = '';
70
+ constructor(config) {
71
+ this.config = config;
72
+ this.apiKey = config.apiKey;
73
+ this.bankId = config.bankId;
74
+ if (config.environment === 'sandbox') {
75
+ // Circle sandbox base URL is the same but uses sandbox API keys
76
+ }
77
+ }
78
+ // ── Setup (interactive) ──────────
79
+ async authenticate(credentials) {
80
+ // GET /configuration — verifies API key works
81
+ // Circle returns { data: { payments: { masterWalletId } } }
82
+ const res = await this.apiCall('GET', '/configuration');
83
+ const data = res.data;
84
+ const payments = data?.payments;
85
+ return {
86
+ valid: true,
87
+ accountId: payments?.masterWalletId,
88
+ };
89
+ }
90
+ async verifySupportedAssets(_credentials) {
91
+ // Circle supports USDC on ETH, SOL, MATIC, AVAX, etc.
92
+ // GET /configuration → data.payments.supportedCurrencies
93
+ // Hardcoded for pattern — real implementation queries the API
94
+ return [
95
+ { asset: 'USDC', network: 'ETH', contractAddress: '0xa0b86991c6218b36c1d19d4a2e9eb0ce3606eb48', minRedemption: toCents(100) },
96
+ { asset: 'USDC', network: 'SOL', contractAddress: 'EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v', minRedemption: toCents(100) },
97
+ { asset: 'USDC', network: 'MATIC', contractAddress: '0x3c499c542cef5e3811e1192ce70d8cc03d5c3359', minRedemption: toCents(100) },
98
+ ];
99
+ }
100
+ async verifyLinkedBank(_credentials) {
101
+ // GET /banks/wires — lists linked wire destinations
102
+ // Response: { data: [{ id, description, trackingRef, bankAddress, billingDetails, status }] }
103
+ const res = await this.apiCall('GET', '/banks/wires');
104
+ const banks = res.data;
105
+ if (!banks || banks.length === 0) {
106
+ return { linked: false, error: 'No linked bank accounts found in Circle' };
107
+ }
108
+ const primary = banks[0];
109
+ return {
110
+ linked: true,
111
+ bankId: primary.id,
112
+ bankName: primary.billingDetails?.name,
113
+ accountLast4: primary.trackingRef
114
+ ? primary.trackingRef.slice(-4)
115
+ : undefined,
116
+ };
117
+ }
118
+ async getInitialBalances(_credentials) {
119
+ return this.fetchStablecoinBalances();
120
+ }
121
+ // ── Runtime (daemon) ──────────
122
+ async getBalances() {
123
+ const stablecoin = await this.fetchStablecoinBalances();
124
+ const totalStablecoinCents = stablecoin.reduce((sum, b) => (sum + b.balanceCents), 0);
125
+ // Fiat balances come from the bank adapter, not the stablecoin provider.
126
+ // The caller (Treasury Planner) combines stablecoin + bank balances.
127
+ return {
128
+ stablecoin,
129
+ fiat: [],
130
+ totalStablecoinCents,
131
+ totalFiatAvailableCents: 0,
132
+ };
133
+ }
134
+ async quoteRedemption(amountCents) {
135
+ // Circle payout fees vary by destination and amount.
136
+ // For wire payouts: typically $25 flat fee.
137
+ // Settlement: 1-2 business days for domestic wire.
138
+ const feeCents = toCents(25);
139
+ return {
140
+ provider: 'circle',
141
+ sourceAsset: 'USDC',
142
+ sourceNetwork: 'ETH',
143
+ requestedCents: amountCents,
144
+ estimatedFeeCents: feeCents,
145
+ estimatedNetCents: (amountCents - feeCents),
146
+ estimatedSettlementMinutes: 24 * 60, // 1 business day estimate
147
+ expiresAt: new Date(Date.now() + 5 * 60 * 1000).toISOString(),
148
+ };
149
+ }
150
+ async initiateOfframp(plan, previousHash) {
151
+ // POST /payouts
152
+ // Body: { idempotencyKey, source: { type: "wallet", id: "master" },
153
+ // destination: { type: "wire", id: bankId },
154
+ // amount: { amount: "1000.00", currency: "USD" },
155
+ // metadata: { beneficiaryEmail: "..." } }
156
+ const res = await this.apiCall('POST', '/payouts', {
157
+ idempotencyKey: plan.idempotencyKey,
158
+ source: { type: 'wallet', id: 'master' },
159
+ destination: { type: 'wire', id: this.bankId },
160
+ amount: { amount: toDollars(plan.requiredCents).toFixed(2), currency: 'USD' },
161
+ });
162
+ const payout = res.data;
163
+ const now = new Date().toISOString();
164
+ const id = crypto.randomUUID();
165
+ const record = {
166
+ id,
167
+ fundingPlanId: plan.id,
168
+ providerTransferId: payout.id,
169
+ provider: 'circle',
170
+ direction: 'crypto_to_fiat',
171
+ sourceAsset: 'USDC',
172
+ sourceNetwork: 'ETH',
173
+ amountCents: plan.requiredCents,
174
+ feesCents: toCents(25),
175
+ netAmountCents: (plan.requiredCents - toCents(25)),
176
+ destinationBankId: plan.destinationBankId,
177
+ status: 'pending',
178
+ initiatedAt: now,
179
+ idempotencyKey: plan.idempotencyKey,
180
+ previousHash,
181
+ };
182
+ const hash = computeTransferHash(record, previousHash);
183
+ return { ...record, hash };
184
+ }
185
+ async getTransferStatus(transferId) {
186
+ // GET /payouts/{id}
187
+ // Response: { data: { id, status, amount, fees, createDate, updateDate } }
188
+ // Circle statuses: pending → processing → complete | failed
189
+ const res = await this.apiCall('GET', `/payouts/${transferId}`);
190
+ const payout = res.data;
191
+ const amount = payout.amount;
192
+ const fees = payout.fees;
193
+ return {
194
+ transferId,
195
+ providerTransferId: payout.id,
196
+ status: mapCircleStatus(payout.status),
197
+ amountCents: toCents(parseFloat(amount.amount)),
198
+ feesCents: fees ? toCents(parseFloat(fees.amount)) : 0,
199
+ initiatedAt: payout.createDate,
200
+ completedAt: payout.status === 'complete' ? payout.updateDate : undefined,
201
+ providerRawStatus: payout.status,
202
+ };
203
+ }
204
+ async cancelTransfer(transferId) {
205
+ // Circle does not support cancellation of payouts once processing begins.
206
+ // Only pending payouts may be cancellable via support — no direct API.
207
+ return {
208
+ cancelled: false,
209
+ reason: 'Circle does not support programmatic payout cancellation. Contact support for pending payouts.',
210
+ };
211
+ }
212
+ async listCompletedTransfers(dateRange) {
213
+ // GET /payouts?destination={bankId}&status=complete
214
+ // &pageBefore=...&pageAfter=...
215
+ // Filter by createDate within dateRange on the client side.
216
+ // Returns array of TransferRecords for reconciliation.
217
+ // In production: paginate and filter by date.
218
+ throw new Error('HTTP implementation — use node:https, no SDK dependencies');
219
+ }
220
+ // ── Private helpers ──────────
221
+ async fetchStablecoinBalances() {
222
+ // GET /wallets/master/balances (or /wallets → pick master → /ballets/{id}/balances)
223
+ // Response: { data: { available: [{ amount: "1500.50", currency: "USD" }] } }
224
+ const res = await this.apiCall('GET', '/wallets');
225
+ const wallets = res.data;
226
+ const now = new Date().toISOString();
227
+ const balances = [];
228
+ for (const wallet of wallets) {
229
+ const available = wallet.balances ?? [];
230
+ for (const bal of available) {
231
+ if (bal.currency === 'USD') {
232
+ balances.push({
233
+ provider: 'circle',
234
+ asset: 'USDC',
235
+ network: 'ETH', // Circle aggregates across chains for USD balance
236
+ balanceCents: toCents(parseFloat(bal.amount)),
237
+ lastUpdated: now,
238
+ });
239
+ }
240
+ }
241
+ }
242
+ return balances;
243
+ }
244
+ async apiCall(method, path, body) {
245
+ // Implementation: raw HTTPS (no SDK — zero dependency principle)
246
+ // Headers:
247
+ // Authorization: Bearer {this.apiKey}
248
+ // Content-Type: application/json
249
+ // Accept: application/json
250
+ // Sanitize response strings per §9.19.16 before returning
251
+ throw new Error('HTTP implementation — use node:https, no SDK dependencies');
252
+ }
253
+ }
254
+ // ── Status Mapping ──────────────────────────────────
255
+ function mapCircleStatus(circleStatus) {
256
+ switch (circleStatus) {
257
+ case 'pending': return 'pending';
258
+ case 'processing': return 'processing';
259
+ case 'complete': return 'completed';
260
+ case 'failed': return 'failed';
261
+ default: return 'pending';
262
+ }
263
+ }
264
+ export { toCents, toDollars, computeTransferHash, mapCircleStatus, CircleAdapter };