Shebang is a special line that tells the operating system which interpreter to use to execute the rest of the script. It is useful for making your files executable without specifying the interpreter from the command line like this ./my_script.sh
instead of bash my_script.sh
.
The shebang line must be the first line in the script, and it must start with #!
without any spaces or other characters before them, followed by the path to the Bash binary, such as #!/bin/bash
or #!/usr/bin/env bash
.
#!/bin/bash
# Print only the even numbers from 1 to 10
for i in {1..10}; do
if [[ $((i % 2)) -ne 0 ]]; then
continue
fi
echo $i
done
If you omit the shebang line, the system will try to guess the interpreter based on the file extension, the file content, or the default command line interpreter. However, this may not always work as expected, and it may cause errors or unexpected behavior.
The shebang syntax is not a Bash-specific feature, but a convention that is recognized by most operating systems. It’s also used in other scripting languages, such as Python, Perl, and Ruby.
#!/path/to/interpreter [optional arguments]
Here’s a breakdown of each part:
#!
: The shebang indicator. These characters must appear at the very beginning of the file./path/to/interpreter
: The absolute path to the interpreter executable that should be used to run the script. This path specifies which program will interpret and execute the script’s commands.[optional arguments]
: You can optionally provide arguments that will be passed to the interpreter when the script is executed. This is particularly useful if the interpreter supports command-line options that modify its behavior.Here are a few specific shebang lines:
#!/bin/sh
#!/bin/bash
#!/usr/bin/python3
#!/usr/bin/perl
#!/bin/bash -x
: Bash shell with the -x
option, which enables debugging modeRemember that the shebang line is used to execute the script directly from the command line. It’s important to use the correct interpreter’s path in the shebang line to ensure that the script is executed by the intended interpreter.
env
utilityAnother option for specifying the interpreter path is to use the env
utility, which can find the interpreter from the user’s PATH
environmental variable.
#!/usr/bin/env interpreter [optional arguments]
This can make the file more portable and flexible, as it does not depend on a fixed location of the interpreter. However, this may also introduce some security risks, as it allows anyone to modify the user’s PATH
and run a malicious program instead of the intended interpreter.
#!/usr/bin/env bash
#!/usr/bin/env python3
#!/usr/bin/env perl
#!/usr/bin/env -S bash -euo pipefail
The order of directories in the PATH
is significant because it determines the precedence of executables with the same name in different directories. If you have multiple versions of an interpreter installed in different directories, the one that appears earlier in the PATH
will be used.
You can view your current PATH by running the echo $PATH
command in a terminal. To modify the PATH, you can use the export command, but be cautious when making changes to avoid unintentional consequences.
#!/bin/false
The /bin/false
is a command that does nothing and always returns a non-zero exit code, which means failure. Therefore, when a script has #!/bin/false
as its shebang, it means that the script will not be executed and will always fail.
One possible reason to use is to prevent a script from being run accidentally or maliciously. For example, if a script contains some sensitive information or commands that are not meant to be executed, using #!/bin/false
can prevent someone from running the script by mistake or on purpose.
Another possible reason is to create a dummy script that can be used as a placeholder or a stub for testing purposes. For example, if a script is not yet implemented or completed, using #!/bin/false
can indicate that the script is not ready and will always fail.
However, using #!/bin/false
as a shebang may not be very user-friendly or informative, as it does not provide any feedback or explanation to the user who tries to run the script.
#!/bin/sh
You should use #!/bin/sh
when you want to write a portable shell script that can run on any system that has a POSIX-compliant shell. The #!/bin/sh
line tells the operating system to use the default system shell, which is usually a link to a POSIX-compatible shell such as bash
, dash
, ksh
, or zsh
.
By using #!/bin/sh
, you can ensure that your script will work on any system that follows the POSIX standard, regardless of the actual location or name of the shell executable.
However, using #!/bin/sh
also means that you have to stick to the features and syntax that are defined by the POSIX specification, and avoid using any extensions or enhancements that are specific to a certain shell.
For example, you cannot use arrays, associative arrays, brace expansion, or process substitution in a #!/bin/sh
script, as they are not part of the POSIX standard.
If you want to use these features, you have to use a specific shell indicate it in the shebang line.
To override the shebang line of a script, you can execute the script by explicitly specifying the interpreter you want to use on the command line. This can be useful in situations where you want to use a different interpreter than the one specified in the shebang line, or if the shebang line is incorrect or not compatible with your environment.
/path/to/interpreter script_file.sh
Replace /path/to/interpreter
with the absolute path to the interpreter you want to use or name of interpreter already available in PATH
, and script_file.sh
with the name of the script file you want to execute.
For example, if you have a script named myscript.sh
with the following shebang line:
#!/bin/bash
And you want to run it using the zsh
interpreter instead of bash
, you can do:
/usr/bin/zsh myscript.sh
This will execute the script myscript.sh
using the zsh
interpreter, regardless of the shebang line in the script.
Keep in mind that when you override the shebang line in this way, you’re explicitly specifying the interpreter for that particular execution only. The shebang line in the script itself remains unchanged, and future executions without specifying an interpreter will still use the interpreter specified in the shebang line.
Overriding the shebang line to run a script with a different interpreter than what’s specified in the script’s shebang line can carry certain risks and considerations. The script may have been written with assumptions about the behavior of a specific interpreter. Using a different interpreter might lead to unexpected behavior, errors, or incorrect results.
In general, it’s safer and more reliable to modify the shebang line in the script itself if you want to change the interpreter permanently.
Overriding the shebang line for a one-time use should be done cautiously and with an understanding of the potential risks. If you find the need to regularly run the script with a different interpreter, consider adapting the script to be more flexible and compatible across multiple interpreters.
Each interpreter has its strengths and purposes. Choose the one that matches your needs, from compatibility and simplicity to advanced features and interactivity.