Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
28 changes: 28 additions & 0 deletions cvs/lib/parallel_ssh_lib.py
Original file line number Diff line number Diff line change
Expand Up @@ -169,11 +169,25 @@ def exec(self, cmd, timeout=None, print_console=True):
Returns a dictionary of host as key and command output as values
"""
print(f'cmd = {cmd}')

# Log command execution
if self.log:
if timeout is not None:
self.log.debug(f"Executing command on {len(self.reachable_hosts)} host(s) [timeout={timeout}s]: {cmd}")
else:
self.log.debug(f"Executing command on {len(self.reachable_hosts)} host(s): {cmd}")

if timeout is None:
output = self.client.run_command(cmd, stop_on_errors=self.stop_on_errors)
else:
output = self.client.run_command(cmd, read_timeout=timeout, stop_on_errors=self.stop_on_errors)
cmd_output = self._process_output(output, cmd=cmd, print_console=print_console)

# Log per-host execution completion
if self.log:
for host in cmd_output.keys():
self.log.debug(f"Command completed on {host}: {cmd}")

return cmd_output

def exec_cmd_list(self, cmd_list, timeout=None, print_console=True):
Expand All @@ -183,13 +197,27 @@ def exec_cmd_list(self, cmd_list, timeout=None, print_console=True):
Returns a dictionary of host as key and command output as values
"""
print(cmd_list)

# Log command list execution
if self.log:
if timeout is not None:
self.log.debug(f"Executing command list on {len(self.reachable_hosts)} host(s) [timeout={timeout}s]")
else:
self.log.debug(f"Executing command list on {len(self.reachable_hosts)} host(s)")

if timeout is None:
output = self.client.run_command('%s', host_args=cmd_list, stop_on_errors=self.stop_on_errors)
else:
output = self.client.run_command(
'%s', host_args=cmd_list, read_timeout=timeout, stop_on_errors=self.stop_on_errors
)
cmd_output = self._process_output(output, cmd_list=cmd_list, print_console=print_console)

# Log per-host command execution
if self.log:
for host, cmd in zip(self.reachable_hosts, cmd_list):
self.log.debug(f"Command on {host}: {cmd}")

return cmd_output

def scp_file(self, local_file, remote_file, recurse=False):
Expand Down
36 changes: 24 additions & 12 deletions cvs/lib/unittests/test_parallel_ssh_lib.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,8 @@ def setUp(self, mock_pssh_client):
mock_pssh_client.return_value = self.mock_client
self.mock_pssh_client = mock_pssh_client
self.host_list = ["host1", "host2"]
self.pssh = Pssh("log", self.host_list, user="user", password="pass")
self.mock_log = MagicMock()
self.pssh = Pssh(self.mock_log, self.host_list, user="user", password="pass")

