From ea2db0a755fa02b17a2b0c61eaa37b8c4ebe6626 Mon Sep 17 00:00:00 2001 From: Isaiah Date: Mon, 18 May 2026 11:40:05 -0400 Subject: [PATCH 1/2] Document AWS Bedrock IAM role setup for BYOLLM, including Oz cloud runs Rewrite the BYOLLM auth section to describe the OIDC + role-assumption flow that Warp actually uses for AWS Bedrock inference, and extend the docs to cover Oz cloud agent runs in addition to interactive terminal agents. Highlights: - Replace the local AWS CLI session-credentials path with a trust policy + permissions policy + AWS CLI setup script that admins follow once per team. - Use scoped_principal:/* in the trust policy so a single role works for human-triggered interactive and cloud runs as well as named-agent service-account runs. Note the full sub claim shape so admins can scope further if they want. - Update prerequisites, troubleshooting, and FAQ to match the new auth model. Companion to the Oz Bedrock plumbing on iw/add-aws-region-to-oz-runs in warp-server. Co-Authored-By: Oz --- .../bring-your-own-llm.mdx | 177 ++++++++++++++---- 1 file changed, 141 insertions(+), 36 deletions(-) diff --git a/src/content/docs/enterprise/enterprise-features/bring-your-own-llm.mdx b/src/content/docs/enterprise/enterprise-features/bring-your-own-llm.mdx index e81d7032..75f0864c 100644 --- a/src/content/docs/enterprise/enterprise-features/bring-your-own-llm.mdx +++ b/src/content/docs/enterprise/enterprise-features/bring-your-own-llm.mdx @@ -12,7 +12,7 @@ This gives you control over cloud spend and model hosting, without changing how :::caution BYOLLM currently supports **AWS Bedrock** only. Coming soon: Azure Foundry and Google Vertex support. -BYOLLM applies to interactive agents in the terminal. Cloud agents do not yet support BYOLLM routing. +BYOLLM applies to both interactive Oz agents in the terminal and Oz cloud agent runs. ::: :::note @@ -21,32 +21,32 @@ BYOLLM is only available on Warp's Enterprise plan. Contact [warp.dev/contact-sa ## Key features -* **Cloud-native credentials** - Authenticate using each user’s AWS IAM identity. Warp does not store API keys. +* **No API keys** - Warp authenticates to AWS Bedrock by assuming an IAM role you control. Warp does not require or store long-lived provider API keys. * **Admin-enforced routing** - Team admins configure which models are available to users in AWS Bedrock, with the ability to disable non-Bedrock model access entirely. * **Consolidated billing** - Inference costs are billed directly to your AWS account, leveraging existing cloud commitments. ## How BYOLLM works -{/* TODO: Add architecture diagram showing BYOLLM request flow (admin configures routing → user authenticates to AWS → Warp routes request → inference in customer AWS account) */} +{/* TODO: Add architecture diagram showing BYOLLM request flow (admin configures routing → admin provisions role → Warp assumes role → inference in customer AWS account) */} When BYOLLM is enabled, Warp redirects inference calls to your AWS Bedrock environment instead of using model providers' direct APIs. Here's the high-level flow: -1. **Admin configures routing** - Your team admin sets routing policies in Warp's admin settings (e.g., "Route Claude Sonnet 4.5 through AWS Bedrock; disable direct Anthropic API"). -2. **Team members authenticate** - Each team member authenticates to AWS locally using the AWS CLI (`aws login`). -3. **Warp routes requests** - When a team member uses an interactive agent in the terminal, Warp uses their short-lived session credentials to authenticate requests to your configured AWS Bedrock API endpoint. -4. **Inference executes in your cloud** - The model runs in your AWS account. Responses return to the Warp client. +1. **Admin configures routing** - Your team admin sets routing policies in Warp's admin settings (for example, "Route Claude Sonnet 4.5 through AWS Bedrock; disable direct Anthropic API"). +2. **Admin provisions an assumable IAM role** - Your cloud admin creates an AWS IAM role with a trust policy that allows Warp's OIDC identity to assume it. +3. **Warp routes requests** - When a team member uses an interactive Oz agent in the terminal or kicks off an Oz cloud agent run, Warp assumes the configured role and calls your AWS Bedrock endpoint using short-lived credentials. +4. **Inference executes in your cloud** - The model runs in your AWS account. Responses return to the Warp client or cloud worker. -### Credential lifecycle +### Role assumption and credentials -BYOLLM uses **cloud-native IAM authentication**, not long-lived API keys: +BYOLLM uses **short-lived AWS credentials derived from role assumption**, not long-lived API keys: -* **Automatic refresh** - Session tokens refresh automatically every ~15 minutes. Users can enable auto-refresh by opening **Settings** and searching for `AWS Bedrock`, or when prompted during first credential expiration. With auto-refresh enabled, sessions can run uninterrupted for up to 12 hours (depending on your AWS admin configuration). -* **Per-user credentials** - Credentials are not shared across the organization. Your cloud provider's default credential provider chain (e.g., AWS CLI) provisions and refreshes them locally. -* **No storage or logging** - Warp never stores or logs your cloud session tokens on its servers. +* **IAM role based** - You provide a role ARN in the Warp admin settings. Warp uses OIDC and `sts:AssumeRoleWithWebIdentity` to obtain temporary credentials for AWS Bedrock requests. +* **Short-lived credentials** - AWS issues temporary credentials during role assumption instead of requiring embedded secrets. +* **No storage or logging** - Warp never stores or logs your cloud credentials on its servers. -This approach ensures access management stays with your cloud provider, giving admins member-by-member control. +This approach keeps access management in AWS while giving your admins tight control over what Warp can invoke. ### Model availability @@ -67,7 +67,7 @@ Before configuring BYOLLM, confirm the following: * Your organization has the desired models enabled in AWS Bedrock. * You have admin access to both Warp's [Admin Panel](/enterprise/team-management/admin-panel/) and your AWS IAM settings. -* Team members have the AWS CLI installed locally. +* Your AWS account already has an IAM OIDC provider configured for Warp's issuer host, or you are prepared to create one before creating the role. ### Step 1: Configure routing policies (admin) @@ -75,13 +75,60 @@ In the [Admin Panel](/enterprise/team-management/admin-panel/), configure which 1. From the [Admin Panel](/enterprise/team-management/admin-panel/), navigate to the BYOLLM or model routing settings. 2. Select which models should use your cloud provider (e.g., "Claude Sonnet 4.5 via AWS Bedrock"). -3. Optionally, disable direct API access to enforce provider-only routing. +3. Enter the AWS IAM role ARN Warp should assume for Bedrock requests. +4. Optionally, disable direct API access to enforce provider-only routing. ### Step 2: Provision IAM roles (cloud admin) -Grant your team members the necessary permissions in AWS. Use least-privilege IAM policies. +Create an IAM role that Warp can assume via OIDC, then attach the minimum Bedrock permissions policy. Use least-privilege IAM policies. -**Example: AWS Bedrock minimum IAM policy** +The role setup has two parts: + +1. A **trust policy** that allows Warp's OIDC identity to call `sts:AssumeRoleWithWebIdentity` +2. A **permissions policy** that grants the minimum Bedrock inference permissions + +#### Trust policy requirements + +Your trust policy should: + +* Use the OIDC provider for your Warp issuer host +* Restrict `sub` to your team's principals using the `scoped_principal:/*` pattern. This single condition covers both regular users running interactive or cloud agents and named-agent service accounts on the team. +* Require `aud` to equal `sts.amazonaws.com` + +**Example trust policy** + +```json +{ + "Version": "2012-10-17", + "Statement": [ + { + "Effect": "Allow", + "Principal": { + "Federated": "arn:aws:iam::123456789012:oidc-provider/app.warp.dev" + }, + "Action": "sts:AssumeRoleWithWebIdentity", + "Condition": { + "StringLike": { + "app.warp.dev:sub": "scoped_principal:/*" + }, + "StringEquals": { + "app.warp.dev:aud": "sts.amazonaws.com" + } + } + } + ] +} +``` + +Replace the account ID, issuer host, and team UID with values for your environment. If you are configuring a non-production environment, use the corresponding issuer host instead of `app.warp.dev`. + +The `` is the Warp team UID for the team that will be allowed to assume this role. You can find it in the Warp [Admin Panel](/enterprise/team-management/admin-panel/) under your team's settings. The trailing `/*` is required and matches any principal on the team (regular users running terminal or cloud agents, plus any named-agent service accounts owned by the team). + +:::note +The full `sub` claim Warp signs has the shape `scoped_principal:/:`, where `` is `user` for human-triggered runs and `service_account` for named-agent runs. Tighten the trust policy further by replacing `/*` with `/user:*` or `/service_account:*` if you want to restrict which actor types may assume the role. +::: + +#### Minimum Bedrock permissions policy ```json { @@ -105,20 +152,76 @@ Grant your team members the necessary permissions in AWS. Use least-privilege IA ``` :::note -This policy covers Warp's current usage. Warp uses global inference profiles for models when available. +`bedrock:InvokeModel` and `bedrock:InvokeModelWithResponseStream` are the minimum useful permissions for inference. If you need tighter scoping later, you can narrow the allowed resources. If your deployment depends on additional Bedrock capabilities, such as inference profiles or extra read APIs, you may need to expand the policy. ::: -### Step 3: Authenticate locally (team member) +#### Create the role with AWS CLI -Each team member authenticates to AWS using the AWS CLI: +If you prefer to create the role from the command line, this shell script creates the trust policy, creates the role, and attaches the minimum permissions policy: ```bash -aws login +ROLE_NAME="WarpBedrock" +ISSUER_HOST="app.warp.dev" +TEAM_UID="" +ACCOUNT_ID="$(aws sts get-caller-identity --query Account --output text)" + +cat > /tmp/warp-bedrock-trust-policy.json < /tmp/warp-bedrock-permissions-policy.json < Date: Mon, 18 May 2026 11:48:59 -0400 Subject: [PATCH 2/2] Split BYOLLM doc: narrow team trust policy to user:*, add BYOLLM on Oz section The team-wide trust policy (Step 2) is now scoped to scoped_principal:/user:* for human team members. Named-agent runs authenticate as service accounts, not users, so they need separate handling. Add a new top-level 'BYOLLM on Oz' section that covers the named-agent flow: - Explains the actor-type difference between human runs (user:) and named-agent runs (service_account:). - Provides two patterns for authorizing named agents: a wildcard service_account:* for all team agents, or per-UID conditions for a subset. - Documents how to find the team UID (Admin Panel) and named-agent UIDs (GET /api/v1/agent/identities or the Oz web app URL). - Documents the per-agent inference_providers.aws override in the public API, including role_arn / region / disabled and the trust-policy implications. Co-Authored-By: Oz --- .../bring-your-own-llm.mdx | 107 +++++++++++++++++- 1 file changed, 102 insertions(+), 5 deletions(-) diff --git a/src/content/docs/enterprise/enterprise-features/bring-your-own-llm.mdx b/src/content/docs/enterprise/enterprise-features/bring-your-own-llm.mdx index 75f0864c..daa375d7 100644 --- a/src/content/docs/enterprise/enterprise-features/bring-your-own-llm.mdx +++ b/src/content/docs/enterprise/enterprise-features/bring-your-own-llm.mdx @@ -24,6 +24,7 @@ BYOLLM is only available on Warp's Enterprise plan. Contact [warp.dev/contact-sa * **No API keys** - Warp authenticates to AWS Bedrock by assuming an IAM role you control. Warp does not require or store long-lived provider API keys. * **Admin-enforced routing** - Team admins configure which models are available to users in AWS Bedrock, with the ability to disable non-Bedrock model access entirely. * **Consolidated billing** - Inference costs are billed directly to your AWS account, leveraging existing cloud commitments. +* **Per-identity scoping** - Trust policy conditions distinguish between human team members and named agents (service accounts), so admins can scope each independently. ## How BYOLLM works @@ -89,10 +90,12 @@ The role setup has two parts: #### Trust policy requirements +This section covers the trust policy for **human team members** assuming the role from the Warp terminal or from Oz cloud agent runs they trigger themselves. For named-agent (service-account) runs, see [BYOLLM on Oz](#byollm-on-oz). + Your trust policy should: * Use the OIDC provider for your Warp issuer host -* Restrict `sub` to your team's principals using the `scoped_principal:/*` pattern. This single condition covers both regular users running interactive or cloud agents and named-agent service accounts on the team. +* Restrict `sub` to your team's human users using the `scoped_principal:/user:*` pattern * Require `aud` to equal `sts.amazonaws.com` **Example trust policy** @@ -109,7 +112,7 @@ Your trust policy should: "Action": "sts:AssumeRoleWithWebIdentity", "Condition": { "StringLike": { - "app.warp.dev:sub": "scoped_principal:/*" + "app.warp.dev:sub": "scoped_principal:/user:*" }, "StringEquals": { "app.warp.dev:aud": "sts.amazonaws.com" @@ -122,10 +125,10 @@ Your trust policy should: Replace the account ID, issuer host, and team UID with values for your environment. If you are configuring a non-production environment, use the corresponding issuer host instead of `app.warp.dev`. -The `` is the Warp team UID for the team that will be allowed to assume this role. You can find it in the Warp [Admin Panel](/enterprise/team-management/admin-panel/) under your team's settings. The trailing `/*` is required and matches any principal on the team (regular users running terminal or cloud agents, plus any named-agent service accounts owned by the team). +The `` is the Warp team UID for the team that will be allowed to assume this role. You can find it in the Warp [Admin Panel](/enterprise/team-management/admin-panel/) under your team's settings. :::note -The full `sub` claim Warp signs has the shape `scoped_principal:/:`, where `` is `user` for human-triggered runs and `service_account` for named-agent runs. Tighten the trust policy further by replacing `/*` with `/user:*` or `/service_account:*` if you want to restrict which actor types may assume the role. +The full `sub` claim Warp signs has the shape `scoped_principal:/:`, where `` is `user` for human-triggered runs and `service_account` for named-agent runs. The `user:*` pattern matches every human user on the team. To also authorize named agents on the same role, see [BYOLLM on Oz](#byollm-on-oz). ::: #### Minimum Bedrock permissions policy @@ -177,7 +180,7 @@ cat > /tmp/warp-bedrock-trust-policy.json </user:`). + +Oz also runs **named agents**, which are service accounts owned by the team rather than individual humans. A named-agent run authenticates as its service account, not as the user who created or scheduled it. The `sub` claim therefore has a different shape: + +* Human run: `scoped_principal:/user:` +* Named-agent run: `scoped_principal:/service_account:` + +Because the actor type differs, the trust policy you set up in Step 2 above (`user:*`) does not authorize named-agent runs. You have two options for adding them. + +### Option A: Authorize all named agents on the same role + +Add a second `StringLike` pattern to the same trust policy condition so the role accepts both human users and any named agent on the team: + +```json +"Condition": { + "StringLike": { + "app.warp.dev:sub": [ + "scoped_principal:/user:*", + "scoped_principal:/service_account:*" + ] + }, + "StringEquals": { + "app.warp.dev:aud": "sts.amazonaws.com" + } +} +``` + +This is the simplest option when every named agent on the team should be allowed to use BYOLLM. + +### Option B: Authorize specific named agents by UID + +If you want only a subset of named agents to use BYOLLM, list their UIDs explicitly: + +```json +"Condition": { + "StringLike": { + "app.warp.dev:sub": [ + "scoped_principal:/user:*", + "scoped_principal:/service_account:", + "scoped_principal:/service_account:" + ] + }, + "StringEquals": { + "app.warp.dev:aud": "sts.amazonaws.com" + } +} +``` + +You can also use `StringEquals` instead of `StringLike` for the service-account UIDs if you want strict matching with no wildcards. + +### Finding team and agent UIDs + +To build the `sub` patterns above, you'll need your team UID and (for Option B) the UID of each named agent. + +* **Team UID** - Visible in the Warp [Admin Panel](/enterprise/team-management/admin-panel/) under your team's settings. +* **Named-agent UID** - Each named agent has a stable `uid` returned by Warp's public API and visible in the Oz web app. + +List all named agents on your team via the public API: + +```bash +curl -H "Authorization: Bearer " \ + https://app.warp.dev/api/v1/agent/identities +``` + +The response contains an `agents[]` array where each entry has a `uid` field. That `uid` is the value to use in the `service_account:` portion of the trust policy. + +You can also see each agent's UID in the Oz web app at `https://oz.warp.dev/agents/` — the trailing path segment is the UID. + +### Per-agent inference provider overrides + +By default, named agents inherit the team-wide BYOLLM routing policy configured in the [Admin Panel](/enterprise/team-management/admin-panel/). You can override the role ARN, AWS region, or disable BYOLLM entirely on a per-agent basis through the public API: + +```json +{ + "inference_providers": { + "aws": { + "role_arn": "arn:aws:iam:::role/", + "region": "us-east-1", + "disabled": false + } + } +} +``` + +Set this field on `POST /api/v1/agent/identities` or `PUT /api/v1/agent/identities/` to give an individual agent its own routing. Common uses: + +* Different agents assume different roles (e.g. for separate cost-allocation tags or different model permissions). +* A specific agent runs in a different AWS region from the team default. +* A specific agent opts out of BYOLLM entirely (`"disabled": true`) and falls back to Warp-managed inference. + +Any override role must have a trust policy that authorizes that agent's `sub` (typically the `service_account:` form). + ## BYOLLM usage and billing behavior ### Billing