failproofai 1.0.1 → 1.0.2-beta.1

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 (390) hide show
  1. package/.next/standalone/.next/BUILD_ID +1 -1
  2. package/.next/standalone/.next/build-manifest.json +3 -3
  3. package/.next/standalone/.next/prerender-manifest.json +6 -6
  4. package/.next/standalone/.next/required-server-files.json +1 -1
  5. package/.next/standalone/.next/server/app/_global-error/page/server-reference-manifest.json +1 -1
  6. package/.next/standalone/.next/server/app/_global-error/page.js +2 -2
  7. package/.next/standalone/.next/server/app/_global-error/page.js.nft.json +1 -1
  8. package/.next/standalone/.next/server/app/_global-error/page_client-reference-manifest.js +1 -1
  9. package/.next/standalone/.next/server/app/_global-error.html +1 -1
  10. package/.next/standalone/.next/server/app/_global-error.rsc +7 -7
  11. package/.next/standalone/.next/server/app/_global-error.segments/__PAGE__.segment.rsc +6 -6
  12. package/.next/standalone/.next/server/app/_global-error.segments/_full.segment.rsc +7 -7
  13. package/.next/standalone/.next/server/app/_global-error.segments/_tree.segment.rsc +1 -1
  14. package/.next/standalone/.next/server/app/_not-found/page/server-reference-manifest.json +1 -1
  15. package/.next/standalone/.next/server/app/_not-found/page.js +2 -2
  16. package/.next/standalone/.next/server/app/_not-found/page.js.nft.json +1 -1
  17. package/.next/standalone/.next/server/app/_not-found/page_client-reference-manifest.js +1 -1
  18. package/.next/standalone/.next/server/app/_not-found.html +1 -1
  19. package/.next/standalone/.next/server/app/_not-found.rsc +15 -15
  20. package/.next/standalone/.next/server/app/_not-found.segments/_full.segment.rsc +15 -15
  21. package/.next/standalone/.next/server/app/_not-found.segments/_not-found/__PAGE__.segment.rsc +14 -14
  22. package/.next/standalone/.next/server/app/_not-found.segments/_tree.segment.rsc +2 -2
  23. package/.next/standalone/.next/server/app/api/audit/invite/route.js +3 -2
  24. package/.next/standalone/.next/server/app/api/audit/invite/route.js.nft.json +1 -1
  25. package/.next/standalone/.next/server/app/api/audit/run/route.js +5 -4
  26. package/.next/standalone/.next/server/app/api/audit/run/route.js.nft.json +1 -1
  27. package/.next/standalone/.next/server/app/api/audit/status/route.js.nft.json +1 -1
  28. package/.next/standalone/.next/server/app/api/auth/login-request/route.js +2 -2
  29. package/.next/standalone/.next/server/app/api/auth/login-request/route.js.nft.json +1 -1
  30. package/.next/standalone/.next/server/app/api/auth/login-verify/route.js +4 -3
  31. package/.next/standalone/.next/server/app/api/auth/login-verify/route.js.nft.json +1 -1
  32. package/.next/standalone/.next/server/app/api/auth/logout/route.js +4 -4
  33. package/.next/standalone/.next/server/app/api/auth/logout/route.js.nft.json +1 -1
  34. package/.next/standalone/.next/server/app/api/auth/status/route.js +4 -4
  35. package/.next/standalone/.next/server/app/api/auth/status/route.js.nft.json +1 -1
  36. package/.next/standalone/.next/server/app/api/download/[project]/[session]/route.js.nft.json +1 -1
  37. package/.next/standalone/.next/server/app/audit/page/server-reference-manifest.json +2 -2
  38. package/.next/standalone/.next/server/app/audit/page.js +2 -2
  39. package/.next/standalone/.next/server/app/audit/page.js.nft.json +1 -1
  40. package/.next/standalone/.next/server/app/audit/page_client-reference-manifest.js +1 -1
  41. package/.next/standalone/.next/server/app/index.html +1 -1
  42. package/.next/standalone/.next/server/app/index.rsc +15 -15
  43. package/.next/standalone/.next/server/app/index.segments/__PAGE__.segment.rsc +14 -14
  44. package/.next/standalone/.next/server/app/index.segments/_full.segment.rsc +15 -15
  45. package/.next/standalone/.next/server/app/index.segments/_tree.segment.rsc +2 -2
  46. package/.next/standalone/.next/server/app/page/server-reference-manifest.json +1 -1
  47. package/.next/standalone/.next/server/app/page.js +2 -2
  48. package/.next/standalone/.next/server/app/page.js.nft.json +1 -1
  49. package/.next/standalone/.next/server/app/page_client-reference-manifest.js +1 -1
  50. package/.next/standalone/.next/server/app/policies/page/server-reference-manifest.json +66 -22
  51. package/.next/standalone/.next/server/app/policies/page.js +5 -4
  52. package/.next/standalone/.next/server/app/policies/page.js.nft.json +1 -1
  53. package/.next/standalone/.next/server/app/policies/page_client-reference-manifest.js +1 -1
  54. package/.next/standalone/.next/server/app/project/[name]/page/server-reference-manifest.json +1 -1
  55. package/.next/standalone/.next/server/app/project/[name]/page.js +2 -2
  56. package/.next/standalone/.next/server/app/project/[name]/page.js.nft.json +1 -1
  57. package/.next/standalone/.next/server/app/project/[name]/page_client-reference-manifest.js +1 -1
  58. package/.next/standalone/.next/server/app/project/[name]/session/[sessionId]/page/react-loadable-manifest.json +2 -2
  59. package/.next/standalone/.next/server/app/project/[name]/session/[sessionId]/page/server-reference-manifest.json +2 -2
  60. package/.next/standalone/.next/server/app/project/[name]/session/[sessionId]/page.js +2 -2
  61. package/.next/standalone/.next/server/app/project/[name]/session/[sessionId]/page.js.nft.json +1 -1
  62. package/.next/standalone/.next/server/app/project/[name]/session/[sessionId]/page_client-reference-manifest.js +1 -1
  63. package/.next/standalone/.next/server/app/projects/page/server-reference-manifest.json +1 -1
  64. package/.next/standalone/.next/server/app/projects/page.js +2 -2
  65. package/.next/standalone/.next/server/app/projects/page.js.nft.json +1 -1
  66. package/.next/standalone/.next/server/app/projects/page_client-reference-manifest.js +1 -1
  67. package/.next/standalone/.next/server/app/settings/page/server-reference-manifest.json +4 -4
  68. package/.next/standalone/.next/server/app/settings/page.js +1 -1
  69. package/.next/standalone/.next/server/app/settings/page.js.nft.json +1 -1
  70. package/.next/standalone/.next/server/app/settings/page_client-reference-manifest.js +1 -1
  71. package/.next/standalone/.next/server/chunks/{[externals]__1qzqcio._.js → [externals]__0e32-7c._.js} +1 -1
  72. package/.next/standalone/.next/server/chunks/[externals]__1s462yl._.js +3 -0
  73. package/.next/standalone/.next/server/chunks/[root-of-the-server]__01eqny5._.js +3 -0
  74. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0_0xu5z._.js +1 -1
  75. package/.next/standalone/.next/server/chunks/{[root-of-the-server]__1p8poxd._.js → [root-of-the-server]__0igxt32._.js} +2 -2
  76. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0neqlu-._.js +3 -0
  77. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0o07qi9._.js +3 -0
  78. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0t9oqnn._.js +3 -0
  79. package/.next/standalone/.next/server/chunks/_0bs-v8p._.js +3 -0
  80. package/.next/standalone/.next/server/chunks/_0tovk6q._.js +3 -0
  81. package/.next/standalone/.next/server/chunks/_0trp3yc._.js +3 -0
  82. package/.next/standalone/.next/server/chunks/_185gyk9._.js +3 -0
  83. package/.next/standalone/.next/server/chunks/_1ek68ln._.js +5 -6
  84. package/.next/standalone/.next/server/chunks/lib_telemetry-id_ts_1k8gj9o._.js +3 -0
  85. package/.next/standalone/.next/server/chunks/{node_modules_posthog-node_dist_entrypoints_index_node_mjs_09d5c79._.js → node_modules_posthog-node_dist_entrypoints_index_node_mjs_04op_ou._.js} +1 -1
  86. package/.next/standalone/.next/server/chunks/{node_modules_posthog-node_dist_entrypoints_index_node_mjs_1d2g73o._.js → node_modules_posthog-node_dist_entrypoints_index_node_mjs_0dr20uz._.js} +1 -1
  87. package/.next/standalone/.next/server/chunks/package_json_[json]_cjs_1nxcc4v._.js +1 -1
  88. package/.next/standalone/.next/server/chunks/src_hooks_0xbw3bu._.js +12 -0
  89. package/.next/standalone/.next/server/chunks/src_hooks_fp-home_ts_09kv0bn._.js +1 -1
  90. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__013jr2b._.js +4 -0
  91. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__01wy8d-._.js +4 -0
  92. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__02npjtd._.js +4 -0
  93. package/.next/standalone/.next/server/chunks/ssr/{[root-of-the-server]__0spkm68._.js → [root-of-the-server]__07gm3zl._.js} +21 -20
  94. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0da85px._.js +4 -0
  95. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0ftmoxc._.js +4 -0
  96. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0l4748x._.js +3 -0
  97. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0oa1lav._.js +1 -1
  98. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0p-5p8u._.js +4 -0
  99. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0s740oi._.js +6 -0
  100. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__192nhvh._.js +5 -0
  101. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__1p2otjt._.js +4 -0
  102. package/.next/standalone/.next/server/chunks/ssr/_08x1r5t._.js +1 -1
  103. package/.next/standalone/.next/server/chunks/ssr/_0bwu160._.js +23 -0
  104. package/.next/standalone/.next/server/chunks/ssr/{_0u5zauv._.js → _0ns6k3a._.js} +1 -1
  105. package/.next/standalone/.next/server/chunks/ssr/_1u8-lu2._.js +1 -1
  106. package/.next/standalone/.next/server/chunks/ssr/_1zopuov._.js +1 -1
  107. package/.next/standalone/.next/server/chunks/ssr/app_audit__components_audit-dashboard_tsx_0p9ud47._.js +13 -13
  108. package/.next/standalone/.next/server/chunks/ssr/app_global-error_tsx_1kp6l3x._.js +1 -1
  109. package/.next/standalone/.next/server/chunks/ssr/app_policies_hooks-client_tsx_19dqvpc._.js +2 -2
  110. package/.next/standalone/.next/server/chunks/ssr/app_settings_settings-client_tsx_20lq-mq._.js +1 -1
  111. package/.next/standalone/.next/server/chunks/ssr/src_hooks_08o7bqo._.js +10 -0
  112. package/.next/standalone/.next/server/chunks/ssr/src_hooks_builtin-policies_ts_09j2ndl._.js +1 -1
  113. package/.next/standalone/.next/server/chunks/ssr/src_hooks_fp-home_ts_0je3xkv._.js +1 -1
  114. package/.next/standalone/.next/server/middleware-build-manifest.js +3 -3
  115. package/.next/standalone/.next/server/middleware.js +1 -1
  116. package/.next/standalone/.next/server/pages/404.html +1 -1
  117. package/.next/standalone/.next/server/pages/500.html +1 -1
  118. package/.next/standalone/.next/server/server-reference-manifest.js +1 -1
  119. package/.next/standalone/.next/server/server-reference-manifest.json +71 -27
  120. package/.next/standalone/.next/static/chunks/{3c808qrfcq0im.js → 01u1cf8js2yd6.js} +1 -1
  121. package/.next/standalone/.next/static/chunks/{0k5050ezjvv49.js → 0izgu7nqh2zp-.js} +1 -1
  122. package/.next/standalone/.next/static/chunks/0u4-org_e7zde.js +1 -0
  123. package/.next/standalone/.next/static/chunks/1mfzsja6ftim5.css +2 -0
  124. package/.next/standalone/.next/static/chunks/{2zpp1we2jv6tb.js → 1tynnrrh711lr.js} +1 -1
  125. package/.next/standalone/.next/static/chunks/{1ide1wl2f7zi1.js → 22rqvlr7p_1mv.js} +13 -13
  126. package/.next/standalone/.next/static/chunks/{31s1smp-g7gks.js → 2whxqyskpirbk.js} +1 -1
  127. package/.next/standalone/.next/static/chunks/31mwk8k0q3_3g.js +6 -0
  128. package/.next/standalone/.next/static/chunks/3ms6gxfm82t6s.js +1 -0
  129. package/.next/standalone/.next/static/chunks/{37fcpc36x9gpe.js → 3tbbs_d8xrvyp.js} +1 -1
  130. package/.next/standalone/.next/static/chunks/43nlc236oo898.js +1 -0
  131. package/.next/standalone/SECURITY.md +5 -4
  132. package/.next/standalone/app/actions/get-hooks-config.ts +108 -17
  133. package/.next/standalone/app/actions/pack-actions.ts +163 -0
  134. package/.next/standalone/app/audit/_components/run-progress.tsx +1 -1
  135. package/.next/standalone/app/audit/_components/share-templates.ts +13 -13
  136. package/.next/standalone/app/policies/hooks-client.tsx +320 -15
  137. package/.next/standalone/components/navbar.tsx +2 -28
  138. package/.next/standalone/components/reach-developers.tsx +8 -1
  139. package/.next/standalone/docs-old/agenteye/python-sdk-skill.mdx +1 -1
  140. package/.next/standalone/docs-old/agenteye/python-sdk.mdx +59 -35
  141. package/.next/standalone/docs-old/i18n/README.ar.md +1 -0
  142. package/.next/standalone/docs-old/i18n/README.de.md +1 -0
  143. package/.next/standalone/docs-old/i18n/README.es.md +1 -0
  144. package/.next/standalone/docs-old/i18n/README.fr.md +1 -0
  145. package/.next/standalone/docs-old/i18n/README.he.md +1 -0
  146. package/.next/standalone/docs-old/i18n/README.hi.md +1 -0
  147. package/.next/standalone/docs-old/i18n/README.it.md +1 -0
  148. package/.next/standalone/docs-old/i18n/README.ja.md +1 -0
  149. package/.next/standalone/docs-old/i18n/README.ko.md +1 -0
  150. package/.next/standalone/docs-old/i18n/README.pt-br.md +1 -0
  151. package/.next/standalone/docs-old/i18n/README.ru.md +1 -0
  152. package/.next/standalone/docs-old/i18n/README.tr.md +1 -0
  153. package/.next/standalone/docs-old/i18n/README.vi.md +1 -0
  154. package/.next/standalone/docs-old/i18n/README.zh.md +1 -0
  155. package/.next/standalone/fp-cloud-cli/CHANGELOG.md +431 -0
  156. package/.next/standalone/fp-cloud-cli/LICENSE +42 -0
  157. package/.next/standalone/fp-cloud-cli/MANIFEST.in +10 -0
  158. package/.next/standalone/fp-cloud-cli/README.md +259 -0
  159. package/.next/standalone/fp-cloud-cli/fp_cli/__init__.py +10 -0
  160. package/.next/standalone/fp-cloud-cli/fp_cli/__main__.py +4 -0
  161. package/.next/standalone/fp-cloud-cli/fp_cli/_click_compat.py +64 -0
  162. package/.next/standalone/fp-cloud-cli/fp_cli/_context.py +332 -0
  163. package/.next/standalone/fp-cloud-cli/fp_cli/_version.py +1 -0
  164. package/.next/standalone/fp-cloud-cli/fp_cli/analytics.py +432 -0
  165. package/.next/standalone/fp-cloud-cli/fp_cli/analytics_config.py +77 -0
  166. package/.next/standalone/fp-cloud-cli/fp_cli/analytics_registry.py +83 -0
  167. package/.next/standalone/fp-cloud-cli/fp_cli/app.py +492 -0
  168. package/.next/standalone/fp-cloud-cli/fp_cli/auth.py +160 -0
  169. package/.next/standalone/fp-cloud-cli/fp_cli/client.py +1694 -0
  170. package/.next/standalone/fp-cloud-cli/fp_cli/commands/__init__.py +0 -0
  171. package/.next/standalone/fp-cloud-cli/fp_cli/commands/_write.py +214 -0
  172. package/.next/standalone/fp-cloud-cli/fp_cli/commands/agent_cmds.py +407 -0
  173. package/.next/standalone/fp-cloud-cli/fp_cli/commands/alerts_cmds.py +445 -0
  174. package/.next/standalone/fp-cloud-cli/fp_cli/commands/audits_cmds.py +1054 -0
  175. package/.next/standalone/fp-cloud-cli/fp_cli/commands/auth_cmds.py +512 -0
  176. package/.next/standalone/fp-cloud-cli/fp_cli/commands/errors_cmds.py +190 -0
  177. package/.next/standalone/fp-cloud-cli/fp_cli/commands/evals_cmds.py +161 -0
  178. package/.next/standalone/fp-cloud-cli/fp_cli/commands/events_cmds.py +159 -0
  179. package/.next/standalone/fp-cloud-cli/fp_cli/commands/fleet_cmds.py +416 -0
  180. package/.next/standalone/fp-cloud-cli/fp_cli/commands/guardrails_cmds.py +148 -0
  181. package/.next/standalone/fp-cloud-cli/fp_cli/commands/incidents_cmds.py +472 -0
  182. package/.next/standalone/fp-cloud-cli/fp_cli/commands/keys_cmds.py +407 -0
  183. package/.next/standalone/fp-cloud-cli/fp_cli/commands/list_cmds.py +63 -0
  184. package/.next/standalone/fp-cloud-cli/fp_cli/commands/orgs_cmds.py +319 -0
  185. package/.next/standalone/fp-cloud-cli/fp_cli/commands/policies_cmds.py +499 -0
  186. package/.next/standalone/fp-cloud-cli/fp_cli/commands/queries_cmds.py +378 -0
  187. package/.next/standalone/fp-cloud-cli/fp_cli/commands/sessions_cmds.py +151 -0
  188. package/.next/standalone/fp-cloud-cli/fp_cli/commands/settings_cmds.py +150 -0
  189. package/.next/standalone/fp-cloud-cli/fp_cli/commands/usage_cmds.py +35 -0
  190. package/.next/standalone/fp-cloud-cli/fp_cli/commands/users_cmds.py +404 -0
  191. package/.next/standalone/fp-cloud-cli/fp_cli/config.py +330 -0
  192. package/.next/standalone/fp-cloud-cli/fp_cli/dates.py +78 -0
  193. package/.next/standalone/fp-cloud-cli/fp_cli/enforcement.py +345 -0
  194. package/.next/standalone/fp-cloud-cli/fp_cli/errors.py +98 -0
  195. package/.next/standalone/fp-cloud-cli/fp_cli/models.py +891 -0
  196. package/.next/standalone/fp-cloud-cli/fp_cli/orgs.py +30 -0
  197. package/.next/standalone/fp-cloud-cli/fp_cli/output.py +6593 -0
  198. package/.next/standalone/fp-cloud-cli/fp_cli/permissions.py +208 -0
  199. package/.next/standalone/fp-cloud-cli/fp_cli/policy_check.py +290 -0
  200. package/.next/standalone/fp-cloud-cli/fp_cli/py.typed +0 -0
  201. package/.next/standalone/fp-cloud-cli/fp_cli/select.py +322 -0
  202. package/.next/standalone/fp-cloud-cli/fp_cli/theme.py +53 -0
  203. package/.next/standalone/fp-cloud-cli/pyproject.toml +106 -0
  204. package/.next/standalone/fp-cloud-cli/skill/SKILL.md +302 -0
  205. package/.next/standalone/fp-cloud-cli/skill/agents/openai.yaml +8 -0
  206. package/.next/standalone/fp-cloud-cli/skill/references/commands.md +254 -0
  207. package/.next/standalone/fp-cloud-cli/tests/__init__.py +0 -0
  208. package/.next/standalone/fp-cloud-cli/tests/conftest.py +92 -0
  209. package/.next/standalone/fp-cloud-cli/tests/test_alerting.py +644 -0
  210. package/.next/standalone/fp-cloud-cli/tests/test_analytics.py +385 -0
  211. package/.next/standalone/fp-cloud-cli/tests/test_audits.py +950 -0
  212. package/.next/standalone/fp-cloud-cli/tests/test_auth.py +98 -0
  213. package/.next/standalone/fp-cloud-cli/tests/test_auth_mode.py +272 -0
  214. package/.next/standalone/fp-cloud-cli/tests/test_click_compat.py +118 -0
  215. package/.next/standalone/fp-cloud-cli/tests/test_client.py +299 -0
  216. package/.next/standalone/fp-cloud-cli/tests/test_commands.py +814 -0
  217. package/.next/standalone/fp-cloud-cli/tests/test_config.py +99 -0
  218. package/.next/standalone/fp-cloud-cli/tests/test_dashboards_agent.py +340 -0
  219. package/.next/standalone/fp-cloud-cli/tests/test_dates.py +76 -0
  220. package/.next/standalone/fp-cloud-cli/tests/test_enforcement_logic.py +481 -0
  221. package/.next/standalone/fp-cloud-cli/tests/test_facets.py +170 -0
  222. package/.next/standalone/fp-cloud-cli/tests/test_failproofai_home.py +722 -0
  223. package/.next/standalone/fp-cloud-cli/tests/test_fp_home_contract.py +198 -0
  224. package/.next/standalone/fp-cloud-cli/tests/test_hardening.py +186 -0
  225. package/.next/standalone/fp-cloud-cli/tests/test_help_table_coverage.py +127 -0
  226. package/.next/standalone/fp-cloud-cli/tests/test_keys_queries.py +496 -0
  227. package/.next/standalone/fp-cloud-cli/tests/test_list.py +59 -0
  228. package/.next/standalone/fp-cloud-cli/tests/test_multivalue.py +183 -0
  229. package/.next/standalone/fp-cloud-cli/tests/test_no_customer_identifiers.py +168 -0
  230. package/.next/standalone/fp-cloud-cli/tests/test_operator.py +492 -0
  231. package/.next/standalone/fp-cloud-cli/tests/test_orgs.py +692 -0
  232. package/.next/standalone/fp-cloud-cli/tests/test_output.py +1732 -0
  233. package/.next/standalone/fp-cloud-cli/tests/test_policy_check.py +191 -0
  234. package/.next/standalone/fp-cloud-cli/tests/test_readme_matches_reality.py +125 -0
  235. package/.next/standalone/fp-cloud-cli/tests/test_review_fixes.py +161 -0
  236. package/.next/standalone/fp-cloud-cli/tests/test_telemetry_completeness.py +90 -0
  237. package/.next/standalone/fp-cloud-cli/tests/test_usage.py +115 -0
  238. package/.next/standalone/fp-cloud-cli/tests/test_v1_origin_diagnostic.py +70 -0
  239. package/.next/standalone/fp-cloud-cli/tests/test_v1_routing.py +214 -0
  240. package/.next/standalone/fp-cloud-cli/tests/test_whoami.py +104 -0
  241. package/.next/standalone/fp-cloud-cli/uv.lock +552 -0
  242. package/.next/standalone/package.json +27 -21
  243. package/.next/standalone/sdk/python/CHANGELOG.md +70 -0
  244. package/.next/standalone/sdk/python/LICENSE +42 -0
  245. package/.next/standalone/sdk/python/MANIFEST.in +21 -0
  246. package/.next/standalone/sdk/python/README.md +466 -0
  247. package/.next/standalone/sdk/python/docs/README.md +249 -0
  248. package/.next/standalone/sdk/python/docs/_shared/README.md +43 -0
  249. package/.next/standalone/sdk/python/docs/_shared/__init__.py +195 -0
  250. package/.next/standalone/sdk/python/docs/crewai/README.md +328 -0
  251. package/.next/standalone/sdk/python/docs/crewai/examples/quickstart.py +61 -0
  252. package/.next/standalone/sdk/python/docs/crewai/examples/research_crew.py +92 -0
  253. package/.next/standalone/sdk/python/docs/langgraph/README.md +481 -0
  254. package/.next/standalone/sdk/python/docs/langgraph/examples/quickstart.py +51 -0
  255. package/.next/standalone/sdk/python/docs/langgraph/examples/research_agent.py +86 -0
  256. package/.next/standalone/sdk/python/docs/langgraph/examples/supervisor_handoff.py +83 -0
  257. package/.next/standalone/sdk/python/docs/llama_index/README.md +332 -0
  258. package/.next/standalone/sdk/python/docs/llama_index/examples/quickstart.py +62 -0
  259. package/.next/standalone/sdk/python/docs/llama_index/examples/research_agent.py +93 -0
  260. package/.next/standalone/sdk/python/docs/manual/README.md +491 -0
  261. package/.next/standalone/sdk/python/docs/manual/examples/quickstart.py +57 -0
  262. package/.next/standalone/sdk/python/docs/manual/examples/research_agent.py +133 -0
  263. package/.next/standalone/sdk/python/docs/pydantic_ai/README.md +323 -0
  264. package/.next/standalone/sdk/python/docs/pydantic_ai/examples/quickstart.py +48 -0
  265. package/.next/standalone/sdk/python/docs/pydantic_ai/examples/research_agent.py +94 -0
  266. package/.next/standalone/sdk/python/failproofai_sdk/__init__.py +131 -0
  267. package/.next/standalone/sdk/python/failproofai_sdk/_context.py +218 -0
  268. package/.next/standalone/sdk/python/failproofai_sdk/_environment.py +78 -0
  269. package/.next/standalone/sdk/python/failproofai_sdk/_events.py +752 -0
  270. package/.next/standalone/sdk/python/failproofai_sdk/_resolver.py +118 -0
  271. package/.next/standalone/sdk/python/failproofai_sdk/_runtime.py +21 -0
  272. package/.next/standalone/sdk/python/failproofai_sdk/_schema.py +317 -0
  273. package/.next/standalone/sdk/python/failproofai_sdk/_scopes.py +422 -0
  274. package/.next/standalone/sdk/python/failproofai_sdk/_version.py +1 -0
  275. package/.next/standalone/sdk/python/failproofai_sdk/_writer.py +750 -0
  276. package/.next/standalone/sdk/python/failproofai_sdk/integrations/__init__.py +274 -0
  277. package/.next/standalone/sdk/python/failproofai_sdk/integrations/_compat.py +247 -0
  278. package/.next/standalone/sdk/python/failproofai_sdk/integrations/_core.py +1076 -0
  279. package/.next/standalone/sdk/python/failproofai_sdk/integrations/crewai.py +1669 -0
  280. package/.next/standalone/sdk/python/failproofai_sdk/integrations/langchain.py +2151 -0
  281. package/.next/standalone/sdk/python/failproofai_sdk/integrations/llama_index.py +1588 -0
  282. package/.next/standalone/sdk/python/failproofai_sdk/integrations/pydantic_ai.py +977 -0
  283. package/.next/standalone/sdk/python/failproofai_sdk/py.typed +0 -0
  284. package/.next/standalone/sdk/python/pyproject.toml +92 -0
  285. package/.next/standalone/sdk/python/skill/SKILL.md +399 -0
  286. package/.next/standalone/sdk/python/skill/agents/openai.yaml +8 -0
  287. package/.next/standalone/sdk/python/skill/references/events.md +234 -0
  288. package/.next/standalone/sdk/python/skill/references/frameworks.md +314 -0
  289. package/.next/standalone/sdk/python/skill/references/install.md +100 -0
  290. package/.next/standalone/sdk/python/skill/references/integration.md +352 -0
  291. package/.next/standalone/sdk/python/tests/__init__.py +0 -0
  292. package/.next/standalone/sdk/python/tests/conftest.py +169 -0
  293. package/.next/standalone/sdk/python/tests/integrations/__init__.py +6 -0
  294. package/.next/standalone/sdk/python/tests/integrations/test_crewai.py +1299 -0
  295. package/.next/standalone/sdk/python/tests/integrations/test_langchain.py +2338 -0
  296. package/.next/standalone/sdk/python/tests/integrations/test_llama_index.py +1576 -0
  297. package/.next/standalone/sdk/python/tests/integrations/test_pydantic_ai.py +1102 -0
  298. package/.next/standalone/sdk/python/tests/test_context.py +410 -0
  299. package/.next/standalone/sdk/python/tests/test_docs.py +411 -0
  300. package/.next/standalone/sdk/python/tests/test_durability.py +1352 -0
  301. package/.next/standalone/sdk/python/tests/test_encoding.py +571 -0
  302. package/.next/standalone/sdk/python/tests/test_integrations.py +1127 -0
  303. package/.next/standalone/sdk/python/tests/test_no_customer_identifiers.py +214 -0
  304. package/.next/standalone/sdk/python/tests/test_packaging.py +185 -0
  305. package/.next/standalone/sdk/python/tests/test_resolver_umbrella.py +178 -0
  306. package/.next/standalone/sdk/python/tests/test_scopes.py +487 -0
  307. package/.next/standalone/sdk/python/tests/test_sdk.py +923 -0
  308. package/.next/standalone/sdk/python/tests/test_server_contract.py +650 -0
  309. package/.next/standalone/sdk/python/tests/test_site_docs.py +371 -0
  310. package/.next/standalone/sdk/python/tests/test_skill_snippets.py +165 -0
  311. package/.next/standalone/sdk/python/tests/test_spool_contract.py +287 -0
  312. package/.next/standalone/sdk/python/tests/test_spool_creation.py +360 -0
  313. package/.next/standalone/sdk/python/tests/test_wire_format.py +279 -0
  314. package/.next/standalone/sdk/python/tests/test_zero_dependencies.py +378 -0
  315. package/.next/standalone/sdk/python/uv.lock +6005 -0
  316. package/.next/standalone/server.js +1 -1
  317. package/README.md +77 -21
  318. package/bin/failproofai.mjs +579 -306
  319. package/dist/cli.mjs +6499 -3662
  320. package/dist/index.js +5 -5
  321. package/dist/worker.mjs +2390 -1978
  322. package/package.json +27 -21
  323. package/scripts/build-policy-pack.mjs +121 -0
  324. package/scripts/changelog-section.py +77 -0
  325. package/scripts/prune-standalone.mjs +3 -0
  326. package/scripts/python-version.py +232 -0
  327. package/scripts/translate-docs/cli.ts +21 -0
  328. package/scripts/translate-docs/mintlify-nav.ts +85 -13
  329. package/scripts/translate-docs/translator.ts +66 -11
  330. package/src/audit/cache.ts +40 -3
  331. package/src/audit/cli.ts +1 -1
  332. package/src/audit/index.ts +1 -1
  333. package/src/audit/replay.ts +89 -3
  334. package/src/audit/report.ts +5 -5
  335. package/src/audit/schedule-cli.ts +49 -53
  336. package/src/hooks/builtin-policies.ts +217 -579
  337. package/src/hooks/cloud-enrollment-cli.ts +66 -27
  338. package/src/hooks/cloud-managed-policies.ts +6 -1
  339. package/src/hooks/configure-wizard.ts +56 -369
  340. package/src/hooks/custom-hooks-loader.ts +89 -6
  341. package/src/hooks/fp-home.ts +92 -4
  342. package/src/hooks/fp-reset.ts +34 -2
  343. package/src/hooks/handler.ts +181 -11
  344. package/src/hooks/harness-cli.ts +79 -25
  345. package/src/hooks/hook-activity-store.ts +13 -3
  346. package/src/hooks/install-prompt.ts +25 -3
  347. package/src/hooks/manager.ts +424 -172
  348. package/src/hooks/migrations.ts +2 -2
  349. package/src/hooks/pack-cli.ts +885 -0
  350. package/src/hooks/pack-failclosed.ts +189 -0
  351. package/src/hooks/pack-manifest.ts +352 -0
  352. package/src/hooks/pack-store.ts +891 -0
  353. package/src/hooks/policy-catalog.ts +535 -0
  354. package/src/hooks/policy-evaluator.ts +24 -16
  355. package/src/hooks/policy-registry.ts +8 -2
  356. package/src/hooks/policy-types.ts +26 -0
  357. package/src/hooks/session-pause-cli.ts +33 -9
  358. package/src/hooks/tui.ts +695 -39
  359. package/src/hooks/types.ts +15 -1
  360. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0_usx0j._.js +0 -3
  361. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0_zk340._.js +0 -3
  362. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0agdw2a._.js +0 -3
  363. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0d1u_na._.js +0 -3
  364. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0oy4kxb._.js +0 -3
  365. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0zf034w._.js +0 -3
  366. package/.next/standalone/.next/server/chunks/[root-of-the-server]__1tvn4wf._.js +0 -3
  367. package/.next/standalone/.next/server/chunks/_0lxbzdq._.js +0 -3
  368. package/.next/standalone/.next/server/chunks/_1ger0a2._.js +0 -3
  369. package/.next/standalone/.next/server/chunks/_1zuiiy3._.js +0 -3
  370. package/.next/standalone/.next/server/chunks/node_modules_posthog-node_dist_entrypoints_index_node_mjs_1iiwm5e._.js +0 -3
  371. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__07tbbf3._.js +0 -3
  372. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0kc8_v5._.js +0 -4
  373. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0kgy9da._.js +0 -4
  374. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0mhqk5a._.js +0 -4
  375. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0pltpn8._.js +0 -4
  376. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0qkcyf-._.js +0 -4
  377. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0w0x_ok._.js +0 -4
  378. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__1_dfocn._.js +0 -4
  379. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__1bfex62._.js +0 -5
  380. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__1kzapg5._.js +0 -6
  381. package/.next/standalone/.next/server/chunks/ssr/_0lvyuv4._.js +0 -23
  382. package/.next/standalone/.next/static/chunks/2_2lhuojq2xop.js +0 -1
  383. package/.next/standalone/.next/static/chunks/36fw6yk1s6x_f.js +0 -1
  384. package/.next/standalone/.next/static/chunks/3k7mxbp9hiom0.js +0 -1
  385. package/.next/standalone/.next/static/chunks/3tzq0260n17ae.js +0 -6
  386. package/.next/standalone/.next/static/chunks/3wq9x0c-7ld5d.css +0 -2
  387. package/src/hooks/policy-presets.ts +0 -135
  388. /package/.next/standalone/.next/static/{ZklXxyA5ygsWSQz2u_zii → I5kEb9kSgYS63j4iqfVLO}/_buildManifest.js +0 -0
  389. /package/.next/standalone/.next/static/{ZklXxyA5ygsWSQz2u_zii → I5kEb9kSgYS63j4iqfVLO}/_clientMiddlewareManifest.js +0 -0
  390. /package/.next/standalone/.next/static/{ZklXxyA5ygsWSQz2u_zii → I5kEb9kSgYS63j4iqfVLO}/_ssgManifest.js +0 -0
@@ -1,9 +1,10 @@
1
1
  # Security Policy
2
2
 
3
- failproofai is an npm package that installs hooks into AI coding agents (Claude
4
- Code, Codex, and others) and runs locally in developers' environments, observing
5
- and gating agent actions. A compromised dependency would therefore run on our
6
- users' machines, inside their agent sessions so we treat our supply chain as
3
+ failproofai is an npm package that installs hooks into AI agent harnesses
4
+ (Claude Code, Codex, Cursor, the Hermes and OpenClaw gateways, and others) and
5
+ runs locally in the environment the agent runs in, observing and gating agent
6
+ actions. A compromised dependency would therefore run on our
7
+ users' machines and servers, inside their agent sessions — so we treat our supply chain as
7
8
  part of our users' trust boundary. This document covers how to report a
8
9
  vulnerability and how our dependency supply-chain scanning works.
9
10
 
@@ -2,7 +2,6 @@
2
2
 
3
3
  import { configuredCustomPolicyPaths, readMergedHooksConfig } from "@/src/hooks/hooks-config";
4
4
  import { hooksInstalledInSettings, getSettingsPath } from "@/src/hooks/manager";
5
- import { BUILTIN_POLICIES } from "@/src/hooks/builtin-policies";
6
5
  import { listIntegrations } from "@/src/hooks/integrations";
