tapimo 0.1.0 → 0.3.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 (520) hide show
  1. package/README.md +57 -16
  2. package/dist/ApiKey.d.ts +4 -1
  3. package/dist/ApiKey.d.ts.map +1 -1
  4. package/dist/ApiKey.js +6 -2
  5. package/dist/ApiKey.js.map +1 -1
  6. package/dist/ApiKeys.d.ts +98 -3
  7. package/dist/ApiKeys.d.ts.map +1 -1
  8. package/dist/ApiKeys.js +150 -1
  9. package/dist/ApiKeys.js.map +1 -1
  10. package/dist/App.d.ts +7917 -2315
  11. package/dist/App.d.ts.map +1 -1
  12. package/dist/App.js +141 -329
  13. package/dist/App.js.map +1 -1
  14. package/dist/Scope.d.ts +20 -4
  15. package/dist/Scope.d.ts.map +1 -1
  16. package/dist/Scope.js +23 -4
  17. package/dist/Scope.js.map +1 -1
  18. package/dist/Webhooks.d.ts +2 -2
  19. package/dist/Webhooks.d.ts.map +1 -1
  20. package/dist/Webhooks.js +2 -2
  21. package/dist/Webhooks.js.map +1 -1
  22. package/dist/admin/App.d.ts +203 -120
  23. package/dist/admin/App.d.ts.map +1 -1
  24. package/dist/admin/apps/api-keys.d.ts +111 -6
  25. package/dist/admin/apps/api-keys.d.ts.map +1 -1
  26. package/dist/admin/apps/api-keys.js +67 -0
  27. package/dist/admin/apps/api-keys.js.map +1 -1
  28. package/dist/admin/apps/scopes.d.ts +12 -1
  29. package/dist/admin/apps/scopes.d.ts.map +1 -1
  30. package/dist/admin/apps/scopes.js +3 -0
  31. package/dist/admin/apps/scopes.js.map +1 -1
  32. package/dist/admin/apps/verified-tokens.d.ts +116 -116
  33. package/dist/admin/apps/verified-tokens.js +1 -1
  34. package/dist/admin/apps/verified-tokens.js.map +1 -1
  35. package/dist/admin/ui.generated.d.ts +1 -1
  36. package/dist/admin/ui.generated.js +13 -13
  37. package/dist/admin/ui.generated.js.map +1 -1
  38. package/dist/analytics/Analytics.d.ts +151 -0
  39. package/dist/analytics/Analytics.d.ts.map +1 -0
  40. package/dist/analytics/Analytics.js +212 -0
  41. package/dist/analytics/Analytics.js.map +1 -0
  42. package/dist/analytics/tables/requestEvents.d.ts +215 -0
  43. package/dist/analytics/tables/requestEvents.d.ts.map +1 -0
  44. package/dist/analytics/tables/requestEvents.js +264 -0
  45. package/dist/analytics/tables/requestEvents.js.map +1 -0
  46. package/dist/apps/data/App.d.ts +19576 -0
  47. package/dist/apps/data/App.d.ts.map +1 -0
  48. package/dist/apps/data/App.js +272 -0
  49. package/dist/apps/data/App.js.map +1 -0
  50. package/dist/apps/data/index.d.ts +3 -0
  51. package/dist/apps/data/index.d.ts.map +1 -0
  52. package/dist/apps/data/index.js +3 -0
  53. package/dist/apps/data/index.js.map +1 -0
  54. package/dist/apps/{activities.d.ts → data/routes/activities.d.ts} +32 -32
  55. package/dist/apps/{activities.d.ts.map → data/routes/activities.d.ts.map} +1 -1
  56. package/dist/apps/{activities.js → data/routes/activities.js} +13 -13
  57. package/dist/apps/data/routes/activities.js.map +1 -0
  58. package/dist/apps/{addresses.d.ts → data/routes/addresses.d.ts} +22 -22
  59. package/dist/apps/{addresses.d.ts.map → data/routes/addresses.d.ts.map} +1 -1
  60. package/dist/apps/{addresses.js → data/routes/addresses.js} +5 -5
  61. package/dist/apps/data/routes/addresses.js.map +1 -0
  62. package/dist/apps/{balances.d.ts → data/routes/balances.d.ts} +4 -4
  63. package/dist/apps/data/routes/balances.d.ts.map +1 -0
  64. package/dist/apps/{balances.js → data/routes/balances.js} +42 -11
  65. package/dist/apps/data/routes/balances.js.map +1 -0
  66. package/dist/apps/{blocks.d.ts → data/routes/blocks.d.ts} +47 -47
  67. package/dist/apps/data/routes/blocks.d.ts.map +1 -0
  68. package/dist/apps/{blocks.js → data/routes/blocks.js} +13 -13
  69. package/dist/apps/data/routes/blocks.js.map +1 -0
  70. package/dist/apps/{coingecko.d.ts → data/routes/coingecko.d.ts} +8 -8
  71. package/dist/apps/data/routes/coingecko.d.ts.map +1 -0
  72. package/dist/apps/{coingecko.js → data/routes/coingecko.js} +13 -13
  73. package/dist/apps/data/routes/coingecko.js.map +1 -0
  74. package/dist/apps/{exchanges.d.ts → data/routes/exchanges.d.ts} +108 -108
  75. package/dist/apps/data/routes/exchanges.d.ts.map +1 -0
  76. package/dist/apps/{exchanges.js → data/routes/exchanges.js} +19 -19
  77. package/dist/apps/data/routes/exchanges.js.map +1 -0
  78. package/dist/apps/{fee-amm.d.ts → data/routes/fee-amm.d.ts} +39 -39
  79. package/dist/apps/data/routes/fee-amm.d.ts.map +1 -0
  80. package/dist/apps/{fee-amm.js → data/routes/fee-amm.js} +17 -17
  81. package/dist/apps/data/routes/fee-amm.js.map +1 -0
  82. package/dist/apps/data/routes/funding.d.ts +765 -0
  83. package/dist/apps/data/routes/funding.d.ts.map +1 -0
  84. package/dist/apps/data/routes/funding.js +383 -0
  85. package/dist/apps/data/routes/funding.js.map +1 -0
  86. package/dist/apps/{indexer.d.ts → data/routes/indexer.d.ts} +4 -4
  87. package/dist/apps/data/routes/indexer.d.ts.map +1 -0
  88. package/dist/apps/{indexer.js → data/routes/indexer.js} +13 -9
  89. package/dist/apps/data/routes/indexer.js.map +1 -0
  90. package/dist/apps/{receipts.d.ts → data/routes/receipts.d.ts} +49 -49
  91. package/dist/apps/data/routes/receipts.d.ts.map +1 -0
  92. package/dist/apps/{receipts.js → data/routes/receipts.js} +14 -20
  93. package/dist/apps/data/routes/receipts.js.map +1 -0
  94. package/dist/apps/{rpc.d.ts → data/routes/rpc.d.ts} +33 -40
  95. package/dist/apps/data/routes/rpc.d.ts.map +1 -0
  96. package/dist/apps/{rpc.js → data/routes/rpc.js} +35 -7
  97. package/dist/apps/data/routes/rpc.js.map +1 -0
  98. package/dist/apps/{tokenlist.d.ts → data/routes/tokenlist.d.ts} +40 -40
  99. package/dist/apps/data/routes/tokenlist.d.ts.map +1 -0
  100. package/dist/apps/{tokenlist.js → data/routes/tokenlist.js} +8 -8
  101. package/dist/apps/data/routes/tokenlist.js.map +1 -0
  102. package/dist/apps/{tokens.d.ts → data/routes/tokens.d.ts} +468 -468
  103. package/dist/apps/data/routes/tokens.d.ts.map +1 -0
  104. package/dist/apps/{tokens.js → data/routes/tokens.js} +19 -19
  105. package/dist/apps/data/routes/tokens.js.map +1 -0
  106. package/dist/apps/{transactions.d.ts → data/routes/transactions.d.ts} +304 -304
  107. package/dist/apps/data/routes/transactions.d.ts.map +1 -0
  108. package/dist/apps/{transactions.js → data/routes/transactions.js} +13 -13
  109. package/dist/apps/data/routes/transactions.js.map +1 -0
  110. package/dist/apps/{transfers.d.ts → data/routes/transfers.d.ts} +62 -62
  111. package/dist/apps/data/routes/transfers.d.ts.map +1 -0
  112. package/dist/apps/{transfers.js → data/routes/transfers.js} +13 -13
  113. package/dist/apps/data/routes/transfers.js.map +1 -0
  114. package/dist/apps/{verified-tokens.d.ts → data/routes/verified-tokens.d.ts} +6 -6
  115. package/dist/apps/data/routes/verified-tokens.d.ts.map +1 -0
  116. package/dist/apps/{verified-tokens.js → data/routes/verified-tokens.js} +9 -9
  117. package/dist/apps/data/routes/verified-tokens.js.map +1 -0
  118. package/dist/apps/{webhooks.d.ts → data/routes/webhooks.d.ts} +17 -17
  119. package/dist/apps/{webhooks.d.ts.map → data/routes/webhooks.d.ts.map} +1 -1
  120. package/dist/apps/{webhooks.js → data/routes/webhooks.js} +38 -34
  121. package/dist/apps/data/routes/webhooks.js.map +1 -0
  122. package/dist/apps/docs/App.d.ts +29 -0
  123. package/dist/apps/docs/App.d.ts.map +1 -0
  124. package/dist/apps/docs/App.js +54 -0
  125. package/dist/apps/docs/App.js.map +1 -0
  126. package/dist/{internal/OpenApi.fonts.d.ts → apps/docs/fonts.d.ts} +1 -1
  127. package/dist/apps/docs/fonts.d.ts.map +1 -0
  128. package/dist/{internal/OpenApi.fonts.js → apps/docs/fonts.js} +1 -1
  129. package/dist/apps/docs/fonts.js.map +1 -0
  130. package/dist/apps/docs/index.d.ts +2 -0
  131. package/dist/apps/docs/index.d.ts.map +1 -0
  132. package/dist/apps/docs/index.js +2 -0
  133. package/dist/apps/docs/index.js.map +1 -0
  134. package/dist/{internal/OpenApi.logo.d.ts → apps/docs/logo.d.ts} +1 -1
  135. package/dist/apps/docs/logo.d.ts.map +1 -0
  136. package/dist/{internal/OpenApi.logo.js → apps/docs/logo.js} +1 -1
  137. package/dist/apps/docs/logo.js.map +1 -0
  138. package/dist/apps/docs/reference.d.ts +21 -0
  139. package/dist/apps/docs/reference.d.ts.map +1 -0
  140. package/dist/apps/docs/reference.js +112 -0
  141. package/dist/apps/docs/reference.js.map +1 -0
  142. package/dist/apps/index.d.ts +5 -0
  143. package/dist/apps/index.d.ts.map +1 -0
  144. package/dist/apps/index.js +5 -0
  145. package/dist/apps/index.js.map +1 -0
  146. package/dist/apps/mcp.d.ts +76 -0
  147. package/dist/apps/mcp.d.ts.map +1 -0
  148. package/dist/apps/mcp.js +188 -0
  149. package/dist/apps/mcp.js.map +1 -0
  150. package/dist/apps/metadata.d.ts +7 -0
  151. package/dist/apps/metadata.d.ts.map +1 -0
  152. package/dist/apps/metadata.js +15 -0
  153. package/dist/apps/metadata.js.map +1 -0
  154. package/dist/apps/platform/App.d.ts +5262 -0
  155. package/dist/apps/platform/App.d.ts.map +1 -0
  156. package/dist/apps/platform/App.js +84 -0
  157. package/dist/apps/platform/App.js.map +1 -0
  158. package/dist/apps/platform/Billing.d.ts +279 -0
  159. package/dist/apps/platform/Billing.d.ts.map +1 -0
  160. package/dist/apps/platform/Billing.js +477 -0
  161. package/dist/apps/platform/Billing.js.map +1 -0
  162. package/dist/apps/platform/index.d.ts +3 -0
  163. package/dist/apps/platform/index.d.ts.map +1 -0
  164. package/dist/apps/platform/index.js +3 -0
  165. package/dist/apps/platform/index.js.map +1 -0
  166. package/dist/apps/platform/routes/api-keys.d.ts +973 -0
  167. package/dist/apps/platform/routes/api-keys.d.ts.map +1 -0
  168. package/dist/apps/platform/routes/api-keys.js +430 -0
  169. package/dist/apps/platform/routes/api-keys.js.map +1 -0
  170. package/dist/apps/platform/routes/billing.d.ts +1520 -0
  171. package/dist/apps/platform/routes/billing.d.ts.map +1 -0
  172. package/dist/apps/platform/routes/billing.js +795 -0
  173. package/dist/apps/platform/routes/billing.js.map +1 -0
  174. package/dist/apps/platform/routes/invitations.d.ts +851 -0
  175. package/dist/apps/platform/routes/invitations.d.ts.map +1 -0
  176. package/dist/apps/platform/routes/invitations.js +471 -0
  177. package/dist/apps/platform/routes/invitations.js.map +1 -0
  178. package/dist/apps/platform/routes/me.d.ts +95 -0
  179. package/dist/apps/platform/routes/me.d.ts.map +1 -0
  180. package/dist/apps/platform/routes/me.js +81 -0
  181. package/dist/apps/platform/routes/me.js.map +1 -0
  182. package/dist/apps/platform/routes/members.d.ts +554 -0
  183. package/dist/apps/platform/routes/members.d.ts.map +1 -0
  184. package/dist/apps/platform/routes/members.js +251 -0
  185. package/dist/apps/platform/routes/members.js.map +1 -0
  186. package/dist/apps/platform/routes/orgs.d.ts +596 -0
  187. package/dist/apps/platform/routes/orgs.d.ts.map +1 -0
  188. package/dist/apps/platform/routes/orgs.js +276 -0
  189. package/dist/apps/platform/routes/orgs.js.map +1 -0
  190. package/dist/apps/platform/routes/projects.d.ts +740 -0
  191. package/dist/apps/platform/routes/projects.d.ts.map +1 -0
  192. package/dist/apps/platform/routes/projects.js +286 -0
  193. package/dist/apps/platform/routes/projects.js.map +1 -0
  194. package/dist/apps/platform/routes/scopes.d.ts +107 -0
  195. package/dist/apps/platform/routes/scopes.d.ts.map +1 -0
  196. package/dist/apps/platform/routes/scopes.js +66 -0
  197. package/dist/apps/platform/routes/scopes.js.map +1 -0
  198. package/dist/apps/platform/routes/usage.d.ts +588 -0
  199. package/dist/apps/platform/routes/usage.d.ts.map +1 -0
  200. package/dist/apps/platform/routes/usage.js +391 -0
  201. package/dist/apps/platform/routes/usage.js.map +1 -0
  202. package/dist/apps/relay/App.d.ts +44 -0
  203. package/dist/apps/relay/App.d.ts.map +1 -0
  204. package/dist/apps/relay/App.js +211 -0
  205. package/dist/apps/relay/App.js.map +1 -0
  206. package/dist/apps/relay/Sponsorships.d.ts +107 -0
  207. package/dist/apps/relay/Sponsorships.d.ts.map +1 -0
  208. package/dist/apps/relay/Sponsorships.js +194 -0
  209. package/dist/apps/relay/Sponsorships.js.map +1 -0
  210. package/dist/apps/relay/index.d.ts +3 -0
  211. package/dist/apps/relay/index.d.ts.map +1 -0
  212. package/dist/apps/relay/index.js +3 -0
  213. package/dist/apps/relay/index.js.map +1 -0
  214. package/dist/cli/Cli.d.ts +9 -2
  215. package/dist/cli/Cli.d.ts.map +1 -1
  216. package/dist/cli/Cli.js +12 -4
  217. package/dist/cli/Cli.js.map +1 -1
  218. package/dist/cli/commands/admin.d.ts +5 -1
  219. package/dist/cli/commands/admin.d.ts.map +1 -1
  220. package/dist/cli/commands/admin.js +82 -3
  221. package/dist/cli/commands/admin.js.map +1 -1
  222. package/dist/db/Db.d.ts +17 -0
  223. package/dist/db/Db.d.ts.map +1 -1
  224. package/dist/db/Db.js +254 -0
  225. package/dist/db/Db.js.map +1 -1
  226. package/dist/db/Schema.d.ts +159 -0
  227. package/dist/db/Schema.d.ts.map +1 -1
  228. package/dist/db/Schema.js +187 -2
  229. package/dist/db/Schema.js.map +1 -1
  230. package/dist/db/tables/billingSettings.d.ts +55 -0
  231. package/dist/db/tables/billingSettings.d.ts.map +1 -0
  232. package/dist/db/tables/billingSettings.js +70 -0
  233. package/dist/db/tables/billingSettings.js.map +1 -0
  234. package/dist/db/tables/invitations.d.ts +84 -0
  235. package/dist/db/tables/invitations.d.ts.map +1 -0
  236. package/dist/db/tables/invitations.js +165 -0
  237. package/dist/db/tables/invitations.js.map +1 -0
  238. package/dist/db/tables/memberships.d.ts +108 -0
  239. package/dist/db/tables/memberships.d.ts.map +1 -0
  240. package/dist/db/tables/memberships.js +153 -0
  241. package/dist/db/tables/memberships.js.map +1 -0
  242. package/dist/db/tables/organizations.d.ts +48 -0
  243. package/dist/db/tables/organizations.d.ts.map +1 -1
  244. package/dist/db/tables/organizations.js +97 -2
  245. package/dist/db/tables/organizations.js.map +1 -1
  246. package/dist/db/tables/projects.d.ts +65 -0
  247. package/dist/db/tables/projects.d.ts.map +1 -0
  248. package/dist/db/tables/projects.js +75 -0
  249. package/dist/db/tables/projects.js.map +1 -0
  250. package/dist/db/tables/requestUsage.d.ts +121 -0
  251. package/dist/db/tables/requestUsage.d.ts.map +1 -0
  252. package/dist/db/tables/requestUsage.js +150 -0
  253. package/dist/db/tables/requestUsage.js.map +1 -0
  254. package/dist/db/tables/sponsoredTransactions.d.ts +239 -0
  255. package/dist/db/tables/sponsoredTransactions.d.ts.map +1 -0
  256. package/dist/db/tables/sponsoredTransactions.js +314 -0
  257. package/dist/db/tables/sponsoredTransactions.js.map +1 -0
  258. package/dist/db/tables/stripeCustomers.d.ts +81 -0
  259. package/dist/db/tables/stripeCustomers.d.ts.map +1 -0
  260. package/dist/db/tables/stripeCustomers.js +120 -0
  261. package/dist/db/tables/stripeCustomers.js.map +1 -0
  262. package/dist/db/tables/users.d.ts +48 -0
  263. package/dist/db/tables/users.d.ts.map +1 -0
  264. package/dist/db/tables/users.js +65 -0
  265. package/dist/db/tables/users.js.map +1 -0
  266. package/dist/handlers/internal/executionError.d.ts.map +1 -1
  267. package/dist/handlers/internal/executionError.js +2 -0
  268. package/dist/handlers/internal/executionError.js.map +1 -1
  269. package/dist/handlers/internal/multisig.d.ts +2 -6
  270. package/dist/handlers/internal/multisig.d.ts.map +1 -1
  271. package/dist/handlers/internal/multisig.js +11 -36
  272. package/dist/handlers/internal/multisig.js.map +1 -1
  273. package/dist/handlers/internal/sponsorship.d.ts +35 -2
  274. package/dist/handlers/internal/sponsorship.d.ts.map +1 -1
  275. package/dist/handlers/internal/sponsorship.js +53 -14
  276. package/dist/handlers/internal/sponsorship.js.map +1 -1
  277. package/dist/handlers/internal/utils.d.ts +10 -3
  278. package/dist/handlers/internal/utils.d.ts.map +1 -1
  279. package/dist/handlers/internal/utils.js +14 -6
  280. package/dist/handlers/internal/utils.js.map +1 -1
  281. package/dist/handlers/relay.d.ts +6 -2
  282. package/dist/handlers/relay.d.ts.map +1 -1
  283. package/dist/handlers/relay.js +16 -2
  284. package/dist/handlers/relay.js.map +1 -1
  285. package/dist/index.d.ts +1 -0
  286. package/dist/index.d.ts.map +1 -1
  287. package/dist/index.js +1 -0
  288. package/dist/index.js.map +1 -1
  289. package/dist/internal/Auth.d.ts +222 -6
  290. package/dist/internal/Auth.d.ts.map +1 -1
  291. package/dist/internal/Auth.js +625 -74
  292. package/dist/internal/Auth.js.map +1 -1
  293. package/dist/internal/Cache.d.ts.map +1 -1
  294. package/dist/internal/Cache.js +4 -1
  295. package/dist/internal/Cache.js.map +1 -1
  296. package/dist/internal/EdgeCache.d.ts +10 -0
  297. package/dist/internal/EdgeCache.d.ts.map +1 -1
  298. package/dist/internal/EdgeCache.js +39 -8
  299. package/dist/internal/EdgeCache.js.map +1 -1
  300. package/dist/internal/Fees.d.ts +27 -0
  301. package/dist/internal/Fees.d.ts.map +1 -0
  302. package/dist/internal/Fees.js +48 -0
  303. package/dist/internal/Fees.js.map +1 -0
  304. package/dist/internal/FundingRoutes.d.ts +183 -0
  305. package/dist/internal/FundingRoutes.d.ts.map +1 -0
  306. package/dist/internal/FundingRoutes.js +490 -0
  307. package/dist/internal/FundingRoutes.js.map +1 -0
  308. package/dist/internal/Id.d.ts +15 -0
  309. package/dist/internal/Id.d.ts.map +1 -0
  310. package/dist/internal/Id.js +22 -0
  311. package/dist/internal/Id.js.map +1 -0
  312. package/dist/internal/Log.d.ts +9 -3
  313. package/dist/internal/Log.d.ts.map +1 -1
  314. package/dist/internal/Log.js +7 -0
  315. package/dist/internal/Log.js.map +1 -1
  316. package/dist/internal/OpenApi.d.ts +10 -20
  317. package/dist/internal/OpenApi.d.ts.map +1 -1
  318. package/dist/internal/OpenApi.js +8 -58
  319. package/dist/internal/OpenApi.js.map +1 -1
  320. package/dist/internal/RateLimit.d.ts +25 -0
  321. package/dist/internal/RateLimit.d.ts.map +1 -1
  322. package/dist/internal/RateLimit.js +51 -0
  323. package/dist/internal/RateLimit.js.map +1 -1
  324. package/dist/internal/Response.d.ts +1 -1
  325. package/dist/internal/Response.d.ts.map +1 -1
  326. package/dist/internal/Schema.d.ts +8 -0
  327. package/dist/internal/Schema.d.ts.map +1 -1
  328. package/dist/internal/Schema.js +7 -0
  329. package/dist/internal/Schema.js.map +1 -1
  330. package/dist/internal/Store.d.ts +7 -1
  331. package/dist/internal/Store.d.ts.map +1 -1
  332. package/dist/internal/Store.js +16 -2
  333. package/dist/internal/Store.js.map +1 -1
  334. package/dist/internal/Viem.d.ts +84 -0
  335. package/dist/internal/Viem.d.ts.map +1 -1
  336. package/dist/internal/Webhooks.d.ts +1 -1
  337. package/dist/internal/Webhooks.d.ts.map +1 -1
  338. package/dist/internal/Webhooks.js +3 -3
  339. package/dist/internal/Webhooks.js.map +1 -1
  340. package/package.json +33 -6
  341. package/src/ApiKey.ts +10 -2
  342. package/src/ApiKeys.test.ts +155 -1
  343. package/src/ApiKeys.ts +203 -1
  344. package/src/App.test.ts +64 -75741
  345. package/src/App.ts +218 -420
  346. package/src/Client.test-d.ts +657 -15
  347. package/src/Scope.ts +26 -4
  348. package/src/Webhooks.ts +2 -2
  349. package/src/admin/apps/api-keys.test.ts +51 -0
  350. package/src/admin/apps/api-keys.ts +84 -0
  351. package/src/admin/apps/scopes.test.ts +11 -1
  352. package/src/admin/apps/scopes.ts +3 -0
  353. package/src/admin/apps/verified-tokens.ts +1 -1
  354. package/src/admin/ui/src/components/Page.tsx +2 -3
  355. package/src/admin/ui/src/routes/__root.tsx +2 -2
  356. package/src/admin/ui/src/routes/api-keys.tsx +2 -2
  357. package/src/admin/ui.generated.ts +13 -13
  358. package/src/analytics/Analytics.test.ts +527 -0
  359. package/src/analytics/Analytics.ts +318 -0
  360. package/src/analytics/tables/requestEvents.ts +523 -0
  361. package/src/apps/composition.test.ts +66 -0
  362. package/src/apps/data/App.test.ts +72 -0
  363. package/src/apps/data/App.ts +330 -0
  364. package/src/apps/data/index.ts +2 -0
  365. package/src/apps/{activities.test.ts → data/routes/activities.test.ts} +3 -3
  366. package/src/apps/{activities.ts → data/routes/activities.ts} +15 -15
  367. package/src/apps/{addresses.ts → data/routes/addresses.ts} +6 -6
  368. package/src/apps/{balances.test.ts → data/routes/balances.test.ts} +2 -2
  369. package/src/apps/{balances.ts → data/routes/balances.ts} +46 -12
  370. package/src/apps/{blocks.test.ts → data/routes/blocks.test.ts} +3 -3
  371. package/src/apps/{blocks.ts → data/routes/blocks.ts} +14 -14
  372. package/src/apps/{coingecko.test.ts → data/routes/coingecko.test.ts} +2 -2
  373. package/src/apps/{coingecko.ts → data/routes/coingecko.ts} +14 -14
  374. package/src/apps/{exchanges.test.ts → data/routes/exchanges.test.ts} +1 -1
  375. package/src/apps/{exchanges.ts → data/routes/exchanges.ts} +20 -20
  376. package/src/apps/{fee-amm.test.ts → data/routes/fee-amm.test.ts} +3 -3
  377. package/src/apps/{fee-amm.ts → data/routes/fee-amm.ts} +18 -18
  378. package/src/apps/data/routes/funding.test.ts +214 -0
  379. package/src/apps/data/routes/funding.ts +584 -0
  380. package/src/apps/{indexer.test.ts → data/routes/indexer.test.ts} +26 -5
  381. package/src/apps/{indexer.ts → data/routes/indexer.ts} +13 -10
  382. package/src/apps/{receipts.test.ts → data/routes/receipts.test.ts} +3 -3
  383. package/src/apps/{receipts.ts → data/routes/receipts.ts} +15 -22
  384. package/src/apps/{rpc.test.ts → data/routes/rpc.test.ts} +122 -7
  385. package/src/apps/{rpc.ts → data/routes/rpc.ts} +38 -8
  386. package/src/apps/{tokenlist.test.ts → data/routes/tokenlist.test.ts} +3 -3
  387. package/src/apps/{tokenlist.ts → data/routes/tokenlist.ts} +9 -9
  388. package/src/apps/{tokens.test.ts → data/routes/tokens.test.ts} +2 -2
  389. package/src/apps/{tokens.ts → data/routes/tokens.ts} +20 -20
  390. package/src/apps/{transactions.test.ts → data/routes/transactions.test.ts} +3 -3
  391. package/src/apps/{transactions.ts → data/routes/transactions.ts} +15 -15
  392. package/src/apps/{transfers.test.ts → data/routes/transfers.test.ts} +2 -2
  393. package/src/apps/{transfers.ts → data/routes/transfers.ts} +15 -15
  394. package/src/apps/{verified-tokens.test.ts → data/routes/verified-tokens.test.ts} +3 -3
  395. package/src/apps/{verified-tokens.ts → data/routes/verified-tokens.ts} +10 -10
  396. package/src/apps/{webhooks.test.ts → data/routes/webhooks.test.ts} +7 -7
  397. package/src/apps/{webhooks.ts → data/routes/webhooks.ts} +50 -43
  398. package/src/apps/docs/App.ts +65 -0
  399. package/src/apps/docs/index.ts +1 -0
  400. package/src/apps/docs/reference.ts +132 -0
  401. package/src/apps/index.ts +4 -0
  402. package/src/apps/mcp.test.ts +206 -0
  403. package/src/apps/mcp.ts +250 -0
  404. package/src/apps/metadata.ts +23 -0
  405. package/src/apps/platform/App.ts +169 -0
  406. package/src/apps/platform/Billing.test.ts +530 -0
  407. package/src/apps/platform/Billing.ts +682 -0
  408. package/src/apps/platform/index.ts +2 -0
  409. package/src/apps/platform/routes/api-keys.test.ts +493 -0
  410. package/src/apps/platform/routes/api-keys.ts +543 -0
  411. package/src/apps/platform/routes/billing.test.ts +1100 -0
  412. package/src/apps/platform/routes/billing.ts +966 -0
  413. package/src/apps/platform/routes/invitations.test.ts +409 -0
  414. package/src/apps/platform/routes/invitations.ts +587 -0
  415. package/src/apps/platform/routes/me.test.ts +351 -0
  416. package/src/apps/platform/routes/me.ts +106 -0
  417. package/src/apps/platform/routes/members.test.ts +195 -0
  418. package/src/apps/platform/routes/members.ts +313 -0
  419. package/src/apps/platform/routes/orgs.test.ts +313 -0
  420. package/src/apps/platform/routes/orgs.ts +365 -0
  421. package/src/apps/platform/routes/projects.test.ts +181 -0
  422. package/src/apps/platform/routes/projects.ts +367 -0
  423. package/src/apps/platform/routes/scopes.test.ts +29 -0
  424. package/src/apps/platform/routes/scopes.ts +85 -0
  425. package/src/apps/platform/routes/usage.test.ts +422 -0
  426. package/src/apps/platform/routes/usage.ts +527 -0
  427. package/src/apps/relay/App.test.ts +933 -0
  428. package/src/apps/relay/App.ts +236 -0
  429. package/src/apps/relay/Sponsorships.test.ts +375 -0
  430. package/src/apps/relay/Sponsorships.ts +306 -0
  431. package/src/apps/relay/index.ts +2 -0
  432. package/src/cli/Cli.test.ts +25 -2
  433. package/src/cli/Cli.ts +18 -3
  434. package/src/cli/commands/admin.test.ts +83 -0
  435. package/src/cli/commands/admin.ts +91 -3
  436. package/src/db/Db.ts +296 -0
  437. package/src/db/Schema.ts +241 -2
  438. package/src/db/tables/billingSettings.test.ts +87 -0
  439. package/src/db/tables/billingSettings.ts +108 -0
  440. package/src/db/tables/invitations.ts +198 -0
  441. package/src/db/tables/memberships.ts +208 -0
  442. package/src/db/tables/organizations.test.ts +38 -2
  443. package/src/db/tables/organizations.ts +117 -2
  444. package/src/db/tables/projects.ts +107 -0
  445. package/src/db/tables/requestUsage.ts +231 -0
  446. package/src/db/tables/sponsoredTransactions.test.ts +325 -0
  447. package/src/db/tables/sponsoredTransactions.ts +464 -0
  448. package/src/db/tables/stripeCustomers.test.ts +109 -0
  449. package/src/db/tables/stripeCustomers.ts +162 -0
  450. package/src/db/tables/users.ts +85 -0
  451. package/src/handlers/internal/executionError.ts +2 -0
  452. package/src/handlers/internal/multisig.test.ts +84 -10
  453. package/src/handlers/internal/multisig.ts +15 -50
  454. package/src/handlers/internal/sponsorship.ts +106 -20
  455. package/src/handlers/internal/utils.ts +19 -7
  456. package/src/handlers/{internal/relay.localnet.test.ts → relay.test.ts} +2 -2
  457. package/src/handlers/relay.ts +23 -5
  458. package/src/index.ts +1 -0
  459. package/src/internal/Auth.test.ts +491 -25
  460. package/src/internal/Auth.ts +839 -84
  461. package/src/internal/Cache.ts +5 -1
  462. package/src/internal/Cursor.test.ts +3 -2
  463. package/src/internal/EdgeCache.test.ts +27 -4
  464. package/src/internal/EdgeCache.ts +47 -9
  465. package/src/internal/Fees.test.ts +32 -0
  466. package/src/internal/Fees.ts +51 -0
  467. package/src/internal/FundingRoutes.ts +583 -0
  468. package/src/internal/Id.test.ts +17 -0
  469. package/src/internal/Id.ts +24 -0
  470. package/src/internal/Log.test.ts +2 -1
  471. package/src/internal/Log.ts +16 -3
  472. package/src/internal/MetricSink.ts +1 -1
  473. package/src/internal/OpenApi.ts +12 -60
  474. package/src/internal/RateLimit.test.ts +84 -0
  475. package/src/internal/RateLimit.ts +70 -0
  476. package/src/internal/Response.ts +1 -1
  477. package/src/internal/Schema.ts +8 -0
  478. package/src/internal/Store.test.ts +52 -0
  479. package/src/internal/Store.ts +24 -5
  480. package/src/internal/Tidx.local.test.ts +1 -1
  481. package/src/internal/VerifiedTokens.test.ts +1 -1
  482. package/src/internal/WebhookDestination.test.ts +1 -1
  483. package/src/internal/Webhooks.test.ts +7 -7
  484. package/src/internal/Webhooks.ts +4 -4
  485. package/dist/apps/activities.js.map +0 -1
  486. package/dist/apps/addresses.js.map +0 -1
  487. package/dist/apps/balances.d.ts.map +0 -1
  488. package/dist/apps/balances.js.map +0 -1
  489. package/dist/apps/blocks.d.ts.map +0 -1
  490. package/dist/apps/blocks.js.map +0 -1
  491. package/dist/apps/coingecko.d.ts.map +0 -1
  492. package/dist/apps/coingecko.js.map +0 -1
  493. package/dist/apps/exchanges.d.ts.map +0 -1
  494. package/dist/apps/exchanges.js.map +0 -1
  495. package/dist/apps/fee-amm.d.ts.map +0 -1
  496. package/dist/apps/fee-amm.js.map +0 -1
  497. package/dist/apps/indexer.d.ts.map +0 -1
  498. package/dist/apps/indexer.js.map +0 -1
  499. package/dist/apps/receipts.d.ts.map +0 -1
  500. package/dist/apps/receipts.js.map +0 -1
  501. package/dist/apps/rpc.d.ts.map +0 -1
  502. package/dist/apps/rpc.js.map +0 -1
  503. package/dist/apps/tokenlist.d.ts.map +0 -1
  504. package/dist/apps/tokenlist.js.map +0 -1
  505. package/dist/apps/tokens.d.ts.map +0 -1
  506. package/dist/apps/tokens.js.map +0 -1
  507. package/dist/apps/transactions.d.ts.map +0 -1
  508. package/dist/apps/transactions.js.map +0 -1
  509. package/dist/apps/transfers.d.ts.map +0 -1
  510. package/dist/apps/transfers.js.map +0 -1
  511. package/dist/apps/verified-tokens.d.ts.map +0 -1
  512. package/dist/apps/verified-tokens.js.map +0 -1
  513. package/dist/apps/webhooks.js.map +0 -1
  514. package/dist/internal/OpenApi.fonts.d.ts.map +0 -1
  515. package/dist/internal/OpenApi.fonts.js.map +0 -1
  516. package/dist/internal/OpenApi.logo.d.ts.map +0 -1
  517. package/dist/internal/OpenApi.logo.js.map +0 -1
  518. package/src/handlers/internal/multisig.localnet.test.ts +0 -146
  519. /package/src/{internal/OpenApi.fonts.ts → apps/docs/fonts.ts} +0 -0
  520. /package/src/{internal/OpenApi.logo.ts → apps/docs/logo.ts} +0 -0
