failproofai 1.0.10 → 1.0.11-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 (296) hide show
  1. package/.next/standalone/.next/BUILD_ID +1 -1
  2. package/.next/standalone/.next/build-manifest.json +6 -6
  3. package/.next/standalone/.next/prerender-manifest.json +4 -4
  4. package/.next/standalone/.next/required-server-files.json +1 -1
  5. package/.next/standalone/.next/server/app/_global-error/page/build-manifest.json +3 -3
  6. package/.next/standalone/.next/server/app/_global-error/page/server-reference-manifest.json +1 -1
  7. package/.next/standalone/.next/server/app/_global-error/page.js +4 -4
  8. package/.next/standalone/.next/server/app/_global-error/page.js.nft.json +1 -1
  9. package/.next/standalone/.next/server/app/_global-error/page_client-reference-manifest.js +1 -1
  10. package/.next/standalone/.next/server/app/_global-error.html +1 -1
  11. package/.next/standalone/.next/server/app/_global-error.meta +8 -0
  12. package/.next/standalone/.next/server/app/_global-error.rsc +7 -7
  13. package/.next/standalone/.next/server/app/_global-error.segments/__PAGE__.segment.rsc +6 -6
  14. package/.next/standalone/.next/server/app/_global-error.segments/_full.segment.rsc +7 -7
  15. package/.next/standalone/.next/server/app/_global-error.segments/_tree.segment.rsc +1 -1
  16. package/.next/standalone/.next/server/app/_not-found/page/build-manifest.json +3 -3
  17. package/.next/standalone/.next/server/app/_not-found/page/server-reference-manifest.json +1 -1
  18. package/.next/standalone/.next/server/app/_not-found/page.js +4 -4
  19. package/.next/standalone/.next/server/app/_not-found/page.js.nft.json +1 -1
  20. package/.next/standalone/.next/server/app/_not-found/page_client-reference-manifest.js +1 -1
  21. package/.next/standalone/.next/server/app/_not-found.html +1 -1
  22. package/.next/standalone/.next/server/app/_not-found.meta +8 -0
  23. package/.next/standalone/.next/server/app/_not-found.rsc +14 -14
  24. package/.next/standalone/.next/server/app/_not-found.segments/_full.segment.rsc +14 -14
  25. package/.next/standalone/.next/server/app/_not-found.segments/_not-found/__PAGE__.segment.rsc +13 -13
  26. package/.next/standalone/.next/server/app/_not-found.segments/_tree.segment.rsc +1 -1
  27. package/.next/standalone/.next/server/app/api/audit/invite/route.js +4 -4
  28. package/.next/standalone/.next/server/app/api/audit/invite/route.js.nft.json +1 -1
  29. package/.next/standalone/.next/server/app/api/audit/run/route.js +4 -4
  30. package/.next/standalone/.next/server/app/api/audit/run/route.js.nft.json +1 -1
  31. package/.next/standalone/.next/server/app/api/audit/status/route.js +1 -1
  32. package/.next/standalone/.next/server/app/api/audit/status/route.js.nft.json +1 -1
  33. package/.next/standalone/.next/server/app/api/auth/login-request/route.js +2 -2
  34. package/.next/standalone/.next/server/app/api/auth/login-request/route.js.nft.json +1 -1
  35. package/.next/standalone/.next/server/app/api/auth/login-verify/route.js +4 -4
  36. package/.next/standalone/.next/server/app/api/auth/login-verify/route.js.nft.json +1 -1
  37. package/.next/standalone/.next/server/app/api/auth/logout/route.js +3 -3
  38. package/.next/standalone/.next/server/app/api/auth/logout/route.js.nft.json +1 -1
  39. package/.next/standalone/.next/server/app/api/auth/status/route.js +3 -3
  40. package/.next/standalone/.next/server/app/api/auth/status/route.js.nft.json +1 -1
  41. package/.next/standalone/.next/server/app/api/download/[project]/[session]/route.js +1 -1
  42. package/.next/standalone/.next/server/app/api/download/[project]/[session]/route.js.nft.json +1 -1
  43. package/.next/standalone/.next/server/app/audit/page/build-manifest.json +3 -3
  44. package/.next/standalone/.next/server/app/audit/page/server-reference-manifest.json +2 -2
  45. package/.next/standalone/.next/server/app/audit/page.js +4 -4
  46. package/.next/standalone/.next/server/app/audit/page.js.nft.json +1 -1
  47. package/.next/standalone/.next/server/app/audit/page_client-reference-manifest.js +1 -1
  48. package/.next/standalone/.next/server/app/index.html +1 -1
  49. package/.next/standalone/.next/server/app/index.meta +8 -0
  50. package/.next/standalone/.next/server/app/index.rsc +14 -14
  51. package/.next/standalone/.next/server/app/index.segments/__PAGE__.segment.rsc +13 -13
  52. package/.next/standalone/.next/server/app/index.segments/_full.segment.rsc +14 -14
  53. package/.next/standalone/.next/server/app/index.segments/_tree.segment.rsc +1 -1
  54. package/.next/standalone/.next/server/app/page/build-manifest.json +3 -3
  55. package/.next/standalone/.next/server/app/page/server-reference-manifest.json +1 -1
  56. package/.next/standalone/.next/server/app/page.js +4 -4
  57. package/.next/standalone/.next/server/app/page.js.nft.json +1 -1
  58. package/.next/standalone/.next/server/app/page_client-reference-manifest.js +1 -1
  59. package/.next/standalone/.next/server/app/policies/page/build-manifest.json +3 -3
  60. package/.next/standalone/.next/server/app/policies/page/server-reference-manifest.json +14 -14
  61. package/.next/standalone/.next/server/app/policies/page.js +8 -8
  62. package/.next/standalone/.next/server/app/policies/page.js.nft.json +1 -1
  63. package/.next/standalone/.next/server/app/policies/page_client-reference-manifest.js +1 -1
  64. package/.next/standalone/.next/server/app/project/[name]/page/build-manifest.json +3 -3
  65. package/.next/standalone/.next/server/app/project/[name]/page/server-reference-manifest.json +1 -1
  66. package/.next/standalone/.next/server/app/project/[name]/page.js +5 -5
  67. package/.next/standalone/.next/server/app/project/[name]/page.js.nft.json +1 -1
  68. package/.next/standalone/.next/server/app/project/[name]/page_client-reference-manifest.js +1 -1
  69. package/.next/standalone/.next/server/app/project/[name]/session/[sessionId]/page/build-manifest.json +3 -3
  70. package/.next/standalone/.next/server/app/project/[name]/session/[sessionId]/page/react-loadable-manifest.json +2 -2
  71. package/.next/standalone/.next/server/app/project/[name]/session/[sessionId]/page/server-reference-manifest.json +2 -2
  72. package/.next/standalone/.next/server/app/project/[name]/session/[sessionId]/page.js +5 -5
  73. package/.next/standalone/.next/server/app/project/[name]/session/[sessionId]/page.js.nft.json +1 -1
  74. package/.next/standalone/.next/server/app/project/[name]/session/[sessionId]/page_client-reference-manifest.js +1 -1
  75. package/.next/standalone/.next/server/app/projects/page/build-manifest.json +3 -3
  76. package/.next/standalone/.next/server/app/projects/page/server-reference-manifest.json +1 -1
  77. package/.next/standalone/.next/server/app/projects/page.js +5 -5
  78. package/.next/standalone/.next/server/app/projects/page.js.nft.json +1 -1
  79. package/.next/standalone/.next/server/app/projects/page_client-reference-manifest.js +1 -1
  80. package/.next/standalone/.next/server/app/settings/page/build-manifest.json +3 -3
  81. package/.next/standalone/.next/server/app/settings/page/server-reference-manifest.json +8 -8
  82. package/.next/standalone/.next/server/app/settings/page.js +9 -9
  83. package/.next/standalone/.next/server/app/settings/page.js.nft.json +1 -1
  84. package/.next/standalone/.next/server/app/settings/page_client-reference-manifest.js +1 -1
  85. package/.next/standalone/.next/server/chunks/{[externals]__0qxhecv._.js → [externals]__0d7i9ea._.js} +2 -2
  86. package/.next/standalone/.next/server/chunks/{[externals]__0sg9-3p._.js → [externals]__0hjaw70._.js} +1 -1
  87. package/.next/standalone/.next/server/chunks/[externals]__1_9ze9b._.js +3 -0
  88. package/.next/standalone/.next/server/chunks/[externals]__1oenfmn._.js +3 -0
  89. package/.next/standalone/.next/server/chunks/[root-of-the-server]__08dchfu._.js +1 -1
  90. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0ga9hs7._.js +3 -0
  91. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0l3yhx4._.js +2 -2
  92. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0moxohc._.js +22 -0
  93. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0o07qi9._.js +1 -1
  94. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0z2ll-a._.js +3 -0
  95. package/.next/standalone/.next/server/chunks/[root-of-the-server]__1adacul._.js +11 -11
  96. package/.next/standalone/.next/server/chunks/[root-of-the-server]__1autwno._.js +3 -0
  97. package/.next/standalone/.next/server/chunks/[root-of-the-server]__1v25n-6._.js +3 -0
  98. package/.next/standalone/.next/server/chunks/_09dz7xv._.js +1 -1
  99. package/.next/standalone/.next/server/chunks/_0tovk6q._.js +1 -1
  100. package/.next/standalone/.next/server/chunks/_0trp3yc._.js +1 -1
  101. package/.next/standalone/.next/server/chunks/_1ek68ln._.js +2 -2
  102. package/.next/standalone/.next/server/chunks/_1fz8m31._.js +1 -1
  103. package/.next/standalone/.next/server/chunks/_1jrv3hg._.js +3 -0
  104. package/.next/standalone/.next/server/chunks/_1nx8fim._.js +3 -0
  105. package/.next/standalone/.next/server/chunks/_1ogwigf._.js +1 -1
  106. package/.next/standalone/.next/server/chunks/{_1q5i8mb._.js → _1q27azx._.js} +2 -2
  107. package/.next/standalone/.next/server/chunks/lib_telemetry_ts_0dctyyw._.js +1 -1
  108. package/.next/standalone/.next/server/chunks/{node_modules_posthog-node_dist_entrypoints_index_node_mjs_0el6rg8._.js → node_modules_posthog-node_dist_entrypoints_index_node_mjs_0ol5pa3._.js} +2 -2
  109. package/.next/standalone/.next/server/chunks/{node_modules_posthog-node_dist_entrypoints_index_node_mjs_04op_ou._.js → node_modules_posthog-node_dist_entrypoints_index_node_mjs_1rqmk27._.js} +2 -2
  110. package/.next/standalone/.next/server/chunks/{node_modules_posthog-node_dist_entrypoints_index_node_mjs_0dr20uz._.js → node_modules_posthog-node_dist_entrypoints_index_node_mjs_1w7tiq4._.js} +2 -2
  111. package/.next/standalone/.next/server/chunks/package_json_[json]_cjs_1nxcc4v._.js +1 -1
  112. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__04usis8._.js +2 -2
  113. package/.next/standalone/.next/server/chunks/ssr/{[root-of-the-server]__1-bm5zf._.js → [root-of-the-server]__0502lat._.js} +1 -1
  114. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0_gn5iz._.js +4 -0
  115. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0f765xr._.js +4 -0
  116. package/.next/standalone/.next/server/chunks/ssr/{[root-of-the-server]__01bmjsj._.js → [root-of-the-server]__0h38gzz._.js} +1 -1
  117. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0hoaz1g._.js +4 -0
  118. package/.next/standalone/.next/server/chunks/ssr/{[root-of-the-server]__1ouobn4._.js → [root-of-the-server]__0mxmwtx._.js} +1 -1
  119. package/.next/standalone/.next/server/chunks/ssr/{[root-of-the-server]__19evfi8._.js → [root-of-the-server]__0uescqv._.js} +1 -1
  120. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__1484zv2._.js +3 -0
  121. package/.next/standalone/.next/server/chunks/ssr/{[root-of-the-server]__1mf3zp6._.js → [root-of-the-server]__19dutr7._.js} +4 -4
  122. package/.next/standalone/.next/server/chunks/ssr/{[root-of-the-server]__0oqrl71._.js → [root-of-the-server]__1_qv8oh._.js} +2 -2
  123. package/.next/standalone/.next/server/chunks/ssr/{[root-of-the-server]__1u6sn69._.js → [root-of-the-server]__1ab4ifb._.js} +1 -1
  124. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__1fbrk56._.js +4 -0
  125. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__1pprgri._.js +2 -2
  126. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__1um4yxn._.js +4 -0
  127. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__1wb4yt2._.js +4 -0
  128. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__1y3n3cn._.js +4 -0
  129. package/.next/standalone/.next/server/chunks/ssr/_08x1r5t._.js +1 -1
  130. package/.next/standalone/.next/server/chunks/ssr/_0bqoto4._.js +1 -1
  131. package/.next/standalone/.next/server/chunks/ssr/{_16pa9ht._.js → _0lnpwk8._.js} +2 -2
  132. package/.next/standalone/.next/server/chunks/ssr/{_0yq5_3a._.js → _15y8myg._.js} +1 -1
  133. package/.next/standalone/.next/server/chunks/ssr/_1gb0ifp._.js +2 -2
  134. package/.next/standalone/.next/server/chunks/ssr/{_042cgl1._.js → _1o95rf0._.js} +2 -2
  135. package/.next/standalone/.next/server/chunks/ssr/{_1zopuov._.js → _1thr5rf._.js} +2 -2
  136. package/.next/standalone/.next/server/chunks/ssr/_next-internal_server_app_policies_page_actions_1sp2-yo.js +12 -14
  137. package/.next/standalone/.next/server/chunks/ssr/app_actions_get-scheduled-audit_ts_0ei9sni._.js +1 -1
  138. package/.next/standalone/.next/server/chunks/ssr/app_audit__components_audit-dashboard_tsx_0p9ud47._.js +1 -1
  139. package/.next/standalone/.next/server/chunks/ssr/app_global-error_tsx_1kp6l3x._.js +1 -1
  140. package/.next/standalone/.next/server/chunks/ssr/app_policies_hooks-client_tsx_19dqvpc._.js +1 -1
  141. package/.next/standalone/.next/server/chunks/ssr/app_settings_02tf1h4._.js +1 -1
  142. package/.next/standalone/.next/server/chunks/ssr/node_modules_1hl81y4._.js +1 -1
  143. package/.next/standalone/.next/server/chunks/ssr/node_modules_next_dist_0nkkbfv._.js +6 -0
  144. package/.next/standalone/.next/server/chunks/ssr/src_hooks_fp-config_ts_04t589g._.js +1 -1
  145. package/.next/standalone/.next/server/chunks/ssr/src_hooks_fp-home_ts_0je3xkv._.js +1 -1
  146. package/.next/standalone/.next/server/middleware-build-manifest.js +6 -6
  147. package/.next/standalone/.next/server/middleware.js +1 -1
  148. package/.next/standalone/.next/server/pages/404.html +1 -1
  149. package/.next/standalone/.next/server/pages/500.html +1 -1
  150. package/.next/standalone/.next/server/server-reference-manifest.js +1 -1
  151. package/.next/standalone/.next/server/server-reference-manifest.json +23 -23
  152. package/.next/standalone/.next/static/chunks/{03h3b-uomi7_d.js → 0pra9i676pym1.js} +1 -1
  153. package/.next/standalone/.next/static/chunks/{2kj826h1w9r47.js → 1-lpi0m-hc1kb.js} +1 -1
  154. package/.next/standalone/.next/static/chunks/{3ob2161ap37ul.js → 17yvyyblr_eb5.js} +1 -1
  155. package/.next/standalone/.next/static/chunks/{3nkc2jlgyygda.js → 1mylcr99gccyz.js} +1 -1
  156. package/.next/standalone/.next/static/chunks/{2j92xul6y24_v.js → 1wozchtn2etvh.js} +1 -1
  157. package/.next/standalone/.next/static/chunks/{3mjfvng11xnoo.js → 23thtelz1a-ur.js} +2 -2
  158. package/.next/standalone/.next/static/chunks/{1fqukzzowjflt.js → 2bc17tohgs4bs.js} +1 -1
  159. package/.next/standalone/.next/static/chunks/{3u1s8dsqiean5.js → 2xq-ejo8kti18.js} +1 -1
  160. package/.next/standalone/.next/static/chunks/3-_pth_c9n938.js +1 -0
  161. package/.next/standalone/.next/static/chunks/{3i8rg2fv9nd6e.js → 3n46e45atic-m.js} +1 -1
  162. package/.next/standalone/.next/static/chunks/{078dofaxvjgpd.js → 3q7sndqftqhw9.js} +1 -1
  163. package/.next/standalone/.next/static/chunks/{0542cuk_va8g1.js → 3sg07wnn969xq.js} +1 -1
  164. package/.next/standalone/.next/static/chunks/{turbopack-11dn2pegmg9_9.js → turbopack-1opxka4dtjbc5.js} +1 -1
  165. package/.next/standalone/app/actions/install-hooks-web.ts +10 -2
  166. package/.next/standalone/hermes-plugin/plugin.yaml +1 -1
  167. package/.next/standalone/node_modules/@next/env/package.json +1 -1
  168. package/.next/standalone/node_modules/next/dist/build/swc/index.js +1 -1
  169. package/.next/standalone/node_modules/next/dist/compiled/hash.js/sha256/256.js +1 -0
  170. package/.next/standalone/node_modules/next/dist/compiled/hash.js/sha256/package.json +1 -0
  171. package/.next/standalone/node_modules/next/dist/compiled/next-server/app-page-turbo-experimental.runtime.prod.js +17 -17
  172. package/.next/standalone/node_modules/next/dist/compiled/next-server/app-page-turbo.runtime.prod.js +18 -18
  173. package/.next/standalone/node_modules/next/dist/compiled/next-server/app-route-turbo.runtime.prod.js +3 -3
  174. package/.next/standalone/node_modules/next/dist/compiled/next-server/pages-turbo.runtime.prod.js +13 -13
  175. package/.next/standalone/node_modules/next/dist/lib/patch-incorrect-lockfile.js +3 -3
  176. package/.next/standalone/node_modules/next/dist/server/base-server.js +1 -2
  177. package/.next/standalone/node_modules/next/dist/server/config.js +1 -1
  178. package/.next/standalone/node_modules/next/dist/server/dev/hot-reloader-turbopack.js +2 -2
  179. package/.next/standalone/node_modules/next/dist/server/dev/hot-reloader-webpack.js +1 -1
  180. package/.next/standalone/node_modules/next/dist/server/image-optimizer.js +265 -53
  181. package/.next/standalone/node_modules/next/dist/server/lib/app-info-log.js +1 -1
  182. package/.next/standalone/node_modules/next/dist/server/lib/incremental-cache/file-system-cache.js +177 -19
  183. package/.next/standalone/node_modules/next/dist/server/lib/incremental-cache/index.js +36 -17
  184. package/.next/standalone/node_modules/next/dist/server/lib/incremental-cache/shared-cache-controls.external.js +14 -6
  185. package/.next/standalone/node_modules/next/dist/server/lib/match-next-data-pathname.js +3 -1
  186. package/.next/standalone/node_modules/next/dist/server/lib/node-fs-methods.js +14 -0
  187. package/.next/standalone/node_modules/next/dist/server/lib/route-cache-key.js +77 -0
  188. package/.next/standalone/node_modules/next/dist/server/lib/router-utils/block-cross-site-dev.js +9 -11
  189. package/.next/standalone/node_modules/next/dist/server/lib/start-server.js +1 -1
  190. package/.next/standalone/node_modules/next/dist/server/mcp/get-mcp-middleware.js +4 -2
  191. package/.next/standalone/node_modules/next/dist/server/next-server.js +7 -3
  192. package/.next/standalone/node_modules/next/dist/server/response-cache/index.js +32 -16
  193. package/.next/standalone/node_modules/next/dist/server/route-matcher-providers/app-page-route-matcher-provider.js +2 -2
  194. package/.next/standalone/node_modules/next/dist/server/route-modules/pages/pages-handler.js +6 -1
  195. package/.next/standalone/node_modules/next/dist/server/route-modules/route-module.js +9 -2
  196. package/.next/standalone/node_modules/next/dist/server/use-cache/use-cache-wrapper.js +30 -29
  197. package/.next/standalone/node_modules/next/dist/shared/lib/router/utils/app-paths.js +18 -1
  198. package/.next/standalone/node_modules/next/dist/telemetry/anonymous-meta.js +1 -1
  199. package/.next/standalone/node_modules/next/dist/telemetry/events/swc-load-failure.js +1 -1
  200. package/.next/standalone/node_modules/next/dist/telemetry/events/version.js +2 -2
  201. package/.next/standalone/node_modules/next/package.json +10 -10
  202. package/.next/standalone/package.json +14 -11
  203. package/.next/standalone/sdk/python/README.md +41 -0
  204. package/.next/standalone/sdk/python/docs/README.md +1 -0
  205. package/.next/standalone/sdk/python/docs/otel/README.md +36 -0
  206. package/.next/standalone/sdk/python/docs/otel/examples/agent_trace.py +30 -0
  207. package/.next/standalone/sdk/python/docs/otel/examples/quickstart.py +22 -0
  208. package/.next/standalone/sdk/python/failproofai_sdk/__init__.py +8 -0
  209. package/.next/standalone/sdk/python/failproofai_sdk/integrations/__init__.py +3 -0
  210. package/.next/standalone/sdk/python/failproofai_sdk/integrations/otel.py +189 -0
  211. package/.next/standalone/sdk/python/pyproject.toml +2 -1
  212. package/.next/standalone/sdk/python/tests/test_docs.py +16 -3
  213. package/.next/standalone/sdk/python/tests/test_integrations.py +1 -1
  214. package/.next/standalone/sdk/python/tests/test_otel.py +147 -0
  215. package/.next/standalone/sdk/python/tests/test_zero_dependencies.py +4 -1
  216. package/.next/standalone/sdk/python/uv.lock +258 -147
  217. package/.next/standalone/sdk/typescript/README.md +43 -0
  218. package/.next/standalone/sdk/typescript/integration/ai.test.ts +9 -2
  219. package/.next/standalone/sdk/typescript/package-lock.json +57 -5
  220. package/.next/standalone/sdk/typescript/package.json +2 -0
  221. package/.next/standalone/sdk/typescript/src/edge/index.ts +9 -0
  222. package/.next/standalone/sdk/typescript/src/index.ts +2 -0
  223. package/.next/standalone/sdk/typescript/src/integrations/index.ts +4 -1
  224. package/.next/standalone/sdk/typescript/src/integrations/otel.ts +204 -0
  225. package/.next/standalone/sdk/typescript/test/integrations.test.ts +1 -1
  226. package/.next/standalone/sdk/typescript/test/otel.test.ts +125 -0
  227. package/.next/standalone/server.js +1 -1
  228. package/bin/failproofai.mjs +653 -1077
  229. package/dist/cli.mjs +8781 -4050
  230. package/dist/worker.mjs +170 -62
  231. package/hermes-plugin/plugin.yaml +1 -1
  232. package/package.json +14 -11
  233. package/scripts/launch-facts.ts +157 -0
  234. package/scripts/launch-ready.ts +228 -0
  235. package/scripts/launch-screen.ts +202 -0
  236. package/scripts/launch.ts +106 -49
  237. package/scripts/skew-log-filter.ts +38 -0
  238. package/src/audit/cli-login.ts +39 -59
  239. package/src/audit/cli.ts +308 -228
  240. package/src/audit/index.ts +45 -2
  241. package/src/audit/schedule-cli.ts +83 -120
  242. package/src/audit/types.ts +31 -0
  243. package/src/hooks/agent-selection.ts +155 -0
  244. package/src/hooks/backfill-cli.ts +151 -137
  245. package/src/hooks/backfill-request.ts +149 -0
  246. package/src/hooks/cloud-connection.ts +1 -1
  247. package/src/hooks/cloud-enrollment-cli.ts +78 -28
  248. package/src/hooks/cloud-introspect.ts +3 -0
  249. package/src/hooks/collector-config.ts +10 -1
  250. package/src/hooks/config-status.ts +717 -0
  251. package/src/hooks/configure-wizard.ts +967 -988
  252. package/src/hooks/daemon-service.ts +16 -6
  253. package/src/hooks/did-you-mean.ts +185 -0
  254. package/src/hooks/flush-cli.ts +33 -7
  255. package/src/hooks/fp-config.ts +96 -0
  256. package/src/hooks/fp-home.ts +11 -0
  257. package/src/hooks/fp-reset.ts +102 -95
  258. package/src/hooks/handler.ts +4 -0
  259. package/src/hooks/harness-cli.ts +87 -138
  260. package/src/hooks/install-prompt.ts +38 -477
  261. package/src/hooks/integrations.ts +1 -1
  262. package/src/hooks/jev-cli.ts +183 -196
  263. package/src/hooks/manager.ts +554 -358
  264. package/src/hooks/onboarding-attempt.ts +11 -9
  265. package/src/hooks/otel-cli.ts +350 -0
  266. package/src/hooks/otel-output.ts +24 -0
  267. package/src/hooks/otel-writers.ts +215 -0
  268. package/src/hooks/pack-cli.ts +219 -204
  269. package/src/hooks/report-body.ts +50 -0
  270. package/src/hooks/safe-config-write.ts +4 -2
  271. package/src/hooks/session-pause-cli.ts +93 -73
  272. package/src/hooks/tui.ts +849 -389
  273. package/src/hooks/uninstall-cli.ts +136 -149
  274. package/src/hooks/untraced-note.ts +52 -0
  275. package/.next/standalone/.next/server/chunks/[externals]__19_pzeq._.js +0 -3
  276. package/.next/standalone/.next/server/chunks/[externals]__20kzpkf._.js +0 -3
  277. package/.next/standalone/.next/server/chunks/[root-of-the-server]__01eqny5._.js +0 -3
  278. package/.next/standalone/.next/server/chunks/[root-of-the-server]__05ja_05._.js +0 -3
  279. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0igxt32._.js +0 -3
  280. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0zyc_nm._.js +0 -3
  281. package/.next/standalone/.next/server/chunks/[root-of-the-server]__1ttrwnd._.js +0 -22
  282. package/.next/standalone/.next/server/chunks/_0bs-v8p._.js +0 -3
  283. package/.next/standalone/.next/server/chunks/_185gyk9._.js +0 -3
  284. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__056wjo4._.js +0 -4
  285. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0n0xg95._.js +0 -4
  286. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0rwtwpm._.js +0 -4
  287. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0yrsbd_._.js +0 -3
  288. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__11mayhe._.js +0 -4
  289. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__15578wp._.js +0 -4
  290. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__1m_svbe._.js +0 -4
  291. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__1q4p5b8._.js +0 -4
  292. package/.next/standalone/.next/server/chunks/ssr/node_modules_next_dist_1n3w9lb._.js +0 -6
  293. package/.next/standalone/.next/static/chunks/1lyg_puttohbc.js +0 -1
  294. /package/.next/standalone/.next/static/{ECs8__hcNabYV58WfDh-3 → xtcpqBNBdjQVerPMkI2HI}/_buildManifest.js +0 -0
  295. /package/.next/standalone/.next/static/{ECs8__hcNabYV58WfDh-3 → xtcpqBNBdjQVerPMkI2HI}/_clientMiddlewareManifest.js +0 -0
  296. /package/.next/standalone/.next/static/{ECs8__hcNabYV58WfDh-3 → xtcpqBNBdjQVerPMkI2HI}/_ssgManifest.js +0 -0
