How should I set the PATH variable on my Mac so the Hombrew-installed tools are found?
I found this related post to be very helpful. Instead of changing the $PATH
variable, it just has you simply edit your /etc/paths
file.
Homebrew wants me to amend my PATH; no clue how
As soon as I followed the directions and put /usr/local/bin
above /usr/bin
, my issues were resolved.
- On OS X, open Terminal
- Type the command:
sudo vi /etc/paths
- Enter your password if you're asked for it
- You will see a list of paths. Edit them so that
/usr/local/bin
path is entered above the/usr/bin
path - *Save and quit
- Restart Terminal
Here's what mine looks like after I did that:
/usr/local/bin
/usr/bin
/bin
/usr/sbin
/sbin
*To save and quit type a colon (:
), then type wq
(to write and quit at the same time), followed by Enter.
You can also open the /etc/paths
file in a graphical text editor and edit it that way.
Credit to fengd over at Stack Overflow for his answer over there.
This answer is obsolete. The preferred Homebrew PATH
ordering used to be as explained, but that is no longer true. However, the approach is more generally applicable, so for interest’s sake, I’m leaving it up.
You shouldn’t.
Homebrew intentionally keeps /usr/local/bin
after /usr/bin
in the path for maximum compatibility. Reversing the order of these directories in PATH
by editing /etc/paths
would mean that all programs anywhere on the system, no matter how they were started, will get the Homebrew version of a command. But some may specifically expect Apple’s version, or just not be able to use a newer version, etc.
How to preserve this principle and still get the Homebrew-installed version of git
? As the saying goes, all problems can be solved with a layer of indirection (except having too many layers of indirection). — Or in this case, as it turns out, two layers.
Specifically, it’s been part of my Unix habits to have a ~/bin
directory which I put at the start of my PATH
. This is one of the first bits in my .bashrc
:
[[ :$PATH: == *:$HOME/bin:* ]] || PATH=$HOME/bin:$PATH
This checks whether PATH
contains ~/bin
, and if not, prepends it. With that in place, then selectively making just the Homebrew-managed git
take precedence over the system version (instead of every Homebrew-managed binary), and just for your shell sessions (instead of all programs started from anywhere, including GUI programs), is as simple as symlinking it:
ln -s /usr/local/bin/git ~/bin/git
You could symlink /usr/local/Cellar/git/1.8.2.1/bin/git
directly, but then you would have to fix your symlink every time you did a brew upgrade git
(directly or indirectly). By symlinking to Homebrew’s fixed-location symlink, you don’t have to worry about it.
So you add a directory to your $HOME
so you can add it your PATH
so you can symlink to a symlink, and that fixes your problem and puts a smile on Dr Seuss. Yo dawg I herd you like symlinks so we put a path in your PATH
so you can symlink while you symlink.
You haven't done anything wrong, but it does seem pretty clear that if you had /usr/local/bin
in your path before /usr/bin
this specific problem would go away. The easiest fix is to do just that and put something like
export PATH=/usr/local/bin:$PATH
in your ~/.bash_profile
so everything that Homebrew installs is found first. That's the way that I have it set up on my Mac, and it has worked for me for this long, however, YMMV.
It does appear that they believe it would work with /usr/local/bin
being after /usr/bin
, so while I might have mucked up my own $PATH
, I can see where their documentation lacks:
Note that you should put
/usr/local/bin
after/usr/bin
because some programs will expect to get the system version of, e.g., ruby, and break if they get the newer Homebrew version.
From Discrepancy between wiki & brew doctor #10738.
Note that this document goes on to say,
"The FAQ (the above quote) refers to the PATH setting for GUI apps;
the doctor (the advice to put /usr/local/bin
ahead of /usr/bin
in your PATH) refers to the PATH setting for CLI apps."
I disagree with jthomas' answer. Editing your /etc/paths file will change the load paths for all programs. This could be dangerous if a system application is expecting to find a specific version of a binary but finds a different version because you have edited your paths file. Instead, change your path variable in ~/.bashrc (or ~/.bash_profile). Then your load path will only change inside the terminal:
# Add homebrew app to PATH
export PATH=/path/to/homebrew/app/bin:$PATH
Then reload bash or source ~/.bashrc
, and you're good to go. Since the homebrew path comes before anything else, bash will load the version that you downloaded with homebrew.
As I understand it, brew
doesn't put anything in /usr/local/bin
that collides (has the same name as) an Apple distributed executable. Therefore, having /usr/local/bin
in the path before /bin
and /usr/bin
shouldn't be an issue, because there should be no name collisions. *However, see the issues with ls
and tar
, and using other package aggregators like fink
and port
(MacPorts), way below.
Brew
does one of two things that I know of that help manage name collisions:
-
Brew
leaves unlinked kegs in the Cellar. To install stuff, brew leaves the tools where they are, and creates symbolic links to those tools in/usr/local/bin
. For tools whichbrew
doesn't want a name collision with, it doesn't create a symbolic link. -
For many if not all of the standard tools which are also in
/bin
and/usr/bin
,brew
prefixes the link in/usr/local/bin
with a "g", so for instance, to perform anls
with a brew version, usegls
. Simply do anls -l
in/usr/local/bin
and look for the linked files - those are the onesbrew
put there. Note: Thebrew
installed tools that must be accessed by their real names are found in/usr/local/Cellar/coreutils/8.21/libexec/gnubin
.
I don't put /usr/local/bin
in my path for two reasons - those reasons are at the bottom of my answer.
To assess the name collisions in your system, use brew doctor
and look for this section -
Here's the brew doctor
's output of interest:
Warning: /usr/bin occurs before /usr/local/bin
This means that system-provided programs will be used instead of those
provided by Homebrew. The following tools exist at both paths:
ctags
emacs
emacsclient
etags
ex
git
git-cvsserver
git-receive-pack
git-shell
git-upload-archive
git-upload-pack
rview
rvim
view
vim
vimdiff
vimtutor
xxd
Consider setting your PATH so that /usr/local/bin
occurs before /usr/bin. Here is a one-liner:
echo export PATH='/usr/local/bin:$PATH' >> ~/.bash_profile
The reason I don't put brew
's tools first, in fact, not at all, is because the brew
installed ls
and tar
commands do not handle the filesystem ACL properly, in fact, last time I checked (which was last week), they weren't handled at all. This is a BIG problem, and to avoid it altogether, along with the associated man
page configuration issue that tags along with setting the $PATH
right, I make sure I put the OSX
related tools, especially those found in /bin
and /usr/bin
, first.
Another reason I don't even put /usr/local/bin
in my path at all is because brew
doesn't play well with others, and fink
and port
(MacPorts) have way more supported packages at present that I need NOW. For instance, I can get gnome-terminal
with fink
, but it would be a big effort to construct a formula and do the same with brew
. So, I keep /sw
and /opt
in my search $PATH
(for fink
and port
, respectively) and reference things I need from /usr/local/bin
, including gnat
, either spelled out, or I use bash
alias
's, or I source a setup
file for an entirely different environment when I writing Ada
code.
The thing is, it really depends on what you want and need at the time.
Here's an example of the ACL problem that I mentioned above.
With the standard OSX
tools:
$ /bin/ls -le /var/root | head -7
total 24
drwx------+ 3 root wheel 102 May 28 2013 Desktop
0: group:everyone deny delete
1: user:_spotlight inherited allow list,search,readattr,readextattr,readsecurity,file_inherit,directory_inherit
drwx------+ 6 root wheel 204 Sep 19 14:22 Documents
0: group:everyone deny delete
1: user:_spotlight inherited allow list,search,readattr,readextattr,readsecurity,file_inherit,directory_inherit
and with the brew
installed tools:
$ /usr/local/bin/gls -le /var/root
/usr/local/bin/gls: invalid option -- 'e'
Try '/usr/local/bin/gls --help' for more information.
and
$ /usr/local/bin/gls --help | grep -i acl
You'll get similar results with tar
and I don't know home many other brew
tools, but who can afford to have something break 6 months down the road because of an ACL
problem!