DEV Community

Cover image for Keep Your OS Clean with $HOME/.local
Nathan Fritz
Nathan Fritz

Posted on • Edited on

Keep Your OS Clean with $HOME/.local

In a *nix environment (Linux, MacOS, WSL), software without packages can sometimes install to global spaces by default. This is often undesirable, due to running unverified scripts as root, conflicts with other packages, and potentially breaking the software during an OS upgrade. Instead, these custom installs should be placed in your home directory. In my case, $HOME is /home/fritzy or /Users/fritzy on MacOS.

But where in your $HOME? As the title implies, $HOME/.local.

This directory is a GNOME convention that other software has adopted as well. Similar to /usr/local, it is designated for custom or non-package installed software. The . at the beginning of the directory name has the added benefit of hiding the directory, preventing cluttering an often-used space.

Setting up $HOME/.local

If it doesn't exist, go ahead and create it, along with a bin directory as your user. No special permissions are needed.

mkdir -p $HOME/.local/bin
Enter fullscreen mode Exit fullscreen mode

Then, make sure that $HOME/.local/bin is in your $PATH, preferably with a higher priority than /usr/bin.

For Linux Bash users do:

echo PATH=$HOME/local.bin:\$PATH >> $HOME/.bashrc
Enter fullscreen mode Exit fullscreen mode

Custom Installers

Now we can install some software. I wanted to install Starship, a cross-shell prompt in my WSL2 Ubuntu. The only documented way to install this is to install by directly executing a download -- questionable from a security perspective.

curl -fsSL https://starship.rs/install.sh | bash
Enter fullscreen mode Exit fullscreen mode

Instead, I downloaded and inspected the script. I discovered a few things. By default, it would install to /usr/bin, a global space requiring root access. But there was good news; I found a command-line option to set the install directory.

curl  https://starship.rs/install.sh --output install.sh # download
chmod +x install.sh # make it executable
./install.sh -b $HOME/.local/bin # the -b option is what discovered
rm ./install.sh # don't need this anymore
Enter fullscreen mode Exit fullscreen mode

I then followed the instructions for setting up Starship for Bash.

echo 'eval "$(starship init bash)"' >> $HOME/.bashrc
Enter fullscreen mode Exit fullscreen mode

Custom Compiled Installs (Node.js)

If you build custom software, you'll want to find the "prefix" option, and set it to $HOME/.local. When following build instructions, you should ignore anything that tells you to use sudo when installing; you won't need it with a prefix in your home directory, and doing so may cause problems later.

Let's clone Node.js, compile it, and install it to our .local prefix.

Checking Out

cd ~/build # I use a build directory for custom compiling
git clone git@github.com:nodejs/node.git
cd node
Enter fullscreen mode Exit fullscreen mode

Updating Tags

git fetch --all --tags # update fetched branches and tags
git tag # lists tags
Enter fullscreen mode Exit fullscreen mode

As an aside, if you want to sort tags with semver logic, you can update your git config.

git config --global tag.sort version:refname
Enter fullscreen mode Exit fullscreen mode

Checkout a Tag As a Branch

git checkout tags/v15.8.0 -b build-v15.8.0
Enter fullscreen mode Exit fullscreen mode

Configure and Compile

Now we can compile it.

./configure --prefix=$HOME/.local
make -j12 # number of hardware thread on my cpu
make install # sets everything up in your prefix directory
Enter fullscreen mode Exit fullscreen mode

The first make line will take a bit, but hey, you look really busy and smart when you're compiling code.

Now when you run node -V, it'll show your newly install Node.js version. You also now have the added benefit of being able to install 'global' npm packages without sudo. You'll notice that you now have include lib and share directories in your $HOME/.local, just like you would with a /usr/local prefix.

You can get similar benefits of using nvm without having to compile.

Keep It Clean

Installing unpackaged software in your $HOME/.local directory is more secure, more stable across OS upgrades, and prevents unnecessary root usage going forward. It can take a bit of investigation with some software, but is worth having a cleaner install in the end. Ideally, the vast majority of your software simply uses OS supported packages, but now you have a plan for when it doesn't.

For you MacOS users, OS upgrades would regularly break Brew for me, but you can even install Brew into your home directory.


Please comment below, or send me your thoughts on Twitter @fritzy.

Top comments (0)