workerstack 0.1.0-beta.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 (605) hide show
  1. package/CHANGELOG.md +13 -0
  2. package/LICENSE +21 -0
  3. package/README.md +138 -0
  4. package/dist/access.d.ts +131 -0
  5. package/dist/access.d.ts.map +1 -0
  6. package/dist/access.js +333 -0
  7. package/dist/access.js.map +1 -0
  8. package/dist/api/builder.d.ts +457 -0
  9. package/dist/api/builder.d.ts.map +1 -0
  10. package/dist/api/builder.js +45 -0
  11. package/dist/api/builder.js.map +1 -0
  12. package/dist/api/catalog.d.ts +8 -0
  13. package/dist/api/catalog.d.ts.map +1 -0
  14. package/dist/api/catalog.js +56 -0
  15. package/dist/api/catalog.js.map +1 -0
  16. package/dist/api/context.d.ts +47 -0
  17. package/dist/api/context.d.ts.map +1 -0
  18. package/dist/api/context.js +40 -0
  19. package/dist/api/context.js.map +1 -0
  20. package/dist/api/crud-router.d.ts +476 -0
  21. package/dist/api/crud-router.d.ts.map +1 -0
  22. package/dist/api/crud-router.js +354 -0
  23. package/dist/api/crud-router.js.map +1 -0
  24. package/dist/api/list-input-schema.d.ts +37 -0
  25. package/dist/api/list-input-schema.d.ts.map +1 -0
  26. package/dist/api/list-input-schema.js +63 -0
  27. package/dist/api/list-input-schema.js.map +1 -0
  28. package/dist/api/list-spec.d.ts +44 -0
  29. package/dist/api/list-spec.d.ts.map +1 -0
  30. package/dist/api/list-spec.js +49 -0
  31. package/dist/api/list-spec.js.map +1 -0
  32. package/dist/api/live-view.d.ts +14 -0
  33. package/dist/api/live-view.d.ts.map +1 -0
  34. package/dist/api/live-view.js +42 -0
  35. package/dist/api/live-view.js.map +1 -0
  36. package/dist/api/live-window.d.ts +40 -0
  37. package/dist/api/live-window.d.ts.map +1 -0
  38. package/dist/api/live-window.js +93 -0
  39. package/dist/api/live-window.js.map +1 -0
  40. package/dist/api/openapi.d.ts +6 -0
  41. package/dist/api/openapi.d.ts.map +1 -0
  42. package/dist/api/openapi.js +146 -0
  43. package/dist/api/openapi.js.map +1 -0
  44. package/dist/api/realtime-router.d.ts +94 -0
  45. package/dist/api/realtime-router.d.ts.map +1 -0
  46. package/dist/api/realtime-router.js +45 -0
  47. package/dist/api/realtime-router.js.map +1 -0
  48. package/dist/api/registry.d.ts +30 -0
  49. package/dist/api/registry.d.ts.map +1 -0
  50. package/dist/api/registry.js +236 -0
  51. package/dist/api/registry.js.map +1 -0
  52. package/dist/api/router.d.ts +15 -0
  53. package/dist/api/router.d.ts.map +1 -0
  54. package/dist/api/router.js +32 -0
  55. package/dist/api/router.js.map +1 -0
  56. package/dist/api/storage-router.d.ts +349 -0
  57. package/dist/api/storage-router.d.ts.map +1 -0
  58. package/dist/api/storage-router.js +155 -0
  59. package/dist/api/storage-router.js.map +1 -0
  60. package/dist/api/types.d.ts +55 -0
  61. package/dist/api/types.d.ts.map +1 -0
  62. package/dist/api/types.js +2 -0
  63. package/dist/api/types.js.map +1 -0
  64. package/dist/auth-password.d.ts +27 -0
  65. package/dist/auth-password.d.ts.map +1 -0
  66. package/dist/auth-password.js +60 -0
  67. package/dist/auth-password.js.map +1 -0
  68. package/dist/auth.d.ts +59 -0
  69. package/dist/auth.d.ts.map +1 -0
  70. package/dist/auth.js +146 -0
  71. package/dist/auth.js.map +1 -0
  72. package/dist/backend-internals.d.ts +35 -0
  73. package/dist/backend-internals.d.ts.map +1 -0
  74. package/dist/backend-internals.js +2 -0
  75. package/dist/backend-internals.js.map +1 -0
  76. package/dist/backend.d.ts +63 -0
  77. package/dist/backend.d.ts.map +1 -0
  78. package/dist/backend.js +59 -0
  79. package/dist/backend.js.map +1 -0
  80. package/dist/blueprint-generator.d.ts +21 -0
  81. package/dist/blueprint-generator.d.ts.map +1 -0
  82. package/dist/blueprint-generator.js +199 -0
  83. package/dist/blueprint-generator.js.map +1 -0
  84. package/dist/blueprint.d.ts +99 -0
  85. package/dist/blueprint.d.ts.map +1 -0
  86. package/dist/blueprint.js +257 -0
  87. package/dist/blueprint.js.map +1 -0
  88. package/dist/cli-skills.d.ts +16 -0
  89. package/dist/cli-skills.d.ts.map +1 -0
  90. package/dist/cli-skills.js +108 -0
  91. package/dist/cli-skills.js.map +1 -0
  92. package/dist/cli.d.ts +18 -0
  93. package/dist/cli.d.ts.map +1 -0
  94. package/dist/cli.js +205 -0
  95. package/dist/cli.js.map +1 -0
  96. package/dist/client/client.d.ts +53 -0
  97. package/dist/client/client.d.ts.map +1 -0
  98. package/dist/client/client.js +111 -0
  99. package/dist/client/client.js.map +1 -0
  100. package/dist/client/index.d.ts +4 -0
  101. package/dist/client/index.d.ts.map +1 -0
  102. package/dist/client/index.js +4 -0
  103. package/dist/client/index.js.map +1 -0
  104. package/dist/client/live-view.d.ts +49 -0
  105. package/dist/client/live-view.d.ts.map +1 -0
  106. package/dist/client/live-view.js +184 -0
  107. package/dist/client/live-view.js.map +1 -0
  108. package/dist/client/react.d.ts +4 -0
  109. package/dist/client/react.d.ts.map +1 -0
  110. package/dist/client/react.js +6 -0
  111. package/dist/client/react.js.map +1 -0
  112. package/dist/client/realtime.d.ts +54 -0
  113. package/dist/client/realtime.d.ts.map +1 -0
  114. package/dist/client/realtime.js +105 -0
  115. package/dist/client/realtime.js.map +1 -0
  116. package/dist/client/rest.d.ts +2 -0
  117. package/dist/client/rest.d.ts.map +1 -0
  118. package/dist/client/rest.js +2 -0
  119. package/dist/client/rest.js.map +1 -0
  120. package/dist/client/rpc-client.d.ts +38 -0
  121. package/dist/client/rpc-client.d.ts.map +1 -0
  122. package/dist/client/rpc-client.js +59 -0
  123. package/dist/client/rpc-client.js.map +1 -0
  124. package/dist/client/solid.d.ts +7 -0
  125. package/dist/client/solid.d.ts.map +1 -0
  126. package/dist/client/solid.js +21 -0
  127. package/dist/client/solid.js.map +1 -0
  128. package/dist/client/svelte.d.ts +6 -0
  129. package/dist/client/svelte.d.ts.map +1 -0
  130. package/dist/client/svelte.js +9 -0
  131. package/dist/client/svelte.js.map +1 -0
  132. package/dist/client/vue.d.ts +5 -0
  133. package/dist/client/vue.d.ts.map +1 -0
  134. package/dist/client/vue.js +11 -0
  135. package/dist/client/vue.js.map +1 -0
  136. package/dist/codegen.d.ts +36 -0
  137. package/dist/codegen.d.ts.map +1 -0
  138. package/dist/codegen.js +235 -0
  139. package/dist/codegen.js.map +1 -0
  140. package/dist/config.d.ts +129 -0
  141. package/dist/config.d.ts.map +1 -0
  142. package/dist/config.js +75 -0
  143. package/dist/config.js.map +1 -0
  144. package/dist/cron.d.ts +4 -0
  145. package/dist/cron.d.ts.map +1 -0
  146. package/dist/cron.js +3 -0
  147. package/dist/cron.js.map +1 -0
  148. package/dist/crud-operations.d.ts +43 -0
  149. package/dist/crud-operations.d.ts.map +1 -0
  150. package/dist/crud-operations.js +249 -0
  151. package/dist/crud-operations.js.map +1 -0
  152. package/dist/database/adapter.d.ts +26 -0
  153. package/dist/database/adapter.d.ts.map +1 -0
  154. package/dist/database/adapter.js +2 -0
  155. package/dist/database/adapter.js.map +1 -0
  156. package/dist/database/libsql.d.ts +3 -0
  157. package/dist/database/libsql.d.ts.map +1 -0
  158. package/dist/database/libsql.js +39 -0
  159. package/dist/database/libsql.js.map +1 -0
  160. package/dist/db.d.ts +15 -0
  161. package/dist/db.d.ts.map +1 -0
  162. package/dist/db.js +8 -0
  163. package/dist/db.js.map +1 -0
  164. package/dist/dev/binaries.d.ts +22 -0
  165. package/dist/dev/binaries.d.ts.map +1 -0
  166. package/dist/dev/binaries.js +119 -0
  167. package/dist/dev/binaries.js.map +1 -0
  168. package/dist/dev/env.d.ts +11 -0
  169. package/dist/dev/env.d.ts.map +1 -0
  170. package/dist/dev/env.js +71 -0
  171. package/dist/dev/env.js.map +1 -0
  172. package/dist/dev/index.d.ts +39 -0
  173. package/dist/dev/index.d.ts.map +1 -0
  174. package/dist/dev/index.js +273 -0
  175. package/dist/dev/index.js.map +1 -0
  176. package/dist/dev/processes.d.ts +37 -0
  177. package/dist/dev/processes.d.ts.map +1 -0
  178. package/dist/dev/processes.js +104 -0
  179. package/dist/dev/processes.js.map +1 -0
  180. package/dist/dev/push.d.ts +2 -0
  181. package/dist/dev/push.d.ts.map +1 -0
  182. package/dist/dev/push.js +30 -0
  183. package/dist/dev/push.js.map +1 -0
  184. package/dist/dialect.d.ts +17 -0
  185. package/dist/dialect.d.ts.map +1 -0
  186. package/dist/dialect.js +12 -0
  187. package/dist/dialect.js.map +1 -0
  188. package/dist/email/smtp.d.ts +20 -0
  189. package/dist/email/smtp.d.ts.map +1 -0
  190. package/dist/email/smtp.js +31 -0
  191. package/dist/email/smtp.js.map +1 -0
  192. package/dist/email.d.ts +26 -0
  193. package/dist/email.d.ts.map +1 -0
  194. package/dist/email.js +2 -0
  195. package/dist/email.js.map +1 -0
  196. package/dist/env-probe.d.ts +9 -0
  197. package/dist/env-probe.d.ts.map +1 -0
  198. package/dist/env-probe.js +72 -0
  199. package/dist/env-probe.js.map +1 -0
  200. package/dist/env.d.ts +62 -0
  201. package/dist/env.d.ts.map +1 -0
  202. package/dist/env.js +86 -0
  203. package/dist/env.js.map +1 -0
  204. package/dist/errors.d.ts +153 -0
  205. package/dist/errors.d.ts.map +1 -0
  206. package/dist/errors.js +106 -0
  207. package/dist/errors.js.map +1 -0
  208. package/dist/handler.d.ts +11 -0
  209. package/dist/handler.d.ts.map +1 -0
  210. package/dist/handler.js +21 -0
  211. package/dist/handler.js.map +1 -0
  212. package/dist/hosted-contract.d.ts +11 -0
  213. package/dist/hosted-contract.d.ts.map +1 -0
  214. package/dist/hosted-contract.js +50 -0
  215. package/dist/hosted-contract.js.map +1 -0
  216. package/dist/idempotency.d.ts +17 -0
  217. package/dist/idempotency.d.ts.map +1 -0
  218. package/dist/idempotency.js +65 -0
  219. package/dist/idempotency.js.map +1 -0
  220. package/dist/index.d.ts +41 -0
  221. package/dist/index.d.ts.map +1 -0
  222. package/dist/index.js +18 -0
  223. package/dist/index.js.map +1 -0
  224. package/dist/inspect.d.ts +15 -0
  225. package/dist/inspect.d.ts.map +1 -0
  226. package/dist/inspect.js +44 -0
  227. package/dist/inspect.js.map +1 -0
  228. package/dist/internal-tables.d.ts +1767 -0
  229. package/dist/internal-tables.d.ts.map +1 -0
  230. package/dist/internal-tables.js +114 -0
  231. package/dist/internal-tables.js.map +1 -0
  232. package/dist/jobs/cron.d.ts +15 -0
  233. package/dist/jobs/cron.d.ts.map +1 -0
  234. package/dist/jobs/cron.js +74 -0
  235. package/dist/jobs/cron.js.map +1 -0
  236. package/dist/jobs/define.d.ts +186 -0
  237. package/dist/jobs/define.d.ts.map +1 -0
  238. package/dist/jobs/define.js +99 -0
  239. package/dist/jobs/define.js.map +1 -0
  240. package/dist/jobs/index.d.ts +9 -0
  241. package/dist/jobs/index.d.ts.map +1 -0
  242. package/dist/jobs/index.js +7 -0
  243. package/dist/jobs/index.js.map +1 -0
  244. package/dist/jobs/queue.d.ts +13 -0
  245. package/dist/jobs/queue.d.ts.map +1 -0
  246. package/dist/jobs/queue.js +71 -0
  247. package/dist/jobs/queue.js.map +1 -0
  248. package/dist/jobs/slots.d.ts +30 -0
  249. package/dist/jobs/slots.d.ts.map +1 -0
  250. package/dist/jobs/slots.js +53 -0
  251. package/dist/jobs/slots.js.map +1 -0
  252. package/dist/jobs/worker.d.ts +45 -0
  253. package/dist/jobs/worker.d.ts.map +1 -0
  254. package/dist/jobs/worker.js +605 -0
  255. package/dist/jobs/worker.js.map +1 -0
  256. package/dist/lifecycle.d.ts +10 -0
  257. package/dist/lifecycle.d.ts.map +1 -0
  258. package/dist/lifecycle.js +37 -0
  259. package/dist/lifecycle.js.map +1 -0
  260. package/dist/list-query.d.ts +62 -0
  261. package/dist/list-query.d.ts.map +1 -0
  262. package/dist/list-query.js +190 -0
  263. package/dist/list-query.js.map +1 -0
  264. package/dist/live/apply.d.ts +13 -0
  265. package/dist/live/apply.d.ts.map +1 -0
  266. package/dist/live/apply.js +32 -0
  267. package/dist/live/apply.js.map +1 -0
  268. package/dist/live/index.d.ts +48 -0
  269. package/dist/live/index.d.ts.map +1 -0
  270. package/dist/live/index.js +108 -0
  271. package/dist/live/index.js.map +1 -0
  272. package/dist/live/protocol.d.ts +47 -0
  273. package/dist/live/protocol.d.ts.map +1 -0
  274. package/dist/live/protocol.js +12 -0
  275. package/dist/live/protocol.js.map +1 -0
  276. package/dist/live/sse.d.ts +22 -0
  277. package/dist/live/sse.d.ts.map +1 -0
  278. package/dist/live/sse.js +41 -0
  279. package/dist/live/sse.js.map +1 -0
  280. package/dist/logging.d.ts +8 -0
  281. package/dist/logging.d.ts.map +1 -0
  282. package/dist/logging.js +6 -0
  283. package/dist/logging.js.map +1 -0
  284. package/dist/manifest-diff.d.ts +6 -0
  285. package/dist/manifest-diff.d.ts.map +1 -0
  286. package/dist/manifest-diff.js +42 -0
  287. package/dist/manifest-diff.js.map +1 -0
  288. package/dist/manifest.d.ts +87 -0
  289. package/dist/manifest.d.ts.map +1 -0
  290. package/dist/manifest.js +237 -0
  291. package/dist/manifest.js.map +1 -0
  292. package/dist/messaging/email.d.ts +16 -0
  293. package/dist/messaging/email.d.ts.map +1 -0
  294. package/dist/messaging/email.js +8 -0
  295. package/dist/messaging/email.js.map +1 -0
  296. package/dist/messaging/index.d.ts +8 -0
  297. package/dist/messaging/index.d.ts.map +1 -0
  298. package/dist/messaging/index.js +4 -0
  299. package/dist/messaging/index.js.map +1 -0
  300. package/dist/messaging/journal.d.ts +4 -0
  301. package/dist/messaging/journal.d.ts.map +1 -0
  302. package/dist/messaging/journal.js +19 -0
  303. package/dist/messaging/journal.js.map +1 -0
  304. package/dist/messaging/runtime.d.ts +16 -0
  305. package/dist/messaging/runtime.d.ts.map +1 -0
  306. package/dist/messaging/runtime.js +213 -0
  307. package/dist/messaging/runtime.js.map +1 -0
  308. package/dist/messaging/standalone.d.ts +27 -0
  309. package/dist/messaging/standalone.d.ts.map +1 -0
  310. package/dist/messaging/standalone.js +18 -0
  311. package/dist/messaging/standalone.js.map +1 -0
  312. package/dist/messaging/telegram.d.ts +16 -0
  313. package/dist/messaging/telegram.d.ts.map +1 -0
  314. package/dist/messaging/telegram.js +5 -0
  315. package/dist/messaging/telegram.js.map +1 -0
  316. package/dist/messaging/types.d.ts +22 -0
  317. package/dist/messaging/types.d.ts.map +1 -0
  318. package/dist/messaging/types.js +17 -0
  319. package/dist/messaging/types.js.map +1 -0
  320. package/dist/platform.d.ts +25 -0
  321. package/dist/platform.d.ts.map +1 -0
  322. package/dist/platform.js +24 -0
  323. package/dist/platform.js.map +1 -0
  324. package/dist/provision-internals.d.ts +23 -0
  325. package/dist/provision-internals.d.ts.map +1 -0
  326. package/dist/provision-internals.js +7 -0
  327. package/dist/provision-internals.js.map +1 -0
  328. package/dist/provision-runtime.d.ts +6 -0
  329. package/dist/provision-runtime.d.ts.map +1 -0
  330. package/dist/provision-runtime.js +41 -0
  331. package/dist/provision-runtime.js.map +1 -0
  332. package/dist/provision-schema.d.ts +16 -0
  333. package/dist/provision-schema.d.ts.map +1 -0
  334. package/dist/provision-schema.js +59 -0
  335. package/dist/provision-schema.js.map +1 -0
  336. package/dist/provision.d.ts +8 -0
  337. package/dist/provision.d.ts.map +1 -0
  338. package/dist/provision.js +16 -0
  339. package/dist/provision.js.map +1 -0
  340. package/dist/query/api.d.ts +10 -0
  341. package/dist/query/api.d.ts.map +1 -0
  342. package/dist/query/api.js +7 -0
  343. package/dist/query/api.js.map +1 -0
  344. package/dist/query/client.d.ts +28 -0
  345. package/dist/query/client.d.ts.map +1 -0
  346. package/dist/query/client.js +87 -0
  347. package/dist/query/client.js.map +1 -0
  348. package/dist/query/fetch.d.ts +3 -0
  349. package/dist/query/fetch.d.ts.map +1 -0
  350. package/dist/query/fetch.js +4 -0
  351. package/dist/query/fetch.js.map +1 -0
  352. package/dist/query/index.d.ts +8 -0
  353. package/dist/query/index.d.ts.map +1 -0
  354. package/dist/query/index.js +4 -0
  355. package/dist/query/index.js.map +1 -0
  356. package/dist/query/infer.d.ts +25 -0
  357. package/dist/query/infer.d.ts.map +1 -0
  358. package/dist/query/infer.js +2 -0
  359. package/dist/query/infer.js.map +1 -0
  360. package/dist/query/react.d.ts +3 -0
  361. package/dist/query/react.d.ts.map +1 -0
  362. package/dist/query/react.js +2 -0
  363. package/dist/query/react.js.map +1 -0
  364. package/dist/query/realtime-flush.d.ts +26 -0
  365. package/dist/query/realtime-flush.d.ts.map +1 -0
  366. package/dist/query/realtime-flush.js +45 -0
  367. package/dist/query/realtime-flush.js.map +1 -0
  368. package/dist/query/realtime-stream.d.ts +3 -0
  369. package/dist/query/realtime-stream.d.ts.map +1 -0
  370. package/dist/query/realtime-stream.js +3 -0
  371. package/dist/query/realtime-stream.js.map +1 -0
  372. package/dist/query/realtime.d.ts +88 -0
  373. package/dist/query/realtime.d.ts.map +1 -0
  374. package/dist/query/realtime.js +255 -0
  375. package/dist/query/realtime.js.map +1 -0
  376. package/dist/rate-limit.d.ts +8 -0
  377. package/dist/rate-limit.d.ts.map +1 -0
  378. package/dist/rate-limit.js +46 -0
  379. package/dist/rate-limit.js.map +1 -0
  380. package/dist/readiness-probes.d.ts +4 -0
  381. package/dist/readiness-probes.d.ts.map +1 -0
  382. package/dist/readiness-probes.js +23 -0
  383. package/dist/readiness-probes.js.map +1 -0
  384. package/dist/readiness.d.ts +39 -0
  385. package/dist/readiness.d.ts.map +1 -0
  386. package/dist/readiness.js +72 -0
  387. package/dist/readiness.js.map +1 -0
  388. package/dist/realtime/facade.d.ts +20 -0
  389. package/dist/realtime/facade.d.ts.map +1 -0
  390. package/dist/realtime/facade.js +37 -0
  391. package/dist/realtime/facade.js.map +1 -0
  392. package/dist/realtime/filter.d.ts +42 -0
  393. package/dist/realtime/filter.d.ts.map +1 -0
  394. package/dist/realtime/filter.js +86 -0
  395. package/dist/realtime/filter.js.map +1 -0
  396. package/dist/realtime/heartbeat.d.ts +20 -0
  397. package/dist/realtime/heartbeat.d.ts.map +1 -0
  398. package/dist/realtime/heartbeat.js +64 -0
  399. package/dist/realtime/heartbeat.js.map +1 -0
  400. package/dist/realtime/publisher.d.ts +19 -0
  401. package/dist/realtime/publisher.d.ts.map +1 -0
  402. package/dist/realtime/publisher.js +8 -0
  403. package/dist/realtime/publisher.js.map +1 -0
  404. package/dist/runtime.d.ts +141 -0
  405. package/dist/runtime.d.ts.map +1 -0
  406. package/dist/runtime.js +463 -0
  407. package/dist/runtime.js.map +1 -0
  408. package/dist/schema-export.d.ts +2 -0
  409. package/dist/schema-export.d.ts.map +1 -0
  410. package/dist/schema-export.js +2 -0
  411. package/dist/schema-export.js.map +1 -0
  412. package/dist/scope.d.ts +4 -0
  413. package/dist/scope.d.ts.map +1 -0
  414. package/dist/scope.js +13 -0
  415. package/dist/scope.js.map +1 -0
  416. package/dist/standard-schema.d.ts +13 -0
  417. package/dist/standard-schema.d.ts.map +1 -0
  418. package/dist/standard-schema.js +34 -0
  419. package/dist/standard-schema.js.map +1 -0
  420. package/dist/start/auth-client.d.ts +11 -0
  421. package/dist/start/auth-client.d.ts.map +1 -0
  422. package/dist/start/auth-client.js +15 -0
  423. package/dist/start/auth-client.js.map +1 -0
  424. package/dist/start/create-start-worker.d.ts +16 -0
  425. package/dist/start/create-start-worker.d.ts.map +1 -0
  426. package/dist/start/create-start-worker.js +24 -0
  427. package/dist/start/create-start-worker.js.map +1 -0
  428. package/dist/start/index.d.ts +66 -0
  429. package/dist/start/index.d.ts.map +1 -0
  430. package/dist/start/index.js +49 -0
  431. package/dist/start/index.js.map +1 -0
  432. package/dist/start/isomorphic-fetch.d.ts +22 -0
  433. package/dist/start/isomorphic-fetch.d.ts.map +1 -0
  434. package/dist/start/isomorphic-fetch.js +49 -0
  435. package/dist/start/isomorphic-fetch.js.map +1 -0
  436. package/dist/start/server-entry.d.ts +7 -0
  437. package/dist/start/server-entry.d.ts.map +1 -0
  438. package/dist/start/server-entry.js +8 -0
  439. package/dist/start/server-entry.js.map +1 -0
  440. package/dist/storage/background.d.ts +3 -0
  441. package/dist/storage/background.d.ts.map +1 -0
  442. package/dist/storage/background.js +3 -0
  443. package/dist/storage/background.js.map +1 -0
  444. package/dist/storage/buckets.d.ts +78 -0
  445. package/dist/storage/buckets.d.ts.map +1 -0
  446. package/dist/storage/buckets.js +177 -0
  447. package/dist/storage/buckets.js.map +1 -0
  448. package/dist/storage/delete.d.ts +8 -0
  449. package/dist/storage/delete.d.ts.map +1 -0
  450. package/dist/storage/delete.js +10 -0
  451. package/dist/storage/delete.js.map +1 -0
  452. package/dist/storage/file-meta.d.ts +37 -0
  453. package/dist/storage/file-meta.d.ts.map +1 -0
  454. package/dist/storage/file-meta.js +166 -0
  455. package/dist/storage/file-meta.js.map +1 -0
  456. package/dist/storage/index.d.ts +28 -0
  457. package/dist/storage/index.d.ts.map +1 -0
  458. package/dist/storage/index.js +5 -0
  459. package/dist/storage/index.js.map +1 -0
  460. package/dist/storage/local.d.ts +15 -0
  461. package/dist/storage/local.d.ts.map +1 -0
  462. package/dist/storage/local.js +56 -0
  463. package/dist/storage/local.js.map +1 -0
  464. package/dist/storage/operations.d.ts +54 -0
  465. package/dist/storage/operations.d.ts.map +1 -0
  466. package/dist/storage/operations.js +212 -0
  467. package/dist/storage/operations.js.map +1 -0
  468. package/dist/storage/registry.d.ts +11 -0
  469. package/dist/storage/registry.d.ts.map +1 -0
  470. package/dist/storage/registry.js +23 -0
  471. package/dist/storage/registry.js.map +1 -0
  472. package/dist/storage/s3.d.ts +35 -0
  473. package/dist/storage/s3.d.ts.map +1 -0
  474. package/dist/storage/s3.js +125 -0
  475. package/dist/storage/s3.js.map +1 -0
  476. package/dist/storage/sigv4.d.ts +24 -0
  477. package/dist/storage/sigv4.d.ts.map +1 -0
  478. package/dist/storage/sigv4.js +107 -0
  479. package/dist/storage/sigv4.js.map +1 -0
  480. package/dist/storage/sweep.d.ts +9 -0
  481. package/dist/storage/sweep.d.ts.map +1 -0
  482. package/dist/storage/sweep.js +17 -0
  483. package/dist/storage/sweep.js.map +1 -0
  484. package/dist/sync/collection.d.ts +106 -0
  485. package/dist/sync/collection.d.ts.map +1 -0
  486. package/dist/sync/collection.js +258 -0
  487. package/dist/sync/collection.js.map +1 -0
  488. package/dist/sync/index.d.ts +8 -0
  489. package/dist/sync/index.d.ts.map +1 -0
  490. package/dist/sync/index.js +4 -0
  491. package/dist/sync/index.js.map +1 -0
  492. package/dist/sync/realtime-sync.d.ts +31 -0
  493. package/dist/sync/realtime-sync.d.ts.map +1 -0
  494. package/dist/sync/realtime-sync.js +46 -0
  495. package/dist/sync/realtime-sync.js.map +1 -0
  496. package/dist/sync/sync-client.d.ts +28 -0
  497. package/dist/sync/sync-client.d.ts.map +1 -0
  498. package/dist/sync/sync-client.js +52 -0
  499. package/dist/sync/sync-client.js.map +1 -0
  500. package/dist/sync/update-queue.d.ts +27 -0
  501. package/dist/sync/update-queue.d.ts.map +1 -0
  502. package/dist/sync/update-queue.js +66 -0
  503. package/dist/sync/update-queue.js.map +1 -0
  504. package/dist/testing/auth.d.ts +85 -0
  505. package/dist/testing/auth.d.ts.map +1 -0
  506. package/dist/testing/auth.js +140 -0
  507. package/dist/testing/auth.js.map +1 -0
  508. package/dist/testing/client.d.ts +6 -0
  509. package/dist/testing/client.d.ts.map +1 -0
  510. package/dist/testing/client.js +9 -0
  511. package/dist/testing/client.js.map +1 -0
  512. package/dist/testing/database.d.ts +6 -0
  513. package/dist/testing/database.d.ts.map +1 -0
  514. package/dist/testing/database.js +8 -0
  515. package/dist/testing/database.js.map +1 -0
  516. package/dist/testing/email.d.ts +15 -0
  517. package/dist/testing/email.d.ts.map +1 -0
  518. package/dist/testing/email.js +32 -0
  519. package/dist/testing/email.js.map +1 -0
  520. package/dist/testing/fixture.d.ts +51 -0
  521. package/dist/testing/fixture.d.ts.map +1 -0
  522. package/dist/testing/fixture.js +177 -0
  523. package/dist/testing/fixture.js.map +1 -0
  524. package/dist/testing/jobs.d.ts +40 -0
  525. package/dist/testing/jobs.d.ts.map +1 -0
  526. package/dist/testing/jobs.js +76 -0
  527. package/dist/testing/jobs.js.map +1 -0
  528. package/dist/testing/logs.d.ts +18 -0
  529. package/dist/testing/logs.d.ts.map +1 -0
  530. package/dist/testing/logs.js +53 -0
  531. package/dist/testing/logs.js.map +1 -0
  532. package/dist/testing/messaging.d.ts +21 -0
  533. package/dist/testing/messaging.d.ts.map +1 -0
  534. package/dist/testing/messaging.js +34 -0
  535. package/dist/testing/messaging.js.map +1 -0
  536. package/dist/testing/storage.d.ts +7 -0
  537. package/dist/testing/storage.d.ts.map +1 -0
  538. package/dist/testing/storage.js +29 -0
  539. package/dist/testing/storage.js.map +1 -0
  540. package/dist/testing/workers-fakes.d.ts +17 -0
  541. package/dist/testing/workers-fakes.d.ts.map +1 -0
  542. package/dist/testing/workers-fakes.js +98 -0
  543. package/dist/testing/workers-fakes.js.map +1 -0
  544. package/dist/testing.d.ts +12 -0
  545. package/dist/testing.d.ts.map +1 -0
  546. package/dist/testing.js +5 -0
  547. package/dist/testing.js.map +1 -0
  548. package/dist/typeid.d.ts +46 -0
  549. package/dist/typeid.d.ts.map +1 -0
  550. package/dist/typeid.js +130 -0
  551. package/dist/typeid.js.map +1 -0
  552. package/dist/vite.d.ts +26 -0
  553. package/dist/vite.d.ts.map +1 -0
  554. package/dist/vite.js +100 -0
  555. package/dist/vite.js.map +1 -0
  556. package/dist/worker-plan.d.ts +37 -0
  557. package/dist/worker-plan.d.ts.map +1 -0
  558. package/dist/worker-plan.js +63 -0
  559. package/dist/worker-plan.js.map +1 -0
  560. package/dist/workers/app.d.ts +19 -0
  561. package/dist/workers/app.d.ts.map +1 -0
  562. package/dist/workers/app.js +56 -0
  563. package/dist/workers/app.js.map +1 -0
  564. package/dist/workers/entry.d.ts +7 -0
  565. package/dist/workers/entry.d.ts.map +1 -0
  566. package/dist/workers/entry.js +8 -0
  567. package/dist/workers/entry.js.map +1 -0
  568. package/dist/workers/index.d.ts +23 -0
  569. package/dist/workers/index.d.ts.map +1 -0
  570. package/dist/workers/index.js +39 -0
  571. package/dist/workers/index.js.map +1 -0
  572. package/dist/workers/r2.d.ts +24 -0
  573. package/dist/workers/r2.d.ts.map +1 -0
  574. package/dist/workers/r2.js +76 -0
  575. package/dist/workers/r2.js.map +1 -0
  576. package/dist/workers/rate-limiter.d.ts +9 -0
  577. package/dist/workers/rate-limiter.d.ts.map +1 -0
  578. package/dist/workers/rate-limiter.js +22 -0
  579. package/dist/workers/rate-limiter.js.map +1 -0
  580. package/dist/workers/realtime-hub.d.ts +20 -0
  581. package/dist/workers/realtime-hub.d.ts.map +1 -0
  582. package/dist/workers/realtime-hub.js +117 -0
  583. package/dist/workers/realtime-hub.js.map +1 -0
  584. package/dist/workers/registry.d.ts +13 -0
  585. package/dist/workers/registry.d.ts.map +1 -0
  586. package/dist/workers/registry.js +19 -0
  587. package/dist/workers/registry.js.map +1 -0
  588. package/dist/workers/scheduler.d.ts +13 -0
  589. package/dist/workers/scheduler.d.ts.map +1 -0
  590. package/dist/workers/scheduler.js +71 -0
  591. package/dist/workers/scheduler.js.map +1 -0
  592. package/dist/workers/types.d.ts +55 -0
  593. package/dist/workers/types.d.ts.map +1 -0
  594. package/dist/workers/types.js +4 -0
  595. package/dist/workers/types.js.map +1 -0
  596. package/dist/workers/wrangler.d.ts +62 -0
  597. package/dist/workers/wrangler.d.ts.map +1 -0
  598. package/dist/workers/wrangler.js +90 -0
  599. package/dist/workers/wrangler.js.map +1 -0
  600. package/package.json +286 -0
  601. package/skills/creating-workerstack-apps/SKILL.md +45 -0
  602. package/skills/creating-workerstack-apps/agents/openai.yaml +4 -0
  603. package/skills/creating-workerstack-apps/references/application-structure.md +219 -0
  604. package/skills/creating-workerstack-apps/references/runtime-integrations.md +96 -0
  605. package/skills/creating-workerstack-apps/references/verification.md +29 -0