7
6
  import { HOOK_SCOPES } from "@/src/hooks/types";
8
7
  import type { HookScope, IntegrationType } from "@/src/hooks/types";
@@ -13,6 +12,8 @@ import { readFile } from "node:fs/promises";
13
12
  import { existsSync } from "node:fs";
14
13
  import { basename, resolve } from "node:path";
15
14
  import { customPoliciesDir } from "@/src/hooks/fp-home";
15
+ import { readInstalledPacks } from "@/src/hooks/pack-manifest";
16
+ import type { PackError, ResolvedPack } from "@/src/hooks/pack-manifest";
16
17
 
17
18
  export interface PolicyParamSpec {
18
19
  type: string;
@@ -30,6 +31,9 @@ export interface PolicyInfo {
30
31
  eventScope: string;
31
32
  params?: Record<string, PolicyParamSpec>;
32
33
  currentParams?: Record<string, unknown>;
34
+ /** The pack this policy came from — every policy has one now. */
35
+ packId: string;
36
+ packVersion: string;
33
37
  }
34
38
 
35
39
  export interface CustomPolicyInfo {
@@ -68,6 +72,25 @@ export interface CliInstallStatus {
68
72
  detected: boolean;
69
73
  }
70
74
 
75
+ /** One policy carried by an installed pack. */
76
+ export interface PackPolicyInfo {
77
+ name: string;
78
+ description: string;
79
+ category: string;
80
+ enabled: boolean;
81
+ }
82
+
83
+ export interface InstalledPackInfo {
84
+ id: string;
85
+ version: string;
86
+ /** Where it came from, verbatim — `github:acme/ops@v1.0.0` or `bundled:...`. */
87
+ source: string;
88
+ effect: "enforce" | "observe";
89
+ policies: PackPolicyInfo[];
90
+ /** Set when the record itself could not be read, e.g. its digest changed. */
91
+ error?: string;
92
+ }
93
+
71
94
  export interface HooksConfigPayload {
72
95
  enabledPolicies: string[];
73
96
  /** Claude-only legacy field; kept for back-compat. New UI should consume `clis`. */
@@ -83,6 +106,8 @@ export interface HooksConfigPayload {
83
106
  customPolicies?: CustomPolicyInfo[];
84
107
  /** Convention-discovered policy files, project scope first. */
85
108
  conventionPolicies: ConventionPolicyFile[];
109
+ /** Installed policy packs, read from `installed.json`. */
110
+ packs: InstalledPackInfo[];
86
111
  }
87
112
 
88
113
  /**
@@ -179,7 +204,6 @@ export async function getHooksConfigAction(): Promise<HooksConfigPayload> {
179
204
  // Match runtime enforcement: project, local, and user config all
180
205
  // contribute to the effective policy state shown by the dashboard.
181
206
  const config = readMergedHooksConfig(launchCwd);
182
- const enabledSet = new Set(config.enabledPolicies);
183
207
  const disabledCustomPolicies = new Set(config.disabledCustomPolicies ?? []);
184
208
 
185
209
  const installedScopes = HOOK_SCOPES.filter((s) => hooksInstalledInSettings(s));
@@ -194,21 +218,52 @@ export async function getHooksConfigAction(): Promise<HooksConfigPayload> {
194
218
  detected: integration.detectInstalled(),
195
219
  }));
196
220
 
197
- const policies: PolicyInfo[] = BUILTIN_POLICIES.map((p) => ({
198
- name: p.name,
199
- description: p.description,
200
- category: p.category,
201
- defaultEnabled: p.defaultEnabled,
202
- beta: !!p.beta,
203
- enabled: enabledSet.has(p.name),
204
- eventScope: buildEventScope(p.match),
205
- params: p.params
206
- ? Object.fromEntries(
207
- Object.entries(p.params).map(([k, v]) => [k, { type: v.type, description: v.description, default: v.default }])
208
- )
209
- : undefined,
210
- currentParams: p.params ? (config.policyParams?.[p.name] ?? {}) : undefined,
211
- }));
221
+ // Read once, ahead of everything that needs it: the policy list IS the packs'
222
+ // policies now, and the pack listing further down describes the same read.
223
+ let installedPacks: ResolvedPack[] = [];
224
+ let packErrors: PackError[] = [];
225
+ try {
226
+ const result = readInstalledPacks();
227
+ installedPacks = result.packs;
228
+ packErrors = result.errors;
229
+ } catch {
230
+ // A listing must not be the thing that turns an unreadable manifest into a
231
+ // broken page.
232
+ }
233
+
234
+ // Every policy that enforces here comes from an installed PACK. Nothing is
235
+ // compiled into this build any more except the always-on self-protection
236
+ // guard — which no listing can switch off, so it has no row.
237
+ const policies: PolicyInfo[] = [];
238
+ for (const pack of installedPacks) {
239
+ const taken = pack.enabled ?? pack.policies.map((p) => p.name);
240
+ for (const policy of pack.policies) {
241
+ policies.push({
242
+ name: policy.name,
243
+ description: policy.description,
244
+ category: policy.category,
245
+ defaultEnabled: policy.defaultEnabled,
246
+ beta: false,
247
+ enabled:
248
+ taken.includes(policy.name) &&
249
+ !disabledCustomPolicies.has(`pack:${pack.id}@${pack.version}:${policy.name}`),
250
+ eventScope: buildEventScope(policy.match),
251
+ packId: pack.id,
252
+ packVersion: pack.version,
253
+ ...(policy.params
254
+ ? {
255
+ params: Object.fromEntries(
256
+ Object.entries(policy.params).map(([k, v]) => [
257
+ k,
258
+ { type: v.type, description: v.description, default: v.default },
259
+ ]),
260
+ ),
261
+ currentParams: config.policyParams?.[policy.name] ?? {},
262
+ }
263
+ : {}),
264
+ });
265
+ }
266
+ }
212
267
 
213
268
  const customPoliciesPaths = configuredCustomPolicyPaths(config);
214
269
  const launchRoot = findProjectConfigDir(launchCwd);
@@ -232,6 +287,41 @@ export async function getHooksConfigAction(): Promise<HooksConfigPayload> {
232
287
  new Set(resolvedCustomPaths),
233
288
  );
234
289
 
290
+ // Metadata only — deliberately never imported. Same rule as the convention
291
+ // files above: this runs on every page load, and importing a pack's artifact
292
+ // would execute a third party's code inside the long-lived dashboard server.
293
+ // The import check that proves a pack still loads belongs to the CLI and to
294
+ // the user-initiated install action.
295
+ const packs: InstalledPackInfo[] = installedPacks.map((pack) => {
296
+ const taken = pack.enabled ?? pack.policies.map((p) => p.name);
297
+ return {
298
+ id: pack.id,
299
+ version: pack.version,
300
+ source: pack.source,
301
+ effect: pack.effect,
302
+ policies: pack.policies.map((policy) => ({
303
+ name: policy.name,
304
+ description: policy.description,
305
+ category: policy.category,
306
+ enabled:
307
+ taken.includes(policy.name) &&
308
+ !disabledCustomPolicies.has(`pack:${pack.id}@${pack.version}:${policy.name}`),
309
+ })),
310
+ };
311
+ });
312
+ for (const err of packErrors) {
313
+ // A pack that will not load is what the machine denies for; a listing that
314
+ // omitted it would be the quietest possible way to report that.
315
+ packs.push({
316
+ id: err.id ?? "(unnamed pack)",
317
+ version: "",
318
+ source: "",
319
+ effect: "enforce",
320
+ policies: [],
321
+ error: err.reason,
322
+ });
323
+ }
324
+
235
325
  return {
236
326
  enabledPolicies: config.enabledPolicies,
237
327
  installedScopes,
@@ -242,5 +332,6 @@ export async function getHooksConfigAction(): Promise<HooksConfigPayload> {
242
332
  customPoliciesPath: customPoliciesPaths.length === 1 ? customPoliciesPaths[0] : undefined,
243
333
  customPolicies: customPolicies.length ? customPolicies : undefined,
244
334
  conventionPolicies,
335
+ packs,
245
336
  };
246
337
  }
@@ -0,0 +1,163 @@
1
+ "use server";
2
+
3
+ /**
4
+ * Installing and managing policy packs from the local dashboard.
5
+ *
6
+ * These are USER-INITIATED actions, which is what makes it acceptable for
7
+ * `addPack` to import the pack's artifact here: it verifies that what a
8
+ * publisher declared is what their code registers, and refusing at install time
9
+ * is the whole reason a broken pack cannot brick the machine. `get-hooks-config`
10
+ * deliberately does the opposite — it lists packs from `installed.json` and
11
+ * imports nothing, because that runs on every page load.
12
+ */
13
+ import {
14
+ addPackFromSource,
15
+ fetchPackPreview,
16
+ CORE_SOURCE,
17
+ addPack,
18
+ removePack,
19
+ setPackPolicyEnabled,
20
+ } from "@/src/hooks/pack-store";
21
+ import { readHooksConfig, writeHooksConfig } from "@/src/hooks/hooks-config";
22
+ import { readInstalledPacks } from "@/src/hooks/pack-manifest";
23
+
24
+ export interface PackActionResult {
25
+ ok: boolean;
26
+ /** Present when ok — what landed, so the UI can say it without a refetch. */
27
+ id?: string;
28
+ version?: string;
29
+ enabled?: string[];
30
+ available?: string[];
31
+ /** Present when not ok — the publisher's or the loader's own words. */
32
+ error?: string;
33
+ }
34
+
35
+ /**
36
+ * Install a pack by the source a person typed: `core`, `acme/ops`,
37
+ * `acme/ops@v1.2.0`, or a release URL.
38
+ *
39
+ * Routed through the SAME resolver the CLI uses. While the alias list lived in
40
+ * `pack-cli.ts`, `core` worked in the terminal and failed in the browser — the
41
+ * one thing a shared entry point exists to prevent.
42
+ */
43
+ export async function addPackWebAction(
44
+ source: string,
45
+ opts?: { all?: boolean; only?: string[]; categories?: string[] },
46
+ ): Promise<PackActionResult> {
47
+ const trimmed = source.trim();
48
+ if (!trimmed) return { ok: false, error: "Enter a pack source, for example acme/ops" };
49
+ try {
50
+ const result = await addPackFromSource(trimmed, opts ?? {});
51
+ return {
52
+ ok: true,
53
+ id: result.id,
54
+ version: result.version,
55
+ enabled: result.enabled,
56
+ available: result.available,
57
+ };
58
+ } catch (err) {
59
+ // Surfaced verbatim. Every refusal on this path already names what was wrong
60
+ // and whose fault it is — an unresolvable source, a digest that does not
61
+ // match, a manifest declaring a policy its artifact never registers.
62
+ return { ok: false, error: err instanceof Error ? err.message : String(err) };
63
+ }
64
+ }
65
+
66
+ /**
67
+ * Install the Failproof AI policies.
68
+ *
69
+ * Fetched from their GitHub release like anybody else's pack — this package
70
+ * carries no copy of them. The name is kept so the dashboard's button does not
71
+ * have to know that, but there is nothing "bundled" about it any more.
72
+ */
73
+ export async function addBundledPackWebAction(): Promise<PackActionResult> {
74
+ try {
75
+ const result = await addPack(CORE_SOURCE);
76
+ return {
77
+ ok: true,
78
+ id: result.id,
79
+ version: result.version,
80
+ enabled: result.enabled,
81
+ available: result.available,
82
+ };
83
+ } catch (err) {
84
+ return { ok: false, error: err instanceof Error ? err.message : String(err) };
85
+ }
86
+ }
87
+
88
+ export async function removePackWebAction(id: string): Promise<PackActionResult> {
89
+ return removePack(id) ? { ok: true, id } : { ok: false, error: `No installed pack with id ${id}` };
90
+ }
91
+
92
+ /**
93
+ * Turn one policy of an installed pack on or off.
94
+ *
95
+ * Writes the pack's own SELECTION, the same lever the CLI uses — not a
96
+ * `disabledCustomPolicies` entry, which is keyed by version and would silently
97
+ * switch everything back on at the next upgrade. Enabling also clears any such
98
+ * key, so a policy switched off before this existed can still be switched back on.
99
+ */
100
+ export async function togglePackPolicyAction(
101
+ packId: string,
102
+ name: string,
103
+ enabled: boolean,
104
+ ): Promise<PackActionResult> {
105
+ const result = setPackPolicyEnabled(packId, name, enabled);
106
+ if (!result.ok) return { ok: false, error: result.reason };
107
+ if (enabled) {
108
+ const pack = readInstalledPacks().packs.find((p) => p.id === packId);
109
+ if (pack) {
110
+ const key = `pack:${pack.id}@${pack.version}:${name}`;
111
+ const config = readHooksConfig();
112
+ const remaining = (config.disabledCustomPolicies ?? []).filter((k) => k !== key);
113
+ if (remaining.length !== (config.disabledCustomPolicies ?? []).length) {
114
+ const { disabledCustomPolicies: _dropped, ...rest } = config;
115
+ writeHooksConfig(
116
+ remaining.length > 0 ? { ...rest, disabledCustomPolicies: remaining } : rest,
117
+ );
118
+ }
119
+ }
120
+ }
121
+ return { ok: true, id: packId };
122
+ }
123
+
124
+ export interface PackPreviewResult {
125
+ ok: boolean;
126
+ id?: string;
127
+ version?: string;
128
+ source?: string;
129
+ effect?: "enforce" | "observe";
130
+ policies?: Array<{ name: string; description: string; category: string; defaultEnabled: boolean }>;
131
+ error?: string;
132
+ }
133
+
134
+ /**
135
+ * Read what a pack contains WITHOUT installing it — the browser half of
136
+ * `failproofai pack list <source>`.
137
+ *
138
+ * Fetches the manifest only. The entry artifact is never downloaded and never
139
+ * imported, so previewing a stranger's pack from the dashboard cannot run a
140
+ * stranger's code inside this long-lived server.
141
+ */
142
+ export async function previewPackWebAction(source: string): Promise<PackPreviewResult> {
143
+ const trimmed = source.trim();
144
+ if (!trimmed) return { ok: false, error: "Enter a pack source, for example acme/ops" };
145
+ try {
146
+ const preview = await fetchPackPreview(trimmed);
147
+ return {
148
+ ok: true,
149
+ id: preview.id,
150
+ version: preview.version,
151
+ source: preview.source,
152
+ effect: preview.effect,
153
+ policies: preview.policies.map((p) => ({
154
+ name: p.name,
155
+ description: p.description,
156
+ category: p.category,
157
+ defaultEnabled: p.defaultEnabled,
158
+ })),
159
+ };
160
+ } catch (err) {
161
+ return { ok: false, error: err instanceof Error ? err.message : String(err) };
162
+ }
163
+ }
@@ -21,7 +21,7 @@ import { useEffect, useState } from "react";
21
21
  const STAGES = [
22
22
  { label: "discovering transcripts", detail: "walking ~/.claude, ~/.codex, ~/.cursor, …" },
23
23
  { label: "parsing session logs", detail: "reading JSONL + sqlite session stores" },
24
- { label: "running policy checks", detail: "replaying through 30 builtin policies" },
24
+ { label: "running policy checks", detail: "replaying every policy against each tool call" },
25
25
  { label: "aggregating results", detail: "counting hits, ranking by frequency" },
26
26
  ];
27
27
 
@@ -34,49 +34,49 @@ const PASTE_LINE = "[ audit card copied to your clipboard — paste it into the
34
34
  /** Short, curiosity-forward — for X / Twitter. Ends on the npx CTA + @failproofai. */
35
35
  export const X_TEMPLATES: ((c: ShareCtx) => string)[] = [
36
36
  ({ score, arch }) =>
37
- `my coding agent has a personality and it's ${arch}. did not see that coming.\n\nran a failproof audit, scored ${score}/100, all local. find out what yours is → ${X_CTA}`,
37
+ `my agent has a personality and it's ${arch}. did not see that coming.\n\nran a failproof audit, scored ${score}/100, all local. find out what yours is → ${X_CTA}`,
38
38
  ({ score, arch }) =>
39
- `spent 30 seconds auditing my coding agent. learned more about it than i did all month.\n\nit's ${arch}. scored ${score}/100. → ${X_CTA}`,
39
+ `spent 30 seconds auditing my agent. learned more about it than i did all month.\n\nit's ${arch}. scored ${score}/100. → ${X_CTA}`,
40
40
  ({ score }) =>
41
41
  `my agent scored ${score}/100. think yours can beat it?\n\n30 sec audit, runs locally, gives you a personality too → ${X_CTA}`,
42
42
  ({ arch }) =>
43
- `turns out my coding agent is ${arch} and honestly it explains everything.\n\n→ ${X_CTA}`,
43
+ `turns out my agent is ${arch} and honestly it explains everything.\n\n→ ${X_CTA}`,
44
44
  ({ score, arch }) =>
45
45
  `ran a failproof audit on my agent. it reads how it actually behaves when things break, not just the happy path.\n\npersonality: ${arch}. score: ${score}/100. all local → ${X_CTA}`,
46
46
  ({ score, arch }) =>
47
- `got to know my coding agent today. it's ${arch} and scored ${score}/100. wow.\n\naudit yours in 30s, nothing leaves your machine → ${X_CTA}`,
47
+ `got to know my agent today. it's ${arch} and scored ${score}/100. wow.\n\naudit yours in 30s, nothing leaves your machine → ${X_CTA}`,
48
48
  ({ score, arch }) =>
49
- `your coding agent has a personality. you just haven't met it.\n\ni met mine today: ${arch}, ${score}/100. → ${X_CTA}`,
49
+ `your agent has a personality. you just haven't met it.\n\ni met mine today: ${arch}, ${score}/100. → ${X_CTA}`,
50
50
  ({ score, arch }) =>
51
51
  `everyone talks about what their agent can build. nobody talks about how it acts when it breaks.\n\nmine's ${arch}, scored ${score}/100, all local → ${X_CTA}`,
52
52
  ({ score, arch }) =>
53
53
  `every agent builder should run this once.\n\n30 sec, local, gives your agent a personality and a quality score. mine: ${arch}, ${score}/100.\n\n${X_CTA}`,
54
54
  ({ score, arch }) =>
55
- `i'll go first: ${arch}, ${score}/100.\n\nwhat's your coding agent? 30 sec audit, no signup → ${X_CTA}`,
55
+ `i'll go first: ${arch}, ${score}/100.\n\nwhat's your agent? 30 sec audit, no signup → ${X_CTA}`,
56
56
  ];
57
57
 
58
58
  /** Longer, reflective — for LinkedIn. Ends on the npx CTA + @Failproof AI. */
59
59
  export const LI_TEMPLATES: ((c: ShareCtx) => string)[] = [
60
60
  ({ score, arch }) =>
61
- `I've spent more hours with my coding agent this month than with most people I know. Today I realized I couldn't tell you a single thing about how it actually behaves.\n\nSo I audited it. Turns out it's ${arch}, and it scored ${score}/100.\n\nThe audit reads its real history, including how it handles failures, not just the clean runs. 30 seconds, runs entirely locally.\n\nMeet yours: ${LI_CTA}`,
61
+ `I've spent more hours with my agent this month than with most people I know. Today I realized I couldn't tell you a single thing about how it actually behaves.\n\nSo I audited it. Turns out it's ${arch}, and it scored ${score}/100.\n\nThe audit reads its real history, including how it handles failures, not just the clean runs. 30 seconds, runs entirely locally.\n\nMeet yours: ${LI_CTA}`,
62
62
  ({ score, arch }) =>
63
- `Took a personality test today. It wasn't for me — it was for my AI coding agent.\n\nThe result: ${arch}, with a quality score of ${score}/100.\n\nIt works by reading the agent's actual run history, so the personality comes from how it really behaves, not a vibe. Took 30 seconds and stayed local.\n\nTry it on yours: ${LI_CTA}`,
63
+ `Took a personality test today. It wasn't for me — it was for my AI agent.\n\nThe result: ${arch}, with a quality score of ${score}/100.\n\nIt works by reading the agent's actual run history, so the personality comes from how it really behaves, not a vibe. Took 30 seconds and stayed local.\n\nTry it on yours: ${LI_CTA}`,
64
64
  ({ score, arch }) =>
65
65
  `Everyone asks what their AI agent can build. I just found out mine has a temper.\n\nAfter watching how it reacts to a failed command, the audit called it ${arch}. It also scored its quality at ${score}/100.\n\nOddly useful to see it written down. 30 seconds, all local: ${LI_CTA}`,
66
66
  ({ score, arch }) =>
67
67
  `My agent does this very specific thing every time a command fails. Today I learned there's basically a name for it.\n\nRan a quick audit and it came back ${arch}, scored ${score}/100. The whole read is based on how the agent handles things going wrong, which is where its real character shows.\n\n30 seconds, nothing leaves your machine: ${LI_CTA}`,
68
68
  ({ score, arch }) =>
69
- `My AI coding agent scored ${score}/100 today. I didn't know you could even measure that.\n\nThe same audit also handed it a personality: ${arch}.\n\nIt reads the agent's real history and tells you where it's solid and where it slips. Took 30 seconds and ran fully locally: ${LI_CTA}`,
69
+ `My AI agent scored ${score}/100 today. I didn't know you could even measure that.\n\nThe same audit also handed it a personality: ${arch}.\n\nIt reads the agent's real history and tells you where it's solid and where it slips. Took 30 seconds and ran fully locally: ${LI_CTA}`,
70
70
  ({ score, arch }) =>
71
- `I'm usually the first to scroll past "audit your X" tools. This one took 30 seconds and actually told me something.\n\nMy coding agent is ${arch}, and it scored ${score}/100.\n\nIt reads the agent's real run history rather than asking me anything, and none of it leaves the machine: ${LI_CTA}`,
71
+ `I'm usually the first to scroll past "audit your X" tools. This one took 30 seconds and actually told me something.\n\nMy agent is ${arch}, and it scored ${score}/100.\n\nIt reads the agent's real run history rather than asking me anything, and none of it leaves the machine: ${LI_CTA}`,
72
72
  ({ score, arch }) =>
73
- `What is your coding agent's personality? I realized today that I had no answer.\n\nSo I checked. Mine is ${arch}, scored ${score}/100, with a clear read on where it shines and where it slips.\n\nIf you work with agents, run it and drop yours in the comments. 30 seconds, fully local: ${LI_CTA}`,
73
+ `What is your agent's personality? I realized today that I had no answer.\n\nSo I checked. Mine is ${arch}, scored ${score}/100, with a clear read on where it shines and where it slips.\n\nIf you work with agents, run it and drop yours in the comments. 30 seconds, fully local: ${LI_CTA}`,
74
74
  ({ score, arch }) =>
75
- `I trusted my coding agent a little less after this morning, and quite a bit more by the afternoon.\n\nI ran an audit on it. It showed me exactly where it's reliable and where it isn't, gave it a personality (${arch}), and scored it ${score}/100.\n\nKnowing the gaps is what made me trust it more. 30 seconds, all local: ${LI_CTA}`,
75
+ `I trusted my agent a little less after this morning, and quite a bit more by the afternoon.\n\nI ran an audit on it. It showed me exactly where it's reliable and where it isn't, gave it a personality (${arch}), and scored it ${score}/100.\n\nKnowing the gaps is what made me trust it more. 30 seconds, all local: ${LI_CTA}`,
76
76
  ({ score, arch }) =>
77
77
  `I almost skipped this because I assumed it would quietly ship my code off somewhere. It doesn't. Everything runs locally.\n\n30 seconds later I had my agent's personality (${arch}) and a quality score (${score}/100).\n\nIf privacy is usually what stops you from trying these, this one is different: ${LI_CTA}`,
78
78
  ({ score, arch }) =>
79
- `Found out my AI coding agent has a personality type. Found out it's ${arch}. Found out that explains a lot.\n\nIt scored ${score}/100 too. The audit reads how the agent handles failures, not just the runs where everything goes fine.\n\n30 seconds, runs locally: ${LI_CTA}`,
79
+ `Found out my AI agent has a personality type. Found out it's ${arch}. Found out that explains a lot.\n\nIt scored ${score}/100 too. The audit reads how the agent handles failures, not just the runs where everything goes fine.\n\n30 seconds, runs locally: ${LI_CTA}`,
80
80
  ];
81
81
 
82
82
  /** djb2 hash — stable per seed so the template choice is deterministic. */