Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 9 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ This package supports the **2025-03-26** version of the Model Context Protocol w

- **PHP** >= 8.1
- **Composer**
- **For HTTP Transport**: An event-driven PHP environment (CLI recommended)
- **For HTTP Transport**: An event-driven PHP environment (CLI recommended) and the optional `react/http` package (see Installation)
- **Extensions**: `json`, `mbstring`, `pcre` (typically enabled by default)

## 📦 Installation
Expand All @@ -39,6 +39,14 @@ This package supports the **2025-03-26** version of the Model Context Protocol w
composer require php-mcp/server
```

The HTTP transports need `react/http`, which is an optional dependency so that
projects using only the stdio transport or their own framework integration are
not tied to its dependency tree:

```bash
composer require react/http
```

> **💡 Laravel Users**: Consider using [`php-mcp/laravel`](https://github.com/php-mcp/laravel) for enhanced framework integration, configuration management, and Artisan commands.

## ⚡ Quick Start: Stdio Server with Discovery
Expand Down
6 changes: 4 additions & 2 deletions composer.json
Original file line number Diff line number Diff line change
Expand Up @@ -29,10 +29,10 @@
"phpdocumentor/reflection-docblock": "^5.6",
"psr/clock": "^1.0",
"psr/container": "^1.0 || ^2.0",
"psr/http-message": "^1.0 || ^2.0",
"psr/log": "^1.0 || ^2.0 || ^3.0",
"psr/simple-cache": "^1.0 || ^2.0 || ^3.0",
"react/event-loop": "^1.5",
"react/http": "^1.11",
"react/promise": "^3.0",
"react/stream": "^1.4",
"symfony/finder": "^6.4 || ^7.2"
Expand All @@ -43,10 +43,12 @@
"pestphp/pest": "^2.36.0|^3.5.0",
"react/async": "^4.0",
"react/child-process": "^0.6.6",
"react/http": "^1.11",
"symfony/var-dumper": "^6.4.11|^7.1.5"
},
"suggest": {
"ext-pcntl": "For signal handling support when using StdioServerTransport with StreamSelectLoop"
"ext-pcntl": "For signal handling support when using StdioServerTransport with StreamSelectLoop",
"react/http": "Required for HttpServerTransport and StreamableHttpServerTransport (^1.11)"
},
"autoload": {
"psr-4": {
Expand Down
6 changes: 6 additions & 0 deletions src/Transports/HttpServerTransport.php
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,12 @@ public function __construct(
private readonly ?array $sslContext = null,
private array $middlewares = []
) {
if (! class_exists(HttpServer::class)) {
throw new TransportException(
'react/http is not installed. It is an optional dependency, required only by the HTTP transports. Install it with "composer require react/http".'
);
}

$this->logger = new NullLogger();
$this->loop = Loop::get();
$this->ssePath = '/' . trim($mcpPathPrefix, '/') . '/sse';
Expand Down
6 changes: 6 additions & 0 deletions src/Transports/StreamableHttpServerTransport.php
Original file line number Diff line number Diff line change
Expand Up @@ -82,6 +82,12 @@ public function __construct(
?EventStoreInterface $eventStore = null,
private array $middlewares = []
) {
if (! class_exists(HttpServer::class)) {
throw new TransportException(
'react/http is not installed. It is an optional dependency, required only by the HTTP transports. Install it with "composer require react/http".'
);
}

$this->logger = new NullLogger();
$this->loop = Loop::get();
$this->mcpPath = '/' . trim($mcpPath, '/');
Expand Down