def test_exec_successful(self):
# Test: Execute command successfully on all hosts
Expand Down Expand Up @@ -89,7 +90,8 @@ def test_exec_with_pruning_unreachable_host(self, mock_check_connectivity, mock_
self.mock_client = MagicMock()
mock_pssh_client.return_value = self.mock_client
self.host_list = ["host1", "host2"]
self.pssh = Pssh("log", self.host_list, user="user", password="pass")
self.mock_log = MagicMock()
self.pssh = Pssh(self.mock_log, self.host_list, user="user", password="pass")
self.pssh.stop_on_errors = False
self.pssh.check_connectivity = mock_check_connectivity
from pssh.exceptions import ConnectionError
Expand Down Expand Up @@ -127,7 +129,8 @@ def test_exec_no_pruning_when_reachable(self, mock_check_connectivity, mock_pssh
self.mock_client = MagicMock()
mock_pssh_client.return_value = self.mock_client
self.host_list = ["host1", "host2"]
self.pssh = Pssh("log", self.host_list, user="user", password="pass")
self.mock_log = MagicMock()
self.pssh = Pssh(self.mock_log, self.host_list, user="user", password="pass")
self.pssh.stop_on_errors = False
self.pssh.check_connectivity = mock_check_connectivity
from pssh.exceptions import Timeout
Expand Down Expand Up @@ -165,7 +168,8 @@ def test_exec_pruning_with_multiple_unreachable_hosts(self, mock_check_connectiv
self.mock_client = MagicMock()
mock_pssh_client.return_value = self.mock_client
self.host_list = ["host1", "host2", "host3"]
self.pssh = Pssh("log", self.host_list, user="user", password="pass")
self.mock_log = MagicMock()
self.pssh = Pssh(self.mock_log, self.host_list, user="user", password="pass")
self.pssh.stop_on_errors = False
self.pssh.check_connectivity = mock_check_connectivity
from pssh.exceptions import ConnectionError
Expand Down Expand Up @@ -211,7 +215,8 @@ def test_exec_no_pruning_on_timeout_exception_reachable(self, mock_pssh_client,
self.mock_client = MagicMock()
mock_pssh_client.return_value = self.mock_client
self.host_list = ["host1", "host2"]
self.pssh = Pssh("log", self.host_list, user="user", password="pass")
self.mock_log = MagicMock()
self.pssh = Pssh(self.mock_log, self.host_list, user="user", password="pass")
self.pssh.stop_on_errors = False
from pssh.exceptions import Timeout

Expand Down Expand Up @@ -248,7 +253,8 @@ def test_exec_pruning_on_timeout_exception_unreachable(self, mock_pssh_client, m
self.mock_client = MagicMock()
mock_pssh_client.return_value = self.mock_client
self.host_list = ["host1", "host2"]
self.pssh = Pssh("log", self.host_list, user="user", password="pass")
self.mock_log = MagicMock()
self.pssh = Pssh(self.mock_log, self.host_list, user="user", password="pass")
self.pssh.stop_on_errors = False
from pssh.exceptions import Timeout

Expand Down Expand Up @@ -355,7 +361,8 @@ def setUp(self, mock_pssh_client):
mock_pssh_client.return_value = self.mock_client
self.mock_pssh_client = mock_pssh_client
self.host_list = ["host1", "host2"]
self.pssh = Pssh("log", self.host_list, user="user", password="pass")
self.mock_log = MagicMock()
self.pssh = Pssh(self.mock_log, self.host_list, user="user", password="pass")

def test_exec_cmd_list_successful(self):
# Test: Execute different commands on different hosts successfully
Expand Down Expand Up @@ -437,7 +444,8 @@ def test_exec_cmd_list_no_pruning_when_reachable(self, mock_check_connectivity,
self.mock_client = MagicMock()
mock_pssh_client.return_value = self.mock_client
self.host_list = ["host1", "host2"]
self.pssh = Pssh("log", self.host_list, user="user", password="pass")
self.mock_log = MagicMock()
self.pssh = Pssh(self.mock_log, self.host_list, user="user", password="pass")
self.pssh.stop_on_errors = False
self.pssh.check_connectivity = mock_check_connectivity
cmd_list = ["echo success", "echo fail"]
Expand Down Expand Up @@ -476,7 +484,8 @@ def test_exec_cmd_list_pruning_on_timeout_exception_unreachable(self, mock_check
self.mock_client = MagicMock()
mock_pssh_client.return_value = self.mock_client
self.host_list = ["host1", "host2"]
self.pssh = Pssh("log", self.host_list, user="user", password="pass")
self.mock_log = MagicMock()
self.pssh = Pssh(self.mock_log, self.host_list, user="user", password="pass")
self.pssh.stop_on_errors = False
self.pssh.check_connectivity = mock_check_connectivity
cmd_list = ["echo success", "echo fail"]
Expand Down Expand Up @@ -516,7 +525,8 @@ def test_exec_cmd_list_with_pruning(self, mock_check_connectivity, mock_pssh_cli
self.mock_client = MagicMock()
mock_pssh_client.return_value = self.mock_client
self.host_list = ["host1", "host2"]
self.pssh = Pssh("log", self.host_list, user="user", password="pass")
self.mock_log = MagicMock()
self.pssh = Pssh(self.mock_log, self.host_list, user="user", password="pass")
self.pssh.stop_on_errors = False
self.pssh.check_connectivity = mock_check_connectivity
cmd_list = ["echo success", "echo fail"]
Expand Down Expand Up @@ -554,7 +564,8 @@ def test_exec_cmd_list_pruning_with_multiple_unreachable_hosts(self, mock_check_
self.mock_client = MagicMock()
mock_pssh_client.return_value = self.mock_client
self.host_list = ["host1", "host2", "host3"]
self.pssh = Pssh("log", self.host_list, user="user", password="pass")
self.mock_log = MagicMock()
self.pssh = Pssh(self.mock_log, self.host_list, user="user", password="pass")
self.pssh.stop_on_errors = False
self.pssh.check_connectivity = mock_check_connectivity
cmd_list = ["echo success", "echo fail1", "echo fail2"]
Expand Down Expand Up @@ -603,7 +614,8 @@ def test_exec_cmd_list_no_pruning_on_connection_error_when_reachable(
self.mock_client = MagicMock()
mock_pssh_client.return_value = self.mock_client
self.host_list = ["host1", "host2"]
self.pssh = Pssh("log", self.host_list, user="user", password="pass")
self.mock_log = MagicMock()
self.pssh = Pssh(self.mock_log, self.host_list, user="user", password="pass")
self.pssh.stop_on_errors = False
self.pssh.check_connectivity = mock_check_connectivity
cmd_list = ["echo success", "echo fail"]
Expand Down
Loading