1. Conduid
  2. AI
  3. Fastmcphp
MCP server · AI

Fastmcphp

PHP 8.2+ implementation of the Model Context Protocol (MCP) using Swoole

Unclaimed ai
34Low

Scored 7 months ago · breakdown

About Fastmcphp

Fastmcphp is an MCP server in the AI category: pHP 8.2+ implementation of the Model Context Protocol (MCP) using Swoole.

Install

From source
git clone https://github.com/mfrederico/fastmcphp

This server has no ConduID identity, so agent calls to it are not receipted. Pin the version you install and review the source before granting it credentials.

Ask AI

✦

Ask AI about Fastmcphp

Powered by Claude · Grounded in docs

I know everything about Fastmcphp. Ask me about installation, configuration, usage, or troubleshooting.

Security checks

  • ✓README presentThe repository ships documentation.

5 checks have not been run yet.

README

Fastmcphp

NOTE:

A PHP 8.2+ implementation of the Model Context Protocol (MCP).

Inspired by FastMCP for Python.

Requirements

  • PHP 8.2+
  • Swoole 5.0+ or OpenSwoole 4.0+ (optional, recommended for production HTTP/SSE)

Installation

composer require fastmcphp/fastmcphp

Quick Start

<?php

use Fastmcphp\Fastmcphp;

$mcp = new Fastmcphp('My Server');

// Register a tool
$mcp->tool(
    callable: fn(string $text) => $text,
    name: 'echo',
    description: 'Echo the input text',
);

// Register a resource
$mcp->resource(
    uri: 'config://app',
    callable: fn() => ['version' => '1.0.0'],
    name: 'config',
);

// Run with stdio transport
$mcp->run();

Features

Tools

Define callable functions that can be invoked by MCP clients:

// Simple tool
$mcp->tool(
    callable: fn(int $a, int $b) => $a + $b,
    name: 'add',
    description: 'Add two numbers',
);

// Tool with context injection
$mcp->tool(
    callable: function(string $query, Context $ctx): array {
        $ctx->info("Searching for: {$query}");
        return ['results' => []];
    },
    name: 'search',
);

Resources

Expose data via URI-based resources:

// Static resource
$mcp->resource(
    uri: 'config://database',
    callable: fn() => ['host' => 'localhost', 'port' => 5432],
);

// Parameterized resource (template)
$mcp->resource(
    uri: 'users://{id}',
    callable: fn(int $id) => getUserById($id),
);

Prompts

Define reusable prompt templates:

use Fastmcphp\Prompts\Message;

$mcp->prompt(
    callable: fn(string $topic) => [
        Message::user("Explain {$topic} in simple terms"),
    ],
    name: 'explain',
);

Transports

Three transport modes are supported:

// Stdio (default) - for subprocess communication
$mcp->run(transport: 'stdio');

// HTTP - JSON-RPC over HTTP (falls back to built-in PHP server without Swoole)
$mcp->run(transport: 'http', host: '0.0.0.0', port: 8080);

// SSE - Server-Sent Events (deprecated, use HTTP instead)
$mcp->run(transport: 'sse', host: '0.0.0.0', port: 8080);

The HTTP transport automatically detects whether Swoole/OpenSwoole is installed. With Swoole, it runs a high-performance async server with multiple workers. Without Swoole, it uses ReactPHP's event-loop-based HTTP server (async, single-process). Swoole is recommended for production deployments.

Authentication

Implement custom authentication providers for bearer tokens, API keys, or any auth system:

use Fastmcphp\Server\Auth\AuthProviderInterface;
use Fastmcphp\Server\Auth\AuthRequest;
use Fastmcphp\Server\Auth\AuthResult;
use Fastmcphp\Server\Auth\AuthenticatedUser;

class MyAuthProvider implements AuthProviderInterface
{
    public function authenticate(AuthRequest $request): AuthResult
    {
        $token = $request->getBearerToken();

        if (!$token) {
            return AuthResult::unauthenticated();
        }

        // Validate token against your auth system
        $user = $this->validateToken($token);

        if (!$user) {
            return AuthResult::failed('Invalid token');
        }

        return AuthResult::success(new AuthenticatedUser(
            id: $user['id'],
            name: $user['name'],
            level: $user['level'],
            scopes: $user['scopes'],
            workspace: $user['workspace'],
        ));
    }
}

// Use the auth provider
$mcp->setAuth(new MyAuthProvider(), required: true);

AuthRequest

AuthRequest is the abstraction layer between transports and authentication. It normalizes request data from any transport (Swoole HTTP, built-in PHP HTTP, SSE) so auth providers don't need to know transport details.

Token extraction — use getToken() for automatic priority-based lookup:

  1. X-API-TOKEN header (via getApiToken())
  2. Authorization: Bearer <token> header (via getBearerToken())
  3. ?key=<token> query parameter (via getApiKeyFromQuery())

Available methods:

