MCP server for managing SSH connections and executing remote commands
Project description
Remote Shell MCP Server
A Model Context Protocol (MCP) server that enables AI models to manage SSH connections and execute commands on remote machines without repeatedly entering credentials. Built with FastMCP and Paramiko for cross-platform compatibility.
Features
- 🔐 Multiple Authentication Methods: Support both password and SSH key authentication
- 🔄 Persistent Connections: Create and maintain SSH connections across multiple operations
- 📁 File Transfer: Upload and download files between local and remote machines
- ⚙️ Flexible Configuration: Three ways to configure connections (global config, server args, or dynamic)
- 🌐 Multi-Connection Support: Manage multiple remote hosts simultaneously
- 🛠️ Simple MCP Tools: Easy-to-use tools for command execution and file operations
Installation
Option 1: Install from PyPI (Recommended)
# Install with pip
pip install remoteshell-mcp
# Or install with uv
uv pip install remoteshell-mcp
Option 2: Install from Source
Prerequisites
- Python 3.11 or higher
- uv package manager
Steps
# Clone the repository
git clone https://github.com/chouzz/remoteShell-mcp.git
cd remoteShell-mcp
# Install dependencies
uv sync
# The server is now ready to use
Configuration
There are three ways to configure SSH connections:
1. Global Configuration File (Recommended for Personal Use)
Create a configuration file at ~/.remoteShell/config.json:
{
"connections": [
{
"id": "prod-server",
"host": "192.168.1.100",
"port": 22,
"user": "admin",
"auth_type": "password",
"password": "your_password"
},
{
"id": "dev-server",
"host": "192.168.1.101",
"port": 22,
"user": "developer",
"auth_type": "key",
"key_path": "~/.ssh/id_rsa"
}
]
}
Security Note: Ensure this file has proper permissions:
chmod 600 ~/.remoteShell/config.json
2. MCP Client Configuration (Recommended for Claude Code/Cursor)
Configure connections directly in your MCP client settings (see below for specific examples).
3. Dynamic Creation
Create connections on-the-fly using the create_connection tool during a conversation with your AI assistant.
Client Setup
Claude Code Configuration
Add the following to your Claude Code MCP settings file (usually located at ~/Library/Application Support/Claude/claude_desktop_config.json on macOS):
{
"mcpServers": {
"remoteshell": {
"command": "uv",
"args": [
"--directory",
"/absolute/path/to/remoteShell-mcp",
"run",
"remoteshell-mcp"
]
}
}
}
With Pre-configured Connections:
{
"mcpServers": {
"remoteshell": {
"command": "uv",
"args": [
"--directory",
"/absolute/path/to/remoteShell-mcp",
"run",
"remoteshell-mcp",
"--connections",
"[{\"id\":\"server1\",\"host\":\"192.168.1.100\",\"user\":\"admin\",\"auth_type\":\"password\",\"password\":\"secret\"}]"
]
}
}
}
Or reference a configuration file:
{
"mcpServers": {
"remoteshell": {
"command": "uv",
"args": [
"--directory",
"/absolute/path/to/remoteShell-mcp",
"run",
"remoteshell-mcp",
"--connections",
"/path/to/your/connections.json"
]
}
}
}
Cursor Configuration
Add the following to your Cursor settings (Settings → Features → MCP):
{
"mcpServers": {
"remoteshell": {
"command": "uv",
"args": [
"--directory",
"/absolute/path/to/remoteShell-mcp",
"run",
"remoteshell-mcp"
]
}
}
}
With Pre-configured Connections:
{
"mcpServers": {
"remoteshell": {
"command": "uv",
"args": [
"--directory",
"/absolute/path/to/remoteShell-mcp",
"run",
"remoteshell-mcp",
"--connections",
"/path/to/your/connections.json"
]
}
}
}
Note: Replace /absolute/path/to/remoteShell-mcp with the actual absolute path to this repository on your system.
Available Tools
1. create_connection
Create a new SSH connection to a remote host.
Parameters:
host(required): Remote host address (IP or domain)user(required): Username for authenticationport(optional): SSH port (default: 22)password(optional): Password for authenticationkey_path(optional): Path to SSH private key fileconnection_id(optional): Custom connection ID (auto-generated if not provided)
Example Usage:
Create a connection to 192.168.1.100 with username admin and password secret123
2. execute_command
Execute a command on a remote host.
Parameters:
connection_id(required): ID of the connection to usecommand(required): Command to executetimeout(optional): Command timeout in secondsworking_dir(optional): Working directory for command execution
Example Usage:
Execute "ls -la /home" on prod-server
3. upload_file
Upload a file from local machine to remote host.
Parameters:
connection_id(required): ID of the connection to uselocal_path(required): Path to local fileremote_path(required): Destination path on remote host
Example Usage:
Upload /tmp/config.txt to /etc/app/config.txt on prod-server
4. download_file
Download a file from remote host to local machine.
Parameters:
connection_id(required): ID of the connection to useremote_path(required): Path to file on remote hostlocal_path(required): Destination path on local machine
Example Usage:
Download /var/log/app.log from prod-server to /tmp/app.log
5. list_connections
List all available connections (both active and pre-configured).
Example Usage:
Show me all available connections
6. close_connection
Close an active SSH connection.
Parameters:
connection_id(required): ID of the connection to close
Example Usage:
Close the connection to prod-server
Usage Examples
Basic Workflow
-
List available connections:
Show me all configured connections -
Execute a command:
Run "df -h" on prod-server -
Create a new connection dynamically:
Connect to 192.168.1.200 with username ubuntu using SSH key at ~/.ssh/mykey.pem, call it web-server -
Upload a file:
Upload my local file /tmp/data.csv to /home/user/data.csv on web-server -
Download a file:
Download /var/log/nginx/access.log from web-server to ~/Downloads/access.log
Advanced Usage
Execute commands in a specific directory:
Run "npm install" on dev-server in the /var/www/myapp directory
Check system resources on multiple servers:
Check disk space on prod-server and dev-server
Batch file operations:
Upload all .conf files from /etc/local to /etc/remote on backup-server
Security Considerations
-
Credential Storage:
- Store passwords and keys securely
- Use file permissions to protect config files (chmod 600)
- Consider using SSH keys instead of passwords when possible
-
SSH Key Authentication:
- More secure than password authentication
- Keys can be password-protected for additional security
- Use different keys for different hosts when possible
-
Connection Timeouts:
- Set appropriate timeouts to prevent hanging connections
- Connections automatically reconnect if they drop
-
Global Config File:
- Located at
~/.remoteShell/config.json - Should have restrictive permissions (600)
- Consider encrypting sensitive data at rest
- Located at
Troubleshooting
Connection Issues
Problem: "Authentication failed"
- Solution: Verify username and password/key path are correct
- Solution: Ensure SSH key has proper permissions (chmod 600)
Problem: "Connection timed out"
- Solution: Check if host is reachable (ping)
- Solution: Verify firewall rules allow SSH connections
- Solution: Confirm SSH service is running on remote host
Problem: "SSH key file not found"
- Solution: Use absolute path or expand ~ properly
- Solution: Verify file exists and is readable
File Transfer Issues
Problem: "Permission denied" during upload
- Solution: Check write permissions on remote directory
- Solution: Ensure remote user has necessary permissions
Problem: "No such file or directory" during download
- Solution: Verify remote file path is correct
- Solution: Check if file exists on remote host
Development
Running Tests
uv run pytest
Project Structure
remoteShell-mcp/
├── src/
│ └── remoteshell_mcp/
│ ├── __init__.py
│ ├── server.py # FastMCP server with tools
│ ├── connection_manager.py # SSH connection management
│ ├── ssh_client.py # Paramiko wrapper
│ └── config_loader.py # Configuration handling
├── config.example.json # Example configuration
├── pyproject.toml # Project dependencies
└── README.md # This file
License
MIT License - See LICENSE file for details
Contributing
Contributions are welcome! Please feel free to submit a Pull Request.
Support
For issues, questions, or contributions, please open an issue on the GitHub repository.
Project details
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file remoteshell_mcp-0.1.0.tar.gz.
File metadata
- Download URL: remoteshell_mcp-0.1.0.tar.gz
- Upload date:
- Size: 89.4 kB
- Tags: Source
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.7
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
0a8e1ed811b607008dbda269327242790acaec4fe18509e46d476d391e98b6de
|
|
| MD5 |
74d39af5032c50862322e830c0dd3735
|
|
| BLAKE2b-256 |
6393d71c1fa1ffbc6be35833259a77ea8b11a2edb825b72bdf52724d8c3923af
|
Provenance
The following attestation bundles were made for remoteshell_mcp-0.1.0.tar.gz:
Publisher:
publish.yml on chouzz/remoteShell-mcp
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
remoteshell_mcp-0.1.0.tar.gz -
Subject digest:
0a8e1ed811b607008dbda269327242790acaec4fe18509e46d476d391e98b6de - Sigstore transparency entry: 699854247
- Sigstore integration time:
-
Permalink:
chouzz/remoteShell-mcp@c33618f898638095430d48f38f8a131f7131d0af -
Branch / Tag:
refs/tags/v0.1.0 - Owner: https://github.com/chouzz
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
publish.yml@c33618f898638095430d48f38f8a131f7131d0af -
Trigger Event:
release
-
Statement type:
File details
Details for the file remoteshell_mcp-0.1.0-py3-none-any.whl.
File metadata
- Download URL: remoteshell_mcp-0.1.0-py3-none-any.whl
- Upload date:
- Size: 14.9 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.7
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
6d36e206709999b9ad8942087cb02409e08a4f1a35b42a47a5c4979d7bb72451
|
|
| MD5 |
87abf8078df556b848451e330fdcc03c
|
|
| BLAKE2b-256 |
a6659482bf4829ba15baabd1aa8798d1a8a2deddc285ce934f48423cedb9deac
|
Provenance
The following attestation bundles were made for remoteshell_mcp-0.1.0-py3-none-any.whl:
Publisher:
publish.yml on chouzz/remoteShell-mcp
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
remoteshell_mcp-0.1.0-py3-none-any.whl -
Subject digest:
6d36e206709999b9ad8942087cb02409e08a4f1a35b42a47a5c4979d7bb72451 - Sigstore transparency entry: 699854248
- Sigstore integration time:
-
Permalink:
chouzz/remoteShell-mcp@c33618f898638095430d48f38f8a131f7131d0af -
Branch / Tag:
refs/tags/v0.1.0 - Owner: https://github.com/chouzz
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
publish.yml@c33618f898638095430d48f38f8a131f7131d0af -
Trigger Event:
release
-
Statement type: