172

Is there a way to include another shell script in a shell script to be able to access its functions?

Like how in PHP you can use the include directive with other PHP files in order to run the functions that are contained within simply by calling the function name.

Anthony Miller
  • 15,101
  • 28
  • 69
  • 98
  • possible duplicate of [Bash: How _best_ to include other scripts?](http://stackoverflow.com/questions/192292/bash-how-best-to-include-other-scripts) – Troubadour May 30 '12 at 20:21
  • @Troubadour thanks for the reference. Even though the post refers to the `source` command, the question in itself is asking how to pinpoint the location of a `source` file. – Anthony Miller May 30 '12 at 20:25

5 Answers5

255

Simply put inside your script :

source FILE

Or

. FILE # POSIX compliant

$ LANG=C help source
source: source filename [arguments]
Execute commands from a file in the current shell.

Read and execute commands from FILENAME in the current shell.  The
entries in $PATH are used to find the directory containing FILENAME.
If any ARGUMENTS are supplied, they become the positional parameters
when FILENAME is executed.

Exit Status:
Returns the status of the last command executed in FILENAME; fails if
FILENAME cannot be read.
Gilles Quénot
  • 173,512
  • 41
  • 224
  • 223
  • 25
    Note that . is POSIX compliant whereas source isn't – Mathieu_Du Feb 20 '15 at 19:38
  • 1
    But here source is not exactly the include same as we do in `C` language. Here source is executing the child script into the main script. What if I just want to call a particular function from the child script? – Paresh Mayani Apr 09 '15 at 13:39
  • 12
    Don't confuse `. script.sh` with `./script.sh`. I lost hours trying to figure out what is going on – Tihomir Mitkov Jun 25 '15 at 18:17
  • 1
    While . is POSIX compliant, which means it will work on sh, dash, zsh and other POSIX shells. It's better to use . as some shells have their own, similar, but a bit different version of "source" which may break your app. – Misty Jul 13 '20 at 13:45
  • 2
    Can we consider `. other.sh` equivalent to a copy and paste of the other script into the parent script or are there any subtle differences? – Silicomancer Dec 13 '21 at 15:47
80

Above answers are correct, but if you run script in another folder, there will be some problem.

For example, a.sh and b.sh are in same folder, a use . ./b.sh to include b.

When you run script out of the folder, for example, xx/xx/xx/a.sh, file b.sh will not found: ./b.sh: No such file or directory.

So I use

. $(dirname "$0")/b.sh
Fancyoung
  • 2,313
  • 26
  • 32
  • 1
    This only works for one level of source/include. If `b.sh` further includes a `c.sh` using `. $(dirname "$0")/c.sh`, then it will fail miserably because while sourcing/including b, `$0` is the shell itself, and I am not aware of any method till date to figure out the directory of `b.sh` – Rads Jan 05 '21 at 13:01
37

Yes, use source or the short form which is just .:

. other_script.sh
Paul
  • 139,544
  • 27
  • 275
  • 264
9

Syntax is source <file-name>

ex. source config.sh

script - config.sh

USERNAME="satish"
EMAIL="satish@linuxconcept.com"

calling script -

#!/bin/bash
source config.sh
echo Welcome ${USERNAME}!
echo Your email is ${EMAIL}.

You can learn to include a bash script in another bash script here.

Satish Kumar
  • 99
  • 1
  • 2
4

In my situation, in order to include color.sh from the same directory in init.sh, I had to do something as follows.

. ./color.sh

Not sure why the ./ and not color.sh directly. The content of color.sh is as follows.

RED=`tput setaf 1`
GREEN=`tput setaf 2`
BLUE=`tput setaf 4`
BOLD=`tput bold`
RESET=`tput sgr0`

Making use of File color.sh does not error but, the color do not display. I have tested this in Ubuntu 18.04 and the Bash version is:

GNU bash, version 4.4.19(1)-release (x86_64-pc-linux-gnu)

hygull
  • 8,464
  • 2
  • 43
  • 52
Raf
  • 7,505
  • 1
  • 42
  • 59
  • That'll just give you the file in your current working directory, not the directory where `init.sh` is (they coincide if you launched it with `./init.sh` in the first place). – ricab Jun 17 '19 at 16:40