# How Skills Are Structured Within Each Plugin in dotnet/skills

> Explore how skills are structured in dotnet/skills. Discover markdown-driven definitions within plugin folders, including JSON manifests, SKILL.md files, and agent configurations.

- Repository: [.NET Platform/skills](https://github.com/dotnet/skills)
- Tags: internals
- Published: 2026-07-06

---

**Skills in dotnet/skills are organized as markdown-driven definitions inside self-contained plugin folders, where each plugin contains a JSON manifest file, a dedicated skills directory with SKILL.md files, and optional agents and MCP server configurations.**

The **dotnet/skills** repository implements a modular architecture that separates capabilities into independent plugins. Understanding how skills are structured within each plugin is essential for extending the system or integrating with the skill-validator runtime. This guide examines the exact file-system contract used by plugins like `dotnet-test` and `dotnet-msbuild` to register and execute AI-driven workflows.

## Plugin Manifest Structure

Every plugin begins with a **plugin manifest** located at `plugins/<plugin-name>/plugin.json`. This JSON file declares the plugin's metadata and points to its skill directories.

According to the source code, the manifest contains:
- **Name, version, and description** – Identifies the plugin for the validator
- **Skills array** – Specifies the folder containing skill definitions (typically `"./skills/"`)
- **Agents array** – Optional references to specialized AI agents
- **MCP servers** – Optional tool server definitions for external process communication

For example, the `dotnet-test` plugin manifest at [`plugins/dotnet-test/plugin.json`](https://github.com/dotnet/skills/blob/main/plugins/dotnet-test/plugin.json) registers its skills folder and several test-generation agents, while [`plugins/dotnet-msbuild/plugin.json`](https://github.com/dotnet/skills/blob/main/plugins/dotnet-msbuild/plugin.json) configures the *binlog* MCP server for MSBuild log parsing.

## Skill Definition Layout

Inside each plugin, the `skills/` directory contains one subfolder per skill. The structure follows this pattern:

```

plugins/<plugin-name>/
├── plugin.json
└── skills/
    └── <skill-name>/
        ├── SKILL.md
        └── references/ (optional)

```

The **SKILL.md** file serves as the single source of truth for a skill's behavior. It contains:
- **Front-matter metadata** – YAML-style headers defining inputs, outputs, and validation rules
- **Workflow steps** – Instructions the validator executes
- **Usage guidance** – Documentation for consumers

For instance, the `writing-mstest-tests` skill in [`plugins/dotnet-test/skills/writing-mstest-tests/SKILL.md`](https://github.com/dotnet/skills/blob/main/plugins/dotnet-test/skills/writing-mstest-tests/SKILL.md) defines input parameters and testing workflows, while [`plugins/dotnet-msbuild/skills/msbuild-antipatterns/SKILL.md`](https://github.com/dotnet/skills/blob/main/plugins/dotnet-msbuild/skills/msbuild-antipatterns/SKILL.md) contains MSBuild-specific analysis logic.

## Optional Components

Beyond the core manifest and skill definitions, plugins may include additional directories that extend functionality.

### References Directory

Skills requiring supplementary documentation include a `references/` folder adjacent to [`SKILL.md`](https://github.com/dotnet/skills/blob/main/SKILL.md). This directory stores supporting files such as diagrams, external markdown documentation, or code samples. The **migrate-nullable-references** skill, for example, includes [`references/nullable-attributes.md`](https://github.com/dotnet/skills/blob/main/references/nullable-attributes.md) to support its migration workflow.

### Agent Definitions

The `agents/` directory at `plugins/<plugin-name>/agents/` houses specialized AI agent definitions. These markdown files (e.g., [`code-testing-generator.agent.md`](https://github.com/dotnet/skills/blob/main/code-testing-generator.agent.md)) describe agents that the skill-validator invokes for code generation or analysis tasks. When a skill's workflow references an agent, the validator loads the definition from this directory to perform specialized operations.

### MCP Server Configuration

For skills requiring external tool integration, the plugin manifest's `"mcpServers"` section defines Model Context Protocol servers. These configurations specify commands to launch external processes that communicate via JSON over stdio. The **dotnet-msbuild** plugin configures the *binlog* MCP server using `dotnet dnx Microsoft.AITools.BinlogMcp --yes`, enabling skills to parse binary MSBuild logs without embedding the parser logic directly.

## How the Validator Processes the Structure

The skill-validator runtime consumes this structure through a five-stage discovery process:

1. **Plugin Discovery** – Walks the `plugins/` directory and parses each [`plugin.json`](https://github.com/dotnet/skills/blob/main/plugin.json)
2. **Skill Registration** – Resolves the paths specified in the `"skills"` array and registers every subfolder containing [`SKILL.md`](https://github.com/dotnet/skills/blob/main/SKILL.md)
3. **Input Validation** – Loads the markdown front-matter and validates user-supplied inputs against the declared schema
4. **Agent Resolution** – Loads agent definitions from `agents/` when workflows reference them
5. **MCP Initialization** – Launches configured MCP servers as separate processes for tool-dependent skills

This architecture ensures that adding a new skill requires only creating a folder with [`SKILL.md`](https://github.com/dotnet/skills/blob/main/SKILL.md) under the plugin's `skills/` directory, without recompiling the validator host.

## Code Examples

### Loading Skills Programmatically

You can discover available skills by parsing the plugin manifest and scanning the skills directory:

```csharp
using System.Text.Json;
using System.IO;

// Load the plugin manifest
var manifestPath = Path.Combine(repoRoot, "plugins", "dotnet-test", "plugin.json");
var manifestJson = File.ReadAllText(manifestPath);
var manifest = JsonSerializer.Deserialize<JsonElement>(manifestJson);

// Resolve the skills folder from the manifest
var skillsRoot = Path.Combine(repoRoot, "plugins", "dotnet-test", 
    manifest.GetProperty("skills")[0].GetString());

// Enumerate available skills
foreach (var skillDir in Directory.GetDirectories(skillsRoot))
{
    var skillFile = Path.Combine(skillDir, "SKILL.md");
    if (File.Exists(skillFile))
        Console.WriteLine($"Found skill: {Path.GetFileName(skillDir)}");
}

```

### Running Skills via CLI

Invoke a specific skill using the validator's run command with the `plugin-name/skill-name` syntax:

```bash
skill-validator run dotnet-test/writing-mstest-tests \
    --input "Test scenario: Verify that OrderService.CalculateTotal applies discount correctly"

```

## Summary

- **Plugin manifests** ([`plugin.json`](https://github.com/dotnet/skills/blob/main/plugin.json)) declare the plugin metadata and locate the skills directory
- **Skill definitions** reside in `skills/<skill-name>/SKILL.md` files containing front-matter metadata and workflow instructions
- **References** stored in `references/` folders provide supplementary documentation for complex skills
- **Agents** defined in `agents/` enable specialized AI behavior for code generation and analysis
- **MCP servers** configured in the manifest allow external tool integration via stdio JSON communication
- The validator discovers and executes skills by walking this file structure without requiring host recompilation

## Frequently Asked Questions

### What is the minimum required structure for a plugin?

A valid plugin requires only two files: `plugins/<plugin-name>/plugin.json` and at least one `plugins/<plugin-name>/skills/<skill-name>/SKILL.md`. The manifest must specify the skills directory path, and the SKILL.md must contain valid front-matter defining the skill's inputs. References, agents, and MCP servers are optional extensions.

### How does the skill-validator discover new skills?

The validator walks the `plugins/` directory and reads each [`plugin.json`](https://github.com/dotnet/skills/blob/main/plugin.json) to locate the `"skills"` array entries. It then scans the specified directories for subfolders containing [`SKILL.md`](https://github.com/dotnet/skills/blob/main/SKILL.md) files, registering each valid file as an executable skill. This discovery happens at runtime, allowing dynamic plugin loading without application restart.

### Can a plugin contain multiple skills?

Yes, a single plugin can contain any number of skills. Each skill resides in its own subfolder under `plugins/<plugin-name>/skills/`, with its own [`SKILL.md`](https://github.com/dotnet/skills/blob/main/SKILL.md) file. The `dotnet-test` plugin, for example, contains multiple testing-related skills including `writing-mstest-tests` and `writing-nunit-tests`, all sharing the same plugin manifest and agent pool.

### What is the purpose of the SKILL.md front-matter?

The front-matter in [`SKILL.md`](https://github.com/dotnet/skills/blob/main/SKILL.md) declares the skill's interface contract, including input parameter definitions, types, validation rules, and output specifications. The validator parses this YAML-style header before execution to validate user inputs and configure the execution environment, ensuring type safety and required parameter enforcement before running the workflow steps.