Agent Skillsdotnet/skills › mcp-csharp-test

mcp-csharp-test

GitHub

用于C# MCP服务器的自动化测试,涵盖工具方法的单元测试及基于MCP协议的全流程集成测试。支持xUnit/NUnit框架、依赖模拟、内存客户端/服务器交互及HTTP传输测试,适用于CI管道构建与质量评估。

plugins/dotnet-ai/skills/mcp-csharp-test/SKILL.md dotnet/skills

Trigger Scenarios

需要为C# MCP服务器编写单元测试或集成测试 配置MCP服务器的CI测试流水线 验证MCP工具的方法逻辑或完整协议交互

Install

npx skills add dotnet/skills --skill mcp-csharp-test -g -y
More Options

Non-standard path

npx skills add https://github.com/dotnet/skills/tree/main/plugins/dotnet-ai/skills/mcp-csharp-test -g -y

Use without installing

npx skills use dotnet/skills@mcp-csharp-test

指定 Agent (Claude Code)

npx skills add dotnet/skills --skill mcp-csharp-test -a claude-code -g -y

安装 repo 全部 skill

npx skills add dotnet/skills --all -g -y

预览 repo 内 skill

npx skills add dotnet/skills --list

SKILL.md

Frontmatter
{
    "name": "mcp-csharp-test",
    "license": "MIT",
    "description": "Test C# MCP servers at multiple levels: unit tests for individual tools and integration tests using the MCP client SDK. USE FOR: unit testing MCP tool methods, integration testing with in-memory MCP client\/server, end-to-end testing via MCP protocol, testing HTTP MCP servers with WebApplicationFactory, mocking dependencies in tool tests, creating evaluations for MCP servers, writing eval questions, measuring tool quality. DO NOT USE FOR: testing MCP clients (this is server testing only), load or performance testing, testing non-.NET MCP servers, debugging server issues (use mcp-csharp-debug).\n"
}

C# MCP Server Testing

Test MCP servers at two levels: unit tests for individual tool methods, and integration tests that exercise the full MCP protocol in-memory.

When to Use

  • Adding automated tests to an MCP server
  • Testing individual tool methods with mocked dependencies
  • Writing integration tests that validate tool listing and invocation via MCP protocol
  • Setting up CI test pipelines for MCP servers

Stop Signals

  • No server yet? → Use mcp-csharp-create first
  • Server not running? → Use mcp-csharp-debug
  • Just need manual/interactive testing? → Use mcp-csharp-debug for MCP Inspector

Inputs

Input Required Description
MCP server project path Yes Path to the server .csproj being tested
Test framework Recommended Default: xUnit. Also supports NUnit or MSTest
Transport type Recommended Determines integration test approach (stdio vs HTTP)

Workflow

Step 1: Create the test project

dotnet new xunit -n <ServerName>.Tests
cd <ServerName>.Tests
dotnet add reference ../<ServerName>/<ServerName>.csproj
dotnet add package ModelContextProtocol
dotnet add package Moq
dotnet add package FluentAssertions

Step 2: Write unit tests for tool methods

Test tool methods directly — fastest and most isolated:

public class MyToolTests
{
    [Fact]
    public void Echo_ReturnsFormattedMessage()
    {
        var result = MyTools.Echo("Hello");
        result.Should().Be("Echo: Hello");
    }

    [Theory]
    [InlineData("")]
    [InlineData("   ")]
    public void Echo_HandlesEdgeCases(string input)
    {
        var result = MyTools.Echo(input);
        result.Should().StartWith("Echo:");
    }
}

For tools with DI dependencies, mock the dependency:

public class ApiToolTests
{
    [Fact]
    public async Task FetchData_ReturnsApiResponse()
    {
        var handler = new MockHttpMessageHandler("""{"id": 1}""");
        var httpClient = new HttpClient(handler);

        var result = await ApiTools.FetchData(httpClient, "resource-1");
        result.Should().Contain("id");
    }
}

Step 3: Write integration tests with MCP client

Test the full MCP protocol using a client-server connection:

using ModelContextProtocol.Client;

public class ServerIntegrationTests : IAsyncLifetime
{
    private McpClient _client = null!;

    public async Task InitializeAsync()
    {
        var transport = new StdioClientTransport(new StdioClientTransportOptions
        {
            Name = "TestClient",
            Command = "dotnet",
            Arguments = ["run", "--project", "../<ServerName>/<ServerName>.csproj"]
        });
        _client = await McpClient.CreateAsync(transport);
    }

    public async Task DisposeAsync() => await _client.DisposeAsync();

    [Fact]
    public async Task Server_ListsExpectedTools()
    {
        var tools = await _client.ListToolsAsync();
        tools.Should().Contain(t => t.Name == "echo");
    }

    [Fact]
    public async Task Tool_ReturnsExpectedResult()
    {
        var result = await _client.CallToolAsync("echo",
            new Dictionary<string, object?> { ["message"] = "Test" });
        var text = result.Content.OfType<TextContentBlock>().First().Text;
        text.Should().Contain("Test");
    }
}

For the SDK's ClientServerTestBase (in-memory testing) and HTTP testing with WebApplicationFactory, see references/test-patterns.md.

Step 4: Run tests

# Run all tests
dotnet test

# Run a specific test class
dotnet test --filter "FullyQualifiedName~MyToolTests"

# Run with coverage
dotnet test --collect:"XPlat Code Coverage"

Step 5: Write evaluations

Evaluations measure how well an LLM uses your tools. Good evaluation questions should be:

  • Read-only and non-destructive — never modify data as a side effect
  • Deterministic — have a single verifiable correct answer
  • Multi-step — require the LLM to call multiple tools or reason across results

