> ## Documentation Index
> Fetch the complete documentation index at: https://docs.hexgate.ai/llms.txt
> Use this file to discover all available pages before exploring further.

# Introduction

> Runtime authorization for AI agents — decide who can run which tool, in which role, with which arguments.

**Hexgate is runtime authorization for AI agents.** On every tool call, it decides
whether **this end user**, acting in **this role**, may run **this tool** with
**these arguments** — and returns `allow`, `deny`, or `approval_required`. Drop it
in front of an OpenAI Agents / LangChain / Google ADK / Pydantic AI agent without
rewriting the agent.

The decision has three inputs and one output:

```text theme={null}
  end user (id + role)  ×  tool call (name + args)  ──►  allow · deny · approval
```

## Same request, different answer

Authorization isn't a property of the agent — it's a property of *who is calling*
and *what they're trying to do*. A support agent and a billing agent can share the
exact same code and the exact same `refund_order` tool, yet get different answers,
because a **policy** maps roles → tools → argument limits:

```yaml theme={null}
roles:
  support:                       # front-line: small USD refunds only
    default_policy: { mode: deny }
    tools:
      refund_order:
        mode: allow
        constraints:
          - args.amount <= 50
          - args.currency == "USD"
      issue_credit:                # support can request; a human confirms
        mode: approval_required
  billing:                       # larger refunds, major currencies
    default_policy: { mode: deny }
    tools:
      refund_order:
        mode: allow
        constraints:
          - args.amount <= 500
          - args.currency in ["USD", "EUR"]
```

The **same** `refund_order($400)` call resolves differently per caller:

| Caller    | Tool call                                  | Decision                 | Why                               |
| --------- | ------------------------------------------ | ------------------------ | --------------------------------- |
| `support` | `refund_order(amount=400, currency="USD")` | ✗ **deny**               | over support's `amount <= 50` cap |
| `billing` | `refund_order(amount=400, currency="EUR")` | ✓ **allow**              | within billing's `amount <= 500`  |
| `support` | `issue_credit(amount=50)`                  | ⚠ **approval\_required** | needs a human's OK                |

The caps live in the policy, **outside the model** — so a prompt-injected or
confused agent can't talk its way past `amount <= 500`. It never even sees the
tool result for a denied call; it gets a `[policy_denied]` marker it can recover
from.

<CardGroup cols={2}>
  <Card title="See it enforce (no keys)" icon="rocket" href="/quickstart">
    Install, then watch a role + arguments decide a tool call in one command.
  </Card>

  <Card title="Author a policy" icon="shield" href="/policy/yaml-shape">
    Roles, tools, modes, and argument constraints — the full policy shape.
  </Card>

  <Card title="Request context + roles" icon="user" href="/concepts/user-scope">
    How the end user's identity + role reach the decision at call time.
  </Card>

  <Card title="Framework adapters" icon="puzzle-piece" href="/adapters/overview">
    OpenAI Agents, LangChain/LangGraph, Google ADK, Pydantic AI — wrap once.
  </Card>
</CardGroup>

## What Hexgate is

Hexgate is two things that move together:

* **`hexgate` — the SDK.** A Python runtime that intercepts every tool call and
  runs it through a `PolicyEnforcer`, resolving the caller's role at call time and
  returning a typed `Decision`. It wraps your existing agent without rewriting it.
* **The Hexgate platform** *(optional)* — a control plane + dashboard for editing
  policy in a browser, minting per-project tokens, watching live decisions stream
  from a serving agent, and shipping signed policy bundles to production. Available
  as **[Hexgate Cloud](/platform/hosted)** (hosted — set one env var) or
  self-hosted.

Two things feed the decision, and one thing records it:

* The **end user's identity and role** are a **decision input** — carried
  per-request via [`HexgateContext`](/concepts/user-scope), they select which role's rules
  apply. (They also tag traces, but that's secondary.)
* The **policy** supplies the rules — a [YAML file or signed WASM
  bundle](/policy/wasm-bundles), loaded locally or from the platform.
* Every decision is written to an [**audit trail**](/concepts/audit-trail): who
  called what, and whether it was allowed.

## The decision path

```text theme={null}
     end user (id + role)          tool call (name + args)
              └───────────────┬────────────────┘
                              ▼
                PolicyEnforcer.decide()  ◄──  policy
                              ▼                (local YAML / bundle,
              allow  ·  deny  ·  approval        or signed cloud bundle)
                              │
                              ▼
        audit log — who called what, and whether it was allowed
```

New here? [Install and see a policy decide a tool call](/quickstart) in 60
seconds — no API keys — then [pick a path](/two-paths) between the local chat REPL
and the platform-backed serve loop.
