[Top][All Lists]

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Revisiting Error handling (errexit)

From: Yair Lenga
Subject: Re: Revisiting Error handling (errexit)
Date: Fri, 8 Jul 2022 13:52:04 +0300


Thanks for time to take a look at my proposal. I believe that you brought
an excellent question - which many readers will be asking themselves. I
opted for longer answer - given the importance of this questions.

While you can achieve results similar to 'errfail' with existing bash
commands (you will need more than && !), the required effort is not
* Consider a common scenario (for me) - a script with 1000 lines, complex
logic, commands than span multiple lines - there is no practical way to
review the scripts, and enter the '&&' into hundreds of lines - in the hope
of not breaking anything, including scripts that generate code on the fly
(The 'evil' eval :-).
* While '&&' works for simple sequences, sometimes the functionality that
is needed require injecting 'break', 'return', etc. See example below.
* To reality (at least for me) is that most developers who are making
changes to my bash scripts are not bash experts, In many cases, they are
wrapping functionality from other languages into a process. They do not
have the knowledge, expertise and patience to implement the above
constructs correctly.

Item #1 and #3 above are not purely technical items - but are real issues.
Without being too philosophical, I would argue that the lack of easy to
implement error handling in bash (which I hope to address with the
errfail), lot of teams (and companies) are opting out of bash, into a much
more complex solutions for simple "glue" job. Even in cases, where the
ideal solution is bash. I've seen many 100 lines pythons scripts written to
implement a 10 line bash script - just because because they could not
figure out to make bash script handle errors consistently.

On the technical aspect - using '&&' vs 'errfail'. Consider the above
example where the "copy logic" is embedded in a while (or for) loop, the
desired behavior in those cases is usually to "break" to enclosing loop. To
implement it, you will need something like below:

function copy-files {
    for f in f1 f2 f3 ; do
        cp ... && cp ... && cp ... && important-job || break
} ;

And for the original function, if you do not use errfail, you will need in
inject a 'return' in the RIGHT place (see below). I think that this level
of detailed implementation will hurt the productivity of using bash for
glue jobs.

Hope it make sense.


function copy-files {
     # ALL files are critical, script will not cont
     cp /new/file1 /production/path/ &&
     cp /new/file2 /production/path/ &&
     # Use the files for something - e.g., count the lines.
     important-job /production/path/file1 /production/path/file2  || return

     ls -l /production/path | mail -s "all-good" notify@company.com

On Fri, Jul 8, 2022 at 1:22 PM Oğuz <oguzismailuysal@gmail.com> wrote:

> 8 Temmuz 2022 Cuma tarihinde Yair Lenga <yair.lenga@gmail.com> yazdı:
>> Practical Example - real life. A job has to copy 3 critical data files. It
>> then sends notification via email (non-critical).
>> #! /bin/bash
>> set -o errfail
>> function copy-files {
>>      # ALL files are critical, script will not cont
>>      cp /new/file1 /production/path/
>>      cp /new/file2 /production/path/
>>      # Use the files for something - e.g., count the lines.
>>      important-job /production/path/file1 /production/path/file2
>>      ls -l /production/path | mail -s "all-good" notify@company.com ||
>> true    # Not critical
>> }
>> if copy-files ; then
>>      more-critical-jobs
>>       echo "ALL GOOD"
>> else
>>       mail -s "PROBLEM" norify@company.com < /dev/null
>> fi
>> What is the difference ? consider the case where /new/file1 does not
>> exists, which is critical error.
>> * Without errfail, an error message will be sent to script stderr, but the
>> script will continue to copy the 2nd file, and to perform the
>> important-job, even though the data is not ready.
> How is this any better than doing `cp ... && cp ... && important-job ...'?
> --
> Oğuz

reply via email to

[Prev in Thread] Current Thread [Next in Thread]