- ›
OAuth for AI agents in a multi-tenant product means each end-user authorizes their own apps— not one shared integration account for everyone. - ›
Naïve stores OAuth grants as connections on the tenant user— Gmail, Slack, GitHub, and 1,000+ apps (per published docs). - ›
The Account Kit controls which apps a user may connect— open, allowlist, or blocklist — enforced when the agent calls connect or execute. - ›Connecting a new app defaults to requiring human approval for agent calls (per published docs).
- ›Tokens never enter the model context; the agent calls governed tools and the platform uses the connection server-side.
- ›White-label the OAuth consent screen with your brand via connections_config on the kit.
When builders add tool use to a multi-tenant product, the first OAuth mistake is sharing one integration account across all customers. Customer A's agent reads Customer B's inbox. The fix is per-user connections: each tenant user completes OAuth for their own apps, and grants live on their agent identity.
Naïve implements this as the /connections primitive — 1,000+ apps (per published docs), Account Kit–gated, approval-routed for agent-initiated connects.
Shared OAuth vs per-user connections
| Shared integration account | Per-user connection | |
|---|---|---|
| Grant lives on | Your server's env vars | One tenant user |
| Cross-tenant risk | High — one token, all customers | Structural — forUser(id) scopes grants |
| Revoke one customer | Rotate shared token → everyone breaks | Revoke that user's connection only |
| Kit policy | Custom if-checks in app code | Account Kit allowlist enforced server-side |
How the connect flow works
1. Your app: forUser(user_id).connections.connect("gmail")
2. End-user: completes OAuth in browser (your branded consent)
3. Naïve: stores encrypted grant on tenant user
4. Agent: calls governed email/connections tools — tokens used server-side
Agent calls to connect a new app default to human approval (per published docs).
Wire it up
const user = await naive.users.create({ email: "customer@acme.com" });
const client = naive.forUser(user.id);
const { redirectUrl } = await client.connections.connect("slack");
// redirect customer to redirectUrl — grant attaches to this tenant user onlyRestrict apps on the kit:
connections_config: {
mode: "allowlist",
allow: ["gmail", "slack", "github"],
}Where to go next
- Build an agentic access-governance platform — connections + kits tutorial
- Multi-tenant AI agents — isolation model
- Connections docs — connect, execute, list
How does OAuth work for AI agents on Naïve?+
Why must OAuth be per-user in a multi-tenant SaaS?+
How does the Account Kit restrict which apps agents can connect?+
Does connecting an app require human approval?+
How many apps can Naïve connect?+
Can I white-label the OAuth consent screen?+
Building the agent-native backend.
Multi-tenant AI agents give every customer their own isolated agent. Here's the operator, tenant-user, and Account Kit model behind per-user isolation.
An AI agent identity is the governed record an agent acts as — tenant user, Account Kit, resources, and audit trail — not the model or the API key alone.
Build an agentic access-governance platform on Naïve where each company's Account Kit decides per tool which GitHub and Slack actions the agent may run.
The connections primitive gives each end-user's agents authenticated access to 1,000+ third-party apps — per user, gated by the Account Kit, in one surface.