# Architecture
Source: https://docs.director.run/concepts/architecture
Understand the main components of the middleware.
Director is a service that sits between your AI agents and MCP servers. It acts as a middleware for organizing and managing MCP capabilities. It's transparent to clients, requiring no additional tokens or configuration changes.
## Core Concepts
### Playbooks
A **playbook** is a set of tools, prompts, and configuration that gives your AI agent new skills. Think of playbooks as portable, declarative skill sets that can be:
* Shared across teams via version control (YAML files)
* Connected to multiple clients (Claude, Cursor, VSCode) with 1-click
* Configured to include only the tools needed for specific tasks
* Enforced declaratively (like Terraform for AI agents)
### Gateway
The `Gateway` implements a proxy pattern in order to:
* Aggregate multiple MCP servers into a single playbook endpoint
* Support all MCP transports (HTTP Streamable, Stdio, SSE)
* Provide tool filtering to preserve context
* Offer unified OAuth for centralized authentication
### Client Integration
Director provides multiple ways to connect MCP clients:
* **1-Click Integration**: Automatically configure Claude, Cursor, or VSCode via the `ClientConfigurator`
* **Manual Integration**: Use standard MCP connection details for any MCP-compliant client
* **Declarative Mapping**: Define client-to-playbook connections in config that are enforced on startup
## Management Interfaces
Director can be managed through multiple interfaces:
* [CLI](../concepts/cli): Primary management tool (npm installable) - `director serve`, `director create`, etc.
* [Studio](../concepts/studio): Web interface for visual playbook and server management
* **SDK**: Programmatic control via TypeScript SDK for advanced use cases
* **Config File**: Direct YAML editing at `~/.director/director.config.yaml`
## Architecture Components
* **Gateway**: Core service that runs the playbooks and serves MCP clients
* **Controller**: HTTP API (TRPC) for dynamic playbook management
* **ClientConfigurator**: Automates client connection setup without manual JSON editing
* **Registry**: Discover and add MCP servers from the community registry
# CLI Reference
Source: https://docs.director.run/concepts/cli
The CLI, along with the [Studio](./studio), are the primary ways to interact with director. The CLI is distributed as a standalone package, and can be installed via [npm](https://www.npmjs.com/package/@director.run/cli).
# Installation
```bash theme={null}
$ curl -LsSf https://director.run/install.sh | sh
```
# Usage
```bash theme={null}
$ director --help
Playbooks for your AI agent
USAGE
director [subcommand] [flags]
CORE COMMANDS
quickstart Start the gateway and open the studio in your browser
serve Start the web service
studio Open the UI in your browser
ls List playbooks
get [serverName] Show playbook details
auth Authenticate a server
create Create a new playbook
destroy Delete a playbook
connect [options] Connect a playbook to a MCP client
disconnect [options] Disconnect a playbook from an MCP client
add [options] Add a server to a playbook
remove Remove a server from a playbook
update [serverName] [options] Update playbook attributes
http2stdio Proxy an HTTP connection (sse or streamable) to a stdio stream
env [options] Print environment variables
status Get the status of the director
REGISTRY
registry ls List all available servers in the registry
registry get Get detailed information about a registry item
registry readme Print the readme for a registry item
MCP
mcp list-tools List tools on a playbook
mcp get-tool Get the details of a tool
mcp call-tool [options] Call a tool on a playbook
PROMPTS
prompts ls List all prompts for a playbook
prompts add Add a new prompt to a playbook
prompts edit Edit an existing prompt
prompts remove Remove a prompt from a playbook
prompts get Show the details of a specific prompt
FLAGS
-V, --version output the version number
EXAMPLES
$ director create my-playbook Create a new playbook
$ director add my-playbook --entry fetch Add a server to a playbook
$ director connect my-playbook --target claude Connect my-playbook to claude
```
# Examples
## Start the gateway
```bash theme={null}
$ director serve
_ _ _
| (_) | |
__| |_ _ __ ___ ___| |_ ___ _ __
/ _' | | '__/ _ \/ __| __/ _ \| '__|
| (_| | | | | __/ (__| || (_) | |
\__,_|_|_| \___|\___|\__\___/|_|
[18:16:21] INFO (Gateway): starting director gateway
[18:16:21] INFO (Gateway): director gateway running on port 3673
```
## Create a playbook
```bash theme={null}
$ director create my-first-playbook
playbook my-first-playbook created
```
## Add a server to the playbook
```bash theme={null}
$ director add my-first-playbook --entry fetch
adding fetch to my-first-playbook
✔ Entry fetched.
✔ Registry entry fetch added to my-first-playbook
```
## Connect the playbook to a client
```bash theme={null}
# connect the playbook to Claude automatically
$ director connect my-first-playbook -t claude
[18:19:06] INFO (client-configurator/claude): reading config from /Users/barnaby/Library/Application Support/Claude/claude_desktop_config.json
[18:19:06] INFO (client-configurator/claude): installing my-first-playbook
[18:19:06] INFO (client-configurator/claude): writing config to /Users/barnaby/Library/Application Support/Claude/claude_desktop_config.json
[18:19:06] INFO (client-configurator/claude): restarting claude
[18:19:06] INFO (restartApp): restarting Claude...
[18:19:08] INFO (restartApp): Claude has been restarted
undefined
# print the manual connection details
$ director connect my-first-playbook
--------------------------------
Connection Details for 'my-first-playbook'
--------------------------------
Note: if you'd like to connect to a client automatically, run:
director connect my-first-playbook --target
HTTP Streamable: http://localhost:3673/my-first-playbook/mcp
HTTP SSE: http://localhost:3673/my-first-playbook/sse
Stdio: {
"command": "npx",
"args": [
"-y",
"@director.run/cli",
"http2stdio",
"http://localhost:3673/my-first-playbook/mcp"
],
"env": {
"LOG_LEVEL": "silent"
}
}
```
## Get the details of a playbook
```bash theme={null}
# list all the playbooks
$ director ls
┌──────────────────┬──────────────────┬────────────────────────────────────────────┐
│ id │ name │ path │
│ my-first-playbook │ my-first-playbook │ http://localhost:3673/my-first-playbook/mcp │
└──────────────────┴──────────────────┴────────────────────────────────────────────┘
# get the details of a single playbook
$ director get my-first-playbook
id=my-first-proxy
name=my-first-proxy
┌───────┬───────────┬──────────────────────┐
│ name │ transport │ url/command │
│ fetch │ stdio │ uvx mcp-server-fetch │
└───────┴───────────┴──────────────────────┘
```
# Configuration Files
Source: https://docs.director.run/concepts/configuration
Learn about Director's configuration files.
Director doesn't use a database, everything is stored in a `director.config.yaml` file. The easiest way to manage this file is via the [Studio UI](https://studio.director.run) or the [CLI](../concepts/cli). But you can of course edit it manually.
*Note: If you'd like to manually edit the configuration files, you'll need to make sure you restart the service for the changes to take effect.*
# Search Paths
Director will search for the configuration file in the following paths (in order):
* `./director.config.yaml`
* `~/.director/director.config.yaml`
# Configuration File Reference
## Example
Your configuration file is a YAML file that defines playbooks and client connections. Here's a example of how to structure it:
```yaml theme={null}
#
# Server config
#
server:
# Defaults to 3673
port: 1234
#
# Client <> Playbook mappings (enforced on startup)
#
clients:
cursor: [ demo ]
#
# Playbooks (MCP servers, prompts, etc.)
#
playbooks:
- id: demo
name: demo
description: A demonstration playbook
#
# Prompts
#
prompts:
- name: changelog
title: changelog
description: ""
body: "write a short changelog based on recent changes on the
director-run/director repository and the post it to to the slack
#general channel. Make sure the message will format correctly inside
of slack"
#
# MCP Servers
#
servers:
# GitHub server
- name: github
type: http
url: https://api.githubcopilot.com/mcp/
headers:
Authorization: Bearer
# This server is enabled
disabled: false
# Only include the tools you need
tools:
include:
- list_commits
- search_pull_requests
- get_latest_release
# Prompts from MCP server are disabled by default
prompts:
include: []
- name: slack
type: stdio
command: npx
args:
- -y
- "@modelcontextprotocol/server-slack"
env:
SLACK_TEAM_ID:
SLACK_BOT_TOKEN:
SLACK_CHANNEL_IDS:
# This server is enabled
disabled: false
# Only include the tools you need
tools:
include:
- slack_list_channels
- slack_post_message
# Prompts from MCP server are disabled by default
prompts:
include: []
```
## Server Configuration
By default, Director will start a server on port 3673. You can change this by setting the `port` option in the `server` section.
```yaml theme={null}
server:
port: 1234
```
## Client Connections
The `clients` section defines which playbooks are available to which MCP clients. This mapping is enforced on startup:
```yaml theme={null}
clients:
claude-code: [my-playbook, another-playbook]
cursor: [my-playbook]
vscode: [development-tools]
```
Supported client identifiers:
* `claude-code` - Claude Code (command-line tool)
* `claude` - Claude Desktop app
* `cursor` - Cursor IDE
* `vscode` - Visual Studio Code
## Playbooks
Each playbook supports the following fields:
* **id** (required): A unique identifier for the playbook
* **name** (required): The name of the playbook
* **description** (optional): The description of the playbook
* **servers** (optional): The MCP servers to include in the playbook
* **prompts** (optional): The prompts to include in the playbook
### Prompts
Prompts are used to invoke the playbook from a MCP client. Each prompt supports the following fields:
* **name** (required): The name of the prompt
* **title** (optional): The title of the prompt
* **description** (optional): The description of the prompt
* **body** (optional): The body of the prompt
### MCP Servers
MCP servers are used to provide the tools and prompts to the playbook. Each server supports the following fields:
* **name** (required): The name of the server
* **type** (required): The type of the server (either `stdio` or `http`).
* **url** (optional): The URL of the server (only for http servers)
* **headers** (optional): The headers to pass to the server (only for http servers)
* **command** (optional): The command to execute for stdio-based servers
* **args** (optional): The command-line arguments for stdio-based servers
* **env** (optional): The environment variables to pass to the server
* **disabled** (optional): Whether the server is disabled (default: false)
* **tools** (optional): The tools to include in the server
* **prompts** (optional): The prompts to include in the server
#### Tools
The `tools.include` option allows you to select only specific tools from an MCP server, which helps preserve context by limiting the available tool set:
```yaml theme={null}
servers:
- name: github
type: http
url: https://api.githubcopilot.com/mcp/
tools:
include: [create_pr, search_code] # Only expose these specific tools
```
This is particularly useful when:
* You want to limit capabilities for security reasons (e.g., read-only access)
* You need to preserve context by only exposing relevant tools for a specific task
* You want to prevent accidental use of destructive operations
#### Prompts
The `prompts.include` option allows you to select only specific prompts from an MCP server, which helps preserve context by limiting the available prompt set:
```yaml theme={null}
servers:
- name: github
prompts:
include: [create_pr, search_code] # Only expose these specific prompts
```
# Registry
Source: https://docs.director.run/concepts/registry
The registry is a collection of servers that are available to be used in the Gateway. It is fully [open source](https://github.com/director-run/director/tree/main/apps/registry) and does not require authentication. We are currently prioritising other parts of director until the official [MCP Registry](https://github.com/modelcontextprotocol/registry) matures.
## Accessing the Registry
The best way to access the registry is in your browser via the [Studio](https://studio.director.run/library). Or alternatively, you can use the [CLI](./cli):
```bash theme={null}
# List all servers in the registry
director registry ls
# Adding a server from the registry
director add my-proxy --entry google-drive
```
## Adding a server to the Registry
We re-populate the registry on a regular basis from the [seed file](https://github.com/director-run/director/tree/main/apps/registry/src/seed/entries.ts). If you'd like to add a new entry, please add it to the file and open a PR. Here's an example of an entry:
```js theme={null}
{
name: "notion",
title: "Notion",
description:
"Connect to Notion API, enabling advanced automation and interaction capabilities for developers and tools.",
isOfficial: true,
icon: "https://registry.director.run/notion.svg",
homepage: "https://github.com/makenotion/notion-mcp-server",
transport: {
type: "stdio",
command: "npx",
args: ["-y", "@notionhq/notion-mcp-server"],
env: {
OPENAPI_MCP_HEADERS:
'{"Authorization": "Bearer ", "Notion-Version": "2022-06-28" }',
},
},
parameters: [
{
name: "notion-bearer-token",
description:
"Get a bearer token from [Notion Settings](https://www.notion.so/profile/integrations)",
type: "string",
required: true,
password: true,
},
],
}
```
# Studio
Source: https://docs.director.run/concepts/studio
The visual interface for managing and deploying MCP servers
The [Studio](https://studio.director.run), along with the [CLI](./cli), are the primary ways to interact with director. The easiest way to get started is to run `director quickstart` which will start the gateway and open the studio in your browser.
# Usage
```bash theme={null}
$ npm install -g @director.run/cli
$ director serve # start the gateway
$ director studio # open the studio - https://studio.director.run
```
# Running in Docker
Source: https://docs.director.run/experimental/docker
We currently have an experimental Docker image that you can use to run the gateway in a containerized environment.
**Note:** Automatic client connections are not supported in the Docker image. You will need to connect manually using the connect command.
```bash theme={null}
# Start the gateway container, listening on port 8080
# Mount the data directory to persist the gateway's state (config files, etc)
docker run \
-d -p 3673:8080 \
-v ./data:/root/.director \
--name director \
barnaby/director:latest
# Tail the logs
docker logs -f director
# Interact with the gateway using the CLI, on the host machine
director create my-playbook
director add my-playbook --entry fetch
director connect my-playbook # print connection details
```
# Quickstart
Source: https://docs.director.run/getting-started/quickstart
Getting started with Director
# Prerequisites
* Works on latest **MacOS** and **Ubuntu Linux**.
* `node` & `npm` for the CLI.
* `uvx` for most of the servers.
* [Claude](https://claude.ai/download), [Cursor](https://www.cursor.com/downloads) or [VSCode](https://code.visualstudio.com/download) installed. (if you'd like director to configure them automatically).
# Quickstart
The fastest way to try director is to use the install script. This will download the dependencies, run the latest version of director and open up the studio in your browser:
```bash theme={null}
curl -LsSf https://director.run/install.sh | sh
director quickstart
```
# Alternative Methods
## Installing Locally
If you'd like to install director locally, you can do so via `npm`.
```bash theme={null}
npm install -g @director.run/cli
director serve # start the gateway
director studio # open the studio in your browser
```
## Getting started with the CLI
If you'd like to set up director without going through the UI, you can do so via the CLI. For more detailed information, check out the [CLI Reference](../concepts/cli).
```bash theme={null}
npm install -g @director.run/cli
director serve # start the gateway
director create my-first-playbook # create a playbook
director add my-first-playbook --entry fetch # add the fetch server to the playbook
director connect my-first-playbook --target claude # connect the playbook to Claude
director connect my-first-playbook --target cursor # connect the playbook to Cursor
director connect my-first-playbook # print the manual connection details
```
# Welcome to Director!
Source: https://docs.director.run/getting-started/welcome
MCP Playbooks for AI agents
export const BetaBadge = () => {
return Director is in BETA and is not yet production ready.;
};
[Director](https://director.run) allows you to provide **playbooks** to AI Agents. A playbook is a set of **MCP tools**, **prompts** and **configuration** that give agents new **skills**. You can connect Claude, Cursor and VSCode in 1-click, or integrate manually through a single MCP endpoint.
Playbooks are portable, declarative YAML files that can easily be shared (or committed to version control). Director is local-first - installation and client integration takes 30 seconds. Director provides all the MCP management functionality you'd expect: tool filtering, logging, strong isolation, and unified OAuth.
## Key Features
#### 📚 Playbooks
Maintain sets of tools, prompts and config for different tasks or environments.
#### 🚀 1-Click Integration
Switch playbooks with a single click. Currently supports Claude Code, Claude Desktop, Cursor, VSCode.
#### 🔗 Shareable
Playbooks are flat files which can be shared or committed to version control easily.
#### 🏠 Local-First
Director is local-first, designed to easily run on your own machine or infrastructure.
#### 🔑 Unified OAuth
Connect to OAuth MCPs centrally, and use them across all of your agents.
#### 🎯 Tool Filtering
Select only the MCP tools that are required for the specific task, preserving context.
#### 📋 Declarative
Like terraform for AI agents, Director will enforce playbook to client mapping on startup.
#### 🔧 Flexibility
Configure director through the UI, by editing the config file, through the CLI or using the Typescript SDK.
#### 📊 Observability
Centralized JSON logging that allows you to understand exactly what your agent is doing.
#### 🔌 MCP Compliant
Just works with any MCP server or client. Up to date with the latest MCP spec.
#### MCP Registry
Discover and evaluate MCP servers securely. Browse available servers through the [Studio](./studio) or CLI.
# Contributing
Source: https://docs.director.run/project/contributing
Hello! We welcome any and all contributions and we'd be more than happy to help you get started with the codebase.
*Note: This project is under active development and the code will likely change pretty significantly. We'll update this message once that's complete!*
## Prerequisites
* [Bun](https://bun.sh/) (tested on 1.2.14+)
* [Docker](https://docker.com)
## Development workflow
### Setup Environment
```bash theme={null}
# clone the repo
git clone https://github.com/director-run/director
cd director
# Setup environment
bun install
docker compose up -d
./scripts/setup-development.sh
bun run test # confirm everything is working
# Teardown environment
docker compose down -v
```
### Running in Development
```bash theme={null}
# Running cli in development
bun cli serve # start the gateway
bun cli:dev # watches for changes
# Working with the registry
# Uncomment the lines in this file
vim apps/cli/.director/development/config.env
bun registry
bun cli registry populate # populate the development database with server entries
bun cli registry enrich # populate the development database with server entries
bun cli registry enrich-tools # populate the development database with server entries
```
### Running Tests
```bash theme={null}
# from project root
$ bun run lint
$ bun run typecheck
$ bun run test
# Automatically fix lint + prettier issues
$ bun run format
```
## Writing code changes
When you make code changes, please remember
1. **Add or update tests.** Every new feature or bug‑fix should come with test coverage that fails before your change and passes afterwards. 100 % coverage is not required, but aim for meaningful assertions.
2. **Document behaviour.** If your change affects user‑facing behaviour, update the `README.md` or the relevant `apps/docs` page.
3. **Keep commits atomic.** Each commit should compile and the tests should pass. This makes reviews and potential rollbacks easier.
## Opening a pull request
* Fill in the PR template (or include similar information) – **What? Why? How?**
* Run **all** checks locally (`bun run test && bun run lint && bun run check-types`). CI failures that could have been caught locally slow down the process.
* Make sure your branch is up‑to‑date with `main` and that you have resolved merge conflicts.
* Mark the PR as **Ready for review** only when you believe it is in a merge‑able state.
## Releasing `director`
```bash theme={null}
# Bump the version
$ ./scripts/print-version.sh
0.0.1
$ ./scripts/bump-version.sh 0.0.2
# Merge the PR in GitHub
$ git checkout main && git pull
$ ./scripts/release.sh
```
# null
Source: https://docs.director.run/project/roadmap
Below is our tentative roadmap for the next few months. We're actively working on the following:
#### Now
* **Secret Management**: Store secrets outside of the config file.
* **Hosting**: Support for hosting director instances in the cloud.
#### Next
* **ACL**: Support for ACLs to control access to the director instance.
* **Desktop Application**: OSX Desktop application for managing director instances.
#### Later
* **Plugins**: Support for plugins to extend the functionality of director.
If you'd like to contribute, please see the [contributing guide](./contributing).
# Client API Reference
Source: https://docs.director.run/sdk/client-configurator
The Client Configurator is a library that helps manage MCP Client configuration (checking client status, adding / removing servers, etc). Currently it supports Claude, Cursor & VSCode. The source code is available in [packages/client-configurator](https://github.com/director-run/director/tree/main/packages/client-configurator).
## API
```ts theme={null}
import { ConfiguratorTarget, getConfigurator } from "@director.run/client-configurator/index";
const claudeConfigurator = getConfigurator(ConfiguratorTarget.Claude);
// Is Claude installed on this machine?
await claudeConfigurator.isClientPresent();
await claudeConfigurator.isInstalled("my-proxy");
// Install an MCP server using a URL. If the client doesn't support HTTP, we use proxies.
await claudeConfigurator.install({
name: "my-proxy",
sseURL: "http://localhost:3673/my-proxy/sse",
streamableURL: "http://localhost:3673/my-proxy/streamable",
});
await claudeConfigurator.uninstall("my-proxy");
// Clear the config file. Useful for development
await claudeConfigurator.reset();
```
## Adding support for a new client
```ts theme={null}
// Create a new configurator in ./src/
export class NewClientConfigurator extends AbstractConfigurator {
// Implement the protected methods
}
```
# Gateway API Reference
Source: https://docs.director.run/sdk/gateway
The Gateway API allows you to start and manage a director instance programmatically. The source code is available in [apps/gateway](https://github.com/director-run/director/tree/main/apps/gateway).
## Examples
```typescript theme={null}
import { Gateway, GatewayConfig } from "@director.run/sdk";
// Start the gateway
const gateway = await Gateway.start({
config: await GatewayConfig.createMemoryBasedConfig({
defaults: {
server: {
port: 3673,
},
registry: {
url: "https://registry.director.run",
},
telemetry: {
writeKey: "",
enabled: false,
},
},
}),
baseUrl: "http://localhost:3673",
});
// Add a new playbook
await gateway.playbookStore.create({
name: "test",
servers: [
{
name: "notion",
type: "http",
url: "https://mcp.notion.com/mcp",
},
],
});
```
# MCP API Reference
Source: https://docs.director.run/sdk/mcp
The Director MCP API provides a simple interface for creating MCP servers, proxies and clients. It extends the official [Typescript SDK](https://github.com/modelcontextprotocol/typescript-sdk). The source code is available in [packages/mcp](https://github.com/director-run/director/tree/main/packages/mcp).
## API
```typescript theme={null}
import { HTTPClient } from "@director.run/sdk";
import { StdioClient } from "@director.run/sdk";
import { ProxyServer } from "@director.run/sdk";
import { serveOverSSE, serveOverStdio, serveOverStreamable } from "@director.run/sdk";
const proxy = new ProxyServer({
id: "my-proxy",
servers: [
new StdioClient({
name: "stdio-server",
command: "npx",
args: ["-y", "@director.run/cli", "http2stdio", "http://example.com/sse"],
}),
new HTTPClient({
name: "http-server",
// supports SSE & Streamable
url: "http://example.com/mcp",
}),
],
});
// Connect to the servers
await proxy.connectTargets();
// Helper methods to serve the proxy
await serveOverStreamable(proxy, 3673);
await serveOverSSE(proxy, 3674);
await serveOverStdio(proxy);
// Connect over Streamable or SSE
const httpClient = await HTTPClient.createAndConnectToHTTP(
"http://localhost:3673/mcp",
);
// Connect over Stdio
const stdioClient = await StdioClient.createAndConnectToStdio(
"server-command",
["server-args"],
);
// List the tools via HTTP client
console.log(await httpClient.listTools());
// List the tools via Stdio client
console.log(await stdioClient.listTools());
```