Wednesday, October 24, 2007

» Add a directory to your PATH

As it's a recurring question, here is how to add one or more directories to your PATH (on openSUSE, but applies more or less to other distributions as well). Note that I assume you're using bash as your shell. First of all, PATH is an environment variable which is set when you log in, by a set of configuration files that augment it. Environment variables are marked as "export" and are inherited to subprocesses (e.g. if you start ls from your shell, the ls process will inherit all the exported variables from the shell process). On login (graphical through KDM, GDM or XDM, or on the console), the sequence of shell configuration files read more or less as follows (slightly simplified):
  • It starts with /etc/profile,
  • followed by every /etc/profile.d/*.sh file that is readable for your user,
  • then /etc/profile.local if it exists,
  • and finally by $HOME/.bashrc and $HOME/.profile
Every time you open a new shell (including through X terminal applications like xterm, konsole, gnome-terminal, urxvt, etc...), the shell process inherits all the environment variables that have been set on login by the files mentioned above. It then merely reads $HOME/.bashrc (which, on openSUSE, defaults to read $HOME/.profile). Now, back to PATH. First of all, you have to decide whether you want to add a directory to the PATH of your user or of all users (including root). If it's just for your own user, then apply the change to $HOME/.profile and if it's for all users, then apply the change to /etc/profile.local (and create it if needed, it doesn't by default). You may either use your favourite text editor (vim, emacs, kate, ...) or use the following shell code snippet to expand PATH, the following example being for your very own environment and hence only applies to your own user:
echo 'PATH=/opt/blah/bin:$PATH' >> ~/.profile
As you can see above, we've prepended the directory /opt/blah/bin to PATH. Make sure to use ">>" and not ">" (>> means "append", while > means "create or overwrite"). The point is, because of how bash reads configuration files on startup and how the configuration files are arranged (see above), changes made to e.g. /etc/profile.local will not be applied when you open your next X terminal application. You have to log out of your session (either X session or console session) and log in again to see the changes. Also note that as opposed to MS Windows, the change doesn't instantly apply to all open cmd.exe windows either. To avoid having to log out and in again, you may just "source" the configuration file you've modified in your existing shells and/or in the shells you open until your log out, like this: ". /etc/profile" (or "source /etc/profile") -- without the "", that is. On openSUSE (and probably on most other Linux distributions nowadays), the directory $HOME/bin is automatically added to PATH if it exists.



Blogger Paul Cobbaut said...

Don't forget that when bash is invoked, it sources the first file found in this threesome: $HOME/.bash_profile, $HOME/.bash_login and $HOME/.profile
in the home directory.

In other words, if someone creates $HOME/.bash_profile, then $HOME/.profile is no longer executed.

(man bash, search for bash_login)

Anonymous Anonymous said...

You mention in your post that you need to `export' environment variables. You then neglect to export your new PATH. :-)

Thus, your command should be:

echo 'export PATH=/opt/blah/bin:$PATH' >> ~/.profile

Blogger Loki said...

anonymous, not quite, because PATH is already marked as export in /etc/profile :)

Once a variable is marked as exported, it keeps that flag all the way down its child processes.

Paul, thanks for the addition. I tried to keep it more or less concise without going too much into the details of an interactive shell (or not), etc...

Blogger DimiG said...

Thank you


Post a Comment

<< Home