Skip to main content
edited title
Link
Stéphane Chazelas
  • 586.9k
  • 96
  • 1.1k
  • 1.7k

How to make bash abort the a command on aan inline execution error

added 39 characters in body; edited tags
Source Link
muru
  • 78.4k
  • 16
  • 214
  • 320

Command substitution, or Inline Execution "$()"as I call it, $() in Bash allows for text returns; before the execution of a main command. How do I abort the main command, if a $() returns an error code

More specifically I want to stop/prevent a secondary Inline Execution from being attempted.

Echo $(ls /devb/*) is better than $(ls /dev/*)

i.e. if "ls /devb/" returns a non-zero exit code, I don't want to run a listing of /dev,

My real example gets to be rather wordy, and the specifics aren't super important to the question, but a simplified version is

Connect_to_foreign_system 1.1.1.1 /u:$(zenity <prompt for user>) /p:$(zenity <prompt for password>)

If the prompt for user is canceled, zenity returns with a exit code of 1, but the main command continues, and then prompts for a password.

If the first prompt errors I really don't want to prompt for the password, and it would be nice to not run Connect_to_foreign_system.

I'm not running this in a script, this is pure command-line, but even if I put it in a script with set -e both the second inline and main command, still runs anyway.

I know that I can write a script to get each text string and then run the command and test for exit-codes as I go. I'm asking how to do it as a standalone statement.

Inline Execution "$()" in Bash allows for text returns; before the execution of a main command. How do I abort the main command, if a $() returns an error code

More specifically I want to stop/prevent a secondary Inline Execution from being attempted.

Echo $(ls /devb/*) is better than $(ls /dev/*)

i.e. if "ls /devb/" returns a non-zero exit code, I don't want to run a listing of /dev,

My real example gets to be rather wordy, and the specifics aren't super important to the question, but a simplified version is

Connect_to_foreign_system 1.1.1.1 /u:$(zenity <prompt for user>) /p:$(zenity <prompt for password>)

If the prompt for user is canceled, zenity returns with a exit code of 1, but the main command continues, and then prompts for a password.

If the first prompt errors I really don't want to prompt for the password, and it would be nice to not run Connect_to_foreign_system.

I'm not running this in a script, this is pure command-line, but even if I put it in a script with set -e both the second inline and main command, still runs anyway.

I know that I can write a script to get each text string and then run the command and test for exit-codes as I go. I'm asking how to do it as a standalone statement.

Command substitution, or Inline Execution as I call it, $() in Bash allows for text returns; before the execution of a main command. How do I abort the main command, if a $() returns an error code

More specifically I want to stop/prevent a secondary Inline Execution from being attempted.

Echo $(ls /devb/*) is better than $(ls /dev/*)

i.e. if "ls /devb/" returns a non-zero exit code, I don't want to run a listing of /dev,

My real example gets to be rather wordy, and the specifics aren't super important to the question, but a simplified version is

Connect_to_foreign_system 1.1.1.1 /u:$(zenity <prompt for user>) /p:$(zenity <prompt for password>)

If the prompt for user is canceled, zenity returns with a exit code of 1, but the main command continues, and then prompts for a password.

If the first prompt errors I really don't want to prompt for the password, and it would be nice to not run Connect_to_foreign_system.

I'm not running this in a script, this is pure command-line, but even if I put it in a script with set -e both the second inline and main command, still runs anyway.

I know that I can write a script to get each text string and then run the command and test for exit-codes as I go. I'm asking how to do it as a standalone statement.

Rollback to Revision 4
Source Link
Ed Morton
  • 36k
  • 6
  • 25
  • 60

Inline Execution, or Command Substitution, Inline Execution "$()" in Bash allows for text returns; before the execution of a main command. How do I abort the main command, if a $() returns an error code

I know that I can write a script to get each text string and then run the command and test for exit-codes as I go. I'm asking how to do it as a standalone statement.


EDIT: for those who don't have Connect_to_foreign_system and zenity, the problem being asked about above can be demonstrated with:

$ cat tst.sh
#!/usr/bin/env bash

a="${1:-0}"
b="${2:-0}"

trc()  { printf 'Executed: %s\n' "${FUNCNAME[1]} $*" >&2; }
main() { trc "$*"; }
foo()  { trc "$*"; return "$1"; }
bar()  { trc "$*"; return "$1"; }

main "$(foo "$a")" "$(bar "$b")"

where the 2 arguments that are used to populate a and b set the exit status for the calls to foo() and bar() respectively:

$ ./tst.sh 0 0
Executed: foo 0
Executed: bar 0
Executed: main

$ ./tst.sh 1 0
Executed: foo 1
Executed: bar 0
Executed: main

and the the OP stated the problem they're asking for help with as:

I want to stop/prevent a secondary Inline Execution from being attempted. ... I know that I can write a script to get each text string and then run the command and test for exit-codes as I go. I'm asking how to do it as a standalone statement.

i.e. how can they write a standalone statement that includes command substituions, like the existing call to main() above, but that will not execute the call to bar() if the call to foo() fails and not execute the call to main() if either foo() or bar() fails?

Inline Execution, or Command Substitution, "$()" in Bash allows for text returns; before the execution of a main command. How do I abort the main command, if a $() returns an error code

I know that I can write a script to get each text string and then run the command and test for exit-codes as I go. I'm asking how to do it as a standalone statement.


EDIT: for those who don't have Connect_to_foreign_system and zenity, the problem being asked about above can be demonstrated with:

$ cat tst.sh
#!/usr/bin/env bash

a="${1:-0}"
b="${2:-0}"

trc()  { printf 'Executed: %s\n' "${FUNCNAME[1]} $*" >&2; }
main() { trc "$*"; }
foo()  { trc "$*"; return "$1"; }
bar()  { trc "$*"; return "$1"; }

main "$(foo "$a")" "$(bar "$b")"

where the 2 arguments that are used to populate a and b set the exit status for the calls to foo() and bar() respectively:

$ ./tst.sh 0 0
Executed: foo 0
Executed: bar 0
Executed: main

$ ./tst.sh 1 0
Executed: foo 1
Executed: bar 0
Executed: main

and the the OP stated the problem they're asking for help with as:

I want to stop/prevent a secondary Inline Execution from being attempted. ... I know that I can write a script to get each text string and then run the command and test for exit-codes as I go. I'm asking how to do it as a standalone statement.

i.e. how can they write a standalone statement that includes command substituions, like the existing call to main() above, but that will not execute the call to bar() if the call to foo() fails and not execute the call to main() if either foo() or bar() fails?

Inline Execution "$()" in Bash allows for text returns; before the execution of a main command. How do I abort the main command, if a $() returns an error code

I know that I can write a script to get each text string and then run the command and test for exit-codes as I go. I'm asking how to do it as a standalone statement.

this bit is just distracting nonsense
Source Link
muru
  • 78.4k
  • 16
  • 214
  • 320
Loading
added the term Command Subtitutuib to orginal question
Source Link
Loading
added 4 characters in body
Source Link
Ed Morton
  • 36k
  • 6
  • 25
  • 60
Loading
added 1125 characters in body
Source Link
Ed Morton
  • 36k
  • 6
  • 25
  • 60
Loading
added 137 characters in body
Source Link
Loading
added 2 characters in body
Source Link
Loading
added 1 character in body
Source Link
Loading
Source Link
Loading