Whenever I write shell scripts (mostly software development utilities or build tools) I've generally tried to avoid using bash in favor of using plain old sh for portability. However lately I've been running into more and more issues where useful features are not available, or behavior is actually less consistent across systems using sh then it is using bash, since sh is aliased to different shells...
As I understand it, sh is the oldest Unix shell and carefully written sh scripts should in theory run on pretty much any system out there... but it also seems there are about 9000 different variants of every major shell, too. Doesn't using bash as your script interpreter effectively limit your script's portability? Sure, no problems on OS X or pretty much any Linux out there, but what about the BSDs? Solaris, AIX, HP-UX? What do you do if you really want to run on everything?
I know bash can be installed on virtually any OS but it is really a first class citizen on all relevant modern systems? Does it come pre-installed? I'm just not really sure whether it's best to avoid or embrace bash with the intent of having the most consistent and portable overall experience.
What do you do if you really want to run on everything?
You follow the POSIX standard for sh
(and the tools you're calling) and hope that the target OS does so too. Any modern product called "UNIX" must follow this standard, and customarily (though not universally), the standard shell will be called /bin/sh
. The BSDs and Linux distros tend to aim at POSIX compatibility as well.
Doesn't using bash as your script interpreter effectively limit your script's portability?
Yes, but it depends on your target audience as you noted. If it's a short script, it's worth testing under dash
(Ubuntu and Debian's default shell) for POSIX compatibility.
Whenever I start thinking about portability issues in my shell script, I switch to another language. Perl is widely available and generally a good choice for scripts, but if your tools are to be consumed by Python, Ruby, $lang developers, use $lang to its full potential.
bash itself is just a plain C program, does not need special authority to run, can be put in any location. You can easily build it from source. Basically, you can run bash if you need to and doesn't need the administrator of the system to install it.
As long as it is in your path, you can always code your script with the line.
#!/usr/bin/env bash