- Renamed all directories: OpenHarbor.MCP.* → Svrnty.MCP.* - Updated all namespaces in 179 C# files - Renamed 20 .csproj files and 3 .sln files - Updated 193 documentation references - Updated 33 references in main CODEX codebase - Updated Codex.sln with new paths - Build verified: 0 errors Preparing for extraction to standalone repositories. 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <noreply@anthropic.com>
612 lines
18 KiB
Markdown
612 lines
18 KiB
Markdown
# Svrnty.MCP
|
|
|
|
**A modular, scalable, secure .NET library for building Model Context Protocol (MCP) servers**
|
|
|
|
[](LICENSE)
|
|
[](https://dotnet.microsoft.com/download/dotnet/8.0)
|
|
[](docs/architecture.md)
|
|
|
|
---
|
|
|
|
## What is Svrnty.MCP?
|
|
|
|
Svrnty.MCP is a **standalone, reusable .NET library** that enables any .NET application to become an MCP server, allowing AI agents (like Claude, ChatGPT, or custom LLMs) to interact with your application through a standardized protocol.
|
|
|
|
**Model Context Protocol (MCP)** is an industry-standard protocol backed by Anthropic that defines how AI agents communicate with external tools and data sources. Think of it as a universal adapter that lets AI assistants safely access your application's capabilities.
|
|
|
|
### Key Features
|
|
|
|
- **Modular & Reusable**: Copy to any .NET project, configure, and go
|
|
- **Clean Architecture**: Core abstractions, infrastructure implementation, ASP.NET Core integration
|
|
- **Security-First**: Permission-based access control, rate limiting, audit logging, deny-by-default model
|
|
- **Transport Flexibility**: HTTP (primary for production) and stdio (legacy for local development)
|
|
- **AI-Automated Setup**: AGENT-PRIMER.md guides AI assistants to configure your integration automatically
|
|
- **TDD Foundation**: Built with test-driven development, comprehensive test coverage
|
|
- **Production-Ready**: Observability, error handling, graceful shutdown, health checks
|
|
|
|
---
|
|
|
|
## Why Svrnty.MCP?
|
|
|
|
**Problem**: Your .NET application has valuable features (search, data access, document processing, APIs) that AI agents can't easily access.
|
|
|
|
**Solution**: Svrnty.MCP transforms your application into an MCP server, exposing tools that AI agents can discover and execute with proper permissions and rate limiting.
|
|
|
|
**Use Cases**:
|
|
- Expose knowledge base search to Claude Code CLI (or Desktop)
|
|
- Allow AI agents to query your database safely
|
|
- Provide document processing tools to LLM workflows
|
|
- Enable AI-assisted data analysis on private data
|
|
- Build custom AI integrations for enterprise applications
|
|
|
|
---
|
|
|
|
## Quick Start
|
|
|
|
### Prerequisites
|
|
|
|
- .NET 8.0 SDK or higher
|
|
- Your existing .NET application (Web API, Console, Worker Service, etc.)
|
|
|
|
### Option 1: AI-Automated Setup (Recommended)
|
|
|
|
If you have access to Claude or another AI assistant:
|
|
|
|
1. Copy this entire folder to your project directory
|
|
2. Open your AI assistant and say: "Read AGENT-PRIMER.md and set up Svrnty.MCP for my project"
|
|
3. The AI will analyze your system, generate configuration, and create sample tools automatically
|
|
|
|
### Option 2: Manual Setup
|
|
|
|
#### Step 1: Add Package Reference
|
|
|
|
```bash
|
|
# Via project reference (development)
|
|
dotnet add reference /path/to/Svrnty.MCP/src/Svrnty.MCP.AspNetCore/Svrnty.MCP.AspNetCore.csproj
|
|
|
|
# OR via NuGet (when published)
|
|
# dotnet add package Svrnty.MCP.AspNetCore
|
|
```
|
|
|
|
#### Step 2: Configure appsettings.json
|
|
|
|
Add MCP configuration:
|
|
|
|
```json
|
|
{
|
|
"Mcp": {
|
|
"Server": {
|
|
"Name": "MyAppMcpServer",
|
|
"Version": "1.0.0",
|
|
"Description": "MCP server for MyApp"
|
|
},
|
|
"Transport": {
|
|
"Type": "Http",
|
|
"Port": 5050
|
|
},
|
|
"Security": {
|
|
"EnablePermissions": true,
|
|
"DefaultDenyAll": true,
|
|
"RateLimit": {
|
|
"Enabled": true,
|
|
"RequestsPerMinute": 60
|
|
}
|
|
}
|
|
}
|
|
}
|
|
```
|
|
|
|
#### Step 3: Update Program.cs
|
|
|
|
```csharp
|
|
using Svrnty.MCP.Core;
|
|
using Microsoft.AspNetCore.Builder;
|
|
|
|
var builder = WebApplication.CreateBuilder(args);
|
|
|
|
// Create tool registry and register your tools
|
|
var registry = new ToolRegistry();
|
|
registry.AddTool(new MyCustomTool());
|
|
|
|
// Create and register MCP server
|
|
var server = new McpServer(registry);
|
|
builder.Services.AddMcpServer(server);
|
|
|
|
// Configure HTTP port
|
|
builder.WebHost.ConfigureKestrel(options =>
|
|
{
|
|
options.ListenLocalhost(5050);
|
|
});
|
|
|
|
var app = builder.Build();
|
|
|
|
// Map MCP HTTP endpoints
|
|
app.MapMcpEndpoints(server);
|
|
|
|
Console.WriteLine("MCP Server listening on http://localhost:5050");
|
|
Console.WriteLine("Endpoints: POST /mcp/invoke, GET /health");
|
|
|
|
await app.RunAsync();
|
|
```
|
|
|
|
#### Step 4: Create Your First Tool
|
|
|
|
```csharp
|
|
using Svrnty.MCP.Core.Abstractions;
|
|
using Svrnty.MCP.Core.Models;
|
|
|
|
public class MyCustomTool : IMcpTool
|
|
{
|
|
public string Name => "my_custom_tool";
|
|
public string Description => "Describes what this tool does";
|
|
|
|
public McpToolSchema Schema => new()
|
|
{
|
|
Type = "object",
|
|
Properties = new Dictionary<string, McpProperty>
|
|
{
|
|
["query"] = new()
|
|
{
|
|
Type = "string",
|
|
Description = "Search query",
|
|
Required = true
|
|
}
|
|
}
|
|
};
|
|
|
|
public async Task<McpToolResult> ExecuteAsync(
|
|
Dictionary<string, object> parameters,
|
|
CancellationToken ct = default)
|
|
{
|
|
var query = parameters["query"].ToString();
|
|
|
|
// Your tool logic here
|
|
var result = await ProcessQueryAsync(query, ct);
|
|
|
|
return McpToolResult.Success(result);
|
|
}
|
|
}
|
|
```
|
|
|
|
#### Step 5: Run and Test
|
|
|
|
```bash
|
|
# Run your application (HTTP mode, default)
|
|
dotnet run
|
|
|
|
# Server will listen on http://localhost:5050
|
|
|
|
# Test health endpoint
|
|
curl http://localhost:5050/health
|
|
|
|
# Test tool listing via HTTP
|
|
curl -X POST http://localhost:5050/mcp/invoke \
|
|
-H "Content-Type: application/json" \
|
|
-d '{"jsonrpc":"2.0","id":1,"method":"tools/list"}'
|
|
|
|
# Test tool execution via HTTP
|
|
curl -X POST http://localhost:5050/mcp/invoke \
|
|
-H "Content-Type: application/json" \
|
|
-d '{"jsonrpc":"2.0","id":2,"method":"tools/call","params":{"name":"my_custom_tool","arguments":{"query":"test"}}}'
|
|
```
|
|
|
|
**Legacy Stdio Mode** (for Claude Desktop integration):
|
|
```bash
|
|
# Run in stdio mode for Claude Desktop
|
|
dotnet run -- --stdio
|
|
|
|
# Test with stdio
|
|
echo '{"jsonrpc":"2.0","id":1,"method":"tools/list"}' | dotnet run -- --stdio
|
|
```
|
|
|
|
---
|
|
|
|
## Architecture
|
|
|
|
Svrnty.MCP follows **Clean Architecture** principles:
|
|
|
|
```
|
|
┌─────────────────────────────────────────────────┐
|
|
│ Svrnty.MCP.Cli (Executable) │
|
|
│ ┌───────────────────────────────────────────┐ │
|
|
│ │ Svrnty.MCP.AspNetCore (HTTP/DI) │ │
|
|
│ │ ┌─────────────────────────────────────┐ │ │
|
|
│ │ │ Svrnty.MCP.Infrastructure │ │ │
|
|
│ │ │ ┌───────────────────────────────┐ │ │ │
|
|
│ │ │ │ Svrnty.MCP.Core │ │ │ │
|
|
│ │ │ │ - IMcpServer │ │ │ │
|
|
│ │ │ │ - IMcpTool │ │ │ │
|
|
│ │ │ │ - IPermissionProvider │ │ │ │
|
|
│ │ │ │ - Models (no dependencies) │ │ │ │
|
|
│ │ │ └───────────────────────────────┘ │ │ │
|
|
│ │ └─────────────────────────────────────┘ │ │
|
|
│ └───────────────────────────────────────────┘ │
|
|
└─────────────────────────────────────────────────┘
|
|
```
|
|
|
|
### Projects
|
|
|
|
| Project | Purpose | Dependencies |
|
|
|---------|---------|--------------|
|
|
| **Svrnty.MCP.Core** | Abstractions, interfaces, models | None |
|
|
| **Svrnty.MCP.Infrastructure** | MCP server implementation, transports, security | Core, System.Text.Json |
|
|
| **Svrnty.MCP.AspNetCore** | ASP.NET Core integration, DI extensions | Core, Infrastructure, ASP.NET Core |
|
|
| **Svrnty.MCP.Cli** | Standalone CLI executable | All above |
|
|
|
|
See [Architecture Documentation](docs/architecture.md) for detailed design.
|
|
|
|
---
|
|
|
|
## Examples
|
|
|
|
### 1. CODEX MCP Server (Knowledge Gateway)
|
|
|
|
CODEX is a knowledge management system. The MCP integration exposes 6 tools:
|
|
|
|
```
|
|
samples/CodexMcpServer/
|
|
├── Tools/
|
|
│ ├── SearchCodexTool.cs # Semantic/keyword search
|
|
│ ├── GetDocumentTool.cs # Retrieve document by ID
|
|
│ ├── ListDocumentsTool.cs # List all documents
|
|
│ ├── SearchByTagTool.cs # Filter by tags
|
|
│ ├── GetDocumentSectionsTool.cs # Get document sections
|
|
│ └── ListTagsTool.cs # List all tags
|
|
```
|
|
|
|
**Usage with MCP Gateway** (Recommended for Production):
|
|
```bash
|
|
# Run CODEX MCP Server in HTTP mode (default)
|
|
cd /path/to/Svrnty.MCP.Server/samples/CodexMcpServer
|
|
dotnet run
|
|
# Server listens on http://localhost:5050
|
|
|
|
# Configure gateway to route to this server
|
|
# See Svrnty.MCP.Gateway documentation
|
|
```
|
|
|
|
**Alternative: Claude Desktop with Stdio** (Legacy, Local Development):
|
|
```json
|
|
{
|
|
"mcpServers": {
|
|
"codex": {
|
|
"command": "dotnet",
|
|
"args": ["run", "--project", "/path/to/samples/CodexMcpServer/CodexMcpServer.csproj", "--", "--stdio"],
|
|
"transport": "stdio"
|
|
}
|
|
}
|
|
}
|
|
```
|
|
|
|
Note: HTTP transport is recommended for production deployments with multiple clients, load balancing, and monitoring.
|
|
|
|
### 2. Database Query Tool
|
|
|
|
```csharp
|
|
public class DatabaseQueryTool : IMcpTool
|
|
{
|
|
private readonly MyDbContext _context;
|
|
|
|
public string Name => "query_database";
|
|
public string Description => "Execute read-only SQL queries";
|
|
|
|
public async Task<McpToolResult> ExecuteAsync(
|
|
Dictionary<string, object> parameters,
|
|
CancellationToken ct = default)
|
|
{
|
|
var sql = parameters["sql"].ToString();
|
|
|
|
// Security: Validate read-only query
|
|
if (!IsReadOnlyQuery(sql))
|
|
{
|
|
return McpToolResult.Error("Only SELECT queries allowed");
|
|
}
|
|
|
|
var results = await _context.Database.SqlQueryRaw<object>(sql).ToListAsync(ct);
|
|
return McpToolResult.Success(results);
|
|
}
|
|
}
|
|
```
|
|
|
|
### 3. Document Processing Tool
|
|
|
|
```csharp
|
|
public class ProcessDocumentTool : IMcpTool
|
|
{
|
|
private readonly IDocumentProcessor _processor;
|
|
|
|
public string Name => "process_document";
|
|
public string Description => "Extract text and metadata from uploaded documents";
|
|
|
|
public async Task<McpToolResult> ExecuteAsync(
|
|
Dictionary<string, object> parameters,
|
|
CancellationToken ct = default)
|
|
{
|
|
var filePath = parameters["filePath"].ToString();
|
|
var result = await _processor.ProcessAsync(filePath, ct);
|
|
|
|
return McpToolResult.Success(new
|
|
{
|
|
extractedText = result.Text,
|
|
metadata = result.Metadata,
|
|
pageCount = result.PageCount
|
|
});
|
|
}
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
## Security
|
|
|
|
Svrnty.MCP implements defense-in-depth security:
|
|
|
|
### 1. Permission-Based Access Control
|
|
|
|
```json
|
|
{
|
|
"Mcp": {
|
|
"Security": {
|
|
"DefaultDenyAll": true,
|
|
"Agents": {
|
|
"claude-desktop": {
|
|
"Permissions": [
|
|
"tools:search",
|
|
"tools:read"
|
|
]
|
|
},
|
|
"public-agent": {
|
|
"Permissions": [
|
|
"tools:search"
|
|
]
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
```
|
|
|
|
### 2. Rate Limiting
|
|
|
|
Token bucket algorithm prevents abuse:
|
|
|
|
```json
|
|
{
|
|
"RateLimit": {
|
|
"Enabled": true,
|
|
"RequestsPerMinute": 60,
|
|
"BurstSize": 10
|
|
}
|
|
}
|
|
```
|
|
|
|
### 3. Audit Logging
|
|
|
|
All MCP operations are logged:
|
|
|
|
```csharp
|
|
[2025-10-19 10:15:32] INFO: Agent 'claude-desktop' executed tool 'search_codex' with parameters {"query":"neural networks"} - Success
|
|
[2025-10-19 10:15:45] WARN: Agent 'public-agent' denied access to tool 'delete_document' - Permission 'tools:delete' not granted
|
|
```
|
|
|
|
### 4. Input Validation
|
|
|
|
All tool parameters are validated against schema before execution.
|
|
|
|
---
|
|
|
|
## Testing
|
|
|
|
Svrnty.MCP is built with **Test-Driven Development (TDD)**:
|
|
|
|
```bash
|
|
# Run all tests
|
|
dotnet test
|
|
|
|
# Run with coverage
|
|
dotnet test /p:CollectCoverage=true
|
|
|
|
# Run specific test category
|
|
dotnet test --filter Category=Integration
|
|
```
|
|
|
|
**Test Structure**:
|
|
```
|
|
tests/
|
|
├── Svrnty.MCP.Core.Tests/ # Unit tests (abstractions, models)
|
|
├── Svrnty.MCP.Infrastructure.Tests/ # Unit tests (server, transports, security)
|
|
└── Svrnty.MCP.Integration.Tests/ # End-to-end integration tests
|
|
```
|
|
|
|
**Example Test** (TDD style):
|
|
|
|
```csharp
|
|
// RED: Write failing test first
|
|
[Fact]
|
|
public async Task ExecuteTool_WithInvalidPermissions_ThrowsUnauthorized()
|
|
{
|
|
var server = new McpServer();
|
|
var tool = new SearchTool();
|
|
var agent = new AgentContext { Id = "test", Permissions = [] };
|
|
|
|
await Assert.ThrowsAsync<UnauthorizedAccessException>(
|
|
() => server.ExecuteToolAsync(tool.Name, agent, new Dictionary<string, object>())
|
|
);
|
|
}
|
|
|
|
// GREEN: Implement minimal code to pass
|
|
// REFACTOR: Improve design while keeping tests green
|
|
```
|
|
|
|
See [TDD Guide](docs/tdd-guide.md) for complete examples.
|
|
|
|
### Test Coverage
|
|
|
|
Svrnty.MCP.Server maintains **42.46% line coverage** and **50.00% branch coverage** with **141 tests** passing (100%).
|
|
|
|
**Coverage Breakdown:**
|
|
- **Lines**: 344 of 810 covered (42.46%)
|
|
- **Branches**: 72 of 144 covered (50.00%)
|
|
- **Test Projects**: 2
|
|
- Svrnty.MCP.Core.Tests: 82 tests
|
|
- CodexMcpServer.Tests: 59 tests
|
|
|
|
**Analysis:**
|
|
- Core domain logic has excellent coverage (> 70%)
|
|
- Lower overall percentage due to Program.cs/startup code (not tested by design)
|
|
- HTTP transport and protocol implementation well-tested
|
|
- Production-ready coverage levels for deployment
|
|
|
|
**Coverage Reports:**
|
|
```bash
|
|
# Generate coverage report
|
|
dotnet test --collect:"XPlat Code Coverage" --results-directory ./TestResults
|
|
|
|
# View detailed coverage
|
|
# See: /home/svrnty/codex/COVERAGE-SUMMARY.md for complete analysis
|
|
```
|
|
|
|
**Status**: ✅ Good - Core business logic exceeds 70% coverage threshold
|
|
|
|
---
|
|
|
|
## Configuration Reference
|
|
|
|
### Server Settings
|
|
|
|
| Setting | Type | Default | Description |
|
|
|---------|------|---------|-------------|
|
|
| `Mcp.Server.Name` | string | (required) | MCP server name |
|
|
| `Mcp.Server.Version` | string | "1.0.0" | Server version (semver) |
|
|
| `Mcp.Server.Description` | string | "" | Human-readable description |
|
|
| `Mcp.Server.Vendor` | string | "" | Vendor/organization name |
|
|
|
|
### Transport Settings
|
|
|
|
| Setting | Type | Default | Description |
|
|
|---------|------|---------|-------------|
|
|
| `Mcp.Transport.Type` | enum | "Http" | "Http" (recommended) or "Stdio" (legacy) |
|
|
| `Mcp.Transport.Port` | int | 5050 | HTTP server port |
|
|
| `Mcp.Transport.Options.BufferSize` | int | 8192 | Buffer size (bytes) for stdio |
|
|
| `Mcp.Transport.Options.EnableLogging` | bool | false | Log all I/O |
|
|
|
|
**HTTP Transport** (Production):
|
|
- Supports multiple concurrent clients
|
|
- Load balancing via gateway
|
|
- Health check endpoint (`/health`)
|
|
- Standard REST API patterns
|
|
- Port 5050 (default for MCP servers)
|
|
|
|
**Stdio Transport** (Legacy):
|
|
- One client per process
|
|
- Used by Claude Desktop
|
|
- Local development only
|
|
- Requires `--stdio` command-line flag
|
|
|
|
### Security Settings
|
|
|
|
| Setting | Type | Default | Description |
|
|
|---------|------|---------|-------------|
|
|
| `Mcp.Security.EnablePermissions` | bool | true | Enable permission checks |
|
|
| `Mcp.Security.DefaultDenyAll` | bool | true | Deny by default |
|
|
| `Mcp.Security.RateLimit.Enabled` | bool | true | Enable rate limiting |
|
|
| `Mcp.Security.RateLimit.RequestsPerMinute` | int | 60 | Global rate limit |
|
|
| `Mcp.Security.RateLimit.BurstSize` | int | 10 | Max burst requests |
|
|
| `Mcp.Security.AuditLogging.Enabled` | bool | true | Log all operations |
|
|
|
|
See [Configuration Guide](docs/configuration.md) for complete reference.
|
|
|
|
---
|
|
|
|
## Roadmap
|
|
|
|
### Phase 1: Core Foundation (COMPLETED)
|
|
- [x] Core abstractions (IMcpServer, IMcpTool, models)
|
|
- [x] Basic server implementation
|
|
- [x] Stdio transport
|
|
- [x] Unit tests (118/118 passing)
|
|
- [x] CODEX MCP Server with 6 tools
|
|
- [x] Full TDD implementation (RED → GREEN → REFACTOR)
|
|
|
|
### Phase 2: Security & Reliability (Week 2)
|
|
- [ ] Permission system
|
|
- [ ] Rate limiting
|
|
- [ ] Audit logging
|
|
- [ ] Error handling
|
|
- [ ] Integration tests
|
|
|
|
### Phase 3: ASP.NET Core Integration (Week 3)
|
|
- [ ] DI extensions
|
|
- [ ] Configuration binding
|
|
- [ ] HTTP transport
|
|
- [ ] Health checks
|
|
- [ ] Observability
|
|
|
|
### Phase 4: Production & CODEX (Week 4)
|
|
- [ ] CODEX MCP server implementation
|
|
- [ ] Performance optimization
|
|
- [ ] Documentation
|
|
- [ ] Deployment guide
|
|
- [ ] Release v1.0.0
|
|
|
|
---
|
|
|
|
## Contributing
|
|
|
|
Contributions are welcome! Please read [CONTRIBUTING.md](CONTRIBUTING.md) for guidelines.
|
|
|
|
**Development Setup**:
|
|
```bash
|
|
# Clone repository
|
|
git clone https://github.com/yourusername/Svrnty.MCP.git
|
|
|
|
# Restore dependencies
|
|
dotnet restore
|
|
|
|
# Run tests
|
|
dotnet test
|
|
|
|
# Build all projects
|
|
dotnet build
|
|
```
|
|
|
|
---
|
|
|
|
## Documentation
|
|
|
|
| Document | Description |
|
|
|----------|-------------|
|
|
| [AGENT-PRIMER.md](AGENT-PRIMER.md) | AI-automated setup guide |
|
|
| [Architecture](docs/architecture.md) | Clean architecture design |
|
|
| [Configuration](docs/configuration.md) | Complete configuration reference |
|
|
| [TDD Guide](docs/tdd-guide.md) | Test-driven development examples |
|
|
| [Security](docs/security.md) | Security model and best practices |
|
|
| [**API Reference**](docs/api/) | **Complete API documentation (IMcpServer, IMcpTool, Models)** |
|
|
| [HTTPS Setup Guide](docs/deployment/https-setup.md) | Production TLS/HTTPS configuration |
|
|
|
|
---
|
|
|
|
## License
|
|
|
|
This project is licensed under the MIT License - see the [LICENSE](LICENSE) file for details.
|
|
|
|
---
|
|
|
|
## Support
|
|
|
|
- **Documentation**: [docs/](docs/)
|
|
- **Examples**: [samples/](samples/)
|
|
- **Issues**: [GitHub Issues](https://github.com/yourusername/Svrnty.MCP/issues)
|
|
|
|
---
|
|
|
|
## Acknowledgments
|
|
|
|
- **Anthropic** for the [Model Context Protocol](https://modelcontextprotocol.io) specification
|
|
- **CODEX** for being the first use case and driving requirements
|
|
- **.NET Community** for excellent libraries and tools
|
|
|
|
---
|
|
|
|
**Built with OpenHarbor framework principles: Clean, Modular, Testable, Secure.**
|