For the evaluation format, example questions, and detailed guidance, see references/evaluations.md.

Validation

  • Unit tests cover all tool methods, including edge cases
  • Integration tests verify tool listing via ListToolsAsync()
  • Integration tests verify tool invocation via CallToolAsync()
  • All tests pass: dotnet test
  • Tests run in CI without manual setup

Common Pitfalls

Pitfall Solution
Integration test hangs on CreateAsync Server fails to start. Verify dotnet build succeeds first. For stdio, ensure no stdout logging
StdioClientTransport not finding project Use the correct relative path to .csproj from the test project directory
Tests pass locally but fail in CI Run dotnet build before test execution. Use --no-build only after an explicit build step
Mocking HttpClient is awkward Mock HttpMessageHandler, not HttpClient directly. See references/test-patterns.md
Full test suite runs are slow Use --filter for development. Run the full suite only for CI verification

Related Skills

  • mcp-csharp-create — Create a new MCP server project
  • mcp-csharp-debug — Running and interactive debugging
  • mcp-csharp-publish — NuGet, Docker, Azure deployment

Reference Files

  • references/test-patterns.md — Complete test code examples: ClientServerTestBase in-memory pattern, WebApplicationFactory for HTTP, MockHttpMessageHandler helper, test categorization, coverage reporting. Load when: writing integration tests or need detailed mock patterns.
  • references/evaluations.md — Evaluation format, question design principles, and example eval questions. Load when: user asks about evaluations, eval questions, or measuring tool quality.

More Info

Version History

  • ce75c35 Current 2026-07-06 00:29

Same Skill Collection

.agents/skills/create-custom-agent/SKILL.md
.agents/skills/create-skill-test/SKILL.md
.agents/skills/create-skill/SKILL.md
.agents/skills/improve-skill-quality/SKILL.md
.github/skills/agentic-workflows/SKILL.md
eng/skill-validator/tests/fixtures/sample-skill/SKILL.md
plugins/dotnet-advanced/skills/csharp-scripts/SKILL.md
plugins/dotnet-advanced/skills/nuget-trusted-publishing/SKILL.md
plugins/dotnet-aspnetcore/skills/configuring-opentelemetry-dotnet/SKILL.md
plugins/dotnet-aspnetcore/skills/dotnet-webapi/SKILL.md
plugins/dotnet-aspnetcore/skills/minimal-api-file-upload/SKILL.md
plugins/dotnet-blazor/skills/create-blazor-project/SKILL.md
plugins/dotnet-blazor/skills/fetch-and-send-data/SKILL.md
plugins/dotnet-blazor/skills/support-prerendering/SKILL.md
plugins/dotnet-blazor/skills/use-js-interop/SKILL.md
plugins/dotnet-data/skills/optimizing-ef-core-queries/SKILL.md
plugins/dotnet-diag/skills/analyzing-dotnet-performance/SKILL.md
plugins/dotnet-diag/skills/clr-activation-debugging/SKILL.md
plugins/dotnet-diag/skills/dotnet-trace-collect/SKILL.md
plugins/dotnet-diag/skills/dump-collect/SKILL.md
plugins/dotnet-experimental/skills/exp-mock-usage-analysis/SKILL.md
plugins/dotnet-experimental/skills/exp-simd-vectorization/SKILL.md
plugins/dotnet-msbuild/skills/binlog-failure-analysis/SKILL.md
plugins/dotnet-msbuild/skills/copy-to-output-directory/SKILL.md
plugins/dotnet-msbuild/skills/msbuild-server/SKILL.md
plugins/dotnet-msbuild/skills/resolve-project-references/SKILL.md
plugins/dotnet-test-migration/skills/migrate-xunit-to-mstest/SKILL.md
plugins/dotnet-test-migration/skills/migrate-xunit-to-xunit-v3/SKILL.md
plugins/dotnet-test/skills/code-testing-extensions/SKILL.md
plugins/dotnet-test/skills/filter-syntax/SKILL.md
plugins/dotnet-test/skills/find-untested-sources/SKILL.md
plugins/dotnet-test/skills/platform-detection/SKILL.md
plugins/dotnet-upgrade/skills/dotnet-aot-compat/SKILL.md
.agents/skills/authoring-github-workflows/SKILL.md
plugins/dotnet-advanced/skills/dotnet-pinvoke/SKILL.md
plugins/dotnet-ai/skills/mcp-csharp-create/SKILL.md
plugins/dotnet-ai/skills/mcp-csharp-debug/SKILL.md
plugins/dotnet-ai/skills/technology-selection/SKILL.md
plugins/dotnet-aspnetcore/skills/convert-blazor-server-to-webapp/SKILL.md
plugins/dotnet-blazor/skills/author-component/SKILL.md
plugins/dotnet-blazor/skills/collect-user-input/SKILL.md
plugins/dotnet-blazor/skills/configure-auth/SKILL.md
plugins/dotnet-blazor/skills/coordinate-components/SKILL.md
plugins/dotnet-blazor/skills/plan-ui-change/SKILL.md
plugins/dotnet-data/skills/create-datadriven-aspnetcore/SKILL.md
plugins/dotnet-diag/skills/android-tombstone-symbolication/SKILL.md
plugins/dotnet-diag/skills/apple-crash-symbolication/SKILL.md
plugins/dotnet-diag/skills/microbenchmarking/SKILL.md
plugins/dotnet-experimental/skills/exp-test-maintainability/SKILL.md

Metadata

Files
0
Version
5354047
Hash
b00d96f4
Indexed
2026-07-06 00:29

- 위키
Copyright © 2011-2026 iteam. Current version is 2.155.2. UTC+08:00, 2026-08-04 11:48
浙ICP备14020137号-1 $방문자$