---
title: fx harness
description: >-
  The fx harness runs Vercel's fx agent in the sandbox on Vercel AI Gateway or
  an OpenAI API key and records its events.
---
> ## Documentation Index
> Fetch the complete documentation index at: https://docs.reeval.ai/llms.txt
> Use this file to discover all available pages before exploring further.

`fx()` runs Vercel's fx agent (`fx acp`) in the sandbox, on Vercel AI Gateway or on OpenAI's Chat Completions API, picked by the model id. The turn runs in fx's `full-access` mode, so no reviewer model checks each action. For more information about the sandbox, see [Choose a sandbox](/configuration/sandboxes).

## `AI_GATEWAY_API_KEY` or `OPENAI_API_KEY`

The model id picks the key:

| `model` | Key | Gateway |
| :--- | :--- | :--- |
| A gateway id, such as `anthropic/claude-sonnet-5` | `AI_GATEWAY_API_KEY` | `vercel()` only |
| A bare OpenAI id, such as `gpt-5.5` | `OPENAI_API_KEY` | `direct()`, or `vercel()` as `openai/<id>` |

`fx()` reads the key from the environment or the `.env.local` file. A run exits with code 2 when the key is unset, or when the value contains whitespace or a line break. A gateway id with no `vercel()` in the config's `gateway` list fails at plan time with exit code 2.

On OpenAI, reeval brokers the key on `POST https://api.openai.com/v1/chat/completions` only, and a restricted egress policy allows `api.openai.com`. On Vercel AI Gateway, reeval brokers it on fx's model list and language-model calls at `ai-gateway.vercel.sh`, which a restricted egress policy allows.

fx ignores `HTTPS_PROXY`, so it sends its model calls to a relay on `127.0.0.1:47823` in the sandbox, which sends them on through the egress gateway.

When the API rejects the key, the attempt error begins with `The API rejected <KEY>: set a valid key in the environment or .env.local`.

For more information about keeping API keys on the host, see [Keep API keys on the host](/configuration/environments/secrets#keep-api-keys-on-the-host).

For more information about the variables, see [`AI_GATEWAY_API_KEY`](/reference/environment-variables#aigatewayapikey) and [`OPENAI_API_KEY`](/reference/environment-variables#openaiapikey).

## `fx()`

`fx()` is exported from `{{ pkg }}/harness`. The `reeval.config.ts` file passes it as the `harness` option:

```ts title="reeval.config.ts"
import { defineConfig } from '{{ pkg }}'
import { direct, vercel } from '{{ pkg }}/gateway'
import { fx } from '{{ pkg }}/harness'

export default defineConfig({
  gateway: [vercel(), direct()],
  harness: fx({ model: 'anthropic/claude-sonnet-5' }),
})
```

`model` is required, `fx()` takes no `effort`, and an unknown option fails at plan time with exit code 2. For what `model` takes, see [Harness factory options](/reference/options#harness-factory-options).



In the sandbox, fx runs with a private home, whose `settings.json` file turns session titles off, so the run's model is the only one called. Auto-upgrade and sound are off.

For more information about model ids, see [Set the agent's model](/configuration/agents/model). For rules, skills, MCP servers, usage, served models, and web events, see [Harness behavior](/reference/options#harness-behavior).

## `plugins`

fx has no plugins of its own. reeval adds each plugin's skills to the home skills directory and passes its MCP servers over ACP with the environment's.

[//]: # (generated:harness-plugins:fx)

- Takes `skills` and `mcp`, and refuses a plugin that keeps `agents`, `commands`, `hooks` and `rules`: narrow it with `only`, or leave it out of the cell.

[//]: # (/generated:harness-plugins:fx)

For more information about plugins, see [Environment helpers reference](/reference/environment-helpers#pluginlocal).