Method Description
getToken() Get token from any source (priority order above)
getHeader(string $name) Get any header value (case-insensitive)
getBearerToken() Extract token from Authorization: Bearer header
getApiToken() Get X-API-TOKEN header value
getApiKeyFromQuery(string $param = 'key') Get token from query parameter
getQuery(string $key) Get any query parameter

Sending tokens from clients:

# Using Authorization header (recommended)
curl -X POST http://localhost:8080/mcp \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer your-token-here" \
  -d '{"jsonrpc":"2.0","id":1,"method":"tools/list","params":{}}'

# Using X-API-TOKEN header
curl -X POST http://localhost:8080/mcp \
  -H "Content-Type: application/json" \
  -H "X-API-TOKEN: your-token-here" \
  -d '{"jsonrpc":"2.0","id":1,"method":"tools/list","params":{}}'

# Using query parameter
curl -X POST "http://localhost:8080/mcp?key=your-token-here" \
  -H "Content-Type: application/json" \
  -d '{"jsonrpc":"2.0","id":1,"method":"tools/list","params":{}}'

Per-Tool Authorization

Control access to individual tools, resources, or prompts:

use Fastmcphp\Server\Auth\AuthorizationContext;

// Admin-only tool
$mcp->tool(
    callable: fn() => 'sensitive data',
    name: 'admin_tool',
    auth: fn(AuthorizationContext $ctx) => $ctx->user->hasLevel(50), // ADMIN level
);

// Scope-based authorization
$mcp->tool(
    callable: fn(string $query) => search($query),
    name: 'search',
    auth: fn(AuthorizationContext $ctx) => $ctx->user->hasScope('tools:search'),
);

Middleware

Intercept and modify requests/responses:

use Fastmcphp\Server\Middleware\Middleware;
use Fastmcphp\Server\Middleware\MiddlewareContext;

class LoggingMiddleware extends Middleware
{
    public function onCallTool(MiddlewareContext $ctx, callable $next): mixed
    {
        $toolName = $ctx->getToolName();
        $user = $ctx->user?->name ?? 'anonymous';

        echo "[{$user}] Calling tool: {$toolName}\n";

        $start = microtime(true);
        $result = $next($ctx);
        $elapsed = microtime(true) - $start;

        echo "[{$user}] Tool completed in {$elapsed}s\n";

        return $result;
    }
}

$mcp->addMiddleware(new LoggingMiddleware());

Multi-Tenant Workspace Support

Fastmcphp supports multi-tenant architectures through the authentication system:

// Auth provider returns workspace context
return AuthResult::success($user, workspace: 'tenant-123');

// Workspace is available in middleware and authorization
$mcp->tool(
    callable: fn() => getWorkspaceData(),
    name: 'get_data',
    auth: fn(AuthorizationContext $ctx) => $ctx->workspace === 'allowed-tenant',
);

Usage with Claude Code

Add your MCP server to .mcp.json in your project root (or ~/.claude/.mcp.json for global access):

Stdio transport (subprocess — Claude Code manages the process):

{
  "mcpServers": {
    "my-server": {
      "command": "php",
      "args": ["path/to/your/server.php"]
    }
  }
}

HTTP transport (remote — start the server separately):

{
  "mcpServers": {
    "my-server": {
      "type": "http",
      "url": "http://localhost:8080/mcp"
    }
  }
}

HTTP with authentication:

{
  "mcpServers": {
    "my-server": {
      "type": "http",
      "url": "http://localhost:8080/mcp",
      "headers": {
        "Authorization": "Bearer your-token-here"
      }
    }
  }
}

Testing

# Test stdio transport
echo '{"jsonrpc":"2.0","id":1,"method":"initialize","params":{}}' | php examples/echo_server.php

# Test tools/list
echo '{"jsonrpc":"2.0","id":2,"method":"tools/list","params":{}}' | php examples/echo_server.php

# Test tools/call
echo '{"jsonrpc":"2.0","id":3,"method":"tools/call","params":{"name":"echo","arguments":{"text":"Hello!"}}}' | php examples/echo_server.php

# Test authenticated HTTP server
php examples/authenticated_server.php &
curl -X POST http://localhost:8080/mcp \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer user-token-123" \
  -d '{"jsonrpc":"2.0","id":1,"method":"tools/list","params":{}}'

MCP Protocol Support

Feature Status
Tools ✅
Resources ✅
Resource Templates ✅
Prompts ✅
Stdio Transport ✅
HTTP Transport ✅
SSE Transport ✅
Authentication ✅
Middleware ✅
Per-Component Auth ✅
Scopes ✅
Multi-Tenant ✅
Pagination ❌

License

MIT

README copy captured when this server was indexed; it may lag the repository. The original is authoritative.

Questions

About Fastmcphp

How do I install Fastmcphp?

No package has been published for this server, so install it from source: clone the repository and follow its README.

Is Fastmcphp safe to use with an AI agent?

Its trust score is 34 out of 100 (low). It passes 1 of the 1 static security checks run so far. It has no ConduID identity yet, so agent calls to it are not receipted.

Is Fastmcphp still maintained?

Conduid hasn't recorded a commit date for this repository yet. Check the repository directly for recent activity.