failproofai 1.0.1 → 1.0.2-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.
- package/.next/standalone/.next/BUILD_ID +1 -1
- package/.next/standalone/.next/build-manifest.json +3 -3
- package/.next/standalone/.next/prerender-manifest.json +6 -6
- package/.next/standalone/.next/required-server-files.json +1 -1
- package/.next/standalone/.next/server/app/_global-error/page/server-reference-manifest.json +1 -1
- package/.next/standalone/.next/server/app/_global-error/page.js +2 -2
- package/.next/standalone/.next/server/app/_global-error/page.js.nft.json +1 -1
- package/.next/standalone/.next/server/app/_global-error/page_client-reference-manifest.js +1 -1
- package/.next/standalone/.next/server/app/_global-error.html +1 -1
- package/.next/standalone/.next/server/app/_global-error.rsc +7 -7
- package/.next/standalone/.next/server/app/_global-error.segments/__PAGE__.segment.rsc +6 -6
- package/.next/standalone/.next/server/app/_global-error.segments/_full.segment.rsc +7 -7
- package/.next/standalone/.next/server/app/_global-error.segments/_tree.segment.rsc +1 -1
- package/.next/standalone/.next/server/app/_not-found/page/server-reference-manifest.json +1 -1
- package/.next/standalone/.next/server/app/_not-found/page.js +2 -2
- package/.next/standalone/.next/server/app/_not-found/page.js.nft.json +1 -1
- package/.next/standalone/.next/server/app/_not-found/page_client-reference-manifest.js +1 -1
- package/.next/standalone/.next/server/app/_not-found.html +1 -1
- package/.next/standalone/.next/server/app/_not-found.rsc +15 -15
- package/.next/standalone/.next/server/app/_not-found.segments/_full.segment.rsc +15 -15
- package/.next/standalone/.next/server/app/_not-found.segments/_not-found/__PAGE__.segment.rsc +14 -14
- package/.next/standalone/.next/server/app/_not-found.segments/_tree.segment.rsc +2 -2
- package/.next/standalone/.next/server/app/api/audit/invite/route.js +3 -2
- package/.next/standalone/.next/server/app/api/audit/invite/route.js.nft.json +1 -1
- package/.next/standalone/.next/server/app/api/audit/run/route.js +5 -4
- package/.next/standalone/.next/server/app/api/audit/run/route.js.nft.json +1 -1
- package/.next/standalone/.next/server/app/api/audit/status/route.js.nft.json +1 -1
- package/.next/standalone/.next/server/app/api/auth/login-request/route.js +2 -2
- package/.next/standalone/.next/server/app/api/auth/login-request/route.js.nft.json +1 -1
- package/.next/standalone/.next/server/app/api/auth/login-verify/route.js +4 -3
- package/.next/standalone/.next/server/app/api/auth/login-verify/route.js.nft.json +1 -1
- package/.next/standalone/.next/server/app/api/auth/logout/route.js +4 -4
- package/.next/standalone/.next/server/app/api/auth/logout/route.js.nft.json +1 -1
- package/.next/standalone/.next/server/app/api/auth/status/route.js +4 -4
- package/.next/standalone/.next/server/app/api/auth/status/route.js.nft.json +1 -1
- package/.next/standalone/.next/server/app/api/download/[project]/[session]/route.js.nft.json +1 -1
- package/.next/standalone/.next/server/app/audit/page/server-reference-manifest.json +2 -2
- package/.next/standalone/.next/server/app/audit/page.js +2 -2
- package/.next/standalone/.next/server/app/audit/page.js.nft.json +1 -1
- package/.next/standalone/.next/server/app/audit/page_client-reference-manifest.js +1 -1
- package/.next/standalone/.next/server/app/index.html +1 -1
- package/.next/standalone/.next/server/app/index.rsc +15 -15
- package/.next/standalone/.next/server/app/index.segments/__PAGE__.segment.rsc +14 -14
- package/.next/standalone/.next/server/app/index.segments/_full.segment.rsc +15 -15
- package/.next/standalone/.next/server/app/index.segments/_tree.segment.rsc +2 -2
- package/.next/standalone/.next/server/app/page/server-reference-manifest.json +1 -1
- package/.next/standalone/.next/server/app/page.js +2 -2
- package/.next/standalone/.next/server/app/page.js.nft.json +1 -1
- package/.next/standalone/.next/server/app/page_client-reference-manifest.js +1 -1
- package/.next/standalone/.next/server/app/policies/page/server-reference-manifest.json +66 -22
- package/.next/standalone/.next/server/app/policies/page.js +5 -4
- package/.next/standalone/.next/server/app/policies/page.js.nft.json +1 -1
- package/.next/standalone/.next/server/app/policies/page_client-reference-manifest.js +1 -1
- package/.next/standalone/.next/server/app/project/[name]/page/server-reference-manifest.json +1 -1
- package/.next/standalone/.next/server/app/project/[name]/page.js +2 -2
- package/.next/standalone/.next/server/app/project/[name]/page.js.nft.json +1 -1
- package/.next/standalone/.next/server/app/project/[name]/page_client-reference-manifest.js +1 -1
- package/.next/standalone/.next/server/app/project/[name]/session/[sessionId]/page/react-loadable-manifest.json +2 -2
- package/.next/standalone/.next/server/app/project/[name]/session/[sessionId]/page/server-reference-manifest.json +2 -2
- package/.next/standalone/.next/server/app/project/[name]/session/[sessionId]/page.js +2 -2
- package/.next/standalone/.next/server/app/project/[name]/session/[sessionId]/page.js.nft.json +1 -1
- package/.next/standalone/.next/server/app/project/[name]/session/[sessionId]/page_client-reference-manifest.js +1 -1
- package/.next/standalone/.next/server/app/projects/page/server-reference-manifest.json +1 -1
- package/.next/standalone/.next/server/app/projects/page.js +2 -2
- package/.next/standalone/.next/server/app/projects/page.js.nft.json +1 -1
- package/.next/standalone/.next/server/app/projects/page_client-reference-manifest.js +1 -1
- package/.next/standalone/.next/server/app/settings/page/server-reference-manifest.json +4 -4
- package/.next/standalone/.next/server/app/settings/page.js +1 -1
- package/.next/standalone/.next/server/app/settings/page.js.nft.json +1 -1
- package/.next/standalone/.next/server/app/settings/page_client-reference-manifest.js +1 -1
- package/.next/standalone/.next/server/chunks/{[externals]__1qzqcio._.js → [externals]__0e32-7c._.js} +1 -1
- package/.next/standalone/.next/server/chunks/[externals]__1s462yl._.js +3 -0
- package/.next/standalone/.next/server/chunks/[root-of-the-server]__01eqny5._.js +3 -0
- package/.next/standalone/.next/server/chunks/[root-of-the-server]__0_0xu5z._.js +1 -1
- package/.next/standalone/.next/server/chunks/{[root-of-the-server]__1p8poxd._.js → [root-of-the-server]__0igxt32._.js} +2 -2
- package/.next/standalone/.next/server/chunks/[root-of-the-server]__0neqlu-._.js +3 -0
- package/.next/standalone/.next/server/chunks/[root-of-the-server]__0o07qi9._.js +3 -0
- package/.next/standalone/.next/server/chunks/[root-of-the-server]__0t9oqnn._.js +3 -0
- package/.next/standalone/.next/server/chunks/_0bs-v8p._.js +3 -0
- package/.next/standalone/.next/server/chunks/_0tovk6q._.js +3 -0
- package/.next/standalone/.next/server/chunks/_0trp3yc._.js +3 -0
- package/.next/standalone/.next/server/chunks/_185gyk9._.js +3 -0
- package/.next/standalone/.next/server/chunks/_1ek68ln._.js +5 -6
- package/.next/standalone/.next/server/chunks/lib_telemetry-id_ts_1k8gj9o._.js +3 -0
- 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
- 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
- package/.next/standalone/.next/server/chunks/package_json_[json]_cjs_1nxcc4v._.js +1 -1
- package/.next/standalone/.next/server/chunks/src_hooks_0xbw3bu._.js +12 -0
- package/.next/standalone/.next/server/chunks/src_hooks_fp-home_ts_09kv0bn._.js +1 -1
- package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__013jr2b._.js +4 -0
- package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__01wy8d-._.js +4 -0
- package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__02npjtd._.js +4 -0
- package/.next/standalone/.next/server/chunks/ssr/{[root-of-the-server]__0spkm68._.js → [root-of-the-server]__07gm3zl._.js} +21 -20
- package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0da85px._.js +4 -0
- package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0ftmoxc._.js +4 -0
- package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0oa1lav._.js +1 -1
- package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0p-5p8u._.js +4 -0
- package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0s740oi._.js +6 -0
- package/.next/standalone/.next/server/chunks/ssr/{[root-of-the-server]__07tbbf3._.js → [root-of-the-server]__0zig5sv._.js} +2 -2
- package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__192nhvh._.js +5 -0
- package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__1p2otjt._.js +4 -0
- package/.next/standalone/.next/server/chunks/ssr/{_0lvyuv4._.js → _00e9tnf._.js} +2 -2
- package/.next/standalone/.next/server/chunks/ssr/_08x1r5t._.js +1 -1
- package/.next/standalone/.next/server/chunks/ssr/{_0u5zauv._.js → _12l4a_k._.js} +1 -1
- package/.next/standalone/.next/server/chunks/ssr/_1u8-lu2._.js +1 -1
- package/.next/standalone/.next/server/chunks/ssr/_1zopuov._.js +1 -1
- package/.next/standalone/.next/server/chunks/ssr/app_audit__components_audit-dashboard_tsx_0p9ud47._.js +13 -13
- package/.next/standalone/.next/server/chunks/ssr/app_global-error_tsx_1kp6l3x._.js +1 -1
- package/.next/standalone/.next/server/chunks/ssr/app_policies_hooks-client_tsx_19dqvpc._.js +2 -2
- package/.next/standalone/.next/server/chunks/ssr/app_settings_settings-client_tsx_20lq-mq._.js +1 -1
- package/.next/standalone/.next/server/chunks/ssr/src_hooks_08o7bqo._.js +10 -0
- package/.next/standalone/.next/server/chunks/ssr/src_hooks_builtin-policies_ts_09j2ndl._.js +1 -1
- package/.next/standalone/.next/server/chunks/ssr/src_hooks_fp-home_ts_0je3xkv._.js +1 -1
- package/.next/standalone/.next/server/middleware-build-manifest.js +3 -3
- package/.next/standalone/.next/server/middleware.js +1 -1
- package/.next/standalone/.next/server/pages/404.html +1 -1
- package/.next/standalone/.next/server/pages/500.html +1 -1
- package/.next/standalone/.next/server/server-reference-manifest.js +1 -1
- package/.next/standalone/.next/server/server-reference-manifest.json +71 -27
- package/.next/standalone/.next/static/chunks/{37fcpc36x9gpe.js → 0eqky-7n7dgdm.js} +1 -1
- package/.next/standalone/.next/static/chunks/{1ide1wl2f7zi1.js → 0sa9v5mhc8861.js} +13 -13
- package/.next/standalone/.next/static/chunks/1mfzsja6ftim5.css +2 -0
- package/.next/standalone/.next/static/chunks/{3k7mxbp9hiom0.js → 1nuqytbta44af.js} +1 -1
- package/.next/standalone/.next/static/chunks/1sl2xmn9inx3y.js +6 -0
- package/.next/standalone/.next/static/chunks/{2_2lhuojq2xop.js → 2aawsjld9ied_.js} +1 -1
- package/.next/standalone/.next/static/chunks/2gn7ut4svofm2.js +1 -0
- package/.next/standalone/.next/static/chunks/{31s1smp-g7gks.js → 2hs7ycvsav7v2.js} +1 -1
- package/.next/standalone/.next/static/chunks/{0k5050ezjvv49.js → 2i2yt3hzjredm.js} +1 -1
- package/.next/standalone/.next/static/chunks/{3c808qrfcq0im.js → 35xg6retpe6rp.js} +1 -1
- package/.next/standalone/.next/static/chunks/{2zpp1we2jv6tb.js → 3y54nw0i7dsjl.js} +1 -1
- package/.next/standalone/SECURITY.md +5 -4
- package/.next/standalone/app/actions/get-hooks-config.ts +108 -17
- package/.next/standalone/app/actions/pack-actions.ts +153 -0
- package/.next/standalone/app/audit/_components/run-progress.tsx +1 -1
- package/.next/standalone/app/audit/_components/share-templates.ts +13 -13
- package/.next/standalone/app/policies/hooks-client.tsx +320 -14
- package/.next/standalone/components/navbar.tsx +2 -28
- package/.next/standalone/components/reach-developers.tsx +8 -1
- package/.next/standalone/docs-old/agenteye/python-sdk-skill.mdx +1 -1
- package/.next/standalone/docs-old/agenteye/python-sdk.mdx +59 -35
- package/.next/standalone/docs-old/i18n/README.ar.md +1 -0
- package/.next/standalone/docs-old/i18n/README.de.md +1 -0
- package/.next/standalone/docs-old/i18n/README.es.md +1 -0
- package/.next/standalone/docs-old/i18n/README.fr.md +1 -0
- package/.next/standalone/docs-old/i18n/README.he.md +1 -0
- package/.next/standalone/docs-old/i18n/README.hi.md +1 -0
- package/.next/standalone/docs-old/i18n/README.it.md +1 -0
- package/.next/standalone/docs-old/i18n/README.ja.md +1 -0
- package/.next/standalone/docs-old/i18n/README.ko.md +1 -0
- package/.next/standalone/docs-old/i18n/README.pt-br.md +1 -0
- package/.next/standalone/docs-old/i18n/README.ru.md +1 -0
- package/.next/standalone/docs-old/i18n/README.tr.md +1 -0
- package/.next/standalone/docs-old/i18n/README.vi.md +1 -0
- package/.next/standalone/docs-old/i18n/README.zh.md +1 -0
- package/.next/standalone/fp-cloud-cli/CHANGELOG.md +431 -0
- package/.next/standalone/fp-cloud-cli/LICENSE +42 -0
- package/.next/standalone/fp-cloud-cli/MANIFEST.in +10 -0
- package/.next/standalone/fp-cloud-cli/README.md +259 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/__init__.py +10 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/__main__.py +4 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/_click_compat.py +64 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/_context.py +332 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/_version.py +1 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/analytics.py +432 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/analytics_config.py +77 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/analytics_registry.py +83 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/app.py +492 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/auth.py +160 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/client.py +1694 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/commands/__init__.py +0 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/commands/_write.py +214 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/commands/agent_cmds.py +407 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/commands/alerts_cmds.py +445 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/commands/audits_cmds.py +1054 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/commands/auth_cmds.py +512 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/commands/errors_cmds.py +190 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/commands/evals_cmds.py +161 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/commands/events_cmds.py +159 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/commands/fleet_cmds.py +416 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/commands/guardrails_cmds.py +148 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/commands/incidents_cmds.py +472 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/commands/keys_cmds.py +407 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/commands/list_cmds.py +63 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/commands/orgs_cmds.py +319 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/commands/policies_cmds.py +499 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/commands/queries_cmds.py +378 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/commands/sessions_cmds.py +151 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/commands/settings_cmds.py +150 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/commands/usage_cmds.py +35 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/commands/users_cmds.py +404 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/config.py +330 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/dates.py +78 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/enforcement.py +345 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/errors.py +98 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/models.py +891 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/orgs.py +30 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/output.py +6593 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/permissions.py +208 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/policy_check.py +290 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/py.typed +0 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/select.py +322 -0
- package/.next/standalone/fp-cloud-cli/fp_cli/theme.py +53 -0
- package/.next/standalone/fp-cloud-cli/pyproject.toml +106 -0
- package/.next/standalone/fp-cloud-cli/skill/SKILL.md +302 -0
- package/.next/standalone/fp-cloud-cli/skill/agents/openai.yaml +8 -0
- package/.next/standalone/fp-cloud-cli/skill/references/commands.md +254 -0
- package/.next/standalone/fp-cloud-cli/tests/__init__.py +0 -0
- package/.next/standalone/fp-cloud-cli/tests/conftest.py +92 -0
- package/.next/standalone/fp-cloud-cli/tests/test_alerting.py +644 -0
- package/.next/standalone/fp-cloud-cli/tests/test_analytics.py +385 -0
- package/.next/standalone/fp-cloud-cli/tests/test_audits.py +950 -0
- package/.next/standalone/fp-cloud-cli/tests/test_auth.py +98 -0
- package/.next/standalone/fp-cloud-cli/tests/test_auth_mode.py +272 -0
- package/.next/standalone/fp-cloud-cli/tests/test_click_compat.py +118 -0
- package/.next/standalone/fp-cloud-cli/tests/test_client.py +299 -0
- package/.next/standalone/fp-cloud-cli/tests/test_commands.py +814 -0
- package/.next/standalone/fp-cloud-cli/tests/test_config.py +99 -0
- package/.next/standalone/fp-cloud-cli/tests/test_dashboards_agent.py +340 -0
- package/.next/standalone/fp-cloud-cli/tests/test_dates.py +76 -0
- package/.next/standalone/fp-cloud-cli/tests/test_enforcement_logic.py +481 -0
- package/.next/standalone/fp-cloud-cli/tests/test_facets.py +170 -0
- package/.next/standalone/fp-cloud-cli/tests/test_failproofai_home.py +722 -0
- package/.next/standalone/fp-cloud-cli/tests/test_fp_home_contract.py +198 -0
- package/.next/standalone/fp-cloud-cli/tests/test_hardening.py +186 -0
- package/.next/standalone/fp-cloud-cli/tests/test_help_table_coverage.py +127 -0
- package/.next/standalone/fp-cloud-cli/tests/test_keys_queries.py +496 -0
- package/.next/standalone/fp-cloud-cli/tests/test_list.py +59 -0
- package/.next/standalone/fp-cloud-cli/tests/test_multivalue.py +183 -0
- package/.next/standalone/fp-cloud-cli/tests/test_no_customer_identifiers.py +168 -0
- package/.next/standalone/fp-cloud-cli/tests/test_operator.py +492 -0
- package/.next/standalone/fp-cloud-cli/tests/test_orgs.py +692 -0
- package/.next/standalone/fp-cloud-cli/tests/test_output.py +1732 -0
- package/.next/standalone/fp-cloud-cli/tests/test_policy_check.py +191 -0
- package/.next/standalone/fp-cloud-cli/tests/test_readme_matches_reality.py +125 -0
- package/.next/standalone/fp-cloud-cli/tests/test_review_fixes.py +161 -0
- package/.next/standalone/fp-cloud-cli/tests/test_telemetry_completeness.py +90 -0
- package/.next/standalone/fp-cloud-cli/tests/test_usage.py +115 -0
- package/.next/standalone/fp-cloud-cli/tests/test_v1_origin_diagnostic.py +70 -0
- package/.next/standalone/fp-cloud-cli/tests/test_v1_routing.py +214 -0
- package/.next/standalone/fp-cloud-cli/tests/test_whoami.py +104 -0
- package/.next/standalone/fp-cloud-cli/uv.lock +552 -0
- package/.next/standalone/package.json +29 -22
- package/.next/standalone/sdk/python/CHANGELOG.md +70 -0
- package/.next/standalone/sdk/python/LICENSE +42 -0
- package/.next/standalone/sdk/python/MANIFEST.in +21 -0
- package/.next/standalone/sdk/python/README.md +466 -0
- package/.next/standalone/sdk/python/docs/README.md +249 -0
- package/.next/standalone/sdk/python/docs/_shared/README.md +43 -0
- package/.next/standalone/sdk/python/docs/_shared/__init__.py +195 -0
- package/.next/standalone/sdk/python/docs/crewai/README.md +328 -0
- package/.next/standalone/sdk/python/docs/crewai/examples/quickstart.py +61 -0
- package/.next/standalone/sdk/python/docs/crewai/examples/research_crew.py +92 -0
- package/.next/standalone/sdk/python/docs/langgraph/README.md +481 -0
- package/.next/standalone/sdk/python/docs/langgraph/examples/quickstart.py +51 -0
- package/.next/standalone/sdk/python/docs/langgraph/examples/research_agent.py +86 -0
- package/.next/standalone/sdk/python/docs/langgraph/examples/supervisor_handoff.py +83 -0
- package/.next/standalone/sdk/python/docs/llama_index/README.md +332 -0
- package/.next/standalone/sdk/python/docs/llama_index/examples/quickstart.py +62 -0
- package/.next/standalone/sdk/python/docs/llama_index/examples/research_agent.py +93 -0
- package/.next/standalone/sdk/python/docs/manual/README.md +491 -0
- package/.next/standalone/sdk/python/docs/manual/examples/quickstart.py +57 -0
- package/.next/standalone/sdk/python/docs/manual/examples/research_agent.py +133 -0
- package/.next/standalone/sdk/python/docs/pydantic_ai/README.md +323 -0
- package/.next/standalone/sdk/python/docs/pydantic_ai/examples/quickstart.py +48 -0
- package/.next/standalone/sdk/python/docs/pydantic_ai/examples/research_agent.py +94 -0
- package/.next/standalone/sdk/python/failproofai_sdk/__init__.py +131 -0
- package/.next/standalone/sdk/python/failproofai_sdk/_context.py +218 -0
- package/.next/standalone/sdk/python/failproofai_sdk/_environment.py +78 -0
- package/.next/standalone/sdk/python/failproofai_sdk/_events.py +752 -0
- package/.next/standalone/sdk/python/failproofai_sdk/_resolver.py +118 -0
- package/.next/standalone/sdk/python/failproofai_sdk/_runtime.py +21 -0
- package/.next/standalone/sdk/python/failproofai_sdk/_schema.py +317 -0
- package/.next/standalone/sdk/python/failproofai_sdk/_scopes.py +422 -0
- package/.next/standalone/sdk/python/failproofai_sdk/_version.py +1 -0
- package/.next/standalone/sdk/python/failproofai_sdk/_writer.py +750 -0
- package/.next/standalone/sdk/python/failproofai_sdk/integrations/__init__.py +274 -0
- package/.next/standalone/sdk/python/failproofai_sdk/integrations/_compat.py +247 -0
- package/.next/standalone/sdk/python/failproofai_sdk/integrations/_core.py +1076 -0
- package/.next/standalone/sdk/python/failproofai_sdk/integrations/crewai.py +1669 -0
- package/.next/standalone/sdk/python/failproofai_sdk/integrations/langchain.py +2151 -0
- package/.next/standalone/sdk/python/failproofai_sdk/integrations/llama_index.py +1588 -0
- package/.next/standalone/sdk/python/failproofai_sdk/integrations/pydantic_ai.py +977 -0
- package/.next/standalone/sdk/python/failproofai_sdk/py.typed +0 -0
- package/.next/standalone/sdk/python/pyproject.toml +92 -0
- package/.next/standalone/sdk/python/skill/SKILL.md +399 -0
- package/.next/standalone/sdk/python/skill/agents/openai.yaml +8 -0
- package/.next/standalone/sdk/python/skill/references/events.md +234 -0
- package/.next/standalone/sdk/python/skill/references/frameworks.md +314 -0
- package/.next/standalone/sdk/python/skill/references/install.md +100 -0
- package/.next/standalone/sdk/python/skill/references/integration.md +352 -0
- package/.next/standalone/sdk/python/tests/__init__.py +0 -0
- package/.next/standalone/sdk/python/tests/conftest.py +169 -0
- package/.next/standalone/sdk/python/tests/integrations/__init__.py +6 -0
- package/.next/standalone/sdk/python/tests/integrations/test_crewai.py +1299 -0
- package/.next/standalone/sdk/python/tests/integrations/test_langchain.py +2338 -0
- package/.next/standalone/sdk/python/tests/integrations/test_llama_index.py +1576 -0
- package/.next/standalone/sdk/python/tests/integrations/test_pydantic_ai.py +1102 -0
- package/.next/standalone/sdk/python/tests/test_context.py +410 -0
- package/.next/standalone/sdk/python/tests/test_docs.py +411 -0
- package/.next/standalone/sdk/python/tests/test_durability.py +1352 -0
- package/.next/standalone/sdk/python/tests/test_encoding.py +571 -0
- package/.next/standalone/sdk/python/tests/test_integrations.py +1127 -0
- package/.next/standalone/sdk/python/tests/test_no_customer_identifiers.py +214 -0
- package/.next/standalone/sdk/python/tests/test_packaging.py +185 -0
- package/.next/standalone/sdk/python/tests/test_resolver_umbrella.py +178 -0
- package/.next/standalone/sdk/python/tests/test_scopes.py +487 -0
- package/.next/standalone/sdk/python/tests/test_sdk.py +923 -0
- package/.next/standalone/sdk/python/tests/test_server_contract.py +650 -0
- package/.next/standalone/sdk/python/tests/test_site_docs.py +371 -0
- package/.next/standalone/sdk/python/tests/test_skill_snippets.py +165 -0
- package/.next/standalone/sdk/python/tests/test_spool_contract.py +287 -0
- package/.next/standalone/sdk/python/tests/test_spool_creation.py +360 -0
- package/.next/standalone/sdk/python/tests/test_wire_format.py +279 -0
- package/.next/standalone/sdk/python/tests/test_zero_dependencies.py +378 -0
- package/.next/standalone/sdk/python/uv.lock +6005 -0
- package/.next/standalone/server.js +1 -1
- package/README.md +77 -21
- package/bin/failproofai.mjs +145 -11
- package/dist/cli.mjs +4482 -2205
- package/dist/index.js +5 -5
- package/dist/worker.mjs +2399 -1978
- package/package.json +29 -22
- package/policy-pack/SHA256SUMS +2 -0
- package/policy-pack/failproofai-pack.json +732 -0
- package/policy-pack/failproofai-pack.mjs +2017 -0
- package/scripts/build-policy-pack.mjs +121 -0
- package/scripts/changelog-section.py +77 -0
- package/scripts/prune-standalone.mjs +3 -0
- package/scripts/python-version.py +232 -0
- package/scripts/translate-docs/cli.ts +21 -0
- package/scripts/translate-docs/mintlify-nav.ts +85 -13
- package/scripts/translate-docs/translator.ts +66 -11
- package/src/audit/cache.ts +40 -3
- package/src/audit/cli.ts +1 -1
- package/src/audit/index.ts +1 -1
- package/src/audit/replay.ts +89 -3
- package/src/audit/report.ts +5 -5
- package/src/audit/schedule-cli.ts +49 -53
- package/src/hooks/builtin-policies.ts +217 -579
- package/src/hooks/cloud-enrollment-cli.ts +66 -27
- package/src/hooks/cloud-managed-policies.ts +6 -1
- package/src/hooks/configure-wizard.ts +1 -1
- package/src/hooks/custom-hooks-loader.ts +89 -6
- package/src/hooks/fp-home.ts +92 -4
- package/src/hooks/fp-reset.ts +26 -2
- package/src/hooks/handler.ts +181 -11
- package/src/hooks/harness-cli.ts +79 -25
- package/src/hooks/hook-activity-store.ts +13 -3
- package/src/hooks/install-prompt.ts +25 -3
- package/src/hooks/manager.ts +418 -172
- package/src/hooks/migrations.ts +2 -2
- package/src/hooks/pack-cli.ts +505 -0
- package/src/hooks/pack-failclosed.ts +189 -0
- package/src/hooks/pack-manifest.ts +344 -0
- package/src/hooks/pack-store.ts +930 -0
- package/src/hooks/policy-catalog.ts +535 -0
- package/src/hooks/policy-evaluator.ts +24 -16
- package/src/hooks/policy-presets.ts +4 -2
- package/src/hooks/policy-registry.ts +8 -2
- package/src/hooks/policy-types.ts +26 -0
- package/src/hooks/session-pause-cli.ts +33 -9
- package/src/hooks/tui.ts +570 -0
- package/src/hooks/types.ts +15 -1
- package/.next/standalone/.next/server/chunks/[root-of-the-server]__0_usx0j._.js +0 -3
- package/.next/standalone/.next/server/chunks/[root-of-the-server]__0_zk340._.js +0 -3
- package/.next/standalone/.next/server/chunks/[root-of-the-server]__0agdw2a._.js +0 -3
- package/.next/standalone/.next/server/chunks/[root-of-the-server]__0d1u_na._.js +0 -3
- package/.next/standalone/.next/server/chunks/[root-of-the-server]__0oy4kxb._.js +0 -3
- package/.next/standalone/.next/server/chunks/[root-of-the-server]__0zf034w._.js +0 -3
- package/.next/standalone/.next/server/chunks/[root-of-the-server]__1tvn4wf._.js +0 -3
- package/.next/standalone/.next/server/chunks/_0lxbzdq._.js +0 -3
- package/.next/standalone/.next/server/chunks/_1ger0a2._.js +0 -3
- package/.next/standalone/.next/server/chunks/_1zuiiy3._.js +0 -3
- package/.next/standalone/.next/server/chunks/node_modules_posthog-node_dist_entrypoints_index_node_mjs_1iiwm5e._.js +0 -3
- package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0kc8_v5._.js +0 -4
- package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0kgy9da._.js +0 -4
- package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0mhqk5a._.js +0 -4
- package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0pltpn8._.js +0 -4
- package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0qkcyf-._.js +0 -4
- package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__0w0x_ok._.js +0 -4
- package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__1_dfocn._.js +0 -4
- package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__1bfex62._.js +0 -5
- package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__1kzapg5._.js +0 -6
- package/.next/standalone/.next/static/chunks/36fw6yk1s6x_f.js +0 -1
- package/.next/standalone/.next/static/chunks/3tzq0260n17ae.js +0 -6
- package/.next/standalone/.next/static/chunks/3wq9x0c-7ld5d.css +0 -2
- /package/.next/standalone/.next/static/{ZklXxyA5ygsWSQz2u_zii → nwbyWT06Ud0XdXOrVJyvS}/_buildManifest.js +0 -0
- /package/.next/standalone/.next/static/{ZklXxyA5ygsWSQz2u_zii → nwbyWT06Ud0XdXOrVJyvS}/_clientMiddlewareManifest.js +0 -0
- /package/.next/standalone/.next/static/{ZklXxyA5ygsWSQz2u_zii → nwbyWT06Ud0XdXOrVJyvS}/_ssgManifest.js +0 -0
|
@@ -0,0 +1,332 @@
|
|
|
1
|
+
# LlamaIndex
|
|
2
|
+
|
|
3
|
+
- [Install](#install)
|
|
4
|
+
- [The integration](#the-integration)
|
|
5
|
+
- [Read this first: token counts](#read-this-first-token-counts)
|
|
6
|
+
- [How it attaches](#how-it-attaches)
|
|
7
|
+
- [What gets recorded](#what-gets-recorded)
|
|
8
|
+
- [A complete example](#a-complete-example)
|
|
9
|
+
- [Options](#options)
|
|
10
|
+
- [Human in the loop](#human-in-the-loop)
|
|
11
|
+
- [Pitfalls](#pitfalls)
|
|
12
|
+
- [Runnable examples](#runnable-examples)
|
|
13
|
+
|
|
14
|
+
---
|
|
15
|
+
|
|
16
|
+
## Install
|
|
17
|
+
|
|
18
|
+
```bash
|
|
19
|
+
pip install 'failproofai-sdk[llamaindex]' # pins llama-index-core >=0.14.23,<0.15
|
|
20
|
+
```
|
|
21
|
+
|
|
22
|
+
**Supported:** `llama-index-core` 0.14.23 → 0.15. 0.14.23 is a capability floor:
|
|
23
|
+
it is the release where `to_payload()` replaced `to_dict()` and where the
|
|
24
|
+
workflow stream started carrying the typed agent events this adapter reads.
|
|
25
|
+
Below it, model names and agent structure both go missing.
|
|
26
|
+
|
|
27
|
+
---
|
|
28
|
+
|
|
29
|
+
## The integration
|
|
30
|
+
|
|
31
|
+
```python
|
|
32
|
+
import asyncio
|
|
33
|
+
import failproofai_sdk
|
|
34
|
+
|
|
35
|
+
failproofai_sdk.configure(environment="production")
|
|
36
|
+
failproofai_sdk.instrument()
|
|
37
|
+
|
|
38
|
+
async def main():
|
|
39
|
+
async with failproofai_sdk.session():
|
|
40
|
+
await agent.run("...")
|
|
41
|
+
|
|
42
|
+
asyncio.run(main())
|
|
43
|
+
```
|
|
44
|
+
|
|
45
|
+
LlamaIndex's agent API is async. Every Failproof scope works under `async with`
|
|
46
|
+
as well as `with`, and produces byte-identical events either way.
|
|
47
|
+
|
|
48
|
+
---
|
|
49
|
+
|
|
50
|
+
## Read this first: token counts
|
|
51
|
+
|
|
52
|
+
**Without one extra argument, every token count in your trace will be null.**
|
|
53
|
+
|
|
54
|
+
`FunctionAgent` — the agent API LlamaIndex documents — calls `astream_chat`. And
|
|
55
|
+
`llama-index-llms-openai` does not send `stream_options={"include_usage": True}`
|
|
56
|
+
when it streams, so **the provider never sends the usage chunk at all**.
|
|
57
|
+
`LLMChatEndEvent.response.raw` arrives with no `usage` key on it, and there is
|
|
58
|
+
nothing for any instrumentation to read.
|
|
59
|
+
|
|
60
|
+
This is upstream LlamaIndex behaviour, not a Failproof one. Verified by spying
|
|
61
|
+
on the dispatcher directly against `llama-index-core` 0.14.23: every single
|
|
62
|
+
`LLMChatEndEvent` in a `FunctionAgent` run has usage absent.
|
|
63
|
+
|
|
64
|
+
**The fix is one argument on your LLM:**
|
|
65
|
+
|
|
66
|
+
```python
|
|
67
|
+
from llama_index.llms.openai import OpenAI
|
|
68
|
+
|
|
69
|
+
llm = OpenAI(
|
|
70
|
+
model="gpt-4o-mini",
|
|
71
|
+
additional_kwargs={"stream_options": {"include_usage": True}},
|
|
72
|
+
)
|
|
73
|
+
```
|
|
74
|
+
|
|
75
|
+
Measured on the same run, same model:
|
|
76
|
+
|
|
77
|
+
| | `input_tokens` | `output_tokens` |
|
|
78
|
+
|---|---|---|
|
|
79
|
+
| without | `None` | `None` |
|
|
80
|
+
| with | `148` | `17` |
|
|
81
|
+
|
|
82
|
+
Non-streaming calls (`llm.chat`, `llm.achat`) extract usage correctly with no
|
|
83
|
+
configuration at all. It is only the streaming path — which is the default agent
|
|
84
|
+
path — that needs this.
|
|
85
|
+
|
|
86
|
+
---
|
|
87
|
+
|
|
88
|
+
## How it attaches
|
|
89
|
+
|
|
90
|
+
Two handlers on LlamaIndex's global dispatcher:
|
|
91
|
+
|
|
92
|
+
- an **event handler** for the typed workflow and LLM events, and
|
|
93
|
+
- a **span handler** for the enter/exit spans around workflows, steps and tools.
|
|
94
|
+
|
|
95
|
+
Both together are what makes the agent *loop* visible, not just its model calls.
|
|
96
|
+
This is the main thing this adapter buys you over a model-only integration: you
|
|
97
|
+
can see `parse_agent_output` taking 160ms, or `aggregate_tool_results` running
|
|
98
|
+
twice.
|
|
99
|
+
|
|
100
|
+
---
|
|
101
|
+
|
|
102
|
+
## What gets recorded
|
|
103
|
+
|
|
104
|
+
| LlamaIndex | Failproof event | When |
|
|
105
|
+
|---|---|---|
|
|
106
|
+
| `Workflow.run` root span | session + `agent_start` / `agent_end` | the outermost run |
|
|
107
|
+
| nested `Workflow.run` span | nested `agent_start` / `agent_end` | a sub-workflow |
|
|
108
|
+
| workflow step span | `hook_triggered` / `hook_completed` | each step in the agent loop |
|
|
109
|
+
| `LLMChatStartEvent` / `EndEvent` | `model_request` / `model_response` | each model call |
|
|
110
|
+
| `FunctionTool.call` span | `tool_use` / `tool_result` | each tool call |
|
|
111
|
+
| `RetrievalStartEvent` / `EndEvent` | `tool_use` / `tool_result` | output summarised, not dumped |
|
|
112
|
+
| embeddings | *nothing* | unless `embeddings=True` |
|
|
113
|
+
| `WaitingForEvent` drop | `human_wait` + `agent_pause` | a tool waits on a person |
|
|
114
|
+
| exception | `error` + `agent_end(outcome="failed")` | the run raises |
|
|
115
|
+
|
|
116
|
+
`agent_id` is the `FunctionAgent.name` when you set one, and the workflow class
|
|
117
|
+
name otherwise — never a span id.
|
|
118
|
+
|
|
119
|
+
```python
|
|
120
|
+
FunctionAgent(name="city_analyst", tools=[...], llm=llm) # agent_id = "city_analyst"
|
|
121
|
+
```
|
|
122
|
+
|
|
123
|
+
### Why retrieval output is summarised
|
|
124
|
+
|
|
125
|
+
A retriever returns documents. Dumping them into the payload puts your entire
|
|
126
|
+
corpus in the events store, one copy per query. The adapter records the count,
|
|
127
|
+
the score range and truncated snippets instead. If you need the documents
|
|
128
|
+
themselves, they are in your index.
|
|
129
|
+
|
|
130
|
+
### Why steps are hooks and not agents
|
|
131
|
+
|
|
132
|
+
`init_run`, `setup_agent`, `run_agent_step`, `parse_agent_output`, `call_tool`
|
|
133
|
+
and `aggregate_tool_results` are the framework's own loop, not units of work you
|
|
134
|
+
wrote. They are hook pairs so `agent_id` stays a meaningful facet instead of
|
|
135
|
+
filling up with machinery.
|
|
136
|
+
|
|
137
|
+
---
|
|
138
|
+
|
|
139
|
+
## A complete example
|
|
140
|
+
|
|
141
|
+
```python
|
|
142
|
+
import asyncio
|
|
143
|
+
|
|
144
|
+
import failproofai_sdk
|
|
145
|
+
from llama_index.core.agent.workflow import FunctionAgent
|
|
146
|
+
from llama_index.core.tools import FunctionTool
|
|
147
|
+
from llama_index.llms.openai import OpenAI
|
|
148
|
+
|
|
149
|
+
failproofai_sdk.configure(environment="production")
|
|
150
|
+
failproofai_sdk.instrument()
|
|
151
|
+
|
|
152
|
+
POP = {"tokyo": "37M", "delhi": "33M", "lagos": "16M"}
|
|
153
|
+
AREA = {"tokyo": "2,194 km2", "delhi": "1,484 km2", "lagos": "1,171 km2"}
|
|
154
|
+
|
|
155
|
+
|
|
156
|
+
def population(city: str) -> str:
|
|
157
|
+
"""Population of a city. Valid: tokyo, delhi, lagos."""
|
|
158
|
+
return POP.get(city.lower().strip(), "unknown")
|
|
159
|
+
|
|
160
|
+
|
|
161
|
+
def area(city: str) -> str:
|
|
162
|
+
"""Land area of a city. Valid: tokyo, delhi, lagos."""
|
|
163
|
+
return AREA.get(city.lower().strip(), "unknown")
|
|
164
|
+
|
|
165
|
+
|
|
166
|
+
async def main():
|
|
167
|
+
agent = FunctionAgent(
|
|
168
|
+
name="city_analyst",
|
|
169
|
+
tools=[
|
|
170
|
+
FunctionTool.from_defaults(fn=population),
|
|
171
|
+
FunctionTool.from_defaults(fn=area),
|
|
172
|
+
],
|
|
173
|
+
llm=OpenAI(
|
|
174
|
+
model="gpt-4o-mini",
|
|
175
|
+
# REQUIRED for token counts on the streaming agent path.
|
|
176
|
+
additional_kwargs={"stream_options": {"include_usage": True}},
|
|
177
|
+
),
|
|
178
|
+
system_prompt="Use the tools. Be terse.",
|
|
179
|
+
)
|
|
180
|
+
|
|
181
|
+
async with failproofai_sdk.session():
|
|
182
|
+
async with failproofai_sdk.agent("city_analyst", goal="compare two cities"):
|
|
183
|
+
answer = await agent.run("Compare Tokyo and Delhi on population and area.")
|
|
184
|
+
|
|
185
|
+
print(answer)
|
|
186
|
+
|
|
187
|
+
|
|
188
|
+
asyncio.run(main())
|
|
189
|
+
```
|
|
190
|
+
|
|
191
|
+
The quickstart version of this produces **26 events across 8 types**, and the
|
|
192
|
+
agent loop is fully visible:
|
|
193
|
+
|
|
194
|
+
```
|
|
195
|
+
1 +0.000s agent_start Agent
|
|
196
|
+
2 +0.001s hook_triggered init_run
|
|
197
|
+
4 +0.548s hook_triggered setup_agent
|
|
198
|
+
6 +0.549s hook_triggered run_agent_step
|
|
199
|
+
7 +0.551s model_request gpt-5.6-terra
|
|
200
|
+
8 +3.546s model_response gpt-5.6-terra
|
|
201
|
+
10 +3.662s hook_triggered parse_agent_output
|
|
202
|
+
12 +3.825s hook_triggered call_tool
|
|
203
|
+
13 +3.825s tool_use city_population
|
|
204
|
+
14 +3.826s tool_result city_population · ok
|
|
205
|
+
16 +3.826s hook_triggered aggregate_tool_results
|
|
206
|
+
...
|
|
207
|
+
26 +6.968s agent_end Agent · success
|
|
208
|
+
```
|
|
209
|
+
|
|
210
|
+
---
|
|
211
|
+
|
|
212
|
+
## Options
|
|
213
|
+
|
|
214
|
+
```python
|
|
215
|
+
failproofai_sdk.instrument(
|
|
216
|
+
"llama_index",
|
|
217
|
+
embeddings=False, # True records embedding calls as tool pairs
|
|
218
|
+
steps=True, # False drops workflow-step hook pairs
|
|
219
|
+
capture_messages=True, # False drops prompts and system text from payloads
|
|
220
|
+
stale_after=600.0, # seconds before an abandoned span is force-closed
|
|
221
|
+
reaper_interval=30.0, # how often the reaper sweeps; 0 disables it
|
|
222
|
+
)
|
|
223
|
+
```
|
|
224
|
+
|
|
225
|
+
| Option | Why you would change it |
|
|
226
|
+
|---|---|
|
|
227
|
+
| `embeddings` | Off by default: a bulk index build is thousands of calls and buries the timeline. On for debugging embedding latency or cost. |
|
|
228
|
+
| `steps` | Off if you want only model and tool events and find the agent loop noisy. |
|
|
229
|
+
| `capture_messages` | Off for regulated data. Structure, timings, tokens and outcomes are still recorded. |
|
|
230
|
+
| `stale_after` | A workflow that never finishes leaves an open span. The reaper force-closes it after this many seconds, so the session settles instead of reading `ongoing` forever. |
|
|
231
|
+
| `reaper_interval` | Sweep frequency. `0` disables the reaper. |
|
|
232
|
+
|
|
233
|
+
**There is no `session_id` option on this adapter, and no `capture_content`.**
|
|
234
|
+
Set the session with a scope, and use `capture_messages` for content:
|
|
235
|
+
|
|
236
|
+
```python
|
|
237
|
+
async with failproofai_sdk.session(f"chat-{user_id}"):
|
|
238
|
+
await agent.run(...)
|
|
239
|
+
```
|
|
240
|
+
|
|
241
|
+
---
|
|
242
|
+
|
|
243
|
+
## Human in the loop
|
|
244
|
+
|
|
245
|
+
Only visible when the wait happens **inside a tool**.
|
|
246
|
+
|
|
247
|
+
```python
|
|
248
|
+
async def ask_human(question: str) -> str:
|
|
249
|
+
"""Ask a person and wait for their answer."""
|
|
250
|
+
ctx = ... # your workflow context
|
|
251
|
+
response = await ctx.wait_for_event(HumanResponseEvent)
|
|
252
|
+
return response.answer
|
|
253
|
+
```
|
|
254
|
+
|
|
255
|
+
That produces `human_wait` + `agent_pause`, then `agent_resume` +
|
|
256
|
+
`human_input` on the retry.
|
|
257
|
+
|
|
258
|
+
`ctx.wait_for_event` in a **plain workflow step** is not captured. The runtime
|
|
259
|
+
catches the drop before it reaches the dispatcher: the step simply exits with
|
|
260
|
+
`None` and re-runs later, so there is no signal to key a pause on. The
|
|
261
|
+
FunctionAgent pattern — which is the one LlamaIndex documents — waits inside a
|
|
262
|
+
tool and is captured in full.
|
|
263
|
+
|
|
264
|
+
---
|
|
265
|
+
|
|
266
|
+
## Pitfalls
|
|
267
|
+
|
|
268
|
+
### Every token count is null
|
|
269
|
+
|
|
270
|
+
See [Read this first](#read-this-first-token-counts). One argument on your LLM.
|
|
271
|
+
|
|
272
|
+
---
|
|
273
|
+
|
|
274
|
+
### Token counts are null on a non-OpenAI integration
|
|
275
|
+
|
|
276
|
+
**Symptom:** `usage` is populated in the payload but `input_tokens` /
|
|
277
|
+
`output_tokens` are `None`.
|
|
278
|
+
|
|
279
|
+
**Cause:** there is no standard usage field in LlamaIndex. The adapter tries
|
|
280
|
+
`response.raw["usage"]`, then `raw["usage_metadata"]`, then
|
|
281
|
+
`response.additional_kwargs`, calling `model_dump()` first when `raw` is a
|
|
282
|
+
pydantic model. An integration that names its counters something new will not
|
|
283
|
+
match.
|
|
284
|
+
|
|
285
|
+
**Why it behaves this way:** the top-level token fields are set **only** when a
|
|
286
|
+
recognised key is present, but the raw dict always ships as `usage` regardless.
|
|
287
|
+
A populated `usage` with blank token columns is the honest outcome, and much
|
|
288
|
+
better than a confident wrong number. Look at `usage` in the payload to see what
|
|
289
|
+
your provider actually called them, and open an issue with that key name.
|
|
290
|
+
|
|
291
|
+
---
|
|
292
|
+
|
|
293
|
+
### The timeline is buried in `init_run` / `setup_agent` noise
|
|
294
|
+
|
|
295
|
+
**Symptom:** far more hook pairs than you expected.
|
|
296
|
+
|
|
297
|
+
**Cause:** that is the FunctionAgent loop. Every iteration is
|
|
298
|
+
`setup_agent` → `run_agent_step` → `parse_agent_output` →
|
|
299
|
+
`call_tool` → `aggregate_tool_results`.
|
|
300
|
+
|
|
301
|
+
**Fix:** nothing is wrong, but you can filter by `hook_name` on the dashboard.
|
|
302
|
+
The step timings are usually the reason people install this adapter rather than
|
|
303
|
+
a model-only one.
|
|
304
|
+
|
|
305
|
+
---
|
|
306
|
+
|
|
307
|
+
### Nothing is recorded at all
|
|
308
|
+
|
|
309
|
+
1. Did `instrument()` run before you constructed the agent? (For LlamaIndex the
|
|
310
|
+
order does not matter, unlike Pydantic AI — but check anyway.)
|
|
311
|
+
2. Is there an `async with failproofai_sdk.session():` around the `await`?
|
|
312
|
+
3. Set `FAILPROOFAI_SDK_STRICT=1` and run again.
|
|
313
|
+
4. Check `llama-index-core >= 0.14.23`.
|
|
314
|
+
|
|
315
|
+
---
|
|
316
|
+
|
|
317
|
+
## Runnable examples
|
|
318
|
+
|
|
319
|
+
| file | what it shows | events |
|
|
320
|
+
|---|---|---|
|
|
321
|
+
| [`examples/quickstart.py`](examples/quickstart.py) | one tool, one turn, async | 26 |
|
|
322
|
+
| [`examples/research_agent.py`](examples/research_agent.py) | 3 tools, several turns, one tool that fails | 64 |
|
|
323
|
+
|
|
324
|
+
```bash
|
|
325
|
+
export OPENAI_API_KEY=sk-...
|
|
326
|
+
export OPENAI_API_BASE=... # note: llama_index reads API_BASE, not BASE_URL
|
|
327
|
+
export FPAI_MODEL=gpt-4o-mini
|
|
328
|
+
python docs/llama_index/examples/quickstart.py
|
|
329
|
+
```
|
|
330
|
+
|
|
331
|
+
Both were run against a live model before shipping. Both set `stream_options`,
|
|
332
|
+
so both report real token counts.
|
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
"""llama_index — the smallest thing that produces a trace.
|
|
2
|
+
|
|
3
|
+
pip install 'failproofai-sdk[llamaindex]'
|
|
4
|
+
python docs/llama_index/examples/quickstart.py
|
|
5
|
+
|
|
6
|
+
`instrument()` attaches an event handler and a span handler to llama_index's
|
|
7
|
+
global dispatcher, so workflow steps arrive as hook pairs and llm calls as
|
|
8
|
+
`model_request`/`model_response`.
|
|
9
|
+
|
|
10
|
+
The scopes work under `async with` as well as `with`, which matters here because
|
|
11
|
+
llama_index's agent api is async.
|
|
12
|
+
"""
|
|
13
|
+
import asyncio
|
|
14
|
+
import sys
|
|
15
|
+
from pathlib import Path
|
|
16
|
+
|
|
17
|
+
# Only so this file can import the shared trace printer from docs/_shared/.
|
|
18
|
+
# Delete these two lines and the `_shared` import below and the example still
|
|
19
|
+
# instruments correctly — it just stops printing its own trace at the end.
|
|
20
|
+
sys.path.insert(0, str(Path(__file__).resolve().parents[2]))
|
|
21
|
+
|
|
22
|
+
import failproofai_sdk
|
|
23
|
+
from _shared import banner, model, trace
|
|
24
|
+
from llama_index.core.agent.workflow import FunctionAgent
|
|
25
|
+
from llama_index.core.tools import FunctionTool
|
|
26
|
+
from llama_index.llms.openai import OpenAI
|
|
27
|
+
|
|
28
|
+
failproofai_sdk.configure(environment="examples")
|
|
29
|
+
failproofai_sdk.instrument()
|
|
30
|
+
|
|
31
|
+
|
|
32
|
+
def city_population(city: str) -> str:
|
|
33
|
+
"""Population of a city."""
|
|
34
|
+
return {"tokyo": "37M", "delhi": "33M"}.get(city.lower(), "unknown")
|
|
35
|
+
|
|
36
|
+
|
|
37
|
+
async def main() -> None:
|
|
38
|
+
banner("llama_index quickstart", "one tool, one turn, async")
|
|
39
|
+
|
|
40
|
+
agent = FunctionAgent(
|
|
41
|
+
tools=[FunctionTool.from_defaults(fn=city_population)],
|
|
42
|
+
llm=OpenAI(
|
|
43
|
+
model=model(),
|
|
44
|
+
# WITHOUT THIS, EVERY TOKEN COUNT IS NULL.
|
|
45
|
+
# FunctionAgent calls `astream_chat`, and llama_index does not ask
|
|
46
|
+
# OpenAI for usage on a stream — so `LLMChatEndEvent` carries a
|
|
47
|
+
# response with no usage on it and there is nothing for any
|
|
48
|
+
# instrumentation to read. This is upstream behaviour, not a
|
|
49
|
+
# failproof one; the line below is the documented way back.
|
|
50
|
+
additional_kwargs={"stream_options": {"include_usage": True}},
|
|
51
|
+
),
|
|
52
|
+
system_prompt="Answer using the tool. Be terse.",
|
|
53
|
+
)
|
|
54
|
+
async with failproofai_sdk.session() as sid:
|
|
55
|
+
answer = await agent.run("What is the population of Tokyo?")
|
|
56
|
+
|
|
57
|
+
print(" answer:", str(answer).strip()[:120])
|
|
58
|
+
trace(sid, title="llama_index quickstart")
|
|
59
|
+
|
|
60
|
+
|
|
61
|
+
if __name__ == "__main__":
|
|
62
|
+
asyncio.run(main())
|
|
@@ -0,0 +1,93 @@
|
|
|
1
|
+
"""llama_index — a multi-tool async agent, including a tool that fails.
|
|
2
|
+
|
|
3
|
+
pip install 'failproofai-sdk[llamaindex]'
|
|
4
|
+
python docs/llama_index/examples/research_agent.py
|
|
5
|
+
|
|
6
|
+
What this demonstrates that the quickstart does not:
|
|
7
|
+
|
|
8
|
+
* three tools across several turns, each a `tool_use`/`tool_result` pair;
|
|
9
|
+
* a tool that raises, recorded as `tool_result` with `error` set while the run
|
|
10
|
+
continues;
|
|
11
|
+
* llama_index workflow steps as `hook_triggered`/`hook_completed`, so you can
|
|
12
|
+
see the agent loop itself and not just its llm calls;
|
|
13
|
+
* a named `agent()` scope wrapping an async run — the scopes support
|
|
14
|
+
`async with`, so nothing about identity changes when the framework does.
|
|
15
|
+
"""
|
|
16
|
+
import asyncio
|
|
17
|
+
import sys
|
|
18
|
+
from pathlib import Path
|
|
19
|
+
|
|
20
|
+
# Only so this file can import the shared trace printer from docs/_shared/.
|
|
21
|
+
# Delete these two lines and the `_shared` import below and the example still
|
|
22
|
+
# instruments correctly — it just stops printing its own trace at the end.
|
|
23
|
+
sys.path.insert(0, str(Path(__file__).resolve().parents[2]))
|
|
24
|
+
|
|
25
|
+
import failproofai_sdk
|
|
26
|
+
from _shared import banner, model, trace
|
|
27
|
+
from llama_index.core.agent.workflow import FunctionAgent
|
|
28
|
+
from llama_index.core.tools import FunctionTool
|
|
29
|
+
from llama_index.llms.openai import OpenAI
|
|
30
|
+
|
|
31
|
+
failproofai_sdk.configure(environment="examples")
|
|
32
|
+
failproofai_sdk.instrument()
|
|
33
|
+
|
|
34
|
+
_POP = {"tokyo": "37M", "delhi": "33M", "lagos": "16M"}
|
|
35
|
+
_AREA = {"tokyo": "2,194 km2", "delhi": "1,484 km2", "lagos": "1,171 km2"}
|
|
36
|
+
|
|
37
|
+
|
|
38
|
+
def population(city: str) -> str:
|
|
39
|
+
"""Population of a city. Valid: tokyo, delhi, lagos."""
|
|
40
|
+
return _POP.get(city.lower().strip(), "unknown")
|
|
41
|
+
|
|
42
|
+
|
|
43
|
+
def area(city: str) -> str:
|
|
44
|
+
"""Land area of a city. Valid: tokyo, delhi, lagos."""
|
|
45
|
+
return _AREA.get(city.lower().strip(), "unknown")
|
|
46
|
+
|
|
47
|
+
|
|
48
|
+
def founding_year(city: str) -> str:
|
|
49
|
+
"""Founding year of a city. Not actually available for any of them."""
|
|
50
|
+
# Deliberately raises: the trace should show a failed tool and the agent
|
|
51
|
+
# carrying on without it.
|
|
52
|
+
raise LookupError(f"no founding-year record for {city!r}")
|
|
53
|
+
|
|
54
|
+
|
|
55
|
+
async def main() -> None:
|
|
56
|
+
banner("llama_index research agent", "3 tools · multi-turn · one failing call")
|
|
57
|
+
|
|
58
|
+
agent = FunctionAgent(
|
|
59
|
+
tools=[
|
|
60
|
+
FunctionTool.from_defaults(fn=population),
|
|
61
|
+
FunctionTool.from_defaults(fn=area),
|
|
62
|
+
FunctionTool.from_defaults(fn=founding_year),
|
|
63
|
+
],
|
|
64
|
+
llm=OpenAI(
|
|
65
|
+
model=model(),
|
|
66
|
+
# WITHOUT THIS, EVERY TOKEN COUNT IS NULL.
|
|
67
|
+
# FunctionAgent calls `astream_chat`, and llama_index does not ask
|
|
68
|
+
# OpenAI for usage on a stream — so `LLMChatEndEvent` carries a
|
|
69
|
+
# response with no usage on it and there is nothing for any
|
|
70
|
+
# instrumentation to read. This is upstream behaviour, not a
|
|
71
|
+
# failproof one; the line below is the documented way back.
|
|
72
|
+
additional_kwargs={"stream_options": {"include_usage": True}},
|
|
73
|
+
),
|
|
74
|
+
system_prompt=(
|
|
75
|
+
"Use the tools. If a tool fails, say so and continue with what you have."
|
|
76
|
+
),
|
|
77
|
+
)
|
|
78
|
+
|
|
79
|
+
question = (
|
|
80
|
+
"Compare Tokyo and Delhi on population and area, then try to get the "
|
|
81
|
+
"founding year for each. Finish with a two-line comparison."
|
|
82
|
+
)
|
|
83
|
+
|
|
84
|
+
async with failproofai_sdk.session() as sid:
|
|
85
|
+
async with failproofai_sdk.agent("city_analyst", goal="compare two cities"):
|
|
86
|
+
answer = await agent.run(question)
|
|
87
|
+
|
|
88
|
+
print(" answer:", str(answer).strip()[:220], "\n")
|
|
89
|
+
trace(sid, title="llama_index research agent")
|
|
90
|
+
|
|
91
|
+
|
|
92
|
+
if __name__ == "__main__":
|
|
93
|
+
asyncio.run(main())
|