ts-procedures 7.2.0 → 8.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (325) hide show
  1. package/README.md +65 -3
  2. package/agent_config/claude-code/agents/ts-procedures-architect.md +6 -8
  3. package/agent_config/claude-code/skills/ts-procedures/SKILL.md +30 -33
  4. package/agent_config/claude-code/skills/ts-procedures/anti-patterns.md +139 -53
  5. package/agent_config/claude-code/skills/ts-procedures/api-reference.md +208 -231
  6. package/agent_config/claude-code/skills/ts-procedures/patterns.md +80 -153
  7. package/agent_config/claude-code/skills/ts-procedures-review/SKILL.md +1 -1
  8. package/agent_config/claude-code/skills/ts-procedures-review/checklist.md +4 -5
  9. package/agent_config/claude-code/skills/ts-procedures-scaffold/SKILL.md +4 -7
  10. package/agent_config/claude-code/skills/ts-procedures-scaffold/templates/hono.md +223 -0
  11. package/agent_config/copilot/copilot-instructions.md +36 -48
  12. package/agent_config/cursor/cursorrules +36 -48
  13. package/build/client/call.js +4 -1
  14. package/build/client/call.js.map +1 -1
  15. package/build/client/call.test.js +23 -0
  16. package/build/client/call.test.js.map +1 -1
  17. package/build/client/fetch-adapter.js +3 -1
  18. package/build/client/fetch-adapter.js.map +1 -1
  19. package/build/client/fetch-adapter.test.js +11 -1
  20. package/build/client/fetch-adapter.test.js.map +1 -1
  21. package/build/client/index.test.js +7 -7
  22. package/build/client/index.test.js.map +1 -1
  23. package/build/client/request-builder.d.ts +1 -1
  24. package/build/client/request-builder.js +2 -2
  25. package/build/client/request-builder.js.map +1 -1
  26. package/build/client/stream.js +13 -2
  27. package/build/client/stream.js.map +1 -1
  28. package/build/client/stream.test.js +32 -7
  29. package/build/client/stream.test.js.map +1 -1
  30. package/build/client/typed-error-dispatch.test.js +8 -92
  31. package/build/client/typed-error-dispatch.test.js.map +1 -1
  32. package/build/client/types.d.ts +21 -3
  33. package/build/codegen/bin/cli.js +0 -0
  34. package/build/codegen/e2e.test.js +87 -23
  35. package/build/codegen/e2e.test.js.map +1 -1
  36. package/build/codegen/emit-errors.integration.test.js +1 -1
  37. package/build/codegen/emit-errors.integration.test.js.map +1 -1
  38. package/build/codegen/emit-scope.js +308 -47
  39. package/build/codegen/emit-scope.js.map +1 -1
  40. package/build/codegen/emit-scope.test.js +363 -110
  41. package/build/codegen/emit-scope.test.js.map +1 -1
  42. package/build/codegen/pipeline.test.js +7 -7
  43. package/build/codegen/pipeline.test.js.map +1 -1
  44. package/build/codegen/resolve-envelope.js +1 -1
  45. package/build/codegen/resolve-envelope.js.map +1 -1
  46. package/build/codegen/resolve-envelope.test.js +5 -5
  47. package/build/codegen/resolve-envelope.test.js.map +1 -1
  48. package/build/codegen/targets/_shared/route-slots.d.ts +8 -3
  49. package/build/codegen/targets/_shared/route-slots.js +49 -8
  50. package/build/codegen/targets/_shared/route-slots.js.map +1 -1
  51. package/build/codegen/targets/_shared/route-slots.test.js +99 -26
  52. package/build/codegen/targets/_shared/route-slots.test.js.map +1 -1
  53. package/build/codegen/targets/kotlin/emit-route-kotlin.test.js +88 -17
  54. package/build/codegen/targets/kotlin/emit-route-kotlin.test.js.map +1 -1
  55. package/build/codegen/targets/kotlin/emit-scope-kotlin.test.js +9 -6
  56. package/build/codegen/targets/kotlin/emit-scope-kotlin.test.js.map +1 -1
  57. package/build/codegen/targets/kotlin/integration.test.js +6 -0
  58. package/build/codegen/targets/kotlin/integration.test.js.map +1 -1
  59. package/build/codegen/targets/swift/access-level.test.js +8 -11
  60. package/build/codegen/targets/swift/access-level.test.js.map +1 -1
  61. package/build/codegen/targets/swift/emit-route-swift.test.js +91 -20
  62. package/build/codegen/targets/swift/emit-route-swift.test.js.map +1 -1
  63. package/build/codegen/targets/swift/emit-scope-swift.test.js +12 -9
  64. package/build/codegen/targets/swift/emit-scope-swift.test.js.map +1 -1
  65. package/build/codegen/targets/swift/integration.test.js +6 -0
  66. package/build/codegen/targets/swift/integration.test.js.map +1 -1
  67. package/build/create-http-stream.d.ts +58 -0
  68. package/build/create-http-stream.js +122 -0
  69. package/build/create-http-stream.js.map +1 -0
  70. package/build/create-http-stream.test.js +88 -0
  71. package/build/create-http-stream.test.js.map +1 -0
  72. package/build/create-http.d.ts +49 -0
  73. package/build/create-http.js +108 -0
  74. package/build/create-http.js.map +1 -0
  75. package/build/create-http.test.js +137 -0
  76. package/build/create-http.test.js.map +1 -0
  77. package/build/create-stream.d.ts +35 -0
  78. package/build/create-stream.js +123 -0
  79. package/build/create-stream.js.map +1 -0
  80. package/build/create-stream.test.js +428 -0
  81. package/build/create-stream.test.js.map +1 -0
  82. package/build/create.d.ts +28 -0
  83. package/build/create.js +82 -0
  84. package/build/create.js.map +1 -0
  85. package/build/create.test.js +483 -0
  86. package/build/create.test.js.map +1 -0
  87. package/build/exports.d.ts +2 -0
  88. package/build/implementations/http/astro/index.test.js +20 -12
  89. package/build/implementations/http/astro/index.test.js.map +1 -1
  90. package/build/implementations/http/doc-registry.js +1 -1
  91. package/build/implementations/http/doc-registry.js.map +1 -1
  92. package/build/implementations/http/doc-registry.test.js +36 -5
  93. package/build/implementations/http/doc-registry.test.js.map +1 -1
  94. package/build/implementations/http/error-dispatch.d.ts +76 -0
  95. package/build/implementations/http/error-dispatch.js +77 -0
  96. package/build/implementations/http/error-dispatch.js.map +1 -0
  97. package/build/implementations/http/error-dispatch.test.js +254 -0
  98. package/build/implementations/http/error-dispatch.test.js.map +1 -0
  99. package/build/implementations/http/error-taxonomy.d.ts +5 -5
  100. package/build/implementations/http/hono/docs/http-doc.d.ts +6 -0
  101. package/build/implementations/http/hono/docs/http-doc.js +42 -0
  102. package/build/implementations/http/hono/docs/http-doc.js.map +1 -0
  103. package/build/implementations/http/hono/docs/http-stream-doc.d.ts +6 -0
  104. package/build/implementations/http/hono/docs/http-stream-doc.js +40 -0
  105. package/build/implementations/http/hono/docs/http-stream-doc.js.map +1 -0
  106. package/build/implementations/http/hono/docs/rpc-doc.d.ts +6 -0
  107. package/build/implementations/http/hono/docs/rpc-doc.js +24 -0
  108. package/build/implementations/http/hono/docs/rpc-doc.js.map +1 -0
  109. package/build/implementations/http/hono/docs/stream-doc.d.ts +6 -0
  110. package/build/implementations/http/hono/docs/stream-doc.js +42 -0
  111. package/build/implementations/http/hono/docs/stream-doc.js.map +1 -0
  112. package/build/implementations/http/hono/handlers/http-stream.d.ts +10 -0
  113. package/build/implementations/http/hono/handlers/http-stream.js +123 -0
  114. package/build/implementations/http/hono/handlers/http-stream.js.map +1 -0
  115. package/build/implementations/http/hono/handlers/http-stream.test.js +128 -0
  116. package/build/implementations/http/hono/handlers/http-stream.test.js.map +1 -0
  117. package/build/implementations/http/hono/handlers/http.d.ts +10 -0
  118. package/build/implementations/http/hono/handlers/http.js +115 -0
  119. package/build/implementations/http/hono/handlers/http.js.map +1 -0
  120. package/build/implementations/http/hono/handlers/http.test.js +118 -0
  121. package/build/implementations/http/hono/handlers/http.test.js.map +1 -0
  122. package/build/implementations/http/hono/handlers/rpc.d.ts +11 -0
  123. package/build/implementations/http/hono/handlers/rpc.js +32 -0
  124. package/build/implementations/http/hono/handlers/rpc.js.map +1 -0
  125. package/build/implementations/http/hono/handlers/rpc.test.js +73 -0
  126. package/build/implementations/http/hono/handlers/rpc.test.js.map +1 -0
  127. package/build/implementations/http/hono/handlers/stream.d.ts +23 -0
  128. package/build/implementations/http/hono/handlers/stream.js +147 -0
  129. package/build/implementations/http/hono/handlers/stream.js.map +1 -0
  130. package/build/implementations/http/hono/handlers/stream.test.d.ts +1 -0
  131. package/build/implementations/http/hono/handlers/stream.test.js +177 -0
  132. package/build/implementations/http/hono/handlers/stream.test.js.map +1 -0
  133. package/build/implementations/http/hono/index.d.ts +57 -0
  134. package/build/implementations/http/hono/index.js +149 -0
  135. package/build/implementations/http/hono/index.js.map +1 -0
  136. package/build/implementations/http/hono/index.test.d.ts +1 -0
  137. package/build/implementations/http/hono/index.test.js +274 -0
  138. package/build/implementations/http/hono/index.test.js.map +1 -0
  139. package/build/implementations/http/hono/path.d.ts +17 -0
  140. package/build/implementations/http/hono/path.js +39 -0
  141. package/build/implementations/http/hono/path.js.map +1 -0
  142. package/build/implementations/http/hono/path.test.d.ts +1 -0
  143. package/build/implementations/http/hono/path.test.js +83 -0
  144. package/build/implementations/http/hono/path.test.js.map +1 -0
  145. package/build/implementations/http/hono/types.d.ts +51 -0
  146. package/build/implementations/http/hono/types.js.map +1 -0
  147. package/build/implementations/http/on-request-error.test.js +6 -96
  148. package/build/implementations/http/on-request-error.test.js.map +1 -1
  149. package/build/implementations/http/route-errors.test.js +11 -59
  150. package/build/implementations/http/route-errors.test.js.map +1 -1
  151. package/build/implementations/types.d.ts +43 -9
  152. package/build/index.d.ts +125 -115
  153. package/build/index.js +10 -222
  154. package/build/index.js.map +1 -1
  155. package/build/index.test.js +30 -822
  156. package/build/index.test.js.map +1 -1
  157. package/build/migration.test.d.ts +1 -0
  158. package/build/migration.test.js +34 -0
  159. package/build/migration.test.js.map +1 -0
  160. package/build/schema/compute-schema.d.ts +11 -3
  161. package/build/schema/compute-schema.js +13 -7
  162. package/build/schema/compute-schema.js.map +1 -1
  163. package/build/schema/parser.d.ts +11 -3
  164. package/build/schema/parser.js +49 -9
  165. package/build/schema/parser.js.map +1 -1
  166. package/build/stack-utils.js +8 -0
  167. package/build/stack-utils.js.map +1 -1
  168. package/build/types.d.ts +142 -0
  169. package/build/types.js.map +1 -0
  170. package/docs/astro-adapter.md +5 -5
  171. package/docs/core.md +34 -17
  172. package/docs/http-integrations.md +83 -170
  173. package/docs/streaming.md +3 -60
  174. package/docs/superpowers/plans/2026-05-07-astro-adapter.md +2 -7
  175. package/docs/superpowers/plans/2026-05-08-create-http.md +3355 -0
  176. package/docs/superpowers/plans/2026-05-08-hono-app-builder-convergence.md +3365 -0
  177. package/docs/superpowers/specs/2026-05-07-astro-adapter-design.md +1 -3
  178. package/docs/superpowers/specs/2026-05-08-create-http-design.md +409 -0
  179. package/docs/superpowers/specs/2026-05-08-hono-app-builder-convergence-design.md +411 -0
  180. package/package.json +4 -22
  181. package/src/client/call.test.ts +26 -0
  182. package/src/client/call.ts +4 -1
  183. package/src/client/fetch-adapter.test.ts +14 -1
  184. package/src/client/fetch-adapter.ts +3 -1
  185. package/src/client/index.test.ts +7 -7
  186. package/src/client/request-builder.ts +2 -2
  187. package/src/client/stream.test.ts +39 -7
  188. package/src/client/stream.ts +16 -2
  189. package/src/client/typed-error-dispatch.test.ts +7 -97
  190. package/src/client/types.ts +21 -3
  191. package/src/codegen/__fixtures__/users-envelope.json +119 -38
  192. package/src/codegen/e2e.test.ts +98 -24
  193. package/src/codegen/emit-errors.integration.test.ts +1 -1
  194. package/src/codegen/emit-scope.test.ts +395 -110
  195. package/src/codegen/emit-scope.ts +350 -55
  196. package/src/codegen/pipeline.test.ts +7 -7
  197. package/src/codegen/resolve-envelope.test.ts +5 -5
  198. package/src/codegen/resolve-envelope.ts +1 -1
  199. package/src/codegen/targets/_shared/route-slots.test.ts +109 -26
  200. package/src/codegen/targets/_shared/route-slots.ts +48 -11
  201. package/src/codegen/targets/kotlin/__fixtures__/users-golden.kt +73 -0
  202. package/src/codegen/targets/kotlin/emit-route-kotlin.test.ts +100 -17
  203. package/src/codegen/targets/kotlin/emit-scope-kotlin.test.ts +9 -6
  204. package/src/codegen/targets/kotlin/integration.test.ts +19 -0
  205. package/src/codegen/targets/swift/__fixtures__/users-golden.swift +79 -0
  206. package/src/codegen/targets/swift/access-level.test.ts +8 -11
  207. package/src/codegen/targets/swift/emit-route-swift.test.ts +103 -20
  208. package/src/codegen/targets/swift/emit-scope-swift.test.ts +12 -9
  209. package/src/codegen/targets/swift/integration.test.ts +17 -0
  210. package/src/create-http-stream.test.ts +97 -0
  211. package/src/create-http-stream.ts +191 -0
  212. package/src/create-http.test.ts +163 -0
  213. package/src/create-http.ts +211 -0
  214. package/src/create-stream.test.ts +565 -0
  215. package/src/create-stream.ts +228 -0
  216. package/src/create.test.ts +658 -0
  217. package/src/create.ts +172 -0
  218. package/src/exports.ts +2 -0
  219. package/src/implementations/http/README.md +135 -95
  220. package/src/implementations/http/astro/README.md +4 -5
  221. package/src/implementations/http/astro/index.test.ts +25 -18
  222. package/src/implementations/http/doc-registry.test.ts +42 -5
  223. package/src/implementations/http/doc-registry.ts +1 -1
  224. package/src/implementations/http/error-dispatch.test.ts +283 -0
  225. package/src/implementations/http/error-dispatch.ts +176 -0
  226. package/src/implementations/http/error-taxonomy.ts +5 -5
  227. package/src/implementations/http/hono/docs/http-doc.ts +43 -0
  228. package/src/implementations/http/hono/docs/http-stream-doc.ts +44 -0
  229. package/src/implementations/http/hono/docs/rpc-doc.ts +34 -0
  230. package/src/implementations/http/hono/docs/stream-doc.ts +53 -0
  231. package/src/implementations/http/hono/handlers/http-stream.test.ts +150 -0
  232. package/src/implementations/http/hono/handlers/http-stream.ts +152 -0
  233. package/src/implementations/http/hono/handlers/http.test.ts +130 -0
  234. package/src/implementations/http/hono/handlers/http.ts +147 -0
  235. package/src/implementations/http/hono/handlers/rpc.test.ts +81 -0
  236. package/src/implementations/http/hono/handlers/rpc.ts +54 -0
  237. package/src/implementations/http/hono/handlers/stream.test.ts +198 -0
  238. package/src/implementations/http/hono/handlers/stream.ts +208 -0
  239. package/src/implementations/http/hono/index.test.ts +329 -0
  240. package/src/implementations/http/hono/index.ts +204 -0
  241. package/src/implementations/http/hono/path.test.ts +96 -0
  242. package/src/implementations/http/hono/path.ts +59 -0
  243. package/src/implementations/http/hono/types.ts +93 -0
  244. package/src/implementations/http/on-request-error.test.ts +10 -116
  245. package/src/implementations/http/route-errors.test.ts +11 -77
  246. package/src/implementations/types.ts +44 -9
  247. package/src/index.test.ts +35 -1091
  248. package/src/index.ts +50 -474
  249. package/src/migration.test.ts +48 -0
  250. package/src/schema/compute-schema.ts +26 -12
  251. package/src/schema/parser.ts +62 -12
  252. package/src/stack-utils.ts +8 -0
  253. package/src/types.ts +133 -0
  254. package/agent_config/claude-code/skills/ts-procedures-scaffold/templates/express-rpc.md +0 -137
  255. package/agent_config/claude-code/skills/ts-procedures-scaffold/templates/hono-api.md +0 -173
  256. package/agent_config/claude-code/skills/ts-procedures-scaffold/templates/hono-rpc.md +0 -142
  257. package/agent_config/claude-code/skills/ts-procedures-scaffold/templates/hono-stream.md +0 -147
  258. package/build/implementations/http/express-rpc/error-taxonomy.test.js +0 -83
  259. package/build/implementations/http/express-rpc/error-taxonomy.test.js.map +0 -1
  260. package/build/implementations/http/express-rpc/index.d.ts +0 -125
  261. package/build/implementations/http/express-rpc/index.js +0 -216
  262. package/build/implementations/http/express-rpc/index.js.map +0 -1
  263. package/build/implementations/http/express-rpc/index.test.js +0 -684
  264. package/build/implementations/http/express-rpc/index.test.js.map +0 -1
  265. package/build/implementations/http/express-rpc/types.d.ts +0 -11
  266. package/build/implementations/http/express-rpc/types.js.map +0 -1
  267. package/build/implementations/http/hono-api/error-taxonomy.test.js +0 -137
  268. package/build/implementations/http/hono-api/error-taxonomy.test.js.map +0 -1
  269. package/build/implementations/http/hono-api/index.d.ts +0 -151
  270. package/build/implementations/http/hono-api/index.js +0 -344
  271. package/build/implementations/http/hono-api/index.js.map +0 -1
  272. package/build/implementations/http/hono-api/index.test.js +0 -992
  273. package/build/implementations/http/hono-api/index.test.js.map +0 -1
  274. package/build/implementations/http/hono-api/types.d.ts +0 -13
  275. package/build/implementations/http/hono-api/types.js.map +0 -1
  276. package/build/implementations/http/hono-rpc/error-taxonomy.test.js +0 -64
  277. package/build/implementations/http/hono-rpc/error-taxonomy.test.js.map +0 -1
  278. package/build/implementations/http/hono-rpc/index.d.ts +0 -130
  279. package/build/implementations/http/hono-rpc/index.js +0 -209
  280. package/build/implementations/http/hono-rpc/index.js.map +0 -1
  281. package/build/implementations/http/hono-rpc/index.test.js +0 -828
  282. package/build/implementations/http/hono-rpc/index.test.js.map +0 -1
  283. package/build/implementations/http/hono-rpc/types.d.ts +0 -11
  284. package/build/implementations/http/hono-rpc/types.js +0 -2
  285. package/build/implementations/http/hono-rpc/types.js.map +0 -1
  286. package/build/implementations/http/hono-stream/error-taxonomy.test.js +0 -159
  287. package/build/implementations/http/hono-stream/error-taxonomy.test.js.map +0 -1
  288. package/build/implementations/http/hono-stream/index.d.ts +0 -171
  289. package/build/implementations/http/hono-stream/index.js +0 -415
  290. package/build/implementations/http/hono-stream/index.js.map +0 -1
  291. package/build/implementations/http/hono-stream/index.test.js +0 -1383
  292. package/build/implementations/http/hono-stream/index.test.js.map +0 -1
  293. package/build/implementations/http/hono-stream/types.d.ts +0 -15
  294. package/build/implementations/http/hono-stream/types.js +0 -2
  295. package/build/implementations/http/hono-stream/types.js.map +0 -1
  296. package/src/implementations/http/express-rpc/README.md +0 -280
  297. package/src/implementations/http/express-rpc/error-taxonomy.test.ts +0 -103
  298. package/src/implementations/http/express-rpc/index.test.ts +0 -957
  299. package/src/implementations/http/express-rpc/index.ts +0 -327
  300. package/src/implementations/http/express-rpc/types.ts +0 -16
  301. package/src/implementations/http/hono-api/README.md +0 -284
  302. package/src/implementations/http/hono-api/error-taxonomy.test.ts +0 -179
  303. package/src/implementations/http/hono-api/index.test.ts +0 -1341
  304. package/src/implementations/http/hono-api/index.ts +0 -519
  305. package/src/implementations/http/hono-api/types.ts +0 -16
  306. package/src/implementations/http/hono-rpc/README.md +0 -357
  307. package/src/implementations/http/hono-rpc/error-taxonomy.test.ts +0 -82
  308. package/src/implementations/http/hono-rpc/index.test.ts +0 -1107
  309. package/src/implementations/http/hono-rpc/index.ts +0 -320
  310. package/src/implementations/http/hono-rpc/types.ts +0 -16
  311. package/src/implementations/http/hono-stream/README.md +0 -559
  312. package/src/implementations/http/hono-stream/error-taxonomy.test.ts +0 -178
  313. package/src/implementations/http/hono-stream/index.test.ts +0 -1804
  314. package/src/implementations/http/hono-stream/index.ts +0 -622
  315. package/src/implementations/http/hono-stream/types.ts +0 -20
  316. /package/build/{implementations/http/express-rpc/error-taxonomy.test.d.ts → create-http-stream.test.d.ts} +0 -0
  317. /package/build/{implementations/http/express-rpc/index.test.d.ts → create-http.test.d.ts} +0 -0
  318. /package/build/{implementations/http/hono-api/error-taxonomy.test.d.ts → create-stream.test.d.ts} +0 -0
  319. /package/build/{implementations/http/hono-api/index.test.d.ts → create.test.d.ts} +0 -0
  320. /package/build/implementations/http/{hono-rpc/error-taxonomy.test.d.ts → error-dispatch.test.d.ts} +0 -0
  321. /package/build/implementations/http/{hono-rpc/index.test.d.ts → hono/handlers/http-stream.test.d.ts} +0 -0
  322. /package/build/implementations/http/{hono-stream/error-taxonomy.test.d.ts → hono/handlers/http.test.d.ts} +0 -0
  323. /package/build/implementations/http/{hono-stream/index.test.d.ts → hono/handlers/rpc.test.d.ts} +0 -0
  324. /package/build/implementations/http/{express-rpc → hono}/types.js +0 -0
  325. /package/build/{implementations/http/hono-api/types.js → types.js} +0 -0
