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

# Grant sandboxes access to AI Object Storage

> Let sandboxes exchange their built-in OIDC token for temporary AI Object Storage credentials

Every CoreWeave sandbox can carry a built-in OIDC token that it exchanges through [Workload Identity Federation (WIF)](/products/storage/object-storage/auth-access/workload-identity-federation/about) for temporary CoreWeave AI Object Storage credentials. The sandbox control plane mints the token, mounts it into the container, and sets the environment variables that AWS SDKs read, so a sandbox reads and writes buckets without you injecting a long-lived access key.

This page is for administrators who set up the trust relationship once per organization, and for researchers who then request object storage access on individual sandboxes. By the end, a sandbox can run `aws s3` commands or Boto3 code against your buckets using credentials that expire on their own.

<Note>
  CoreWeave sandboxes are in public preview. For access, contact your CoreWeave account team, [CoreWeave Support](https://cloud.coreweave.com/contact), or email [support@coreweave.com](mailto:support@coreweave.com).
</Note>

## How it works

The sandbox gateway issues each sandbox a JSON Web Token (JWT) from the fixed CoreWeave issuer `https://oidc.cwsandbox.com`. AI Object Storage validates that token against a workload federation configuration in your organization, derives a role identity from the token's `iss` and `sub` claims, and returns temporary credentials scoped by your access policies.

Three pieces of configuration have to line up:

| Configuration                   | Where it lives                                  | What it does                                                                                                         |
| ------------------------------- | ----------------------------------------------- | -------------------------------------------------------------------------------------------------------------------- |
| OIDC workload federation config | Cloud console, under **Organization** > **IAM** | Tells AI Object Storage to trust tokens from `https://oidc.cwsandbox.com`. Produces a **Config ID**.                 |
| Organization access policies    | AI Object Storage                               | Grant the derived sandbox role permission to exchange tokens and to act on buckets.                                  |
| Sandbox WIF configuration       | Sandbox control plane                           | Points the sandbox control plane at the Config ID and caps which buckets and permission level sandboxes may request. |

The derived role identity follows the format `role/https://oidc.cwsandbox.com:user:[USER-ID]`, where `[USER-ID]` is the CoreWeave user ID of the caller whose API access token started the sandbox. Because the subject varies per user, access policies either list each user's role or match the whole issuer with a trailing wildcard. See [Grant permissions to the sandbox role](#step-2-grant-permissions-to-the-sandbox-role).

Inside the sandbox, no credential-fetching process of your own is needed. The AWS SDK's container credentials provider reads the mounted token, calls the CoreWeave credential endpoint, and refreshes the credentials before they expire.

## Before you begin

The administrator steps require the following:

* A CoreWeave organization with AI Object Storage enabled, and at least one bucket. To create one, see [Create a bucket](/products/storage/object-storage/buckets/create-bucket).
* Administrator privileges for your organization: the **IAM Admin** and **Object Storage Admin** roles, or equivalent legacy access.
* The `SANDBOX_ADMIN` action in Identity and Access Management (IAM), which lets you set the sandbox WIF configuration. Grant it on the [Access Policies](https://console.coreweave.com/organization/iam/access-policies) page in the cloud console.
* Your CoreWeave organization ID, shown on the [Settings](https://console.coreweave.com/account/settings) page in the cloud console.
* A CoreWeave API access token. Generate one on the [Tokens](https://console.coreweave.com/tokens) page and copy the **Token Secret** value. For more information, see [Manage API access tokens](/security/authn-authz/manage-api-access-tokens).

Export the token so the `curl` examples on this page can read it:

```bash theme={"system"}
export TOKEN="[YOUR-ACCESS-TOKEN]"
```

For the researcher steps, you need a working sandbox setup. If you don't have one, follow [Get started with CoreWeave sandboxes](/products/sandboxes/get-started) first.

## Step 1: Create an OIDC workload federation config

Register the sandbox issuer with your organization so that AI Object Storage accepts sandbox tokens.

1. In the cloud console, go to the [Workload Federation](https://console.coreweave.com/organization/iam/workload-federation/oidc) page.

2. Click **Create OIDC configuration**.

3. Provide the following values:

   * **Name**: a name that identifies this configuration, such as `coreweave-sandboxes`.
   * **Issuer URL**: `https://oidc.cwsandbox.com`
   * **Client ID (Audience)**: `https://oidc.cwsandbox.com`
   * **Description** (Optional): a description of this configuration.

4. Click **Create**.

<Warning>
  The issuer host has no hyphen. Sandbox tokens carry the issuer claim `https://oidc.cwsandbox.com`, and token validation compares that value exactly, so a configuration created against `https://oidc.cw-sandbox.com` never matches.
</Warning>

After the configuration is created, the Workload Federation page shows its **Config ID**. Copy that value: [Step 3](#step-3-register-the-wif-configuration-with-the-sandbox-control-plane) needs it.

At this point AI Object Storage can validate sandbox tokens, but the resulting role has no permissions yet.

## Step 2: Grant permissions to the sandbox role

Organization access policies decide what a sandbox can do with the credentials it receives. Two grants are required, and they must be separate statements because the token exchange action is global while the S3 actions are scoped to buckets.

The following policy grants the token exchange. The `cwobject:CreateAccessKeyOIDC` action operates on all resources, so its statement uses `"resources": ["*"]`. Replace `[USER-ID]` with the CoreWeave user ID whose API access token starts sandboxes:

```json highlight={9-14} theme={"system"}
{
  "policy": {
    "version": "v1alpha1",
    "name": "allow-sandbox-oidc-key-creation",
    "statements": [
      {
        "name": "allow-create-access-key-from-sandbox-oidc",
        "effect": "Allow",
        "actions": [
          "cwobject:CreateAccessKeyOIDC"
        ],
        "resources": ["*"],
        "principals": [
          "role/https://oidc.cwsandbox.com:user:[USER-ID]"
        ]
      }
    ]
  }
}
```

To cover every user in your organization without listing each subject, principals accept a trailing wildcard: `role/https://oidc.cwsandbox.com:*`. Because the issuer portion still has to match exactly, this grant applies only to sandbox tokens, not to other identity providers you federate.

Next, grant the credentials permission to act on buckets. Replace `[BUCKET-NAME]` with the bucket your sandboxes use:

```json highlight={16-19} theme={"system"}
{
  "policy": {
    "version": "v1alpha1",
    "name": "sandbox-read-write-bucket",
    "statements": [
      {
        "name": "allow-sandbox-rw-bucket",
        "effect": "Allow",
        "actions": [
          "s3:Get*",
          "s3:List*",
          "s3:Put*",
          "s3:DeleteObject"
        ],
        "resources": [
          "[BUCKET-NAME]",
          "[BUCKET-NAME]/*"
        ],
        "principals": [
          "role/https://oidc.cwsandbox.com:*"
        ]
      }
    ]
  }
}
```

Without the second policy, the token exchange succeeds and every bucket operation is denied. For the full schema, see [Organization access policies](/products/storage/object-storage/auth-access/organization-policies/about).

With both statements in place, the sandbox role can exchange its token for credentials and act on the buckets you listed.

Organization access policies are enough for most deployments. Add [bucket access policies](/products/storage/object-storage/auth-access/bucket-access/bucket-policies) only when you need cross-organization access or want to narrow access using the token's claims. In a bucket policy, the same principal takes its full ARN form, `arn:aws:iam::[ORG-ID]:role/https://oidc.cwsandbox.com:*`, and claims are referenced as condition keys named `oidc:[ORG-ID]:[CLAIM]`. See [Token claims](#token-claims) for the claims a sandbox token carries.

## Step 3: Register the WIF configuration with the sandbox control plane

Tell the sandbox control plane which workload federation configuration to mint tokens against, and set the ceiling on what any sandbox in your organization may request. There is one configuration per organization, and the request is an idempotent upsert.

Replace `[WIF-CONFIG-ID]` with the Config ID from [Step 1](#step-1-create-an-oidc-workload-federation-config) and `[BUCKET-NAME]` with each bucket you want to allow:

```bash title="Set the sandbox WIF configuration" theme={"system"}
curl -X PUT "https://api.coreweave.com/v1beta2/object-storage/wif-config" \
  -H "Authorization: Bearer $TOKEN" \
  -H "Content-Type: application/json" \
  -d '{
    "wifConfigId": "[WIF-CONFIG-ID]",
    "enabled": true,
    "allowedBuckets": ["[BUCKET-NAME]"],
    "maxPermission": "OBJECT_STORAGE_PERMISSION_READ_WRITE"
  }'
```

The fields behave as follows:

| Field            | Required | Description                                                                                                                   |
| ---------------- | -------- | ----------------------------------------------------------------------------------------------------------------------------- |
| `wifConfigId`    | Yes      | The Config ID from the cloud console workload federation configuration.                                                       |
| `maxPermission`  | Yes      | The highest access level any sandbox may request: `OBJECT_STORAGE_PERMISSION_READ` or `OBJECT_STORAGE_PERMISSION_READ_WRITE`. |
| `enabled`        | No       | Defaults to `true`. Set it to `false` to turn off object storage access without deleting the configuration.                   |
| `allowedBuckets` | No       | Bucket names sandboxes may request. An empty list allows all buckets.                                                         |

The organization comes from the authenticated caller, so the request body has no organization field, and callers can only manage their own organization's configuration.

Confirm the configuration was stored:

```bash title="Get the sandbox WIF configuration" theme={"system"}
curl "https://api.coreweave.com/v1beta2/object-storage/wif-config" \
  -H "Authorization: Bearer $TOKEN"
```

To stop issuing new object storage credentials, delete the configuration:

```bash title="Delete the sandbox WIF configuration" theme={"system"}
curl -X DELETE "https://api.coreweave.com/v1beta2/object-storage/wif-config" \
  -H "Authorization: Bearer $TOKEN"
```

Deleting the configuration rejects new sandbox requests that ask for object storage access. Sandboxes that are already running keep working until their token expires.

For the per-field reference, see [Set object storage WIF config](/products/sandboxes/reference/control-plane-api) in the control plane API reference.

## Step 4: Request object storage access when you start a sandbox

Steps 1 through 3 are one-time administrator setup for the organization. The remaining steps are what a researcher does for each sandbox that needs object storage.

Object storage access is opt-in per sandbox. Add `objectStorageAccess` to the start request, naming the buckets the sandbox needs and the permission level it requires:

```bash title="Start a sandbox with object storage access" highlight={7-12} theme={"system"}
curl -X POST "https://api.coreweave.com/v1beta2/sandboxes" \
  -H "Authorization: Bearer $TOKEN" \
  -H "Content-Type: application/json" \
  -d '{
    "containerImage": "[CONTAINER-IMAGE]",
    "command": "sleep",
    "args": ["3600"],
    "objectStorageAccess": {
      "buckets": ["[BUCKET-NAME]"],
      "permission": "OBJECT_STORAGE_PERMISSION_READ_WRITE"
    }
  }'
```

Both fields are constrained by the organization configuration from [Step 3](#step-3-register-the-wif-configuration-with-the-sandbox-control-plane). The `buckets` list must be a subset of `allowedBuckets`, and `permission` cannot exceed `maxPermission`. A request that asks for more than the organization allows is rejected, as is any request made while the organization has no active WIF configuration.

Requesting a narrower scope than the ceiling is worthwhile: a sandbox that only reads training data should ask for `OBJECT_STORAGE_PERMISSION_READ` even in an organization whose ceiling is read-write.

## Step 5: Use the credentials inside the sandbox

When a sandbox starts with `objectStorageAccess`, the control plane mounts its OIDC token and sets the environment variables that AWS SDKs use for [container credentials](https://docs.aws.amazon.com/sdkref/latest/guide/feature-container-credentials.html):

| Variable                                 | Value                                                                       |
| ---------------------------------------- | --------------------------------------------------------------------------- |
| `AWS_CONTAINER_CREDENTIALS_FULL_URI`     | `https://api.coreweave.com/v1/cwobject/temporary-credentials/oidc/[ORG-ID]` |
| `AWS_CONTAINER_AUTHORIZATION_TOKEN_FILE` | `/var/run/secrets/sandbox/storage-token/osa-token`                          |
| `AWS_ENDPOINT_URL_S3`                    | The AI Object Storage endpoint, such as `https://cwobject.com`              |

The token itself is a read-only file at `/var/run/secrets/sandbox/storage-token/osa-token`. You don't need to read it, and you shouldn't copy it out of the sandbox or pass it to another workload.

Your client library performs the exchange. Set the region for your buckets, then use any S3-compatible client. Replace `[AVAILABILITY-ZONE]` with the availability zone your buckets are in, such as `US-EAST-04A`:

```bash title="List objects from inside a sandbox" theme={"system"}
export AWS_REGION="[AVAILABILITY-ZONE]"

aws configure set s3.addressing_style virtual

aws s3 ls s3://[BUCKET-NAME]/
```

AI Object Storage requires virtual-hosted addressing. Path-style requests fail with `PathStyleRequestNotAllowed`.

Boto3 picks up the same environment variables, so no explicit credentials are needed. The following example lists objects in a bucket, reading the endpoint and region from the sandbox environment:

```python title="list_objects.py" theme={"system"}
import os

import boto3
from botocore.client import Config

boto_config = Config(
    region_name=os.environ['AWS_REGION'],
    s3={'addressing_style': 'virtual'}
)

s3 = boto3.client(
    's3',
    endpoint_url=os.environ['AWS_ENDPOINT_URL_S3'],
    config=boto_config
)

response = s3.list_objects_v2(Bucket=os.environ['BUCKET_NAME'])

for item in response.get('Contents', []):
    print(item['Key'], item['Size'])
```

Run it inside the sandbox, with `BUCKET_NAME` set to the bucket you granted:

```bash theme={"system"}
export BUCKET_NAME="[BUCKET-NAME]"

python list_objects.py
```

Successful output lists each object key and its size in bytes:

```text title="Example output" theme={"system"}
datasets/train/shard-00000.tar 268435456
datasets/train/shard-00001.tar 268435456
datasets/val/shard-00000.tar 67108864
```

<Note>
  Credential exchange needs SDK support for container credentials against a non-loopback host. Use `awscli` 2.33.2 or later, or `boto3` 1.42.5 or later. Older versions fail with `Unsupported host 'api.coreweave.com'`. Build these versions into your sandbox container image.
</Note>

## Token lifetimes

The sandbox OIDC token and the temporary credentials it buys expire on different schedules:

* **Sandbox OIDC token**: one hour by default, up to a maximum of 12 hours. The control plane mints it when the sandbox starts.
* **Temporary AI Object Storage credentials**: minted on demand from the token. The exchange response carries an `Expiration` timestamp, and the AWS SDK refreshes the credentials before that time without any action from your code.

A sandbox that outlives its OIDC token can no longer exchange it, and object storage operations then fail with permission errors. For long-running sandboxes, set `maxLifetimeSeconds` on the start request so the token covers the sandbox's full lifetime.

## Token claims

Sandbox object storage tokens carry the following claims. Reference them in bucket policy conditions as `oidc:[ORG-ID]:[CLAIM]`:

| Claim           | Description                                                                                                     |
| --------------- | --------------------------------------------------------------------------------------------------------------- |
| `iss`           | Always `https://oidc.cwsandbox.com`.                                                                            |
| `sub`           | `user:[USER-ID]`, the CoreWeave user that started the sandbox. Combined with `iss` to derive the role identity. |
| `aud`           | The audience configured on your workload federation configuration.                                              |
| `org_id`        | The CoreWeave organization that owns the sandbox.                                                               |
| `wif_config_id` | The workload federation Config ID the token was minted against.                                                 |
| `buckets`       | The buckets requested in `objectStorageAccess`.                                                                 |
| `permission`    | The permission level requested in `objectStorageAccess`.                                                        |
| `exp`           | Expiration time as a Unix timestamp.                                                                            |

## Troubleshooting

The following sections describe the failures you are most likely to see when setting up or using sandbox object storage access, and what to check for each one.

### The start request is rejected

If a start request with `objectStorageAccess` fails, check that:

* The organization has a WIF configuration with `enabled` set to `true`. Retrieve it with the Get request in [Step 3](#step-3-register-the-wif-configuration-with-the-sandbox-control-plane).
* Every bucket in the request appears in `allowedBuckets`, or `allowedBuckets` is empty.
* The requested `permission` does not exceed `maxPermission`.

### Credential exchange returns permission denied

If the first S3 operation fails with a permission error, the exchange itself was refused. Check that:

* An organization access policy grants `cwobject:CreateAccessKeyOIDC` on `"resources": ["*"]` to the sandbox role, in its own statement.
* The policy principal matches the derived role exactly, including the `user:` prefix on the subject. The principal is `role/https://oidc.cwsandbox.com:user:[USER-ID]`, not `role/https://oidc.cwsandbox.com:[USER-ID]`.
* The workload federation configuration in the cloud console is active and its issuer URL is `https://oidc.cwsandbox.com`, with no hyphen.
* The sandbox OIDC token has not expired. Restart the sandbox to mint a fresh one.

### Credential exchange succeeds but S3 operations return AccessDenied

The exchange worked and the resulting credentials lack bucket permissions. Confirm that an organization access policy grants the needed `s3:` actions on the short-form bucket resources (`[BUCKET-NAME]` and `[BUCKET-NAME]/*`) to the sandbox role. If bucket access policies also apply, check them for `Deny` statements, which override any `Allow`.

### The credential request times out

Sandboxes on a profile with allowlist-only egress must be able to reach `https://api.coreweave.com`. Without that route, the credential fetch times out and the first S3 operation fails. Add the host to the profile's egress allowlist. See [Configure a profile](/products/sandboxes/profiles/configure).

### The workload creates a large number of access keys

Each exchange creates a short-lived access key. Let the SDK's credential provider cache and refresh the credentials for the lifetime of your process instead of constructing a new client per work item. Minting keys per request generates large volumes of keys for no benefit.

## Related pages

* [Workload Identity Federation for AI Object Storage](/products/storage/object-storage/auth-access/workload-identity-federation/about): how WIF works across CoreWeave.
* [Use Workload Identity Federation with OIDC](/products/storage/object-storage/auth-access/workload-identity-federation/use-oidc-tokens): the general OIDC federation guide, for identity providers other than sandboxes.
* [Organization access policies](/products/storage/object-storage/auth-access/organization-policies/about): the policy schema used in [Step 2](#step-2-grant-permissions-to-the-sandbox-role).
* [Sandboxes architecture](/products/sandboxes/architecture): where the gateway and runner sit in the sandbox request path.
