Skip to main content
Glama

System Information MCP Server

by dknell
test_tools.py•12.4 kB
"""Tests for tool implementations.""" import pytest from unittest.mock import patch, MagicMock from system_info_mcp.tools import ( get_cpu_info, get_memory_info, get_disk_info, get_network_info, get_process_list, get_system_uptime, get_temperature_info, ) from system_info_mcp.utils import clear_cache class TestCpuInfo: """Test CPU information tool.""" def setup_method(self): """Clear cache before each test.""" clear_cache() @patch("system_info_mcp.tools.psutil.cpu_percent") @patch("system_info_mcp.tools.psutil.cpu_count") @patch("system_info_mcp.tools.psutil.cpu_freq") @patch("system_info_mcp.tools.os.getloadavg") def test_get_cpu_info_basic( self, mock_loadavg, mock_freq, mock_count, mock_percent ): """Test basic CPU info retrieval.""" # Mock psutil responses mock_percent.return_value = 45.2 mock_count.side_effect = lambda logical=True: 8 if logical else 4 mock_freq.return_value = MagicMock(current=2400.0, max=3400.0) mock_loadavg.return_value = (1.2, 1.5, 1.8) result = get_cpu_info(interval=0.1) assert result["cpu_percent"] == 45.2 assert result["cpu_count_logical"] == 8 assert result["cpu_count_physical"] == 4 assert result["cpu_freq_current"] == 2400.0 assert result["cpu_freq_max"] == 3400.0 assert result["load_average"] == [1.2, 1.5, 1.8] assert "per_cpu_percent" not in result @patch("system_info_mcp.tools.psutil.cpu_percent") @patch("system_info_mcp.tools.psutil.cpu_count") @patch("system_info_mcp.tools.psutil.cpu_freq") @patch("system_info_mcp.tools.os.getloadavg") def test_get_cpu_info_per_cpu( self, mock_loadavg, mock_freq, mock_count, mock_percent ): """Test CPU info with per-CPU breakdown.""" # First call is for overall CPU, second call is for per-CPU mock_percent.side_effect = [45.2, [42.1, 48.3, 44.7, 46.9]] mock_count.side_effect = lambda logical=True: 4 if logical else 2 mock_freq.return_value = MagicMock(current=2400.0, max=3400.0) mock_loadavg.return_value = (1.0, 1.0, 1.0) result = get_cpu_info(interval=0.1, per_cpu=True) assert result["per_cpu_percent"] == [42.1, 48.3, 44.7, 46.9] @patch("system_info_mcp.tools.psutil.cpu_percent") @patch("system_info_mcp.tools.psutil.cpu_count") @patch("system_info_mcp.tools.psutil.cpu_freq") @patch("system_info_mcp.tools.os.getloadavg") def test_get_cpu_info_invalid_interval(self, mock_loadavg, mock_freq, mock_count, mock_percent): """Test CPU info with invalid interval.""" clear_cache() # Clear cache for clean test with pytest.raises(ValueError, match="Interval must be a positive number"): get_cpu_info(interval=-1.0) with pytest.raises(ValueError, match="Interval must be a positive number"): get_cpu_info(interval=0.0) class TestMemoryInfo: """Test memory information tool.""" def setup_method(self): """Clear cache before each test.""" clear_cache() @patch("system_info_mcp.tools.psutil.virtual_memory") @patch("system_info_mcp.tools.psutil.swap_memory") def test_get_memory_info(self, mock_swap, mock_virtual): """Test memory info retrieval.""" # Mock virtual memory mock_virtual.return_value = MagicMock( total=17179869184, # 16 GB available=8589934592, # 8 GB used=8589934592, # 8 GB percent=50.0, ) # Mock swap memory mock_swap.return_value = MagicMock( total=2147483648, used=0, free=2147483648, percent=0.0 # 2 GB ) result = get_memory_info() assert result["virtual_memory"]["total"] == 17179869184 assert result["virtual_memory"]["available"] == 8589934592 assert result["virtual_memory"]["used"] == 8589934592 assert result["virtual_memory"]["percent"] == 50.0 assert result["virtual_memory"]["total_gb"] == 16.0 assert result["virtual_memory"]["available_gb"] == 8.0 assert result["virtual_memory"]["used_gb"] == 8.0 assert result["swap_memory"]["total"] == 2147483648 assert result["swap_memory"]["used"] == 0 assert result["swap_memory"]["free"] == 2147483648 assert result["swap_memory"]["percent"] == 0.0 assert result["swap_memory"]["total_gb"] == 2.0 class TestDiskInfo: """Test disk information tool.""" def setup_method(self): """Clear cache before each test.""" clear_cache() @patch("system_info_mcp.tools.psutil.disk_partitions") @patch("system_info_mcp.tools.psutil.disk_usage") def test_get_disk_info_all_disks(self, mock_usage, mock_partitions): """Test disk info for all disks.""" # Mock partitions mock_partitions.return_value = [ MagicMock(mountpoint="/", device="/dev/disk1s1", fstype="apfs") ] # Mock disk usage mock_usage.return_value = MagicMock( total=494384795648, # ~460 GB used=123456789012, # ~115 GB free=370927006636, # ~345 GB ) result = get_disk_info() assert len(result["disks"]) == 1 disk = result["disks"][0] assert disk["mountpoint"] == "/" assert disk["device"] == "/dev/disk1s1" assert disk["fstype"] == "apfs" assert disk["total"] == 494384795648 assert disk["used"] == 123456789012 assert disk["free"] == 370927006636 assert disk["percent"] == 25.0 @patch("system_info_mcp.tools.psutil.disk_usage") def test_get_disk_info_specific_path(self, mock_usage): """Test disk info for specific path.""" mock_usage.return_value = MagicMock( total=1000000000, used=500000000, free=500000000 ) result = get_disk_info(path="/home") assert len(result["disks"]) == 1 disk = result["disks"][0] assert disk["mountpoint"] == "/home" assert disk["device"] == "N/A" assert disk["fstype"] == "N/A" assert disk["percent"] == 50.0 class TestNetworkInfo: """Test network information tool.""" def setup_method(self): """Clear cache before each test.""" clear_cache() @patch("system_info_mcp.tools.psutil.net_if_addrs") @patch("system_info_mcp.tools.psutil.net_if_stats") @patch("system_info_mcp.tools.psutil.net_io_counters") def test_get_network_info(self, mock_io, mock_stats, mock_addrs): """Test network info retrieval.""" # Mock network interfaces mock_addrs.return_value = { "en0": [ MagicMock( family=2, # AF_INET address="192.168.1.100", netmask="255.255.255.0", ) ] } mock_stats.return_value = {"en0": MagicMock(isup=True, speed=1000, mtu=1500)} mock_io.return_value = MagicMock( bytes_sent=1234567890, bytes_recv=9876543210, packets_sent=123456, packets_recv=654321, errin=0, errout=0, dropin=0, dropout=0, ) result = get_network_info() assert len(result["interfaces"]) == 1 interface = result["interfaces"][0] assert interface["name"] == "en0" assert interface["is_up"] is True assert interface["speed"] == 1000 assert interface["mtu"] == 1500 assert len(interface["addresses"]) == 1 assert interface["addresses"][0]["address"] == "192.168.1.100" stats = result["stats"] assert stats["bytes_sent"] == 1234567890 assert stats["bytes_recv"] == 9876543210 assert stats["packets_sent"] == 123456 assert stats["packets_recv"] == 654321 class TestProcessList: """Test process list tool.""" def setup_method(self): """Clear cache before each test.""" clear_cache() @patch("system_info_mcp.tools.psutil.process_iter") def test_get_process_list_basic(self, mock_iter): """Test basic process list retrieval.""" # Mock process data mock_process = MagicMock() mock_process.info = { "pid": 1234, "name": "python3", "username": "user", "status": "running", "cpu_percent": 15.2, "memory_percent": 2.1, "memory_info": MagicMock(rss=134217728), # 128 MB "create_time": 1642252200.0, "cmdline": ["python3", "app.py"], } mock_iter.return_value = [mock_process] result = get_process_list(limit=10) assert len(result["processes"]) == 1 assert result["total_processes"] == 1 process = result["processes"][0] assert process["pid"] == 1234 assert process["name"] == "python3" assert process["username"] == "user" assert process["status"] == "running" assert process["cpu_percent"] == 15.2 assert process["memory_percent"] == 2.1 assert process["memory_rss"] == 134217728 assert process["memory_rss_mb"] == 128.0 assert process["cmdline"] == ["python3", "app.py"] def test_get_process_list_invalid_parameters(self): """Test process list with invalid parameters.""" clear_cache() # Clear cache for clean test with pytest.raises(ValueError, match="Limit must be a positive number"): get_process_list(limit=-1) with pytest.raises(ValueError, match="sort_by must be one of"): get_process_list(sort_by="invalid") class TestSystemUptime: """Test system uptime tool.""" def setup_method(self): """Clear cache before each test.""" clear_cache() @patch("system_info_mcp.tools.psutil.boot_time") @patch("system_info_mcp.tools.time.time") def test_get_system_uptime(self, mock_time, mock_boot): """Test system uptime retrieval.""" mock_boot.return_value = 1609459200.0 # 2021-01-01 00:00:00 UTC mock_time.return_value = ( 1609545600.0 # 2021-01-02 00:00:00 UTC (24 hours later) ) result = get_system_uptime() assert result["boot_time"] == "2021-01-01T00:00:00+00:00" assert result["uptime_seconds"] == 86400 # 24 hours assert result["uptime_formatted"] == "1 day" class TestTemperatureInfo: """Test temperature information tool.""" def setup_method(self): """Clear cache before each test.""" clear_cache() @patch("system_info_mcp.tools.psutil.sensors_temperatures", create=True) @patch("system_info_mcp.tools.psutil.sensors_fans", create=True) def test_get_temperature_info_available(self, mock_fans, mock_temps): """Test temperature info when sensors are available.""" # Mock temperature sensors mock_temps.return_value = { "cpu_thermal": [ MagicMock(label="CPU Package", current=45.0, high=100.0, critical=105.0) ] } # Mock fan sensors mock_fans.return_value = {"cpu_fan": [MagicMock(label="CPU Fan", current=1200)]} result = get_temperature_info() assert len(result["temperatures"]) == 1 temp = result["temperatures"][0] assert temp["name"] == "CPU Package" assert temp["current"] == 45.0 assert temp["high"] == 100.0 assert temp["critical"] == 105.0 assert temp["unit"] == "celsius" assert len(result["fans"]) == 1 fan = result["fans"][0] assert fan["name"] == "CPU Fan" assert fan["current_speed"] == 1200 assert fan["unit"] == "rpm" @patch("system_info_mcp.tools.psutil.sensors_temperatures", create=True) @patch("system_info_mcp.tools.psutil.sensors_fans", create=True) def test_get_temperature_info_unavailable(self, mock_fans, mock_temps): """Test temperature info when sensors are unavailable.""" mock_temps.side_effect = AttributeError("Not supported") mock_fans.side_effect = AttributeError("Not supported") result = get_temperature_info() assert result["temperatures"] == [] assert result["fans"] == []

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/dknell/mcp-system-info'

If you have feedback or need assistance with the MCP directory API, please join our Discord server