Fix MCP initialization timeout and add daemon management

- Fix protocol version mismatch (0.1.0 -> 2024-11-05)
- Fix server mode blocking on startup causing Claude Desktop timeout
- Add --version flag to show version information
- Implement proper daemon cleanup when starting new daemon
- Add kill_daemon_with_children() to properly terminate process tree
- Fix dictionary iteration error during shutdown
- Ensure sparse mode is always enabled (3 tools only)
- Fix async stdin reading in base server to prevent EOF loops
- Add syslog support for server mode logging
- Switch from stdin.read() to readline() for proper JSON-RPC handling
- Add comprehensive MCP protocol test suite

The tool now works correctly as an MCP proxy between Claude Desktop
and MCP servers with additional built-in tools.

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
Claude4Ξlope 2025-06-27 22:00:32 +02:00
parent 6df97a9dcf
commit 5aacf468a4
13 changed files with 1156 additions and 91 deletions

381
.tags
View File

@ -5,184 +5,537 @@
!_TAG_PROGRAM_URL http://ctags.sourceforge.net /official site/ !_TAG_PROGRAM_URL http://ctags.sourceforge.net /official site/
!_TAG_PROGRAM_VERSION Development // !_TAG_PROGRAM_VERSION Development //
AIAssistant examples/ai_optimized.py /^class AIAssistant:$/;" c AIAssistant examples/ai_optimized.py /^class AIAssistant:$/;" c
BaseMCPServer build/lib/mcp_servers/base.py /^class BaseMCPServer(ABC):$/;" c
BaseMCPServer mcp_servers/base.py /^class BaseMCPServer(ABC):$/;" c BaseMCPServer mcp_servers/base.py /^class BaseMCPServer(ABC):$/;" c
ConfigLoader build/lib/mcp_browser/config.py /^class ConfigLoader:$/;" c
ConfigLoader mcp_browser/config.py /^class ConfigLoader:$/;" c ConfigLoader mcp_browser/config.py /^class ConfigLoader:$/;" c
ConfigManager build/lib/mcp_browser/default_configs.py /^class ConfigManager:$/;" c
ConfigManager mcp_browser/default_configs.py /^class ConfigManager:$/;" c
DEFAULT_CONFIG build/lib/mcp_browser/config.py /^ DEFAULT_CONFIG = {$/;" v class:ConfigLoader
DEFAULT_CONFIG mcp_browser/config.py /^ DEFAULT_CONFIG = {$/;" v class:ConfigLoader DEFAULT_CONFIG mcp_browser/config.py /^ DEFAULT_CONFIG = {$/;" v class:ConfigLoader
DEFAULT_CONFIGS build/lib/mcp_browser/default_configs.py /^DEFAULT_CONFIGS = {$/;" v
DEFAULT_CONFIGS mcp_browser/default_configs.py /^DEFAULT_CONFIGS = {$/;" v
Decision build/lib/mcp_servers/memory/memory_server.py /^class Decision:$/;" c
Decision mcp_servers/memory/memory_server.py /^class Decision:$/;" c Decision mcp_servers/memory/memory_server.py /^class Decision:$/;" c
GenerateAIDocs setup.py /^class GenerateAIDocs(Command):$/;" c GenerateAIDocs setup.py /^class GenerateAIDocs(Command):$/;" c
JSONRPCTestClient tests/test_integration.py /^class JSONRPCTestClient:$/;" c
JsonRpcBuffer build/lib/mcp_browser/buffer.py /^class JsonRpcBuffer:$/;" c
JsonRpcBuffer mcp_browser/buffer.py /^class JsonRpcBuffer:$/;" c JsonRpcBuffer mcp_browser/buffer.py /^class JsonRpcBuffer:$/;" c
MCPBrowser build/lib/mcp_browser/proxy.py /^class MCPBrowser:$/;" c
MCPBrowser mcp_browser/proxy.py /^class MCPBrowser:$/;" c MCPBrowser mcp_browser/proxy.py /^class MCPBrowser:$/;" c
MCPBrowserClient build/lib/mcp_browser/daemon.py /^class MCPBrowserClient:$/;" c
MCPBrowserClient mcp_browser/daemon.py /^class MCPBrowserClient:$/;" c
MCPBrowserConfig build/lib/mcp_browser/config.py /^class MCPBrowserConfig:$/;" c
MCPBrowserConfig mcp_browser/config.py /^class MCPBrowserConfig:$/;" c MCPBrowserConfig mcp_browser/config.py /^class MCPBrowserConfig:$/;" c
MCPBrowserDaemon build/lib/mcp_browser/daemon.py /^class MCPBrowserDaemon:$/;" c
MCPBrowserDaemon mcp_browser/daemon.py /^class MCPBrowserDaemon:$/;" c
MCPServer build/lib/mcp_browser/server.py /^class MCPServer:$/;" c
MCPServer mcp_browser/server.py /^class MCPServer:$/;" c MCPServer mcp_browser/server.py /^class MCPServer:$/;" c
MCPServerConfig build/lib/mcp_browser/config.py /^class MCPServerConfig:$/;" c
MCPServerConfig mcp_browser/config.py /^class MCPServerConfig:$/;" c MCPServerConfig mcp_browser/config.py /^class MCPServerConfig:$/;" c
MemoryServer build/lib/mcp_servers/memory/memory_server.py /^class MemoryServer(BaseMCPServer):$/;" c
MemoryServer mcp_servers/memory/memory_server.py /^class MemoryServer(BaseMCPServer):$/;" c MemoryServer mcp_servers/memory/memory_server.py /^class MemoryServer(BaseMCPServer):$/;" c
MessageFilter build/lib/mcp_browser/filter.py /^class MessageFilter:$/;" c
MessageFilter mcp_browser/filter.py /^class MessageFilter:$/;" c MessageFilter mcp_browser/filter.py /^class MessageFilter:$/;" c
MultiServerManager build/lib/mcp_browser/multi_server.py /^class MultiServerManager:$/;" c
MultiServerManager mcp_browser/multi_server.py /^class MultiServerManager:$/;" c MultiServerManager mcp_browser/multi_server.py /^class MultiServerManager:$/;" c
OnboardingServer build/lib/mcp_servers/onboarding/onboarding_server.py /^class OnboardingServer(BaseMCPServer):$/;" c
OnboardingServer mcp_servers/onboarding/onboarding_server.py /^class OnboardingServer(BaseMCPServer):$/;" c OnboardingServer mcp_servers/onboarding/onboarding_server.py /^class OnboardingServer(BaseMCPServer):$/;" c
Pattern build/lib/mcp_servers/memory/memory_server.py /^class Pattern:$/;" c
Pattern mcp_servers/memory/memory_server.py /^class Pattern:$/;" c Pattern mcp_servers/memory/memory_server.py /^class Pattern:$/;" c
PatternServer build/lib/mcp_servers/pattern_manager/pattern_server.py /^class PatternServer(BaseMCPServer):$/;" c
PatternServer mcp_servers/pattern_manager/pattern_server.py /^class PatternServer(BaseMCPServer):$/;" c PatternServer mcp_servers/pattern_manager/pattern_server.py /^class PatternServer(BaseMCPServer):$/;" c
RawIOFilter build/lib/mcp_browser/logging_config.py /^class RawIOFilter(logging.Filter):$/;" c
RawIOFilter mcp_browser/logging_config.py /^class RawIOFilter(logging.Filter):$/;" c
ScreenServer build/lib/mcp_servers/screen/screen_server.py /^class ScreenServer(BaseMCPServer):$/;" c
ScreenServer mcp_servers/screen/screen_server.py /^class ScreenServer(BaseMCPServer):$/;" c ScreenServer mcp_servers/screen/screen_server.py /^class ScreenServer(BaseMCPServer):$/;" c
ServerNameAdapter build/lib/mcp_browser/logging_config.py /^class ServerNameAdapter(logging.LoggerAdapter):$/;" c
ServerNameAdapter mcp_browser/logging_config.py /^class ServerNameAdapter(logging.LoggerAdapter):$/;" c
TRACE build/lib/mcp_browser/logging_config.py /^TRACE = 5$/;" v
TRACE mcp_browser/logging_config.py /^TRACE = 5$/;" v
Task build/lib/mcp_servers/memory/memory_server.py /^class Task:$/;" c
Task mcp_servers/memory/memory_server.py /^class Task:$/;" c Task mcp_servers/memory/memory_server.py /^class Task:$/;" c
TestCommand setup.py /^class TestCommand(Command):$/;" c
TestMCPBrowser tests/test_basic.py /^class TestMCPBrowser:$/;" c TestMCPBrowser tests/test_basic.py /^class TestMCPBrowser:$/;" c
TestMessageFilter tests/test_basic.py /^class TestMessageFilter:$/;" c TestMessageFilter tests/test_basic.py /^class TestMessageFilter:$/;" c
TestToolRegistry tests/test_basic.py /^class TestToolRegistry:$/;" c TestToolRegistry tests/test_basic.py /^class TestToolRegistry:$/;" c
ToolRegistry build/lib/mcp_browser/registry.py /^class ToolRegistry:$/;" c
ToolRegistry mcp_browser/registry.py /^class ToolRegistry:$/;" c ToolRegistry mcp_browser/registry.py /^class ToolRegistry:$/;" c
VirtualToolHandler build/lib/mcp_browser/filter.py /^class VirtualToolHandler:$/;" c
VirtualToolHandler mcp_browser/filter.py /^class VirtualToolHandler:$/;" c VirtualToolHandler mcp_browser/filter.py /^class VirtualToolHandler:$/;" c
__aenter__ build/lib/mcp_browser/daemon.py /^ async def __aenter__(self):$/;" m class:MCPBrowserClient file:
__aenter__ build/lib/mcp_browser/proxy.py /^ async def __aenter__(self):$/;" m class:MCPBrowser file:
__aenter__ mcp_browser/daemon.py /^ async def __aenter__(self):$/;" m class:MCPBrowserClient file:
__aenter__ mcp_browser/proxy.py /^ async def __aenter__(self):$/;" m class:MCPBrowser file: __aenter__ mcp_browser/proxy.py /^ async def __aenter__(self):$/;" m class:MCPBrowser file:
__aenter__ tests/test_integration.py /^ async def __aenter__(self):$/;" m class:JSONRPCTestClient file:
__aexit__ build/lib/mcp_browser/daemon.py /^ async def __aexit__(self, exc_type, exc_val, exc_tb):$/;" m class:MCPBrowserClient file:
__aexit__ build/lib/mcp_browser/proxy.py /^ async def __aexit__(self, exc_type, exc_val, exc_tb):$/;" m class:MCPBrowser file:
__aexit__ mcp_browser/daemon.py /^ async def __aexit__(self, exc_type, exc_val, exc_tb):$/;" m class:MCPBrowserClient file:
__aexit__ mcp_browser/proxy.py /^ async def __aexit__(self, exc_type, exc_val, exc_tb):$/;" m class:MCPBrowser file: __aexit__ mcp_browser/proxy.py /^ async def __aexit__(self, exc_type, exc_val, exc_tb):$/;" m class:MCPBrowser file:
__aexit__ tests/test_integration.py /^ async def __aexit__(self, exc_type, exc_val, exc_tb):$/;" m class:JSONRPCTestClient file:
__all__ build/lib/mcp_browser/__init__.py /^__all__ = ["MCPBrowser"]/;" v
__all__ mcp_browser/__init__.py /^__all__ = ["MCPBrowser"]/;" v __all__ mcp_browser/__init__.py /^__all__ = ["MCPBrowser"]/;" v
__author__ build/lib/mcp_browser/__init__.py /^__author__ = "Claude4Ξlope"$/;" v
__author__ mcp_browser/__init__.py /^__author__ = "Claude4Ξlope"$/;" v
__email__ build/lib/mcp_browser/__init__.py /^__email__ = "xilope@esus.name"$/;" v
__email__ mcp_browser/__init__.py /^__email__ = "xilope@esus.name"$/;" v
__init__ build/lib/mcp_browser/buffer.py /^ def __init__(self):$/;" m class:JsonRpcBuffer
__init__ build/lib/mcp_browser/config.py /^ def __init__(self, config_path: Optional[Path] = None):$/;" m class:ConfigLoader
__init__ build/lib/mcp_browser/daemon.py /^ def __init__(self, browser: MCPBrowser, socket_path: Path):$/;" m class:MCPBrowserDaemon
__init__ build/lib/mcp_browser/daemon.py /^ def __init__(self, socket_path: Path):$/;" m class:MCPBrowserClient
__init__ build/lib/mcp_browser/default_configs.py /^ def __init__(self, config_dir: Optional[Path] = None):$/;" m class:ConfigManager
__init__ build/lib/mcp_browser/filter.py /^ def __init__(self, registry: ToolRegistry, server_callback: Callable):$/;" m class:VirtualToolHandler
__init__ build/lib/mcp_browser/filter.py /^ def __init__(self, registry: ToolRegistry, sparse_mode: bool = True):$/;" m class:MessageFilter
__init__ build/lib/mcp_browser/multi_server.py /^ def __init__(self, logger=None):$/;" m class:MultiServerManager
__init__ build/lib/mcp_browser/proxy.py /^ def __init__(self, config_path: Optional[Path] = None, server_name: Optional[str] = None,$/;" m class:MCPBrowser
__init__ build/lib/mcp_browser/registry.py /^ def __init__(self):$/;" m class:ToolRegistry
__init__ build/lib/mcp_browser/server.py /^ def __init__(self, config: MCPServerConfig, logger: Optional[logging.Logger] = None):$/;" m class:MCPServer
__init__ build/lib/mcp_servers/base.py /^ def __init__(self, name: str, version: str = "1.0.0"):$/;" m class:BaseMCPServer
__init__ build/lib/mcp_servers/memory/memory_server.py /^ def __init__(self):$/;" m class:MemoryServer
__init__ build/lib/mcp_servers/onboarding/onboarding_server.py /^ def __init__(self):$/;" m class:OnboardingServer
__init__ build/lib/mcp_servers/pattern_manager/pattern_server.py /^ def __init__(self):$/;" m class:PatternServer
__init__ build/lib/mcp_servers/screen/screen_server.py /^ def __init__(self):$/;" m class:ScreenServer
__init__ examples/ai_optimized.py /^ def __init__(self):$/;" m class:AIAssistant __init__ examples/ai_optimized.py /^ def __init__(self):$/;" m class:AIAssistant
__init__ mcp_browser/buffer.py /^ def __init__(self):$/;" m class:JsonRpcBuffer __init__ mcp_browser/buffer.py /^ def __init__(self):$/;" m class:JsonRpcBuffer
__init__ mcp_browser/config.py /^ def __init__(self, config_path: Optional[Path] = None):$/;" m class:ConfigLoader __init__ mcp_browser/config.py /^ def __init__(self, config_path: Optional[Path] = None):$/;" m class:ConfigLoader
__init__ mcp_browser/daemon.py /^ def __init__(self, browser: MCPBrowser, socket_path: Path):$/;" m class:MCPBrowserDaemon
__init__ mcp_browser/daemon.py /^ def __init__(self, socket_path: Path):$/;" m class:MCPBrowserClient
__init__ mcp_browser/default_configs.py /^ def __init__(self, config_dir: Optional[Path] = None):$/;" m class:ConfigManager
__init__ mcp_browser/filter.py /^ def __init__(self, registry: ToolRegistry, server_callback: Callable):$/;" m class:VirtualToolHandler __init__ mcp_browser/filter.py /^ def __init__(self, registry: ToolRegistry, server_callback: Callable):$/;" m class:VirtualToolHandler
__init__ mcp_browser/filter.py /^ def __init__(self, registry: ToolRegistry, sparse_mode: bool = True):$/;" m class:MessageFilter __init__ mcp_browser/filter.py /^ def __init__(self, registry: ToolRegistry, sparse_mode: bool = True):$/;" m class:MessageFilter
__init__ mcp_browser/multi_server.py /^ def __init__(self, debug: bool = False):$/;" m class:MultiServerManager __init__ mcp_browser/multi_server.py /^ def __init__(self, logger=None):$/;" m class:MultiServerManager
__init__ mcp_browser/proxy.py /^ def __init__(self, config_path: Optional[Path] = None, server_name: Optional[str] = None,$/;" m class:MCPBrowser __init__ mcp_browser/proxy.py /^ def __init__(self, config_path: Optional[Path] = None, server_name: Optional[str] = None,$/;" m class:MCPBrowser
__init__ mcp_browser/registry.py /^ def __init__(self):$/;" m class:ToolRegistry __init__ mcp_browser/registry.py /^ def __init__(self):$/;" m class:ToolRegistry
__init__ mcp_browser/server.py /^ def __init__(self, config: MCPServerConfig, debug: bool = False):$/;" m class:MCPServer __init__ mcp_browser/server.py /^ def __init__(self, config: MCPServerConfig, logger: Optional[logging.Logger] = None):$/;" m class:MCPServer
__init__ mcp_servers/base.py /^ def __init__(self, name: str, version: str = "1.0.0"):$/;" m class:BaseMCPServer __init__ mcp_servers/base.py /^ def __init__(self, name: str, version: str = "1.0.0"):$/;" m class:BaseMCPServer
__init__ mcp_servers/memory/memory_server.py /^ def __init__(self):$/;" m class:MemoryServer __init__ mcp_servers/memory/memory_server.py /^ def __init__(self):$/;" m class:MemoryServer
__init__ mcp_servers/onboarding/onboarding_server.py /^ def __init__(self):$/;" m class:OnboardingServer __init__ mcp_servers/onboarding/onboarding_server.py /^ def __init__(self):$/;" m class:OnboardingServer
__init__ mcp_servers/pattern_manager/pattern_server.py /^ def __init__(self):$/;" m class:PatternServer __init__ mcp_servers/pattern_manager/pattern_server.py /^ def __init__(self):$/;" m class:PatternServer
__init__ mcp_servers/screen/screen_server.py /^ def __init__(self):$/;" m class:ScreenServer __init__ mcp_servers/screen/screen_server.py /^ def __init__(self):$/;" m class:ScreenServer
__init__ tests/test_integration.py /^ def __init__(self, timeout: float = 5.0):$/;" m class:JSONRPCTestClient
__license__ build/lib/mcp_browser/__init__.py /^__license__ = "GPLv3+"$/;" v
__license__ mcp_browser/__init__.py /^__license__ = "GPLv3+"$/;" v
__version__ build/lib/mcp_browser/__init__.py /^__version__ = "0.1.0"$/;" v
__version__ mcp_browser/__init__.py /^__version__ = "0.1.0"$/;" v __version__ mcp_browser/__init__.py /^__version__ = "0.1.0"$/;" v
_add_pattern build/lib/mcp_servers/pattern_manager/pattern_server.py /^ async def _add_pattern(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:PatternServer
_add_pattern mcp_servers/pattern_manager/pattern_server.py /^ async def _add_pattern(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:PatternServer _add_pattern mcp_servers/pattern_manager/pattern_server.py /^ async def _add_pattern(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:PatternServer
_calculate_checksum build/lib/mcp_browser/default_configs.py /^ def _calculate_checksum(self, filepath: Path) -> str:$/;" m class:ConfigManager
_calculate_checksum mcp_browser/default_configs.py /^ def _calculate_checksum(self, filepath: Path) -> str:$/;" m class:ConfigManager
_create_session build/lib/mcp_servers/screen/screen_server.py /^ async def _create_session(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:ScreenServer
_create_session mcp_servers/screen/screen_server.py /^ async def _create_session(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:ScreenServer _create_session mcp_servers/screen/screen_server.py /^ async def _create_session(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:ScreenServer
_decision_add build/lib/mcp_servers/memory/memory_server.py /^ async def _decision_add(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer
_decision_add mcp_servers/memory/memory_server.py /^ async def _decision_add(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer _decision_add mcp_servers/memory/memory_server.py /^ async def _decision_add(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer
_delete_onboarding build/lib/mcp_servers/onboarding/onboarding_server.py /^ async def _delete_onboarding(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:OnboardingServer
_delete_onboarding mcp_servers/onboarding/onboarding_server.py /^ async def _delete_onboarding(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:OnboardingServer _delete_onboarding mcp_servers/onboarding/onboarding_server.py /^ async def _delete_onboarding(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:OnboardingServer
_ensure_config_file build/lib/mcp_browser/default_configs.py /^ def _ensure_config_file(self, filename: str, config_data: Dict[str, str]) -> None:$/;" m class:ConfigManager
_ensure_config_file mcp_browser/default_configs.py /^ def _ensure_config_file(self, filename: str, config_data: Dict[str, str]) -> None:$/;" m class:ConfigManager
_execute_command build/lib/mcp_servers/screen/screen_server.py /^ async def _execute_command(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:ScreenServer
_execute_command mcp_servers/screen/screen_server.py /^ async def _execute_command(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:ScreenServer _execute_command mcp_servers/screen/screen_server.py /^ async def _execute_command(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:ScreenServer
_execute_pattern build/lib/mcp_servers/pattern_manager/pattern_server.py /^ async def _execute_pattern(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:PatternServer
_execute_pattern mcp_servers/pattern_manager/pattern_server.py /^ async def _execute_pattern(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:PatternServer _execute_pattern mcp_servers/pattern_manager/pattern_server.py /^ async def _execute_pattern(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:PatternServer
_export_onboarding build/lib/mcp_servers/onboarding/onboarding_server.py /^ async def _export_onboarding(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:OnboardingServer
_export_onboarding mcp_servers/onboarding/onboarding_server.py /^ async def _export_onboarding(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:OnboardingServer _export_onboarding mcp_servers/onboarding/onboarding_server.py /^ async def _export_onboarding(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:OnboardingServer
_filter_tools_response build/lib/mcp_browser/filter.py /^ def _filter_tools_response(self, message: dict) -> dict:$/;" m class:MessageFilter
_filter_tools_response mcp_browser/filter.py /^ def _filter_tools_response(self, message: dict) -> dict:$/;" m class:MessageFilter _filter_tools_response mcp_browser/filter.py /^ def _filter_tools_response(self, message: dict) -> dict:$/;" m class:MessageFilter
_find_config_file mcp_browser/config.py /^ def _find_config_file(self) -> Optional[Path]:$/;" m class:ConfigLoader _format_onboarding build/lib/mcp_servers/onboarding/onboarding_server.py /^ def _format_onboarding(self, identity: str, data: Dict[str, Any]) -> str:$/;" m class:OnboardingServer
_format_onboarding mcp_servers/onboarding/onboarding_server.py /^ def _format_onboarding(self, identity: str, data: Dict[str, Any]) -> str:$/;" m class:OnboardingServer _format_onboarding mcp_servers/onboarding/onboarding_server.py /^ def _format_onboarding(self, identity: str, data: Dict[str, Any]) -> str:$/;" m class:OnboardingServer
_forward_to_server build/lib/mcp_browser/proxy.py /^ async def _forward_to_server(self, request: dict) -> dict:$/;" m class:MCPBrowser
_forward_to_server mcp_browser/proxy.py /^ async def _forward_to_server(self, request: dict) -> dict:$/;" m class:MCPBrowser _forward_to_server mcp_browser/proxy.py /^ async def _forward_to_server(self, request: dict) -> dict:$/;" m class:MCPBrowser
_get_builtin_servers build/lib/mcp_browser/multi_server.py /^ def _get_builtin_servers(self) -> Dict[str, MCPServerConfig]:$/;" m class:MultiServerManager
_get_builtin_servers mcp_browser/multi_server.py /^ def _get_builtin_servers(self) -> Dict[str, MCPServerConfig]:$/;" m class:MultiServerManager _get_builtin_servers mcp_browser/multi_server.py /^ def _get_builtin_servers(self) -> Dict[str, MCPServerConfig]:$/;" m class:MultiServerManager
_handle_call build/lib/mcp_browser/filter.py /^ async def _handle_call(self, message: dict) -> dict:$/;" m class:VirtualToolHandler
_handle_call mcp_browser/filter.py /^ async def _handle_call(self, message: dict) -> dict:$/;" m class:VirtualToolHandler _handle_call mcp_browser/filter.py /^ async def _handle_call(self, message: dict) -> dict:$/;" m class:VirtualToolHandler
_handle_client build/lib/mcp_browser/daemon.py /^ async def _handle_client(self, reader: asyncio.StreamReader, writer: asyncio.StreamWriter):$/;" m class:MCPBrowserDaemon
_handle_client mcp_browser/daemon.py /^ async def _handle_client(self, reader: asyncio.StreamReader, writer: asyncio.StreamWriter):$/;" m class:MCPBrowserDaemon
_handle_discover build/lib/mcp_browser/filter.py /^ async def _handle_discover(self, message: dict) -> dict:$/;" m class:VirtualToolHandler
_handle_discover mcp_browser/filter.py /^ async def _handle_discover(self, message: dict) -> dict:$/;" m class:VirtualToolHandler _handle_discover mcp_browser/filter.py /^ async def _handle_discover(self, message: dict) -> dict:$/;" m class:VirtualToolHandler
_handle_message build/lib/mcp_browser/server.py /^ async def _handle_message(self, message: dict):$/;" m class:MCPServer
_handle_message mcp_browser/server.py /^ async def _handle_message(self, message: dict):$/;" m class:MCPServer _handle_message mcp_browser/server.py /^ async def _handle_message(self, message: dict):$/;" m class:MCPServer
_handle_onboarding build/lib/mcp_servers/onboarding/onboarding_server.py /^ async def _handle_onboarding(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:OnboardingServer
_handle_onboarding mcp_servers/onboarding/onboarding_server.py /^ async def _handle_onboarding(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:OnboardingServer _handle_onboarding mcp_servers/onboarding/onboarding_server.py /^ async def _handle_onboarding(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:OnboardingServer
_handle_server_message build/lib/mcp_browser/proxy.py /^ def _handle_server_message(self, message: dict):$/;" m class:MCPBrowser
_handle_server_message mcp_browser/proxy.py /^ def _handle_server_message(self, message: dict):$/;" m class:MCPBrowser _handle_server_message mcp_browser/proxy.py /^ def _handle_server_message(self, message: dict):$/;" m class:MCPBrowser
_initialize_connection build/lib/mcp_browser/proxy.py /^ async def _initialize_connection(self):$/;" m class:MCPBrowser
_initialize_connection mcp_browser/proxy.py /^ async def _initialize_connection(self):$/;" m class:MCPBrowser _initialize_connection mcp_browser/proxy.py /^ async def _initialize_connection(self):$/;" m class:MCPBrowser
_kill_session build/lib/mcp_servers/screen/screen_server.py /^ async def _kill_session(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:ScreenServer
_kill_session mcp_servers/screen/screen_server.py /^ async def _kill_session(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:ScreenServer _kill_session mcp_servers/screen/screen_server.py /^ async def _kill_session(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:ScreenServer
_knowledge_add build/lib/mcp_servers/memory/memory_server.py /^ async def _knowledge_add(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer
_knowledge_add mcp_servers/memory/memory_server.py /^ async def _knowledge_add(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer _knowledge_add mcp_servers/memory/memory_server.py /^ async def _knowledge_add(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer
_knowledge_get build/lib/mcp_servers/memory/memory_server.py /^ async def _knowledge_get(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer
_knowledge_get mcp_servers/memory/memory_server.py /^ async def _knowledge_get(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer _knowledge_get mcp_servers/memory/memory_server.py /^ async def _knowledge_get(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer
_list_identities build/lib/mcp_servers/onboarding/onboarding_server.py /^ async def _list_identities(self) -> Dict[str, Any]:$/;" m class:OnboardingServer
_list_identities mcp_servers/onboarding/onboarding_server.py /^ async def _list_identities(self) -> Dict[str, Any]:$/;" m class:OnboardingServer _list_identities mcp_servers/onboarding/onboarding_server.py /^ async def _list_identities(self) -> Dict[str, Any]:$/;" m class:OnboardingServer
_list_patterns build/lib/mcp_servers/pattern_manager/pattern_server.py /^ async def _list_patterns(self) -> Dict[str, Any]:$/;" m class:PatternServer
_list_patterns mcp_servers/pattern_manager/pattern_server.py /^ async def _list_patterns(self) -> Dict[str, Any]:$/;" m class:PatternServer _list_patterns mcp_servers/pattern_manager/pattern_server.py /^ async def _list_patterns(self) -> Dict[str, Any]:$/;" m class:PatternServer
_list_sessions build/lib/mcp_servers/screen/screen_server.py /^ async def _list_sessions(self) -> Dict[str, Any]:$/;" m class:ScreenServer
_list_sessions mcp_servers/screen/screen_server.py /^ async def _list_sessions(self) -> Dict[str, Any]:$/;" m class:ScreenServer _list_sessions mcp_servers/screen/screen_server.py /^ async def _list_sessions(self) -> Dict[str, Any]:$/;" m class:ScreenServer
_load_json build/lib/mcp_servers/memory/memory_server.py /^ def _load_json(self, filename: str, default: Any) -> Any:$/;" m class:MemoryServer
_load_json mcp_servers/memory/memory_server.py /^ def _load_json(self, filename: str, default: Any) -> Any:$/;" m class:MemoryServer _load_json mcp_servers/memory/memory_server.py /^ def _load_json(self, filename: str, default: Any) -> Any:$/;" m class:MemoryServer
_load_memory build/lib/mcp_servers/memory/memory_server.py /^ def _load_memory(self):$/;" m class:MemoryServer
_load_memory mcp_servers/memory/memory_server.py /^ def _load_memory(self):$/;" m class:MemoryServer _load_memory mcp_servers/memory/memory_server.py /^ def _load_memory(self):$/;" m class:MemoryServer
_load_patterns build/lib/mcp_servers/pattern_manager/pattern_server.py /^ def _load_patterns(self) -> Dict[str, Dict[str, Any]]:$/;" m class:PatternServer
_load_patterns mcp_servers/pattern_manager/pattern_server.py /^ def _load_patterns(self) -> Dict[str, Dict[str, Any]]:$/;" m class:PatternServer _load_patterns mcp_servers/pattern_manager/pattern_server.py /^ def _load_patterns(self) -> Dict[str, Dict[str, Any]]:$/;" m class:PatternServer
_mark_offline build/lib/mcp_browser/server.py /^ def _mark_offline(self):$/;" m class:MCPServer
_mark_offline mcp_browser/server.py /^ def _mark_offline(self):$/;" m class:MCPServer
_matches_pattern build/lib/mcp_servers/pattern_manager/pattern_server.py /^ def _matches_pattern(self, text: str, trigger: List[str]) -> bool:$/;" m class:PatternServer
_matches_pattern mcp_servers/pattern_manager/pattern_server.py /^ def _matches_pattern(self, text: str, trigger: List[str]) -> bool:$/;" m class:PatternServer _matches_pattern mcp_servers/pattern_manager/pattern_server.py /^ def _matches_pattern(self, text: str, trigger: List[str]) -> bool:$/;" m class:PatternServer
_memory_summary build/lib/mcp_servers/memory/memory_server.py /^ async def _memory_summary(self) -> Dict[str, Any]:$/;" m class:MemoryServer
_memory_summary mcp_servers/memory/memory_server.py /^ async def _memory_summary(self) -> Dict[str, Any]:$/;" m class:MemoryServer _memory_summary mcp_servers/memory/memory_server.py /^ async def _memory_summary(self) -> Dict[str, Any]:$/;" m class:MemoryServer
_merge_configs build/lib/mcp_browser/config.py /^ def _merge_configs(self, base: Dict[str, Any], override: Dict[str, Any]):$/;" m class:ConfigLoader
_merge_configs mcp_browser/config.py /^ def _merge_configs(self, base: Dict[str, Any], override: Dict[str, Any]):$/;" m class:ConfigLoader _merge_configs mcp_browser/config.py /^ def _merge_configs(self, base: Dict[str, Any], override: Dict[str, Any]):$/;" m class:ConfigLoader
_pattern_add build/lib/mcp_servers/memory/memory_server.py /^ async def _pattern_add(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer
_pattern_add mcp_servers/memory/memory_server.py /^ async def _pattern_add(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer _pattern_add mcp_servers/memory/memory_server.py /^ async def _pattern_add(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer
_pattern_resolve build/lib/mcp_servers/memory/memory_server.py /^ async def _pattern_resolve(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer
_pattern_resolve mcp_servers/memory/memory_server.py /^ async def _pattern_resolve(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer _pattern_resolve mcp_servers/memory/memory_server.py /^ async def _pattern_resolve(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer
_peek_session build/lib/mcp_servers/screen/screen_server.py /^ async def _peek_session(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:ScreenServer
_peek_session mcp_servers/screen/screen_server.py /^ async def _peek_session(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:ScreenServer _peek_session mcp_servers/screen/screen_server.py /^ async def _peek_session(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:ScreenServer
_process_request build/lib/mcp_browser/daemon.py /^ async def _process_request(self, line: str, writer: asyncio.StreamWriter):$/;" m class:MCPBrowserDaemon
_process_request mcp_browser/daemon.py /^ async def _process_request(self, line: str, writer: asyncio.StreamWriter):$/;" m class:MCPBrowserDaemon
_process_response build/lib/mcp_servers/pattern_manager/pattern_server.py /^ async def _process_response(self, response: Any, context: Dict[str, Any]) -> str:$/;" m class:PatternServer
_process_response mcp_servers/pattern_manager/pattern_server.py /^ async def _process_response(self, response: Any, context: Dict[str, Any]) -> str:$/;" m class:PatternServer _process_response mcp_servers/pattern_manager/pattern_server.py /^ async def _process_response(self, response: Any, context: Dict[str, Any]) -> str:$/;" m class:PatternServer
_process_single_response build/lib/mcp_servers/pattern_manager/pattern_server.py /^ async def _process_single_response(self, response: str, context: Dict[str, Any]) -> str:$/;" m class:PatternServer
_process_single_response mcp_servers/pattern_manager/pattern_server.py /^ async def _process_single_response(self, response: str, context: Dict[str, Any]) -> str:$/;" m class:PatternServer _process_single_response mcp_servers/pattern_manager/pattern_server.py /^ async def _process_single_response(self, response: str, context: Dict[str, Any]) -> str:$/;" m class:PatternServer
_project_switch build/lib/mcp_servers/memory/memory_server.py /^ async def _project_switch(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer
_project_switch mcp_servers/memory/memory_server.py /^ async def _project_switch(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer _project_switch mcp_servers/memory/memory_server.py /^ async def _project_switch(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer
_read_stderr build/lib/mcp_browser/server.py /^ async def _read_stderr(self):$/;" m class:MCPServer
_read_stderr mcp_browser/server.py /^ async def _read_stderr(self):$/;" m class:MCPServer _read_stderr mcp_browser/server.py /^ async def _read_stderr(self):$/;" m class:MCPServer
_read_stdout build/lib/mcp_browser/server.py /^ async def _read_stdout(self):$/;" m class:MCPServer
_read_stdout mcp_browser/server.py /^ async def _read_stdout(self):$/;" m class:MCPServer _read_stdout mcp_browser/server.py /^ async def _read_stdout(self):$/;" m class:MCPServer
_register_tools build/lib/mcp_servers/memory/memory_server.py /^ def _register_tools(self):$/;" m class:MemoryServer
_register_tools build/lib/mcp_servers/onboarding/onboarding_server.py /^ def _register_tools(self):$/;" m class:OnboardingServer
_register_tools build/lib/mcp_servers/pattern_manager/pattern_server.py /^ def _register_tools(self):$/;" m class:PatternServer
_register_tools build/lib/mcp_servers/screen/screen_server.py /^ def _register_tools(self):$/;" m class:ScreenServer
_register_tools mcp_servers/memory/memory_server.py /^ def _register_tools(self):$/;" m class:MemoryServer _register_tools mcp_servers/memory/memory_server.py /^ def _register_tools(self):$/;" m class:MemoryServer
_register_tools mcp_servers/onboarding/onboarding_server.py /^ def _register_tools(self):$/;" m class:OnboardingServer _register_tools mcp_servers/onboarding/onboarding_server.py /^ def _register_tools(self):$/;" m class:OnboardingServer
_register_tools mcp_servers/pattern_manager/pattern_server.py /^ def _register_tools(self):$/;" m class:PatternServer _register_tools mcp_servers/pattern_manager/pattern_server.py /^ def _register_tools(self):$/;" m class:PatternServer
_register_tools mcp_servers/screen/screen_server.py /^ def _register_tools(self):$/;" m class:ScreenServer _register_tools mcp_servers/screen/screen_server.py /^ def _register_tools(self):$/;" m class:ScreenServer
_remove_pattern build/lib/mcp_servers/pattern_manager/pattern_server.py /^ async def _remove_pattern(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:PatternServer
_remove_pattern mcp_servers/pattern_manager/pattern_server.py /^ async def _remove_pattern(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:PatternServer _remove_pattern mcp_servers/pattern_manager/pattern_server.py /^ async def _remove_pattern(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:PatternServer
_run_command build/lib/mcp_servers/screen/screen_server.py /^ async def _run_command(self, cmd: List[str]) -> subprocess.CompletedProcess:$/;" m class:ScreenServer
_run_command mcp_servers/screen/screen_server.py /^ async def _run_command(self, cmd: List[str]) -> subprocess.CompletedProcess:$/;" m class:ScreenServer _run_command mcp_servers/screen/screen_server.py /^ async def _run_command(self, cmd: List[str]) -> subprocess.CompletedProcess:$/;" m class:ScreenServer
_sanitize_identity build/lib/mcp_servers/onboarding/onboarding_server.py /^ def _sanitize_identity(self, identity: str) -> str:$/;" m class:OnboardingServer
_sanitize_identity mcp_servers/onboarding/onboarding_server.py /^ def _sanitize_identity(self, identity: str) -> str:$/;" m class:OnboardingServer _sanitize_identity mcp_servers/onboarding/onboarding_server.py /^ def _sanitize_identity(self, identity: str) -> str:$/;" m class:OnboardingServer
_save_json build/lib/mcp_servers/memory/memory_server.py /^ def _save_json(self, filename: str, data: Any):$/;" m class:MemoryServer
_save_json mcp_servers/memory/memory_server.py /^ def _save_json(self, filename: str, data: Any):$/;" m class:MemoryServer _save_json mcp_servers/memory/memory_server.py /^ def _save_json(self, filename: str, data: Any):$/;" m class:MemoryServer
_save_patterns build/lib/mcp_servers/pattern_manager/pattern_server.py /^ def _save_patterns(self):$/;" m class:PatternServer
_save_patterns mcp_servers/pattern_manager/pattern_server.py /^ def _save_patterns(self):$/;" m class:PatternServer _save_patterns mcp_servers/pattern_manager/pattern_server.py /^ def _save_patterns(self):$/;" m class:PatternServer
_signal_handler build/lib/mcp_browser/daemon.py /^ def _signal_handler(self, signum, frame):$/;" m class:MCPBrowserDaemon
_signal_handler mcp_browser/daemon.py /^ def _signal_handler(self, signum, frame):$/;" m class:MCPBrowserDaemon
_task_add build/lib/mcp_servers/memory/memory_server.py /^ async def _task_add(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer
_task_add mcp_servers/memory/memory_server.py /^ async def _task_add(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer _task_add mcp_servers/memory/memory_server.py /^ async def _task_add(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer
_task_list build/lib/mcp_servers/memory/memory_server.py /^ async def _task_list(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer
_task_list mcp_servers/memory/memory_server.py /^ async def _task_list(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer _task_list mcp_servers/memory/memory_server.py /^ async def _task_list(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer
_task_update build/lib/mcp_servers/memory/memory_server.py /^ async def _task_update(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer
_task_update mcp_servers/memory/memory_server.py /^ async def _task_update(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer _task_update mcp_servers/memory/memory_server.py /^ async def _task_update(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer
_test_pattern build/lib/mcp_servers/pattern_manager/pattern_server.py /^ async def _test_pattern(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:PatternServer
_test_pattern mcp_servers/pattern_manager/pattern_server.py /^ async def _test_pattern(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:PatternServer _test_pattern mcp_servers/pattern_manager/pattern_server.py /^ async def _test_pattern(self, args: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:PatternServer
add_message_handler build/lib/mcp_browser/server.py /^ def add_message_handler(self, handler: Callable[[dict], None]):$/;" m class:MCPServer
add_message_handler mcp_browser/server.py /^ def add_message_handler(self, handler: Callable[[dict], None]):$/;" m class:MCPServer add_message_handler mcp_browser/server.py /^ def add_message_handler(self, handler: Callable[[dict], None]):$/;" m class:MCPServer
add_server build/lib/mcp_browser/multi_server.py /^ async def add_server(self, name: str, config: MCPServerConfig):$/;" m class:MultiServerManager
add_server mcp_browser/multi_server.py /^ async def add_server(self, name: str, config: MCPServerConfig):$/;" m class:MultiServerManager add_server mcp_browser/multi_server.py /^ async def add_server(self, name: str, config: MCPServerConfig):$/;" m class:MultiServerManager
append build/lib/mcp_browser/buffer.py /^ def append(self, data: str) -> List[dict]:$/;" m class:JsonRpcBuffer
append mcp_browser/buffer.py /^ def append(self, data: str) -> List[dict]:$/;" m class:JsonRpcBuffer append mcp_browser/buffer.py /^ def append(self, data: str) -> List[dict]:$/;" m class:JsonRpcBuffer
args build/lib/mcp_browser/__main__.py /^ args = parser.parse_args()$/;" v
args mcp_browser/__main__.py /^ args = parser.parse_args()$/;" v
async_main build/lib/mcp_browser/__main__.py /^async def async_main(browser: MCPBrowser):$/;" f
async_main mcp_browser/__main__.py /^async def async_main(browser: MCPBrowser):$/;" f async_main mcp_browser/__main__.py /^async def async_main(browser: MCPBrowser):$/;" f
author setup.py /^ author="AI Assistant",$/;" v author setup.py /^ author="Claude4Ξlope",$/;" v
author_email setup.py /^ author_email="ai@anthropic.com",$/;" v author_email setup.py /^ author_email="xilope@esus.name",$/;" v
browser build/lib/mcp_browser/__main__.py /^ browser = MCPBrowser($/;" v
browser mcp_browser/__main__.py /^ browser = MCPBrowser($/;" v
build_mcp_request build/lib/mcp_browser/__main__.py /^def build_mcp_request(args) -> Dict[str, Any]:$/;" f
build_mcp_request mcp_browser/__main__.py /^def build_mcp_request(args) -> Dict[str, Any]:$/;" f
build_request build/lib/mcp_browser/client_main.py /^def build_request(args) -> Dict[str, Any]:$/;" f
build_request mcp_browser/client_main.py /^def build_request(args) -> Dict[str, Any]:$/;" f
call build/lib/mcp_browser/daemon.py /^ async def call(self, request: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MCPBrowserClient
call build/lib/mcp_browser/proxy.py /^ async def call(self, jsonrpc_object: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MCPBrowser
call mcp_browser/daemon.py /^ async def call(self, request: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MCPBrowserClient
call mcp_browser/proxy.py /^ async def call(self, jsonrpc_object: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MCPBrowser call mcp_browser/proxy.py /^ async def call(self, jsonrpc_object: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MCPBrowser
call_tool build/lib/mcp_browser/__main__.py /^ call_tool = subparsers.add_parser("tools-call", help="Call a tool")$/;" v
call_tool mcp_browser/__main__.py /^ call_tool = subparsers.add_parser("tools-call", help="Call a tool")$/;" v
classifiers setup.py /^ classifiers=[$/;" v classifiers setup.py /^ classifiers=[$/;" v
clear build/lib/mcp_browser/buffer.py /^ def clear(self):$/;" m class:JsonRpcBuffer
clear mcp_browser/buffer.py /^ def clear(self):$/;" m class:JsonRpcBuffer clear mcp_browser/buffer.py /^ def clear(self):$/;" m class:JsonRpcBuffer
close build/lib/mcp_browser/daemon.py /^ async def close(self):$/;" m class:MCPBrowserClient
close build/lib/mcp_browser/proxy.py /^ async def close(self):$/;" m class:MCPBrowser
close examples/ai_optimized.py /^ async def close(self):$/;" m class:AIAssistant close examples/ai_optimized.py /^ async def close(self):$/;" m class:AIAssistant
close mcp_browser/daemon.py /^ async def close(self):$/;" m class:MCPBrowserClient
close mcp_browser/proxy.py /^ async def close(self):$/;" m class:MCPBrowser close mcp_browser/proxy.py /^ async def close(self):$/;" m class:MCPBrowser
cmdclass setup.py /^ cmdclass={$/;" v cmdclass setup.py /^ cmdclass={$/;" v
completion build/lib/mcp_browser/__main__.py /^ completion = subparsers.add_parser("completion", help="Get completion")$/;" v
completion mcp_browser/__main__.py /^ completion = subparsers.add_parser("completion", help="Get completion")$/;" v
config build/lib/mcp_browser/__main__.py /^ config = loader.load()$/;" v
config mcp_browser/__main__.py /^ config = loader.load()$/;" v
config_path build/lib/mcp_browser/__main__.py /^ config_path=config_path,$/;" v
config_path build/lib/mcp_browser/__main__.py /^ config_path = Path(args.config) if args.config else None$/;" v
config_path mcp_browser/__main__.py /^ config_path=config_path,$/;" v
config_path mcp_browser/__main__.py /^ config_path = Path(args.config) if args.config else None$/;" v
connect build/lib/mcp_browser/daemon.py /^ async def connect(self):$/;" m class:MCPBrowserClient
connect mcp_browser/daemon.py /^ async def connect(self):$/;" m class:MCPBrowserClient
content_text build/lib/mcp_servers/base.py /^ def content_text(self, text: str) -> Dict[str, Any]:$/;" m class:BaseMCPServer
content_text mcp_servers/base.py /^ def content_text(self, text: str) -> Dict[str, Any]:$/;" m class:BaseMCPServer content_text mcp_servers/base.py /^ def content_text(self, text: str) -> Dict[str, Any]:$/;" m class:BaseMCPServer
create_browser build/lib/mcp_browser/proxy.py /^async def create_browser(config_path: Optional[Path] = None, $/;" f
create_browser mcp_browser/proxy.py /^async def create_browser(config_path: Optional[Path] = None, $/;" f create_browser mcp_browser/proxy.py /^async def create_browser(config_path: Optional[Path] = None, $/;" f
debug_json build/lib/mcp_browser/utils.py /^def debug_json(label: str, data: Any):$/;" f
debug_print build/lib/mcp_browser/utils.py /^def debug_print(message: str):$/;" f
demo_builtin_servers examples/builtin_servers_demo.py /^async def demo_builtin_servers():$/;" f demo_builtin_servers examples/builtin_servers_demo.py /^async def demo_builtin_servers():$/;" f
demonstrate_mcp_browser examples/complete_demo.py /^async def demonstrate_mcp_browser():$/;" f demonstrate_mcp_browser examples/complete_demo.py /^async def demonstrate_mcp_browser():$/;" f
description setup.py /^ description = 'Generate documentation for AI navigation'$/;" v class:GenerateAIDocs description setup.py /^ description = 'Generate documentation for AI navigation'$/;" v class:GenerateAIDocs
description setup.py /^ description = 'Run unit and integration tests'$/;" v class:TestCommand
description setup.py /^ description="A generic MCP browser with context optimization for AI systems",$/;" v description setup.py /^ description="A generic MCP browser with context optimization for AI systems",$/;" v
discover build/lib/mcp_browser/proxy.py /^ def discover(self, jsonpath: str) -> Any:$/;" m class:MCPBrowser
discover build/lib/mcp_browser/registry.py /^ def discover(self, jsonpath: str) -> Union[List[Any], Any, None]:$/;" m class:ToolRegistry
discover mcp_browser/proxy.py /^ def discover(self, jsonpath: str) -> Any:$/;" m class:MCPBrowser discover mcp_browser/proxy.py /^ def discover(self, jsonpath: str) -> Any:$/;" m class:MCPBrowser
discover mcp_browser/registry.py /^ def discover(self, jsonpath: str) -> Union[List[Any], Any, None]:$/;" m class:ToolRegistry discover mcp_browser/registry.py /^ def discover(self, jsonpath: str) -> Union[List[Any], Any, None]:$/;" m class:ToolRegistry
enable_builtin_servers build/lib/mcp_browser/__main__.py /^ enable_builtin_servers=not args.no_builtin$/;" v
enable_builtin_servers mcp_browser/__main__.py /^ enable_builtin_servers=not args.no_builtin$/;" v
ensure_config_directory build/lib/mcp_browser/default_configs.py /^ def ensure_config_directory(self) -> None:$/;" m class:ConfigManager
ensure_config_directory mcp_browser/default_configs.py /^ def ensure_config_directory(self) -> None:$/;" m class:ConfigManager
entry_points setup.py /^ entry_points={$/;" v entry_points setup.py /^ entry_points={$/;" v
execute_user_request examples/ai_optimized.py /^ async def execute_user_request(self, user_request: str):$/;" m class:AIAssistant execute_user_request examples/ai_optimized.py /^ async def execute_user_request(self, user_request: str):$/;" m class:AIAssistant
extras_require setup.py /^ extras_require={$/;" v extras_require setup.py /^ extras_require={$/;" v
filter build/lib/mcp_browser/logging_config.py /^ def filter(self, record):$/;" m class:RawIOFilter
filter mcp_browser/logging_config.py /^ def filter(self, record):$/;" m class:RawIOFilter
filter_incoming build/lib/mcp_browser/filter.py /^ def filter_incoming(self, message: dict) -> Optional[dict]:$/;" m class:MessageFilter
filter_incoming mcp_browser/filter.py /^ def filter_incoming(self, message: dict) -> Optional[dict]:$/;" m class:MessageFilter filter_incoming mcp_browser/filter.py /^ def filter_incoming(self, message: dict) -> Optional[dict]:$/;" m class:MessageFilter
filter_outgoing build/lib/mcp_browser/filter.py /^ def filter_outgoing(self, message: dict) -> Optional[dict]:$/;" m class:MessageFilter
filter_outgoing mcp_browser/filter.py /^ def filter_outgoing(self, message: dict) -> Optional[dict]:$/;" m class:MessageFilter filter_outgoing mcp_browser/filter.py /^ def filter_outgoing(self, message: dict) -> Optional[dict]:$/;" m class:MessageFilter
finalize_options setup.py /^ def finalize_options(self):$/;" m class:GenerateAIDocs finalize_options setup.py /^ def finalize_options(self):$/;" m class:GenerateAIDocs
finalize_options setup.py /^ def finalize_options(self):$/;" m class:TestCommand
format_mcp_response build/lib/mcp_browser/__main__.py /^def format_mcp_response(args, request: Dict[str, Any], response: Dict[str, Any]):$/;" f
format_mcp_response mcp_browser/__main__.py /^def format_mcp_response(args, request: Dict[str, Any], response: Dict[str, Any]):$/;" f
format_response build/lib/mcp_browser/client_main.py /^def format_response(args, response: Dict[str, Any]):$/;" f
format_response mcp_browser/client_main.py /^def format_response(args, response: Dict[str, Any]):$/;" f
formatter_class build/lib/mcp_browser/__main__.py /^ formatter_class=argparse.RawDescriptionHelpFormatter$/;" v
formatter_class mcp_browser/__main__.py /^ formatter_class=argparse.RawDescriptionHelpFormatter$/;" v
generate_api_summary setup.py /^ def generate_api_summary(self):$/;" m class:GenerateAIDocs generate_api_summary setup.py /^ def generate_api_summary(self):$/;" m class:GenerateAIDocs
generate_structure_doc setup.py /^ def generate_structure_doc(self):$/;" m class:GenerateAIDocs generate_structure_doc setup.py /^ def generate_structure_doc(self):$/;" m class:GenerateAIDocs
get_all_tool_names build/lib/mcp_browser/registry.py /^ def get_all_tool_names(self) -> List[str]:$/;" m class:ToolRegistry
get_all_tool_names mcp_browser/registry.py /^ def get_all_tool_names(self) -> List[str]:$/;" m class:ToolRegistry get_all_tool_names mcp_browser/registry.py /^ def get_all_tool_names(self) -> List[str]:$/;" m class:ToolRegistry
get_all_tools build/lib/mcp_browser/multi_server.py /^ async def get_all_tools(self) -> List[Dict[str, Any]]:$/;" m class:MultiServerManager
get_all_tools mcp_browser/multi_server.py /^ async def get_all_tools(self) -> List[Dict[str, Any]]:$/;" m class:MultiServerManager get_all_tools mcp_browser/multi_server.py /^ async def get_all_tools(self) -> List[Dict[str, Any]]:$/;" m class:MultiServerManager
get_config_path build/lib/mcp_browser/default_configs.py /^ def get_config_path(self) -> Path:$/;" m class:ConfigManager
get_config_path mcp_browser/default_configs.py /^ def get_config_path(self) -> Path:$/;" m class:ConfigManager
get_logger build/lib/mcp_browser/logging_config.py /^def get_logger(name: str, server: Optional[str] = None) -> logging.Logger:$/;" f
get_logger mcp_browser/logging_config.py /^def get_logger(name: str, server: Optional[str] = None) -> logging.Logger:$/;" f
get_onboarding_path build/lib/mcp_browser/default_configs.py /^ def get_onboarding_path(self) -> Path:$/;" m class:ConfigManager
get_onboarding_path mcp_browser/default_configs.py /^ def get_onboarding_path(self) -> Path:$/;" m class:ConfigManager
get_onboarding_text build/lib/mcp_browser/default_configs.py /^ def get_onboarding_text(self, identity: Optional[str] = None) -> str:$/;" m class:ConfigManager
get_onboarding_text mcp_browser/default_configs.py /^ def get_onboarding_text(self, identity: Optional[str] = None) -> str:$/;" m class:ConfigManager
get_patterns_dir build/lib/mcp_browser/default_configs.py /^ def get_patterns_dir(self) -> Path:$/;" m class:ConfigManager
get_patterns_dir mcp_browser/default_configs.py /^ def get_patterns_dir(self) -> Path:$/;" m class:ConfigManager
get_prompt build/lib/mcp_browser/__main__.py /^ get_prompt = subparsers.add_parser("prompts-get", help="Get a prompt")$/;" v
get_prompt mcp_browser/__main__.py /^ get_prompt = subparsers.add_parser("prompts-get", help="Get a prompt")$/;" v
get_socket_path build/lib/mcp_browser/daemon.py /^def get_socket_path(server_name: Optional[str] = None) -> Path:$/;" f
get_socket_path mcp_browser/daemon.py /^def get_socket_path(server_name: Optional[str] = None) -> Path:$/;" f
get_sparse_tools build/lib/mcp_browser/registry.py /^ def get_sparse_tools(self) -> List[Dict[str, Any]]:$/;" m class:ToolRegistry
get_sparse_tools mcp_browser/registry.py /^ def get_sparse_tools(self) -> List[Dict[str, Any]]:$/;" m class:ToolRegistry get_sparse_tools mcp_browser/registry.py /^ def get_sparse_tools(self) -> List[Dict[str, Any]]:$/;" m class:ToolRegistry
get_tool build/lib/mcp_browser/registry.py /^ def get_tool(self, name: str) -> Optional[Dict[str, Any]]:$/;" m class:ToolRegistry
get_tool mcp_browser/registry.py /^ def get_tool(self, name: str) -> Optional[Dict[str, Any]]:$/;" m class:ToolRegistry get_tool mcp_browser/registry.py /^ def get_tool(self, name: str) -> Optional[Dict[str, Any]]:$/;" m class:ToolRegistry
handle_mcp_command build/lib/mcp_browser/__main__.py /^async def handle_mcp_command(args):$/;" f
handle_mcp_command mcp_browser/__main__.py /^async def handle_mcp_command(args):$/;" f
handle_request build/lib/mcp_servers/base.py /^ async def handle_request(self, request: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:BaseMCPServer
handle_request mcp_servers/base.py /^ async def handle_request(self, request: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:BaseMCPServer handle_request mcp_servers/base.py /^ async def handle_request(self, request: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:BaseMCPServer
handle_systemd_socket build/lib/mcp_browser/daemon_main.py /^def handle_systemd_socket():$/;" f
handle_systemd_socket mcp_browser/daemon_main.py /^def handle_systemd_socket():$/;" f
handle_tool_call build/lib/mcp_browser/filter.py /^ async def handle_tool_call(self, message: dict) -> Optional[dict]:$/;" m class:VirtualToolHandler
handle_tool_call build/lib/mcp_servers/base.py /^ async def handle_tool_call(self, tool_name: str, arguments: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:BaseMCPServer
handle_tool_call build/lib/mcp_servers/memory/memory_server.py /^ async def handle_tool_call(self, tool_name: str, arguments: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer
handle_tool_call build/lib/mcp_servers/onboarding/onboarding_server.py /^ async def handle_tool_call(self, tool_name: str, arguments: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:OnboardingServer
handle_tool_call build/lib/mcp_servers/pattern_manager/pattern_server.py /^ async def handle_tool_call(self, tool_name: str, arguments: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:PatternServer
handle_tool_call build/lib/mcp_servers/screen/screen_server.py /^ async def handle_tool_call(self, tool_name: str, arguments: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:ScreenServer
handle_tool_call mcp_browser/filter.py /^ async def handle_tool_call(self, message: dict) -> Optional[dict]:$/;" m class:VirtualToolHandler handle_tool_call mcp_browser/filter.py /^ async def handle_tool_call(self, message: dict) -> Optional[dict]:$/;" m class:VirtualToolHandler
handle_tool_call mcp_servers/base.py /^ async def handle_tool_call(self, tool_name: str, arguments: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:BaseMCPServer handle_tool_call mcp_servers/base.py /^ async def handle_tool_call(self, tool_name: str, arguments: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:BaseMCPServer
handle_tool_call mcp_servers/memory/memory_server.py /^ async def handle_tool_call(self, tool_name: str, arguments: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer handle_tool_call mcp_servers/memory/memory_server.py /^ async def handle_tool_call(self, tool_name: str, arguments: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MemoryServer
handle_tool_call mcp_servers/onboarding/onboarding_server.py /^ async def handle_tool_call(self, tool_name: str, arguments: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:OnboardingServer handle_tool_call mcp_servers/onboarding/onboarding_server.py /^ async def handle_tool_call(self, tool_name: str, arguments: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:OnboardingServer
handle_tool_call mcp_servers/pattern_manager/pattern_server.py /^ async def handle_tool_call(self, tool_name: str, arguments: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:PatternServer handle_tool_call mcp_servers/pattern_manager/pattern_server.py /^ async def handle_tool_call(self, tool_name: str, arguments: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:PatternServer
handle_tool_call mcp_servers/screen/screen_server.py /^ async def handle_tool_call(self, tool_name: str, arguments: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:ScreenServer handle_tool_call mcp_servers/screen/screen_server.py /^ async def handle_tool_call(self, tool_name: str, arguments: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:ScreenServer
help build/lib/mcp_browser/__main__.py /^ help="Automatically use daemon if available")$/;" v
help build/lib/mcp_browser/__main__.py /^ help="Check daemon status")$/;" v
help build/lib/mcp_browser/__main__.py /^ help="Disable built-in servers (screen, memory, patterns)")$/;" v
help build/lib/mcp_browser/__main__.py /^ help="Disable sparse mode (show all tools)")$/;" v
help build/lib/mcp_browser/__main__.py /^ help="Enable debug output")$/;" v
help build/lib/mcp_browser/__main__.py /^ help="List available MCP servers from config")$/;" v
help build/lib/mcp_browser/__main__.py /^ help="Set logging level")$/;" v
help build/lib/mcp_browser/__main__.py /^ help="Show current configuration path and content")$/;" v
help build/lib/mcp_browser/__main__.py /^ help="Show program version and exit")$/;" v
help build/lib/mcp_browser/__main__.py /^ help="Start daemon in background")$/;" v
help build/lib/mcp_browser/__main__.py /^ help="Stop running daemon")$/;" v
help build/lib/mcp_browser/__main__.py /^ help="Test connection to specified server")$/;" v
help mcp_browser/__main__.py /^ help="Automatically use daemon if available")$/;" v
help mcp_browser/__main__.py /^ help="Check daemon status")$/;" v
help mcp_browser/__main__.py /^ help="Disable built-in servers (screen, memory, patterns)")$/;" v
help mcp_browser/__main__.py /^ help="Disable sparse mode (show all tools)")$/;" v
help mcp_browser/__main__.py /^ help="Enable debug output")$/;" v
help mcp_browser/__main__.py /^ help="List available MCP servers from config")$/;" v
help mcp_browser/__main__.py /^ help="Set logging level")$/;" v
help mcp_browser/__main__.py /^ help="Show current configuration path and content")$/;" v
help mcp_browser/__main__.py /^ help="Show program version and exit")$/;" v
help mcp_browser/__main__.py /^ help="Start daemon in background")$/;" v
help mcp_browser/__main__.py /^ help="Stop running daemon")$/;" v
help mcp_browser/__main__.py /^ help="Test connection to specified server")$/;" v
include_package_data setup.py /^ include_package_data=True,$/;" v
initialize build/lib/mcp_browser/proxy.py /^ async def initialize(self):$/;" m class:MCPBrowser
initialize examples/ai_optimized.py /^ async def initialize(self):$/;" m class:AIAssistant initialize examples/ai_optimized.py /^ async def initialize(self):$/;" m class:AIAssistant
initialize mcp_browser/proxy.py /^ async def initialize(self):$/;" m class:MCPBrowser initialize mcp_browser/proxy.py /^ async def initialize(self):$/;" m class:MCPBrowser
initialize_options setup.py /^ def initialize_options(self):$/;" m class:GenerateAIDocs initialize_options setup.py /^ def initialize_options(self):$/;" m class:GenerateAIDocs
initialize_options setup.py /^ def initialize_options(self):$/;" m class:TestCommand
install_requires setup.py /^ install_requires=[$/;" v install_requires setup.py /^ install_requires=[$/;" v
interactive_mode build/lib/mcp_browser/__main__.py /^async def interactive_mode(browser: MCPBrowser):$/;" f
interactive_mode mcp_browser/__main__.py /^async def interactive_mode(browser: MCPBrowser):$/;" f interactive_mode mcp_browser/__main__.py /^async def interactive_mode(browser: MCPBrowser):$/;" f
interactive_mode_with_daemon build/lib/mcp_browser/__main__.py /^async def interactive_mode_with_daemon(socket_path: Path):$/;" f
interactive_mode_with_daemon mcp_browser/__main__.py /^async def interactive_mode_with_daemon(socket_path: Path):$/;" f
is_daemon_running build/lib/mcp_browser/daemon.py /^def is_daemon_running(socket_path: Path) -> bool:$/;" f
is_daemon_running mcp_browser/daemon.py /^def is_daemon_running(socket_path: Path) -> bool:$/;" f
is_virtual_tool build/lib/mcp_browser/filter.py /^ def is_virtual_tool(self, tool_name: str) -> bool:$/;" m class:MessageFilter
is_virtual_tool mcp_browser/filter.py /^ def is_virtual_tool(self, tool_name: str) -> bool:$/;" m class:MessageFilter is_virtual_tool mcp_browser/filter.py /^ def is_virtual_tool(self, tool_name: str) -> bool:$/;" m class:MessageFilter
jsonrpc build/lib/mcp_browser/__main__.py /^ jsonrpc = subparsers.add_parser("jsonrpc", help="Send raw JSON-RPC request")$/;" v
jsonrpc mcp_browser/__main__.py /^ jsonrpc = subparsers.add_parser("jsonrpc", help="Send raw JSON-RPC request")$/;" v
keywords setup.py /^ keywords="mcp model-context-protocol ai llm tools json-rpc",$/;" v keywords setup.py /^ keywords="mcp model-context-protocol ai llm tools json-rpc",$/;" v
kill_daemon_with_children build/lib/mcp_browser/daemon.py /^def kill_daemon_with_children(socket_path: Path) -> bool:$/;" f
kill_daemon_with_children mcp_browser/daemon.py /^def kill_daemon_with_children(socket_path: Path) -> bool:$/;" f
list_prompts build/lib/mcp_browser/__main__.py /^ list_prompts = subparsers.add_parser("prompts-list", help="List available prompts")$/;" v
list_prompts mcp_browser/__main__.py /^ list_prompts = subparsers.add_parser("prompts-list", help="List available prompts")$/;" v
list_resources build/lib/mcp_browser/__main__.py /^ list_resources = subparsers.add_parser("resources-list", help="List available resources")$/;" v
list_resources mcp_browser/__main__.py /^ list_resources = subparsers.add_parser("resources-list", help="List available resources")$/;" v
list_tools build/lib/mcp_browser/__main__.py /^ list_tools = subparsers.add_parser("tools-list", help="List available tools")$/;" v
list_tools mcp_browser/__main__.py /^ list_tools = subparsers.add_parser("tools-list", help="List available tools")$/;" v
load build/lib/mcp_browser/config.py /^ def load(self) -> MCPBrowserConfig:$/;" m class:ConfigLoader
load mcp_browser/config.py /^ def load(self) -> MCPBrowserConfig:$/;" m class:ConfigLoader load mcp_browser/config.py /^ def load(self) -> MCPBrowserConfig:$/;" m class:ConfigLoader
long_description setup.py /^ long_description = fh.read()$/;" v class:GenerateAIDocs load_config build/lib/mcp_browser/default_configs.py /^ def load_config(self) -> dict:$/;" m class:ConfigManager
load_config mcp_browser/default_configs.py /^ def load_config(self) -> dict:$/;" m class:ConfigManager
loader build/lib/mcp_browser/__main__.py /^ loader = ConfigLoader()$/;" v
loader mcp_browser/__main__.py /^ loader = ConfigLoader()$/;" v
long_description setup.py /^ long_description = fh.read()$/;" v
long_description setup.py /^ long_description=long_description,$/;" v long_description setup.py /^ long_description=long_description,$/;" v
long_description_content_type setup.py /^ long_description_content_type="text\/markdown",$/;" v long_description_content_type setup.py /^ long_description_content_type="text\/markdown",$/;" v
main build/lib/mcp_browser/__main__.py /^def main():$/;" f
main build/lib/mcp_browser/client_main.py /^def main():$/;" f
main build/lib/mcp_browser/daemon_main.py /^def main():$/;" f
main examples/ai_optimized.py /^async def main():$/;" f main examples/ai_optimized.py /^async def main():$/;" f
main examples/basic_usage.py /^async def main():$/;" f main examples/basic_usage.py /^async def main():$/;" f
main mcp_browser/__main__.py /^def main():$/;" f main mcp_browser/__main__.py /^def main():$/;" f
main mcp_browser/client_main.py /^def main():$/;" f
main mcp_browser/daemon_main.py /^def main():$/;" f
main tests/test_browser_functionality.py /^def main():$/;" f
main tests/test_integration.py /^async def main():$/;" f
mark_handled build/lib/mcp_browser/filter.py /^ def mark_handled(self, request_id: Union[str, int]):$/;" m class:MessageFilter
mark_handled mcp_browser/filter.py /^ def mark_handled(self, request_id: Union[str, int]):$/;" m class:MessageFilter mark_handled mcp_browser/filter.py /^ def mark_handled(self, request_id: Union[str, int]):$/;" m class:MessageFilter
name setup.py /^ name="mcp-browser",$/;" v name setup.py /^ name="mcp-browser",$/;" v
package_data setup.py /^ package_data={$/;" v package_data setup.py /^ package_data={$/;" v
packages setup.py /^ packages=find_packages(),$/;" v packages setup.py /^ packages=find_packages(include=['mcp_browser*', 'mcp_servers*']),$/;" v
pid_exists build/lib/mcp_browser/daemon.py /^ def pid_exists(pid):$/;" m class:psutil
pid_exists mcp_browser/daemon.py /^ def pid_exists(pid):$/;" m class:psutil
process build/lib/mcp_browser/logging_config.py /^ def process(self, msg, kwargs):$/;" m class:ServerNameAdapter
process mcp_browser/logging_config.py /^ def process(self, msg, kwargs):$/;" m class:ServerNameAdapter
psutil build/lib/mcp_browser/daemon.py /^ class psutil:$/;" c
psutil mcp_browser/daemon.py /^ class psutil:$/;" c
read_resource build/lib/mcp_browser/__main__.py /^ read_resource = subparsers.add_parser("resources-read", help="Read a resource")$/;" v
read_resource mcp_browser/__main__.py /^ read_resource = subparsers.add_parser("resources-read", help="Read a resource")$/;" v
register_tool build/lib/mcp_servers/base.py /^ def register_tool(self, name: str, description: str, input_schema: Dict[str, Any], $/;" m class:BaseMCPServer
register_tool mcp_servers/base.py /^ def register_tool(self, name: str, description: str, input_schema: Dict[str, Any], $/;" m class:BaseMCPServer register_tool mcp_servers/base.py /^ def register_tool(self, name: str, description: str, input_schema: Dict[str, Any], $/;" m class:BaseMCPServer
route_tool_call build/lib/mcp_browser/multi_server.py /^ async def route_tool_call(self, tool_name: str, arguments: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MultiServerManager
route_tool_call mcp_browser/multi_server.py /^ async def route_tool_call(self, tool_name: str, arguments: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MultiServerManager route_tool_call mcp_browser/multi_server.py /^ async def route_tool_call(self, tool_name: str, arguments: Dict[str, Any]) -> Dict[str, Any]:$/;" m class:MultiServerManager
run build/lib/mcp_browser/client_main.py /^ async def run():$/;" f function:main
run build/lib/mcp_servers/base.py /^ async def run(self):$/;" m class:BaseMCPServer
run mcp_browser/client_main.py /^ async def run():$/;" f function:main
run mcp_servers/base.py /^ async def run(self):$/;" m class:BaseMCPServer run mcp_servers/base.py /^ async def run(self):$/;" m class:BaseMCPServer
run setup.py /^ def run(self):$/;" m class:GenerateAIDocs run setup.py /^ def run(self):$/;" m class:GenerateAIDocs
run setup.py /^ def run(self):$/;" m class:TestCommand
run_command build/lib/mcp_browser/client_main.py /^async def run_command(args, request: Dict[str, Any]):$/;" f
run_command mcp_browser/client_main.py /^async def run_command(args, request: Dict[str, Any]):$/;" f
run_daemon build/lib/mcp_browser/daemon_main.py /^async def run_daemon(args):$/;" f
run_daemon mcp_browser/daemon_main.py /^async def run_daemon(args):$/;" f
run_daemon_mode build/lib/mcp_browser/__main__.py /^async def run_daemon_mode(browser: MCPBrowser, socket_path: Path):$/;" f
run_daemon_mode mcp_browser/__main__.py /^async def run_daemon_mode(browser: MCPBrowser, socket_path: Path):$/;" f
run_mcp_server_mode build/lib/mcp_browser/client_main.py /^async def run_mcp_server_mode(args):$/;" f
run_mcp_server_mode mcp_browser/client_main.py /^async def run_mcp_server_mode(args):$/;" f
run_server_mode build/lib/mcp_browser/__main__.py /^async def run_server_mode(browser: MCPBrowser):$/;" f
run_server_mode mcp_browser/__main__.py /^async def run_server_mode(browser: MCPBrowser):$/;" f run_server_mode mcp_browser/__main__.py /^async def run_server_mode(browser: MCPBrowser):$/;" f
run_server_mode_with_daemon build/lib/mcp_browser/__main__.py /^async def run_server_mode_with_daemon(socket_path: Path):$/;" f
run_server_mode_with_daemon mcp_browser/__main__.py /^async def run_server_mode_with_daemon(socket_path: Path):$/;" f
save_config build/lib/mcp_browser/default_configs.py /^ def save_config(self, config: dict) -> None:$/;" m class:ConfigManager
save_config mcp_browser/default_configs.py /^ def save_config(self, config: dict) -> None:$/;" m class:ConfigManager
send_raw build/lib/mcp_browser/server.py /^ def send_raw(self, message: str):$/;" m class:MCPServer
send_raw mcp_browser/server.py /^ def send_raw(self, message: str):$/;" m class:MCPServer send_raw mcp_browser/server.py /^ def send_raw(self, message: str):$/;" m class:MCPServer
send_request build/lib/mcp_browser/server.py /^ async def send_request(self, method: str, params: Optional[Dict[str, Any]] = None) -> Dict[str, Any]:$/;" m class:MCPServer
send_request mcp_browser/server.py /^ async def send_request(self, method: str, params: Optional[Dict[str, Any]] = None) -> Dict[str, Any]:$/;" m class:MCPServer send_request mcp_browser/server.py /^ async def send_request(self, method: str, params: Optional[Dict[str, Any]] = None) -> Dict[str, Any]:$/;" m class:MCPServer
send_request tests/test_integration.py /^ async def send_request(self, method: str, params: Optional[Dict[str, Any]] = None) -> Dict[str, Any]:$/;" m class:JSONRPCTestClient
server build/lib/mcp_servers/memory/memory_server.py /^ server = MemoryServer()$/;" v class:MemoryServer
server build/lib/mcp_servers/onboarding/onboarding_server.py /^ server = OnboardingServer()$/;" v class:OnboardingServer
server build/lib/mcp_servers/pattern_manager/pattern_server.py /^ server = PatternServer()$/;" v class:PatternServer
server build/lib/mcp_servers/screen/screen_server.py /^ server = ScreenServer()$/;" v class:ScreenServer
server mcp_servers/memory/memory_server.py /^ server = MemoryServer()$/;" v class:MemoryServer server mcp_servers/memory/memory_server.py /^ server = MemoryServer()$/;" v class:MemoryServer
server mcp_servers/onboarding/onboarding_server.py /^ server = OnboardingServer()$/;" v class:OnboardingServer server mcp_servers/onboarding/onboarding_server.py /^ server = OnboardingServer()$/;" v class:OnboardingServer
server mcp_servers/pattern_manager/pattern_server.py /^ server = PatternServer()$/;" v class:PatternServer server mcp_servers/pattern_manager/pattern_server.py /^ server = PatternServer()$/;" v class:PatternServer
server mcp_servers/screen/screen_server.py /^ server = ScreenServer()$/;" v class:ScreenServer server mcp_servers/screen/screen_server.py /^ server = ScreenServer()$/;" v class:ScreenServer
server_name build/lib/mcp_browser/__main__.py /^ server_name=args.server,$/;" v
server_name mcp_browser/__main__.py /^ server_name=args.server,$/;" v
set_metadata build/lib/mcp_browser/registry.py /^ def set_metadata(self, key: str, value: Any):$/;" m class:ToolRegistry
set_metadata mcp_browser/registry.py /^ def set_metadata(self, key: str, value: Any):$/;" m class:ToolRegistry set_metadata mcp_browser/registry.py /^ def set_metadata(self, key: str, value: Any):$/;" m class:ToolRegistry
simulate_response tests/test_basic.py /^ async def simulate_response():$/;" f function:TestMCPBrowser.test_call_method set_onboarding_text build/lib/mcp_browser/default_configs.py /^ def set_onboarding_text(self, text: str, identity: Optional[str] = None) -> None:$/;" m class:ConfigManager
set_onboarding_text mcp_browser/default_configs.py /^ def set_onboarding_text(self, text: str, identity: Optional[str] = None) -> None:$/;" m class:ConfigManager
setup_logging build/lib/mcp_browser/logging_config.py /^def setup_logging(debug: bool = False, log_file: Optional[Path] = None, $/;" f
setup_logging mcp_browser/logging_config.py /^def setup_logging(debug: bool = False, log_file: Optional[Path] = None, $/;" f
show_available_servers build/lib/mcp_browser/__main__.py /^def show_available_servers(config_path: Optional[str] = None):$/;" f
show_available_servers mcp_browser/__main__.py /^def show_available_servers(config_path: Optional[str] = None):$/;" f
show_configuration build/lib/mcp_browser/__main__.py /^def show_configuration(config_path: Optional[str] = None):$/;" f
show_configuration mcp_browser/__main__.py /^def show_configuration(config_path: Optional[str] = None):$/;" f
show_daemon_status build/lib/mcp_browser/__main__.py /^def show_daemon_status(args):$/;" f
show_daemon_status mcp_browser/__main__.py /^def show_daemon_status(args):$/;" f
signal_handler build/lib/mcp_browser/daemon_main.py /^ def signal_handler(signum):$/;" f function:run_daemon
signal_handler mcp_browser/daemon_main.py /^ def signal_handler(signum):$/;" f function:run_daemon
socket_path build/lib/mcp_browser/__main__.py /^ socket_path = get_socket_path(args.server)$/;" v
socket_path mcp_browser/__main__.py /^ socket_path = get_socket_path(args.server)$/;" v
start build/lib/mcp_browser/daemon.py /^ async def start(self):$/;" m class:MCPBrowserDaemon
start build/lib/mcp_browser/server.py /^ async def start(self):$/;" m class:MCPServer
start mcp_browser/daemon.py /^ async def start(self):$/;" m class:MCPBrowserDaemon
start mcp_browser/server.py /^ async def start(self):$/;" m class:MCPServer start mcp_browser/server.py /^ async def start(self):$/;" m class:MCPServer
start_builtin_servers build/lib/mcp_browser/multi_server.py /^ async def start_builtin_servers(self):$/;" m class:MultiServerManager
start_builtin_servers mcp_browser/multi_server.py /^ async def start_builtin_servers(self):$/;" m class:MultiServerManager start_builtin_servers mcp_browser/multi_server.py /^ async def start_builtin_servers(self):$/;" m class:MultiServerManager
start_daemon_background build/lib/mcp_browser/__main__.py /^async def start_daemon_background(args):$/;" f
start_daemon_background mcp_browser/__main__.py /^async def start_daemon_background(args):$/;" f
start_daemon_if_needed build/lib/mcp_browser/client_main.py /^def start_daemon_if_needed(server_name: Optional[str] = None, timeout: float = 5.0) -> bool:$/;" f
start_daemon_if_needed mcp_browser/client_main.py /^def start_daemon_if_needed(server_name: Optional[str] = None, timeout: float = 5.0) -> bool:$/;" f
stop build/lib/mcp_browser/daemon.py /^ async def stop(self):$/;" m class:MCPBrowserDaemon
stop build/lib/mcp_browser/server.py /^ async def stop(self):$/;" m class:MCPServer
stop mcp_browser/daemon.py /^ async def stop(self):$/;" m class:MCPBrowserDaemon
stop mcp_browser/server.py /^ async def stop(self):$/;" m class:MCPServer stop mcp_browser/server.py /^ async def stop(self):$/;" m class:MCPServer
stop_all build/lib/mcp_browser/multi_server.py /^ async def stop_all(self):$/;" m class:MultiServerManager
stop_all mcp_browser/multi_server.py /^ async def stop_all(self):$/;" m class:MultiServerManager stop_all mcp_browser/multi_server.py /^ async def stop_all(self):$/;" m class:MultiServerManager
test_call_method tests/test_basic.py /^ async def test_call_method(self):$/;" m class:TestMCPBrowser stop_daemon build/lib/mcp_browser/__main__.py /^def stop_daemon(args):$/;" f
test_claude_connection test_claude_connection.py /^async def test_claude_connection():$/;" f stop_daemon mcp_browser/__main__.py /^def stop_daemon(args):$/;" f
subparsers build/lib/mcp_browser/__main__.py /^ subparsers = parser.add_subparsers(dest="command", help="MCP methods")$/;" v
subparsers mcp_browser/__main__.py /^ subparsers = parser.add_subparsers(dest="command", help="MCP methods")$/;" v
test_basic_flow tests/test_integration.py /^async def test_basic_flow():$/;" f
test_brave_search_integration tests/test_brave_search.py /^async def test_brave_search_integration():$/;" f
test_browser_without_servers tests/test_basic.py /^ async def test_browser_without_servers(self):$/;" m class:TestMCPBrowser
test_browser_without_servers tests/test_browser_functionality.py /^async def test_browser_without_servers():$/;" f
test_claude_connection tests/test_claude_connection.py /^async def test_claude_connection():$/;" f
test_discover_jsonpath tests/test_basic.py /^ def test_discover_jsonpath(self):$/;" m class:TestToolRegistry test_discover_jsonpath tests/test_basic.py /^ def test_discover_jsonpath(self):$/;" m class:TestToolRegistry
test_discover_method tests/test_basic.py /^ async def test_discover_method(self):$/;" m class:TestMCPBrowser
test_duplicate_error_filtering tests/test_basic.py /^ def test_duplicate_error_filtering(self):$/;" m class:TestMessageFilter test_duplicate_error_filtering tests/test_basic.py /^ def test_duplicate_error_filtering(self):$/;" m class:TestMessageFilter
test_initialization tests/test_basic.py /^ async def test_initialization(self):$/;" m class:TestMCPBrowser test_error_handling tests/test_integration.py /^async def test_error_handling():$/;" f
test_onboarding test_onboarding.py /^async def test_onboarding():$/;" f test_message_filter tests/test_simple.py /^def test_message_filter():$/;" f
test_onboarding tests/test_onboarding.py /^async def test_onboarding():$/;" f
test_server_connection build/lib/mcp_browser/__main__.py /^async def test_server_connection(browser: MCPBrowser, server_name: Optional[str] = None):$/;" f
test_server_connection mcp_browser/__main__.py /^async def test_server_connection(browser: MCPBrowser, server_name: Optional[str] = None):$/;" f
test_sparse_mode tests/test_simple.py /^def test_sparse_mode():$/;" f
test_sparse_mode_filtering tests/test_basic.py /^ def test_sparse_mode_filtering(self):$/;" m class:TestMessageFilter test_sparse_mode_filtering tests/test_basic.py /^ def test_sparse_mode_filtering(self):$/;" m class:TestMessageFilter
test_sparse_tools tests/test_basic.py /^ def test_sparse_tools(self):$/;" m class:TestToolRegistry test_sparse_tools tests/test_basic.py /^ def test_sparse_tools(self):$/;" m class:TestToolRegistry
test_tool_registry tests/test_simple.py /^def test_tool_registry():$/;" f
test_update_tools tests/test_basic.py /^ def test_update_tools(self):$/;" m class:TestToolRegistry test_update_tools tests/test_basic.py /^ def test_update_tools(self):$/;" m class:TestToolRegistry
test_virtual_tool_handling tests/test_basic.py /^ async def test_virtual_tool_handling(self):$/;" m class:TestMCPBrowser
to_json build/lib/mcp_browser/registry.py /^ def to_json(self) -> str:$/;" m class:ToolRegistry
to_json mcp_browser/registry.py /^ def to_json(self) -> str:$/;" m class:ToolRegistry to_json mcp_browser/registry.py /^ def to_json(self) -> str:$/;" m class:ToolRegistry
trace build/lib/mcp_browser/logging_config.py /^def trace(self, message, *args, **kwargs):$/;" f
trace mcp_browser/logging_config.py /^def trace(self, message, *args, **kwargs):$/;" f
update_checksums build/lib/mcp_browser/default_configs.py /^def update_checksums():$/;" f
update_checksums mcp_browser/default_configs.py /^def update_checksums():$/;" f
update_tools build/lib/mcp_browser/registry.py /^ def update_tools(self, tools: List[Dict[str, Any]]):$/;" m class:ToolRegistry
update_tools mcp_browser/registry.py /^ def update_tools(self, tools: List[Dict[str, Any]]):$/;" m class:ToolRegistry update_tools mcp_browser/registry.py /^ def update_tools(self, tools: List[Dict[str, Any]]):$/;" m class:ToolRegistry
url setup.py /^ url="https:\/\/github.com\/anthropics\/mcp-browser",$/;" v url setup.py /^ url="https:\/\/github.com\/Xilope0\/mcp-browser",$/;" v
user_options setup.py /^ user_options = []$/;" v class:GenerateAIDocs user_options setup.py /^ user_options = []$/;" v class:GenerateAIDocs
user_options setup.py /^ user_options = []$/;" v class:TestCommand
version build/lib/mcp_browser/__main__.py /^ version=f"%(prog)s {__version__}",$/;" v
version mcp_browser/__main__.py /^ version=f"%(prog)s {__version__}",$/;" v
version setup.py /^ version="0.1.0",$/;" v version setup.py /^ version="0.1.0",$/;" v

View File

@ -3,33 +3,84 @@
``` ```
./ ./
setup.py setup.py
test_claude_connection.py mcp_browser.egg-info/
test_onboarding.py systemd/
build/
lib/
mcp_servers/
__init__.py
base.py
screen/
__init__.py
screen_server.py
memory/
__init__.py
memory_server.py
pattern_manager/
__init__.py
pattern_server.py
onboarding/
__init__.py
onboarding_server.py
mcp_browser/
__init__.py
__main__.py
buffer.py
client_main.py
config.py
daemon.py
daemon_main.py
default_configs.py
filter.py
logging_config.py
multi_server.py
proxy.py
registry.py
server.py
utils.py
bdist.linux-x86_64/
docs/ docs/
examples/ examples/
ai_optimized.py ai_optimized.py
basic_usage.py basic_usage.py
builtin_servers_demo.py builtin_servers_demo.py
complete_demo.py complete_demo.py
dist/
tests/ tests/
test_basic.py test_basic.py
test_brave_search.py
test_browser_functionality.py
test_claude_connection.py
test_integration.py
test_onboarding.py
test_simple.py
config/ config/
mcp_servers/ mcp_servers/
__init__.py
base.py base.py
screen/ screen/
__init__.py
screen_server.py screen_server.py
memory/ memory/
__init__.py
memory_server.py memory_server.py
pattern_manager/ pattern_manager/
__init__.py
pattern_server.py pattern_server.py
onboarding/ onboarding/
__init__.py
onboarding_server.py onboarding_server.py
mcp_browser/ mcp_browser/
__init__.py __init__.py
__main__.py __main__.py
buffer.py buffer.py
client_main.py
config.py config.py
daemon.py
daemon_main.py
default_configs.py
filter.py filter.py
logging_config.py
multi_server.py multi_server.py
proxy.py proxy.py
registry.py registry.py

1
init-cmd.json Normal file
View File

@ -0,0 +1 @@
{"method":"initialize","params":{"protocolVersion":"2024-11-05","capabilities":{},"clientInfo":{"name":"claude-ai","version":"0.1.0"}},"jsonrpc":"2.0","id":0}

View File

@ -274,12 +274,23 @@ def main():
# Setup logging # Setup logging
log_file = Path(args.log_file) if args.log_file else None log_file = Path(args.log_file) if args.log_file else None
# In server mode, use syslog unless a log file is specified
use_syslog = args.mode == "server" and not log_file
setup_logging( setup_logging(
debug=args.debug, debug=args.debug,
log_file=log_file, log_file=log_file,
log_level=args.log_level log_level=args.log_level,
use_syslog=use_syslog
) )
# Log startup message
logger = get_logger(__name__)
if args.mode == "server":
logger.debug("mcp-browser client started in server mode")
# Handle modes # Handle modes
if args.mode == "server": if args.mode == "server":
# Run as MCP server # Run as MCP server
@ -302,4 +313,4 @@ def main():
if __name__ == "__main__": if __name__ == "__main__":
main() main()

View File

@ -274,4 +274,73 @@ def is_daemon_running(socket_path: Path) -> bool:
pid = int(pid_file.read_text().strip()) pid = int(pid_file.read_text().strip())
return psutil.pid_exists(pid) return psutil.pid_exists(pid)
except (ValueError, psutil.Error): except (ValueError, psutil.Error):
return False return False
def kill_daemon_with_children(socket_path: Path) -> bool:
"""Kill the daemon and all its child processes."""
pid_file = socket_path.with_suffix('.pid')
if not pid_file.exists():
return False
try:
pid = int(pid_file.read_text().strip())
# Try to use psutil to kill the process tree
if hasattr(psutil, 'Process'):
try:
parent = psutil.Process(pid)
children = parent.children(recursive=True)
# Kill children first
for child in children:
try:
child.terminate()
except psutil.NoSuchProcess:
pass
# Kill parent
parent.terminate()
# Wait a bit for graceful termination
import time
time.sleep(0.5)
# Force kill any remaining processes
for child in children:
try:
child.kill()
except psutil.NoSuchProcess:
pass
try:
parent.kill()
except psutil.NoSuchProcess:
pass
return True
except (psutil.NoSuchProcess, psutil.AccessDenied):
pass
# Fallback to simple kill
try:
os.kill(pid, signal.SIGTERM)
import time
time.sleep(0.5)
os.kill(pid, signal.SIGKILL)
except OSError:
pass
return True
except (ValueError, OSError):
return False
finally:
# Clean up socket and PID file
try:
socket_path.unlink()
except FileNotFoundError:
pass
try:
pid_file.unlink()
except FileNotFoundError:
pass

View File

@ -5,17 +5,18 @@ Intercepts and modifies JSON-RPC messages to implement
sparse mode and virtual tool injection. sparse mode and virtual tool injection.
""" """
import sys
import json import json
from typing import Dict, Any, Optional, List, Callable, Union from typing import Dict, Any, Optional, List, Callable, Union
from .registry import ToolRegistry from .registry import ToolRegistry
class MessageFilter: class MessageFilter:
"""Filter and transform JSON-RPC messages for sparse mode.""" """Filter and transform JSON-RPC messages to always show sparse tools."""
def __init__(self, registry: ToolRegistry, sparse_mode: bool = True): def __init__(self, registry: ToolRegistry, sparse_mode: bool = True):
self.registry = registry self.registry = registry
self.sparse_mode = sparse_mode # Ignore sparse_mode parameter - always use sparse mode
self._handled_ids: set = set() self._handled_ids: set = set()
def filter_outgoing(self, message: dict) -> Optional[dict]: def filter_outgoing(self, message: dict) -> Optional[dict]:
@ -48,9 +49,8 @@ class MessageFilter:
self._handled_ids.discard(message.get("id")) self._handled_ids.discard(message.get("id"))
return None return None
# Intercept tools/list responses for sparse mode # ALWAYS intercept tools/list responses to show only sparse tools
if (self.sparse_mode and if (message.get("id") and
message.get("id") and
message.get("result", {}).get("tools")): message.get("result", {}).get("tools")):
return self._filter_tools_response(message) return self._filter_tools_response(message)
@ -66,7 +66,8 @@ class MessageFilter:
# Replace with sparse tools # Replace with sparse tools
message = message.copy() message = message.copy()
message["result"] = message["result"].copy() message["result"] = message["result"].copy()
message["result"]["tools"] = self.registry.get_sparse_tools() sparse_tools = self.registry.get_sparse_tools()
message["result"]["tools"] = sparse_tools
return message return message

View File

@ -4,6 +4,7 @@ Logging configuration for MCP Browser.
import logging import logging
import sys import sys
import os
from pathlib import Path from pathlib import Path
from typing import Optional from typing import Optional
from datetime import datetime from datetime import datetime
@ -17,7 +18,8 @@ class ServerNameAdapter(logging.LoggerAdapter):
return f"[{server}] {msg}", kwargs return f"[{server}] {msg}", kwargs
def setup_logging(debug: bool = False, log_file: Optional[Path] = None, log_level: Optional[str] = None): def setup_logging(debug: bool = False, log_file: Optional[Path] = None,
log_level: Optional[str] = None, use_syslog: bool = False):
""" """
Configure logging for MCP Browser. Configure logging for MCP Browser.
@ -25,6 +27,7 @@ def setup_logging(debug: bool = False, log_file: Optional[Path] = None, log_leve
debug: Enable debug logging debug: Enable debug logging
log_file: Optional file to write logs to log_file: Optional file to write logs to
log_level: Override log level (DEBUG, INFO, WARNING, ERROR) log_level: Override log level (DEBUG, INFO, WARNING, ERROR)
use_syslog: Use syslog instead of console/file (for server mode)
""" """
# Determine log level # Determine log level
if log_level: if log_level:
@ -52,16 +55,51 @@ def setup_logging(debug: bool = False, log_file: Optional[Path] = None, log_leve
# Remove existing handlers # Remove existing handlers
root_logger.handlers.clear() root_logger.handlers.clear()
# Console handler (stderr) if use_syslog:
console_handler = logging.StreamHandler(sys.stderr) # Use syslog for server mode - NEVER write to stdout/stderr
console_handler.setFormatter(formatter) from logging.handlers import SysLogHandler
root_logger.addHandler(console_handler) try:
# Try Unix socket first (most common on Linux)
# File handler if requested syslog_handler = SysLogHandler(
if log_file: facility=SysLogHandler.LOG_DAEMON,
address='/dev/log'
)
except (OSError, FileNotFoundError):
# Fall back to UDP socket (for macOS, some Linux distros)
try:
syslog_handler = SysLogHandler(
facility=SysLogHandler.LOG_DAEMON,
address=('localhost', 514)
)
except Exception:
# If syslog is not available, log to a file instead
import tempfile
fallback_log = Path(tempfile.gettempdir()) / 'mcp-browser-server.log'
file_handler = logging.FileHandler(fallback_log, mode='a')
file_handler.setFormatter(formatter)
root_logger.addHandler(file_handler)
return
# Syslog has its own format, but we can prepend our app name
syslog_formatter = logging.Formatter('mcp-browser[%(process)d]: %(name)s - %(levelname)s - %(message)s')
syslog_handler.setFormatter(syslog_formatter)
root_logger.addHandler(syslog_handler)
elif log_file:
# File handler if requested
file_handler = logging.FileHandler(log_file, mode='a') file_handler = logging.FileHandler(log_file, mode='a')
file_handler.setFormatter(formatter) file_handler.setFormatter(formatter)
root_logger.addHandler(file_handler) root_logger.addHandler(file_handler)
# Only add console handler if not logging to /dev/null
if str(log_file) != '/dev/null':
console_handler = logging.StreamHandler(sys.stderr)
console_handler.setFormatter(formatter)
root_logger.addHandler(console_handler)
else:
# Console handler (stderr) only if no file specified
console_handler = logging.StreamHandler(sys.stderr)
console_handler.setFormatter(formatter)
root_logger.addHandler(console_handler)
# Set levels for specific loggers # Set levels for specific loggers
# Suppress some noisy libraries unless in debug mode # Suppress some noisy libraries unless in debug mode

View File

@ -62,7 +62,7 @@ class MultiServerManager:
# Initialize each server # Initialize each server
await server.send_request("initialize", { await server.send_request("initialize", {
"protocolVersion": "0.1.0", "protocolVersion": "2024-11-05",
"capabilities": {}, "capabilities": {},
"clientInfo": { "clientInfo": {
"name": "mcp-browser", "name": "mcp-browser",
@ -84,7 +84,7 @@ class MultiServerManager:
# Initialize # Initialize
await server.send_request("initialize", { await server.send_request("initialize", {
"protocolVersion": "0.1.0", "protocolVersion": "2024-11-05",
"capabilities": {}, "capabilities": {},
"clientInfo": { "clientInfo": {
"name": "mcp-browser", "name": "mcp-browser",
@ -148,8 +148,14 @@ class MultiServerManager:
async def stop_all(self): async def stop_all(self):
"""Stop all servers.""" """Stop all servers."""
for name, server in self.servers.items(): # Create a copy of the dictionary to avoid iteration errors
servers_copy = dict(self.servers)
for name, server in servers_copy.items():
self.logger.info(f"Stopping server: {name}") self.logger.info(f"Stopping server: {name}")
await server.stop() try:
await server.stop()
except Exception as e:
self.logger.error(f"Error stopping server {name}: {e}")
self.servers.clear() self.servers.clear()

View File

@ -129,9 +129,6 @@ class MCPBrowser:
} }
}) })
""" """
if not self._initialized:
await self.initialize()
# Ensure request has an ID # Ensure request has an ID
if "id" not in jsonrpc_object: if "id" not in jsonrpc_object:
jsonrpc_object = jsonrpc_object.copy() jsonrpc_object = jsonrpc_object.copy()
@ -140,6 +137,32 @@ class MCPBrowser:
request_id = jsonrpc_object["id"] request_id = jsonrpc_object["id"]
# Handle initialize request specially when acting as a server
if jsonrpc_object.get("method") == "initialize":
# Initialize ourselves if needed
if not self._initialized:
await self.initialize()
# Return our capabilities
return {
"jsonrpc": "2.0",
"id": request_id,
"result": {
"protocolVersion": "2024-11-05",
"capabilities": {
"tools": {}
},
"serverInfo": {
"name": "mcp-browser",
"version": "0.1.0"
}
}
}
# Initialize if needed for other requests
if not self._initialized:
await self.initialize()
# Check if this is a virtual tool call # Check if this is a virtual tool call
if jsonrpc_object.get("method") == "tools/call": if jsonrpc_object.get("method") == "tools/call":
tool_name = jsonrpc_object.get("params", {}).get("name") tool_name = jsonrpc_object.get("params", {}).get("name")
@ -173,16 +196,21 @@ class MCPBrowser:
# In builtin-only mode, try to route to multi-server # In builtin-only mode, try to route to multi-server
if self.multi_server: if self.multi_server:
# Try to route based on method # Try to route based on method
if jsonrpc_object.get("method") == "tools/list": method = jsonrpc_object.get("method")
# Apply filter to multi-server tools
if method == "tools/list":
# Get all tools and apply sparse filter
tools = await self.multi_server.get_all_tools() tools = await self.multi_server.get_all_tools()
filtered_tools = self.filter.filter_outgoing({ response = {
"jsonrpc": "2.0", "jsonrpc": "2.0",
"id": request_id, "id": request_id,
"result": {"tools": tools} "result": {"tools": tools}
}) }
return filtered_tools # Always filter to show only sparse tools
elif jsonrpc_object.get("method") == "tools/call": filtered_response = self.filter.filter_incoming(response)
return filtered_response
elif method == "tools/call":
# Route tool call to multi-server # Route tool call to multi-server
tool_name = jsonrpc_object.get("params", {}).get("name") tool_name = jsonrpc_object.get("params", {}).get("name")
args = jsonrpc_object.get("params", {}).get("arguments", {}) args = jsonrpc_object.get("params", {}).get("arguments", {})
@ -199,6 +227,57 @@ class MCPBrowser:
"id": request_id, "id": request_id,
"error": {"code": -32603, "message": str(e)} "error": {"code": -32603, "message": str(e)}
} }
elif method == "prompts/list":
# No prompts in builtin-only mode
return {
"jsonrpc": "2.0",
"id": request_id,
"result": {"prompts": []}
}
elif method == "prompts/get":
# No prompts available
return {
"jsonrpc": "2.0",
"id": request_id,
"error": {"code": -32602, "message": "Prompt not found"}
}
elif method == "resources/list":
# No resources in builtin-only mode
return {
"jsonrpc": "2.0",
"id": request_id,
"result": {"resources": []}
}
elif method == "resources/read":
# No resources available
return {
"jsonrpc": "2.0",
"id": request_id,
"error": {"code": -32602, "message": "Resource not found"}
}
elif method == "completion/complete":
# No completions in builtin-only mode
return {
"jsonrpc": "2.0",
"id": request_id,
"result": {"completion": {"values": []}}
}
else:
# Unknown method
return {
"jsonrpc": "2.0",
"id": request_id,
"error": {
"code": -32601,
"message": f"Method '{method}' not found"
}
}
# No server available # No server available
return { return {
@ -269,7 +348,7 @@ class MCPBrowser:
# Send initialize request directly to server # Send initialize request directly to server
init_response = await self.server.send_request("initialize", { init_response = await self.server.send_request("initialize", {
"protocolVersion": "0.1.0", "protocolVersion": "2024-11-05",
"capabilities": {}, "capabilities": {},
"clientInfo": { "clientInfo": {
"name": "mcp-browser", "name": "mcp-browser",

View File

@ -105,58 +105,83 @@ class BaseMCPServer(ABC):
"""Run the MCP server, reading from stdin and writing to stdout.""" """Run the MCP server, reading from stdin and writing to stdout."""
self._running = True self._running = True
# Platform-specific non-blocking setup # Log server startup
print(f"DEBUG: {self.name} server starting", file=sys.stderr, flush=True)
# Use asyncio for stdin reading
loop = asyncio.get_event_loop()
stdin_reader = asyncio.StreamReader()
stdin_protocol = asyncio.StreamReaderProtocol(stdin_reader)
try: try:
import fcntl # Connect stdin to async reader
import os await loop.connect_read_pipe(lambda: stdin_protocol, sys.stdin)
flags = fcntl.fcntl(sys.stdin.fileno(), fcntl.F_GETFL) except Exception as e:
fcntl.fcntl(sys.stdin.fileno(), fcntl.F_SETFL, flags | os.O_NONBLOCK) print(f"ERROR: {self.name} failed to setup async stdin: {e}", file=sys.stderr, flush=True)
except ImportError: return
# Windows doesn't have fcntl
pass
buffer = ""
# Main server loop
while self._running: while self._running:
try: try:
# Try to read available data # Read a line with timeout to prevent hanging
chunk = sys.stdin.read(4096) line = await asyncio.wait_for(
if not chunk: stdin_reader.readline(),
# EOF reached timeout=None # No timeout - we want to wait indefinitely for commands
)
if not line:
# Empty bytes means EOF
print(f"DEBUG: {self.name} detected EOF on stdin", file=sys.stderr, flush=True)
break break
buffer += chunk
# Process complete lines # Decode and process line
while '\n' in buffer: line_str = line.decode('utf-8').strip()
line, buffer = buffer.split('\n', 1) if not line_str:
line = line.strip() continue
print(f"DEBUG: {self.name} received: {line_str}", file=sys.stderr, flush=True)
try:
request = json.loads(line_str)
response = await self.handle_request(request)
response_str = json.dumps(response)
print(f"DEBUG: {self.name} sending: {response_str}", file=sys.stderr, flush=True)
print(response_str, flush=True)
except json.JSONDecodeError as e:
print(f"ERROR: {self.name} JSON decode error: {e}", file=sys.stderr, flush=True)
error_response = {
"jsonrpc": "2.0",
"id": None,
"error": {
"code": -32700,
"message": "Parse error"
}
}
print(json.dumps(error_response), flush=True)
except Exception as e:
print(f"ERROR: {self.name} request handling error: {e}", file=sys.stderr, flush=True)
error_response = {
"jsonrpc": "2.0",
"id": None,
"error": {
"code": -32603,
"message": str(e)
}
}
print(json.dumps(error_response), flush=True)
if line: except asyncio.CancelledError:
try: print(f"DEBUG: {self.name} cancelled", file=sys.stderr, flush=True)
request = json.loads(line)
response = await self.handle_request(request)
print(json.dumps(response), flush=True)
except json.JSONDecodeError:
pass
except Exception as e:
error_response = {
"jsonrpc": "2.0",
"id": None,
"error": {
"code": -32700,
"message": "Parse error"
}
}
print(json.dumps(error_response), flush=True)
except BlockingIOError:
# No data available, sleep briefly
await asyncio.sleep(0.01)
except EOFError:
# stdin closed
break break
except KeyboardInterrupt: except KeyboardInterrupt:
print(f"DEBUG: {self.name} interrupted", file=sys.stderr, flush=True)
break break
except Exception as e:
print(f"ERROR: {self.name} unexpected error: {e}", file=sys.stderr, flush=True)
# Continue running despite errors
await asyncio.sleep(0.1)
print(f"DEBUG: {self.name} server exiting", file=sys.stderr, flush=True)
def content_text(self, text: str) -> Dict[str, Any]: def content_text(self, text: str) -> Dict[str, Any]:
"""Helper to create text content response.""" """Helper to create text content response."""

View File

@ -205,9 +205,9 @@ setup(
python_requires=">=3.8", python_requires=">=3.8",
entry_points={ entry_points={
"console_scripts": [ "console_scripts": [
"mcp-browser=mcp_browser.client_main:main", "mcp-browser=mcp_browser.__main__:main",
"mcp-browser-daemon=mcp_browser.daemon_main:main", "mcp-browser-daemon=mcp_browser.daemon_main:main",
"mcp-browser-legacy=mcp_browser.__main__:main", "mcp-browser-client=mcp_browser.client_main:main",
], ],
}, },
cmdclass={ cmdclass={

171
test_claude_desktop_flow.py Normal file
View File

@ -0,0 +1,171 @@
#!/usr/bin/env python3
"""
Test the exact Claude Desktop flow to identify the timeout issue.
"""
import asyncio
import json
import subprocess
import sys
import os
sys.path.insert(0, os.path.dirname(os.path.abspath(__file__)))
async def test_server_mode_timeout():
"""Test server mode with proper timeout handling."""
print("Testing Claude Desktop flow with timeout...")
# Start mcp-browser in server mode
proc = subprocess.Popen(
[sys.executable, "-m", "mcp_browser", "--mode", "server"],
stdin=subprocess.PIPE,
stdout=subprocess.PIPE,
stderr=subprocess.PIPE,
text=True,
bufsize=1
)
try:
# Send initialize request like Claude Desktop does
init_request = {
"jsonrpc": "2.0",
"id": 0,
"method": "initialize",
"params": {
"protocolVersion": "2024-11-05",
"capabilities": {},
"clientInfo": {
"name": "claude-desktop",
"version": "0.7.2"
}
}
}
print(f"Sending: {json.dumps(init_request)}")
proc.stdin.write(json.dumps(init_request) + "\n")
proc.stdin.flush()
# Wait for response with timeout
response_received = False
start_time = asyncio.get_event_loop().time()
while asyncio.get_event_loop().time() - start_time < 5.0: # 5 second timeout
try:
# Non-blocking read
line = proc.stdout.readline()
if line:
response = json.loads(line.strip())
print(f"Received: {json.dumps(response, indent=2)}")
response_received = True
break
except:
await asyncio.sleep(0.1)
continue
await asyncio.sleep(0.1)
if not response_received:
print("ERROR: No response received within 5 seconds!")
# Check stderr for errors
stderr_output = proc.stderr.read()
if stderr_output:
print(f"STDERR: {stderr_output}")
else:
# Send initialized notification
initialized = {
"jsonrpc": "2.0",
"method": "initialized"
}
print(f"\nSending: {json.dumps(initialized)}")
proc.stdin.write(json.dumps(initialized) + "\n")
proc.stdin.flush()
# Test tools/list
tools_request = {
"jsonrpc": "2.0",
"id": 1,
"method": "tools/list"
}
print(f"\nSending: {json.dumps(tools_request)}")
proc.stdin.write(json.dumps(tools_request) + "\n")
proc.stdin.flush()
# Wait for tools response
start_time = asyncio.get_event_loop().time()
while asyncio.get_event_loop().time() - start_time < 2.0:
line = proc.stdout.readline()
if line:
response = json.loads(line.strip())
print(f"Received: {json.dumps(response, indent=2)}")
break
await asyncio.sleep(0.1)
finally:
proc.terminate()
proc.wait()
async def test_with_logging():
"""Test with debug logging enabled."""
print("\n\nTesting with debug logging...")
# Start mcp-browser in server mode with debug
proc = subprocess.Popen(
[sys.executable, "-m", "mcp_browser", "--mode", "server", "--debug", "--log-file", "/tmp/mcp-test.log"],
stdin=subprocess.PIPE,
stdout=subprocess.PIPE,
stderr=subprocess.PIPE,
text=True,
bufsize=1
)
try:
# Send initialize
init_request = {
"jsonrpc": "2.0",
"id": 0,
"method": "initialize",
"params": {
"protocolVersion": "2024-11-05",
"capabilities": {},
"clientInfo": {
"name": "test-client",
"version": "1.0.0"
}
}
}
proc.stdin.write(json.dumps(init_request) + "\n")
proc.stdin.flush()
# Read with timeout
await asyncio.sleep(1.0)
# Try to read response
output = proc.stdout.read()
if output:
print(f"STDOUT: {output}")
stderr = proc.stderr.read()
if stderr:
print(f"STDERR: {stderr}")
# Check log file
try:
with open("/tmp/mcp-test.log", "r") as f:
log_content = f.read()
if log_content:
print(f"\nLOG FILE:\n{log_content}")
except:
pass
finally:
proc.terminate()
proc.wait()
if __name__ == "__main__":
asyncio.run(test_server_mode_timeout())
asyncio.run(test_with_logging())

260
test_mcp_protocol.py Normal file
View File

@ -0,0 +1,260 @@
#!/usr/bin/env python3
"""
Test MCP Protocol flow to understand and verify the initialization handshake.
This test will:
1. Create a minimal MCP server that logs all interactions
2. Create an MCP browser client
3. Verify the complete initialization flow
4. Test tools/list and tools/call
"""
import asyncio
import json
import sys
import os
import tempfile
from pathlib import Path
# Add project to path
sys.path.insert(0, os.path.dirname(os.path.abspath(__file__)))
from mcp_browser import MCPBrowser
from mcp_browser.daemon import MCPBrowserDaemon, MCPBrowserClient, get_socket_path
def log_test(msg):
"""Log test messages with timestamp."""
import datetime
timestamp = datetime.datetime.now().strftime("%H:%M:%S.%f")[:-3]
print(f"[{timestamp}] {msg}")
async def test_direct_initialization():
"""Test direct initialization without daemon."""
log_test("=== TEST 1: Direct Initialization ===")
# Create browser with correct config
browser = MCPBrowser(enable_builtin_servers=True)
try:
log_test("Initializing browser...")
await browser.initialize()
log_test("✓ Browser initialized successfully")
# Test tools/list
log_test("Calling tools/list...")
response = await browser.call({
"jsonrpc": "2.0",
"id": 1,
"method": "tools/list"
})
if "result" in response:
tools = response["result"].get("tools", [])
log_test(f"✓ Got {len(tools)} tools: {[t['name'] for t in tools]}")
else:
log_test(f"✗ Error in tools/list: {response}")
except Exception as e:
log_test(f"✗ Error: {e}")
import traceback
traceback.print_exc()
finally:
await browser.close()
async def test_daemon_initialization():
"""Test initialization through daemon."""
log_test("\n=== TEST 2: Daemon Initialization ===")
# Use a temporary socket
with tempfile.TemporaryDirectory() as tmpdir:
socket_path = Path(tmpdir) / "test-mcp.sock"
# Create browser and daemon
browser = MCPBrowser(enable_builtin_servers=True)
daemon = MCPBrowserDaemon(browser, socket_path)
# Start daemon in background
daemon_task = asyncio.create_task(daemon.start())
try:
# Give daemon time to start
await asyncio.sleep(0.1)
# Connect as client
async with MCPBrowserClient(socket_path) as client:
log_test("Connected to daemon")
# Send initialize - this should be handled by the proxy
log_test("Sending initialize request...")
init_request = {
"jsonrpc": "2.0",
"id": 0,
"method": "initialize",
"params": {
"protocolVersion": "2024-11-05",
"capabilities": {},
"clientInfo": {
"name": "test-client",
"version": "1.0.0"
}
}
}
response = await client.call(init_request)
log_test(f"Initialize response: {json.dumps(response, indent=2)}")
# Check response
if "result" in response:
result = response["result"]
if result.get("protocolVersion") == "2024-11-05":
log_test("✓ Got correct protocol version")
else:
log_test(f"✗ Wrong protocol version: {result.get('protocolVersion')}")
else:
log_test(f"✗ Error in initialize: {response}")
# Test tools/list
log_test("\nSending tools/list request...")
tools_request = {
"jsonrpc": "2.0",
"id": 1,
"method": "tools/list"
}
response = await client.call(tools_request)
if "result" in response:
tools = response["result"].get("tools", [])
log_test(f"✓ Got {len(tools)} tools: {[t['name'] for t in tools]}")
else:
log_test(f"✗ Error in tools/list: {response}")
finally:
# Stop daemon
await daemon.stop()
daemon_task.cancel()
try:
await daemon_task
except asyncio.CancelledError:
pass
async def test_server_mode_initialization():
"""Test server mode (stdin/stdout) initialization."""
log_test("\n=== TEST 3: Server Mode Initialization ===")
# This simulates what Claude Desktop does
browser = MCPBrowser(enable_builtin_servers=True)
await browser.initialize()
# Simulate initialize request from Claude Desktop
init_request = {
"jsonrpc": "2.0",
"id": 0,
"method": "initialize",
"params": {
"protocolVersion": "2024-11-05",
"capabilities": {},
"clientInfo": {
"name": "claude-desktop",
"version": "0.7.2"
}
}
}
log_test("Processing initialize request from Claude Desktop...")
response = await browser.call(init_request)
log_test(f"Response: {json.dumps(response, indent=2)}")
# Check if we need to send initialized notification
if "result" in response:
log_test("✓ Initialize successful")
# Claude Desktop would send initialized notification
initialized_notif = {
"jsonrpc": "2.0",
"method": "initialized"
}
log_test("Sending initialized notification...")
# Notifications don't expect responses
await browser.call(initialized_notif)
# Now test tools/list
tools_request = {
"jsonrpc": "2.0",
"id": 1,
"method": "tools/list"
}
response = await browser.call(tools_request)
if "result" in response:
tools = response["result"].get("tools", [])
log_test(f"✓ Got {len(tools)} tools in sparse mode")
else:
log_test(f"✗ Error in tools/list: {response}")
await browser.close()
async def test_double_handshake_issue():
"""Test the specific issue: Claude Desktop -> mcp-browser -> MCP servers."""
log_test("\n=== TEST 4: Double Handshake Issue ===")
# When Claude Desktop connects to mcp-browser in server mode:
# 1. Claude Desktop sends initialize to mcp-browser
# 2. mcp-browser should respond with its capabilities
# 3. mcp-browser internally initializes connections to MCP servers
# 4. But it should NOT forward the initialize request to MCP servers
browser = MCPBrowser(enable_builtin_servers=True)
# The browser should initialize its internal servers first
log_test("Browser initializing internal servers...")
await browser.initialize()
# Now simulate Claude Desktop connecting
init_from_claude = {
"jsonrpc": "2.0",
"id": 0,
"method": "initialize",
"params": {
"protocolVersion": "2024-11-05",
"capabilities": {},
"clientInfo": {
"name": "claude-desktop",
"version": "0.7.2"
}
}
}
log_test("Claude Desktop sends initialize...")
response = await browser.call(init_from_claude)
if "result" in response:
log_test("✓ mcp-browser responded to initialize")
log_test(f" Protocol: {response['result'].get('protocolVersion')}")
log_test(f" Server: {response['result'].get('serverInfo', {}).get('name')}")
else:
log_test(f"✗ Error: {response}")
await browser.close()
async def main():
"""Run all tests."""
log_test("Starting MCP Protocol Tests")
log_test("=" * 60)
# Run tests
await test_direct_initialization()
await test_daemon_initialization()
await test_server_mode_initialization()
await test_double_handshake_issue()
log_test("\n" + "=" * 60)
log_test("Tests completed!")
if __name__ == "__main__":
asyncio.run(main())