camayoc.command module¶
Execute local or remote commands.
-
class
camayoc.command.Command(system, response_handler=None)[source]¶ Bases:
objectA convenience class for working with local or remote commands.
This class provides the ability to execute shell commands on either the local system or a remote system. Here is a pedagogic usage example:
>>> from camayoc import command >>> system = command.System(hostname='localhost', transport='local') >>> cmd = command.Command(system) >>> response = cmd.run(('echo', '-n', 'foo')) >>> response.returncode == 0 True >>> response.stdout == 'foo' True >>> response.stderr == '' True
The above example shows how various classes fit together. It’s also verbose: smartly chosen defaults mean that most real code is much more concise.
You can customize how
Commandobjects execute commands and handle responses by fiddling with the two public instance attributes:machine- A Plumbum machine.
run()delegates all command execution responsibilities to this object. response_handler- A callback function. Each time
machineexecutes a command, the result is handed to this callback, and the callback’s return value is handed to the user.
If
system.transportislocalorssh,machinewill be set so that commands run locally or over SSH, respectively. Ifsystem.transportisNone, the constructor will guess how to setmachineby comparing the hostname embedded insystem.hostnameagainst the current system’s hostname. If they match,machineis set to execute commands locally; and vice versa.Parameters: - system (camayoc.command.System) – Information about the system on which commands will be executed.
- response_handler – A callback function. Defaults to
camayoc.command.code_handler().
-
run(args, **kwargs)[source]¶ Run a command and
return self.response_handler(result).This method is a thin wrapper around Plumbum’s BaseCommand.run method, which is itself a thin wrapper around the standard library’s subprocess.Popen class. See their documentation for detailed usage instructions. See
camayoc.command.Commandfor a usage example.
-
class
camayoc.command.CompletedProcess(args, returncode, stdout, stderr)[source]¶ Bases:
objectA process that has finished running.
This class is similar to the
subprocess.CompletedProcessclass available in Python 3.5 and above. Significant differences include the following:- All constructor arguments are required.
check_returncode()returns a custom exception, notsubprocess.CalledProcessError.
All constructor arguments are stored as instance attributes.
Parameters: - args – A string or a sequence. The arguments passed to
camayoc.command.Command.run(). - returncode – The integer exit code of the executed process. Negative for signals.
- stdout – The standard output of the executed process.
- stderr – The standard error of the executed process.
-
check_returncode()[source]¶ Raise an exception if
returncodeis non-zero.Raise
camayoc.exceptions.CalledProcessErrorifreturncodeis non-zero.Why not raise
subprocess.CalledProcessError? Because stdout and stderr are not included when str() is called on a CalledProcessError object. A typical message is:"Command '('ls', 'foo')' returned non-zero exit status 2"This information is valuable. One could still make
subprocess.CalledProcessErrorwork by overloadingargs:>>> if isinstance(args, (str, bytes)): ... custom_args = (args, stdout, stderr) ... else: ... custom_args = tuple(args) + (stdout, stderr) >>> subprocess.CalledProcessError(args, returncode)
But this seems like a hack.
In addition, it’s generally good for an application to raise expected exceptions from its own namespace, so as to better abstract away dependencies.
-
class
camayoc.command.System(hostname, transport)¶ Bases:
tupleA system representation to run commands on.
-
hostname¶ Alias for field number 0
-
transport¶ Alias for field number 1
-
-
camayoc.command.code_handler(completed_proc)[source]¶ Check the process for a non-zero return code. Return the process.
Check the return code by calling
completed_proc.check_returncode(). See:camayoc.command.CompletedProcess.check_returncode().