Killing python ffmpeg subprocess breaks cli output
Question: I'm trying to execute a system command with subprocess and reading the output.

But if the command takes more than 10 seconds I want to kill the subprocess.

I've tried doing this in several ways.

My last try was inspired by this post:
<http://stackoverflow.com/a/3326559/969208>

Example:

    
    
    import os
    import signal
    from subprocess import Popen, PIPE
    
    class Alarm(Exception):
        pass
    
    def alarm_handler(signum, frame):
        raise Alarm
    
    def pexec(args):
    
        p = Popen(args, stdout=PIPE, stderr=PIPE)
    
        signal.signal(signal.SIGALRM, alarm_handler)
        signal.alarm(10)
    
        stdout = stderr = ''
        try:
            stdout, stderr = p.communicate()
            signal.alarm(0)
        except Alarm:
            try:
                os.kill(p.pid, signal.SIGKILL)
            except:
                pass
    
        return (stdout, stderr)
    

The problem is: After the program exits no chars are shown in the cli until I
hit return. And hitting return will not give me a new line.

I suppose this has something to do with the stdout and stderr pipe.

I've tried flushing and reading from the pipe (p.stdout.flush())

I've also tried with different Popen args, but might've missed something. Just
thought I'd keep it simple here.

I'm running this on a Debian server.

Am I missing something here?

EDIT:

It seems this is only the case when killing an ongoing ffmpeg process. If the
ffmpeg process exits normally before 10 seconds, there is no problem at all.

I've tried executing a couple of different command that take longer than 10
seconds, one who prints output, one who doesn't and a ffmpeg command to check
the integrity of a file.

    
    
    args = ['sleep', '12s'] # Works fine
    args = ['ls', '-R', '/var'] # Works fine, prints lots for a long time
    args = ['ffmpeg', '-v', '1', '-i', 'large_file.mov','-f', 'null', '-'] # Breaks cli output
    

I believe ffmpeg prints using \r and prints everything on the strerr pipe. Can
this be the cause? Any ideas how to fix it?


Answer: Well. your code surely works fine on my Ubuntu server.

(which is close cousin or brother of Debian I suppose)

I added few more lines, so that I can test your code.

    
    
    import os
    import signal
    from subprocess import Popen, PIPE
    
    class Alarm(Exception):
        pass
    
    def alarm_handler(signum, frame):
        raise Alarm
    def pexec(args):
        p = Popen(args, stdout=PIPE, stderr=PIPE)
    
        signal.signal(signal.SIGALRM, alarm_handler)
        signal.alarm(1)
    
        stderr = ''
        try:
            stdout, stderr = p.communicate()
            signal.alarm(0)
        except Alarm:
        print "Done!"
            try:
                os.kill(p.pid, signal.SIGKILL)
            except:
                pass
    
        return (stdout, stderr)
    
    args = ('find', '/', '-name','*')
    stdout = pexec(args)
    print "----------------------result--------------------------"
    print stdout
    print "----------------------result--------------------------"
    

Works like a charm.

If this code works on your server, I guess problem actually lies on

command line application that you trying to retrieve data.