@@ -2,7 +2,6 @@ import type { Context, Env, MiddlewareHandler, ValidationTargets } from 'hono'
2
2
  import type { HasRequiredKeys } from 'hono/utils/types'
3
3
  import { resolver, type ResponsesWithResolver, validator } from 'hono-openapi'
4
4
  import * as z from 'zod/mini'
5
- import { pilatFontFaces } from './OpenApi.fonts.js'
6
5
  import * as Response from './Response.js'
7
6
  import * as Schema from './Schema.js'
8
7
 
@@ -50,64 +49,6 @@ export {
50
49
  validator,
51
50
  } from 'hono-openapi'
52
51
 
53
- // Theme-aware Tempo API wordmark for the docs header (`vocs.logoUrl`), inlined
54
- // as SVG data URIs. See {@link file://./OpenApi.logo.ts}.
55
- export { logoUrl } from './OpenApi.logo.js'
56
-
57
- /**
58
- * Custom CSS injected into the standalone reference's shell `<head>` (via
59
- * `Handler.openApi(_, { css })`), after the Vocs design-system styles so it
60
- * overrides them:
61
- *
62
- * - Page/surface backgrounds use Tempo's near-black dark palette and pure-white
63
- * light palette via `light-dark(<light>, <dark>)`.
64
- * - The dark border color is darkened (the light theme keeps its default).
65
- * - Every corner is squared. The universal `!important` rule beats hard-coded
66
- * `border-radius` values and inline styles (e.g. the Scalar playground), which
67
- * overriding the radius scale variables alone would miss.
68
- * - The default sans/body font is Pilat (Vocs reads `--vocs-font-family`); the
69
- * webfont is embedded via {@link pilatFontFaces}. Body stays at the default
70
- * weight (400); headings are pinned to 500, which renders Pilat Demi (the
71
- * family has no 500 cut, so Demi covers the 500-600 range — see
72
- * {@link pilatFontFaces}).
73
- */
74
- export const css = `${pilatFontFaces}
75
-
76
- :root {
77
- --vocs-font-family: "Pilat", Arial, Helvetica, sans-serif;
78
- --vocs-background-color-primary: light-dark(#fafafa, #0a0a0a);
79
- --vocs-background-color-surface: light-dark(#fff, #121212);
80
- }
81
-
82
- :is(h1, h2, h3, h4, h5, h6)[data-v] {
83
- font-weight: 500;
84
- }
85
-
86
- /* Nudge the header logo a touch larger than the default max-h-7 (1.75rem). */
87
- [data-v-logo-image] {
88
- max-height: 2rem;
89
- }
90
-
91
- /* Sidebar leaf items render Regular (the nav's 450 default otherwise resolves to
92
- * Demi via the 500-600 range). Group labels ([data-v-sidebar-section-header])
93
- * keep their heavier weight. */
94
- [data-v-sidebar-item] {
95
- font-weight: 400;
96
- }
97
-
98
- [data-vocs-theme='dark'] {
99
- --vocs-color-gray4: oklch(20% 0 0);
100
- --vocs-color-gray5: oklch(0.23 0 0);
101
- --vocs-border-color-primary: oklch(0.25 0 0);
102
- --vocs-border-color-secondary: oklch(0.25 0 0);
103
- }
104
-
105
- *,
106
- *::before,
107
- *::after {
108
- border-radius: 0 !important;
109
- }`
110
-
111
52
  /**
112
53
  * Standard machine-readable `error.code` values per status, shared API-wide.
113
54
  * The reference enumerates `error.code` to these so generated clients narrow it
@@ -148,9 +89,11 @@ export const errorCodes = {
148
89
  'webhook_not_found',
149
90
  'delivery_not_found',
150
91
  'webhooks_not_enabled',
92
+ 'billing_not_found',
151
93
  ],
152
94
  429: ['rate_limit_exceeded', 'payment_required'],
153
95
  500: ['internal_error'],
96
+ 501: ['billing_unconfigured'],
154
97
  502: ['upstream_error'],
155
98
  } as const satisfies Record<number, readonly [string, ...string[]]>
156
99
 
@@ -318,7 +261,11 @@ export function responses<schema extends z.ZodMiniType>(
318
261
  content: {
319
262
  'application/json': {
320
263
  schema: resolver(success.schema, schemaOptions),
321
- ...(success.example === undefined ? {} : { example: success.example }),
264
+ ...(success.examples === undefined
265
+ ? success.example === undefined
266
+ ? {}
267
+ : { example: success.example }
268
+ : { examples: success.examples }),
322
269
  },
323
270
  },
324
271
  description: success.description,
@@ -334,6 +281,7 @@ export function responses<schema extends z.ZodMiniType>(
334
281
  ...(errors?.[415] && { 415: error(415, 'Unsupported media type.') }),
335
282
  429: responseRef('RateLimited'),
336
283
  500: responseRef('InternalError'),
284
+ ...(errors?.[501] && { 501: error(501, 'Not implemented.') }),
337
285
  502: error(502, 'Upstream data failure.'),
338
286
  }
339
287
  }
@@ -377,6 +325,8 @@ export declare namespace responses {
377
325
  413?: ErrorOverride | undefined
378
326
  /** Override for the 415 response. Setting this includes 415 in the map. */