@@ -0,0 +1,223 @@
1
+ # Hono Template: {{Name}}
2
+
3
+ A single `HonoAppBuilder` can host all four procedure kinds — RPC (`Create`), RPC stream (`CreateStream`), HTTP REST (`CreateHttp`), and HTTP stream (`CreateHttpStream`) — registered against one `Procedures` factory and mounted with one `register(...)` call. This template demonstrates that.
4
+
5
+ ## Implementation — `{{Name}}.hono.ts`
6
+
7
+ ```typescript
8
+ import { Procedures } from 'ts-procedures'
9
+ import type { RPCConfig } from 'ts-procedures/http'
10
+ import { defineErrorTaxonomy, HonoAppBuilder } from 'ts-procedures/hono'
11
+ import { Type } from 'typebox'
12
+
13
+ // ─── Context ──────────────────────────────────────────────
14
+
15
+ type {{Name}}Context = {
16
+ userId: string
17
+ requestId: string
18
+ }
19
+
20
+ // ─── Procedures ───────────────────────────────────────────
21
+ // Capture the factory in a single `procs` variable so every kind shares
22
+ // the same context type and the same final register() call.
23
+
24
+ const procs = Procedures<{{Name}}Context, RPCConfig>()
25
+
26
+ // RPC — `Create`. Mounted at POST /api/{{kebab}}/get-item/1
27
+ export const { GetItem } = procs.Create(
28
+ 'GetItem',
29
+ {
30
+ scope: '{{kebab}}',
31
+ version: 1,
32
+ description: 'Fetch an item by id (RPC).',
33
+ schema: {
34
+ params: Type.Object({
35
+ id: Type.String(),
36
+ }),
37
+ returnType: Type.Object({
38
+ id: Type.String(),
39
+ name: Type.String(),
40
+ }),
41
+ },
42
+ },
43
+ async (ctx, params) => {
44
+ // TODO: implement
45
+ return { id: params.id, name: 'Example' }
46
+ }
47
+ )
48
+
49
+ // RPC stream — `CreateStream`. Mounted at POST /api/{{kebab}}/stream-events/1 (SSE)
50
+ export const { StreamEvents } = procs.CreateStream(
51
+ 'StreamEvents',
52
+ {
53
+ scope: '{{kebab}}',
54
+ version: 1,
55
+ description: 'Stream events for the given subject (rpc-stream / SSE).',
56
+ schema: {
57
+ params: Type.Object({
58
+ subject: Type.String(),
59
+ }),
60
+ yieldType: Type.Object({
61
+ seq: Type.Number(),
62
+ message: Type.String(),
63
+ }),
64
+ },
65
+ },
66
+ async function* (ctx, params) {
67
+ // ctx.signal is guaranteed for streams. Pass it to all downstream async work.
68
+ for (let seq = 0; seq < 3; seq++) {
69
+ if (ctx.signal.aborted) return
70
+ yield { seq, message: `event-${params.subject}-${seq}` }
71
+ }
72
+ }
73
+ )
74
+
75
+ // HTTP REST — `CreateHttp`. Mounted at GET /api/{{kebab}}/:id
76
+ export const { GetUser } = procs.CreateHttp(
77
+ 'GetUser',
78
+ {
79
+ path: '/{{kebab}}/:id',
80
+ method: 'get',
81
+ description: 'Fetch a user (REST).',
82
+ schema: {
83
+ req: {
84
+ pathParams: Type.Object({ id: Type.String() }),
85
+ },
86
+ res: {
87
+ body: Type.Object({
88
+ id: Type.String(),
89
+ name: Type.String(),
90
+ }),
91
+ },
92
+ },
93
+ },
94
+ async (ctx, { pathParams }) => {
95
+ // TODO: implement
96
+ return { id: pathParams.id, name: 'Example' }
97
+ }
98
+ )
99
+
100
+ // HTTP stream — `CreateHttpStream`. Mounted at GET /api/{{kebab}}/:id/watch (text/event-stream)
101
+ export const { WatchUser } = procs.CreateHttpStream(
102
+ 'WatchUser',
103
+ {
104
+ path: '/{{kebab}}/:id/watch',
105
+ method: 'get',
106
+ description: 'Server-sent stream of user updates (http-stream).',
107
+ schema: {
108
+ req: {
109
+ pathParams: Type.Object({ id: Type.String() }),
110
+ },
111
+ yield: Type.Object({
112
+ id: Type.String(),
113
+ revision: Type.Number(),
114
+ }),
115
+ },
116
+ },
117
+ async function* (ctx, { pathParams }) {
118
+ for (let revision = 1; revision <= 3; revision++) {
119
+ if (ctx.signal.aborted) return
120
+ yield { id: pathParams.id, revision }
121
+ }
122
+ }
123
+ )
124
+
125
+ // ─── Error Taxonomy ───────────────────────────────────────
126
+ // Declare the error classes this service throws. Framework errors
127
+ // (ProcedureValidationError → 400, ctx.error() → 500) are caught by the
128
+ // default taxonomy automatically. Add your own classes here — handlers just
129
+ // `throw` them and the builder serializes via this map. See
130
+ // docs/http-integrations.md#error-handling for the full contract.
131
+
132
+ const {{name}}Errors = defineErrorTaxonomy({
133
+ // Example — replace with your app's error classes:
134
+ // NotFoundError: { class: NotFoundError, statusCode: 404 },
135
+ // AuthError: { class: AuthError, statusCode: 401 },
136
+ })
137
+
138
+ // ─── Hono App Builder ─────────────────────────────────────
139
+ // One builder, one register() call, all four kinds. Config is stratified by
140
+ // kind: rpc.{onSuccess}, api.{queryParser, onSuccess}, stream.{...}. Cross-cutting
141
+ // concerns (errors, unknownError, onError, onRequestError, onRequestStart/End,
142
+ // pathPrefix) live at the top level. See src/implementations/http/hono/types.ts.
143
+
144
+ // Optional observers (uncomment as needed):
145
+ // onRequestStart: (c) => {...} // every inbound request (all kinds)
146
+ // rpc: { onSuccess: (procedure, c) => {...} } // successful RPC (Create) responses
147
+ // api: { onSuccess: (procedure, c) => {...} } // successful REST (CreateHttp) responses
148
+ // stream: { onStreamStart: (procedure, c, mode) => {...}, onStreamEnd: (procedure, c, mode) => {...} }
149
+
150
+ const {{name}}Builder = new HonoAppBuilder({
151
+ pathPrefix: '/api',
152
+ errors: {{name}}Errors,
153
+ unknownError: {
154
+ statusCode: 500,
155
+ toResponse: () => ({ name: 'InternalServerError', message: 'Unexpected error' }),
156
+ onCatch: (err, { procedure }) => console.error(`[${procedure.name}]`, err),
157
+ },
158
+ })
159
+ .register(procs, (c) => ({
160
+ userId: c.req.header('x-user-id') || 'anonymous',
161
+ requestId: c.req.header('x-request-id') || crypto.randomUUID(),
162
+ }))
163
+
164
+ export const {{name}}App = {{name}}Builder.build()
165
+
166
+ // Route map:
167
+ // POST /api/{{kebab}}/get-item/1 → RPC (Create)
168
+ // POST /api/{{kebab}}/stream-events/1 → RPC stream (CreateStream, SSE)
169
+ // GET /api/{{kebab}}/:id → REST (CreateHttp)
170
+ // GET /api/{{kebab}}/:id/watch → HTTP stream (CreateHttpStream, SSE)
171
+
172
+ // Documentation: {{name}}Builder.docs or {{name}}Builder.toDocEnvelope()
173
+ ```
174
+
175
+ ## Test — `{{Name}}.hono.test.ts`
176
+
177
+ ```typescript
178
+ import { describe, test, expect } from 'vitest'
179
+ import { {{name}}App } from './{{Name}}.hono'
180
+
181
+ describe('{{Name}} Hono — all four kinds', () => {
182
+ test('Create (RPC) — POST /api/{{kebab}}/get-item/1', async () => {
183
+ const res = await {{name}}App.request('/api/{{kebab}}/get-item/1', {
184
+ method: 'POST',
185
+ headers: { 'Content-Type': 'application/json' },
186
+ body: JSON.stringify({ id: 'item-1' }),
187
+ })
188
+ expect(res.status).toBe(200)
189
+ expect(await res.json()).toEqual({ id: 'item-1', name: 'Example' })
190
+ })
191
+
192
+ test('CreateStream (rpc-stream) — POST /api/{{kebab}}/stream-events/1 yields SSE', async () => {
193
+ const res = await {{name}}App.request('/api/{{kebab}}/stream-events/1', {
194
+ method: 'POST',
195
+ headers: { 'Content-Type': 'application/json' },
196
+ body: JSON.stringify({ subject: 'orders' }),
197
+ })
198
+ expect(res.status).toBe(200)
199
+ expect(res.headers.get('content-type') ?? '').toContain('text/event-stream')
200
+
201
+ const text = await res.text()
202
+ // Yielded events are emitted as SSE `data:` frames.
203
+ expect(text).toContain('event-orders-0')
204
+ expect(text).toContain('event-orders-2')
205
+ })
206
+
207
+ test('CreateHttp (REST) — GET /api/{{kebab}}/:id', async () => {
208
+ const res = await {{name}}App.request('/api/{{kebab}}/u-1')
209
+ expect(res.status).toBe(200)
210
+ expect(await res.json()).toEqual({ id: 'u-1', name: 'Example' })
211
+ })
212
+
213
+ test('CreateHttpStream (http-stream) — GET /api/{{kebab}}/:id/watch yields SSE', async () => {
214
+ const res = await {{name}}App.request('/api/{{kebab}}/u-1/watch')
215
+ expect(res.status).toBe(200)
216
+ expect(res.headers.get('content-type') ?? '').toContain('text/event-stream')
217
+
218
+ const text = await res.text()
219
+ expect(text).toContain('"revision":1')
220
+ expect(text).toContain('"revision":3')
221
+ })
222
+ })
223
+ ```
@@ -26,18 +26,15 @@ import { ProcedureError, ProcedureValidationError, ProcedureYieldValidationError
26
26
  // HTTP types
27
27
  import type { RPCConfig, RPCHttpRouteDoc, StreamHttpRouteDoc, StreamMode } from 'ts-procedures/http'
28
28
 
29
- // Express RPC
30
- import { ExpressRPCAppBuilder } from 'ts-procedures/express-rpc'
31
-
32
29
  // Hono RPC
33
- import { HonoRPCAppBuilder } from 'ts-procedures/hono-rpc'
30
+ import { HonoAppBuilder } from 'ts-procedures/hono'
34
31
 
35
32
  // Hono Streaming
36
- import { HonoStreamAppBuilder, sse } from 'ts-procedures/hono-stream'
33
+ import { HonoAppBuilder, sse } from 'ts-procedures/hono'
37
34
 
38
35
  // Hono API (REST-style)
39
- import { HonoAPIAppBuilder } from 'ts-procedures/hono-api'
40
- import type { APIConfig, APIInput } from 'ts-procedures/hono-api'
36
+ import { HonoAppBuilder } from 'ts-procedures/hono'
37
+ import type { APIConfig, APIInput } from 'ts-procedures/hono'
41
38
 
42
39
  // Doc Registry — compose route docs from multiple builders
43
40
  import { DocRegistry } from 'ts-procedures/http-docs'
@@ -62,6 +59,8 @@ import type { DocEnvelope, HeaderDoc, ErrorDoc } from 'ts-procedures/http-docs'
62
59
 
63
60
  8. **getProcedures() for introspection.** Returns all registered procedures with metadata.
64
61
 
62
+ 9. **`Procedures({ config: { noRuntimeValidation: true } })` skips per-call AJV validation** for every procedure on the factory (both `Create` and `CreateStream`, both `schema.params` and `schema.input`). Shape is `noRuntimeValidation?: true` — only `true` is accepted. JSON Schema is still computed at registration time, so codegen and `info.schema` are unaffected; only the validator runs are bypassed. **Never enable this on a factory whose handlers are reachable from public/untrusted callers** — coerceTypes and removeAdditional also stop running. Reserve for trusted internal factories whose callers are already type-checked at build time. Independent of the per-call `ctx.isPrevalidated` escape hatch used by HTTP builders.
63
+
65
64
  ## Procedure Pattern
66
65
 
67
66
  ```typescript
@@ -112,31 +111,12 @@ const { StreamEvents } = CreateStream(
112
111
  )
113
112
  ```
114
113
 
115
- ## Express RPC Pattern
116
-
117
- ```typescript
118
- import { ExpressRPCAppBuilder } from 'ts-procedures/express-rpc'
119
- import type { RPCConfig } from 'ts-procedures/http'
120
-
121
- const RPC = Procedures<AppContext, RPCConfig>()
122
-
123
- RPC.Create('GetUser', {
124
- scope: 'users', version: 1,
125
- schema: { params: Type.Object({ id: Type.String() }) },
126
- }, async (ctx, params) => fetchUser(params.id))
127
-
128
- const app = new ExpressRPCAppBuilder({ pathPrefix: '/api' })
129
- .register(RPC, async (req) => ({ userId: await authenticate(req) }))
130
- .build()
131
- // POST /api/users/get-user/1
132
- ```
133
-
134
114
  ## Hono RPC Pattern
135
115
 
136
116
  ```typescript
137
- import { HonoRPCAppBuilder } from 'ts-procedures/hono-rpc'
117
+ import { HonoAppBuilder } from 'ts-procedures/hono'
138
118
 
139
- const app = new HonoRPCAppBuilder({ pathPrefix: '/api' })
119
+ const app = new HonoAppBuilder({ pathPrefix: '/api' })
140
120
  .register(RPC, (c) => ({ userId: c.req.header('x-user-id') }))
141
121
  .build()
142
122
  ```
@@ -144,7 +124,7 @@ const app = new HonoRPCAppBuilder({ pathPrefix: '/api' })
144
124
  ## Hono Streaming Pattern
145
125
 
146
126
  ```typescript
147
- import { HonoStreamAppBuilder, sse } from 'ts-procedures/hono-stream'
127
+ import { HonoAppBuilder, sse } from 'ts-procedures/hono'
148
128
 
149
129
  const StreamRPC = Procedures<AppContext, RPCConfig>()
150
130
 
@@ -158,43 +138,53 @@ StreamRPC.CreateStream('Feed', {
158
138
  }
159
139
  })
160
140
 
161
- const app = new HonoStreamAppBuilder({ defaultStreamMode: 'sse' })
141
+ const app = new HonoAppBuilder({ defaultStreamMode: 'sse' })
162
142
  .register(StreamRPC, (c) => ({ userId: c.req.header('x-user-id') }))
163
143
  .build()
164
144
  // GET|POST /events/feed/1
165
145
  ```
166
146
 
167
- ## Hono API Pattern (REST-style)
147
+ ## Hono API Pattern (REST-style) — v8 `CreateHttp`
148
+
149
+ In v8, HTTP routes use `CreateHttp` (not `Create + APIConfig`). `schema.input` is renamed `schema.req`. The factory needs no `APIConfig` type parameter.
168
150
 
169
151
  ```typescript
170
- import { HonoAPIAppBuilder } from 'ts-procedures/hono-api'
171
- import type { APIConfig } from 'ts-procedures/http'
152
+ import { HonoAppBuilder } from 'ts-procedures/hono'
172
153
 
173
- const API = Procedures<AppContext, APIConfig>()
154
+ const API = Procedures<AppContext>()
174
155
 
175
- API.Create('GetUser', {
156
+ API.CreateHttp('GetUser', {
176
157
  path: '/users/:id', method: 'get',
177
158
  schema: {
178
- input: { pathParams: Type.Object({ id: Type.String() }) },
159
+ req: { pathParams: Type.Object({ id: Type.String() }) },
160
+ res: { body: Type.Object({ id: Type.String(), name: Type.String() }) },
179
161
  },
180
162
  }, async (ctx, { pathParams }) => fetchUser(pathParams.id))
181
163
 
182
- API.Create('CreateUser', {
164
+ API.CreateHttp('CreateUser', {
183
165
  path: '/users', method: 'post',
184
166
  schema: {
185
- input: { body: Type.Object({ name: Type.String() }) },
167
+ req: { body: Type.Object({ name: Type.String() }) },
186
168
  },
187
169
  }, async (ctx, { body }) => createUser(body))
188
170
 
189
- const app = new HonoAPIAppBuilder({ pathPrefix: '/api' })
171
+ const app = new HonoAppBuilder({ pathPrefix: '/api' })
190
172
  .register(API, (c) => ({ userId: c.req.header('x-user-id') }))
191
173
  .build()
192
174
  // GET /api/users/:id → 200, POST /api/users → 201
193
175
  ```
194
176
 
177
+ **v7 → v8 migration:**
178
+
179
+ 1. `Procedures<Ctx, APIConfig>()` → `Procedures<Ctx>()`
180
+ 2. `.Create(` → `.CreateHttp(` for HTTP routes
181
+ 3. `schema.input` → `schema.req` (same channels: `pathParams`, `query`, `body`, `headers`)
182
+ 4. Move response type to `schema.res.body` (optional)
183
+ 5. Re-run `npx ts-procedures-codegen`
184
+
195
185
  ## Astro adapter
196
186
 
197
- Catch-all endpoint pattern. Build Hono apps once with HonoAPI/RPC/Stream builders, mount via `createAstroHandler` in `src/pages/api/[...rest].ts` with `pathPrefix: '/api'`. Read Astro context inside factory closures with `getAstroContext(c)`. Multi-app dispatch is first-non-404-wins. Express builders are not supported.
187
+ Catch-all endpoint pattern. Build Hono apps once with `HonoAppBuilder`, mount via `createAstroHandler` in `src/pages/api/[...rest].ts` with `pathPrefix: '/api'`. Read Astro context inside factory closures with `getAstroContext(c)`. Multi-app dispatch is first-non-404-wins.
198
188
 
199
189
  ## Error Handling
200
190
 
@@ -207,7 +197,7 @@ Catch-all endpoint pattern. Build Hono apps once with HonoAPI/RPC/Stream builder
207
197
 
208
198
  ### Error Taxonomy (required for custom errors)
209
199
 
210
- `defineErrorTaxonomy` maps error classes to HTTP responses declaratively. Works with every HTTP builder (`hono-api`, `hono-rpc`, `express-rpc`, `hono-stream` pre-stream).
200
+ `defineErrorTaxonomy` maps error classes to HTTP responses declaratively. Works with `HonoAppBuilder` for `rpc`, `http`, and pre-stream paths (`rpc-stream` / `http-stream`).
211
201
 
212
202
  Do NOT write `onError` `instanceof` ladders — that's anti-pattern #20. Use the taxonomy instead:
213
203
 
@@ -237,13 +227,13 @@ const appErrors = defineErrorTaxonomy({
237
227
  },
238
228
  })
