* pipe_in() for "piping in" input to an external command.

* system() like os.system() except with error checking.
* getenv() to get look for a value from a list of environment variables--
  they are searched sequentially in definite order.
master
wirawan 14 years ago
parent 75d4c2240c
commit a6582aa8f2
  1. 66
      shell_tools.py

@ -1,4 +1,4 @@
# $Id: shell_tools.py,v 1.6 2010-02-19 18:40:19 wirawan Exp $
# $Id: shell_tools.py,v 1.7 2010-05-28 18:45:51 wirawan Exp $
#
# wpylib.shell_tools
# Created: 20100106
@ -70,6 +70,21 @@ def env_pop(name, old_value):
else:
os.environ[name] = old_value
def getenv(*names, **opts):
"""Tries to get a value from a list of environment variables.
The first found one will be used; if none is found, then a default will
be tried (use `default' parameter to specify this).
If no default is found, then a KeyError exception will be raised.
"""
for n in names:
if n in os.environ:
return os.environ[n]
if "default" in opts:
return opts["default"]
else:
raise KeyError, \
"Cannot find value among environment variables: %s" % (str(names))
# Low-level utilities:
def errchk(cmd, args, retcode):
@ -101,6 +116,15 @@ def quote_cmdline(seq):
rslt.append(inew)
return " ".join(rslt)
"""
pipe_out and pipe_in defines unidirectional pipes for external programs.
Note the unconventional meaning: `pipe_in' means we drive the program with
python input as the stdin, `pipe_out' means we run the program and read in
the output into python.
"""
if has_subprocess:
def run(prg, args):
@ -108,6 +132,13 @@ if has_subprocess:
errchk(prg, args, retcode)
return 0
def system(cmdline):
"""Similar to os.system(), except that errors are caught.
cmdline *must* be a string."""
retcode = subprocess.call(cmdline, shell=True)
errchk(cmdline, (), retcode)
return 0
def pipe_out(args, split=False, shell=False):
"""Executes a shell command, piping out the stdout to python for parsing.
This is my customary shortcut for backtick operator.
@ -119,6 +150,21 @@ if has_subprocess:
else:
return retval.splitlines()
class pipe_in:
"""Executes a shell command, piping in the stdin from python for driving.
This is the reverse of pipe_out.
Commands are given through file-like write() or writelines() methods."""
def __init__(self, args, shell=False):
self.px = subprocess.Popen(args, stdin=subprocess.PIPE, shell=shell)
self.args = args
def write(self, line):
self.px.stdin.write(line)
def writelines(self, lines):
for line in lines:
self.write(line)
def close(self):
self.px.stdin.close()
else:
def run(prg, args=()):
@ -127,6 +173,12 @@ else:
errchk(prg, args, retcode)
return 0
def system(cmdline):
"""Similar to os.system(), except that errors are caught."""
retcode = os.system(cmdline)
errchk(cmdline, (), retcode)
return 0
def pipe_out(args, split=False, shell=False):
"""Executes a shell command, piping out the stdout to python for parsing.
This is my customary shortcut for backtick operator.
@ -145,6 +197,18 @@ else:
else:
return retval.splitlines()
def pipe_in(args, shell=False):
"""Executes a shell command, piping in the stdin from python for driving.
This is the reverse of pipe_out.
Commands are given through file-like write() or writelines() methods."""
if shell or isinstance(args, str):
# BEWARE: args should be a string in this case
p = os.popen(args, "w")
else:
args = quote_cmdline(args)
p = os.popen(args, "w")
return p
# coreutils

Loading…
Cancel
Save