4

I am trying to use popen to kick off a subprocess that calls two commands (with multiple arguements) one after the other. The second command relies on the first command running, so I was hoping to use a single subprocess to run both rather than spawning two processes and wait on the first.

But I am running into issues because I am not sure how to give two command inputs or to seperate the command as one single object.

Also, I am trying to avoid setting shell to true if possible.

This is essentially, what I am trying to do:

for test in resources:
    command = [
        'pgh',
        'resource',
        'create',
        '--name', test['name'],
        '--description', test['description'],
    ]
    command2 = [
        'pgh',
        'assignment',
        'create',
        '--name', test['name'],
        '--user', test['user'],
    ]


    p = Popen(command, stdout=PIPE, stderr=PIPE)
    stdout, stderr = p.communicate()
    print(stdout)
    print(stderr)
Pectus Excavatum
  • 3,593
  • 16
  • 47
  • 68
  • Could you be a bit more specific what the problem is? What prevents you from calling `Popen` a second time with `command2`? – Yourstruly Jun 20 '17 at 09:37
  • I was hoping to use the same process since ithe commands need to be called sequentially, so one subprocess to run both commands one after the other, rather than multiple subprocesses – Pectus Excavatum Jun 20 '17 at 09:47
  • Should the question be **"sequential"** not "synchronous" then? – Baldrickk Jun 20 '17 at 09:57

2 Answers2

1

You will have to launch command and wait for completion before launching another command. You should do this repeatedly for each command.

This can be done as

ps = [ Popen(c, stdout=PIPE, stderr=PIPE).communicate() 
       for c in command]

Note that this launches the next command irrespective of weather the first command succeeded or failed. If you want to launch the next command only if the previous command succeds then use

def check_execute(commands):
    return_code = 0
    for c in commands:
        p = Popen(c, stdout=PIPE, stderr=PIPE)
        result = p.communicate()
        yield result
        return_code = p.returncode
        if return_code != 0:
            break
shanmuga
  • 4,329
  • 2
  • 21
  • 35
1

As per my understanding the following should work for you. To chain the execution once the previous completes use.

p1 = subprocess.Popen(command, stdout=subprocess.PIPE)
p2 = subprocess.Popen(command2, stdin=p1.stdout, stdout=subprocess.PIPE)
print p2.communicate()
RoshP
  • 19
  • 1
  • 5