The sarge package provides a wrapper for subprocess which provides command pipeline functionality.

Related tags

Documentationsarge
Overview

Overview

The sarge package provides a wrapper for subprocess which provides command pipeline functionality.

This package leverages subprocess to provide easy-to-use cross-platform command pipelines with a Posix flavour: you can have chains of commands using ;, &, pipes using | and |&, and redirection.

Requirements & Installation

The sarge package requires Python 2.6 or greater, and can be installed with the standard Python installation procedure:

python setup.py install

There is a set of unit tests which you can invoke with:

python setup.py test

before running the installation.

Availability & Documentation

The latest version of sarge can be found on GitHub.

The latest documentation (kept updated between releases) is on Read The Docs:

Please report any problems or suggestions for improvement either via the mailing list or the issue tracker.

Comments
  • problem with run async=true & returncodes  .....

    problem with run async=true & returncodes .....

    Hi

    below code always return [0, 0, None] and command never finish : seems have problem with sleep ...

    cmd = 'echo "Hello " && sleep 2  && echo "Finish " '
    p = run(cmd, async_=True)
    
    opened by Maziar123 19
  • hang with redirection

    hang with redirection

    Original report by Anonymous.


    When using redirection that leads to an ioerror, sarge can hang waiting for spawned processes that will never complete due to waiting on a full pipe that no one is reading.

    A simple test case:

    #!python
    
    import sarge
    pipeline = sarge.run('head -c 65K /dev/zero | cat > /does/not/exist')
    
    

    The first command hangs on a write to the pipe, which is never closed and sarge hangs on a wait() for this process that will never finish.

    bug major 
    opened by vsajip 13
  • Retcode is 0 using shell=True

    Retcode is 0 using shell=True

    Original report by Dmitry Malinovsky (Bitbucket: malinoff, GitHub: malinoff).


    In [1]: from sarge import run
    
    In [2]: p = run('exit 1', shell=True)
    
    In [3]: p.returncode
    Out[3]: 0
    
    bug major 
    opened by vsajip 11
  • ValueError: need more than 2 values to unpack

    ValueError: need more than 2 values to unpack

    Original report by Allan Lei (Bitbucket: allanlei, GitHub: allanlei).


    I get this error for any commands I run.

    • Windows 7 Pro 64
    • Python 2.7.6 (default, Nov 10 2013, 19:24:24) [MSC v.1500 64 bit (AMD64)] on win32
    • pip install sarge==0.1.2

    Simple run

    #!python
    
    sarge.run('echo abc')
    

    Trying the test_sarge.py script from repo

    #!bash
    
    PS C:\Users\allan.lei\Desktop> python test_sarge.py
    E.EEEEE.E...EEE..EEEEEEEE....EException in thread Thread-3:
    Traceback (most recent call last):
      File "C:\Python27\lib\threading.py", line 810, in __bootstrap_inner
        self.run()
      File "C:\Python27\lib\threading.py", line 763, in run
        self.__target(*self.__args, **self.__kwargs)
      File "C:\Python27\lib\site-packages\sarge\__init__.py", line 1055, in run_node
        result = getattr(self, method)(node, input, async)
      File "C:\Python27\lib\site-packages\sarge\__init__.py", line 1201, in run_command_node
        node.cmd.run(input=input, async=async)
      File "C:\Python27\lib\site-packages\sarge\__init__.py", line 593, in run
        self.process = p = Popen(self.args, **self.kwargs)
      File "C:\Python27\lib\subprocess.py", line 701, in __init__
        errread, errwrite), to_close = self._get_handles(stdin, stdout, stderr)
      File "C:\Python27\lib\site-packages\sarge\__init__.py", line 481, in _get_handles
        stderr)
    ValueError: need more than 2 values to unpack
    
    Exception in thread Thread-4:
    Traceback (most recent call last):
      File "C:\Python27\lib\threading.py", line 810, in __bootstrap_inner
        self.run()
      File "C:\Python27\lib\threading.py", line 763, in run
        self.__target(*self.__args, **self.__kwargs)
      File "C:\Python27\lib\site-packages\sarge\__init__.py", line 1055, in run_node
        result = getattr(self, method)(node, input, async)
      File "C:\Python27\lib\site-packages\sarge\__init__.py", line 1289, in run_list_node
        self.run_node(curr, input, async=use_async)
      File "C:\Python27\lib\site-packages\sarge\__init__.py", line 1055, in run_node
        result = getattr(self, method)(node, input, async)
      File "C:\Python27\lib\site-packages\sarge\__init__.py", line 1201, in run_command_node
        node.cmd.run(input=input, async=async)
      File "C:\Python27\lib\site-packages\sarge\__init__.py", line 593, in run
        self.process = p = Popen(self.args, **self.kwargs)
      File "C:\Python27\lib\subprocess.py", line 701, in __init__
        errread, errwrite), to_close = self._get_handles(stdin, stdout, stderr)
      File "C:\Python27\lib\site-packages\sarge\__init__.py", line 481, in _get_handles
        stderr)
    ValueError: need more than 2 values to unpack
    
    bug major 
    opened by vsajip 11
  • shell_quote(

    shell_quote("'ab?'") should return '"\'ab?\'"', not "'ab?'"

    Original report by David Lowe (Bitbucket: [David D Lowe](https://bitbucket.org/David D Lowe), ).


    Current behaviour:

    >>> shell_quote("'ab?'")
     "'ab?'"
    >>> print(shell_quote("'ab?'"))
    'ab?'
    

    Expected behaviour:

     >>> shell_quote("'ab?'")
     '"\'ab?\'"'
     >>> print(shell_quote("'ab?'"))
     "'ab?'"
    

    For example, to create a file named 'ab?', that is, a filename that consists of a single quote character, the a character, the b character, the ? character and the single quote character, in bash you would type the following:

     $ touch "'ab?'"
    

    And not the following:

     $ touch 'ab?'
    
    bug major 
    opened by vsajip 11
  • Use capture_both with Feeder

    Use capture_both with Feeder

    Original report by Jeet Ray (Bitbucket: shadowrylander, GitHub: shadowrylander).


    Hello! Would it be possible to use the feeder with capture_both? I would like to store the result in a variable until I can display or return it manually! My current code is something like this:

    from sarge import Feeder, get_stdout, capture_both
    
    feeder = Feeder()
    for line in capture_both("cowsay", input=feeder, async_=True).stdout:
        print(line.decode("utf-8").rstrip())
    feeder.feed(get_stdout("fortune"))
    feeder.close()
    

    Thank you kindly for the help!

    enhancement minor 
    opened by vsajip 9
  • Unstable/inconsistent behaviour of progress.py example code

    Unstable/inconsistent behaviour of progress.py example code

    Original report by CDuv (Bitbucket: CDuv, GitHub: CDuv).


    In want to use the sarge library to execute a simple cmd1 | cmd2 shell command from my Python script an grab it's output (both stdout and stderr) live while the shell command executes. I was previously using subprocess.Popen() + subprocess.PIPE + communicate() but the output was buffered.

    As a working base I tested the progress.py code detailed in the tutorial.

    File "test_sarge_live.py":

    import optparse # because of 2.6 support
    import sys
    import threading
    import time
    import logging
    
    from sarge import capture_stdout
    
    logging.basicConfig(level=logging.DEBUG, filename='/tmp/test_sarge_live.log',
                        filemode='w', format='%(asctime)s %(threadName)-10s %(name)-15s %(lineno)4d %(message)s')
    
    def progress(capture, options):
        lines_seen = 0
        messages = {
            'line 25\n': 'Getting going ...\n',
            'line 50\n': 'Well on the way ...\n',
            'line 75\n': 'Almost there ...\n',
        }
        while True:
            s = capture.readline()
            if not s and lines_seen:
                break
            if options.dots:
                sys.stderr.write('.')
            else:
                msg = messages.get(s)
                if msg:
                    sys.stderr.write(msg)
            lines_seen += 1
        if options.dots:
            sys.stderr.write('\n')
        sys.stderr.write('Done - %d lines seen.\n' % lines_seen)
    
    def main():
        parser = optparse.OptionParser()
        parser.add_option('-n', '--no-dots', dest='dots', default=True,
                          action='store_false', help='Show dots for progress')
        options, args = parser.parse_args()
    
        #~ p = capture_stdout('ncat -k -l -p 42421', async=True)
        p = capture_stdout('python lister.py -d 0.1 -c 100', async=True)
    
        t = threading.Thread(target=progress, args=(p.stdout, options))
        t.start()
    
        while(p.returncodes[0] is None):
            # We could do other useful work here. If we have no useful
            # work to do here, we can call readline() and process it
            # directly in this loop, instead of creating a thread to do it in.
            p.commands[0].poll()
            time.sleep(0.05)
        t.join()
    
    if __name__ == '__main__':
        sys.exit(main())
    

    But running it gives very inconsistent output:

    On Ubuntu v16.04 using Python v2.7.12 and sarge v0.1.4 I get theses (at random):

    • This ('NoneType' object has no attribute 'returncode' + sys.excepthook is missing)
    Traceback (most recent call last):
    File "test_sarge_live.py", line 55, in <module>
      sys.exit(main())
    File "test_sarge_live.py", line 46, in main
      while(p.returncodes[0] is None):
    File "/usr/local/lib/python2.7/dist-packages/sarge/__init__.py", line 1072, in returncodes
      result = [c.process.returncode for c in self.commands]
    AttributeError: 'NoneType' object has no attribute 'returncode'
    ..
    Done - 2 lines seen.
    close failed in file object destructor:                                                                                                                                                                                                                         
    sys.excepthook is missing
    lost sys.stderr
    
    • Or also this (no 'NoneType' object has no attribute 'returncode')
    close failed in file object destructor:
    sys.excepthook is missing
    lost sys.stderr
    
    • Or even this:
    Traceback (most recent call last):
    .  File "test_sarge_live.py", line 55, in <module>
      
    sys.exit(main())Done - 1 lines seen.
    
    File "test_sarge_live.py", line 46, in main
      while(p.returncodes[0] is None):
    IndexError: list index out of range
    Exception in thread Thread-1 (most likely raised during interpreter shutdown):
    Traceback (most recent call last):
    File "/usr/lib/python2.7/threading.py", line 801, in __bootstrap_inner
    File "/usr/lib/python2.7/threading.py", line 754, in run
    File "/usr/local/lib/python2.7/dist-packages/sarge/__init__.py", line 1136, in run_node
    File "/usr/local/lib/python2.7/dist-packages/sarge/__init__.py", line 1282, in run_command_node
    File "/usr/local/lib/python2.7/dist-packages/sarge/__init__.py", line 656, in run
    File "/usr/lib/python2.7/threading.py", line 585, in set
    File "/usr/lib/python2.7/threading.py", line 407, in notifyAll
    <type 'exceptions.TypeError'>: 'NoneType' object is not callable
    
    • And sometimes this no failure output:
    .
    Done - 1 lines seen.
    

    I also tested on Docker container Debian v9.4 using Python v2.7.13 and sarge v0.1.4: I get the same outputs.

    When I kill (via [Ctrl]+[C]) one instance and immediately run the script again I get:

    .Traceback (most recent call last):
      File "test_sarge_live.py", line 55, in <module>
        sys.exit(main())
      File "test_sarge_live.py", line 46, in main
        while(p.returncodes[0] is None):
    IndexError: list index out of range
    
    Done - 1 lines seen.
    Exception in thread Thread-1 (most likely raised during interpreter shutdown):
    Traceback (most recent call last):
      File "/usr/lib/python2.7/threading.py", line 801, in __bootstrap_inner
      File "/usr/lib/python2.7/threading.py", line 754, in run
      File "/usr/local/lib/python2.7/dist-packages/sarge/__init__.py", line 1136, in run_node
      File "/usr/local/lib/python2.7/dist-packages/sarge/__init__.py", line 1282, in run_command_node
      File "/usr/local/lib/python2.7/dist-packages/sarge/__init__.py", line 656, in run
      File "/usr/lib/python2.7/threading.py", line 585, in set
      File "/usr/lib/python2.7/threading.py", line 407, in notifyAll
    <type 'exceptions.TypeError'>: 'NoneType' object is not callable
    [email protected]:/app# close failed in file object destructor:
    sys.excepthook is missing
    lost sys.stderr
    

    but I think this is normal.

    Is the tutorial code still accurate?

    bug minor 
    opened by vsajip 9
  • Inconsistent behavior with async=True

    Inconsistent behavior with async=True

    Original report by Dmitry Malinovsky (Bitbucket: malinoff, GitHub: malinoff).


    Hi,

    I found that I can't specify sleep n call before any other command (including another sleep n call) without waiting for it using async=True. Is it expected behavior?

    This works as expected:

    In [1]: from sarge import run
    
    In [2]: p = run('echo abc | cat && sleep 5', async=True)
    # Returns immediately
    abc
    
    In [3]: p.commands[-1].poll()
    
    In [4]: p.commands[-1].poll()
    Out[4]: 0
    
    

    This is not:

    In [5]: p = run('sleep 5 && echo abc | cat', async=True)
    # Hangs for 5 seconds
    abc
    
    
    bug major 
    opened by vsajip 9
  • Capturing output from an infinite cycle

    Capturing output from an infinite cycle

    Original report by Dmitry Malinovsky (Bitbucket: malinoff, GitHub: malinoff).


    Hi,

    I tried to run a simple script: run_forever.py

    import time
    
    i = 0
    while True:
        time.sleep(1)
        print(i)
        i += 1
    

    with sarge as described in the docs:

    In [1]: import sarge
    
    In [2]: p = sarge.run('python run_forever.py', async=True, stdout=sarge.Capture())
    

    However, I can't capture the output:

    In [3]: p.stdout.readline()
    Out[3]: b''
    
    In [4]: p.commands[0].stdout.readline()
    Out[4]: b''
    

    Am I doing it wrong? How can I achieve that?

    bug major 
    opened by vsajip 8
  • `shell_format` work incorrect on windows.

    `shell_format` work incorrect on windows.

    Original report by pahaz NA (Bitbucket: pahaz, GitHub: pahaz).


    from sarge import shell_shlex, shell_format
    import shlex
    import subprocess
    
    cmd = shell_format("python -c {0}", "print('aw')")
    print(cmd)
    

    This code produse:

    C:\Users\pahaz_000>C:\Python27\python.exe z.py
    python -c 'print('\''aw'\'')'
    

    And on windows whis in incorrect:

    C:\Users\pahaz_000\PycharmProjects\dokku>python -c 'print('\''aw'\'')'
      File "<string>", line 1
        'print('\''aw'\'')'
                          ^
    SyntaxError: unexpected character after line continuation character
    

    On linux correct:

    (venv)[email protected]:/vagrant# python -c 'print('\''aw'\'')'
    aw
    
    bug major 
    opened by vsajip 7
  • Child process stdout seems to be getting closed unexpectedly

    Child process stdout seems to be getting closed unexpectedly

    Original report by Paul Moore (Bitbucket: pmoore, GitHub: pmoore).

    The original report had attachments: yada.py, yadatest.py


    I wanted to use sarge to read process output line by line. As a small test case I created the attached files, yada.py and yadatest.py. The yada.py script writes its argument repeatedly, with a user-specified delay between each write. Standard output is flushed after each write. Used at the command line, this works as expected.

    The yadatest script exercises yada.py via sarge, capturing stdout and displaying each line as it is received. Again, stdout is flushed after each write.

    The yadatest script runs for a while (about 5 seconds) with no output, and then fails with the following error:

    #!python
    
    >python .\yadatest.py
    Traceback (most recent call last):
      File "yada.py", line 11, in <module>
        print(args.text, flush=True)
    OSError: [Errno 22] Invalid argument
    Exception OSError: OSError(22, 'Invalid argument') in <_io.TextIOWrapper name='<stdout>' mode='w' encoding='cp1252'> ignored
    0 foo
    

    Did something close my child process' stdout? Note that there is no "Error encountered" message, implying that the failure was in the child, not in the parent.

    bug minor 
    opened by vsajip 7
  • ENH: Equivalent to subprocess.check_output

    ENH: Equivalent to subprocess.check_output

    Original report by Wes Turner (Bitbucket: westurner, GitHub: westurner).


    Is there a (easy) way to raise an Exception if the returncode is not (by default?) 0?

    enhancement major 
    opened by vsajip 18