@@ -0,0 +1 @@
1
+ {"version":3,"file":"list-spec.js","sourceRoot":"","sources":["../../src/api/list-spec.ts"],"names":[],"mappings":"AAGA,OAAO,EAAE,eAAe,EAAE,YAAY,EAAE,MAAM,aAAa,CAAA;AAK3D,OAAO,EAAE,WAAW,EAAE,iBAAiB,EAAE,MAAM,eAAe,CAAA;AAC9D,OAAO,EAAE,oBAAoB,EAAE,MAAM,qBAAqB,CAAA;AAY1D;;;;;;;;;;;;;;;;;;GAkBG;AACH,MAAM,UAAU,QAAQ,CACtB,KAAa,EACb,UAA2B,EAAE;IAE7B,MAAM,WAAW,GAAG,OAAO,CAAC,WAAW,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,KAAK,EAAE,KAAK,EAAE,CAAA;IACzE,MAAM,eAAe,GAAG,OAAO,CAAC,QAAQ,IAAI,CAAC,WAAW,CAAC,MAAM,CAAC,CAAA;IAEhE,MAAM,WAAW,GAAG,oBAAoB,CAAC,KAAK,EAAE;QAC9C,iBAAiB,EAAE,OAAO,CAAC,UAAU,IAAI,EAAE;QAC3C,eAAe;KAChB,CAGA,CAAA;IAED,0EAA0E;IAC1E,4EAA4E;IAC5E,wDAAwD;IACxD,MAAM,MAAM,GAAG;QACb,iBAAiB,EAAE,OAAO,CAAC,UAAU,IAAI,EAAE;QAC3C,eAAe;QACf,iBAAiB,EAAE,OAAO,CAAC,UAAU,IAAI,EAAE;QAC3C,WAAW;KACsB,CAAA;IAEnC,MAAM,QAAQ,GAAG,eAAe,CAAC,KAAK,CAAC,CAAC,EAAE,CAAA;IAC1C,IAAI,CAAC,QAAQ,EAAE,CAAC;QACd,MAAM,IAAI,KAAK,CACb,4DAA4D,YAAY,CAAC,KAAK,CAAC,GAAG,CACnF,CAAA;IACH,CAAC;IAED,MAAM,OAAO,GAAG,KAAK,EAAE,cAGtB,EAA+C,EAAE;QAChD,MAAM,MAAM,GAAG,iBAAiB,CAAC,cAAc,CAAC,KAAK,IAAI,EAAE,EAAE,MAAM,CAAC,CAAA;QACpE,OAAO,WAAW,CAChB,cAAc,CAAC,OAAO,CAAC,EAAW,EAClC,KAAc,EACd,MAAM,EACN,MAAM,EACN,QAAQ,CACT,CAAA;IACH,CAAC,CAAA;IAED,OAAO,EAAE,KAAK,EAAE,WAAW,EAAE,OAAO,EAAE,CAAA;AACxC,CAAC","sourcesContent":["import type { Table } from 'drizzle-orm'\nimport type * as v from 'valibot'\n\nimport { getTableColumns, getTableName } from 'drizzle-orm'\n\nimport type { ResolvedTableAccess } from '../access'\nimport type { ListParamsInput, ListResult } from '../list-query'\n\nimport { executeList, resolveListParams } from '../list-query'\nimport { buildListInputSchema } from './list-input-schema'\n\nexport type ListSpecOptions = {\n /** Columns a caller may filter on. Others are rejected by the schema. */\n filterable?: readonly string[]\n /** Columns a caller may sort on. Defaults to the default sort column. */\n sortable?: readonly string[]\n defaultSort?: { column: string; order: 'asc' | 'desc' }\n /** Columns the `q` parameter searches. */\n searchable?: readonly string[]\n}\n\n/**\n * The input schema and handler of a list endpoint, with the same filter, sort,\n * cursor, and count contract that the generated CRUD list uses.\n *\n * The caller applies both to its own base procedure:\n *\n * ```ts\n * const logsList = listSpec(appLogs, { filterable: ['level'] })\n * getLogs: adminProcedure.input(logsList.input).handler(logsList.handler)\n * ```\n *\n * The two parts are returned separately rather than as a finished procedure,\n * because a procedure built here would have to receive the builder as a\n * generic parameter. TypeScript resolves a method call on a generic parameter\n * through its constraint, which erases the input schema and the row type. With\n * this shape the builder stays concrete at the call site and keeps both.\n *\n * It reads no `access` configuration: the base procedure carries the policy.\n */\nexport function listSpec<TTable extends Table>(\n table: TTable,\n options: ListSpecOptions = {},\n) {\n const defaultSort = options.defaultSort ?? { column: 'id', order: 'asc' }\n const sortableColumns = options.sortable ?? [defaultSort.column]\n\n const inputSchema = buildListInputSchema(table, {\n filterableColumns: options.filterable ?? [],\n sortableColumns,\n }) as unknown as v.GenericSchema<\n ListParamsInput | undefined,\n ListParamsInput | undefined\n >\n\n // `executeList` reads its policy from a resolved access record. This spec\n // declares that policy at the call site instead, because the base procedure\n // — not `access.ts` — carries the authorization for it.\n const access = {\n filterableColumns: options.filterable ?? [],\n sortableColumns,\n searchableColumns: options.searchable ?? [],\n defaultSort,\n } as unknown as ResolvedTableAccess\n\n const idColumn = getTableColumns(table).id\n if (!idColumn) {\n throw new Error(\n `[workerstack] listSpec requires an \"id\" column on table \"${getTableName(table)}\"`,\n )\n }\n\n const handler = async (handlerOptions: {\n context: { db: unknown }\n input: ListParamsInput | undefined\n }): Promise<ListResult<TTable['$inferSelect']>> => {\n const params = resolveListParams(handlerOptions.input ?? {}, access)\n return executeList<TTable['$inferSelect']>(\n handlerOptions.context.db as never,\n table as never,\n access,\n params,\n idColumn,\n )\n }\n\n return { input: inputSchema, handler }\n}\n"]}
@@ -0,0 +1,14 @@
1
+ /**
2
+ * Server-side membership for a live view: does one record belong to a view,
3
+ * given that view's filters?
4
+ *
5
+ * The rule is evaluated per streamed record, so a change is routed to the
6
+ * views that want it without asking the database.
7
+ */
8
+ /**
9
+ * Workerstack's filter contract — a scalar is `=`, an array is `IN`, `null` is
10
+ * `IS NULL` — evaluated against one record. The string `'null'` means the same
11
+ * as `null`, because a query string cannot carry a real null.
12
+ */
13
+ export declare function matchesLiveFilters(record: Record<string, unknown>, filters: Record<string, unknown> | undefined): boolean;
14
+ //# sourceMappingURL=live-view.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"live-view.d.ts","sourceRoot":"","sources":["../../src/api/live-view.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAYH;;;;GAIG;AACH,wBAAgB,kBAAkB,CAChC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAC/B,OAAO,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,SAAS,GAC3C,OAAO,CAeT"}
@@ -0,0 +1,42 @@
1
+ /**
2
+ * Server-side membership for a live view: does one record belong to a view,
3
+ * given that view's filters?
4
+ *
5
+ * The rule is evaluated per streamed record, so a change is routed to the
6
+ * views that want it without asking the database.
7
+ */
8
+ /** Same value semantics as list filters: dates by time, the rest by identity. */
9
+ function sameValue(a, b) {
10
+ if (a instanceof Date && b instanceof Date)
11
+ return a.getTime() === b.getTime();
12
+ return a === b;
13
+ }
14
+ function isNullish(value) {
15
+ return value === null || value === undefined;
16
+ }
17
+ /**
18
+ * Workerstack's filter contract — a scalar is `=`, an array is `IN`, `null` is
19
+ * `IS NULL` — evaluated against one record. The string `'null'` means the same
20
+ * as `null`, because a query string cannot carry a real null.
21
+ */
22
+ export function matchesLiveFilters(record, filters) {
23
+ for (const [column, expected] of Object.entries(filters ?? {})) {
24
+ if (expected === undefined)
25
+ continue;
26
+ const actual = record[column];
27
+ if (expected === null || expected === 'null') {
28
+ if (!isNullish(actual))
29
+ return false;
30
+ continue;
31
+ }
32
+ if (Array.isArray(expected)) {
33
+ if (!expected.some((value) => sameValue(value, actual)))
34
+ return false;
35
+ continue;
36
+ }
37
+ if (!sameValue(expected, actual))
38
+ return false;
39
+ }
40
+ return true;
41
+ }
42
+ //# sourceMappingURL=live-view.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"live-view.js","sourceRoot":"","sources":["../../src/api/live-view.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,iFAAiF;AACjF,SAAS,SAAS,CAAC,CAAU,EAAE,CAAU;IACvC,IAAI,CAAC,YAAY,IAAI,IAAI,CAAC,YAAY,IAAI;QAAE,OAAO,CAAC,CAAC,OAAO,EAAE,KAAK,CAAC,CAAC,OAAO,EAAE,CAAA;IAC9E,OAAO,CAAC,KAAK,CAAC,CAAA;AAChB,CAAC;AAED,SAAS,SAAS,CAAC,KAAc;IAC/B,OAAO,KAAK,KAAK,IAAI,IAAI,KAAK,KAAK,SAAS,CAAA;AAC9C,CAAC;AAED;;;;GAIG;AACH,MAAM,UAAU,kBAAkB,CAChC,MAA+B,EAC/B,OAA4C;IAE5C,KAAK,MAAM,CAAC,MAAM,EAAE,QAAQ,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,OAAO,IAAI,EAAE,CAAC,EAAE,CAAC;QAC/D,IAAI,QAAQ,KAAK,SAAS;YAAE,SAAQ;QACpC,MAAM,MAAM,GAAG,MAAM,CAAC,MAAM,CAAC,CAAA;QAC7B,IAAI,QAAQ,KAAK,IAAI,IAAI,QAAQ,KAAK,MAAM,EAAE,CAAC;YAC7C,IAAI,CAAC,SAAS,CAAC,MAAM,CAAC;gBAAE,OAAO,KAAK,CAAA;YACpC,SAAQ;QACV,CAAC;QACD,IAAI,KAAK,CAAC,OAAO,CAAC,QAAQ,CAAC,EAAE,CAAC;YAC5B,IAAI,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC,KAAK,EAAE,EAAE,CAAC,SAAS,CAAC,KAAK,EAAE,MAAM,CAAC,CAAC;gBAAE,OAAO,KAAK,CAAA;YACrE,SAAQ;QACV,CAAC;QACD,IAAI,CAAC,SAAS,CAAC,QAAQ,EAAE,MAAM,CAAC;YAAE,OAAO,KAAK,CAAA;IAChD,CAAC;IACD,OAAO,IAAI,CAAA;AACb,CAAC","sourcesContent":["/**\n * Server-side membership for a live view: does one record belong to a view,\n * given that view's filters?\n *\n * The rule is evaluated per streamed record, so a change is routed to the\n * views that want it without asking the database.\n */\n\n/** Same value semantics as list filters: dates by time, the rest by identity. */\nfunction sameValue(a: unknown, b: unknown): boolean {\n if (a instanceof Date && b instanceof Date) return a.getTime() === b.getTime()\n return a === b\n}\n\nfunction isNullish(value: unknown): boolean {\n return value === null || value === undefined\n}\n\n/**\n * Workerstack's filter contract — a scalar is `=`, an array is `IN`, `null` is\n * `IS NULL` — evaluated against one record. The string `'null'` means the same\n * as `null`, because a query string cannot carry a real null.\n */\nexport function matchesLiveFilters(\n record: Record<string, unknown>,\n filters: Record<string, unknown> | undefined,\n): boolean {\n for (const [column, expected] of Object.entries(filters ?? {})) {\n if (expected === undefined) continue\n const actual = record[column]\n if (expected === null || expected === 'null') {\n if (!isNullish(actual)) return false\n continue\n }\n if (Array.isArray(expected)) {\n if (!expected.some((value) => sameValue(value, actual))) return false\n continue\n }\n if (!sameValue(expected, actual)) return false\n }\n return true\n}\n"]}
@@ -0,0 +1,40 @@
1
+ import type { LiveDeltaFrame } from '../live/protocol.js';
2
+ import type { RealtimeChange } from '../realtime/publisher.js';
3
+ /**
4
+ * The server-side state of one live-view connection: which rows the client
5
+ * holds, in view order, and whether rows exist below the window.
6
+ *
7
+ * The window is what lets the server place a row for the client (`afterId`)
8
+ * instead of making the browser repeat `ORDER BY`. It is also what makes a
9
+ * removal from a truncated view ask for a fresh snapshot instead of silently
10
+ * shrinking the view.
11
+ *
12
+ * Ordering follows `buildOrderBy` in `../list-query`: the sort column first,
13
+ * then `id`, both in the query's direction. Values are compared in the process
14
+ * on raw column values. That is exact for numbers, dates, and booleans, and
15
+ * matches the database for ordinary text. A collation that differs from
16
+ * code-unit order, or a NULLS rule other than "nulls first", can place a row
17
+ * inside the window differently from the database.
18
+ */
19
+ export type LiveWindowOptions = {
20
+ sort: string;
21
+ order: 'asc' | 'desc';
22
+ limit: number;
23
+ filters?: Record<string, unknown>;
24
+ };
25
+ export type LiveWindowResult = {
26
+ type: 'none';
27
+ } | {
28
+ type: 'frames';
29
+ frames: LiveDeltaFrame[];
30
+ } | {
31
+ type: 'resnapshot';
32
+ };
33
+ export type LiveWindow = {
34
+ /** Adopt a query result as the current view. */
35
+ reset: (items: Record<string, unknown>[], hasMore: boolean) => void;
36
+ /** What this change means for this view. */
37
+ apply: (change: RealtimeChange) => LiveWindowResult;
38
+ };
39
+ export declare function createLiveWindow(options: LiveWindowOptions): LiveWindow;
40
+ //# sourceMappingURL=live-window.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"live-window.d.ts","sourceRoot":"","sources":["../../src/api/live-window.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,kBAAkB,CAAA;AACtD,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,uBAAuB,CAAA;AAI3D;;;;;;;;;;;;;;;GAeG;AAEH,MAAM,MAAM,iBAAiB,GAAG;IAC9B,IAAI,EAAE,MAAM,CAAA;IACZ,KAAK,EAAE,KAAK,GAAG,MAAM,CAAA;IACrB,KAAK,EAAE,MAAM,CAAA;IACb,OAAO,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAA;CAClC,CAAA;AAED,MAAM,MAAM,gBAAgB,GACxB;IAAE,IAAI,EAAE,MAAM,CAAA;CAAE,GAChB;IAAE,IAAI,EAAE,QAAQ,CAAC;IAAC,MAAM,EAAE,cAAc,EAAE,CAAA;CAAE,GAC5C;IAAE,IAAI,EAAE,YAAY,CAAA;CAAE,CAAA;AAE1B,MAAM,MAAM,UAAU,GAAG;IACvB,gDAAgD;IAChD,KAAK,EAAE,CAAC,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAAE,EAAE,OAAO,EAAE,OAAO,KAAK,IAAI,CAAA;IACnE,4CAA4C;IAC5C,KAAK,EAAE,CAAC,MAAM,EAAE,cAAc,KAAK,gBAAgB,CAAA;CACpD,CAAA;AAmBD,wBAAgB,gBAAgB,CAAC,OAAO,EAAE,iBAAiB,GAAG,UAAU,CAgFvE"}
@@ -0,0 +1,93 @@
1
+ import { matchesLiveFilters } from './live-view.js';
2
+ function compareValues(a, b) {
3
+ if (a === b)
4
+ return 0;
5
+ const aNull = a === null || a === undefined;
6
+ const bNull = b === null || b === undefined;
7
+ if (aNull || bNull)
8
+ return aNull ? (bNull ? 0 : -1) : 1;
9
+ if (a instanceof Date && b instanceof Date)
10
+ return a.getTime() - b.getTime();
11
+ if (typeof a === 'number' && typeof b === 'number')
12
+ return a - b;
13
+ if (typeof a === 'boolean' && typeof b === 'boolean') {
14
+ return Number(a) - Number(b);
15
+ }
16
+ const left = String(a);
17
+ const right = String(b);
18
+ return left < right ? -1 : left > right ? 1 : 0;
19
+ }
20
+ export function createLiveWindow(options) {
21
+ const direction = options.order === 'desc' ? -1 : 1;
22
+ let rows = [];
23
+ let hasMore = false;
24
+ const compareRows = (a, b) => direction * (compareValues(a.key, b.key) || compareValues(a.id, b.id));
25
+ const rowOf = (record) => ({
26
+ id: String(record.id),
27
+ key: record[options.sort],
28
+ });
29
+ /** Where this row belongs among rows that are already in order. */
30
+ const placeOf = (row) => {
31
+ const index = rows.findIndex((current) => compareRows(row, current) < 0);
32
+ return index === -1 ? rows.length : index;
33
+ };
34
+ return {
35
+ reset(items, nextHasMore) {
36
+ rows = items.map(rowOf);
37
+ hasMore = nextHasMore;
38
+ },
39
+ apply(change) {
40
+ const id = String(change.record.id);
41
+ const metadata = change.operationId
42
+ ? { operationId: change.operationId }
43
+ : {};
44
+ const index = rows.findIndex((row) => row.id === id);
45
+ const held = index !== -1;
46
+ // The row left the view: deleted, or no longer a match for the filters.
47
+ if (change.action === 'delete' ||
48
+ !matchesLiveFilters(change.record, options.filters)) {
49
+ if (!held)
50
+ return { type: 'none' };
51
+ rows.splice(index, 1);
52
+ // A row from below the window must take the free place, and only the
53
+ // database knows which one.
54
+ if (hasMore)
55
+ return { type: 'resnapshot' };
56
+ return {
57
+ type: 'frames',
58
+ frames: [{ type: 'remove', id, ...metadata }],
59
+ };
60
+ }
61
+ if (held)
62
+ rows.splice(index, 1);
63
+ const row = rowOf(change.record);
64
+ const place = placeOf(row);
65
+ if (place >= options.limit) {
66
+ // It sorts below the window. If the client holds it, it moved out.
67
+ if (!held)
68
+ return { type: 'none' };
69
+ hasMore = true;
70
+ return {
71
+ type: 'frames',
72
+ frames: [{ type: 'remove', id, ...metadata }],
73
+ };
74
+ }
75
+ rows.splice(place, 0, row);
76
+ const frames = [
77
+ {
78
+ type: 'upsert',
79
+ record: change.record,
80
+ afterId: place === 0 ? null : rows[place - 1].id,
81
+ ...metadata,
82
+ },
83
+ ];
84
+ if (rows.length > options.limit) {
85
+ const evicted = rows.pop();
86
+ hasMore = true;
87
+ frames.push({ type: 'remove', id: evicted.id, ...metadata });
88
+ }
89
+ return { type: 'frames', frames };
90
+ },
91
+ };
92
+ }
93
+ //# sourceMappingURL=live-window.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"live-window.js","sourceRoot":"","sources":["../../src/api/live-window.ts"],"names":[],"mappings":"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","sourcesContent":["import type { LiveDeltaFrame } from '../live/protocol'\nimport type { RealtimeChange } from '../realtime/publisher'\n\nimport { matchesLiveFilters } from './live-view'\n\n/**\n * The server-side state of one live-view connection: which rows the client\n * holds, in view order, and whether rows exist below the window.\n *\n * The window is what lets the server place a row for the client (`afterId`)\n * instead of making the browser repeat `ORDER BY`. It is also what makes a\n * removal from a truncated view ask for a fresh snapshot instead of silently\n * shrinking the view.\n *\n * Ordering follows `buildOrderBy` in `../list-query`: the sort column first,\n * then `id`, both in the query's direction. Values are compared in the process\n * on raw column values. That is exact for numbers, dates, and booleans, and\n * matches the database for ordinary text. A collation that differs from\n * code-unit order, or a NULLS rule other than \"nulls first\", can place a row\n * inside the window differently from the database.\n */\n\nexport type LiveWindowOptions = {\n sort: string\n order: 'asc' | 'desc'\n limit: number\n filters?: Record<string, unknown>\n}\n\nexport type LiveWindowResult =\n | { type: 'none' }\n | { type: 'frames'; frames: LiveDeltaFrame[] }\n | { type: 'resnapshot' }\n\nexport type LiveWindow = {\n /** Adopt a query result as the current view. */\n reset: (items: Record<string, unknown>[], hasMore: boolean) => void\n /** What this change means for this view. */\n apply: (change: RealtimeChange) => LiveWindowResult\n}\n\ntype WindowRow = { id: string; key: unknown }\n\nfunction compareValues(a: unknown, b: unknown): number {\n if (a === b) return 0\n const aNull = a === null || a === undefined\n const bNull = b === null || b === undefined\n if (aNull || bNull) return aNull ? (bNull ? 0 : -1) : 1\n if (a instanceof Date && b instanceof Date) return a.getTime() - b.getTime()\n if (typeof a === 'number' && typeof b === 'number') return a - b\n if (typeof a === 'boolean' && typeof b === 'boolean') {\n return Number(a) - Number(b)\n }\n const left = String(a)\n const right = String(b)\n return left < right ? -1 : left > right ? 1 : 0\n}\n\nexport function createLiveWindow(options: LiveWindowOptions): LiveWindow {\n const direction = options.order === 'desc' ? -1 : 1\n let rows: WindowRow[] = []\n let hasMore = false\n\n const compareRows = (a: WindowRow, b: WindowRow): number =>\n direction * (compareValues(a.key, b.key) || compareValues(a.id, b.id))\n\n const rowOf = (record: Record<string, unknown>): WindowRow => ({\n id: String(record.id),\n key: record[options.sort],\n })\n\n /** Where this row belongs among rows that are already in order. */\n const placeOf = (row: WindowRow): number => {\n const index = rows.findIndex((current) => compareRows(row, current) < 0)\n return index === -1 ? rows.length : index\n }\n\n return {\n reset(items, nextHasMore) {\n rows = items.map(rowOf)\n hasMore = nextHasMore\n },\n\n apply(change) {\n const id = String(change.record.id)\n const metadata = change.operationId\n ? { operationId: change.operationId }\n : {}\n const index = rows.findIndex((row) => row.id === id)\n const held = index !== -1\n\n // The row left the view: deleted, or no longer a match for the filters.\n if (\n change.action === 'delete' ||\n !matchesLiveFilters(change.record, options.filters)\n ) {\n if (!held) return { type: 'none' }\n rows.splice(index, 1)\n // A row from below the window must take the free place, and only the\n // database knows which one.\n if (hasMore) return { type: 'resnapshot' }\n return {\n type: 'frames',\n frames: [{ type: 'remove', id, ...metadata }],\n }\n }\n\n if (held) rows.splice(index, 1)\n const row = rowOf(change.record)\n const place = placeOf(row)\n\n if (place >= options.limit) {\n // It sorts below the window. If the client holds it, it moved out.\n if (!held) return { type: 'none' }\n hasMore = true\n return {\n type: 'frames',\n frames: [{ type: 'remove', id, ...metadata }],\n }\n }\n\n rows.splice(place, 0, row)\n const frames: LiveDeltaFrame[] = [\n {\n type: 'upsert',\n record: change.record,\n afterId: place === 0 ? null : rows[place - 1]!.id,\n ...metadata,\n },\n ]\n if (rows.length > options.limit) {\n const evicted = rows.pop()!\n hasMore = true\n frames.push({ type: 'remove', id: evicted.id, ...metadata })\n }\n return { type: 'frames', frames }\n },\n }\n}\n"]}
@@ -0,0 +1,6 @@
1
+ export interface MergeOpenAPISpecsOptions {
2
+ nativeSpec: Record<string, any>;
3
+ authSpec?: Record<string, any>;
4
+ }
5
+ export declare function mergeOpenAPISpecs(options: MergeOpenAPISpecsOptions): Record<string, any>;
6
+ //# sourceMappingURL=openapi.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"openapi.d.ts","sourceRoot":"","sources":["../../src/api/openapi.ts"],"names":[],"mappings":"AAUA,MAAM,WAAW,wBAAwB;IACvC,UAAU,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAAA;IAC/B,QAAQ,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAAA;CAC/B;AAED,wBAAgB,iBAAiB,CAC/B,OAAO,EAAE,wBAAwB,GAChC,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAsKrB"}
@@ -0,0 +1,146 @@
1
+ const HTTP_METHODS = new Set([
2
+ 'GET',
3
+ 'POST',
4
+ 'PUT',
5
+ 'PATCH',
6
+ 'DELETE',
7
+ 'HEAD',
8
+ 'OPTIONS',
9
+ ]);
10
+ export function mergeOpenAPISpecs(options) {
11
+ const { nativeSpec, authSpec } = options;
12
+ const merged = {
13
+ openapi: nativeSpec.openapi || authSpec?.openapi || '3.1.0',
14
+ info: {
15
+ title: 'Workerstack API',
16
+ version: '1.0.0',
17
+ ...nativeSpec.info,
18
+ },
19
+ paths: JSON.parse(JSON.stringify(nativeSpec.paths || {})),
20
+ components: {},
21
+ security: [...(nativeSpec.security || [])],
22
+ tags: [...(nativeSpec.tags || [])],
23
+ };
24
+ if (authSpec) {
25
+ // Merge paths and check for overwrite collisions
26
+ if (authSpec.paths && typeof authSpec.paths === 'object') {
27
+ for (const [routePath, authPathItem] of Object.entries(authSpec.paths)) {
28
+ if (!authPathItem || typeof authPathItem !== 'object')
29
+ continue;
30
+ const clonedPathItem = JSON.parse(JSON.stringify(authPathItem));
31
+ // Normalize tags for Better Auth operations (replace generic "Default" with "Auth")
32
+ if (routePath.startsWith('/api/auth')) {
33
+ for (const [methodKey, operation] of Object.entries(clonedPathItem)) {
34
+ if (HTTP_METHODS.has(methodKey.toUpperCase()) &&
35
+ operation &&
36
+ typeof operation === 'object') {
37
+ if (Array.isArray(operation.tags)) {
38
+ operation.tags = operation.tags.map((t) => t === 'Default' ? 'Auth' : t);
39
+ if (!operation.tags.includes('Auth')) {
40
+ operation.tags.unshift('Auth');
41
+ }
42
+ }
43
+ else {
44
+ operation.tags = ['Auth'];
45
+ }
46
+ }
47
+ }
48
+ }
49
+ if (!(routePath in merged.paths)) {
50
+ merged.paths[routePath] = clonedPathItem;
51
+ }
52
+ else {
53
+ const existingPathItem = merged.paths[routePath];
54
+ const incomingPathItem = clonedPathItem;
55
+ for (const [key, authVal] of Object.entries(incomingPathItem)) {
56
+ const upperKey = key.toUpperCase();
57
+ const isOperation = HTTP_METHODS.has(upperKey);
58
+ if (key in existingPathItem) {
59
+ const existingVal = existingPathItem[key];
60
+ if (JSON.stringify(existingVal) !== JSON.stringify(authVal)) {
61
+ if (isOperation) {
62
+ throw new Error(`[workerstack] OpenAPI path overwrite collision: operation "${upperKey} ${routePath}"`);
63
+ }
64
+ else {
65
+ throw new Error(`[workerstack] OpenAPI path property collision on "${routePath}": key "${key}"`);
66
+ }
67
+ }
68
+ }
69
+ else {
70
+ existingPathItem[key] = JSON.parse(JSON.stringify(authVal));
71
+ }
72
+ }
73
+ }
74
+ }
75
+ }
76
+ // Merge security metadata
77
+ if (Array.isArray(authSpec.security)) {
78
+ for (const sec of authSpec.security) {
79
+ if (!merged.security.some((s) => JSON.stringify(s) === JSON.stringify(sec))) {
80
+ merged.security.push(sec);
81
+ }
82
+ }
83
+ }
84
+ // Merge tags
85
+ if (!merged.tags.some((t) => t.name === 'Auth')) {
86
+ merged.tags.push({
87
+ name: 'Auth',
88
+ description: 'Authentication and session management',
89
+ });
90
+ }
91
+ if (Array.isArray(authSpec.tags)) {
92
+ for (const tag of authSpec.tags) {
93
+ if (tag.name !== 'Default' &&
94
+ !merged.tags.some((t) => t.name === tag.name)) {
95
+ merged.tags.push(tag);
96
+ }
97
+ }
98
+ }
99
+ }
100
+ // Merge components by category
101
+ const categories = new Set([
102
+ ...Object.keys(nativeSpec.components || {}),
103
+ ...Object.keys(authSpec?.components || {}),
104
+ ]);
105
+ for (const category of categories) {
106
+ const nativeCat = nativeSpec.components?.[category] || {};
107
+ const authCat = authSpec?.components?.[category] || {};
108
+ const mergedCat = { ...nativeCat };
109
+ for (const [key, authVal] of Object.entries(authCat)) {
110
+ if (key in nativeCat) {
111
+ const nativeVal = nativeCat[key];
112
+ if (JSON.stringify(nativeVal) !== JSON.stringify(authVal)) {
113
+ throw new Error(`[workerstack] OpenAPI component collision: category "${category}" component "${key}"`);
114
+ }
115
+ }
116
+ else {
117
+ mergedCat[key] = authVal;
118
+ }
119
+ }
120
+ merged.components[category] = mergedCat;
121
+ }
122
+ // Ensure all tags used in path operations are declared in merged.tags
123
+ for (const pathItem of Object.values(merged.paths)) {
124
+ if (!pathItem || typeof pathItem !== 'object')
125
+ continue;
126
+ for (const [key, op] of Object.entries(pathItem)) {
127
+ if (HTTP_METHODS.has(key.toUpperCase()) &&
128
+ op &&
129
+ typeof op === 'object' &&
130
+ Array.isArray(op.tags)) {
131
+ for (const tagName of op.tags) {
132
+ if (tagName &&
133
+ tagName !== 'Default' &&
134
+ !merged.tags.some((t) => t.name === tagName)) {
135
+ merged.tags.push({
136
+ name: tagName,
137
+ description: `${tagName} operations`,
138
+ });
139
+ }
140
+ }
141
+ }
142
+ }
143
+ }
144
+ return merged;
145
+ }
146
+ //# sourceMappingURL=openapi.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"openapi.js","sourceRoot":"","sources":["../../src/api/openapi.ts"],"names":[],"mappings":"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","sourcesContent":["const HTTP_METHODS = new Set([\n 'GET',\n 'POST',\n 'PUT',\n 'PATCH',\n 'DELETE',\n 'HEAD',\n 'OPTIONS',\n])\n\nexport interface MergeOpenAPISpecsOptions {\n nativeSpec: Record<string, any>\n authSpec?: Record<string, any>\n}\n\nexport function mergeOpenAPISpecs(\n options: MergeOpenAPISpecsOptions,\n): Record<string, any> {\n const { nativeSpec, authSpec } = options\n\n const merged: Record<string, any> = {\n openapi: nativeSpec.openapi || authSpec?.openapi || '3.1.0',\n info: {\n title: 'Workerstack API',\n version: '1.0.0',\n ...nativeSpec.info,\n },\n paths: JSON.parse(JSON.stringify(nativeSpec.paths || {})),\n components: {},\n security: [...(nativeSpec.security || [])],\n tags: [...(nativeSpec.tags || [])],\n }\n\n if (authSpec) {\n // Merge paths and check for overwrite collisions\n if (authSpec.paths && typeof authSpec.paths === 'object') {\n for (const [routePath, authPathItem] of Object.entries(authSpec.paths)) {\n if (!authPathItem || typeof authPathItem !== 'object') continue\n\n const clonedPathItem = JSON.parse(\n JSON.stringify(authPathItem),\n ) as Record<string, any>\n\n // Normalize tags for Better Auth operations (replace generic \"Default\" with \"Auth\")\n if (routePath.startsWith('/api/auth')) {\n for (const [methodKey, operation] of Object.entries(clonedPathItem)) {\n if (\n HTTP_METHODS.has(methodKey.toUpperCase()) &&\n operation &&\n typeof operation === 'object'\n ) {\n if (Array.isArray(operation.tags)) {\n operation.tags = operation.tags.map((t: string) =>\n t === 'Default' ? 'Auth' : t,\n )\n if (!operation.tags.includes('Auth')) {\n operation.tags.unshift('Auth')\n }\n } else {\n operation.tags = ['Auth']\n }\n }\n }\n }\n\n if (!(routePath in merged.paths)) {\n merged.paths[routePath] = clonedPathItem\n } else {\n const existingPathItem = merged.paths[routePath]\n const incomingPathItem = clonedPathItem\n\n for (const [key, authVal] of Object.entries(incomingPathItem)) {\n const upperKey = key.toUpperCase()\n const isOperation = HTTP_METHODS.has(upperKey)\n\n if (key in existingPathItem) {\n const existingVal = existingPathItem[key]\n if (JSON.stringify(existingVal) !== JSON.stringify(authVal)) {\n if (isOperation) {\n throw new Error(\n `[workerstack] OpenAPI path overwrite collision: operation \"${upperKey} ${routePath}\"`,\n )\n } else {\n throw new Error(\n `[workerstack] OpenAPI path property collision on \"${routePath}\": key \"${key}\"`,\n )\n }\n }\n } else {\n existingPathItem[key] = JSON.parse(JSON.stringify(authVal))\n }\n }\n }\n }\n }\n\n // Merge security metadata\n if (Array.isArray(authSpec.security)) {\n for (const sec of authSpec.security) {\n if (\n !merged.security.some(\n (s: any) => JSON.stringify(s) === JSON.stringify(sec),\n )\n ) {\n merged.security.push(sec)\n }\n }\n }\n\n // Merge tags\n if (!merged.tags.some((t: any) => t.name === 'Auth')) {\n merged.tags.push({\n name: 'Auth',\n description: 'Authentication and session management',\n })\n }\n if (Array.isArray(authSpec.tags)) {\n for (const tag of authSpec.tags) {\n if (\n tag.name !== 'Default' &&\n !merged.tags.some((t: any) => t.name === tag.name)\n ) {\n merged.tags.push(tag)\n }\n }\n }\n }\n\n // Merge components by category\n const categories = new Set([\n ...Object.keys(nativeSpec.components || {}),\n ...Object.keys(authSpec?.components || {}),\n ])\n\n for (const category of categories) {\n const nativeCat = nativeSpec.components?.[category] || {}\n const authCat = authSpec?.components?.[category] || {}\n\n const mergedCat: Record<string, any> = { ...nativeCat }\n\n for (const [key, authVal] of Object.entries(authCat)) {\n if (key in nativeCat) {\n const nativeVal = nativeCat[key]\n if (JSON.stringify(nativeVal) !== JSON.stringify(authVal)) {\n throw new Error(\n `[workerstack] OpenAPI component collision: category \"${category}\" component \"${key}\"`,\n )\n }\n } else {\n mergedCat[key] = authVal\n }\n }\n\n merged.components[category] = mergedCat\n }\n\n // Ensure all tags used in path operations are declared in merged.tags\n for (const pathItem of Object.values(merged.paths)) {\n if (!pathItem || typeof pathItem !== 'object') continue\n for (const [key, op] of Object.entries(pathItem as Record<string, any>)) {\n if (\n HTTP_METHODS.has(key.toUpperCase()) &&\n op &&\n typeof op === 'object' &&\n Array.isArray(op.tags)\n ) {\n for (const tagName of op.tags) {\n if (\n tagName &&\n tagName !== 'Default' &&\n !merged.tags.some((t: any) => t.name === tagName)\n ) {\n merged.tags.push({\n name: tagName,\n description: `${tagName} operations`,\n })\n }\n }\n }\n }\n }\n\n return merged\n}\n"]}
@@ -0,0 +1,94 @@
1
+ import '@orpc/openapi/extensions/route';
2
+ import * as v from 'valibot';
3
+ import type { ResolvedAccess } from '../access.js';
4
+ import type { RealtimePublisher } from '../realtime/publisher.js';
5
+ type RealtimeRouterOptions = {
6
+ heartbeatMs?: number;
7
+ };
8
+ export declare function buildRealtimeApiRouter(publisher: RealtimePublisher | undefined, access: ResolvedAccess, options?: RealtimeRouterOptions): {
9
+ realtime: {
10
+ changes: import("@orpc/server").DecoratedProcedure<import("./context.js").ApiContext<Record<string, unknown>, Record<string, unknown>, import("..").MessagingConfig, Record<never, never>> & object, object, v.StrictObjectSchema<{
11
+ readonly tables: v.SchemaWithPipe<readonly [v.UnionSchema<[v.StringSchema<undefined>, v.ArraySchema<v.StringSchema<undefined>, undefined>], undefined>, v.TransformAction<string | string[], string[]>]>;
12
+ }, undefined>, import("@orpc/contract").Schema<AsyncIteratorObject<{
13
+ table: string;
14
+ action: "create" | "update" | "delete";
15
+ record: {
16
+ [x: string]: unknown;
17
+ };
18
+ operationId?: string | undefined;
19
+ } | {
20
+ type: "heartbeat";
21
+ intervalMs: number;
22
+ }, unknown, void>, import("@orpc/client").AsyncIteratorClass<{
23
+ table: string;
24
+ action: "create" | "update" | "delete";
25
+ record: {
26
+ [x: string]: unknown;
27
+ };
28
+ operationId?: string | undefined;
29
+ } | {
30
+ type: "heartbeat";
31
+ intervalMs: number;
32
+ }, unknown, void>>, {
33
+ readonly BAD_REQUEST: {
34
+ readonly data: v.OptionalSchema<v.StrictObjectSchema<{
35
+ readonly code: v.OptionalSchema<v.LiteralSchema<"BAD_REQUEST", undefined>, "BAD_REQUEST">;
36
+ readonly details: v.OptionalSchema<v.UnknownSchema, undefined>;
37
+ }, undefined>, {
38
+ readonly code: "BAD_REQUEST";
39
+ }>;
40
+ };
41
+ readonly UNAUTHORIZED: {
42
+ readonly data: v.OptionalSchema<v.StrictObjectSchema<{
43
+ readonly code: v.OptionalSchema<v.LiteralSchema<"UNAUTHORIZED", undefined>, "UNAUTHORIZED">;
44
+ readonly details: v.OptionalSchema<v.UnknownSchema, undefined>;
45
+ }, undefined>, {
46
+ readonly code: "UNAUTHORIZED";
47
+ }>;
48
+ };
49
+ readonly FORBIDDEN: {
50
+ readonly data: v.OptionalSchema<v.StrictObjectSchema<{
51
+ readonly code: v.OptionalSchema<v.LiteralSchema<"FORBIDDEN", undefined>, "FORBIDDEN">;
52
+ readonly details: v.OptionalSchema<v.UnknownSchema, undefined>;
53
+ }, undefined>, {
54
+ readonly code: "FORBIDDEN";
55
+ }>;
56
+ };
57
+ readonly NOT_FOUND: {
58
+ readonly data: v.OptionalSchema<v.StrictObjectSchema<{
59
+ readonly code: v.OptionalSchema<v.LiteralSchema<"NOT_FOUND", undefined>, "NOT_FOUND">;
60
+ readonly details: v.OptionalSchema<v.UnknownSchema, undefined>;
61
+ }, undefined>, {
62
+ readonly code: "NOT_FOUND";
63
+ }>;
64
+ };
65
+ readonly CONFLICT: {
66
+ readonly data: v.OptionalSchema<v.StrictObjectSchema<{
67
+ readonly code: v.OptionalSchema<v.LiteralSchema<"CONFLICT", undefined>, "CONFLICT">;
68
+ readonly details: v.OptionalSchema<v.UnknownSchema, undefined>;
69
+ }, undefined>, {
70
+ readonly code: "CONFLICT";
71
+ }>;
72
+ };
73
+ readonly PAYLOAD_TOO_LARGE: {
74
+ readonly data: v.OptionalSchema<v.StrictObjectSchema<{
75
+ readonly code: v.OptionalSchema<v.LiteralSchema<"PAYLOAD_TOO_LARGE", undefined>, "PAYLOAD_TOO_LARGE">;
76
+ readonly details: v.OptionalSchema<v.UnknownSchema, undefined>;
77
+ }, undefined>, {
78
+ readonly code: "PAYLOAD_TOO_LARGE";
79
+ }>;
80
+ };
81
+ readonly TOO_MANY_REQUESTS: {
82
+ readonly data: v.OptionalSchema<v.StrictObjectSchema<{
83
+ readonly code: v.OptionalSchema<v.LiteralSchema<"TOO_MANY_REQUESTS", undefined>, "TOO_MANY_REQUESTS">;
84
+ readonly details: v.OptionalSchema<v.UnknownSchema, undefined>;
85
+ }, undefined>, {
86
+ readonly code: "TOO_MANY_REQUESTS";
87
+ }>;
88
+ };
89
+ }>;
90
+ };
91
+ } | undefined;
92
+ export type RealtimeApiRouter = NonNullable<ReturnType<typeof buildRealtimeApiRouter>>;
93
+ export {};
94
+ //# sourceMappingURL=realtime-router.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"realtime-router.d.ts","sourceRoot":"","sources":["../../src/api/realtime-router.ts"],"names":[],"mappings":"AACA,OAAO,gCAAgC,CAAA;AACvC,OAAO,KAAK,CAAC,MAAM,SAAS,CAAA;AAE5B,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,WAAW,CAAA;AAC/C,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,uBAAuB,CAAA;AAyB9D,KAAK,qBAAqB,GAAG;IAC3B,WAAW,CAAC,EAAE,MAAM,CAAA;CACrB,CAAA;AAED,wBAAgB,sBAAsB,CACpC,SAAS,EAAE,iBAAiB,GAAG,SAAS,EACxC,MAAM,EAAE,cAAc,EACtB,OAAO,GAAE,qBAA0B;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;cAqCpC;AAED,MAAM,MAAM,iBAAiB,GAAG,WAAW,CACzC,UAAU,CAAC,OAAO,sBAAsB,CAAC,CAC1C,CAAA"}
@@ -0,0 +1,45 @@
1
+ import { eventIterator } from '@orpc/server';
2
+ import '@orpc/openapi/extensions/route';
3
+ import * as v from 'valibot';
4
+ import { filterRealtimeChanges } from '../realtime/filter.js';
5
+ import { withRealtimeHeartbeat } from '../realtime/heartbeat.js';
6
+ import { createApiBuilder } from './builder.js';
7
+ const tablesSchema = v.pipe(v.union([v.string(), v.array(v.string())]), v.transform((value) => (Array.isArray(value) ? value : [value])));
8
+ const changeSchema = v.strictObject({
9
+ table: v.string(),
10
+ action: v.picklist(['create', 'update', 'delete']),
11
+ record: v.record(v.string(), v.unknown()),
12
+ operationId: v.optional(v.string()),
13
+ });
14
+ const heartbeatSchema = v.strictObject({
15
+ type: v.literal('heartbeat'),
16
+ // The cadence this stream sends heartbeats at, so a client can size its
17
+ // dead-stream timeout from the server's real setting.
18
+ intervalMs: v.number(),
19
+ });
20
+ export function buildRealtimeApiRouter(publisher, access, options = {}) {
21
+ if (!publisher)
22
+ return undefined;
23
+ const builder = createApiBuilder();
24
+ const changes = builder.public
25
+ .route({
26
+ method: 'GET',
27
+ path: '/api/realtime',
28
+ summary: 'Subscribe to realtime changes',
29
+ tags: ['realtime'],
30
+ queryStyles: { tables: 'array' },
31
+ })
32
+ .input(v.strictObject({ tables: tablesSchema }))
33
+ .output(eventIterator(v.union([changeSchema, heartbeatSchema])))
34
+ .handler(({ input, context, signal, lastEventId }) => withRealtimeHeartbeat(filterRealtimeChanges(publisher.subscribe('change', { signal, lastEventId }), {
35
+ subscriptions: input.tables,
36
+ access,
37
+ request: context.request,
38
+ getSession: context.getSession,
39
+ }), {
40
+ intervalMs: options.heartbeatMs,
41
+ signal,
42
+ }));
43
+ return { realtime: { changes } };
44
+ }
45
+ //# sourceMappingURL=realtime-router.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"realtime-router.js","sourceRoot":"","sources":["../../src/api/realtime-router.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,aAAa,EAAE,MAAM,cAAc,CAAA;AAC5C,OAAO,gCAAgC,CAAA;AACvC,OAAO,KAAK,CAAC,MAAM,SAAS,CAAA;AAK5B,OAAO,EAAE,qBAAqB,EAAE,MAAM,oBAAoB,CAAA;AAC1D,OAAO,EAAE,qBAAqB,EAAE,MAAM,uBAAuB,CAAA;AAC7D,OAAO,EAAE,gBAAgB,EAAE,MAAM,WAAW,CAAA;AAE5C,MAAM,YAAY,GAAG,CAAC,CAAC,IAAI,CACzB,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,MAAM,EAAE,EAAE,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,MAAM,EAAE,CAAC,CAAC,CAAC,EAC1C,CAAC,CAAC,SAAS,CAAC,CAAC,KAAK,EAAE,EAAE,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,CACjE,CAAA;AAED,MAAM,YAAY,GAAG,CAAC,CAAC,YAAY,CAAC;IAClC,KAAK,EAAE,CAAC,CAAC,MAAM,EAAE;IACjB,MAAM,EAAE,CAAC,CAAC,QAAQ,CAAC,CAAC,QAAQ,EAAE,QAAQ,EAAE,QAAQ,CAAC,CAAC;IAClD,MAAM,EAAE,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,MAAM,EAAE,EAAE,CAAC,CAAC,OAAO,EAAE,CAAC;IACzC,WAAW,EAAE,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,MAAM,EAAE,CAAC;CACpC,CAAC,CAAA;AAEF,MAAM,eAAe,GAAG,CAAC,CAAC,YAAY,CAAC;IACrC,IAAI,EAAE,CAAC,CAAC,OAAO,CAAC,WAAW,CAAC;IAC5B,wEAAwE;IACxE,sDAAsD;IACtD,UAAU,EAAE,CAAC,CAAC,MAAM,EAAE;CACvB,CAAC,CAAA;AAMF,MAAM,UAAU,sBAAsB,CACpC,SAAwC,EACxC,MAAsB,EACtB,UAAiC,EAAE;IAEnC,IAAI,CAAC,SAAS;QAAE,OAAO,SAAS,CAAA;IAChC,MAAM,OAAO,GAAG,gBAAgB,EAG7B,CAAA;IAEH,MAAM,OAAO,GAAG,OAAO,CAAC,MAAM;SAC3B,KAAK,CAAC;QACL,MAAM,EAAE,KAAK;QACb,IAAI,EAAE,eAAe;QACrB,OAAO,EAAE,+BAA+B;QACxC,IAAI,EAAE,CAAC,UAAU,CAAC;QAClB,WAAW,EAAE,EAAE,MAAM,EAAE,OAAO,EAAE;KACjC,CAAC;SACD,KAAK,CAAC,CAAC,CAAC,YAAY,CAAC,EAAE,MAAM,EAAE,YAAY,EAAE,CAAC,CAAC;SAC/C,MAAM,CAAC,aAAa,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,YAAY,EAAE,eAAe,CAAC,CAAC,CAAC,CAAC;SAC/D,OAAO,CAAC,CAAC,EAAE,KAAK,EAAE,OAAO,EAAE,MAAM,EAAE,WAAW,EAAE,EAAE,EAAE,CACnD,qBAAqB,CACnB,qBAAqB,CACnB,SAAS,CAAC,SAAS,CAAC,QAAQ,EAAE,EAAE,MAAM,EAAE,WAAW,EAAE,CAAC,EACtD;QACE,aAAa,EAAE,KAAK,CAAC,MAAM;QAC3B,MAAM;QACN,OAAO,EAAE,OAAO,CAAC,OAAO;QACxB,UAAU,EAAE,OAAO,CAAC,UAAU;KAC/B,CACF,EACD;QACE,UAAU,EAAE,OAAO,CAAC,WAAW;QAC/B,MAAM;KACP,CACF,CACF,CAAA;IAEH,OAAO,EAAE,QAAQ,EAAE,EAAE,OAAO,EAAE,EAAE,CAAA;AAClC,CAAC","sourcesContent":["import { eventIterator } from '@orpc/server'\nimport '@orpc/openapi/extensions/route'\nimport * as v from 'valibot'\n\nimport type { ResolvedAccess } from '../access'\nimport type { RealtimePublisher } from '../realtime/publisher'\n\nimport { filterRealtimeChanges } from '../realtime/filter'\nimport { withRealtimeHeartbeat } from '../realtime/heartbeat'\nimport { createApiBuilder } from './builder'\n\nconst tablesSchema = v.pipe(\n v.union([v.string(), v.array(v.string())]),\n v.transform((value) => (Array.isArray(value) ? value : [value])),\n)\n\nconst changeSchema = v.strictObject({\n table: v.string(),\n action: v.picklist(['create', 'update', 'delete']),\n record: v.record(v.string(), v.unknown()),\n operationId: v.optional(v.string()),\n})\n\nconst heartbeatSchema = v.strictObject({\n type: v.literal('heartbeat'),\n // The cadence this stream sends heartbeats at, so a client can size its\n // dead-stream timeout from the server's real setting.\n intervalMs: v.number(),\n})\n\ntype RealtimeRouterOptions = {\n heartbeatMs?: number\n}\n\nexport function buildRealtimeApiRouter(\n publisher: RealtimePublisher | undefined,\n access: ResolvedAccess,\n options: RealtimeRouterOptions = {},\n) {\n if (!publisher) return undefined\n const builder = createApiBuilder<\n Record<string, unknown>,\n Record<string, unknown>\n >()\n\n const changes = builder.public\n .route({\n method: 'GET',\n path: '/api/realtime',\n summary: 'Subscribe to realtime changes',\n tags: ['realtime'],\n queryStyles: { tables: 'array' },\n })\n .input(v.strictObject({ tables: tablesSchema }))\n .output(eventIterator(v.union([changeSchema, heartbeatSchema])))\n .handler(({ input, context, signal, lastEventId }) =>\n withRealtimeHeartbeat(\n filterRealtimeChanges(\n publisher.subscribe('change', { signal, lastEventId }),\n {\n subscriptions: input.tables,\n access,\n request: context.request,\n getSession: context.getSession,\n },\n ),\n {\n intervalMs: options.heartbeatMs,\n signal,\n },\n ),\n )\n\n return { realtime: { changes } }\n}\n\nexport type RealtimeApiRouter = NonNullable<\n ReturnType<typeof buildRealtimeApiRouter>\n>\n"]}
@@ -0,0 +1,30 @@
1
+ export interface ApiRegistryEntry {
2
+ handle: string;
3
+ operationId: string;
4
+ method: string;
5
+ path: string;
6
+ source: string;
7
+ }
8
+ export interface ApiRegistry {
9
+ entries: ApiRegistryEntry[];
10
+ }
11
+ export interface ForeignSpecEntry {
12
+ spec: Record<string, unknown>;
13
+ prefix?: string;
14
+ source?: string;
15
+ }
16
+ export interface BuildApiRegistryOptions {
17
+ nativeRouter?: Record<string, unknown>;
18
+ foreignSpecs?: Array<Record<string, unknown> | ForeignSpecEntry>;
19
+ /** Native procedures generated by Workerstack itself may own reserved paths. */
20
+ reservedCoreHandles?: ReadonlySet<string>;
21
+ }
22
+ export declare function normalizeApiPath(path: string, prefix?: string): string;
23
+ export interface ForeignSpecOptions {
24
+ prefix?: string;
25
+ source?: string;
26
+ }
27
+ export declare function normalizeForeignOpenAPISpec(spec: Record<string, unknown>, options?: ForeignSpecOptions): Record<string, unknown>;
28
+ export declare function mergeApiRoutersStrict(target: Record<string, unknown>, source?: Record<string, unknown>, prefix?: string[]): Record<string, unknown>;
29
+ export declare function buildApiRegistry(options?: BuildApiRegistryOptions): Promise<ApiRegistry>;
30
+ //# sourceMappingURL=registry.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"registry.d.ts","sourceRoot":"","sources":["../../src/api/registry.ts"],"names":[],"mappings":"AAmBA,MAAM,WAAW,gBAAgB;IAC/B,MAAM,EAAE,MAAM,CAAA;IACd,WAAW,EAAE,MAAM,CAAA;IACnB,MAAM,EAAE,MAAM,CAAA;IACd,IAAI,EAAE,MAAM,CAAA;IACZ,MAAM,EAAE,MAAM,CAAA;CACf;AAED,MAAM,WAAW,WAAW;IAC1B,OAAO,EAAE,gBAAgB,EAAE,CAAA;CAC5B;AAED,MAAM,WAAW,gBAAgB;IAC/B,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAA;IAC7B,MAAM,CAAC,EAAE,MAAM,CAAA;IACf,MAAM,CAAC,EAAE,MAAM,CAAA;CAChB;AAED,MAAM,WAAW,uBAAuB;IACtC,YAAY,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAA;IACtC,YAAY,CAAC,EAAE,KAAK,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,gBAAgB,CAAC,CAAA;IAChE,gFAAgF;IAChF,mBAAmB,CAAC,EAAE,WAAW,CAAC,MAAM,CAAC,CAAA;CAC1C;AAYD,wBAAgB,gBAAgB,CAAC,IAAI,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,MAAM,GAAG,MAAM,CActE;AAED,MAAM,WAAW,kBAAkB;IACjC,MAAM,CAAC,EAAE,MAAM,CAAA;IACf,MAAM,CAAC,EAAE,MAAM,CAAA;CAChB;AAED,wBAAgB,2BAA2B,CACzC,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAC7B,OAAO,GAAE,kBAAuB,GAC/B,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAqBzB;AAED,wBAAgB,qBAAqB,CACnC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAC/B,MAAM,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAChC,MAAM,GAAE,MAAM,EAAO,GACpB,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAmCzB;AAiHD,wBAAsB,gBAAgB,CACpC,OAAO,GAAE,uBAA4B,GACpC,OAAO,CAAC,WAAW,CAAC,CAgFtB"}