4

I have a python script which is a little unstable and gives an SSL error every now and then. The exception is raised by some function buried deep within some library so there is essentially no fix to it.

I have implemented a hacky solution by creating a shell script with a while loop that runs a large number of times and executing the python script from within that loop.

Now what I'm hoping is that as an iteration of the loop starts and the script is executed, the loop inside the shell script stays where it is until the python script fails and the next iteration of the loop re-executes the script and so on.

Is doing it like this efficient? Is there a better way to do it? and most importantly is it correct?

  • 1
    Why can't you catch the exception, fix the script or fix the library? – MatthewRock Sep 29 '16 at 10:48
  • This doesn't sound very secure. Are you using a recent version of Python 3? – PM 2Ring Sep 29 '16 at 13:42
8

In:

cmd1
cmd2

or

cmd1; cmd2

They are executed sequentially.

In

cmd1 && cmd2

Or

cmd1 || cmd2

They are executed sequentially but whether cmd2 is executed at all depends on whether cmd1 succeeds (for &&) or fails (for ||).

In

cmd1 | cmd2

or

cmd1 & cmd2
cmd1 |& cmd2 # ksh
coproc cmd1; cmd2 # bash/zsh

or

cmd1 <(cmd2) # ksh/zsh/bash (also yash though with a different meaning)

They are executed concurrently. In the first case, some shells only wait for cmd2 before carrying on with the rest of the script while some wait for both. In the second case, shells only wait for cmd2 (cmd1 is said to be run asynchronously (or in background when run in an interactive shell)) and in the third for cmd1 (cmd2 asynchronous).

In:

< "$(cmd1)" x=$(cmd2) y=$(cmd3) cmd4 "$(cmd5)" > "$(cmd6)"

Commands are run sequentially, but the order depends on the shell. In any case, cmd4 will be executed last.

In:

cmd1 =(cmd2) # zsh

They are executed sequentially (cmd2 first).

Note that in all those cases, any of those commands could start other processes. The shell would have no knowledge of them so can't possibly wait for them.

1

Yes. It is correct. Consider this:

#!/bin/bash

while true; do
    sleep 1
    echo "Slept 1"
    echo "Exit status $?, ok."
    sleep 1
    echo "Slept 1, now executing faulty command 'ps q'"
    ps q
    echo "Exit status $?, not ok. Loop continues forever..."
done

...will look like this when executed:

./loop.sh 
Slept 1
Exit status 0, ok.
Slept 1, now executing faulty command 'ps q'
ps: illegal option -- q
usage: ps [-AaCcEefhjlMmrSTvwXx] [-O fmt | -o fmt] [-G gid[,gid...]]
          [-u]
          [-p pid[,pid...]] [-t tty[,tty...]] [-U user[,user...]]
       ps [-L]
Exit status 1, not ok. Loop continues forever...
Slept 1
Exit status 0, ok.
Slept 1, now executing faulty command 'ps q'
ps: illegal option -- q
usage: ps [-AaCcEefhjlMmrSTvwXx] [-O fmt | -o fmt] [-G gid[,gid...]]
          [-u]
          [-p pid[,pid...]] [-t tty[,tty...]] [-U user[,user...]]
       ps [-L]
Exit status 1, not ok. Loop continues forever...
^C

As long as the loop is always true it does not matter which exit codes the programs inside the loop have. They will continue to execute in the sequence they are written.

Is doing it like this efficient? Is there a better way to do it?

The best way to do it would be to squash the bug in your Python program!

0

To answer your title question: Yes, commands in a shell script are executed synchronously in sequence, so the shell is blocked while your Python script is running.

It certainly would be better to fix the source of the error, but if that's not an option a shell script that will try to run the python script until it returns a zero status code (while true;do ./script.py; if [[ "$?" = 0]];break;done) is a sensible approach.

  • 1
    Note that programs exist that start threads or childs to continue in the background. – rudimeier Sep 29 '16 at 10:29

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.