# How to Use the OpenWork Den Control Plane: Complete Developer Guide

> Master the OpenWork Den control plane with this developer guide. Learn to centralize organization management, discover MCP capabilities, and orchestrate AI agents via RESTful endpoints.

- Repository: [Different AI/openwork](https://github.com/different-ai/openwork)
- Tags: how-to-guide
- Published: 2026-08-21

---

**The OpenWork Den control plane is a Hono-based HTTP server that centralizes organization management, MCP capability discovery, and AI agent orchestration through RESTful endpoints protected by bearer tokens or API keys.**

The OpenWork Den serves as the backend control plane for the `different-ai/openwork` repository, enabling organizations to manage teams, members, model providers, and MCP-enabled capabilities from a single unified interface. This TypeScript-based server exposes a comprehensive REST API defined in [`ee/apps/den-api/src/app.ts`](https://github.com/different-ai/openwork/blob/main/ee/apps/den-api/src/app.ts) that handles authentication, health monitoring, and agent tool execution through a modular route architecture.

## Architecture Overview of the Den Control Plane

The Den control plane is built on the **Hono** web framework and structured as a scalable HTTP server that consolidates administrative and operational functions. At its core, the server defined in [`ee/apps/den-api/src/app.ts`](https://github.com/different-ai/openwork/blob/main/ee/apps/den-api/src/app.ts) orchestrates multiple subsystems through a centralized registration pattern.

The architecture implements **five primary responsibilities**:

1. **Health and Readiness Monitoring**: Exposes `/health` and `/ready` endpoints for service verification and database connectivity checks.
2. **Auto-Generated API Documentation**: Serves an OpenAPI specification at [`/openapi.json`](https://github.com/different-ai/openwork/blob/main//openapi.json) and interactive Swagger UI at `/docs`.
3. **Multi-Modal Authentication**: Supports session-based bearer tokens (`Authorization: Bearer`) and organization API keys (`x-api-key`), enforced by `sessionMiddleware`.
4. **Modular Route Groups**: Registers functional domains through dedicated functions like `registerOrgRoutes(app)`, `registerMcpRoutes(app)`, and `registerAgentMcpRoutes(app)`.
5. **MCP Capability Registry**: Maintains a hierarchical catalog of tools and plugins via [`src/mcp/capability-registry.ts`](https://github.com/different-ai/openwork/blob/main/src/mcp/capability-registry.ts), enabling agents to discover and execute capabilities dynamically.

Environment configuration is handled through [`load-env.js`](https://github.com/different-ai/openwork/blob/main/load-env.js), which injects variables such as `VITE_DEN_API_BASE_URL` and `OPENWORK_DEV_DEN_PROXY_TARGET` into the runtime `env` object used throughout the application.

## Starting a Local Den Instance

To spin up the control plane for local development, use the workspace development command from the repository root:

```bash
pnpm dev:worktree

```

For single worktree environments, the alternative command is:

```bash
pnpm dev

```

These commands launch both the Electron desktop application and the Den API server concurrently. The console output displays a banner indicating the control plane URL, typically `cdp=http://127.0.0.1:9223`, while the Den API itself listens on the port defined by the `OPENWORK_PORT` environment variable (defaulting to **8778**).

## Health Monitoring and Readiness Checks

Before integrating with the API, verify the server state using the dedicated health endpoints defined in [`ee/apps/den-api/src/app.ts`](https://github.com/different-ai/openwork/blob/main/ee/apps/den-api/src/app.ts).

To check basic service availability:

```bash
curl http://127.0.0.1:8778/health

```

This returns a JSON confirmation:

```json
{
  "ok": true,
  "service": "den-api",
  "version": "dev"
}

```

To verify database connectivity and full system readiness:

```bash
curl http://127.0.0.1:8778/ready

```

A healthy system responds with:

```json
{
  "ok": true,
  "service": "den-api",
  "checks": {
    "database": "ok"
  }
}

```

If the PostgreSQL instance is unreachable, the endpoint returns HTTP 503 with an error payload, enabling orchestrators to implement proper load balancing and failover logic.

## Authentication Methods

The Den control plane protects all `/v1/*` routes through `sessionMiddleware`, while leaving public routes (health checks and documentation) unauthenticated. Two authentication schemes are supported:

**Session Token Authentication**: Pass a user session token in the `Authorization` header using the Bearer scheme. Tokens are obtained through the authentication endpoints registered in [`ee/apps/den-api/src/routes/auth/index.ts`](https://github.com/different-ai/openwork/blob/main/ee/apps/den-api/src/routes/auth/index.ts).

**Organization API Key Authentication**: Provide an organization-scoped API key via the `x-api-key` header for service-to-service communication.

Example authenticated request using a bearer token:

```javascript
import fetch from 'node-fetch';

const token = 'YOUR_SESSION_TOKEN';
const resp = await fetch('http://127.0.0.1:8778/v1/org', {
  headers: { 'Authorization': `Bearer ${token}` }
});
const data = await resp.json();

```

## Exploring the API with OpenAPI and Swagger

The Den server automatically generates a complete OpenAPI 3.0 specification accessible at [`/openapi.json`](https://github.com/different-ai/openwork/blob/main//openapi.json). This document describes every endpoint, request/response schema (defined using Zod), and security scheme (`bearerAuth` and `denApiKey`).

To retrieve the specification programmatically:

```bash
curl http://127.0.0.1:8778/openapi.json | jq .info.version

```

For interactive exploration, open `http://127.0.0.1:8778/docs` in your browser. The Swagger UI is served by the `swaggerUI` middleware and reads the live specification directly from the `openAPIRouteHandler` registration, ensuring documentation always matches the deployed code.

## MCP Capability Discovery and Execution

The control plane implements a sophisticated **Model Context Protocol (MCP)** system that allows AI agents to discover and invoke organizational tools dynamically.

### Discovering Capabilities

Agents query the capability catalog through the endpoint registered in [`ee/apps/den-api/src/mcp/index.ts`](https://github.com/different-ai/openwork/blob/main/ee/apps/den-api/src/mcp/index.ts):

```bash
curl -H 'Authorization: Bearer $TOKEN' \
  http://127.0.0.1:8778/v1/capabilities

```

The `search_capabilities` handler returns a hierarchical tree of available skills, plugins, and remote MCP connections defined in the capability registry.

### Executing Capabilities

To invoke a specific tool, send a POST request to the execution endpoint handled in [`ee/apps/den-api/src/mcp/agent.ts`](https://github.com/different-ai/openwork/blob/main/ee/apps/den-api/src/mcp/agent.ts):

```bash
curl -X POST \
  -H 'Authorization: Bearer $TOKEN' \
  -H 'Content-Type: application/json' \
  -d '{"capabilityId":"my-plugin.my-action","input":{}}' \
  http://127.0.0.1:8778/v1/execute

```

The `execute_capability` handler resolves the plugin, validates input against the defined schema, runs the underlying tool, and returns structured results or standardized error responses.

## Key Source Files and Implementation Details

Understanding the codebase structure enables advanced customization and debugging of the control plane:

| File | Purpose |
|------|---------|
| [`ee/apps/den-api/src/app.ts`](https://github.com/different-ai/openwork/blob/main/ee/apps/den-api/src/app.ts) | Main Hono server, registers middleware, health endpoints, Swagger UI, and all route groups |
| [`ee/apps/den-api/src/env.ts`](https://github.com/different-ai/openwork/blob/main/ee/apps/den-api/src/env.ts) | Loads and validates environment variables including `VITE_DEN_API_BASE_URL` |
| [`ee/apps/den-api/src/mcp/index.ts`](https://github.com/different-ai/openwork/blob/main/ee/apps/den-api/src/mcp/index.ts) | Core MCP registration; builds the capability catalog for `search_capabilities` |
| [`ee/apps/den-api/src/mcp/agent.ts`](https://github.com/different-ai/openwork/blob/main/ee/apps/den-api/src/mcp/agent.ts) | Handles agent-side routes including `execute_capability` |
| [`ee/apps/den-api/src/routes/auth/index.ts`](https://github.com/different-ai/openwork/blob/main/ee/apps/den-api/src/routes/auth/index.ts) | Authentication endpoints that issue session tokens |
| [`ee/apps/den-api/src/routes/org/index.ts`](https://github.com/different-ai/openwork/blob/main/ee/apps/den-api/src/routes/org/index.ts) | Organization CRUD, team management, and member role APIs |
| [`ee/apps/den-api/src/observability/logger.ts`](https://github.com/different-ai/openwork/blob/main/ee/apps/den-api/src/observability/logger.ts) | Centralized logging utility for request access logs and error handling |
| [`ee/apps/den-api/src/openapi.ts`](https://github.com/different-ai/openwork/blob/main/ee/apps/den-api/src/openapi.ts) | Helper utilities for OpenAPI document generation |
| [`ee/apps/den-api/src/automation/service.ts`](https://github.com/different-ai/openwork/blob/main/ee/apps/den-api/src/automation/service.ts) | Automation route registration for workflow triggers |

## Summary

- The **OpenWork Den control plane** is a Hono-based HTTP server defined in [`ee/apps/den-api/src/app.ts`](https://github.com/different-ai/openwork/blob/main/ee/apps/den-api/src/app.ts) that centralizes organizational resource management.
- Start local development using `pnpm dev:worktree`, which launches the server on port 8778 by default.
- Monitor system health via `/health` and database readiness via `/ready` endpoints.
- Authenticate using either `Authorization: Bearer` tokens or `x-api-key` headers for all `/v1/*` routes.
- Explore the complete API using the auto-generated OpenAPI spec at [`/openapi.json`](https://github.com/different-ai/openwork/blob/main//openapi.json) or the Swagger UI at `/docs`.
- Leverage the **MCP capability registry** in [`src/mcp/capability-registry.ts`](https://github.com/different-ai/openwork/blob/main/src/mcp/capability-registry.ts) to enable agents to discover tools via `/v1/capabilities` and execute them via `/v1/execute`.

## Frequently Asked Questions

### What is the default port for the OpenWork Den control plane?

The Den server listens on the port specified by the `OPENWORK_PORT` environment variable, defaulting to **8778** when the variable is unset. This is configured during the environment loading phase in [`ee/apps/den-api/src/env.ts`](https://github.com/different-ai/openwork/blob/main/ee/apps/den-api/src/env.ts).

### How do I obtain a session token for API authentication?

Session tokens are issued through the authentication endpoints registered in [`ee/apps/den-api/src/routes/auth/index.ts`](https://github.com/different-ai/openwork/blob/main/ee/apps/den-api/src/routes/auth/index.ts). After completing the authentication flow (typically via OAuth or credential exchange), the server returns a bearer token that must be included in the `Authorization` header for subsequent requests to protected routes.

### What is the MCP capability registry and how does it work?

The **capability registry** implemented in [`src/mcp/capability-registry.ts`](https://github.com/different-ai/openwork/blob/main/src/mcp/capability-registry.ts) maintains a searchable index of all available tools, plugins, and remote MCP servers that agents can access. When an agent calls `/v1/capabilities`, the `search_capabilities` handler queries this registry to return a hierarchical catalog. The registry abstracts the underlying implementation details, allowing agents to invoke complex workflows through standardized `execute_capability` calls without knowing the specific backend service handling the request.

### How can I verify that the Den control plane is ready to accept requests?

Query the `/ready` endpoint, which performs dependency checks including database connectivity. A successful response indicates the PostgreSQL instance is reachable and the system is fully initialized. If the database is unavailable, the endpoint returns HTTP 503, signaling that the control plane is running but not ready for traffic.