Skip to main content
The dotbot MCP server auto-discovers tools at startup by scanning tool directories for subdirectories that contain both a metadata.json and a script.ps1. There is no registration step - dropping the right files into the right folder is all that is needed. This same discovery mechanism applies to tools added by workflows and stacks installed in your project.

How tool discovery works

When the MCP server starts, it walks three sets of directories. For each subdirectory that contains both metadata.json and script.ps1, the server:
  1. Reads the tool name and input schema from metadata.json
  2. Dot-sources script.ps1 to load the Invoke-* function into memory
  3. Registers the tool with the MCP protocol handler
The three discovery locations are: No changes to the server itself are needed. Restart the MCP server process (by restarting your AI tool) to pick up new or modified tools.

Directory structure

Each tool lives in its own folder inside one of the discovery directories. Use kebab-case for the folder name:
For workflow-scoped tools, place the folder under either <workflow>/tools/ or <workflow>/systems/mcp/tools/. For stack-scoped tools, use the same structure under <stack>/tools/ or <stack>/systems/mcp/tools/. The server scans both layout variants for each installed workflow and stack.

Naming conventions

The three files follow different case conventions that must be consistent with each other: The server derives the function name to call from the name field in metadata.json by capitalizing each underscore-separated segment and prepending Invoke-. If the naming is inconsistent, the tool will load but fail at call time with a function-not-found error.

The required files

metadata.json

Defines the tool’s name, description, and JSON Schema for its input parameters. The following is based on the real metadata.json for the built-in task_create tool, which you can use as a reference for field structure:
Mark all parameters the AI must supply in the required array. Parameters not in required are treated as optional.

script.ps1

Contains a single PowerShell function named Invoke-YourToolName. The function receives a [hashtable]$Arguments parameter and returns a hashtable with the result data. The MCP server serializes the returned hashtable to JSON before sending it back to the AI tool.
The MCP server sets $global:DotbotProjectRoot before loading tool scripts. Use this variable to build paths to .bot/workspace/, .bot/.control/, or any other project-relative location - do not hardcode paths.

test.ps1

Tests the tool by sending a JSON-RPC request to a running MCP server process. Including a test file is optional but recommended, especially for tools that modify project state.

Creating a custom tool

The following example creates a tool called project_summary that returns a count of tasks in each lifecycle state.
1

Create the tool folder

Inside your workflow’s tools/ directory, create a new directory using kebab-case:
2

Write metadata.json

Create <workflow-path>/tools/project-summary/metadata.json with the snake_case tool name, a description, and the input schema. For a tool with no required inputs, use an empty properties object:
3

Write script.ps1

Create <workflow-path>/tools/project-summary/script.ps1 with the Invoke-ProjectSummary function:
4

Restart the MCP server

The server loads tools at startup. Restart your AI tool (or the MCP server process) to pick up the new tool. Ask your AI tool to list available dotbot tools - project_summary should appear in the list.

Tool name collision warning

Tool name collisions are possible if two installed workflows or stacks define a tool with the same name field in their metadata.json. When a collision occurs, the last tool loaded wins, which may produce unexpected behavior. Use unique, workflow-prefixed names (for example, jira_repo_clone rather than repo_clone) to avoid conflicts.