Unit Test MCP
Intelligent test generation and execution for GitHub Copilot
A VS Code extension that enables GitHub Copilot to generate, run, and improve Jest, Vitest, Pytest, and .NET tests using the Model Context Protocol (MCP).
✨ Features
- 🚀 Zero Setup: Install and use immediately — MCP server registers automatically via the VS Code API
- 🧪 Multi-Framework Support: Jest/Vitest (JS/TS), Pytest (Python), and .NET (C#)
- 🤖 AI-Powered: Works seamlessly with GitHub Copilot Chat
- 📊 Coverage Reports: Run fresh coverage with
run_tests and inspect existing artifacts with inspect_coverage
- 📁 Batch Test Generation: Generate tests for entire folders at once with prioritization
- 🛡️ Protective Test Review: Use
review_test to catch weak assertions, excessive mocking, and unsafe coercion
- 🎯
@UnitTestEngineer Agent: Built-in custom agent for test generation, coverage improvement, and batch workflows
- 📝 Copilot Instructions: Auto-creates and syncs workspace instruction files that teach Copilot the test workflow
- 📖 Getting Started Walkthrough: Built-in tutorial accessible via
Unit Test MCP: Open Tutorial
📦 Installation
Install from the VS Code Marketplace or search for "Unit Test MCP" in the Extensions view (Ctrl+Shift+X).
🚀 Quick Start
1. Install the Extension
Install from the Marketplace link above. The extension auto-configures on first activation.
2. Start Using with Copilot
Open GitHub Copilot Chat and try:
Generate unit tests for this file
Generate tests for all files in src/
Run tests with coverage
What files have low coverage?
Or use the built-in @UnitTestEngineer agent for a guided workflow.
The extension will automatically activate and handle the requests.
review_test blocks a mock only when it replaces the module the test exists to cover. Mocking a real
network or platform boundary — including one you wrapped in your own module — is not reported, so no
annotations or allowlists are needed. Broader mocking judgement is left to the self-review checklist
it returns.
📋 Requirements
| Requirement |
Version |
Notes |
| VS Code |
1.101.0+ |
Required (MCP server API) |
| GitHub Copilot |
Latest |
Must be active |
| Node.js |
20+ |
Required only for the standalone npm server; bundled with VS Code for the extension |
| Python |
Any |
Only needed if running Pytest tests |
| .NET SDK |
6.0+ |
Only needed if running .NET tests |
🎯 What You Can Do
With Jest or Vitest (JavaScript/TypeScript)
- ✅ Generate JS/TS unit tests (including React component tests)
- ✅ Run tests with coverage
- ✅ Watch mode support
- ✅ Targeted test execution
- ✅ Update snapshots (Jest, via
--updateSnapshot, when applicable)
With Pytest (Python)
- ✅ Generate Python unit tests
- ✅ Run tests with coverage
- ✅ Parametrized test support
- ✅ Fixture-based testing
With .NET (C#)
- ✅ Generate xUnit/NUnit tests
- ✅ Run tests via
dotnet test
- ✅ Coverage reporting
- ✅ Solution-aware test generation
Coverage Reports
Ask Copilot "Run tests with coverage" or "What files have low coverage?" to get an interactive coverage report showing per-file line, branch, function, and statement coverage. For folder work, run_tests supports scope='directory' with an optional scope_path so coverage.met reflects only files under that source directory.
⚙️ Configuration
The extension works out-of-the-box, but you can customize it using the Unit Test MCP side panel.
- Open the Unit Test MCP view in the VS Code sidebar (look for the clipboard/gear icon in the Activity Bar).
- Use the UI to:
- Browse and select custom instruction files for Jest, Vitest, Pytest, or .NET.
- View currently loaded instructions.
- Set target code coverage percentage.
- Configure custom test commands.
Changes take effect immediately - no restart required!
📝 Custom Instructions
Customize test generation by selecting your own Markdown instruction files in the Unit Test MCP side
panel. The extension combines them with its framework-specific guidance.
📁 Generated Files & Git
The extension creates files in your workspace that Copilot reads at runtime:
.github/instructions/unittestMcp.instructions.md # Auto-synced on each activation
.github/prompts/UnitTestMcp.UnitTestEngineer.agent.md # Created once, never overwritten
These files work whether committed or gitignored — Copilot reads them from the filesystem. To keep your git history clean, add this to your .gitignore:
# Unit Test MCP (auto-managed by extension)
**/.github/instructions/unittestMcp.instructions.md
**/.github/prompts/UnitTestMcp.UnitTestEngineer.agent.md
Each developer's copy is managed independently by the extension — no commits needed.
💡 How It Works
┌─────────────────────────┐
│ GitHub Copilot Chat │
└───────────┬─────────────┘
│ MCP Protocol
┌───────────▼─────────────┐
│ TypeScript MCP Server │
│ (Bundled in Extension) │
└───────────┬─────────────┘
│
┌───────────▼─────────────┐
│ Jest / Vitest / Pytest │
│ / Dotnet │
└─────────────────────────┘
- You ask Copilot to generate/run tests
- Copilot calls the MCP server via standard protocol
- Server executes Jest/Vitest/Pytest/.NET and returns results
- Copilot shows you formatted output
🐛 Troubleshooting
Extension Not Working?
Check Status:
- Open the Unit Test MCP sidebar view.
- Verify that the server is connected and configuration is valid.
Still not working?
- Reload VS Code:
Ctrl+Shift+P → "Reload Window"
- Check Output panel: View → Output → Select "Log (Extension Host)" and search for "Unit Test MCP"
- Ensure GitHub Copilot extension is installed and active
- Run
MCP: List Servers from the Command Palette — "Unit Test MCP" should appear
- If not listed, reload VS Code:
Ctrl+Shift+P → "Reload Window"
- Try asking: "What MCP tools are available?"
Tests Not Running?
For Jest:
- Ensure
package.json exists in your project root
- Verify Jest is installed:
npm list jest
For Vitest:
- Ensure
package.json exists in your project root
- Verify Vitest is installed:
npm list vitest
For Pytest:
- Ensure Python is installed:
python --version
- Verify Pytest is installed:
pip list | grep pytest
For .NET:
- Ensure .NET SDK is installed:
dotnet --version
- Ensure your project is a valid .NET project
Structured Error Codes
When a tool call fails, the response carries isError: true with a human-readable message in content[0].text and a machine-readable envelope in structuredContent.error of the form:
{
"error": {
"code": "INVALID_ROOT_DIR",
"message": "root_dir is required and must be a non-empty string",
"details": { /* optional, code-specific */ }
}
}
Agents should branch on code rather than parsing message. Common recovery cases include:
| Code |
What to do |
INVALID_INPUT |
Correct the argument named in details.issues[].path. |
INVALID_ROOT_DIR |
Pass an absolute project directory containing files such as package.json, *.csproj, or pytest.ini. |
INVALID_SCOPE |
Add test_pattern when using scope='file', or use scope='directory' with scope_path / scope='repo' when you need a broader gate. |
NO_FRAMEWORK_DETECTED |
Pass an explicit framework such as jest, vitest, pytest, dotnet, or custom. |
TIMEOUT |
Retry with a larger timeout_ms, or investigate hanging tests. |
SPAWN_FAILED |
Verify node, python, or dotnet is installed and available on PATH. |
INTERNAL |
File an issue with the message and reproduction steps. |
Clients can use the stable errorCode values in structured tool errors for exhaustive handling.
Back-compat: consumers that only read content[0].text continue to work — structuredContent.error is additive.
📚 Examples
Example 1: Generate React Tests
You: Generate unit tests for src/components/Button.tsx
Copilot: [Uses generate_test tool]
Creates: src/components/__tests__/Button.test.tsx
Example 2: Run Tests with Coverage
You: Run tests with coverage for the Button component
Copilot: [Uses run_tests tool]
Shows: Test results + coverage report
Example 3: Batch Test Generation
You: Generate tests for all files in src/services/
Copilot: [Uses generate_tests_batch tool]
Scans folder, prioritizes by missing tests/low coverage
Creates tests for each file sequentially
Runs coverage with scope='directory' and scope_path='src/services'
Example 4: Inspect Coverage
You: What files have low test coverage?
Copilot: [Uses inspect_coverage tool]
Shows: Worst-covered files and branches from existing coverage artifacts
🖥️ Using with Copilot CLI
The VS Code extension automatically registers the MCP server for VS Code's built-in Copilot Chat. In current VS Code builds, extension-provided MCP servers can also be bridged into nearby Copilot CLI and Claude agent sessions when those clients are launched from VS Code. If run_tests, generate_test, and generate_tests_batch are already listed, prefer that bridged server because it shares the extension configuration and workspace instructions.
For users signed in to a Microsoft tenant account, the extension also registers the hosted
TestEvaluator MCP as a standalone tool. Its evaluate_tests tool is always available for manual
calls after authentication. By default it is not part of generated test workflows; enable Hosted
Test Evaluation in the side panel or set unittestMcp.testEvaluator.enabled to true to add the
advisory evaluation step to generated instructions. The local review_test protective-test gate
remains mandatory either way.
On first use, VS Code follows the server's OAuth metadata and prompts for GitHub authorization; no PAT
or GITHUB_TOKEN setting is required. Evaluation submits the selected source and test code to the
hosted service. Without a Microsoft tenant session the server is not registered; local test generation
works the same either way.
Use the standalone server for non-VS Code clients, older VS Code builds, remote agent hosts where extension-provided MCP servers are not visible, or any CLI/agent session where the tools are not listed.
The standalone npm server requires Node.js 20 or later.
VS Code runTests vs Unit Test MCP run_tests: use VS Code's built-in runTests tool when you want the native Testing UI/test-adapter path for an already configured workspace. Use Unit Test MCP run_tests when the workflow depends on generate_test, coverage target enforcement, per-file or directory-scoped coverage gates, or the same behavior across Copilot CLI, Claude agents, and standalone MCP clients.
To add the standalone server:
- Open a Copilot CLI session (type
copilot in VS Code's integrated terminal)
- Run
/mcp add and fill in the form:
- Server Name:
unittest-mcp
- Server Type:
STDIO (or Local)
- Command:
npx -y unittest-mcp
- Environment Variables:
{} (leave empty)
- Tools:
*
- Press
Ctrl+S to save — the tools are available immediately
Alternatively, edit ~/.copilot/mcp-config.json directly:
{
"mcpServers": {
"unittest-mcp": {
"type": "local",
"command": "npx",
"args": ["-y", "unittest-mcp"],
"env": {},
"tools": ["*"]
}
}
}
Or add it to your workspace .vscode/mcp.json for VS Code-level access:
{
"servers": {
"unittest-mcp": {
"command": "npx",
"args": ["-y", "unittest-mcp"]
}
}
}
Local Server Security and Data Handling
- Authentication: The local
unittest-mcp server uses stdio and has no network listener or
inbound authentication flow. The MCP client launches it as the signed-in operating-system user.
Use it only in trusted workspaces; it executes repository-controlled test commands with that
user's permissions.
- Local data access: Tool arguments can select source files, test files, coverage artifacts, and
project directories. The server reads that data locally and returns requested content/results to
the configured MCP client. The client and its model provider apply their own data-handling policy.
- Process execution:
run_tests starts the configured Jest, Vitest, Pytest, .NET, or custom test
command. Shell-backed Windows arguments reject command-control characters before execution.
- Persistence: Test runners may create their normal coverage, cache, and result artifacts in the
workspace. Unit Test MCP also keeps a per-user runtime config and redacted diagnostic log in VS
Code global storage when launched by the extension.
- Network and telemetry: The standalone npm bundle does not make tool-directed network calls and
ships with telemetry disabled. The VS Code extension and bundled MCP server also disable all
telemetry emission, including when
UNITTEST_MCP_TELEMETRY_CONNECTION_STRING is supplied. Common
credential/token patterns are redacted before diagnostic output is buffered or persisted.
Update or Remove the Local Server
- Update: Package-manager clients using
npx -y unittest-mcp resolve the current package
version. Restart the MCP client after an update.
- Remove: Delete the
unittest-mcp entry from ~/.copilot/mcp-config.json, .vscode/mcp.json,
or the equivalent MCP client configuration, then restart that client.
📄 License
MIT License
📮 Support
- Issues/Feedback: Use the "Unit Test MCP: Give Feedback" button in the Unit Test MCP sidebar panel