@@ -146,7 +146,37 @@ import {
146
146
  import { jevStats, type JevStats } from "./semantic/jev-stats";
147
147
  import { readCredentials, readJevCloudCredential, type JevCloudCredential } from "./fp-config";
148
148
  import type { JevRequest } from "./semantic/types";
149
- import { TOKEN_ON_ARGV, emptyState, nextStep, note, optsFor, rows, rule, stack, title, warning, type RenderOpts } from "./tui";
149
+ import { TOKEN_ON_ARGV, optsFor, paint, screenKit, stack, wrap, type RenderOpts } from "./tui";
150
+
151
+ // ── the 2026-10 look, for the jev result screens ─────────────────────────────
152
+ //
153
+ // The header names the subcommand and carries its outcome as meta, the way
154
+ // every action result does. Rows are the kit's kv rows, a note is grey prose,
155
+ // a warning is ▲ with the rest indented under it, and a next step is its lead
156
+ // and the command, the command never split.
157
+ function jevHeader(name: string, meta: string | undefined, opts: RenderOpts): string[] {
158
+ return [screenKit(opts).header(meta ? `${name} · ${meta}` : name)];
159
+ }
160
+ function jevRows(items: Array<[string, string]>, opts: RenderOpts): string[] {
161
+ return screenKit(opts).kv(items);
162
+ }
163
+ function jevNote(text: string, opts: RenderOpts): string[] {
164
+ const c = paint(opts.color ?? false);
165
+ return wrap(text, Math.max(20, (opts.cols ?? 80) - 2)).map((line) => ` ${c.ink3(line)}`);
166
+ }
167
+ function jevWarn(lines: string[], opts: RenderOpts): string[] {
168
+ const kit = screenKit(opts);
169
+ const width = Math.max(20, (opts.cols ?? 80) - 2);
170
+ return lines.flatMap((line, i) =>
171
+ wrap(line, width).map((part, j) => (i === 0 && j === 0 ? kit.caution(part) : ` ${part}`)),
172
+ );
173
+ }
174
+ function jevNext(cmd: string, lead: string | undefined, opts: RenderOpts): string[] {
175
+ const kit = screenKit(opts);
176
+ if (!lead) return [` ${kit.cmd(cmd)}`];
177
+ if (lead.length + 2 + cmd.length <= (opts.cols ?? 80)) return [`${lead} ${kit.cmd(cmd)}`];
178
+ return [...wrap(lead, Math.max(20, (opts.cols ?? 80) - 2)), ` ${kit.cmd(cmd)}`];
179
+ }
150
180
 
151
181
  export interface JevCliResult {
152
182
  lines: string[];
@@ -182,11 +212,13 @@ const liveModelListReader: JevModelListReader = (url, apiKey) => readJevModelLis
182
212
  const ok = (lines: string[], json?: string): JevCliResult => ({ lines, exitCode: 0, ...(json !== undefined ? { json } : {}) });
183
213
  const fail = (lines: string[], json?: string): JevCliResult => ({ lines, exitCode: 1, ...(json !== undefined ? { json } : {}) });
184
214
 
215
+ // The same usage rows as `jev --help`, so the usage printed after a mistake can
216
+ // never disagree with the help page.
185
217
  export const JEV_USAGE = [
186
218
  "Usage:",
187
- " failproofai jev --url <url> [--key-stdin | --token <token>] [options]",
188
- " failproofai jev setup --provider <kind> [--key-stdin | --key-from-env] [options]",
189
- " failproofai jev setup --provider failproofai [--mode off|observe|enforce] (FailproofAI Cloud: no key, no URL)",
219
+ " failproofai jev setup --provider <kind> --key-stdin",
220
+ " failproofai jev --url <url> --key-stdin",
221
+ " failproofai jev setup --provider failproofai",
190
222
  " failproofai jev status [--json]",
191
223
  " failproofai jev test [--json]",
192
224
  " failproofai jev models [--provider <kind>] [--url <base>] [--json]",
@@ -442,10 +474,11 @@ function remedy(code: string, provider?: JevProviderKind, message?: string): str
442
474
 
443
475
  /** The `jev status` activity block, from `jevStats()` (null when it could not be read). */
444
476
  export function jevStatsLines(stats: JevStats | null, opts: RenderOpts = {}): string[] {
477
+ const kit = screenKit(opts);
445
478
  const hours = stats ? Math.round(stats.windowMs / 3_600_000) : 24;
446
- const heading = rule(`last ${hours} hours`, opts);
447
- if (!stats) return stack(heading, note("Activity could not be read.", opts));
448
- if (stats.total === 0) return stack(heading, note(`No Jev evaluations recorded in the last ${hours} hours.`, opts));
479
+ const heading = kit.head("Activity", `last ${hours} hours`);
480
+ if (!stats) return [heading, " Activity could not be read."];
481
+ if (stats.total === 0) return [heading, " No Jev evaluations recorded."];
449
482
  const pct = (x: number) => `${(x * 100).toFixed(1)}%`;
450
483
  const reasons = Object.entries(stats.fallbackReasons)
451
484
  .sort((a, b) => b[1] - a[1])
@@ -464,19 +497,16 @@ export function jevStatsLines(stats: JevStats | null, opts: RenderOpts = {}): st
464
497
  // they turned observe mode on to watch.
465
498
  const observeClears = byPolicy(stats.observeClearsByPolicy);
466
499
  const ms = (v: number | null) => (v === null ? "—" : `${Math.round(v)} ms`);
467
- return stack(
500
+ return [
468
501
  heading,
469
- rows(
470
- [
471
- ["evaluations", String(stats.total)],
472
- ["fell back to regex", `${pct(stats.fallbackRate)}${reasons ? ` (${reasons})` : ""}`],
473
- ["latency", `p50 ${ms(stats.latencyP50Ms)} · p95 ${ms(stats.latencyP95Ms)}`],
474
- ["cleared", clears || "nothing"],
475
- ...(observeClears ? ([["would have cleared (observe)", observeClears]] as Array<[string, string]>) : []),
476
- ],
477
- opts,
478
- ),
479
- );
502
+ ...kit.kv([
503
+ ["evaluations", String(stats.total)],
504
+ ["fell back to regex", `${pct(stats.fallbackRate)}${reasons ? ` (${reasons})` : ""}`],
505
+ ["latency", `p50 ${ms(stats.latencyP50Ms)} · p95 ${ms(stats.latencyP95Ms)}`],
506
+ ["cleared", clears || "nothing"],
507
+ ...(observeClears ? ([["would have cleared (observe)", observeClears]] as Array<[string, string]>) : []),
508
+ ]),
509
+ ];
480
510
  }
481
511
 
482
512
  // ── setup ────────────────────────────────────────────────────────────────────
@@ -1069,8 +1099,8 @@ async function setupRun(argv: string[], deps: JevCliDeps, opts: RenderOpts): Pro
1069
1099
  const offBase = offProviderBase(cfg, route.endpoint);
1070
1100
  return ok(
1071
1101
  stack(
1072
- title("failproofai jev setup", `saved · ${provider} · ${cfg.mode ?? DEFAULT_JEV_MODE}`, opts),
1073
- rows(
1102
+ jevHeader("Jev setup", `saved · ${provider} · ${cfg.mode ?? DEFAULT_JEV_MODE}`, opts),
1103
+ jevRows(
1074
1104
  [
1075
1105
  ["provider", provider],
1076
1106
  ["endpoint", displayEndpoint(route.endpoint)],
@@ -1087,7 +1117,7 @@ async function setupRun(argv: string[], deps: JevCliDeps, opts: RenderOpts): Pro
1087
1117
  // to discover from the fallback counts that the URL they gave is not an
1088
1118
  // API base. So the file is written and what it will do is named.
1089
1119
  offBase
1090
- ? warning(
1120
+ ? jevWarn(
1091
1121
  [
1092
1122
  `Saved as given, but ${provider}'s API is at ${offBase.api}, and this URL sends requests to ${offBase.endpoint} instead.`,
1093
1123
  `Unless something of yours answers Jev requests at that path, every evaluation will fail there and hooks will fall back to regex — \`failproofai jev test\` says which it is in one request. To send requests back to ${provider}'s own API: failproofai jev setup --base-url default`,
@@ -1096,7 +1126,7 @@ async function setupRun(argv: string[], deps: JevCliDeps, opts: RenderOpts): Pro
1096
1126
  )
1097
1127
  : null,
1098
1128
  tightenedDir
1099
- ? note(
1129
+ ? jevNote(
1100
1130
  `${tightenedDir.path} was writable by other users, who could have replaced this file whatever its own permissions were; it is now ${tightenedDir.to}.`,
1101
1131
  opts,
1102
1132
  )
@@ -1105,11 +1135,11 @@ async function setupRun(argv: string[], deps: JevCliDeps, opts: RenderOpts): Pro
1105
1135
  // command line it came on is not — it is in this shell's history file and
1106
1136
  // was readable from /proc by anything running as this user while the
1107
1137
  // process lived.
1108
- tokenOnCommandLine ? warning(TOKEN_HISTORY_WARNING, opts) : null,
1109
- note("Hooks read this file on every tool call — no restart. Without it they run the regex policies exactly as before.", opts),
1138
+ tokenOnCommandLine ? jevWarn(TOKEN_HISTORY_WARNING, opts) : null,
1139
+ jevNote("Hooks read this file on every tool call — no restart. Without it they run the regex policies exactly as before.", opts),
1110
1140
  // Switched off, `jev test` only answers "not run — switched off": a next
1111
1141
  // step that leads nowhere is worse than none.
1112
- (cfg.mode ?? DEFAULT_JEV_MODE) === "off" ? null : nextStep("failproofai jev test", "Check it with one live request:", opts),
1142
+ (cfg.mode ?? DEFAULT_JEV_MODE) === "off" ? null : jevNext("failproofai jev test", "Check it with one live request:", opts),
1113
1143
  ),
1114
1144
  );
1115
1145
  }
@@ -1292,8 +1322,8 @@ async function cloudSetup(values: Map<string, string>, bools: Set<string>, opts:
1292
1322
  const shownMode = cfg.mode ?? DEFAULT_JEV_MODE;
1293
1323
  return ok(
1294
1324
  stack(
1295
- title("failproofai jev setup", `saved · FailproofAI Cloud · ${shownMode}`, opts),
1296
- rows(
1325
+ jevHeader("Jev setup", `saved · FailproofAI Cloud · ${shownMode}`, opts),
1326
+ jevRows(
1297
1327
  [
1298
1328
  ["provider", providerLabel(JEV_CLOUD_PROVIDER)],
1299
1329
  ["endpoint", shownEndpoint(JEV_CLOUD_PROVIDER, route.endpoint)],
@@ -1309,14 +1339,14 @@ async function cloudSetup(values: Map<string, string>, bools: Set<string>, opts:
1309
1339
  ],
1310
1340
  opts,
1311
1341
  ),
1312
- note("Hooks read this file on every tool call — no restart. Calls are charged to your FailproofAI Cloud org's plan.", opts),
1342
+ jevNote("Hooks read this file on every tool call — no restart. Calls are charged to your FailproofAI Cloud org's plan.", opts),
1313
1343
  // With no usable key, `jev test` only answers "not run": the step that
1314
1344
  // helps is the connection. Switched off, there is no step to take.
1315
1345
  shownMode === "off"
1316
1346
  ? null
1317
1347
  : keySource
1318
- ? nextStep("failproofai jev test", "Check it with one live request:", opts)
1319
- : nextStep(
1348
+ ? jevNext("failproofai jev test", "Check it with one live request:", opts)
1349
+ : jevNext(
1320
1350
  "failproofai config --token <key>",
1321
1351
  "Jev stays off until this machine is connected with a key that carries jev:evaluate (the \"machine\" preset on the dashboard's Keys page):",
1322
1352
  opts,
@@ -1509,35 +1539,38 @@ async function status(argv: string[], opts: RenderOpts): Promise<JevCliResult> {
1509
1539
  return inspection.status === "refused" ? fail([], json) : ok([], json);
1510
1540
  }
1511
1541
 
1542
+ // The design's jevStatus: the header, then `label value` rows — a status row
1543
+ // first, so every state answers "is Jev running?" in the same place — then
1544
+ // any attention line, the activity block, and the next command last. There
1545
+ // is no "last test" row: nothing records one (D16), and a row with nothing
1546
+ // behind it would be invented. Nor a key tail: no output of this module
1547
+ // contains the key.
1548
+ const kit = screenKit(opts);
1549
+ const screen = (facts: Array<[string, string]>, attention: string[][], next: string[]): string[] =>
1550
+ stack([kit.header("Jev")], kit.kv(facts), ...attention, jevStatsLines(stats, opts), next);
1551
+ /** A closing next step: what it does, then the command, in pink. */
1552
+ const step = (lead: string, command: string): string => `${lead} ${kit.cmd(command)}`;
1553
+ const modelText = (r: { model: string; modelIsDefault: boolean }): string =>
1554
+ r.modelIsDefault ? `${r.model} (provider default)` : r.model;
1512
1555
  const legacyNote = legacy
1513
- ? warning(
1514
- [
1515
- "FAILPROOFAI_EVALUATOR=legacy is set in this shell: sessions started from it skip Jev when their hooks evaluate in-process.",
1556
+ ? kit.notice(
1557
+ "caution",
1558
+ "FAILPROOFAI_EVALUATOR=legacy is set in this shell: sessions started from it skip Jev when their hooks evaluate in-process.\n" +
1516
1559
  "The daemon does not see this shell's environment.",
1517
- ],
1518
- opts,
1519
1560
  )
1520
- : null;
1561
+ : [];
1521
1562
 
1522
1563
  if (inspection.status === "absent") {
1523
1564
  return ok(
1524
- stack(
1525
- title("failproofai jev status", "off", opts),
1526
- emptyState(
1527
- {
1528
- what: `Jev is off: there is no ${inspection.path}. Hooks run the regex policies exactly as before.`,
1529
- hint: "Turn it on with your own Jev endpoint and key:",
1530
- cmd: "failproofai jev setup --provider <typesafe|openrouter|vercel|cloudflare|custom> --key-stdin",
1531
- },
1532
- opts,
1533
- ),
1534
- note(
1565
+ screen(
1566
+ [["status", `${kit.off} off: there is no ${inspection.path}`]],
1567
+ [],
1568
+ [
1569
+ step("Turn it on with your own key:", "failproofai jev setup --provider <typesafe|openrouter|vercel|cloudflare|custom> --key-stdin"),
1535
1570
  cloudCredentialPresent()
1536
- ? "Or through FailproofAI Cloud, on your org's plan — this machine's key already carries jev:evaluate: failproofai jev setup --provider failproofai"
1537
- : "Or through FailproofAI Cloud, on your org's plan, with no key of your own: connect with a key that carries jev:evaluate (the \"machine\" preset) — failproofai config --token <key>",
1538
- opts,
1539
- ),
1540
- jevStatsLines(stats, opts),
1571
+ ? step("Or through FailproofAI Cloud, which this machine's key already allows:", "failproofai jev setup --provider failproofai")
1572
+ : step("Or through FailproofAI Cloud, with a key that carries jev:evaluate:", "failproofai config --token <key>"),
1573
+ ],
1541
1574
  ),
1542
1575
  );
1543
1576
  }
@@ -1549,32 +1582,18 @@ async function status(argv: string[], opts: RenderOpts): Promise<JevCliResult> {
1549
1582
  // and the next step is the variable, not a rewrite.
1550
1583
  const route = routeForRouting(inspection.routing);
1551
1584
  return ok(
1552
- stack(
1553
- title("failproofai jev status", "off in this shell", opts),
1554
- note(
1555
- `Jev is off in this shell: ${inspection.path} stores no key and takes it from ${JEV_API_KEY_ENV}, which is not set here. ` +
1556
- "The config is fine; hooks run the regex policies wherever the variable is unset — including under the daemon, which does not see a shell's environment.",
1557
- opts,
1558
- ),
1559
- rows(
1560
- [
1561
- ["provider", inspection.routing.provider],
1562
- ...((route
1563
- ? [
1564
- ["endpoint", displayEndpoint(route.endpoint)],
1565
- ["model", route.modelIsDefault ? `${route.model} (provider default)` : route.model],
1566
- ]
1567
- : []) as Array<[string, string]>),
1568
- ["mode", modeLine(inspection.routing.mode ?? DEFAULT_JEV_MODE)],
1569
- ["config", inspection.path],
1570
- ["permissions", permissions(inspection.mode)],
1571
- ["key", `from ${JEV_API_KEY_ENV} — not set in this shell`],
1572
- ],
1573
- opts,
1574
- ),
1575
- nextStep(`failproofai jev setup --key-stdin < key-file`, `Set ${JEV_API_KEY_ENV} for this shell, or store the key in the file instead:`, opts),
1576
- legacyNote,
1577
- jevStatsLines(stats, opts),
1585
+ screen(
1586
+ [
1587
+ ["status", `${kit.off} off in this shell: ${JEV_API_KEY_ENV} is not set here`],
1588
+ ["provider", providerLabel(inspection.routing.provider) + (route ? `, model ${modelText(route)}` : "")],
1589
+ ...((route ? [["endpoint", displayEndpoint(route.endpoint)]] : []) as Array<[string, string]>),
1590
+ ["mode", modeLine(inspection.routing.mode ?? DEFAULT_JEV_MODE)],
1591
+ // The daemon is the one place a setting in this shell can never reach.
1592
+ ["key", `from ${JEV_API_KEY_ENV}, not set in this shell; the daemon never sees a shell's environment`],
1593
+ ["config", `${inspection.path}${kit.sep}${permissions(inspection.mode)}`],
1594
+ ],
1595
+ [legacyNote],
1596
+ [step(`Set ${JEV_API_KEY_ENV} for this shell, or store the key in the file:`, "failproofai jev setup --key-stdin < key-file")],
1578
1597
  ),
1579
1598
  );
1580
1599
  }
@@ -1586,22 +1605,17 @@ async function status(argv: string[], opts: RenderOpts): Promise<JevCliResult> {
1586
1605
  const r = inspection.routing;
1587
1606
  const route = routeForRouting(r);
1588
1607
  return ok(
1589
- stack(
1590
- title("failproofai jev status", "off (switched off)", opts),
1591
- note(`Jev is switched off in ${inspection.path}: it is not asked about any tool call, and hooks run the regex policies exactly as before.`, opts),
1592
- rows(
1593
- [
1594
- ["provider", providerLabel(r.provider)],
1595
- ...((route ? [["endpoint", shownEndpoint(r.provider, route.endpoint)]] : []) as Array<[string, string]>),
1596
- ["mode", modeLine("off")],
1597
- ["config", inspection.path],
1598
- ...((r.provider === JEV_CLOUD_PROVIDER ? [["key", cloudKeyRow()]] : []) as Array<[string, string]>),
1599
- ],
1600
- opts,
1601
- ),
1602
- nextStep("failproofai jev setup --mode observe", "Switch it back on (observe logs Jev and keeps enforcing regex; enforce lets it clear), here or from the dashboard:", opts),
1603
- legacyNote,
1604
- jevStatsLines(stats, opts),
1608
+ screen(
1609
+ [
1610
+ ["status", `${kit.off} off (switched off)`],
1611
+ ["provider", providerLabel(r.provider)],
1612
+ ...((route ? [["endpoint", shownEndpoint(r.provider, route.endpoint)]] : []) as Array<[string, string]>),
1613
+ ["mode", modeLine("off")],
1614
+ ...((r.provider === JEV_CLOUD_PROVIDER ? [["key", cloudKeyRow()]] : []) as Array<[string, string]>),
1615
+ ["config", inspection.path],
1616
+ ],
1617
+ [legacyNote],
1618
+ [step("Switch it back on, here or from the dashboard:", "failproofai jev setup --mode observe")],
1605
1619
  ),
1606
1620
  );
1607
1621
  }
@@ -1612,31 +1626,20 @@ async function status(argv: string[], opts: RenderOpts): Promise<JevCliResult> {
1612
1626
  const r = inspection.routing;
1613
1627
  const route = routeForRouting(r);
1614
1628
  return ok(
1615
- stack(
1616
- title("failproofai jev status", "off — this machine is not connected to FailproofAI Cloud", opts),
1617
- note(
1618
- `Jev is off: ${inspection.path} sends Jev requests through FailproofAI Cloud, and this machine holds no FailproofAI Cloud key that carries jev:evaluate. ` +
1619
- "Hooks run the regex policies exactly as before.",
1620
- opts,
1621
- ),
1622
- rows(
1623
- [
1624
- ["provider", providerLabel(r.provider)],
1625
- ...((route ? [["endpoint", shownEndpoint(r.provider, route.endpoint)]] : []) as Array<[string, string]>),
1626
- ["mode", modeLine(r.mode ?? DEFAULT_JEV_MODE)],
1627
- ["config", inspection.path],
1628
- ["key", `${CLOUD_KEY_SOURCE} — not connected`],
1629
- ],
1630
- opts,
1631
- ),
1632
- nextStep(
1633
- "failproofai config --token <key>",
1634
- "Connect with a key that carries jev:evaluate (the \"machine\" preset on the dashboard's Keys page):",
1635
- opts,
1636
- ),
1637
- nextStep("failproofai jev remove", "Or switch Jev off:", opts),
1638
- legacyNote,
1639
- jevStatsLines(stats, opts),
1629
+ screen(
1630
+ [
1631
+ ["status", `${kit.off} off — this machine is not connected to FailproofAI Cloud`],
1632
+ ["provider", providerLabel(r.provider)],
1633
+ ...((route ? [["endpoint", shownEndpoint(r.provider, route.endpoint)]] : []) as Array<[string, string]>),
1634
+ ["mode", modeLine(r.mode ?? DEFAULT_JEV_MODE)],
1635
+ ["key", `${CLOUD_KEY_SOURCE} — not connected`],
1636
+ ["config", inspection.path],
1637
+ ],
1638
+ [legacyNote],
1639
+ [
1640
+ step("Connect with a key that carries jev:evaluate (the \"machine\" preset):", "failproofai config --token <key>"),
1641
+ step("Or switch Jev off:", "failproofai jev remove"),
1642
+ ],
1640
1643
  ),
1641
1644
  );
1642
1645
  }
@@ -1644,34 +1647,24 @@ async function status(argv: string[], opts: RenderOpts): Promise<JevCliResult> {
1644
1647
  if (inspection.status === "key-lacks-jev") {
1645
1648
  // Connected, so "not connected" would be false and send its owner to
1646
1649
  // reconnect with the same key. The remedy is a key WITH Jev.
1650
+ // Its key lacks jev:evaluate, or the last connect could not confirm that.
1647
1651
  const r = inspection.routing;
1648
1652
  const route = routeForRouting(r);
1649
1653
  return ok(
1650
- stack(
1651
- title("failproofai jev status", KEY_LACKS_JEV_TITLE, opts),
1652
- note(
1653
- `Jev is off: ${inspection.path} sends Jev requests through FailproofAI Cloud, and no Jev key is stored for this machine's connection: its key lacks jev:evaluate, or the last connect could not confirm that. ` +
1654
- "Hooks run the regex policies exactly as before.",
1655
- opts,
1656
- ),
1657
- rows(
1658
- [
1659
- ["provider", providerLabel(r.provider)],
1660
- ...((route ? [["endpoint", shownEndpoint(r.provider, route.endpoint)]] : []) as Array<[string, string]>),
1661
- ["mode", modeLine(r.mode ?? DEFAULT_JEV_MODE)],
1662
- ["config", inspection.path],
1663
- ["key", `${CLOUD_KEY_SOURCE} — connected, no Jev key stored for it`],
1664
- ],
1665
- opts,
1666
- ),
1667
- nextStep(
1668
- "failproofai config --token <key>",
1669
- "Reconnect with this machine's key to re-check what it carries (a key without jev:evaluate needs the \"machine\" preset on the dashboard's Keys page):",
1670
- opts,
1671
- ),
1672
- nextStep("failproofai jev setup --mode off", "Or keep Jev off for good:", opts),
1673
- legacyNote,
1674
- jevStatsLines(stats, opts),
1654
+ screen(
1655
+ [
1656
+ ["status", `${kit.off} ${KEY_LACKS_JEV_TITLE}`],
1657
+ ["provider", providerLabel(r.provider)],
1658
+ ...((route ? [["endpoint", shownEndpoint(r.provider, route.endpoint)]] : []) as Array<[string, string]>),
1659
+ ["mode", modeLine(r.mode ?? DEFAULT_JEV_MODE)],
1660
+ ["key", `${CLOUD_KEY_SOURCE} — connected, no Jev key stored for it`],
1661
+ ["config", inspection.path],
1662
+ ],
1663
+ [legacyNote],
1664
+ [
1665
+ step("Reconnect to re-check what this machine's key carries:", "failproofai config --token <key>"),
1666
+ step("Or keep Jev off for good:", "failproofai jev setup --mode off"),
1667
+ ],
1675
1668
  ),
1676
1669
  );
1677
1670
  }
@@ -1684,13 +1677,13 @@ async function status(argv: string[], opts: RenderOpts): Promise<JevCliResult> {
1684
1677
  const named = inspection.reason === "too-open" ? namedEndpoint(raw) : null;
1685
1678
  const next = refusedNextStep(inspection, cloudRoute(raw));
1686
1679
  return fail(
1687
- stack(
1688
- title("failproofai jev status", "off (config refused)", opts),
1689
- warning([`Jev is off: ${inspection.path} was refused — ${inspection.problem}.`, "Hooks run the regex policies exactly as before."], opts),
1690
- named ? rows([["endpoint it names", named]], opts) : null,
1691
- nextStep(next.cmd, next.lead, opts),
1692
- legacyNote,
1693
- jevStatsLines(stats, opts),
1680
+ screen(
1681
+ [
1682
+ ["status", `${kit.failed} off: ${inspection.path} was refused — ${inspection.problem}`],
1683
+ ...((named ? [["endpoint it names", named]] : []) as Array<[string, string]>),
1684
+ ],
1685
+ [legacyNote],
1686
+ [step(next.lead, next.cmd)],
1694
1687
  ),
1695
1688
  );
1696
1689
  }
@@ -1699,32 +1692,26 @@ async function status(argv: string[], opts: RenderOpts): Promise<JevCliResult> {
1699
1692
  const route = jevRoute(cfg);
1700
1693
  const mode = cfg.mode ?? DEFAULT_JEV_MODE;
1701
1694
  return ok(
1702
- stack(
1703
- title("failproofai jev status", legacy ? "on (legacy override in this shell)" : `on · ${mode}`, opts),
1704
- rows(
1695
+ screen(
1696
+ [
1697
+ ["status", `${kit.on} ${legacy ? "on, with a legacy override in this shell" : `on · ${mode}`}`],
1698
+ ["provider", `${providerLabel(cfg.provider)}, model ${modelText(route)}`],
1699
+ ["endpoint", shownEndpoint(cfg.provider, route.endpoint)],
1700
+ ["mode", modeLine(mode)],
1701
+ ["timeout", `${cfg.timeoutMs} ms`],
1705
1702
  [
1706
- ["provider", providerLabel(cfg.provider)],
1707
- ["endpoint", shownEndpoint(cfg.provider, route.endpoint)],
1708
- ["model", route.modelIsDefault ? `${route.model} (provider default)` : route.model],
1709
- ["mode", modeLine(mode)],
1710
- ["timeout", `${cfg.timeoutMs} ms`],
1711
- ["config", inspection.path],
1712
- ["permissions", permissions(inspection.mode)],
1713
- [
1714
- "key",
1715
- inspection.keySource === "cloud"
1716
- ? CLOUD_KEY_SOURCE
1717
- : inspection.keySource === "file"
1718
- ? "set in the config file"
1719
- : `from ${JEV_API_KEY_ENV} (this shell only; the daemon does not see it)`,
1720
- ],
1703
+ "key",
1704
+ inspection.keySource === "cloud"
1705
+ ? CLOUD_KEY_SOURCE
1706
+ : inspection.keySource === "file"
1707
+ ? "set in the config file"
1708
+ : `from ${JEV_API_KEY_ENV} (this shell only; the daemon does not see it)`,
1721
1709
  ],
1722
- opts,
1723
- ),
1724
- coverage ? note(reviewableSummary(coverage), opts) : null,
1725
- coverageProblem ? warning([coverageProblem], opts) : null,
1726
- legacyNote,
1727
- jevStatsLines(stats, opts),
1710
+ ["config", `${inspection.path}${kit.sep}${permissions(inspection.mode)}`],
1711
+ ...((coverage ? [["reviewable", reviewableSummary(coverage)]] : []) as Array<[string, string]>),
1712
+ ],
1713
+ [coverageProblem ? kit.notice("caution", coverageProblem) : [], legacyNote],
1714
+ [],
1728
1715
  ),
1729
1716
  );
1730
1717
  }
@@ -1802,7 +1789,7 @@ async function test(argv: string[], deps: JevCliDeps, opts: RenderOpts): Promise
1802
1789
  ? "Reconnect with this machine's key to re-check what it carries (a key without jev:evaluate needs the \"machine\" preset on the dashboard's Keys page):"
1803
1790
  : undefined;
1804
1791
  const json = asJson ? JSON.stringify({ ok: false, error: { code, message: why } }, null, 2) : undefined;
1805
- return fail(stack(title("failproofai jev test", "not run", opts), note(why, opts), nextStep(fixCmd, fixLead, opts)), json);
1792
+ return fail(stack(jevHeader("Jev test", "not run", opts), jevNote(why, opts), jevNext(fixCmd, fixLead, opts)), json);
1806
1793
  }
1807
1794
 
1808
1795
  const cfg = inspection.config;
@@ -1860,8 +1847,8 @@ async function test(argv: string[], deps: JevCliDeps, opts: RenderOpts): Promise
1860
1847
  problem === "over-timeout" ? `over timeout · ${latencyMs} ms` : problem ? `wrong answer · p = ${p.toFixed(3)}` : `ok · ${latencyMs} ms`;
1861
1848
  return done(
1862
1849
  stack(
1863
- title("failproofai jev test", status, opts),
1864
- rows(
1850
+ jevHeader("Jev test", status, opts),
1851
+ jevRows(
1865
1852
  [
1866
1853
  ["provider", cfg.provider],
1867
1854
  ["endpoint", displayEndpoint(route.endpoint)],
@@ -1876,12 +1863,12 @@ async function test(argv: string[], deps: JevCliDeps, opts: RenderOpts): Promise
1876
1863
  ],
1877
1864
  opts,
1878
1865
  ),
1879
- note(
1866
+ jevNote(
1880
1867
  "One request, sent directly: the hook path's cache and rate limit were not involved, and a fresh process pays DNS and TLS setup that the daemon's warm worker does not.",
1881
1868
  opts,
1882
1869
  ),
1883
1870
  problem === "over-timeout"
1884
- ? nextStep("failproofai jev setup --timeout-ms <n>", `Give hooks longer (up to ${MAX_JEV_TIMEOUT_MS} ms), or use a faster route:`, opts)
1871
+ ? jevNext("failproofai jev setup --timeout-ms <n>", `Give hooks longer (up to ${MAX_JEV_TIMEOUT_MS} ms), or use a faster route:`, opts)
1885
1872
  : null,
1886
1873
  ),
1887
1874
  );
@@ -1896,8 +1883,8 @@ async function test(argv: string[], deps: JevCliDeps, opts: RenderOpts): Promise
1896
1883
  if (asJson) return fail([], JSON.stringify({ ok: false, provider: cfg.provider, latencyMs, timeoutMs: budget, withinTimeout: !late, error: e }, null, 2));
1897
1884
  return fail(
1898
1885
  stack(
1899
- title("failproofai jev test", `failed · ${e.code}`, opts),
1900
- rows(
1886
+ jevHeader("Jev test", `failed · ${e.code}`, opts),
1887
+ jevRows(
1901
1888
  [
1902
1889
  ["provider", cfg.provider],
1903
1890
  ["endpoint", displayEndpoint(route.endpoint)],
@@ -1907,7 +1894,7 @@ async function test(argv: string[], deps: JevCliDeps, opts: RenderOpts): Promise
1907
1894
  ],
1908
1895
  opts,
1909
1896
  ),
1910
- note(
1897
+ jevNote(
1911
1898
  late
1912
1899
  ? `Hooks stop waiting after ${budget} ms, so they record this as \`timeout\`, not ${e.code}: the provider or FailproofAI Cloud is slow or failing upstream.`
1913
1900
  : remedy(e.code, cfg.provider, e.message),
@@ -2056,8 +2043,8 @@ async function models(argv: string[], deps: JevCliDeps, opts: RenderOpts): Promi
2056
2043
  }
2057
2044
  return fail(
2058
2045
  stack(
2059
- title("failproofai jev models", "not read", opts),
2060
- rows(
2046
+ jevHeader("Jev models", "not read", opts),
2047
+ jevRows(
2061
2048
  [
2062
2049
  ["provider", provider],
2063
2050
  ["endpoint", shown],
@@ -2066,7 +2053,7 @@ async function models(argv: string[], deps: JevCliDeps, opts: RenderOpts): Promi
2066
2053
  ],
2067
2054
  opts,
2068
2055
  ),
2069
- note(
2056
+ jevNote(
2070
2057
  "Not every endpoint serves a model list — a proxy may expose only /systemone — and nothing depends on one: setup and hooks work without it.",
2071
2058
  opts,
2072
2059
  ),
@@ -2083,8 +2070,8 @@ async function models(argv: string[], deps: JevCliDeps, opts: RenderOpts): Promi
2083
2070
  const listed = list.models.slice(0, MAX_SHOWN_MODELS);
2084
2071
  return ok(
2085
2072
  stack(
2086
- title("failproofai jev models", `${list.models.length} · ${provider}`, opts),
2087
- rows(
2073
+ jevHeader("Jev models", `${list.models.length} · ${provider}`, opts),
2074
+ jevRows(
2088
2075
  [
2089
2076
  ["provider", provider],
2090
2077
  ["endpoint", shown],
@@ -2093,13 +2080,13 @@ async function models(argv: string[], deps: JevCliDeps, opts: RenderOpts): Promi
2093
2080
  ],
2094
2081
  opts,
2095
2082
  ),
2096
- rows(
2083
+ jevRows(
2097
2084
  listed.map((name) => [name, name === configuredModel ? "configured" : ""] as [string, string]),
2098
2085
  opts,
2099
2086
  ),
2100
- list.models.length > listed.length ? note(`… and ${list.models.length - listed.length} more.`, opts) : null,
2087
+ list.models.length > listed.length ? jevNote(`… and ${list.models.length - listed.length} more.`, opts) : null,
2101
2088
  configuredModel !== null && !modelListHasModel(list, configuredModel) && listDescribesSystemOne(list)
2102
- ? warning(
2089
+ ? jevWarn(
2103
2090
  [
2104
2091
  `The configured model ${configuredModel} is not one of these, so every evaluation would fail at this endpoint and hooks would fall back to regex.`,
2105
2092
  `Point it at one of them: failproofai jev setup --model ${list.models[0]}`,
@@ -2119,7 +2106,7 @@ function remove(argv: string[], opts: RenderOpts): JevCliResult {
2119
2106
  if (parsed.positionals.length > 0) return fail([STRAY_ARGUMENT, "", ...JEV_USAGE]);
2120
2107
  const path = jevConfigPath();
2121
2108
  if (!existsSync(path)) {
2122
- return ok(stack(title("failproofai jev remove", "nothing to do", opts), note(`There is no ${path}; Jev is already off.`, opts)));
2109
+ return ok(stack(jevHeader("Jev remove", "nothing to do", opts), jevNote(`There is no ${path}; Jev is already off.`, opts)));
2123
2110
  }
2124
2111
  try {
2125
2112
  unlinkSync(path);
@@ -2128,9 +2115,9 @@ function remove(argv: string[], opts: RenderOpts): JevCliResult {
2128
2115
  }
2129
2116
  return ok(
2130
2117
  stack(
2131
- title("failproofai jev remove", "off", opts),
2132
- note(`Removed ${path}. Jev is off; hooks run the regex policies exactly as before, from the next tool call.`, opts),
2133
- process.env[JEV_API_KEY_ENV] ? note(`${JEV_API_KEY_ENV} is still set in this shell. Without the file it does nothing.`, opts) : null,
2118
+ jevHeader("Jev remove", "off", opts),
2119
+ jevNote(`Removed ${path}. Jev is off; hooks run the regex policies exactly as before, from the next tool call.`, opts),
2120
+ process.env[JEV_API_KEY_ENV] ? jevNote(`${JEV_API_KEY_ENV} is still set in this shell. Without the file it does nothing.`, opts) : null,
2134
2121
  ),
2135
2122
  );
2136
2123
  }