/add-harness-package
Guide for adding new AI SDK harness packages. Use when creating a new @ai-sdk/harness-<name> package that adapts a coding-agent runtime to HarnessV1.
$ npx -y skills add vercel/ai --skill add-harness-package --agent claude-codeHow it fires
How this skill gets triggered: by you, by Claude, or both.
- Fires itselfAuto-invocation. Claude auto-loads it when your prompt matches the work.Auto-invocation is when the right skill fires by itself at the right moment, driven by a FLOW.md router and a hook, instead of you invoking it by name. It is the difference between a skill being installed and a skill actually getting used.Read the full definition →
- You can call itInvoke it directly when you want it.
- Slash command
/add-harness-package
Context preview
The summary Claude sees to decide when to auto-load this skill.
Guide for adding new AI SDK harness packages. Use when creating a new @ai-sdk/harness-<name> package that adapts a coding-agent runtime to HarnessV1.
SKILL.md
add-harness-package.SKILL.mdname: add-harness-package
description: Guide for adding new AI SDK harness packages. Use when creating a new @ai-sdk/harness-<name> package that adapts a coding-agent runtime to HarnessV1.
metadata:
internal: true
Adding a New Harness Package
This guide covers creating a new `@ai-sdk/harness-<name>` package for an agent harness.
A harness can be **host-driven**, where the runtime runs in the host process and uses the sandbox remotely, or **bridge-backed**, where a small bridge runs inside the sandbox because the runtime needs local access to the sandbox filesystem or process environment. Prefer host-driven when the runtime supports it.
First-Party vs Third-Party Harnesses
- **Third-party packages**: Any runtime can publish an external harness package.
- **First-party `@ai-sdk/harness-<name>` packages**: Create an issue first to discuss whether the runtime belongs in this repo.
Reference Example
See https://github.com/vercel/ai/pull/16255/changes for a complete example of adding a new harness.
Harness Architecture
The AI SDK uses a layered harness architecture following the adapter pattern:
1. **Harness specification** (`@ai-sdk/harness`): Defines interfaces like `HarnessV1` and `HarnessV1Session` 2. **Utilities** (`@ai-sdk/harness/utils`): Shared code for implementing harnesses 3. **Harness implementations** (`@ai-sdk/harness-<name>`): Concrete adapters for harnesses 4. **Harness agent** (`@ai-sdk/harness/agent`): The high-level user-facing `HarnessAgent` API
Step-by-Step Guide
1. Create Package Structure
Create `packages/harness-<name>` with this baseline structure:
packages/harness-<name>/
├── src/
│ ├── index.ts
│ ├── <name>-harness.ts
│ ├── <name>-harness.test.ts
│ └── <name>-auth.ts # if the runtime needs auth resolution
├── package.json
├── tsconfig.json
├── tsconfig.build.json
├── tsup.config.ts
├── turbo.json
├── vitest.node.config.js
└── README.md
If the runtime must execute inside the sandbox, add bridge files as well:
src/
├── <name>-bridge-protocol.ts
├── <name>-bridge-protocol.test.ts
└── bridge/
├── index.ts
├── package.json
└── pnpm-lock.yamlAdd a `CHANGELOG.md` containing just the package heading (`# @ai-sdk/harness-<name>`). Every package is required to have one.
2. Configure package.json
Use existing harness packages as the source of truth for scripts, exports, repository metadata, and publish settings.
Required package basics:
- `"name": "@ai-sdk/harness-<name>"`
- `"type": "module"`
- `"version": "0.0.0"` (starting point for new packages)
- `"license": "Apache-2.0"`
- `"sideEffects": false`
- dependency on `@ai-sdk/harness` via `workspace:*`
- dependency on `@ai-sdk/provider-utils` via `workspace:*` when using sandbox/auth/schema utilities
- runtime SDK/CLI dependencies required by the harness
- dev dependencies matching existing harness packages
- `"engines": { "node": ">=22" }`
For bridge packages, add any bridge asset copy step required for files under `src/bridge/`.
Bridge dependency rules (bridge-backed harnesses):
- The bridge's runtime deps live in `src/bridge/package.json` (installed in-sandbox at bootstrap), not the main package.json. After changing them, regenerate `src/bridge/pnpm-lock.yaml` with `pnpm --dir packages/harness-<name>/src/bridge install --lockfile-only --ignore-workspace` (runnable from the repo root).
- For every third-party import in `src/bridge/`, keep three things in sync: the import, the `external` array in `tsup.config.ts`, and the dep in `src/bridge/package.json`. A missing entry shows up only at sandbox runtime as a module-resolution error.
- Include packages the runtime _lazily_ imports — e.g. provider SDKs (`@anthropic-ai/sdk`, `openai`) resolved from the model id at runtime — even though nothing imports them directly. These fail only when a model of that provider is actually used.
- Match shared dependency versions (transport, schema, tooling, runtime SDKs) to what the other harness packages currently use — copy from a sibling package rather than choosing your own pins. Stale pins drift from security patches and can desync from the shared bridge runtime; check the current versions at creation time.
3. Create TypeScript, Build, and Test Configs
Copy the nearest existing harness package config files and adjust paths/package names:
- `tsconfig.json`
- `tsconfig.build.json`
- `tsup.config.ts`
- `turbo.json`
- `vitest.node.config.js`
Harness packages currently use Node tests only unless the implementation has a specific reason to add another runtime.
4. Implement the Harness Adapter
Export a factory from `<name>-harness.ts` and re-export it from `src/index.ts`.
Use the architecture doc for contract details. At implementation time, verify:
- return a `HarnessV1` with `specificationVersion: 'harness-v1'`;
- use a stable kebab-case `harnessId`;
- expose adapter-native built-in tools through `builtinTools`;
- keep construction synchronous and side-effect free;
- use `startOpts.sandboxSession` and `startOpts.sessionWorkDir`; never create a separate sandbox;
- throw `HarnessCapabilityUnsupportedError` from the method that needs an unsupported runtime capability;
- don't hardcode a default model unless the runtime technically requires one — some underlying SDKs have no default of their own. Otherwise pass the model only when the consumer configured one and leave the original SDK's default untouched; keep the session's `modelId` consistent with what's actually sent (don't report a model the bridge silently overrode);
- handle the `tools` and `instructions` that `doPromptTurn`/`doContinueTurn` may receive: if the runtime can't take custom `tools`, throw `HarnessCapabilityUnsupportedError` so it's obvious rather than silently dropped; if it has no native `instructions` input, prepend them to the first user message (the Codex/Claude Code workaround);
- quote interpolated paths (`workDir`, bridge-state dir, …) when building shel
Read more
name: add-harness-package description: Guide for adding new AI SDK harness packages. Use when creating a new @ai-sdk/harness-<name> package that adapts a coding-agent runtime to HarnessV1. metadata: internal: true
Adding a New Harness Package
This guide covers creating a new `@ai-sdk/harness-<name>` package for an agent harness.
A harness can be **host-driven**, where the runtime runs in the host process and uses the sandbox remotely, or **bridge-backed**, where a small bridge runs inside the sandbox because the runtime needs local access to the sandbox filesystem or process environment. Prefer host-driven when the runtime supports it.
First-Party vs Third-Party Harnesses
- **Third-party packages**: Any runtime can publish an external harness package.
- **First-party `@ai-sdk/harness-<name>` packages**: Create an issue first to discuss whether the runtime belongs in this repo.
Reference Example
See https://github.com/vercel/ai/pull/16255/changes for a complete example of adding a new harness.
Harness Architecture
The AI SDK uses a layered harness architecture following the adapter pattern:
1. **Harness specification** (`@ai-sdk/harness`): Defines interfaces like `HarnessV1` and `HarnessV1Session` 2. **Utilities** (`@ai-sdk/harness/utils`): Shared code for implementing harnesses 3. **Harness implementations** (`@ai-sdk/harness-<name>`): Concrete adapters for harnesses 4. **Harness agent** (`@ai-sdk/harness/agent`): The high-level user-facing `HarnessAgent` API
Step-by-Step Guide
1. Create Package Structure
Create `packages/harness-<name>` with this baseline structure:
packages/harness-<name>/ ├── src/ │ ├── index.ts │ ├── <name>-harness.ts │ ├── <name>-harness.test.ts │ └── <name>-auth.ts # if the runtime needs auth resolution ├── package.json ├── tsconfig.json ├── tsconfig.build.json ├── tsup.config.ts ├── turbo.json ├── vitest.node.config.js └── README.md
If the runtime must execute inside the sandbox, add bridge files as well:
src/
├── <name>-bridge-protocol.ts
├── <name>-bridge-protocol.test.ts
└── bridge/
├── index.ts
├── package.json
└── pnpm-lock.yamlAdd a `CHANGELOG.md` containing just the package heading (`# @ai-sdk/harness-<name>`). Every package is required to have one.
2. Configure package.json
Use existing harness packages as the source of truth for scripts, exports, repository metadata, and publish settings.
Required package basics:
- `"name": "@ai-sdk/harness-<name>"`
- `"type": "module"`
- `"version": "0.0.0"` (starting point for new packages)
- `"license": "Apache-2.0"`
- `"sideEffects": false`
- dependency on `@ai-sdk/harness` via `workspace:*`
- dependency on `@ai-sdk/provider-utils` via `workspace:*` when using sandbox/auth/schema utilities
- runtime SDK/CLI dependencies required by the harness
- dev dependencies matching existing harness packages
- `"engines": { "node": ">=22" }`
For bridge packages, add any bridge asset copy step required for files under `src/bridge/`.
Bridge dependency rules (bridge-backed harnesses):
- The bridge's runtime deps live in `src/bridge/package.json` (installed in-sandbox at bootstrap), not the main package.json. After changing them, regenerate `src/bridge/pnpm-lock.yaml` with `pnpm --dir packages/harness-<name>/src/bridge install --lockfile-only --ignore-workspace` (runnable from the repo root).
- For every third-party import in `src/bridge/`, keep three things in sync: the import, the `external` array in `tsup.config.ts`, and the dep in `src/bridge/package.json`. A missing entry shows up only at sandbox runtime as a module-resolution error.
- Include packages the runtime _lazily_ imports — e.g. provider SDKs (`@anthropic-ai/sdk`, `openai`) resolved from the model id at runtime — even though nothing imports them directly. These fail only when a model of that provider is actually used.
- Match shared dependency versions (transport, schema, tooling, runtime SDKs) to what the other harness packages currently use — copy from a sibling package rather than choosing your own pins. Stale pins drift from security patches and can desync from the shared bridge runtime; check the current versions at creation time.
3. Create TypeScript, Build, and Test Configs
Copy the nearest existing harness package config files and adjust paths/package names:
- `tsconfig.json`
- `tsconfig.build.json`
- `tsup.config.ts`
- `turbo.json`
- `vitest.node.config.js`
Harness packages currently use Node tests only unless the implementation has a specific reason to add another runtime.
4. Implement the Harness Adapter
Export a factory from `<name>-harness.ts` and re-export it from `src/index.ts`.
Use the architecture doc for contract details. At implementation time, verify:
- return a `HarnessV1` with `specificationVersion: 'harness-v1'`;
- use a stable kebab-case `harnessId`;
- expose adapter-native built-in tools through `builtinTools`;
- keep construction synchronous and side-effect free;
- use `startOpts.sandboxSession` and `startOpts.sessionWorkDir`; never create a separate sandbox;
- throw `HarnessCapabilityUnsupportedError` from the method that needs an unsupported runtime capability;
- don't hardcode a default model unless the runtime technically requires one — some underlying SDKs have no default of their own. Otherwise pass the model only when the consumer configured one and leave the original SDK's default untouched; keep the session's `modelId` consistent with what's actually sent (don't report a model the bridge silently overrode);
- handle the `tools` and `instructions` that `doPromptTurn`/`doContinueTurn` may receive: if the runtime can't take custom `tools`, throw `HarnessCapabilityUnsupportedError` so it's obvious rather than silently dropped; if it has no native `instructions` input, prepend them to the first user message (the Codex/Claude Code workaround);
- quote interpolated paths (`workDir`, bridge-state dir, …) when building shel
The AI Toolkit for TypeScript. From the creators of Next.js, the AI SDK is a free open-source library for building AI-powered applications and agents
Repo: vercel/ai
Other skills on vercel-ai.
- /add-function-examples
Guide for adding new AI function examples, for testing specific features against the actual provider APIs.
Open skill - /add-provider-package
Guide for adding new AI provider packages to the AI SDK. Use when creating a new @ai-sdk/<provider> package to integrate an AI service into the SDK.
Open skill - /adr-skill
Create and maintain Architecture Decision Records (ADRs) optimized for agentic coding workflows. Use when you need to propose, write, update, accept/reject, deprecate, or supersede an ADR; bootstrap an adr folder and index; consult existing ADRs before implementing changes; or
Open skill - /capture-api-response-test-fixture
Capture API response test fixture.
Open skill - /develop-ai-functions-example
Develop examples for AI SDK functions. Use when creating, running, or modifying examples under examples/ai-functions/src to validate provider support, demonstrate features, or create test fixtures.
Open skill - /list-npm-package-content
List the contents of an npm package tarball before publishing. Use when the user wants to see what files are included in an npm bundle, verify package contents, or debug npm publish issues.
Open skill

