关于 Laravel MCP Server by OP.GG
Laravel MCP Server 是 OP.GG 开发的 Laravel 扩展包,用于在 Laravel 和 Lumen 中通过路由注册 MCP 端点。它基于 Streamable HTTP 传输,面向需要在 PHP 项目中构建可扩展 MCP 服务的团队。
主要功能
- 01基于路由注册 MCP 端点
- 02仅支持 Streamable HTTP 传输
- 03按端点注册工具、资源、资源模板与提示词
- 04根据查询参数动态过滤工具集
- 05由 OpenAPI 规范生成 MCP 工具
适用场景
- 01在现有 Laravel 应用中提供 MCP 接口
- 02将 Swagger/OpenAPI 接口转换为 MCP 工具
- 03按 URL 参数为不同客户端暴露不同工具集
MCP 相关
作为 MCP 服务端,它将已注册的工具、资源、提示词和通知处理器通过 Route::mcp 端点暴露给 MCP 客户端,并支持路由缓存。
配置
本地服务的配置在各客户端中通用,复制后粘贴到客户端的 MCP 配置文件即可。
我们还没有获取到这个服务的安装包或远程地址,请按项目 README 中的说明安装。
工具
本地服务需要在你的电脑上运行后才能读取工具,维护者暂未提供工具列表。
详细介绍
OP.GG 的 Laravel MCP 服务
在 Laravel 和 Lumen 中构建路由优先的 MCP 服务
English | Português do Brasil | 한국어 | Русский | 简体中文 | 繁體中文 | Polski | Español
2.0.0 重大变更
- 端点设置从配置驱动的注册改为路由驱动的注册。
- 仅支持 Streamable HTTP 传输。
- 服务元数据修改方法已合并到
setServerInfo(...)。 - 运行时已移除旧版工具传输方法(
messageType()、ProcessMessageType::SSE)。
完整迁移指南:docs/migrations/v2.0.0-migration.md
概述
Laravel MCP Server 为 Laravel 和 Lumen 提供基于路由的 MCP 端点注册。
要点:
- Streamable HTTP 传输
- 路由优先配置(
Route::mcp(...)/McpRoute::register(...)) - 为每个端点注册工具、资源、资源模板和提示词
- 端点元数据兼容路由缓存
要求
- PHP >= 8.2
- Laravel(Illuminate)>= 9.x
- Lumen >= 9.x(可选)
快速开始
1) 安装
composer require opgginc/laravel-mcp-server
2) 注册端点(Laravel)
use Illuminate\Support\Facades\Route;
use OPGG\LaravelMcpServer\Enums\ProtocolVersion;
use OPGG\LaravelMcpServer\Services\ToolService\Examples\HelloWorldTool;
use OPGG\LaravelMcpServer\Services\ToolService\Examples\VersionCheckTool;
Route::mcp('/mcp')
->setServerInfo(
name: 'OP.GG MCP Server',
version: '2.0.0',
)
->setConfig(
compactEnumExampleCount: 3,
)
->setProtocolVersion(ProtocolVersion::V2025_11_25)
->enabledApi()
->tools([
HelloWorldTool::class,
VersionCheckTool::class,
]);
如果需要兼容不支持 2025-11-25 的客户端,请设置:
->setProtocolVersion(ProtocolVersion::V2025_06_18)
3) 验证
php artisan route:list | grep mcp
php artisan mcp:test-tool --list --endpoint=/mcp
快速 JSON-RPC 检查:
curl -X POST http://localhost:8000/mcp \
-H "Content-Type: application/json" \
-d '{"jsonrpc":"2.0","id":1,"method":"tools/list"}'
按查询字符串动态筛选工具
如果某个端点需要根据传入 URL 提供不同的工具集,可为路由附加动态工具解析器。 解析器负责该端点声明的工具目录,以及每个请求中可见的子集。
use OPGG\LaravelMcpServer\Data\ToolResolutionContext;
use OPGG\LaravelMcpServer\Routing\McpEndpointDefinition;
use OPGG\LaravelMcpServer\Services\ToolService\DynamicToolResolverInterface;
final class LolPhaseToolResolver implements DynamicToolResolverInterface
{
public function declaredTools(McpEndpointDefinition $endpoint): array
{
return [
\App\MCP\Tools\LolSearchChampionMetaTool::class,
\App\MCP\Tools\LolGetChampionAnalysisTool::class,
\App\MCP\Tools\LolGetLiveItemRecommendationsTool::class,
];
}
public function resolve(
McpEndpointDefinition $endpoint,
ToolResolutionContext $context,
): array {
return match ($context->queryParameters['phase'] ?? null) {
'lobby' => [
\App\MCP\Tools\LolSearchChampionMetaTool::class,
\App\MCP\Tools\LolGetChampionAnalysisTool::class,
],
'inprogress' => [
\App\MCP\Tools\LolGetLiveItemRecommendationsTool::class,
],
default => $this->declaredTools($endpoint),
};
}
public function consumedQueryParameters(): array
{
return ['phase'];
}
}
Route::mcp('/mcp/voice/lol/live')
->setServerInfo(
name: 'OP.GG MCP Server - Voice lol Live',
version: '1.0.0',
)
->dynamicTools(LolPhaseToolResolver::class);
请求示例:
/mcp/voice/lol/live?phase=lobby
/mcp/voice/lol/live?phase=inprogress
相同的筛选工具集会一致地应用于:
tools/listtools/calltools/execute- 启用
->enabledApi()时的POST /tools/{tool_name}
如果同一端点还使用 POST /tools/{tool_name},可以选择在解析器中公开一个
consumedQueryParameters(): array 钩子,指定仅用于筛选、不转发为工具参数的查询键。此钩子是文档约定,
不属于 DynamicToolResolverInterface;未实现该钩子的解析器会将这些查询键转发为工具参数。
Lumen 设置
// bootstrap/app.php
$app->withFacades();
$app->withEloquent();
$app->register(OPGG\LaravelMcpServer\LaravelMcpServerServiceProvider::class);
use OPGG\LaravelMcpServer\Routing\McpRoute;
use OPGG\LaravelMcpServer\Services\ToolService\Examples\HelloWorldTool;
McpRoute::register('/mcp')
->setServerInfo(
name: 'OP.GG MCP Server',
version: '2.0.0',
)
->tools([
HelloWorldTool::class,
]);
最低安全配置(生产环境)
在 MCP 路由组中使用 Laravel 中间件。
use Illuminate\Support\Facades\Route;
Route::middleware([
'auth:sanctum',
'throttle:100,1',
])->group(function (): void {
Route::mcp('/mcp')
->setServerInfo(
name: 'Secure MCP',
version: '2.0.0',
)
->tools([
\App\MCP\Tools\MyCustomTool::class,
]);
});
v2.0.0 迁移说明(从 v1.0.0 迁移)
- MCP 端点设置已从配置迁移至路由注册。
- 仅支持 Streamable HTTP 传输。
- 服务元数据修改方法已合并到
setServerInfo(...)。 - 提供了用于迁移旧版签名的工具迁移命令:
php artisan mcp:migrate-tools
完整指南:docs/migrations/v2.0.0-migration.md
高级功能(快速链接)
- 创建工具:
php artisan make:mcp-tool ToolName - 创建资源:
php artisan make:mcp-resource ResourceName - 创建资源模板:
php artisan make:mcp-resource-template TemplateName - 创建提示词:
php artisan make:mcp-prompt PromptName - 创建通知:
php artisan make:mcp-notification HandlerName --method=notifications/method - 从 OpenAPI 生成:
php artisan make:swagger-mcp-tool <spec-url-or-file> - 将工具导出为 OpenAPI:
php artisan mcp:export-openapi --output=storage/api-docs-mcp/api-docs.json
代码参考:
- 工具示例:
src/Services/ToolService/Examples/ - 资源示例:
src/Services/ResourceService/Examples/ - 提示词服务:
src/Services/PromptService/ - 通知处理器:
src/Server/Notification/ - 路由构建器:
src/Routing/McpRouteBuilder.php
Swagger/OpenAPI → MCP 工具
从 Swagger/OpenAPI 规范生成 MCP 工具:
# From URL
php artisan make:swagger-mcp-tool https://api.example.com/openapi.json
# From local file
php artisan make:swagger-mcp-tool ./specs/openapi.json
实用选项:
php artisan make:swagger-mcp-tool ./specs/openapi.json \
--group-by=tag \
--prefix=Billing \
--test-api
--group-by:tag、path或none--prefix:生成的工具/资源的类名前缀--test-api:生成前测试端点的连通性
生成行为:
- 在交互模式下,可以为每个端点选择工具或资源。
- 在非交互模式下,
GET端点会生成为资源,其他方法会生成为工具。
增强的交互式预览
如果运行命令时未指定 --group-by,生成器会在创建前显示文件夹结构和文件数量的交互式预览。
php artisan make:swagger-mcp-tool ./specs/openapi.json
预览输出示例:
Choose how to organize your generated tools and resources:
Tag-based grouping (organize by OpenAPI tags)
Total: 25 endpoints -> 15 tools + 10 resources
Examples: Tools/Pet, Tools/Store, Tools/User
Path-based grouping (organize by API path)
Total: 25 endpoints -> 15 tools + 10 resources
Examples: Tools/Api, Tools/Users, Tools/Orders
No grouping (everything in root folder)
Total: 25 endpoints -> 15 tools + 10 resources
Examples: Tools/, Resources/
生成后,在 MCP 端点上注册生成的工具类:
use Illuminate\Support\Facades\Route;
Route::mcp('/mcp')
->setServerInfo(
name: 'Generated MCP Server',
version: '2.0.0',
)
->tools([
\App\MCP\Tools\Billing\CreateInvoiceTool::class,
\App\MCP\Tools\Billing\UpdateInvoiceTool::class,
]);
将 MCP 工具导出为 OpenAPI
使用每个工具的 inputSchema(),将所有已注册的 ToolInterface 类(通过 Route::mcp(...)->tools([...]) 或 ->dynamicTools(...))导出为 OpenAPI JSON 文档。
只有配置了 ->enabledApi() 的端点才会包含在导出内容中,并通过 POST /tools/{tool_name} 对外提供。
操作会使用 OpenAPI tags 按端点 name 分组。
如果多个端点注册了同名工具,操作会保留首次注册时的行为,并将所有匹配的端点名称合并到 tags 中。
如果缺少路由注册,命令会自动在默认路径 app/MCP/Tools 和 app/Tools 下发现工具。
# Default output: storage/api-docs-mcp/api-docs.json
php artisan mcp:export-openapi
# Custom output + metadata
php artisan mcp:export-openapi \
--output=storage/app/mcp.openapi.json \
--title="MCP Tools API" \
--api-version=2.1.0
# Limit to one endpoint (id or path)
php artisan mcp:export-openapi --endpoint=/mcp
# Discover tools from additional directory paths
php artisan mcp:export-openapi --discover-path=app/MCP/Tools
# Existing output is overwritten by default
php artisan mcp:export-openapi
启用工具 API 路由生成:
use Illuminate\Support\Facades\Route;
Route::mcp('/mcp')
->setServerInfo(name: 'OP.GG MCP Server', version: '2.0.0')
->enabledApi()
->tools([
\App\MCP\Tools\GreetingTool::class,
]);
Swagger UI 测试提示:
- 导出的操作仅使用
query parameters(不包含requestBody),以便简化手动测试。 - 每个工具
inputSchema().required中的必填字段都会反映在 Swagger 参数校验中。 - 枚举字段会以
schema.enum导出,以便 Swagger 显示下拉选项。 - 数组字段会以
style=form+explode=true导出(重复键格式,例如desired_output_fields=items&desired_output_fields=runes)。 /tools/{tool_name}的参数解析优先使用查询参数,而非 body/form 载荷,以避免 Swagger 冲突。- 未显式指定
default/example的枚举字段会自动填入第一个枚举值(或第一个非 null 枚举值)。 - 描述中包含
e.g., en_US, ko_KR, ja_JP等内容的字符串字段会自动将第一个示例值推断为default和example。
工具类示例
<?php
namespace App\MCP\Tools;
use App\Enums\Platform;
use OPGG\LaravelMcpServer\JsonSchema\JsonSchema;
use OPGG\LaravelMcpServer\Services\ToolService\ToolInterface;
class GreetingTool implements ToolInterface
{
public function name(): string
{
return 'greeting-tool';
}
public function description(): string
{
return 'Return a greeting message.';
}
public function inputSchema(): array
{
return [
'name' => JsonSchema::string()
->description('Developer Name')
->required(),
'platform' => JsonSchema::string()
->enum(Platform::class)
->description('Client platform')
->compact(),
];
}
public function annotations(): array
{
return [
'readOnlyHint' => true,
'destructiveHint' => false,
];
}
public function execute(array $arguments): mixed
{
return [
'message' => 'Hello '.$arguments['name'],
];
}
}
JsonSchema 构建器(Laravel 风格)
此软件包在 OPGG\LaravelMcpServer 命名空间下提供自己的 JsonSchema 构建器。
你可以使用 Laravel 12 风格的流畅格式定义工具架构,同时保留 inputSchema(): array。
<?php
namespace App\MCP\Tools;
use App\Enums\Platform;
use OPGG\LaravelMcpServer\JsonSchema\JsonSchema;
use OPGG\LaravelMcpServer\Services\ToolService\ToolInterface;
class WeatherTool implements ToolInterface
{
public function name(): string
{
return 'weather-tool';
}
public function description(): string
{
return 'Get weather by location.';
}
public function inputSchema(): array
{
return [
'location' => JsonSchema::string()
->description('Location to query')
->required(),
'platform' => JsonSchema::string()
->enum(Platform::class)
->description('Client platform'),
'days' => JsonSchema::integer()
->min(1)
->max(7)
->default(1),
];
}
public function annotations(): array
{
return [];
}
public function execute(array $arguments): mixed
{
return ['ok' => true];
}
}
说明:
- 仍支持现有的完整 JSON Schema 数组。
enum()接受数组或BackedEnum::class。- 在
enum()后链式调用compact(),可以从生成的架构中移除enum,并在description中追加紧凑提示(compact()、compact(null)、compact(3)或compact('custom hint'))。 - 默认紧凑示例数量为
3,也可以通过Route::mcp(...)->setConfig(compactEnumExampleCount: N)按端点覆盖。 - 导出时(
tools/list、OpenAPI),属性映射会自动规范化为 JSON Schema 对象格式。
示例提示词类
<?php
namespace App\MCP\Prompts;
use OPGG\LaravelMcpServer\Services\PromptService\Prompt;
class WelcomePrompt extends Prompt
{
public string $name = 'welcome-user';
public ?string $description = 'Generate a welcome message.';
public array $arguments = [
[
'name' => 'username',
'description' => 'User name',
'required' => true,
],
];
public string $text = 'Welcome, {username}!';
}
示例资源类
<?php
namespace App\MCP\Resources;
use OPGG\LaravelMcpServer\Services\ResourceService\Resource;
class BuildInfoResource extends Resource
{
public string $uri = 'app://build-info';
public string $name = 'Build Info';
public ?string $mimeType = 'application/json';
public function read(): array
{
return [
'uri' => $this->uri,
'mimeType' => $this->mimeType,
'text' => json_encode([
'version' => '2.0.0',
'environment' => app()->environment(),
], JSON_THROW_ON_ERROR),
];
}
}
在路由上注册示例
use App\MCP\Prompts\WelcomePrompt;
use App\MCP\Resources\BuildInfoResource;
use App\MCP\Tools\GreetingTool;
use Illuminate\Support\Facades\Route;
Route::mcp('/mcp')
->setServerInfo(
name: 'Example MCP Server',
version: '2.0.0',
)
->tools([GreetingTool::class])
->resources([BuildInfoResource::class])
->prompts([WelcomePrompt::class]);
测试和质量检查命令
vendor/bin/pest
vendor/bin/phpstan analyse
vendor/bin/pint
翻译
pip install -r scripts/requirements.txt
export ANTHROPIC_API_KEY='your-api-key'
python scripts/translate_readme.py
翻译指定语言:
python scripts/translate_readme.py es ko
许可证
本项目根据 MIT 许可证发行。
评论
一个开放协议,规定了 AI 应用如何以统一方式连接外部工具与数据源。客户端负责与模型对话,MCP 服务负责提供工具、资源和提示模板,两者通过标准消息通信,同一个服务可以被不同客户端复用。