| Index: third_party/pexpect/pexpect/run.py
|
| diff --git a/third_party/pexpect/pexpect/run.py b/third_party/pexpect/pexpect/run.py
|
| new file mode 100644
|
| index 0000000000000000000000000000000000000000..d9dfe76ba585446e2864e1c9caa4e4490baf420f
|
| --- /dev/null
|
| +++ b/third_party/pexpect/pexpect/run.py
|
| @@ -0,0 +1,157 @@
|
| +import sys
|
| +import types
|
| +
|
| +from .exceptions import EOF, TIMEOUT
|
| +from .pty_spawn import spawn
|
| +
|
| +def run(command, timeout=30, withexitstatus=False, events=None,
|
| + extra_args=None, logfile=None, cwd=None, env=None, **kwargs):
|
| +
|
| + '''
|
| + This function runs the given command; waits for it to finish; then
|
| + returns all output as a string. STDERR is included in output. If the full
|
| + path to the command is not given then the path is searched.
|
| +
|
| + Note that lines are terminated by CR/LF (\\r\\n) combination even on
|
| + UNIX-like systems because this is the standard for pseudottys. If you set
|
| + 'withexitstatus' to true, then run will return a tuple of (command_output,
|
| + exitstatus). If 'withexitstatus' is false then this returns just
|
| + command_output.
|
| +
|
| + The run() function can often be used instead of creating a spawn instance.
|
| + For example, the following code uses spawn::
|
| +
|
| + from pexpect import *
|
| + child = spawn('scp foo user@example.com:.')
|
| + child.expect('(?i)password')
|
| + child.sendline(mypassword)
|
| +
|
| + The previous code can be replace with the following::
|
| +
|
| + from pexpect import *
|
| + run('scp foo user@example.com:.', events={'(?i)password': mypassword})
|
| +
|
| + **Examples**
|
| +
|
| + Start the apache daemon on the local machine::
|
| +
|
| + from pexpect import *
|
| + run("/usr/local/apache/bin/apachectl start")
|
| +
|
| + Check in a file using SVN::
|
| +
|
| + from pexpect import *
|
| + run("svn ci -m 'automatic commit' my_file.py")
|
| +
|
| + Run a command and capture exit status::
|
| +
|
| + from pexpect import *
|
| + (command_output, exitstatus) = run('ls -l /bin', withexitstatus=1)
|
| +
|
| + The following will run SSH and execute 'ls -l' on the remote machine. The
|
| + password 'secret' will be sent if the '(?i)password' pattern is ever seen::
|
| +
|
| + run("ssh username@machine.example.com 'ls -l'",
|
| + events={'(?i)password':'secret\\n'})
|
| +
|
| + This will start mencoder to rip a video from DVD. This will also display
|
| + progress ticks every 5 seconds as it runs. For example::
|
| +
|
| + from pexpect import *
|
| + def print_ticks(d):
|
| + print d['event_count'],
|
| + run("mencoder dvd://1 -o video.avi -oac copy -ovc copy",
|
| + events={TIMEOUT:print_ticks}, timeout=5)
|
| +
|
| + The 'events' argument should be either a dictionary or a tuple list that
|
| + contains patterns and responses. Whenever one of the patterns is seen
|
| + in the command output, run() will send the associated response string.
|
| + So, run() in the above example can be also written as:
|
| +
|
| + run("mencoder dvd://1 -o video.avi -oac copy -ovc copy",
|
| + events=[(TIMEOUT,print_ticks)], timeout=5)
|
| +
|
| + Use a tuple list for events if the command output requires a delicate
|
| + control over what pattern should be matched, since the tuple list is passed
|
| + to pexpect() as its pattern list, with the order of patterns preserved.
|
| +
|
| + Note that you should put newlines in your string if Enter is necessary.
|
| +
|
| + Like the example above, the responses may also contain a callback, either
|
| + a function or method. It should accept a dictionary value as an argument.
|
| + The dictionary contains all the locals from the run() function, so you can
|
| + access the child spawn object or any other variable defined in run()
|
| + (event_count, child, and extra_args are the most useful). A callback may
|
| + return True to stop the current run process. Otherwise run() continues
|
| + until the next event. A callback may also return a string which will be
|
| + sent to the child. 'extra_args' is not used by directly run(). It provides
|
| + a way to pass data to a callback function through run() through the locals
|
| + dictionary passed to a callback.
|
| +
|
| + Like :class:`spawn`, passing *encoding* will make it work with unicode
|
| + instead of bytes. You can pass *codec_errors* to control how errors in
|
| + encoding and decoding are handled.
|
| + '''
|
| + if timeout == -1:
|
| + child = spawn(command, maxread=2000, logfile=logfile, cwd=cwd, env=env,
|
| + **kwargs)
|
| + else:
|
| + child = spawn(command, timeout=timeout, maxread=2000, logfile=logfile,
|
| + cwd=cwd, env=env, **kwargs)
|
| + if isinstance(events, list):
|
| + patterns= [x for x,y in events]
|
| + responses = [y for x,y in events]
|
| + elif isinstance(events, dict):
|
| + patterns = list(events.keys())
|
| + responses = list(events.values())
|
| + else:
|
| + # This assumes EOF or TIMEOUT will eventually cause run to terminate.
|
| + patterns = None
|
| + responses = None
|
| + child_result_list = []
|
| + event_count = 0
|
| + while True:
|
| + try:
|
| + index = child.expect(patterns)
|
| + if isinstance(child.after, child.allowed_string_types):
|
| + child_result_list.append(child.before + child.after)
|
| + else:
|
| + # child.after may have been a TIMEOUT or EOF,
|
| + # which we don't want appended to the list.
|
| + child_result_list.append(child.before)
|
| + if isinstance(responses[index], child.allowed_string_types):
|
| + child.send(responses[index])
|
| + elif (isinstance(responses[index], types.FunctionType) or
|
| + isinstance(responses[index], types.MethodType)):
|
| + callback_result = responses[index](locals())
|
| + sys.stdout.flush()
|
| + if isinstance(callback_result, child.allowed_string_types):
|
| + child.send(callback_result)
|
| + elif callback_result:
|
| + break
|
| + else:
|
| + raise TypeError("parameter `event' at index {index} must be "
|
| + "a string, method, or function: {value!r}"
|
| + .format(index=index, value=responses[index]))
|
| + event_count = event_count + 1
|
| + except TIMEOUT:
|
| + child_result_list.append(child.before)
|
| + break
|
| + except EOF:
|
| + child_result_list.append(child.before)
|
| + break
|
| + child_result = child.string_type().join(child_result_list)
|
| + if withexitstatus:
|
| + child.close()
|
| + return (child_result, child.exitstatus)
|
| + else:
|
| + return child_result
|
| +
|
| +def runu(command, timeout=30, withexitstatus=False, events=None,
|
| + extra_args=None, logfile=None, cwd=None, env=None, **kwargs):
|
| + """Deprecated: pass encoding to run() instead.
|
| + """
|
| + kwargs.setdefault('encoding', 'utf-8')
|
| + return run(command, timeout=timeout, withexitstatus=withexitstatus,
|
| + events=events, extra_args=extra_args, logfile=logfile, cwd=cwd,
|
| + env=env, **kwargs)
|
|
|