379
327
  415?: ErrorOverride | undefined
328
+ /** Override for the 501 response. Setting this includes 501 in the map. */
329
+ 501?: ErrorOverride | undefined
380
330
  /** Override for the 502 response. */
381
331
  502?: ErrorOverride | undefined
382
332
  }
@@ -387,6 +337,8 @@ export declare namespace responses {
387
337
  description: string
388
338
  /** Optional full example body rendered for the 200 response. */
389
339
  example?: unknown
340
+ /** Optional named example bodies rendered for the 200 response. */
341
+ examples?: Record<string, { description?: string; summary?: string; value: unknown }>
390
342
  /** Zod schema describing the 200 response body. */
391
343
  schema: schema
392
344
  }
@@ -91,3 +91,87 @@ describe('memory', () => {
91
91
  `)
92
92
  })
93
93
  })
94
+
95
+ describe('edge', () => {
96
+ function binding(success = true) {
97
+ return { limit: vi.fn(async (_: { key: string }) => ({ success })) }
98
+ }
99
+
100
+ function request(options: { asn?: number | undefined; ip?: string | undefined } = {}) {
101
+ const value = new Request('https://api.tempo.xyz/v1/health', {
102
+ headers: options.ip ? { 'cf-connecting-ip': options.ip } : {},
103
+ })
104
+ if (options.asn) Object.assign(value, { cf: { asn: options.asn } })
105
+ return value
106
+ }
107
+
108
+ test('allows when every layer is under quota', async () => {
109
+ const asn = binding()
110
+ const global = binding()
111
+ const ip = binding()
112
+
113
+ const response = await RateLimit.edge(request({ asn: 64512, ip: '203.0.113.7' }), {
114
+ asn,
115
+ global,
116
+ ip,
117
+ })
118
+
119
+ expect(response).toBeUndefined()
120
+ expect(ip.limit).toHaveBeenCalledWith({ key: '203.0.113.7' })
121
+ expect(asn.limit).toHaveBeenCalledWith({ key: 'asn:64512' })
122
+ expect(global.limit).toHaveBeenCalledWith({ key: 'global' })
123
+ })
124
+
125
+ test('buckets IPv6 clients by /64 prefix', async () => {
126
+ const ip = binding()
127
+
128
+ await RateLimit.edge(request({ ip: '2001:db8:abcd:12::1' }), { ip })
129
+
130
+ expect(ip.limit).toHaveBeenCalledWith({ key: '2001:db8:abcd:12' })
131
+ })
132
+
133
+ test('returns 429 when any layer denies', async () => {
134
+ const response = await RateLimit.edge(request({ asn: 64512, ip: '203.0.113.7' }), {
135
+ asn: binding(false),
136
+ global: binding(),
137
+ ip: binding(),
138
+ })
139
+
140
+ expect(response?.status).toBe(429)
141
+ expect(response?.headers.get('retry-after')).toBe('10')
142
+ })
143
+
144
+ test('skips the asn layer when the request has no cf metadata', async () => {
145
+ const asn = binding(false)
146
+
147
+ const response = await RateLimit.edge(request({ ip: '203.0.113.7' }), { asn })
148
+
149
+ expect(response).toBeUndefined()
150
+ expect(asn.limit).not.toHaveBeenCalled()
151
+ })
152
+
153
+ test('keys unknown clients together when the ip header is missing', async () => {
154
+ const ip = binding()
155
+
156
+ await RateLimit.edge(request(), { ip })
157
+
158
+ expect(ip.limit).toHaveBeenCalledWith({ key: 'unknown' })
159
+ })
160
+
161
+ test('fails open when a binding errors', async () => {
162
+ const consoleError = vi.spyOn(console, 'error').mockImplementation(() => {})
163
+ try {
164
+ const response = await RateLimit.edge(request({ ip: '203.0.113.7' }), {
165
+ ip: {
166
+ limit() {
167
+ return Promise.reject(new Error('binding unavailable'))
168
+ },
169
+ },
170
+ })
171
+
172
+ expect(response).toBeUndefined()
173
+ } finally {
174
+ consoleError.mockRestore()
175
+ }
176
+ })
177
+ })
@@ -90,4 +90,74 @@ export declare namespace memory {
90
90
  }
91
91
  }
92
92
 
93
+ /** Cloudflare rate-limit binding (per-colo counters). */
94
+ export type Binding = {
95
+ /** Consumes one request; `success: false` when the key is over quota. */
96
+ limit(options: { key: string }): Promise<{ success: boolean }>
97
+ }
98
+
99
+ /**
100
+ * Layered edge rate limit over Cloudflare rate-limit bindings. Returns a 429
101
+ * when any configured layer denies; fails open when a binding errors.
102
+ */
103
+ export async function edge(request: Request, options: edge.Options): Promise<Response | undefined> {
104
+ try {
105
+ const checks: Promise<{ success: boolean }>[] = []
106
+ if (options.ip) checks.push(options.ip.limit({ key: clientKey(request) }))
107
+ const asn = (request as Request & { cf?: CfProperties }).cf?.asn
108
+ if (options.asn && asn !== undefined) checks.push(options.asn.limit({ key: `asn:${asn}` }))
109
+ if (options.global) checks.push(options.global.limit({ key: 'global' }))
110
+
111
+ const results = await Promise.all(checks)
112
+ if (results.some((result) => !result.success))
113
+ return new Response('Rate limit exceeded', {
114
+ headers: { 'retry-after': '10' },
115
+ status: 429,
116
+ })
117
+ } catch (error) {
118
+ console.error('Edge rate limit check failed:', error)
119
+ }
120
+ return undefined
121
+ }
122
+
123
+ export declare namespace edge {
124
+ /** Layers applied by {@link edge}; omitted layers are skipped. */
125
+ type Options = {
126
+ /** Per-network backstop; catches clients rotating addresses within one ASN. */
127
+ asn?: Binding | undefined
128
+ /** Fixed-key circuit breaker capping total throughput per colo. */
129
+ global?: Binding | undefined
130
+ /** Per-client limit, keyed by IPv4 address or IPv6 /64 prefix. */
131
+ ip?: Binding | undefined
132
+ }
133
+ }
134
+
135
+ /** Cloudflare-enriched request properties; absent outside Workers (tests, service bindings). */
136
+ type CfProperties = { asn?: number | undefined }
137
+
138
+ /** IPv4 clients key by address; IPv6 clients by /64 prefix so they cannot rotate within their allocation. */
139
+ function clientKey(request: Request): string {
140
+ const ip = request.headers.get('cf-connecting-ip')
141
+ if (!ip) return 'unknown'
142
+ if (ip.includes('.')) return ip
143
+ return ipv6Prefix(ip)
144
+ }
145
+
146
+ /** First four hextets of an IPv6 address, with `::` expanded. */
147
+ function ipv6Prefix(ip: string): string {
148
+ const [address = ''] = ip.split('%')
149
+ const [head = '', tail = ''] = address.split('::')
150
+ const left = head ? head.split(':') : []
151
+ const right = tail ? tail.split(':') : []
152
+ const groups = [
153
+ ...left,
154
+ ...Array.from({ length: Math.max(8 - left.length - right.length, 0) }, () => '0'),
155
+ ...right,
156
+ ]
157
+ return groups
158
+ .slice(0, 4)
159
+ .map((group) => Number.parseInt(group || '0', 16).toString(16))
160
+ .join(':')
161
+ }
162
+
93
163
  export { type RateLimitStore as Store }
@@ -96,7 +96,7 @@ export declare namespace error {
96
96
  }
97
97
 
98
98
  /** HTTP status code accepted by the public error helper. */
99
- type Status = 400 | 401 | 403 | 404 | 409 | 412 | 413 | 415 | 429 | 500 | 502 | 503
99
+ type Status = 400 | 401 | 403 | 404 | 409 | 412 | 413 | 415 | 429 | 500 | 501 | 502 | 503
100
100
 
101
101
  /** Options for creating a JSON error response. */
102
102
  type Options<status extends Status = Status, code extends string = string> = {
@@ -417,6 +417,14 @@ export const TotalCountCapped = z
417
417
  z.meta({ examples: [false] }),
418
418
  )
419
419
 
420
+ /**
421
+ * Resource environment (`production`/`sandbox`) query parameter shared across
422
+ * environment-scoped endpoints. Defaults to `production`.
423
+ */
424
+ export const Environment = z
425
+ ._default(z.enum(['production', 'sandbox']), 'production')
426
+ .check(z.describe('Resource environment.'), z.meta({ examples: ['sandbox'] }))
427
+
420
428
  /** Sort-direction (`asc`/`desc`) query parameter shared across list endpoints. */
421
429
  export const Order = z
422
430
  ._default(z.enum(['asc', 'desc']), 'desc')
@@ -230,6 +230,8 @@ describe('cloudflareKv', () => {
230
230
  .filter((key) => !options.prefix || key.startsWith(options.prefix))
231
231
  .sort()
232
232
  .map((name) => ({ name })),
233
+ list_complete: true,
234
+ cursor: '',
233
235
  }
234
236
  },
235
237
  async put(key, value, options) {
@@ -272,6 +274,56 @@ describe('cloudflareKv', () => {
272
274
  `[RangeError: Cloudflare KV expirationTtl must be at least 60 seconds]`,
273
275
  )
274
276
  })
277
+
278
+ test('lists every Cloudflare Workers KV page', async () => {
279
+ const calls: unknown[] = []
280
+ const namespace = {
281
+ async delete() {},
282
+ async get() {
283
+ return null
284
+ },
285
+ async list(options = {}) {
286
+ calls.push(options)
287
+ if (options.cursor === 'page-2')
288
+ return {
289
+ keys: [{ name: 'secret:2' }],
290
+ list_complete: true,
291
+ cursor: '',
292
+ }
293
+ return {
294
+ keys: [{ name: 'secret:1' }],
295
+ list_complete: false,
296
+ cursor: 'page-2',
297
+ }
298
+ },
299
+ async put() {},
300
+ } satisfies Store.cloudflareKv.Namespace
301
+ const store = Store.cloudflareKv(namespace)
302
+
303
+ expect(await store.list({ prefix: 'secret:' })).toMatchInlineSnapshot(`
304
+ {
305
+ "keys": [
306
+ {
307
+ "name": "secret:1",
308
+ },
309
+ {
310
+ "name": "secret:2",
311
+ },
312
+ ],
313
+ }
314
+ `)
315
+ expect(calls).toMatchInlineSnapshot(`
316
+ [
317
+ {
318
+ "prefix": "secret:",
319
+ },
320
+ {
321
+ "cursor": "page-2",
322
+ "prefix": "secret:",
323
+ },
324
+ ]
325
+ `)
326
+ })
275
327
  })
276
328
 
277
329
  describe('durableObject', () => {
@@ -281,10 +281,23 @@ export function cloudflareKv(namespace: cloudflareKv.Namespace): State {
281
281
  return namespace.get(key)
282
282
  },
283
283
  async list(options = {}) {
284
- const result = await namespace.list(
285
- options.prefix === undefined ? undefined : { prefix: options.prefix },
286
- )
287
- return { keys: result.keys.map(({ name }) => ({ name })) }
284
+ const keys: { name: string }[] = []
285
+ let cursor: string | undefined
286
+
287
+ for (;;) {
288
+ const result = await namespace.list(
289
+ options.prefix === undefined && cursor === undefined
290
+ ? undefined
291
+ : {
292
+ ...(options.prefix === undefined ? {} : { prefix: options.prefix }),
293
+ ...(cursor === undefined ? {} : { cursor }),
294
+ },
295
+ )
296
+ keys.push(...result.keys.map(({ name }) => ({ name })))
297
+ if (result.list_complete) return { keys }
298
+ if (result.cursor === undefined) throw new Error('Cloudflare KV list is missing a cursor.')
299
+ cursor = result.cursor
300
+ }
288
301
  },
289
302
  async put(key, value, options = {}) {
290
303
  const expirationTtl = cloudflareKvExpirationTtl(options.ttl)
@@ -308,13 +321,19 @@ export declare namespace cloudflareKv {
308
321
  /** Lists keys. */
309
322
  list(options?: {
310
323
  /** Restrict results to keys with this prefix. */
311
- prefix?: string | null | undefined
324
+ prefix?: string | undefined
325
+ /** Continue from a previous page. */
326
+ cursor?: string | undefined
312
327
  }): Promise<{
313
328
  /** Matching keys. */
314
329
  keys: readonly {
315
330
  /** Key name. */
316
331
  name: string
317
332
  }[]
333
+ /** Whether every matching key was returned. */
334
+ list_complete: boolean
335
+ /** Cursor for the next page. */
336
+ cursor?: string | undefined
318
337
  }>
319
338
  /** Writes a text value. */
320
339
  put(
@@ -1,6 +1,6 @@
1
1
  import * as TestApp from '../../test/App.js'
2
2
  import * as Runtime from '../../test/runtime.js'
3
- import * as Indexer from '../apps/indexer.js'
3
+ import * as Indexer from '../apps/data/routes/indexer.js'
4
4
 
5
5
  describe('local TIDX runtime', () => {
6
6
  test.runIf(Runtime.get().mode === 'localnet')(
@@ -30,7 +30,7 @@ const unreachable = () =>
30
30
 
31
31
  // Minimal context serving the verified-tokens feature config and the app db
32
32
  // (both the fresh and cached bindings, as `App.create` sets them).
33
- function context(db: Db.Db, config?: App.create.VerifiedTokens): Context<App.Environment> {
33
+ function context(db: Db.Db, config?: App.data.VerifiedTokens): Context<App.Environment> {
34
34
  return {
35
35
  get: (key: string) => (key === 'verifiedTokens' ? (config ?? {}) : key === 'db' || key === 'dbCached' ? db : undefined), // prettier-ignore
36
36
  } as unknown as Context<App.Environment>
@@ -3,7 +3,7 @@ import * as WebhookDestination from './WebhookDestination.js'
3
3
  const envelope = {
4
4
  chainId: 4217,
5
5
  createdAt: '2026-01-01T00:00:00.000Z',
6
- data: { amount: '1000', token: '0xabc' },
6
+ data: { amount: '1000', token: `0x${'aa'.repeat(20)}` },
7
7
  id: 'evt_test',
8
8
  subscriptionId: 'wh_test',
9
9
  type: 'token:transfer',
@@ -10,7 +10,7 @@ const fixedNow = () => new Date('2026-01-01T00:00:00.000Z')
10
10
  /** Asserts the random id/secret shape, then redacts them for a stable snapshot. */
11
11
  function redact(subscription: Webhooks.Subscription | null) {
12
12
  expect(subscription).not.toBeNull()
13
- expect(subscription?.id).toMatch(/^wh_\d{15}_[A-Za-z0-9_-]{21}$/)
13
+ expect(subscription?.id).toMatch(/^wh_\d{15}_[A-Za-z0-9]{24}$/)
14
14
  expect(subscription?.secret).toMatch(/^whsec_[0-9a-f]{64}$/)
15
15
  return { ...subscription, id: '<id>', secret: '<secret>' }
16
16
  }
@@ -155,7 +155,7 @@ describe('updateSubscription', () => {
155
155
  created.id,
156
156
  {
157
157
  destination: { type: 'url', url: 'https://hooks.example.com/v2' },
158
- filters: { token: '0xtoken' },
158
+ filters: { token: `0x${'aa'.repeat(20)}` },
159
159
  },
160
160
  { now: () => new Date('2026-01-02T00:00:00.000Z') },
161
161
  )
@@ -171,7 +171,7 @@ describe('updateSubscription', () => {
171
171
  "eventType": "token:transfer",
172
172
  "failureCount": 0,
173
173
  "filters": {
174
- "token": "0xtoken",
174
+ "token": "0xaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa",
175
175
  },
176
176
  "id": "<id>",
177
177
  "owner": {
@@ -380,7 +380,7 @@ describe('eventId / buildEnvelope', () => {
380
380
  const envelope = Webhooks.buildEnvelope({
381
381
  blockNumber: 100,
382
382
  createdAt: new Date('2026-01-01T00:00:00.000Z'),
383
- data: { amount: '1', to: '0x1' },
383
+ data: { amount: '1', to: `0x${'aa'.repeat(20)}` },
384
384
  logIndex: 3,
385
385
  subscription,
386
386
  })
@@ -392,7 +392,7 @@ describe('eventId / buildEnvelope', () => {
392
392
  "createdAt": "2026-01-01T00:00:00.000Z",
393
393
  "data": {
394
394
  "amount": "1",
395
- "to": "0x1",
395
+ "to": "0xaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa",
396
396
  },
397
397
  "id": "evt_d7c75afd0abccdc90a391d9313762a957c7e4383cac1fae76e5de56e49c9d3f8",
398
398
  "subscriptionId": "<subscriptionId>",
@@ -405,8 +405,8 @@ describe('eventId / buildEnvelope', () => {
405
405
  describe('delivery log', () => {
406
406
  /** Asserts the time-sortable delivery id shape and redacts non-deterministic fields. */
407
407
  function redactDelivery(delivery: Webhooks.Delivery) {
408
- expect(delivery.id).toMatch(/^whd_\d{15}_[A-Za-z0-9_-]{21}$/)
409
- expect(delivery.subscriptionId).toMatch(/^wh_\d{15}_[A-Za-z0-9_-]{21}$/)
408
+ expect(delivery.id).toMatch(/^whd_\d{15}_[A-Za-z0-9]{24}$/)
409
+ expect(delivery.subscriptionId).toMatch(/^wh_\d{15}_[A-Za-z0-9]{24}$/)
410
410
  return {
411
411
  ...delivery,
412
412
  envelope: { ...delivery.envelope, subscriptionId: '<subscriptionId>' },
@@ -1,11 +1,11 @@
1
- import { nanoid } from 'nanoid'
2
1
  import { Hash, Hex } from 'ox'
3
2
 
4
- import type * as app_Webhooks from '../apps/webhooks.js'
3
+ import type * as app_Webhooks from '../apps/data/routes/webhooks.js'
5
4
  import type * as Db from '../db/Db.js'
6
5
  import * as WebhookDeliveries from '../db/tables/webhookDeliveries.js'
7
6
  import * as WebhookSubscriptions from '../db/tables/webhookSubscriptions.js'
8
7
  import type * as Metrics from '../Metrics.js'
8
+ import * as Id from './Id.js'
9
9
  import * as MetricSink from './MetricSink.js'
10
10
  import * as WebhookDestination from './WebhookDestination.js'
11
11
 
@@ -758,14 +758,14 @@ function generateId(now: Date): string {
758
758
  // (mirroring delivery ids), letting listSubscriptions page newest-first; 15
759
759
  // digits leaves headroom well past the year 5138.
760
760
  const timestamp = now.getTime().toString().padStart(15, '0')
761
- return `wh_${timestamp}_${nanoid()}`
761
+ return `wh_${timestamp}_${Id.random()}`
762
762
  }
763
763
 
764
764
  function generateDeliveryId(now: Date): string {
765
765
  // Zero-pad the epoch-ms so ids sort chronologically by string comparison; 15
766
766
  // digits leaves headroom well past the year 5138.
767
767
  const timestamp = now.getTime().toString().padStart(15, '0')
768
- return `whd_${timestamp}_${nanoid()}`
768
+ return `whd_${timestamp}_${Id.random()}`
769
769
  }
770
770
 
771
771
  function generateSecret(): string {