239
229
 
240
- new HonoAPIAppBuilder({
230
+ new HonoAppBuilder({
241
231
  errors: appErrors,
242
232
  unknownError: { statusCode: 500, toResponse: () => ({ name: 'InternalServerError' }) },
243
233
  })
244
234
  ```
245
235
 
246
- Handlers throw the error classes directly — the builder auto-serializes. `onError` is the first-class imperative peer when you want to handle errors in one callback instead (both modes coexist). In v6 `HonoStreamAppBuilder.onPreStreamError` was renamed to `onError`. Cross-cutting `onRequestError` observer fires for every caught error.
236
+ Handlers throw the error classes directly — the builder auto-serializes. `onError` is the first-class imperative peer when you want to handle errors in one callback instead (both modes coexist). In v6 `HonoAppBuilder.onPreStreamError` was renamed to `onError`. Cross-cutting `onRequestError` observer fires for every caught error.
247
237
 
248
238
  ### Per-route errors (typed)
249
239
 
@@ -311,10 +301,7 @@ onRequestStart → factoryContext() → validation → onStreamStart → handler
311
301
  - **TypeBox** (`import { Type } from 'typebox'`)
312
302
 
313
303
  **Which HTTP implementation?**
314
- - Express → `ExpressRPCAppBuilder`
315
- - Hono (standard) → `HonoRPCAppBuilder`
316
- - Hono (streaming) → `HonoStreamAppBuilder`
317
- - Hono (REST-style, per-channel input) → `HonoAPIAppBuilder`
304
+ - Hono (RPC, streams, REST, REST streams) → `HonoAppBuilder`
318
305
 
319
306
  **Stream mode?**
320
307
  - Browser EventSource → `'sse'` (default)
@@ -327,13 +314,14 @@ onRequestStart → factoryContext() → validation → onStreamStart → handler
327
314
  3. **Never put validation logic in handler** — use `schema.params`
328
315
  4. **Never ignore ctx.signal** — pass to all async calls
329
316
  5. **Never skip signal.aborted check in stream loops** — causes resource leaks
330
- 6. **Never register Create procedures with HonoStreamAppBuilder** — they're silently ignored
317
+ 6. **Never register Create procedures with HonoAppBuilder** — they're silently ignored
331
318
  7. **Never use plain JSON Schema objects** — use TypeBox builders
332
319
  8. **Never swallow errors without re-throwing** — hides failures
333
320
  9. **Never assume extra params fields survive** — `removeAdditional: true` strips them
334
321
  10. **Never manually parse types AJV coerces** — `coerceTypes: true` handles it
335
322
  11. **Never define both schema.params and schema.input** — mutually exclusive, throws ProcedureRegistrationError
336
323
  12. **Never catch raw DOMException/TypeError from generated callables** — catch `ClientTimeoutError`, `ClientAbortError`, `ClientNetworkError` instead; or use `.safe()` for Result-based narrowing
324
+ 13. **Never use `Create` for HTTP routes (v8+)** — use `CreateHttp` (unary) or `CreateHttpStream` (streaming); `schema.input` → `schema.req`; `Procedures<Ctx, APIConfig>()` → `Procedures<Ctx>()`
337
325
 
338
326
  ## Testing
339
327
 
@@ -26,18 +26,15 @@ import { ProcedureError, ProcedureValidationError, ProcedureYieldValidationError
26
26
  // HTTP types
27
27
  import type { RPCConfig, RPCHttpRouteDoc, StreamHttpRouteDoc, StreamMode } from 'ts-procedures/http'
28
28
 
29
- // Express RPC
30
- import { ExpressRPCAppBuilder } from 'ts-procedures/express-rpc'
31
-
32
29
  // Hono RPC
33
- import { HonoRPCAppBuilder } from 'ts-procedures/hono-rpc'
30
+ import { HonoAppBuilder } from 'ts-procedures/hono'
34
31
 
35
32
  // Hono Streaming
36
- import { HonoStreamAppBuilder, sse } from 'ts-procedures/hono-stream'
33
+ import { HonoAppBuilder, sse } from 'ts-procedures/hono'
37
34
 
38
35
  // Hono API (REST-style)
39
- import { HonoAPIAppBuilder } from 'ts-procedures/hono-api'
40
- import type { APIConfig, APIInput } from 'ts-procedures/hono-api'
36
+ import { HonoAppBuilder } from 'ts-procedures/hono'
37
+ import type { APIConfig, APIInput } from 'ts-procedures/hono'
41
38
 
42
39
  // Doc Registry — compose route docs from multiple builders
43
40
  import { DocRegistry } from 'ts-procedures/http-docs'
@@ -62,6 +59,8 @@ import type { DocEnvelope, HeaderDoc, ErrorDoc } from 'ts-procedures/http-docs'
62
59
 
63
60
  8. **getProcedures() for introspection.** Returns all registered procedures with metadata.
64
61
 
62
+ 9. **`Procedures({ config: { noRuntimeValidation: true } })` skips per-call AJV validation** for every procedure on the factory (both `Create` and `CreateStream`, both `schema.params` and `schema.input`). Shape is `noRuntimeValidation?: true` — only `true` is accepted. JSON Schema is still computed at registration time, so codegen and `info.schema` are unaffected; only the validator runs are bypassed. **Never enable this on a factory whose handlers are reachable from public/untrusted callers** — coerceTypes and removeAdditional also stop running. Reserve for trusted internal factories whose callers are already type-checked at build time. Independent of the per-call `ctx.isPrevalidated` escape hatch used by HTTP builders.
63
+
65
64
  ## Procedure Pattern
66
65
 
67
66
  ```typescript
@@ -112,31 +111,12 @@ const { StreamEvents } = CreateStream(
112
111
  )
113
112
  ```
114
113
 
115
- ## Express RPC Pattern
116
-
117
- ```typescript
118
- import { ExpressRPCAppBuilder } from 'ts-procedures/express-rpc'
119
- import type { RPCConfig } from 'ts-procedures/http'
120
-
121
- const RPC = Procedures<AppContext, RPCConfig>()
122
-
123
- RPC.Create('GetUser', {
124
- scope: 'users', version: 1,
125
- schema: { params: Type.Object({ id: Type.String() }) },
126
- }, async (ctx, params) => fetchUser(params.id))
127
-
128
- const app = new ExpressRPCAppBuilder({ pathPrefix: '/api' })
129
- .register(RPC, async (req) => ({ userId: await authenticate(req) }))
130
- .build()
131
- // POST /api/users/get-user/1
132
- ```
133
-
134
114
  ## Hono RPC Pattern
135
115
 
136
116
  ```typescript
137
- import { HonoRPCAppBuilder } from 'ts-procedures/hono-rpc'
117
+ import { HonoAppBuilder } from 'ts-procedures/hono'
138
118
 
139
- const app = new HonoRPCAppBuilder({ pathPrefix: '/api' })
119
+ const app = new HonoAppBuilder({ pathPrefix: '/api' })
140
120
  .register(RPC, (c) => ({ userId: c.req.header('x-user-id') }))
141
121
  .build()
142
122
  ```
@@ -144,7 +124,7 @@ const app = new HonoRPCAppBuilder({ pathPrefix: '/api' })
144
124
  ## Hono Streaming Pattern
145
125
 
146
126
  ```typescript
147
- import { HonoStreamAppBuilder, sse } from 'ts-procedures/hono-stream'
127
+ import { HonoAppBuilder, sse } from 'ts-procedures/hono'
148
128
 
149
129
  const StreamRPC = Procedures<AppContext, RPCConfig>()
150
130
 
@@ -158,43 +138,53 @@ StreamRPC.CreateStream('Feed', {
158
138
  }
159
139
  })
160
140
 
161
- const app = new HonoStreamAppBuilder({ defaultStreamMode: 'sse' })
141
+ const app = new HonoAppBuilder({ defaultStreamMode: 'sse' })
162
142
  .register(StreamRPC, (c) => ({ userId: c.req.header('x-user-id') }))
163
143
  .build()
164
144
  // GET|POST /events/feed/1
165
145
  ```
166
146
 
167
- ## Hono API Pattern (REST-style)
147
+ ## Hono API Pattern (REST-style) — v8 `CreateHttp`
148
+
149
+ In v8, HTTP routes use `CreateHttp` (not `Create + APIConfig`). `schema.input` is renamed `schema.req`. The factory needs no `APIConfig` type parameter.
168
150
 
169
151
  ```typescript
170
- import { HonoAPIAppBuilder } from 'ts-procedures/hono-api'
171
- import type { APIConfig } from 'ts-procedures/http'
152
+ import { HonoAppBuilder } from 'ts-procedures/hono'
172
153
 
173
- const API = Procedures<AppContext, APIConfig>()
154
+ const API = Procedures<AppContext>()
174
155
 
175
- API.Create('GetUser', {
156
+ API.CreateHttp('GetUser', {
176
157
  path: '/users/:id', method: 'get',
177
158
  schema: {
178
- input: { pathParams: Type.Object({ id: Type.String() }) },
159
+ req: { pathParams: Type.Object({ id: Type.String() }) },
160
+ res: { body: Type.Object({ id: Type.String(), name: Type.String() }) },
179
161
  },
180
162
  }, async (ctx, { pathParams }) => fetchUser(pathParams.id))
181
163
 
182
- API.Create('CreateUser', {
164
+ API.CreateHttp('CreateUser', {
183
165
  path: '/users', method: 'post',
184
166
  schema: {
185
- input: { body: Type.Object({ name: Type.String() }) },
167
+ req: { body: Type.Object({ name: Type.String() }) },
186
168
  },
187
169
  }, async (ctx, { body }) => createUser(body))
188
170
 
189
- const app = new HonoAPIAppBuilder({ pathPrefix: '/api' })
171
+ const app = new HonoAppBuilder({ pathPrefix: '/api' })
190
172
  .register(API, (c) => ({ userId: c.req.header('x-user-id') }))
191
173
  .build()
192
174
  // GET /api/users/:id → 200, POST /api/users → 201
193
175
  ```
194
176
 
177
+ **v7 → v8 migration:**
178
+
179
+ 1. `Procedures<Ctx, APIConfig>()` → `Procedures<Ctx>()`
180
+ 2. `.Create(` → `.CreateHttp(` for HTTP routes
181
+ 3. `schema.input` → `schema.req` (same channels: `pathParams`, `query`, `body`, `headers`)
182
+ 4. Move response type to `schema.res.body` (optional)
183
+ 5. Re-run `npx ts-procedures-codegen`
184
+
195
185
  ## Astro adapter
196
186
 
197
- Catch-all endpoint pattern. Build Hono apps once with HonoAPI/RPC/Stream builders, mount via `createAstroHandler` in `src/pages/api/[...rest].ts` with `pathPrefix: '/api'`. Read Astro context inside factory closures with `getAstroContext(c)`. Multi-app dispatch is first-non-404-wins. Express builders are not supported.
187
+ Catch-all endpoint pattern. Build Hono apps once with `HonoAppBuilder`, mount via `createAstroHandler` in `src/pages/api/[...rest].ts` with `pathPrefix: '/api'`. Read Astro context inside factory closures with `getAstroContext(c)`. Multi-app dispatch is first-non-404-wins.
198
188
 
199
189
  ## Error Handling
200
190
 
@@ -207,7 +197,7 @@ Catch-all endpoint pattern. Build Hono apps once with HonoAPI/RPC/Stream builder
207
197
 
208
198
  ### Error Taxonomy (required for custom errors)
209
199
 
210
- `defineErrorTaxonomy` maps error classes to HTTP responses declaratively. Works with every HTTP builder (`hono-api`, `hono-rpc`, `express-rpc`, `hono-stream` pre-stream).
200
+ `defineErrorTaxonomy` maps error classes to HTTP responses declaratively. Works with `HonoAppBuilder` for `rpc`, `http`, and pre-stream paths (`rpc-stream` / `http-stream`).
211
201
 
212
202
  Do NOT write `onError` `instanceof` ladders — that's anti-pattern #20. Use the taxonomy instead:
213
203
 
@@ -237,13 +227,13 @@ const appErrors = defineErrorTaxonomy({
237
227
  },
238
228
  })
239
229
 
240
- new HonoAPIAppBuilder({
230
+ new HonoAppBuilder({
241
231
  errors: appErrors,
242
232
  unknownError: { statusCode: 500, toResponse: () => ({ name: 'InternalServerError' }) },
243
233
  })
244
234
  ```
245
235
 
246
- Handlers throw the error classes directly — the builder auto-serializes. `onError` is the first-class imperative peer when you want to handle errors in one callback instead (both modes coexist). In v6 `HonoStreamAppBuilder.onPreStreamError` was renamed to `onError`. Cross-cutting `onRequestError` observer fires for every caught error.
236
+ Handlers throw the error classes directly — the builder auto-serializes. `onError` is the first-class imperative peer when you want to handle errors in one callback instead (both modes coexist). In v6 `HonoAppBuilder.onPreStreamError` was renamed to `onError`. Cross-cutting `onRequestError` observer fires for every caught error.
247
237
 
248
238
  ### Per-route errors (typed)
249
239
 
@@ -311,10 +301,7 @@ onRequestStart → factoryContext() → validation → onStreamStart → handler
311
301
  - **TypeBox** (`import { Type } from 'typebox'`)
312
302
 
313
303
  **Which HTTP implementation?**
314
- - Express → `ExpressRPCAppBuilder`
315
- - Hono (standard) → `HonoRPCAppBuilder`
316
- - Hono (streaming) → `HonoStreamAppBuilder`
317
- - Hono (REST-style, per-channel input) → `HonoAPIAppBuilder`
304
+ - Hono (RPC, streams, REST, REST streams) → `HonoAppBuilder`
318
305
 
319
306
  **Stream mode?**
320
307
  - Browser EventSource → `'sse'` (default)
@@ -327,13 +314,14 @@ onRequestStart → factoryContext() → validation → onStreamStart → handler
327
314
  3. **Never put validation logic in handler** — use `schema.params`
328
315
  4. **Never ignore ctx.signal** — pass to all async calls
329
316
  5. **Never skip signal.aborted check in stream loops** — causes resource leaks
330
- 6. **Never register Create procedures with HonoStreamAppBuilder** — they're silently ignored
317
+ 6. **Never register Create procedures with HonoAppBuilder** — they're silently ignored
331
318
  7. **Never use plain JSON Schema objects** — use TypeBox builders
332
319
  8. **Never swallow errors without re-throwing** — hides failures
333
320
  9. **Never assume extra params fields survive** — `removeAdditional: true` strips them
334
321
  10. **Never manually parse types AJV coerces** — `coerceTypes: true` handles it
335
322
  11. **Never define both schema.params and schema.input** — mutually exclusive, throws ProcedureRegistrationError
336
323
  12. **Never catch raw DOMException/TypeError from generated callables** — catch `ClientTimeoutError`, `ClientAbortError`, `ClientNetworkError` instead; or use `.safe()` for Result-based narrowing
324
+ 13. **Never use `Create` for HTTP routes (v8+)** — use `CreateHttp` (unary) or `CreateHttpStream` (streaming); `schema.input` → `schema.req`; `Procedures<Ctx, APIConfig>()` → `Procedures<Ctx>()`
337
325
 
338
326
  ## Testing
339
327
 
@@ -84,7 +84,10 @@ export async function executeCall(config) {
84
84
  scope: descriptor.scope,
85
85
  });
86
86
  }
87
- // 8. Return the body
87
+ // 8. Return the body (or { body, headers } when the route declares res.headers)
88
+ if (descriptor.responseHeadersDeclared) {
89
+ return { body: response.body, headers: response.headers };
90
+ }
88
91
  return response.body;
89
92
  }
90
93
  /**
@@ -1 +1 @@
1
- {"version":3,"file":"call.js","sourceRoot":"","sources":["../../src/client/call.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"call.js","sourceRoot":"","sources":["../../src/client/call.ts"],"names":[],"mappings":"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"}