diff --git a/src/mcp-bundle/composer.json b/src/mcp-bundle/composer.json index 2bf13ec11..bf05aa7dc 100644 --- a/src/mcp-bundle/composer.json +++ b/src/mcp-bundle/composer.json @@ -24,7 +24,8 @@ "require-dev": { "phpstan/phpstan": "^2.1", "phpstan/phpstan-strict-rules": "^2.0", - "phpunit/phpunit": "^11.5" + "phpunit/phpunit": "^11.5", + "symfony/monolog-bundle": "^3.10" }, "minimum-stability": "dev", "prefer-stable": true, diff --git a/src/mcp-bundle/config/services.php b/src/mcp-bundle/config/services.php index 9f836a81b..9bf56d7e2 100644 --- a/src/mcp-bundle/config/services.php +++ b/src/mcp-bundle/config/services.php @@ -13,24 +13,33 @@ use Mcp\Server; use Mcp\Server\Builder; +use Symfony\Bundle\MonologBundle\MonologBundle; return static function (ContainerConfigurator $container): void { - $container->services() - ->set('monolog.logger.mcp') - ->parent('monolog.logger_prototype') - ->args(['mcp']) - ->tag('monolog.logger', ['channel' => 'mcp']) + if (class_exists(MonologBundle::class)) { + $container->services() + ->set('monolog.logger.mcp') + ->parent('monolog.logger_prototype') + ->args(['mcp']) + ->tag('monolog.logger', ['channel' => 'mcp']) + ; + } + $builderDefinition = $container->services() ->set('mcp.server.builder', Builder::class) ->factory([Server::class, 'builder']) ->call('setServerInfo', [param('mcp.app'), param('mcp.version')]) ->call('setPaginationLimit', [param('mcp.pagination_limit')]) ->call('setInstructions', [param('mcp.instructions')]) - ->call('setLogger', [service('monolog.logger.mcp')]) ->call('setEventDispatcher', [service('event_dispatcher')]) ->call('setSession', [service('mcp.session.store')]) - ->call('setDiscovery', [param('kernel.project_dir'), param('mcp.discovery.scan_dirs'), param('mcp.discovery.exclude_dirs')]) + ->call('setDiscovery', [param('kernel.project_dir'), param('mcp.discovery.scan_dirs'), param('mcp.discovery.exclude_dirs')]); + + if (class_exists(MonologBundle::class)) { + $builderDefinition->call('setLogger', [service('monolog.logger.mcp')]); + } + $container->services() ->set('mcp.server', Server::class) ->factory([service('mcp.server.builder'), 'build']) diff --git a/src/mcp-bundle/src/Command/McpCommand.php b/src/mcp-bundle/src/Command/McpCommand.php index f939ffc10..5abf26dff 100644 --- a/src/mcp-bundle/src/Command/McpCommand.php +++ b/src/mcp-bundle/src/Command/McpCommand.php @@ -24,14 +24,16 @@ class McpCommand extends Command { public function __construct( private readonly Server $server, - private readonly LoggerInterface $logger, + private readonly ?LoggerInterface $logger = null, ) { parent::__construct(); } protected function execute(InputInterface $input, OutputInterface $output): int { - $transport = new StdioTransport(logger: $this->logger); + $transport = $this->logger + ? new StdioTransport(logger: $this->logger) + : new StdioTransport(); $this->server->run($transport); return Command::SUCCESS; diff --git a/src/mcp-bundle/src/Controller/McpController.php b/src/mcp-bundle/src/Controller/McpController.php index 54d19df3d..7e5d891f6 100644 --- a/src/mcp-bundle/src/Controller/McpController.php +++ b/src/mcp-bundle/src/Controller/McpController.php @@ -35,12 +35,18 @@ public function __construct( public function handle(Request $request): Response { - $transport = new StreamableHttpTransport( - $this->httpMessageFactory->createRequest($request), - $this->responseFactory, - $this->streamFactory, - logger: $this->logger, - ); + $transport = $this->logger + ? new StreamableHttpTransport( + $this->httpMessageFactory->createRequest($request), + $this->responseFactory, + $this->streamFactory, + logger: $this->logger, + ) + : new StreamableHttpTransport( + $this->httpMessageFactory->createRequest($request), + $this->responseFactory, + $this->streamFactory, + ); return $this->httpFoundationFactory->createResponse( $this->server->run($transport), diff --git a/src/mcp-bundle/src/McpBundle.php b/src/mcp-bundle/src/McpBundle.php index bec84d4fd..25080dddf 100644 --- a/src/mcp-bundle/src/McpBundle.php +++ b/src/mcp-bundle/src/McpBundle.php @@ -114,7 +114,7 @@ private function configureClient(array $transports, array $httpConfig, Container $container->register('mcp.server.command', McpCommand::class) ->setArguments([ new Reference('mcp.server'), - new Reference('logger'), + new Reference('monolog.logger.mcp', ContainerInterface::NULL_ON_INVALID_REFERENCE), ]) ->addTag('console.command'); } diff --git a/src/mcp-bundle/tests/DependencyInjection/McpBundleTest.php b/src/mcp-bundle/tests/DependencyInjection/McpBundleTest.php index 976811ba4..2b456051b 100644 --- a/src/mcp-bundle/tests/DependencyInjection/McpBundleTest.php +++ b/src/mcp-bundle/tests/DependencyInjection/McpBundleTest.php @@ -14,6 +14,7 @@ use PHPUnit\Framework\Attributes\DataProvider; use PHPUnit\Framework\TestCase; use Symfony\AI\McpBundle\McpBundle; +use Symfony\Bundle\MonologBundle\MonologBundle; use Symfony\Component\DependencyInjection\ContainerBuilder; class McpBundleTest extends TestCase @@ -49,6 +50,10 @@ public function testCustomConfiguration() public function testMcpLoggerServiceIsCreated() { + if (!class_exists(MonologBundle::class)) { + $this->markTestSkipped('MonologBundle is not installed'); + } + $container = $this->buildContainer([]); $this->assertTrue($container->hasDefinition('monolog.logger.mcp'));