Releases(0.1.7.post1)
Owner
Vinay Sajip
I'm a developer experienced in desktop & Web development. I'm a Python committer - I implemented stdlib logging, venv and the Windows Python launcher.
Vinay Sajip
learn python in 100 days, a simple step could be follow from beginner to master of every aspect of python programming and project also include side project which you can use as demo project for your personal portfolio

learn python in 100 days, a simple step could be follow from beginner to master of every aspect of python programming and project also include side project which you can use as demo project for your

BDFD 6 Nov 05, 2022
Beautiful static documentation generator for OpenAPI/Swagger 2.0

Spectacle The gentleman at REST Spectacle generates beautiful static HTML5 documentation from OpenAPI/Swagger 2.0 API specifications. The goal of Spec

Sourcey 1.3k Dec 13, 2022
Pystm32ai - A Python wrapper for the stm32ai command-line tool

PySTM32.AI A python wrapper for the stm32ai command-line tool to analyse deep le

Thibaut Vercueil 5 Jul 28, 2022
Paper and Code for "Curriculum Learning by Optimizing Learning Dynamics" (AISTATS 2021)

Curriculum Learning by Optimizing Learning Dynamics (DoCL) AISTATS 2021 paper: Title: Curriculum Learning by Optimizing Learning Dynamics [pdf] [appen

Tianyi Zhou 15 Dec 06, 2022
Que es S4K Builder?, Fácil un constructor de tokens grabbers con muchas opciones, como BTC Miner, Clipper, shutdown PC, Y más! Disfrute el proyecto. <3

S4K Builder Este script Python 3 de código abierto es un constructor del muy popular registrador de tokens que está en [mi GitHub] (https://github.com

SadicX 1 Oct 22, 2021
Convenient tools for using Swagger to define and validate your interfaces in a Pyramid webapp.

Convenient tools for using Swagger to define and validate your interfaces in a Pyramid webapp.

Scott Triglia 64 Sep 18, 2022
DataRisk Detection Learning Resources

DataRisk Detection Learning Resources Data security: Based on the "data-centric security system" position, it generally refers to the entire security

Liao Wenzhe 59 Dec 05, 2022
Reproducible Data Science at Scale!

Pachyderm: The Data Foundation for Machine Learning Pachyderm provides the data layer that allows machine learning teams to productionize and scale th

Pachyderm 5.7k Dec 29, 2022
graphical orbitational simulation of solar system planets with real values and physics implemented so you get a nice elliptical orbits. you can change timestamp value or scale from source code idc.

solarSystemOrbitalSimulation graphical orbitational simulation of solar system planets with real values and physics implemented so you get a nice elli

Mega 3 Mar 03, 2022
DocumentPy is a Python application that runs in a command-line interface environment, made for creating HTML documents.

DocumentPy DocumentPy is a Python application that runs in a command-line interface environment, made for creating HTML documents. Usage DocumentPy, a

Lotus 0 Jul 15, 2021
Data science on SDGs - Udemy Online Course Material: Data Science on Sustainable Development Goals

Data Science on Sustainable Development Goals (SDGs) Udemy Online Course Material: Data Science on Sustainable Development Goals https://bit.ly/data_s

Frank Kienle 1 Jan 04, 2022
:blue_book: Automatic documentation from sources, for MkDocs.

mkdocstrings Automatic documentation from sources, for MkDocs. Features - Python handler - Requirements - Installation - Quick usage Features Language

1.1k Jan 04, 2023
NoVmpy - NoVmpy with python

git clone -b dev-1 https://github.com/wallds/VTIL-Python.git cd VTIL-Python py s

263 Dec 23, 2022
30 days of Python programming challenge is a step-by-step guide to learn the Python programming language in 30 days

30 days of Python programming challenge is a step-by-step guide to learn the Python programming language in 30 days. This challenge may take more than100 days, follow your own pace.

Asabeneh 17.7k Jan 07, 2023
Hjson for Python

hjson-py Hjson, a user interface for JSON Hjson works with Python 2.5+ and Python 3.3+ The Python implementation of Hjson is based on simplejson. For

Hjson 185 Dec 13, 2022
freeCodeCamp Scientific Computing with Python Project for Certification.

Polygon_Area_Calculator freeCodeCamp Python Project freeCodeCamp Scientific Computing with Python Project for Certification. In this project you will

Rajdeep Mondal 1 Dec 23, 2021
CoderByte | Practice, Tutorials & Interview Preparation Solutions|

CoderByte | Practice, Tutorials & Interview Preparation Solutions This repository consists of solutions to CoderByte practice, tutorials, and intervie

Eda AYDIN 6 Aug 09, 2022
Data Inspector is an open-source python library that brings 15++ types of different functions to make EDA, data cleaning easier.

Data Inspector Data Inspector is an open-source python library that brings 15 types of different functions to make EDA, data cleaning easier. Author:

Kazi Amit Hasan 38 Nov 24, 2022
sphinx builder that outputs markdown files.

sphinx-markdown-builder sphinx builder that outputs markdown files Please ★ this repo if you found it useful ★ ★ ★ If you want frontmatter support ple

Clay Risser 144 Jan 06, 2023
An introduction to hikari, complete with different examples for different command handlers.

An intro to hikari This repo provides some simple examples to get you started with hikari. Contained in this repo are bots designed with both the hika

Ethan Henderson 18 Nov 29, 2022