Metadata-Version: 2.4
Name: promptrak
Version: 0.1.0
Summary: Security and governance middleware for AI agents
License-Expression: MIT
Project-URL: Homepage, https://promptrak.io
Project-URL: Documentation, https://docs.promptrak.io
Project-URL: Repository, https://github.com/promptrak/promptrak-python
Keywords: ai,llm,security,agents,pii,governance
Requires-Python: >=3.9
Description-Content-Type: text/markdown
Requires-Dist: requests>=2.28
Provides-Extra: dev
Requires-Dist: pytest>=8.0; extra == "dev"
Requires-Dist: pytest-mock>=3.12; extra == "dev"

# Promptrak Python SDK

Secure and govern your AI agents — prompt security, PII vault, and tool authorization in three lines of code.

```bash
pip install promptrak
```

---

## Quickstart

```python
from promptrak import Promptrak

client = Promptrak(api_key="tp_...", tenant_id="acme")
```

---

## Tier 1 — Prompt Security (10 minutes)

Protects against prompt injection, jailbreak attempts, credential extraction,
and policy bypass. Secures what goes **into** the model.

```python
decision = client.evaluate(prompt, actor_id="agent-1")

if decision.action == "allow":
    response = my_llm.complete(prompt)
elif decision.action == "minimize":
    # Use the sanitized version — unsafe content has been removed
    response = my_llm.complete(decision.safe_prompt)
else:
    # "block" — do not proceed
    return "Request blocked by security policy"
```

`decision.policy_trace` contains the human-readable reason for any non-allow decision.
Use it for audit logs and user-facing explanations.

---

## Tier 2 — PII Vault (1 hour)

Protects against PII leakage through the LLM. Real values are stored in the
vault — the model only sees placeholders. Output is scrubbed before it reaches
the user.

```python
safe = client.sanitize(prompt, actor_id="agent-1")
response = my_llm.complete(safe.safe_prompt)   # model sees [NAME], [EMAIL] etc.
clean = client.scrub_output(response, session_id=safe.session_id)
return clean   # safe to deliver to the user
```

The session links the sanitize and scrub calls. You never need to track the
vault mapping — the SDK handles it.

---

## Tier 3 — Tool Authorization (half day)

Protects against unauthorized tool execution, high-blast-radius actions, and
malicious tool parameters. Every tool call requires explicit authorization
before execution.

```python
auth = client.authorize_tool("query_database", params, actor_id="agent-1")

if auth.action == "allow":
    result = db.execute(params)
elif auth.action == "pending_approval":
    # Queue for human review
    queue_for_review(auth.approval_id, params)
    return "Tool call queued for human approval"
else:
    # "deny"
    return f"Tool access denied: {auth.reason}"
```

### Resolving a pending approval

```python
# Called by your review system or human approver
client.submit_approval(
    auth.approval_id,
    "approve",           # or "deny"
    approver_id="reviewer-jane",
)
```

---

## Choose Your Tier

| Use case | Tier |
|---|---|
| Internal productivity bot (doc summarization, HR Q&A) | Tier 1 |
| Customer-facing agent with PII (support, CRM) | Tier 2 |
| Autonomous agent with write access (emails, tickets, data modification) | Tier 3 |
| Healthcare / financial systems (HIPAA, SOX) | Tier 2 minimum, Tier 3 recommended |

---

## Return Types

```python
@dataclass
class Decision:
    action: str        # "allow" | "minimize" | "local-only" | "block"
    safe_prompt: str   # use instead of original when action == "minimize"
    risk_score: float  # 0.0 → 1.0
    policy_trace: list # who, what, why, which rule
    request_id: str    # for audit correlation

@dataclass
class SanitizedPrompt:
    safe_prompt: str   # prompt with PII replaced by vault placeholders
    session_id: str    # pass to scrub_output()
    action: str
    risk_score: float
    policy_trace: list

@dataclass
class ToolDecision:
    action: str        # "allow" | "deny" | "pending_approval"
    reason: str
    approval_id: str | None  # present when action == "pending_approval"
```

---

## Error Handling

All SDK methods raise `PromptrakError` on failure.

```python
from promptrak import PromptrakError

try:
    decision = client.evaluate(prompt, actor_id="agent-1")
except PromptrakError as e:
    print(e.status_code)   # HTTP status, or None for connection errors
    print(e.request_id)    # correlate with backend audit logs
    raise
```

Token management and retry on transient failures are handled internally.
You never call `/auth/token` directly.

---

## Self-hosted deployments

```python
client = Promptrak(
    api_key="tp_...",
    tenant_id="acme",
    base_url="https://your-deployment.internal",
)
```

---

## Development

```bash
pip install -e ".[dev]"
pytest
```
