Metadata-Version: 2.4
Name: frootai
Version: 5.1.2
Summary: FrootAI SDK — 102 solution plays, 940+ primitives, and a 62-tool Python MCP companion. Offline knowledge, BM25 search, FAI Protocol wiring, scaffold, evaluation, A/B testing, and CLI.
Author-email: Pavleen Bali <pavleenbali@frootai.dev>
License: MIT
Project-URL: Homepage, https://frootai.dev
Project-URL: Repository, https://github.com/frootai/frootai
Project-URL: Documentation, https://frootai.dev/api-docs
Keywords: frootai,ai,architecture,azure,mcp,agents,rag,sdk
Classifier: Development Status :: 4 - Beta
Classifier: Intended Audience :: Developers
Classifier: License :: OSI Approved :: MIT License
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3.10
Classifier: Programming Language :: Python :: 3.11
Classifier: Programming Language :: Python :: 3.12
Classifier: Programming Language :: Python :: 3.13
Classifier: Topic :: Software Development :: Libraries
Classifier: Topic :: Scientific/Engineering :: Artificial Intelligence
Requires-Python: >=3.10
Description-Content-Type: text/markdown

<p align="center"><img src="https://frootai.dev/img/frootai-mark.png" width="88" alt="FrootAI mark"></p>
<h1 align="center">FrootAI Python SDK</h1>
<p align="center"><strong>Direct Python APIs for FrootAI knowledge, Solution Plays, FAI Protocol wiring, evaluation, and trusted federation.</strong></p>
<p align="center">
  <a href="https://pypi.org/project/frootai/"><img src="https://img.shields.io/pypi/v/frootai?style=flat-square&logo=python" alt="PyPI version"></a>
  <a href="https://pypi.org/project/frootai/"><img src="https://img.shields.io/pypi/dm/frootai?style=flat-square&label=downloads" alt="PyPI downloads"></a>
  <a href="https://www.python.org"><img src="https://img.shields.io/pypi/pyversions/frootai?style=flat-square" alt="Python versions"></a>
  <a href="https://opensource.org/license/mit"><img src="https://img.shields.io/badge/license-MIT-f2c94c?style=flat-square" alt="MIT license"></a>
</p>
<p align="center"><a href="https://frootai.dev/python">Python product page</a> · <a href="https://frootai.dev/setup-guide#python">Setup guide</a> · <a href="https://pypi.org/project/frootai/">PyPI</a> · <a href="https://frootai.dev/api-docs">API docs</a></p>

![Choose between the FrootAI Python SDK and Python MCP](https://frootai.dev/images/package-readmes/python-mcp.png)

## Choose SDK or Python MCP

| Use | Choose |
|---|---|
| Application, service, notebook, evaluation job, or script needs direct Python return values | **FrootAI Python SDK** — this package |
| VS Code, Claude, Cursor, or another agent should call tools over Model Context Protocol | [`frootai-mcp`](https://pypi.org/project/frootai-mcp/) |

The SDK is Python-standard-library based with zero runtime dependencies. Bundled knowledge and search work offline. Federation is lazy, but the current default client is deliberately transport-pending: applications must inject a supported transport before making live federation calls.

## Five steps to first value

### 1. Install and verify

```bash
python -m pip install --upgrade frootai
frootai --version
```

Requirements: Python 3.10 or newer. Published classifiers cover Python 3.10–3.13.

### 2. Search bundled knowledge

```python
from frootai import FrootAI

fai = FrootAI()

for result in fai.search("secure enterprise RAG", max_results=3):
    print(result["id"], result["title"], result["score"])

module = fai.get_module("R2")
print(module["title"] if module else "Module not found")
```

Knowledge, glossary, Play metadata, and the BM25 search index are packaged with the wheel. No API key is required for these operations.

### 3. Inspect a Solution Play and cost direction

```python
from frootai import FrootAI, SolutionPlay

fai = FrootAI()
play = SolutionPlay.get("01")
if play:
    print(play.name, play.complexity)

estimate = fai.estimate_cost("01-enterprise-rag", scale="prod")
print(estimate)
```

Cost output is directional reference data, not a cloud bill or deployment quote. Confirm region, SKU, traffic, retention, and current provider pricing before committing spend.

### 4. Wire and validate the FAI Protocol

```python
from frootai import FrootAI

fai = FrootAI()
manifest = fai.wire_play("01")
validation = fai.validate_manifest(manifest)

print(validation)

# Preview before creating a project structure
preview = fai.scaffold_play("01", project_name="customer-rag", dry_run=True)
print(preview)
```

The manifest connects knowledge, WAF context, agents, instructions, skills, hooks, and guardrails. Validation reports structure and references; it does not deploy infrastructure.

<details open>
<summary><strong>See the Python working loop</strong></summary>

![Search, inspect, evaluate, and integrate with FrootAI for Python](https://frootai.dev/images/package-readmes/python-sdk.png)

Explore the live [FrootAI for Python product page](https://frootai.dev/python).

</details>

### 5. Evaluate quality or connect trusted tools

```python
from frootai import Evaluator

scores = {
    "groundedness": 4.6,
    "relevance": 4.2,
    "coherence": 4.4,
    "fluency": 4.5,
}

evaluator = Evaluator()
print(evaluator.summary(scores))
print("passed:", evaluator.all_passed(scores))
```

Federation is optional and asynchronous. The current SDK exposes the client contract but does not silently start a kernel transport:

```python
from frootai.federation import create_federation_client

# `transport` implements: async call({"method": str, "params": mapping})
mcp = create_federation_client(
    transport=your_transport,
    federation={
        "pre_attach": ["azure"],
        "trust_file": "/etc/frootai/trust.json",
        "idle_disconnect_minutes": 30,
    },
)

async def inspect_azure() -> None:
    handle = await mcp.attach({"name": "azure", "trustOverride": True})
    tools = await mcp.list_tools(handle)
    print([tool["qualifiedName"] for tool in tools])
    await mcp.detach(handle)
```

Without an injected transport, federation calls fail explicitly with `kernel_connection_pending` (or `remote_mode_pending` for the reserved remote mode). Review publisher evidence, credentials, tool annotations, and permissions before overriding a trust decision.

## API map

<details open>
<summary><strong>FrootAI client</strong></summary>

| Area | Methods |
|---|---|
| Knowledge | `search`, `get_module`, `list_modules`, `list_layers`, `lookup_term`, `search_glossary` |
| Solution Plays | `estimate_cost`, `check_play_compatibility`, `get_learning_path` |
| FAI Protocol | `wire_play`, `validate_manifest`, `inspect_wiring`, `fai_protocol` |
| Scaffolding | `scaffold_play`, `list_templates` |
| Architecture governance | `get_waf_guidance`, `primitives_catalog` |
| Federation | Lazy `mcp` client with `discover`, `attach`, `list_tools`, `invoke`, `chain`, and `detach` |

</details>

<details>
<summary><strong>SolutionPlay catalog</strong></summary>

```python
from frootai import SolutionPlay

all_plays = SolutionPlay.all()
ready_plays = SolutionPlay.ready()
rag_plays = SolutionPlay.search("RAG")
play = SolutionPlay.get("01")
```

Use `by_layer(...)` to filter by FROOT layer. Readiness labels describe packaged metadata, not live cloud-state certification.

</details>

<details>
<summary><strong>Evaluation</strong></summary>

`Evaluator` supports configurable metrics and thresholds, `check_thresholds`, `all_passed`, `summary`, JSON output, and `from_config`.

Evaluation scores are caller-supplied unless your application integrates a scorer. The SDK does not claim that a model or deployment is safe solely because a dictionary passed local thresholds.

</details>

<details>
<summary><strong>Lean primitive resolution</strong></summary>

```python
from frootai import resolve_primitive, fetch_primitive

resolved = resolve_primitive("fai-rag-architect", lean_mode=True)
content = fetch_primitive("fai-rag-architect", lean_mode=True)
```

Lean resolution prefers fidelity-verified compact variants and preserves an explicit full-content path when exact source is needed.

</details>

<details>
<summary><strong>Advanced SDK modules: prompt experiments, Copilot patterns, and agentic loops</strong></summary>

The wheel also includes callback-driven advanced modules:

| Module | Public pattern | Important boundary |
|---|---|---|
| `frootai.ab_testing` | `PromptExperiment`, `PromptVariant`, `ExperimentResult` | The caller supplies the model and optional scorer callbacks |
| `frootai.copilot` | `CopilotSession`, retry/error/event helpers | The default send implementation is a test placeholder; integrate a real provider by overriding `_execute_send` |
| `frootai.agentic_loop` | `AgenticLoop`, `Task`, `LoopConfig`, `run_plan` | Uses disk state and optional validation commands; only run trusted commands in a controlled workspace |

Example prompt experiment:

```python
from frootai.ab_testing import PromptExperiment, PromptVariant

experiment = PromptExperiment(
    name="rag-prompt",
    variants=[
        PromptVariant("control", "Answer with citations."),
        PromptVariant("concise", "Answer briefly and cite sources."),
    ],
)

results = experiment.run(
    test_queries=["What is hybrid search?"],
    model_fn=your_model_callback,
    scorer_fn=your_scorer_callback,
)
print(experiment.summary(results))
```

These utilities are composition patterns, not bundled model access. The SDK never supplies provider credentials or production quality scores automatically.

</details>

<details>
<summary><strong>Federation composition, errors, and forward compatibility</strong></summary>

`chain()` performs SDK-side sequential composition over `invoke()`; there is no hidden `fai_chain` kernel operation. A chain is capped at 32 steps, and `mapPrev` can derive the next call's arguments from the previous result.

```python
result = await mcp.chain([
    {"tool": "azure.subscription_list", "args": {"tier": "verified"}},
    {
        "tool": "azure.resource_list",
        "mapPrev": lambda previous: {"subscription": previous["id"]},
    },
])
```

Canonical `FederationError.code` values are:

| Code | Meaning |
|---|---|
| `kernel_connection_pending` | No local kernel transport has been injected |
| `remote_mode_pending` | Reserved remote transport is not implemented in this release |
| `user_error` | Invalid caller arguments, handle, or tool name |
| `detach_failed` | The kernel explicitly rejected detach |
| `trust_blocked` | Trust policy refused the area |
| `tool_error` | The downstream tool failed |
| `transport_error` | Process or wire transport failed |
| `attach_timeout` | Attach did not complete within its deadline |
| `namespace_collision` | Attached areas exposed conflicting bare tool names |

Typed Tier-1 helpers are optional conveniences. Generic `invoke("<area>.<tool>", args)` remains the forward-compatible route for newly introduced tools.

</details>

## Command-line reference

| Command | Purpose |
|---|---|
| `frootai plays [--layer LAYER] [--ready]` | Browse packaged Solution Plays |
| `frootai search <query> [--limit N]` | Search bundled knowledge |
| `frootai modules` | List FROOT modules |
| `frootai glossary [term]` | Browse or look up terminology |
| `frootai cost <play> [--scale dev\|prod]` | Produce directional cost output |
| `frootai scaffold <play> [--name NAME] [--dry-run]` | Preview or create SDK scaffold output |
| `frootai wire <play>` | Generate a FAI manifest |
| `frootai validate <file>` | Validate a manifest file |
| `frootai evaluate metric=score ...` | Apply local evaluation thresholds |
| `frootai waf <pillar>` | Inspect Well-Architected guidance |
| `frootai primitives` | Show the packaged primitive catalog |
| `frootai learning-path <topic>` | Get a curated learning path |

## Operating boundaries

| Boundary | Contract |
|---|---|
| Offline behavior | Bundled knowledge/search works without a network; live federation does not |
| Secrets | Pass tokens through application configuration or secret stores; do not log them |
| Cost | Estimates are static and directional |
| Scaffolding | Use `dry_run=True` before writing files |
| Federation | Trust gates, qualified tool names, bounded chains, and explicit detach preserve lifecycle visibility |
| Compatibility | New MCP tools can be invoked through generic `invoke` before typed helpers catch up |

## Verify and develop

```bash
cd python-sdk
python -m pip install --upgrade build pytest
python -m pytest tests -v
python -m build
```

## Related packages

| Package | Use it when |
|---|---|
| [`frootai-mcp` on PyPI](https://pypi.org/project/frootai-mcp/) | An MCP client needs the Python tool server |
| [`frootai-mcp` on npm](https://www.npmjs.com/package/frootai-mcp) | A Node.js MCP process or local federation router is preferred |
| [`frootai` on npm](https://www.npmjs.com/package/frootai) | A terminal user needs Agent FAI and Operator CLI |

## License

MIT © 2026 FrootAI.
