{"id":10020,"library":"parallel-ssh","title":"parallel-ssh (pssh)","description":"parallel-ssh, imported as `pssh`, is an asynchronous Python library for executing commands and transferring files over SSH to multiple hosts in parallel. It leverages `asyncio` for high-performance operations, making it suitable for managing large clusters or performing fast, concurrent remote tasks. The current version is 2.16.0.post1, and it maintains a relatively active release cadence with minor updates every few months.","status":"active","version":"2.16.0.post1","language":"en","source_language":"en","source_url":"https://github.com/ParallelSSH/parallel-ssh","tags":["ssh","parallel processing","remote execution","asyncio","automation","devops"],"install":[{"cmd":"pip install parallel-ssh","lang":"bash","label":"Install stable version"}],"dependencies":[],"imports":[{"note":"The PyPI package `parallel-ssh` is imported as `pssh`.","wrong":"from parallel_ssh.clients import ParallelSSHClient","symbol":"ParallelSSHClient","correct":"from pssh.clients import ParallelSSHClient"},{"note":"The PyPI package `parallel-ssh` is imported as `pssh`.","wrong":"from parallel_ssh.clients import SSHClient","symbol":"SSHClient","correct":"from pssh.clients import SSHClient"}],"quickstart":{"code":"import asyncio\nfrom pssh.clients import ParallelSSHClient\nimport os\n\nasync def run_remote_commands():\n    # Replace with your actual hostnames or IP addresses\n    hosts = ['hostname1', 'hostname2'] \n    \n    # You can specify username, password, or private key path\n    # client = ParallelSSHClient(hosts, user='myuser', password=os.environ.get('SSH_PASSWORD', ''))\n    # client = ParallelSSHClient(hosts, user='myuser', pkey='/path/to/id_rsa')\n    client = ParallelSSHClient(hosts, user=os.environ.get('SSH_USER', 'your_user'))\n\n    print(f\"Connecting to {hosts} and running 'ls -l /tmp'...\")\n    output = await client.run_command('ls -l /tmp')\n\n    async for host_output in output:\n        print(f\"\\n--- Host: {host_output.host} ---\")\n        print(f\"Return Code: {host_output.return_code}\")\n        print(\"Stdout:\")\n        for line in host_output.stdout:\n            print(f\"  {line}\")\n        print(\"Stderr:\")\n        for line in host_output.stderr:\n            print(f\"  {line}\")\n\nif __name__ == '__main__':\n    # Ensure your SSH_USER env var is set or replace 'your_user' directly\n    # Also, ensure SSH agents or known_hosts are configured for passwordless access\n    # or provide password/pkey arguments to ParallelSSHClient.\n    asyncio.run(run_remote_commands())\n","lang":"python","description":"This quickstart demonstrates connecting to multiple hosts using `ParallelSSHClient` and executing a command. It uses `asyncio` to run the asynchronous operations. Replace `hostname1`, `hostname2`, and `your_user` with your actual host details and username. For authentication, consider using SSH agents, `known_hosts`, or passing credentials/private key paths to the client."},"warnings":[{"fix":"Upgrade your Python environment to 3.8 or newer if you are using `parallel-ssh` version 2.13.0 or later.","message":"Python 3.8+ is now required. Support for Python versions prior to 3.8 was dropped in `parallel-ssh` version 2.13.0.","severity":"breaking","affected_versions":">=2.13.0"},{"fix":"Remove explicit calls to `SSHClient.disconnect()`. The client will handle resource cleanup automatically. Relying on explicit calls will not close the connection and may lead to resource leaks.","message":"`SSHClient.disconnect()` is a no-op since version 2.14.0. Individual `SSHClient` instances now manage their own disconnection upon de-allocation.","severity":"gotcha","affected_versions":">=2.14.0"},{"fix":"To enable compression, explicitly pass `compress=True` when initializing `SSHClient`, `ParallelSSHClient`, or `HostConfig` (e.g., `ParallelSSHClient(hosts, compress=True)`).","message":"Compression is opt-in. As of version 2.15.0, `parallel-ssh` supports compression, but it is not enabled by default for clients.","severity":"gotcha","affected_versions":">=2.15.0"},{"fix":"Always use `from pssh.clients import ParallelSSHClient` (or `import pssh`) to import the library components.","message":"The PyPI package `parallel-ssh` installs as the `pssh` Python module. Attempting to import `parallel_ssh` will result in a `ModuleNotFoundError`.","severity":"gotcha","affected_versions":"All versions"}],"env_vars":null,"last_verified":"2026-04-17T00:00:00.000Z","next_check":"2026-07-16T00:00:00.000Z","problems":[{"fix":"Change your import statements from `import parallel_ssh` (or similar) to `import pssh` or `from pssh.clients import ParallelSSHClient`.","cause":"The PyPI package `parallel-ssh` is imported as the `pssh` Python module.","error":"ModuleNotFoundError: No module named 'parallel_ssh'"},{"fix":"Ensure you are calling `parallel-ssh` methods with the `await` keyword within an `async` function, and that your main script is run via `asyncio.run()`.","cause":"`parallel-ssh` clients are asynchronous and their methods (e.g., `run_command`, `put_file`) must be `await`ed.","error":"TypeError: object NoneType can't be used in 'await' expression"},{"fix":"Verify the `user`, `password`, `pkey`, and `passphrase` arguments passed to your `SSHClient` or `ParallelSSHClient`. Ensure target hosts' public keys are correctly added to your `~/.ssh/known_hosts` file, or consider explicitly disabling strict host key checking for development (not recommended for production).","cause":"Incorrect SSH credentials (username, password, private key path), wrong private key passphrase, or issues with host key verification (`known_hosts`).","error":"[Errno -1] Authentication failed (or similar SSH authentication error messages like 'Permission denied')"},{"fix":"To enable debug mode, set the environment variable `PYTHONASYNCIODEBUG=1` before running your script, or call `asyncio.get_event_loop().set_debug(True)` early in your program.","cause":"This is a common warning from `asyncio` when debug mode is not enabled, not an error specific to `parallel-ssh`. It indicates that `asyncio` will not provide full stack traces, which can make debugging harder.","error":"RuntimeWarning: Enable asyncio debug mode to show full stack traces."}]}